using Elasticsearch.Net;
using JiaZhiQuan.Common.ElasticSearch;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
using Senparc.Weixin.MP.Containers;
using System;
using System.Collections.Generic;
using System.Data;
using System.Diagnostics;
using System.Dynamic;
using System.Linq;
using System.Net.Http;
using System.Reflection;
using System.Security.Cryptography;
using System.Text;
using System.Threading.Tasks;
using Wicture.DbRESTFul;
using Wicture.DbRESTFul.Cache;
using Wicture.DbRESTFul.Infrastructure.Repository;
namespace JiaZhiQuan.Common
{
public static partial class RepositoryExtension
{
///
/// 保存用户信息到ES。创建新的或者更新部分字段
/// 必须包含id字段
/// 是否忽略更新文章索引中用户昵称(暂时仅用于用户注销时,指定为true)
///
public static async Task UserInfoSave2ES(this DbRESTFulRepository repository, object userInfo, bool ignorePost = false)
{
var id = userInfo.GetType().GetProperty("id").GetValue(userInfo);
var idStr = id.ToString();
bool exist = await ESHelper.CheckExist("user", idStr);
if (exist)
{
var rsp = await ESHelper.Client.UpdateAsync("user", idStr, PostData.Serializable(new { doc = userInfo }));
if (!rsp.Success)
{
LoggerManager.Logger.Error("更新用户信息到ES失败:" + rsp.Body);
return;
}
// 如果存在,还需要更新 Post 中的用户昵称
if (IsPropertyExist(userInfo, "alias"))
{
string alias = userInfo.GetType().GetProperty("alias").GetValue(userInfo) as string;
alias = alias.Replace("'", "");
var query = new
{
script = new { source = $"ctx._source['userAlias']='{alias}'" },
query = new
{
term = new { userId = id }
}
};
rsp = await ESHelper.Client.UpdateByQueryAsync(ESConstants.ESIndexName.Post, PostData.Serializable(query));
if (!rsp.Success)
{
LoggerManager.Logger.Error("更新ES中POST用户信息失败:" + rsp.Body);
}
}
}
else
{
var rsp = await ESHelper.Client.CreateAsync("user", idStr, PostData.Serializable(userInfo));
if (!rsp.Success)
{
LoggerManager.Logger.Error("创建用户信息到ES失败:" + rsp.Body);
return;
}
}
}
///
/// 通过用户Id加载用户信息
/// id(string), alias, authType, authName, vip, headImage, domainTalent, publicTags, official, curProvince,watermark
///
///
/// 可以为空
///
public static async Task> UsersInfoByIds(this DbRESTFulRepository repository, IEnumerable userIds, IDbConnection conn = null) where T : UserInfoBase
{
userIds = userIds.Distinct();
var list = await repository.QueryAsync("select id, alias, authType, authName, vip, headImage, domainTalent, description, publicTags, official, curProvince,watermark from n_user where id in @userIds", new { userIds }, conn);
var dic = new Dictionary(userIds.Count());
foreach (var id in userIds)
{
dic[id] = list.FirstOrDefault(e => id.ToString() == e.id);
}
return dic;
}
///
/// 通过用户Id加载用户信息
/// id(string), username, alias, authType, authName, vip, headImage, domainTalent, mpRole, publicTags, official, curProvince,watermark
///
///
/// 可以为空
///
public static async Task> UsersInfoFullByIds(this DbRESTFulRepository repository, IEnumerable userIds, IDbConnection conn = null) where T : UserInfoFull
{
userIds = userIds.Distinct();
var list = await repository.QueryAsync("select id, username, alias, authType, authName, vip, headImage, domainTalent, description, mpRole, superior, publicTags, official, curProvince,watermark from n_user where id in @userIds", new { userIds }, conn);
var dic = new Dictionary(userIds.Count());
foreach (var id in userIds)
{
dic[id] = list.FirstOrDefault(e => id.ToString() == e.id);
}
return dic;
}
///
/// 通过用户Id加载用户信息,附带是否关注
/// id(string), alias, authType, authName, vip, headImage, domainTalent, publicTags, official, curProvince, focused,watermark
///
/// 当前用户
/// 可以为空
/// 忽略当前用户关注用户列表的状态
/// 忽略用户列表是否关注当前用户的状态
///
public static async Task> UsersInfoWithFocusStateByIds(this DbRESTFulRepository repository, long userId, IEnumerable userIds, IDbConnection conn = null, bool ignoreFocusState = false, bool ignoreFanState = false) where T : UserInfoBaseWithFocusState
{
userIds = userIds.Distinct();
var dic = new Dictionary(userIds.Count());
if (userIds.Count() == 0)
{
return dic;
}
if (userId < 1)
{
ignoreFanState = true;
ignoreFocusState = true;
}
var list = await repository.QueryAsync("select id, alias, authType, authName, vip, headImage, domainTalent, description, publicTags, official, curProvince,watermark,growLevel level from n_user where id in @userIds", new { userIds }, conn);
HashSet focusState = null;
if (!ignoreFocusState)
{
focusState = await CheckFocusState(repository, userId, userIds, conn);
}
HashSet fanState = null;
if (!ignoreFanState)
{
fanState = await CheckFanState(repository, userId, userIds, conn);
}
foreach (var id in userIds)
{
var user = list.FirstOrDefault(e => id.ToString() == e.id);
if (user != null)
{
if (focusState != null) user.focused = focusState.Contains(id) ? 1 : 0;
if (fanState != null) user.isFan = fanState.Contains(id) ? 1 : 0;
}
dic[id] = user;
}
return dic;
}
///
/// 返回 userIds 参数中 userId 所关注的用户Id列表
///
public static async Task> CheckFocusState(this DbRESTFulRepository repository, long userId, IEnumerable userIds, IDbConnection conn = null)
{
var list = await repository.QueryAsync("select userId from n_user_fan where fanId=@userId and userId in @userIds", new { userId, userIds }, conn);
var count = list.Count();
if (count > 0)
{
return list.ToHashSet();
}
return new HashSet(0);
}
///
/// 返回 userIds 参数中 userId 所被关注的用户Id列表
///
public static async Task> CheckFanState(this DbRESTFulRepository repository, long userId, IEnumerable userIds, IDbConnection conn = null)
{
var list = await repository.QueryAsync("select fanId from n_user_fan where userId=@userId and fanId in @userIds", new { userId, userIds }, conn);
var count = list.Count();
if (count > 0)
{
return list.ToHashSet();
}
return new HashSet(0);
}
///
/// 通过用户编号查询用户的隐私设置
///
public static async Task GetPrivacySettingByUserId(this DbRESTFulRepository repository, long userId, RedisCacheProvider cacheProvider, IDbConnection conn = null)
{
var cacheKey = CacheKeys.UserPrivacySetting(userId);
var cacheVal = await cacheProvider.Get(cacheKey);
if (cacheVal != null)
{
return UserPrivacySetting.InstanceByIntValue(cacheVal.Value);
}
else
{
UserPrivacySetting setting = await repository.QuerySingleOrDefaultAsync($"select likePostRecordsHidden, collectPostRecordsHidden, focusRecordsHidden, fansHidden, personalRecommend from n_user_settings where userId={userId}", null, conn);
bool watermark = await repository.QuerySingleOrDefaultAsync($"SELECT watermark FROM n_user WHERE id={userId}", null, conn);
if (setting == null) setting = new UserPrivacySetting();
setting.watermark = watermark;
await cacheProvider.Set(cacheKey, setting.GetIntValue(), CacheKeys.UserPrivacySettingCacheSecs);
return setting;
}
}
public static async Task GetUserState(this DbRESTFulRepository repository, long userId, RedisCacheProvider cacheProvider, IDbConnection conn = null)
{
var cacheKey = CacheKeys.UserStateValue(userId);
var cacheVal = await cacheProvider.Get(cacheKey);
if (cacheVal != null)
{
return cacheVal.Value;
}
else
{
var info = await repository.QuerySingleOrDefaultAsync($"select state from n_user where id={userId}", null, conn);
var state = info?.state ?? -1;
await cacheProvider.Set(cacheKey, state, CacheKeys.UserStateValueCacheSecs);
return state;
}
}
}
}