WechatService.cs 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129
  1. using Furion.DataEncryption;
  2. using Furion.DependencyInjection;
  3. using Furion.DynamicApiController;
  4. using Furion.FriendlyException;
  5. using Mapster;
  6. using Microsoft.AspNetCore.Authorization;
  7. using Microsoft.AspNetCore.Mvc;
  8. using SKIT.FlurlHttpClient.Wechat.Api;
  9. using SKIT.FlurlHttpClient.Wechat.Api.Models;
  10. using System.Collections.Generic;
  11. using System.ComponentModel.DataAnnotations;
  12. using System.Threading.Tasks;
  13. namespace Admin.NET.Core.Service
  14. {
  15. /// <summary>
  16. /// 微信公众号服务
  17. /// </summary>
  18. [ApiDescriptionSettings(Name = "微信公众号", Order = 100)]
  19. public class WechatService : IDynamicApiController, ITransient
  20. {
  21. private readonly SqlSugarRepository<WechatUser> _wechatUserRep;
  22. private readonly WechatApiClient _wechatApiClient;
  23. public WechatService(SqlSugarRepository<WechatUser> wechatUserRep,
  24. WeChatApiHttpClient wechatApiHttpClient)
  25. {
  26. _wechatUserRep = wechatUserRep;
  27. _wechatApiClient = wechatApiHttpClient.CreateWechatClient();
  28. }
  29. /// <summary>
  30. /// 生成网页授权Url
  31. /// </summary>
  32. /// <param name="input"></param>
  33. /// <returns></returns>
  34. [HttpPost("/weChat/genAuthUrl")]
  35. [AllowAnonymous]
  36. public string GenAuthUrl(GenAuthUrlInput input)
  37. {
  38. return _wechatApiClient.GenerateParameterizedUrlForConnectOAuth2Authorize(input.RedirectUrl, input.Scope);
  39. }
  40. /// <summary>
  41. /// 授权登录(Code换取OpenId)
  42. /// </summary>
  43. /// <param name="input"></param>
  44. [HttpPost("/weChat/snsOAuth2")]
  45. [AllowAnonymous]
  46. public async Task<string> LoginOAuth2([Required] WechatOAuth2Input input)
  47. {
  48. var reqOAuth2 = new SnsOAuth2AccessTokenRequest()
  49. {
  50. Code = input.Code,
  51. };
  52. var resOAuth2 = await _wechatApiClient.ExecuteSnsOAuth2AccessTokenAsync(reqOAuth2);
  53. if (resOAuth2.ErrorCode != (int)WeChatReturnCodeEnum.请求成功)
  54. throw Oops.Oh(resOAuth2.ErrorMessage + resOAuth2.ErrorCode);
  55. var wxUser = await _wechatUserRep.GetFirstAsync(p => p.OpenId == resOAuth2.OpenId);
  56. if (wxUser == null)
  57. {
  58. var reqUserInfo = new SnsUserInfoRequest()
  59. {
  60. OpenId = resOAuth2.OpenId,
  61. AccessToken = resOAuth2.AccessToken,
  62. };
  63. var resUserInfo = await _wechatApiClient.ExecuteSnsUserInfoAsync(reqUserInfo);
  64. wxUser = resUserInfo.Adapt<WechatUser>();
  65. wxUser.Avatar = resUserInfo.HeadImageUrl;
  66. wxUser.NickName = resUserInfo.Nickname;
  67. wxUser = await _wechatUserRep.AsInsertable(wxUser).ExecuteReturnEntityAsync();
  68. }
  69. else
  70. {
  71. wxUser.AccessToken = resOAuth2.AccessToken;
  72. wxUser.RefreshToken = resOAuth2.RefreshToken;
  73. await _wechatUserRep.AsUpdateable(wxUser).IgnoreColumns(true).ExecuteCommandAsync();
  74. }
  75. return resOAuth2.OpenId;
  76. }
  77. /// <summary>
  78. /// 微信用户登录
  79. /// </summary>
  80. /// <param name="input"></param>
  81. /// <returns></returns>
  82. [HttpPost("/weChat/openIdLogin")]
  83. [AllowAnonymous]
  84. public async Task<dynamic> WechatUserLogin(WechatUserLogin input)
  85. {
  86. var wxUser = await _wechatUserRep.GetFirstAsync(p => p.OpenId == input.OpenId);
  87. if (wxUser == null)
  88. throw Oops.Oh("微信用户不存在");
  89. return new
  90. {
  91. wxUser.Id,
  92. wxUser.OpenId,
  93. wxUser.NickName,
  94. wxUser.Avatar,
  95. accessToken = JWTEncryption.Encrypt(new Dictionary<string, object>
  96. {
  97. { ClaimConst.UserId, wxUser.Id },
  98. { ClaimConst.OpenId, wxUser.OpenId },
  99. { ClaimConst.RealName, wxUser.NickName },
  100. })
  101. };
  102. }
  103. /// <summary>
  104. /// 获取配置签名参数(wx.config)
  105. /// </summary>
  106. /// <returns></returns>
  107. [HttpPost("/weChat/genConfigPara")]
  108. public async Task<dynamic> GenConfigPara(SignatureInput input)
  109. {
  110. var resCgibinToken = await _wechatApiClient.ExecuteCgibinTokenAsync(new CgibinTokenRequest());
  111. var request = new CgibinTicketGetTicketRequest()
  112. {
  113. AccessToken = resCgibinToken.AccessToken
  114. };
  115. var response = await _wechatApiClient.ExecuteCgibinTicketGetTicketAsync(request);
  116. if (!response.IsSuccessful())
  117. throw Oops.Oh(response.ErrorMessage);
  118. return _wechatApiClient.GenerateParametersForJSSDKConfig(response.Ticket, input.Url);
  119. }
  120. }
  121. }