package domain

import (
	"fmt"
	"github.com/tal-tech/go-zero/core/collection"
	"gitlab.fjmaimaimai.com/allied-creation/allied-creation-user/pkg/constant"
	"strconv"
	"strings"
	"time"
)

const (
	DefaultOrgCodeCompany = "ENTERPRISE01" //默认的低级组织标识
)

const (
	IsOrgFlag    = 1 //   标记为组织
	IsNotOrgFlag = 2 // 标记为非组织
)

const (
	OrgStatusEnable  = 1
	OrgStatusDisable = 2
)

// 组织 organization
type Org struct {
	// 组织ID
	OrgId int64 `json:"orgId,omitempty"`
	// 企业id
	CompanyId int64 `json:"companyId,omitempty"`
	// 创建时间
	CreatedAt time.Time `json:"createdAt,omitempty"`
	// 更新时间
	UpdatedAt time.Time `json:"updatedAt,omitempty"`
	// 删除时间
	DeletedAt time.Time `json:"deletedAt,omitempty"`
	// 组织编码
	OrgCode string `json:"orgCode,omitempty"`
	// 组织名称
	OrgName string `json:"orgName,omitempty"`
	// 扩展数据
	Ext *Ext `json:"ext,omitempty"`
	// 是否是组织标识 1:是 2:不是
	IsOrg int `json:"isOrg,omitempty"`
	// 组织状态 1:启用 2:禁用 3.删除
	OrgStatus int `json:"orgStatus,omitempty"`
	// 父级ID
	ParentId int64 `json:"parentId,omitempty"`
	// 父级节点路径("11,12") 注意:parent_id为0时 parentPath "",公司级别的组织没有父级组织
	ParentPath string `json:"parentPath,omitempty"`

	// 企业id
	Company *CompanyVisible `json:"company,omitempty"`
}

type OrgRepository interface {
	Save(org *Org) (*Org, error)
	Remove(org *Org) (*Org, error)
	FindOne(queryOptions map[string]interface{}) (*Org, error)
	Find(queryOptions map[string]interface{}) (int64, []*Org, error)
}

func (org *Org) Identify() interface{} {
	if org.OrgId == 0 {
		return nil
	}
	return org.OrgId
}

func (org *Org) Update(data map[string]interface{}) error {
	if createdAt, ok := data["createdAt"]; ok {
		org.CreatedAt = createdAt.(time.Time)
	}
	if updatedAt, ok := data["updatedAt"]; ok {
		org.UpdatedAt = updatedAt.(time.Time)
	}
	if deletedAt, ok := data["deletedAt"]; ok {
		org.DeletedAt = deletedAt.(time.Time)
	}
	if orgCode, ok := data["orgCode"]; ok {
		org.OrgCode = orgCode.(string)
	}
	if orgName, ok := data["orgName"]; ok {
		org.OrgName = orgName.(string)
	}
	if org.Ext == nil {
		org.Ext = &Ext{}
	}
	//if userName, ok := data["userName"]; ok {
	//	org.Ext.UserName = userName.(string)
	//}
	//if orgName, ok := data["orgName"]; ok {
	//	org.Ext.OrgName = orgName.(string)
	//}
	//if phone, ok := data["phone"]; ok {
	//	org.Ext.Phone = phone.(string)
	//}
	//if depName, ok := data["depName"]; ok {
	//	org.Ext.DepName = depName.(string)
	//}
	if parentDepName, ok := data["parentDepName"]; ok {
		org.Ext.ParentDepName = parentDepName.(string)
	}
	if isOrg, ok := data["isOrg"]; ok {
		org.IsOrg = isOrg.(int)
	}
	if parentId, ok := data["parentId"]; ok {
		org.ParentId = parentId.(int64)
	}
	if parentPath, ok := data["parentPath"]; ok {
		org.ParentPath = parentPath.(string)
	}
	return nil
}

