user.go 21 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578
  1. package xiangyu
  2. import (
  3. "encoding/json"
  4. "errors"
  5. "eta_gn/eta_bridge/global"
  6. "eta_gn/eta_bridge/utils"
  7. "fmt"
  8. "io"
  9. "net/http"
  10. "strings"
  11. "time"
  12. )
  13. // LoginReq
  14. // @Description: 登录请求参数
  15. type LoginReq struct {
  16. SystemCode string `json:"systemCode" description:"来源系统"`
  17. In0 In0 `json:"in0"`
  18. IntegrationKey string `json:"integrationKey" description:"集成密钥"`
  19. }
  20. // In0
  21. // @Description: 通用参数
  22. type In0 struct {
  23. PageTotal string `json:"pageTotal" description:"总页数"`
  24. PageNo string `json:"pageNo" description:"当前请求页"`
  25. DocType string `json:"docType" description:"单据类型"`
  26. Property string `json:"property" description:"备用字段"`
  27. DocCode string `json:"docCode" description:"单据号码"`
  28. Source string `json:"source" description:"来源系统"`
  29. Target string `json:"target" description:"目标系统"`
  30. }
  31. // BaseResponse
  32. // @Description: 基础返回数据返回
  33. type BaseResponse struct {
  34. ReturnCode string `json:"returnCode" description:"响应代码,成功--S,失败--F"`
  35. ReturnMsg string `json:"returnMsg" description:"响应消息"`
  36. Success bool `description:"true 执行成功,false 执行失败"`
  37. Message string `description:"消息"`
  38. }
  39. // LoginResp
  40. // @Description: 登录响应参数
  41. type LoginResp struct {
  42. Out struct {
  43. ReturnCode string `json:"returnCode" description:"响应代码,成功--S,失败--F"`
  44. ReturnMsg string `json:"returnMsg" description:"响应消息"`
  45. TokenId string `json:"tokenId" description:"令牌id,login接口生成"`
  46. Success bool `description:"true 执行成功,false 执行失败"`
  47. Message string `description:"消息"`
  48. } `json:"out"`
  49. }
  50. // Login
  51. // @Description: 第三方应用系统集成统一身份管理平台,通过login接口进行身份验证,获取token,用于后续调用身份信息同步接口
  52. // @author: Roc
  53. // @datetime 2024-01-16 16:20:10
  54. // @return tokenId string
  55. // @return err error
  56. func Login() (tokenId string, err error) {
  57. urlPath := `/IAM/XYGIntegrationService/login/ProxyServices/loginPS`
  58. req := LoginReq{
  59. SystemCode: global.CONFIG.Xiangyu.SystemCode,
  60. In0: In0{
  61. PageTotal: "",
  62. PageNo: "",
  63. DocType: "login",
  64. Property: "",
  65. //DocCode: getDocCode(),
  66. Source: global.CONFIG.Xiangyu.SystemCode,
  67. Target: global.CONFIG.Xiangyu.UserSyncTarget,
  68. },
  69. IntegrationKey: global.CONFIG.Xiangyu.UserKey,
  70. }
  71. postData, err := json.Marshal(req)
  72. if err != nil {
  73. return
  74. }
  75. result, err := HttpPost(urlPath, string(postData), "application/json")
  76. if err != nil {
  77. return
  78. }
  79. // 解析响应结果
  80. var resp *LoginResp
  81. err = json.Unmarshal(result, &resp)
  82. if err != nil {
  83. return
  84. }
  85. if resp.Out.Success == false {
  86. err = errors.New(fmt.Sprintf("响应代码:%s,响应消息:%s,错误信息:%s", resp.Out.ReturnCode, resp.Out.ReturnMsg, resp.Out.Message))
  87. return
  88. }
  89. if resp.Out.TokenId == "" {
  90. err = errors.New(fmt.Sprintf("响应代码:%s,响应消息:%s,错误信息:%s", resp.Out.ReturnCode, resp.Out.ReturnMsg, resp.Out.Message))
  91. return
  92. }
  93. tokenId = resp.Out.TokenId
  94. return
  95. }
  96. // LogoutReq
  97. // @Description: 清除tokenId的请求参数
  98. type LogoutReq struct {
  99. SystemCode string `json:"systemCode" description:"来源系统"`
  100. In0 In0 `json:"in0"`
  101. TokenId string `json:"tokenId" description:"令牌id,login接口生成"`
  102. }
  103. // Logout
  104. // @Description: 第三方应用系统集成统一身份管理平台,身份信息同步完成后,调用logout接口清除tokenId,结束整个身份信息同步流程
  105. // @author: Roc
  106. // @datetime 2024-01-16 13:53:12
  107. // @param tokenId string
  108. // @return err error
  109. func Logout(tokenId string) (err error) {
  110. urlPath := `/IAM/XYGIntegrationService/logout/ProxyServices/logoutPS`
  111. req := LogoutReq{
  112. SystemCode: global.CONFIG.Xiangyu.SystemCode,
  113. In0: In0{
  114. PageTotal: "",
  115. PageNo: "",
  116. DocType: "logout",
  117. Property: "",
  118. DocCode: getDocCode(),
  119. Source: global.CONFIG.Xiangyu.SystemCode,
  120. Target: global.CONFIG.Xiangyu.UserSyncTarget,
  121. },
  122. TokenId: tokenId,
  123. }
  124. postData, err := json.Marshal(req)
  125. if err != nil {
  126. return
  127. }
  128. result, err := HttpPost(urlPath, string(postData), "application/json")
  129. if err != nil {
  130. return
  131. }
  132. // 解析响应结果
  133. var resp *LoginResp
  134. err = json.Unmarshal(result, &resp)
  135. if err != nil {
  136. return
  137. }
  138. if resp.Out.Success == false {
  139. err = errors.New(fmt.Sprintf("响应代码:%s,响应消息:%s,错误信息:%s", resp.Out.ReturnCode, resp.Out.ReturnMsg, resp.Out.Message))
  140. return
  141. }
  142. return
  143. }
  144. // PullTaskResp
  145. // @Description: 开始同步用户的接口返回数据
  146. type PullTaskResp struct {
  147. BaseResponse
  148. ObjectCode string `json:"objectCode" description:"对象代码,BIM中注册对象代码:账号:T_ACC;机构:T_ORC;岗位:T_POS"`
  149. Id string `json:"id" description:"身份管理平台内部对象ID"`
  150. TaskId string `json:"taskId" description:"身份管理平台下拉任务ID"`
  151. EffectOn string `json:"effectOn" description:"任务操作类型;创建:CREATED、更新:UPDATED、禁用:DISABLED、启用:ENABLED"`
  152. Timestamp int64 `json:"timestamp" description:"BIM当前时间戳"`
  153. ObjectType string `json:"objectType" description:"对象类型:账号:TARGET_ACCOUNT、机构;TARGET_ORGANIZATION、资源:TARGET_RESOURCE、角色:TARGET_ROLE"`
  154. Data string `json:"data" description:"任务数据,JSON格式,具体数据结构根据任务类型不同而不同"`
  155. }
  156. // AccountData
  157. // @Description: 账号对象信息
  158. type AccountData struct {
  159. Username string `json:"username"`
  160. Password interface{} `json:"password"`
  161. Fullname string `json:"fullname"`
  162. IsDisabled bool `json:"isDisabled"`
  163. StartDate interface{} `json:"startDate"`
  164. EndDate interface{} `json:"endDate"`
  165. IsAdmin bool `json:"isAdmin"`
  166. CompanyEmail interface{} `json:"companyEmail"`
  167. CompanyPlate string `json:"companyPlate"`
  168. DepartName string `json:"departName"`
  169. Departld string `json:"departld"`
  170. CompanyName string `json:"companyName"`
  171. Companyld string `json:"companyld"`
  172. Sex string `json:"sex"`
  173. PyName string `json:"pyName"`
  174. Personld string `json:"personld"`
  175. IdCard interface{} `json:"idCard"`
  176. EmployeeNo string `json:"employeeNo"`
  177. Mobile interface{} `json:"mobile"`
  178. ScEmail interface{} `json:"ScEmail"`
  179. Email interface{} `json:"email"`
  180. }
  181. // SyncTaskResp
  182. // @Description: 全量同步的响应数据
  183. // 1.objectType 为TARGET_ACCOUNT 时,表示下拉数据为账号信息。
  184. // 2.objectType 为TARGET_ORGANIZATION 时,表示下拉数据为机构(公司和部门)信息。
  185. // 3.objectType 为TARGET_RESOURCE并且objectCode为T_USR时,表示下拉数据为HR人员信息。
  186. // 4.objectType为TARGET_RESOURCE 并且objectCode为T_POS 时,表示下拉数据为岗位信息。
  187. // 5.objectType 为TARGET_RESOURCE并且objectCode为T_SEQ时,表示下拉数据为岗位序列信息
  188. type SyncTaskResp struct {
  189. Out struct {
  190. ReturnCode string `json:"returnCode" description:"响应代码,成功--S,失败--F"`
  191. ReturnMsg string `json:"returnMsg" description:"响应消息"`
  192. ObjectCode string `json:"objectCode" description:"BIM中注册对象代码:账号:T_ACC;机构:T_ORC;岗位:T_POS"`
  193. Success bool `description:"true 执行成功,false 执行失败"`
  194. Message string `description:"消息"`
  195. Id string `json:"id"`
  196. Timestamp int64 `json:"timestamp"`
  197. ObjectType string `json:"objectType" description:"对象类型:账号:TARGET_ACCOUNT、机构;TARGET_ORGANIZATION、资源:TARGET_RESOURCE、角色:TARGET_ROLE"`
  198. } `json:"out"`
  199. }
  200. // SyncTaskUserResp
  201. // @Description: 全量同步的账号响应数据
  202. type SyncTaskUserResp struct {
  203. Out struct {
  204. ReturnCode string `json:"returnCode" description:"响应代码,成功--S,失败--F"`
  205. ReturnMsg string `json:"returnMsg" description:"响应消息"`
  206. ObjectCode string `json:"objectCode" description:"BIM中注册对象代码:账号:T_ACC;机构:T_ORC;岗位:T_POS"`
  207. Success bool `description:"true 执行成功,false 执行失败"`
  208. Message string `description:"消息"`
  209. Id string `json:"id"`
  210. Timestamp int64 `json:"timestamp"`
  211. ObjectType string `json:"objectType" description:"对象类型:账号:TARGET_ACCOUNT、机构;TARGET_ORGANIZATION、资源:TARGET_RESOURCE、角色:TARGET_ROLE"`
  212. Data UserData `json:"data"`
  213. } `json:"out"`
  214. }
  215. // UserData
  216. // @Description: 用户账户信息
  217. type UserData struct {
  218. Username string `json:"username" description:"统一登录名,和AD账号一致"`
  219. Password string `json:"password" description:"密码"`
  220. FullName string `json:"fullname" description:"姓名"`
  221. IsDisabled bool `json:"isDisabled" description:"状态(true禁用,false启用)"`
  222. StartDate interface{} `json:"startDate" description:""`
  223. EndDate interface{} `json:"endDate" description:""`
  224. PositionId string `json:"positionId" description:"HR人员中所属岗位ID(主岗职位记录中的)"`
  225. DepartId string `json:"departId" description:"HR人员中所属部门ID(主岗职位记录中的)"`
  226. CompanyId string `json:"companyId" description:"HR人员中所属公司ID(主岗职位记录中的)"`
  227. RefOrgid interface{} `json:"ref_orgid" description:""`
  228. PositionName string `json:"positionName" description:"HR人员中所属岗位名称(主岗职位记录中的)"`
  229. CompanyName string `json:"companyName" description:"HR人员中所属公司名称(主岗职位记录中的)"`
  230. DepartmentName string `json:"departmentName" description:"HR人员中所属部门名称(主岗职位记录中的)"`
  231. Mobile string `json:"mobile" description:"手机号"`
  232. OfficePhone string `json:"officePhone" description:""`
  233. Sex string `json:"sex" description:"性别(1男,2女)"`
  234. EmployeeNo string `json:"employeeNo" description:"员工号。"`
  235. }
  236. // SyncTask
  237. // @Description: 第三方应用系统集成统一身份管理平台,通过调用syncTask同步接口,从统一身份管理平台全量同步数据(账号、机构、岗位
  238. // @author: Roc
  239. // @datetime 2024-01-18 13:30:38
  240. // @param tokenId string
  241. // @return resp *BaseResponse
  242. // @return err error
  243. func SyncTask(tokenId string) (userResp *SyncTaskUserResp, err error) {
  244. urlPath := `/IAM/XYGIntegrationService/syncTask/ProxyServices/syncTaskPS`
  245. req := LogoutReq{
  246. SystemCode: global.CONFIG.Xiangyu.SystemCode,
  247. In0: In0{
  248. PageTotal: "",
  249. PageNo: "",
  250. DocType: "syncTask",
  251. Property: "",
  252. DocCode: getDocCode(),
  253. Source: global.CONFIG.Xiangyu.SystemCode,
  254. Target: global.CONFIG.Xiangyu.UserSyncTarget,
  255. },
  256. TokenId: tokenId,
  257. }
  258. postData, err := json.Marshal(req)
  259. if err != nil {
  260. return
  261. }
  262. result, err := HttpPost(urlPath, string(postData), "application/json")
  263. if err != nil {
  264. return
  265. }
  266. var baseResp *SyncTaskResp
  267. err = json.Unmarshal(result, &baseResp)
  268. if err != nil {
  269. return
  270. }
  271. if baseResp.Out.Success == false {
  272. err = errors.New(fmt.Sprintf("响应代码:%s,响应消息:%s,错误信息:%s", baseResp.Out.ReturnCode, baseResp.Out.ReturnMsg, baseResp.Out.Message))
  273. return
  274. }
  275. // 如果不是账号信息的话,那么就过滤,不做处理
  276. if baseResp.Out.ObjectType != "TARGET_ACCOUNT" {
  277. return
  278. }
  279. // 解析数据 获取账号信息
  280. err = json.Unmarshal(result, &userResp)
  281. if err != nil {
  282. return
  283. }
  284. return
  285. }
  286. // SyncFinishReq
  287. // @Description: 结束同步的接口请求
  288. type SyncFinishReq struct {
  289. SystemCode string `json:"systemCode" description:"来源系统"`
  290. In0 In0 `json:"in0"`
  291. TokenId string `json:"tokenId" description:"令牌id,login接口生成"`
  292. ObjectCode string `json:"objectCode" description:"对象代码,BIM中注册对象代码"`
  293. ObjectType string `json:"objectType" description:"对象类型:账号:TARGET__ACCOUNT、机构:TARGET_ORGANIZATION、资源:TARGET__RESOURCE、角色:TARGET_ROLE"`
  294. Id string `json:"id" description:"BIM中对象ID,从syncTask响应中获取"`
  295. Success bool `json:"success" description:"成功--true,失败--false"`
  296. Data interface{} `json:"data" description:"默认给空Map对象{)不能为null"`
  297. Guid string `json:"guid" description:"下游系统中对象主键字段success=true时必须"`
  298. Message string `json:"message" description:"success=false时必须"`
  299. }
  300. // SyncFinish
  301. // @Description: syncFinish 接口需要配合syncTask 接 口 同 时 使 用 ,syncFinish 接口作用是:应用系统调用syncTask 接口同步数据,并对数据做处理后,将结果通过syncFinish接口回写到统一身份管理平台
  302. // @author: Roc
  303. // @datetime 2024-01-18 13:30:38
  304. // @param tokenId string
  305. // @return resp *BaseResponse
  306. // @return err error
  307. func SyncFinish(tokenId, objectCode, objectType, id, guid, message string, success bool) (err error) {
  308. urlPath := `/IAM/XYGIntegrationService/syncFinish/ProxyServices/syncFinishPS`
  309. req := SyncFinishReq{
  310. SystemCode: global.CONFIG.Xiangyu.SystemCode,
  311. In0: In0{
  312. PageTotal: "",
  313. PageNo: "",
  314. DocType: "syncFinish",
  315. Property: "",
  316. DocCode: getDocCode(),
  317. Source: global.CONFIG.Xiangyu.SystemCode,
  318. Target: global.CONFIG.Xiangyu.UserSyncTarget,
  319. },
  320. TokenId: tokenId,
  321. ObjectCode: objectCode,
  322. ObjectType: objectType,
  323. Id: id,
  324. Success: success,
  325. Data: struct{}{},
  326. Guid: guid,
  327. Message: message,
  328. }
  329. postData, err := json.Marshal(req)
  330. if err != nil {
  331. return
  332. }
  333. result, err := HttpPost(urlPath, string(postData), "application/json")
  334. if err != nil {
  335. return
  336. }
  337. // 解析响应结果
  338. var resp *LoginResp
  339. err = json.Unmarshal(result, &resp)
  340. if err != nil {
  341. return
  342. }
  343. if resp.Out.Success == false {
  344. err = errors.New(fmt.Sprintf("响应代码:%s,响应消息:%s,错误信息:%s", resp.Out.ReturnCode, resp.Out.ReturnMsg, resp.Out.Message))
  345. return
  346. }
  347. return
  348. }
  349. // PullTaskUserResp
  350. // @Description: 增量同步的账号响应数据
  351. type PullTaskUserResp struct {
  352. Out struct {
  353. ReturnCode string `json:"returnCode" description:"响应代码,成功--S,失败--F"`
  354. ReturnMsg string `json:"returnMsg" description:"响应消息"`
  355. ObjectCode string `json:"objectCode" description:"BIM中注册对象代码:账号:T_ACC;机构:T_ORC;岗位:T_POS"`
  356. Success bool `description:"true 执行成功,false 执行失败"`
  357. Message string `description:"消息"`
  358. Id string `json:"id" description:"身份管理平台内部对象ID"`
  359. Timestamp int64 `json:"timestamp"`
  360. ObjectType string `json:"objectType" description:"对象类型:账号:TARGET_ACCOUNT、机构;TARGET_ORGANIZATION、资源:TARGET_RESOURCE、角色:TARGET_ROLE"`
  361. Data UserData `json:"data"`
  362. GUid string `json:"guid" description:"下游数据主键,下游系统下拉到的数据后,若要做更新、启 用、禁用操作,可根据此字段查询到对应记录。"`
  363. EffectOn string `json:"effectOn" description:"作用点,任务操作类型;创建:CREATED、更新:UPDATED、禁用:DISABLED、启用:ENABLED。"`
  364. TaskId string `json:"Taskid" description:"任务id,身份管理平台下拉任务ID"`
  365. } `json:"out"`
  366. }
  367. // PullTask
  368. // @Description: 第三方应用系统集成统一身份管理平台,通过调用pulITask 下拉接口,从统一身份管理平台获取身份信息(机构、账号、岗位)。 注:下拉接口只会从统一身份管理平台下拉变更(新增、更新、启用、禁用)的记录,并且每一条变更记录在统一身份管理平台,都是 以待处理任务形式存在。 pullTask 接口下拉逻辑为:每调用一次下拉接口,获取一条待处理任务(任务中有详细身份数据)。当接口响应中 "objectCode" 为N U L L 时 , 表 示 统 一 身 份 管 理 平 台 待 处 理 任 务 全 部 下 拉 完 成 。
  369. // @Description: 这个接口只会返回一条数据,所以同步账号的时候,需要循环调用
  370. // @author: Roc
  371. // @datetime 2024-01-16 14:04:47
  372. // @param tokenId string
  373. // @return resp *BaseResponse
  374. // @return err error
  375. func PullTask(tokenId string) (userResp *PullTaskUserResp, err error) {
  376. urlPath := `/IAM/XYGIntegrationService/pullTask/ProxyServices/pullTaskPS`
  377. req := LogoutReq{
  378. SystemCode: global.CONFIG.Xiangyu.SystemCode,
  379. In0: In0{
  380. PageTotal: "",
  381. PageNo: "",
  382. DocType: "pullTask",
  383. Property: "",
  384. DocCode: getDocCode(),
  385. Source: global.CONFIG.Xiangyu.SystemCode,
  386. Target: global.CONFIG.Xiangyu.UserSyncTarget,
  387. },
  388. TokenId: tokenId,
  389. }
  390. postData, err := json.Marshal(req)
  391. if err != nil {
  392. return
  393. }
  394. result, err := HttpPost(urlPath, string(postData), "application/json")
  395. if err != nil {
  396. return
  397. }
  398. var baseResp *SyncTaskResp
  399. err = json.Unmarshal(result, &baseResp)
  400. if err != nil {
  401. return
  402. }
  403. if baseResp.Out.Success == false {
  404. err = errors.New(fmt.Sprintf("响应代码:%s,响应消息:%s,错误信息:%s", baseResp.Out.ReturnCode, baseResp.Out.ReturnMsg, baseResp.Out.Message))
  405. return
  406. }
  407. // 如果不是账号信息的话,那么就过滤,不做处理
  408. if baseResp.Out.ObjectType != "TARGET_ACCOUNT" {
  409. return
  410. }
  411. // 解析数据 获取账号信息
  412. err = json.Unmarshal(result, &userResp)
  413. if err != nil {
  414. return
  415. }
  416. return
  417. }
  418. type PullFinishReq struct {
  419. SystemCode string `json:"systemCode" description:"来源系统"`
  420. In0 In0 `json:"in0"`
  421. TokenId string `json:"tokenId" description:"令牌id,login接口生成"`
  422. TaskId string `json:"taskId" description:"任务ID,pullTask获取的下拉任务ID"`
  423. Guid string `json:"guid" description:"唯一标识,第三方系统中对象唯一标识success=true时必须"`
  424. Success bool `json:"success" description:"true 成功,false 失败"`
  425. Message string `json:"message" description:"错误消息,success=false时必须"`
  426. }
  427. // PullFinish
  428. // @Description: pullFinish接口作用是:应用系统调用pullTask 接口下拉数据,并对数据做处理后,将结果通过pullFinish接口回写到统一身份管理平台,统一身份管理平台根据结果标记下拉任务状态。
  429. // @Description: pullFinish接口需要配合pullTask 接口同时使用。
  430. // @author: Roc
  431. // @datetime 2024-01-16 14:17:27
  432. // @param tokenId string
  433. // @param taskId string
  434. // @param guid string
  435. // @param success bool
  436. // @param message string
  437. // @return resp *BaseResponse
  438. // @return err error
  439. func PullFinish(tokenId, taskId, guid, message string, success bool) (err error) {
  440. urlPath := `/IAM/XYGIntegrationService/pullFinish/ProxyServices/pullFinishPS`
  441. req := PullFinishReq{
  442. SystemCode: global.CONFIG.Xiangyu.SystemCode,
  443. In0: In0{
  444. PageTotal: "",
  445. PageNo: "",
  446. DocType: "pullFinish",
  447. Property: "",
  448. DocCode: getDocCode(),
  449. Source: global.CONFIG.Xiangyu.SystemCode,
  450. Target: global.CONFIG.Xiangyu.UserSyncTarget,
  451. },
  452. TokenId: tokenId,
  453. TaskId: taskId,
  454. Guid: guid,
  455. Success: success,
  456. Message: message,
  457. }
  458. postData, err := json.Marshal(req)
  459. if err != nil {
  460. return
  461. }
  462. result, err := HttpPost(urlPath, string(postData), "application/json")
  463. if err != nil {
  464. return
  465. }
  466. // 解析响应结果
  467. var resp *LoginResp
  468. err = json.Unmarshal(result, &resp)
  469. if err != nil {
  470. return
  471. }
  472. if resp.Out.Success == false {
  473. err = errors.New(fmt.Sprintf("响应代码:%s,响应消息:%s,错误信息:%s", resp.Out.ReturnCode, resp.Out.ReturnMsg, resp.Out.Message))
  474. return
  475. }
  476. return
  477. }
  478. // getDocCode
  479. // @Description: 获取单据号码
  480. // @author: Roc
  481. // @datetime 2024-01-16 10:29:02
  482. // @return string
  483. func getDocCode() string {
  484. return fmt.Sprintf("%s-%s", time.Now().Format(utils.FormatDateTimeUnSpace), utils.GetRandStringNoSpecialChar(32))
  485. }
  486. func HttpPost(urlPath, postData string, params ...string) ([]byte, error) {
  487. if global.CONFIG.Xiangyu.UserSyncHost == `` {
  488. return nil, errors.New("统一用户同步接口地址为空")
  489. }
  490. // 请求地址
  491. postUrl := global.CONFIG.Xiangyu.UserSyncHost + urlPath
  492. //body := strings.NewReader(postData)
  493. body := io.NopCloser(strings.NewReader(postData))
  494. client := &http.Client{}
  495. req, err := http.NewRequest("POST", postUrl, body)
  496. if err != nil {
  497. return nil, err
  498. }
  499. contentType := "application/x-www-form-urlencoded;charset=utf-8"
  500. if len(params) > 0 && params[0] != "" {
  501. contentType = params[0]
  502. }
  503. req.Header.Set("content-Type", contentType)
  504. req.SetBasicAuth(global.CONFIG.Xiangyu.UserSyncAuthUserName, global.CONFIG.Xiangyu.UserSyncAuthPwd)
  505. resp, err := client.Do(req)
  506. if err != nil {
  507. return nil, err
  508. }
  509. defer resp.Body.Close()
  510. result, err := io.ReadAll(resp.Body)
  511. if err != nil {
  512. return nil, err
  513. }
  514. // 日志记录
  515. global.FILE_LOG.Debug("统一身份:地址:" + postUrl + ";\n请求参数:" + postData + ";\n返回参数:" + string(result))
  516. // 解析返回参数,判断是否是json
  517. if !json.Valid(result) {
  518. err = errors.New("返回参数不是json格式")
  519. }
  520. return result, err
  521. }