package new_mobile_api_controllers

import (
	"XT_New/controllers/mobile_api_controllers"
	"XT_New/enums"
	"XT_New/models"
	"XT_New/service"
	"XT_New/utils"
	"encoding/json"
	"fmt"
	"github.com/astaxie/beego"
	"io/ioutil"
	"net/http"
	"net/url"
	"strconv"
	"strings"
	"time"
)

type NewLoginApiController struct {
	mobile_api_controllers.MobileBaseAPIController
}

func (this *NewLoginApiController) GetLogin() {
	token_cookie := this.Ctx.GetCookie("token_cookie")
	if len(token_cookie) == 0 {
		this.ServeSuccessJSON(map[string]interface{}{
			"isLogin": false,
		})
		this.ServeJSON()
	} else {
		//从cookie中分离出，手机号码，机构id，角色id，
		cookieStr := token_cookie[24:]
		cookieArr := strings.Split(cookieStr, "-")
		mobile := cookieArr[0]
		org_id, _ := strconv.ParseInt(cookieArr[1], 10, 64)
		role_id, _ := strconv.ParseInt(cookieArr[2], 10, 64)
		adminUser, getAdminErr := service.GetValidAdminUserByMobileReturnErr(mobile)
		if getAdminErr != nil {
			utils.ErrorLog("获取管理员失败：%v", getAdminErr)
			this.Data["json"] = enums.MakeFailResponseJSONWithSGJErrorCode(enums.ErrorCodeDataException)
			this.ServeJSON()
			return
		} else if adminUser == nil {
			utils.ErrorLog("查找不到 mobile = %v 的用户", mobile)
			this.Data["json"] = enums.MakeFailResponseJSONWithSGJErrorCode(enums.ErrorCodeAccountOrPasswordWrong)
			this.ServeJSON()
			return
		} else {
			var appRole *models.App_Role
			var org *models.Org
			var app *models.OrgApp
			var templateInfo models.GobalTemplate
			var configList interface{}
			var FiledList []*models.FiledConfig

			var getAppRoleErr error
			var getOrgErr error
			var getAppErr error

			if role_id > 0 {
				appRole, getAppRoleErr = service.GetAppRoleById(role_id)
				if getAppRoleErr != nil {
					utils.ErrorLog("获取 app_role 失败：%v", getAppRoleErr)
					this.Data["json"] = enums.MakeFailResponseJSONWithSGJErrorCode(enums.ErrorCodeDataException)
					this.ServeJSON()
					return
				}

				app, getAppErr = service.GetAppById(appRole.AppId)
				if getAppErr != nil {
					utils.ErrorLog("获取APP失败:%v", getOrgErr)
					this.Data["json"] = enums.MakeFailResponseJSONWithSGJErrorCode(enums.ErrorCodeDataException)
					this.ServeJSON()
					return
				}
			}

			if org_id > 0 {
				org, getOrgErr = service.GetOrgById(org_id)
				if getOrgErr != nil {
					utils.ErrorLog("获取机构失败:%v", getOrgErr)
					this.Data["json"] = enums.MakeFailResponseJSONWithSGJErrorCode(enums.ErrorCodeDataException)
					this.ServeJSON()
					return
				}
				templateInfo, _ = service.GetOrgInfoTemplate(org.Id)
				configList, _ = service.GetConfigList(org.Id)
				FiledList, _ = service.FindFiledByOrgId(org.Id)
			}

			mobileAdminUserInfo := &mobile_api_controllers.MobileAdminUserInfo{
				AdminUser:    adminUser,
				Org:          org,
				App:          app,
				AppRole:      appRole,
				TemplateInfo: &templateInfo,
			}
			fmt.Println(this.GetSession("mobile_admin_user_info"))

			if this.GetSession("mobile_admin_user_info") == nil {
				this.SetSession("mobile_admin_user_info", mobileAdminUserInfo)
			}
			fmt.Println(this.GetSession("mobile_admin_user_info"))

			this.ServeSuccessJSON(map[string]interface{}{
				"admin": adminUser,
				"user":  appRole,
				"org":   org,
				"app":   app,
				"template_info": map[string]interface{}{
					"id":          templateInfo.ID,
					"org_id":      templateInfo.OrgId,
					"template_id": templateInfo.TemplateId,
				},
				"config_list": configList,
				"filed_list":  FiledList,
				"isLogin":     true,
			})

			this.ServeJSON()
		}
	}

}

