package service import ( "errors" "regexp" "strconv" "time" "videoplayer/dao" "videoplayer/proto" "videoplayer/worker" ) func CreateUser(name, password, email, gender string, age int) uint { id := dao.CreateUser(name, password, email, gender, age) if id != 0 { //添加用户信息到同步列表 err := setSyncUserDataSet("add", int(id)) if err != nil { return id } } return id } func GetUser(name, email, password string) dao.User { emailRegex := `^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}$` re := regexp.MustCompile(emailRegex) var user dao.User if re.MatchString(name) { user = dao.FindUserByEmail(name) } else { user = dao.FindUserByName(name) } if user.ID != 0 && user.Password == password { return user } return dao.User{} } func ContainsUser(name, email string) bool { user := dao.FindUserByName(name) user2 := dao.FindUserByEmail(email) if user.ID != 0 || user2.ID != 0 { return true } return false } func GetUserByID(id int) []proto.User { return dao.FindUserByID(id) } func GetUserByNameLike(name string) []proto.User { return dao.FindUserByNameLike(name) } func UpdateUser(user_id int, req proto.UpdateUserInfoReq) (int, error) { cur_user := dao.FindUserByID2(user_id) //fmt.Println("cur_user:", cur_user, "req:", req) if user_id == req.ID && cur_user.Role != "admin" { err := dao.UpdateUserByID3(user_id, req) //用户修改自己的信息,不能修改权限信息 //添加修改用户信息到同步列表 if err == nil { err2 := setSyncUserDataSet("update", user_id) if err2 != nil { return user_id, nil } } return user_id, err } else if cur_user.Role == "admin" { dao.UpdateUserByID2(req.ID, req) return req.ID, nil } else { return 0, nil } } func DeleteUserService(id, user_id int) int { res := 0 if user_id == id { res = dao.DeleteUserByID(id) } else { user := dao.FindUserByID2(user_id) if user.Role == "admin" { res = dao.DeleteUserByID(id) } } if res != 0 { //添加删除用户信息到同步列表 err := setSyncUserDataSet("delete", id) if err != nil { return res } } return res } func UserSyncDataFromMaster() { //从接口获取数据 url := "https://" + proto.Config.MASTER_SERVER_DOMAIN + "/user/sync" tokens := worker.GetRedisSetMembers("super_permission_tokens") var req proto.SyncUserReq req.Token = tokens[0] req.Device = proto.Config.SERVER_NAME all := worker.GetRedis("user_sync_all") if all == "" || all == "1" { req.Types = 1 } else { worker.SetRedis("user_sync_all", "2") req.Types = 2 } user_sync_data := worker.SyncDataFromMasterReq2(url, req) add_users := user_sync_data.Add update_users := user_sync_data.Update delete_users := user_sync_data.Delete //未成功操作的id var fail_ids []uint //添加用户 var add_confirm []proto.UserConfirmID for _, v := range add_users { res := dao.AddUserSync(v) if res == 0 { fail_ids = append(fail_ids, v.ID) } else { add_confirm = append(add_confirm, proto.UserConfirmID{ID: v.ID}) } } //更新用户 var update_confirm []proto.UserConfirmID for _, v := range update_users { res := dao.UpdateUserSync(v) if res == 0 { fail_ids = append(fail_ids, v.ID) } else { update_confirm = append(update_confirm, proto.UserConfirmID{ID: v.ID}) } } //删除用户 var delete_confirm []proto.UserConfirmID for _, v := range delete_users { res := dao.DeleteUserSync(v) if res == 0 { fail_ids = append(fail_ids, v.ID) } else { delete_confirm = append(delete_confirm, proto.UserConfirmID{ID: v.ID}) } } //确认同步数据 var data proto.UserSyncConfirm data.Add = add_confirm data.Update = update_confirm data.Delete = delete_confirm //确认同步数据请求 var confirm_req proto.SyncUserReq confirm_req.Token = tokens[0] confirm_req.Device = proto.Config.SERVER_NAME confirm_req.Types = 3 confirm_req.Confirm = data worker.SyncDataFromMasterReq2(url, confirm_req) } // 同步数据到主服务器-增删改数据 func GetUserSyncData(device string) dao.UserSyncResp { key := device + "_sync_user_ids" add_temp_key := device + "_sync_user_ids_add_confirm_temp" update_temp_key := device + "_sync_user_ids_update_confirm_temp" delete_temp_key := device + "_sync_user_ids_delete_confirm_temp" //需要获取暂存集合的并集,清空暂存集合,存入待确认集合 add_user_ids := worker.GetRedisSetUnion(key+"_add", add_temp_key) update_user_ids := worker.GetRedisSetUnion(key+"_update", update_temp_key) delete_user_ids := worker.GetRedisSetUnion(key+"_delete", delete_temp_key) add_users := []dao.User{} update_users := []dao.User{} delete_users := []proto.UserDelID{} for _, v := range add_user_ids { id, _ := strconv.Atoi(v) user := dao.FindUserByUserID(id) add_users = append(add_users, user) } for _, v := range update_user_ids { id, _ := strconv.Atoi(v) user := dao.FindUserByUserID(id) update_users = append(update_users, user) } for _, v := range delete_user_ids { id, _ := strconv.Atoi(v) delete_users = append(delete_users, proto.UserDelID{ID: uint(id)}) } //将id存入暂存集合,清空原集合,存入待确认集合主要保证在确认时,有新的数据加入不会在确认时漏掉 worker.SetRedisSetUnionAndStore(add_temp_key, key+"_add") worker.ClearRedisSet(key + "_add") worker.SetRedisSetUnionAndStore(update_temp_key, key+"_update") worker.ClearRedisSet(key + "_update") worker.SetRedisSetUnionAndStore(delete_temp_key, key+"_delete") worker.ClearRedisSet(key + "_delete") return dao.UserSyncResp{Add: add_users, Update: update_users, Delete: delete_users} } func setSyncUserDataSet(t string, id int) error { devices := worker.GetRedisSetMembers("sync_devices_ids") //主服务器查看从服务器的设备列表 var err error for _, device := range devices { key := device + "_sync_user_ids" if t == "add" { key_ := key + "_add" worker.SetRedisSetAdd(key_, strconv.Itoa(id)) } else if t == "update" { key_ := key + "_update" worker.SetRedisSetAdd(key_, strconv.Itoa(id)) } else if t == "delete" { key_ := key + "_delete" worker.SetRedisSetAdd(key_, strconv.Itoa(id)) } else { err = errors.New("error") } } return err } // 确认同步数据 func ConfirmSyncUserData(device string, data proto.UserSyncConfirm) error { var ids_add []string var err error for _, v := range data.Add { ids_add = append(ids_add, strconv.Itoa(int(v.ID))) } add_key := device + "_sync_user_ids_add_confirm" isSuccess := worker.SetRedisSetAddBatchWithExpire(add_key, ids_add, time.Second*30) if !isSuccess { err = errors.New("set confirm error") } var ids_update []string for _, v := range data.Update { ids_update = append(ids_update, strconv.Itoa(int(v.ID))) } update_key := device + "_sync_user_ids_update_confirm" isSuccess = worker.SetRedisSetAddBatchWithExpire(update_key, ids_update, time.Second*30) if !isSuccess { err = errors.New("set confirm error") } var ids_delete []string for _, v := range data.Delete { ids_delete = append(ids_delete, strconv.Itoa(int(v.ID))) } del_key := device + "_sync_user_ids_delete_confirm" isSuccess = worker.SetRedisSetAddBatchWithExpire(del_key, ids_delete, time.Second*30) if !isSuccess { err = errors.New("set confirm error") } //待确认集合暂存 ids_add_confirm_temp := device + "_sync_user_ids_add_confirm_temp" ids_update_confirm_temp := device + "_sync_user_ids_update_confirm_temp" ids_delete_confirm_temp := device + "_sync_user_ids_delete_confirm_temp" //取差集 add_diff := worker.SetRedisSetDiffAndStore(ids_add_confirm_temp, add_key) update_diff := worker.SetRedisSetDiffAndStore(ids_update_confirm_temp, update_key) delete_diff := worker.SetRedisSetDiffAndStore(ids_delete_confirm_temp, del_key) if add_diff != true || update_diff != true || delete_diff != true { err = errors.New("confirm error") } return err }