// 部门
type Department struct {
	// 部门ID
	DepartmentId int64 `json:"departmentId"`
	// 部门名称
	DepartmentName string `json:"departmentName"`
	// 部门编号
	DepartmentNumber string `json:"departmentNumber"`
}

//type SampleOrg struct {
//	// 组织ID
//	OrgId int64 `json:"orgId,omitempty"`
//	// 企业id
//	CompanyId int64 `json:"companyId,omitempty"`
//	// 组织名称
//	OrgName string `json:"orgName,omitempty"`
//	// 组织编码
//	OrgCode string `json:"orgCode,omitempty"`
//}

/*****   0.基础函数模块  *****/

// 通过组织获取当前部门信息
func (org *Org) ConvDep() *Department {
	return &Department{
		DepartmentId:     org.OrgId,
		DepartmentName:   org.OrgName,
		DepartmentNumber: org.OrgCode,
	}
}

func (org *Org) CloneSample() *Org {
	return &Org{
		OrgId:   org.OrgId,
		OrgName: org.OrgName,
		OrgCode: org.OrgCode,
	}
}

func (org *Org) SetOrgStatus(orgStatus int) error {
	if !(orgStatus == OrgStatusEnable || orgStatus == OrgStatusDisable) {
		return fmt.Errorf("非法组织状态")
	}
	if org.OrgStatus == orgStatus {
		return nil
	}
	//if !org.DeletedAt.IsZero() {
	//	return fmt.Errorf("组织不存在")
	//}
	org.UpdatedAt = time.Now()
	org.OrgStatus = orgStatus
	return nil
}

/*****   1.实现树  *****/
/*1.1 实现树的方法*/
// GetParentPath 获取菜单路径
func (org *Org) GetParentPath() string {
	if org.ParentId == 0 {
		return ""
	}
	if len(org.ParentPath) > 0 {
		return fmt.Sprintf("%v%v%v", org.ParentPath, PathSegment, org.OrgId)
	}
	return fmt.Sprintf("%v", org.OrgId)
}

// GetFullPath 获取菜单全路径
func (org *Org) GetFullPath() string {
	if org.ParentId == 0 {
		return ""
	}
	if len(org.ParentPath) > 0 {
		return fmt.Sprintf("%v%v%v", org.ParentPath, PathSegment, org.OrgId)
	}
	return fmt.Sprintf("%v", org.OrgId)
}

func (org *Org) PID() string {
	return org.ParentPath
}
func (org *Org) ID() string {
	return org.GetFullPath()
}

func (org *Org) IsChild(pid int64) bool {
	paths := strings.Split(org.ParentPath, PathSegment)
	pidStr := strconv.FormatInt(pid, 10)
	if org.OrgId == pid {
		return true
	}
	if org.ParentId == pid {
		return true
	}
	for _, v := range paths {
		if strings.EqualFold(pidStr, v) {
			return true
		}
	}
	return false
}

/*****   2.缓存模块  *****/

func (m *Org) CacheKeyFunc() string {
	if constant.DISABLE_REPOSITORY_CACHE {
		return ""
	}
	if m.OrgId == 0 {
		return ""
	}
	return fmt.Sprintf("%v:cache:org:id:%v", constant.CACHE_PREFIX, m.OrgId)
}

/*****   3.批量添加组织项  *****/

type BatchAddOrgItem struct {
	// 组织编码
	OrgCode string `json:"orgCode,omitempty"`
	// 父级组织编码
	ParentOrgCode string `json:"parentOrgCode,omitempty"`
	// 组织名称
	OrgName string `json:"orgName,omitempty"`
	// 企业id
	CompanyId int64 `json:"companyId,omitempty"`

	// 失败理由
	FailReason string `json:"failReason"`
}

type Organizations []*Org

func (list Organizations) OrgIds() []int64 {
	set := collection.NewSet()
	for i := range list {
		set.Add(list[i].OrgId)
	}
	return set.KeysInt64()
}