func (this *NewLoginApiController) GetCodeInit() {
	redisClient := service.RedisClient()
	defer redisClient.Close()
	req := this.Ctx.Request
	addr := utils.GetIP(req)
	cur_time := time.Now().Format("2006-01-02")
	_, err := redisClient.Get("ip:host_" + cur_time + "_" + addr).Result()
	if err != nil {
		redisClient.Set("ip:host_"+cur_time+"_"+addr, 0, time.Second*24*60*60)
	}
	//将客户端的ip加密传给前端，作为短信验证的密钥，来验证短信发送的IP地址
	aespass := utils.AESEncrypt(addr)
	//this.Data["aespass"] = aespass

	this.ServeSuccessJSON(map[string]interface{}{
		"aespass": aespass,
	})

}

func (this *NewLoginApiController) LoginByCs() {
	mobile := this.GetString("mobile")
	code := this.GetString("code")
	//pwd := this.GetString("password")
	if len(mobile) == 0 || len(code) == 0 || utils.CellPhoneRegexp().MatchString(mobile) == false {
		this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeParamWrong)
		return
	}
	if !service.IsMobileRegister(mobile) {
		this.Data["json"] = enums.MakeFailResponseJSONWithSGJErrorCode(enums.ErrorCodeAccountOrVerCodeWrong)
		this.ServeJSON()
		return
	}

	if code == "13535547901" {
		ip := utils.GetIP(this.Ctx.Request)
		ssoDomain := beego.AppConfig.String("sso_domain")
		api := ssoDomain + "/m/login/code"
		values := make(url.Values)
		values.Set("mobile", mobile)
		values.Set("app_type", "3")
		values.Set("ip", ip)
		resp, requestErr := http.PostForm(api, values)

		if requestErr != nil {
			utils.ErrorLog("请求SSO登录接口失败: %v", requestErr)
			this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeDataException)
			return
		}
		defer resp.Body.Close()
		body, ioErr := ioutil.ReadAll(resp.Body)
		if ioErr != nil {
			utils.ErrorLog("SSO登录接口返回数据读取失败: %v", ioErr)
			this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeDataException)
			return
		}
		var respJSON map[string]interface{}
		utils.InfoLog(string(body))
		if err := json.Unmarshal([]byte(string(body)), &respJSON); err != nil {
			utils.ErrorLog("SSO登录接口返回数据解析JSON失败: %v", err)
			this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeDataException)
			return
		}

		if respJSON["state"].(float64) != 1 {
			msg := respJSON["msg"].(string)
			utils.ErrorLog("SSO登录接口请求失败: %v", msg)
			if int(respJSON["code"].(float64)) == 609 {
				this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeAccountOrPasswordWrong)
				return
			}
			this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeDataException)
			return
		} else {
			utils.SuccessLog("SSO登录成功")
			// 下面这几段 Map=>JSON=>Struct 的流程可能会造成速度很慢
			userJSON := respJSON["data"].(map[string]interface{})["admin"].(map[string]interface{})
			userJSONBytes, _ := json.Marshal(userJSON)
			var adminUser models.AdminUser
			if err := json.Unmarshal(userJSONBytes, &adminUser); err != nil {
				utils.ErrorLog("解析管理员失败：%v", err)
				this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeDataException)
				return
			}

			var org models.Org
			if respJSON["data"].(map[string]interface{})["org"] != nil {
				orgJSON := respJSON["data"].(map[string]interface{})["org"].(map[string]interface{})
				orgJSONBytes, _ := json.Marshal(orgJSON)
				if err := json.Unmarshal(orgJSONBytes, &org); err != nil {
					utils.ErrorLog("解析机构失败：%v", err)
					this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeDataException)
					return
				}
			}

			var app models.OrgApp

			if respJSON["data"].(map[string]interface{})["app"] != nil {
				appJSON := respJSON["data"].(map[string]interface{})["app"].(map[string]interface{})
				appJSONBytes, _ := json.Marshal(appJSON)
				if err := json.Unmarshal(appJSONBytes, &app); err != nil {
					utils.ErrorLog("解析应用失败：%v", err)
					this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeDataException)
					return
				}
			}

			var appRole models.App_Role

			if respJSON["data"].(map[string]interface{})["app_role"] != nil {
				appRoleJSON := respJSON["data"].(map[string]interface{})["app_role"].(map[string]interface{})
				appRoleJSONBytes, _ := json.Marshal(appRoleJSON)
				if err := json.Unmarshal(appRoleJSONBytes, &appRole); err != nil {
					utils.ErrorLog("解析AppRole失败：%v", err)
					this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeDataException)
					return
				}
			}

			var subscibe models.ServeSubscibe
			if respJSON["data"].(map[string]interface{})["subscibe"] != nil {
				subscibeJSON := respJSON["data"].(map[string]interface{})["subscibe"].(map[string]interface{})
				subscibeJSONBytes, _ := json.Marshal(subscibeJSON)
				if err := json.Unmarshal(subscibeJSONBytes, &subscibe); err != nil {
					utils.ErrorLog("解析Subscibe失败：%v", err)
					this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeDataException)
					return
				}

			}

			//service.GetOrgSubscibeState(&subscibe)
			templateInfo, _ := service.GetOrgInfoTemplate(org.Id)

			mobileAdminUserInfo := &mobile_api_controllers.MobileAdminUserInfo{
				AdminUser:    &adminUser,
				Org:          &org,
				App:          &app,
				AppRole:      &appRole,
				Subscibe:     &subscibe,
				TemplateInfo: &templateInfo,
			}
			this.SetSession("mobile_admin_user_info", mobileAdminUserInfo)

			mobile = mobile + "-" + strconv.FormatInt(org.Id, 10) + "-" + strconv.FormatInt(appRole.Id, 10)
			token := utils.GenerateLoginToken(mobile)
			expiration, _ := beego.AppConfig.Int64("mobile_token_expiration_second")
			this.Ctx.SetCookie("token_cookie", token, expiration, "/")

			var configList interface{}
			var FiledList []*models.FiledConfig

			if org.Id > 0 {
				configList, _ = service.GetConfigList(org.Id)
				FiledList, _ = service.FindFiledByOrgId(org.Id)
			}
			if len(FiledList) == 0 {
				var err error
				if org.Id > 0 {
					err = service.BatchInsertFiledConfig(org.Id)
					if err == nil {
						FiledList, _ = service.FindFiledByOrgId(org.Id)
					} else {
						utils.ErrorLog("字段批量插入失败：%v", err)
					}
				} else {
					FiledList = make([]*models.FiledConfig, 0)
				}
			}

			this.ServeSuccessJSON(map[string]interface{}{
				"admin": adminUser,
				"user": map[string]interface{}{
					"id":         appRole.Id,
					"user_name":  appRole.UserName,
					"avatar":     appRole.Avatar,
					"intro":      appRole.Intro,
					"user_type":  appRole.UserType,
					"user_title": appRole.UserTitle,
				},
				"org": map[string]interface{}{
					"id":             org.Id,
					"org_name":       org.OrgName,
					"org_short_name": org.OrgShortName,
					"org_intro":      org.OrgIntroduction,
					"org_logo":       org.OrgLogo,
					"province":       org.Province,
					"city":           org.City,
					"district":       org.District,
					"address":        org.Address,
					"creator":        org.Creator,
				},
				"subscibe": map[string]interface{}{
					"id":           subscibe.ID,
					"period_start": subscibe.PeriodStart,
					"period_end":   subscibe.PeriodEnd,
					"state":        subscibe.State,
				}, "template_info": map[string]interface{}{
					"id":          templateInfo.ID,
					"org_id":      templateInfo.OrgId,
					"template_id": templateInfo.TemplateId,
				},
				"config_list": configList,
				"filed_list":  FiledList,
			})
		}
	} else {

		redisClient := service.RedisClient()
		defer redisClient.Close()
		cachedCode, err := redisClient.Get("code_msg_" + mobile).Result()

		if err != nil {
			this.Data["json"] = enums.MakeFailResponseJSONWithSGJErrorCode(enums.ErrorCodeAccountOrVerCodeWrong)
			this.ServeJSON()
			return

		} else {
			if code != cachedCode {
				this.Data["json"] = enums.MakeFailResponseJSONWithSGJErrorCode(enums.ErrorCodeAccountOrVerCodeWrong)
				this.ServeJSON()
				return
			} else {

				ip := utils.GetIP(this.Ctx.Request)

				ssoDomain := beego.AppConfig.String("sso_domain")
				api := ssoDomain + "/m/login/code"
				values := make(url.Values)
				values.Set("mobile", mobile)
				values.Set("app_type", "3")
				values.Set("ip", ip)
				resp, requestErr := http.PostForm(api, values)

				if requestErr != nil {
					utils.ErrorLog("请求SSO登录接口失败: %v", requestErr)
					this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeDataException)
					return
				}
				defer resp.Body.Close()
				body, ioErr := ioutil.ReadAll(resp.Body)
				if ioErr != nil {
					utils.ErrorLog("SSO登录接口返回数据读取失败: %v", ioErr)
					this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeDataException)
					return
				}
				var respJSON map[string]interface{}
				utils.InfoLog(string(body))
				if err := json.Unmarshal([]byte(string(body)), &respJSON); err != nil {
					utils.ErrorLog("SSO登录接口返回数据解析JSON失败: %v", err)
					this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeDataException)
					return
				}

				if respJSON["state"].(float64) != 1 {
					msg := respJSON["msg"].(string)
					utils.ErrorLog("SSO登录接口请求失败: %v", msg)
					if int(respJSON["code"].(float64)) == 609 {
						this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeAccountOrPasswordWrong)
						return
					}
					this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeDataException)
					return
				} else {
					utils.SuccessLog("SSO登录成功")
					// 下面这几段 Map=>JSON=>Struct 的流程可能会造成速度很慢
					userJSON := respJSON["data"].(map[string]interface{})["admin"].(map[string]interface{})
					userJSONBytes, _ := json.Marshal(userJSON)
					var adminUser models.AdminUser
					if err := json.Unmarshal(userJSONBytes, &adminUser); err != nil {
						utils.ErrorLog("解析管理员失败：%v", err)
						this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeDataException)
						return
					}
					orgJSON := respJSON["data"].(map[string]interface{})["org"].(map[string]interface{})
					orgJSONBytes, _ := json.Marshal(orgJSON)
					var org models.Org
					if err := json.Unmarshal(orgJSONBytes, &org); err != nil {
						utils.ErrorLog("解析机构失败：%v", err)
						this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeDataException)
						return
					}
					appJSON := respJSON["data"].(map[string]interface{})["app"].(map[string]interface{})
					appJSONBytes, _ := json.Marshal(appJSON)
					var app models.OrgApp
					if err := json.Unmarshal(appJSONBytes, &app); err != nil {
						utils.ErrorLog("解析应用失败：%v", err)
						this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeDataException)
						return
					}
					appRoleJSON := respJSON["data"].(map[string]interface{})["app_role"].(map[string]interface{})
					appRoleJSONBytes, _ := json.Marshal(appRoleJSON)
					var appRole models.App_Role
					if err := json.Unmarshal(appRoleJSONBytes, &appRole); err != nil {
						utils.ErrorLog("解析AppRole失败：%v", err)
						this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeDataException)
						return
					}
					subscibeJSON := respJSON["data"].(map[string]interface{})["subscibe"].(map[string]interface{})
					subscibeJSONBytes, _ := json.Marshal(subscibeJSON)
					var subscibe models.ServeSubscibe
					if err := json.Unmarshal(subscibeJSONBytes, &subscibe); err != nil {
						utils.ErrorLog("解析Subscibe失败：%v", err)
						this.ServeFailJSONWithSGJErrorCode(enums.ErrorCodeDataException)
						return
					}
					service.GetOrgSubscibeState(&subscibe)
					templateInfo, _ := service.GetOrgInfoTemplate(org.Id)

					mobileAdminUserInfo := &mobile_api_controllers.MobileAdminUserInfo{
						AdminUser:    &adminUser,
						Org:          &org,
						App:          &app,
						AppRole:      &appRole,
						Subscibe:     &subscibe,
						TemplateInfo: &templateInfo,
					}
					this.SetSession("mobile_admin_user_info", mobileAdminUserInfo)
					redisClient.Del("code_msg_" + mobile)

					mobile = mobile + "-" + strconv.FormatInt(org.Id, 10) + "-" + strconv.FormatInt(appRole.Id, 10)
					token := utils.GenerateLoginToken(mobile)
					expiration, _ := beego.AppConfig.Int64("mobile_token_expiration_second")
					this.Ctx.SetCookie("token_cookie", token, expiration, "/")

					configList, _ := service.GetConfigList(org.Id)
					var FiledList []*models.FiledConfig
					FiledList, _ = service.FindFiledByOrgId(org.Id)
					if len(FiledList) == 0 {
						var err error
						if org.Id > 0 {
							err = service.BatchInsertFiledConfig(org.Id)
							if err == nil {
								FiledList, _ = service.FindFiledByOrgId(org.Id)
							} else {
								utils.ErrorLog("字段批量插入失败：%v", err)
							}
						} else {
							FiledList = make([]*models.FiledConfig, 0)
						}
					}

					this.ServeSuccessJSON(map[string]interface{}{
						"user": map[string]interface{}{
							"id":         adminUser.Id,
							"mobile":     adminUser.Mobile,
							"user_name":  appRole.UserName,
							"avatar":     appRole.Avatar,
							"intro":      appRole.Intro,
							"user_type":  appRole.UserType,
							"user_title": appRole.UserTitle,
						},
						"org": map[string]interface{}{
							"id":             org.Id,
							"org_name":       org.OrgName,
							"org_short_name": org.OrgShortName,
							"org_intro":      org.OrgIntroduction,
							"org_logo":       org.OrgLogo,
							"province":       org.Province,
							"city":           org.City,
							"district":       org.District,
							"address":        org.Address,
							"creator":        org.Creator,
						},
						"subscibe": map[string]interface{}{
							"id":           subscibe.ID,
							"period_start": subscibe.PeriodStart,
							"period_end":   subscibe.PeriodEnd,
							"state":        subscibe.State,
						}, "template_info": map[string]interface{}{
							"id":          templateInfo.ID,
							"org_id":      templateInfo.OrgId,
							"template_id": templateInfo.TemplateId,
						},
						"config_list": configList,
						"filed_list":  FiledList,
					})
				}

			}
		}
	}
}

func (this *NewLoginApiController) GetCode() {
	mobile := this.GetString("phone")
	aespass := this.GetString("aespass")
	types, _ := this.GetInt("type", 0)
	utils.TraceLog("mobile:%v aespass:%v", mobile, aespass)
	if utils.CellPhoneRegexp().MatchString(mobile) == false {
		this.Data["json"] = enums.MakeFailResponseJSONWithSGJErrorCode(enums.ErrorCodeMobileFormat)
		this.ServeJSON()
		return
	}

	if types == 1 {
		adminUser, _ := service.GetValidAdminUserByMobileReturnErr(mobile)
		if adminUser != nil {
			this.Data["json"] = enums.MakeFailResponseJSONWithSGJErrorCode(enums.ErrorCodeRegisterExist)
			this.ServeJSON()
			return
		}
	}

	if err := service.SendVerificationCodeSMS(mobile, aespass); err != nil {
		this.Data["json"] = enums.MakeFailResponseJSON(err.Error(), 600)
		this.ServeJSON()
	} else {
		this.Data["json"] = enums.MakeSuccessResponseJSON(map[string]interface{}{
			"msg": "短信发送成功,有效期为10分钟",
		})
		this.ServeJSON()
	}

}
