body_mapping.go 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114
  1. package gateway
  2. import (
  3. "git.sxidc.com/go-framework/baize/framework/binding"
  4. "git.sxidc.com/go-framework/baize/framework/binding/request"
  5. "git.sxidc.com/go-framework/baize/framework/binding/response"
  6. "git.sxidc.com/go-framework/baize/framework/core/api"
  7. "git.sxidc.com/go-framework/baize/framework/core/domain"
  8. "git.sxidc.com/go-framework/baize/framework/core/infrastructure"
  9. "git.sxidc.com/go-framework/baize/framework/core/infrastructure/logger"
  10. "git.sxidc.com/go-tools/utils/http_client"
  11. "git.sxidc.com/service-supports/fserr"
  12. "io"
  13. "net/http"
  14. "strings"
  15. "time"
  16. )
  17. func (gw *Gateway) BodyMapping(binder *binding.Binder, bodyMapping *BodyMapping, middlewares ...api.Handler) {
  18. bodyMapping.bind(binder, gw.httpClient, gw.options.timeoutSec, middlewares...)
  19. }
  20. type BodyMapping struct {
  21. HttpMethod string
  22. RelativePath string
  23. ToUrl string
  24. BodyMappingFunc func(body []byte) ([]byte, error)
  25. }
  26. func (bodyMapping *BodyMapping) bind(binder *binding.Binder, httpClient *http_client.Client, timeoutSec int64, middlewares ...api.Handler) {
  27. binding.Bind[any](binder, &binding.BindItem[any]{
  28. Method: bodyMapping.HttpMethod,
  29. SimpleBindItem: &binding.SimpleBindItem[any]{
  30. Path: bodyMapping.RelativePath,
  31. ResponseFunc: response.NoResponse,
  32. ServiceFunc: func(c *api.Context, params request.Params, objects []domain.Object, i *infrastructure.Infrastructure) (any, error) {
  33. body, err := io.ReadAll(c.Request.Body)
  34. if err != nil {
  35. logger.GetInstance().Error(err)
  36. c.AbortWithStatus(http.StatusBadGateway)
  37. return nil, err
  38. }
  39. defer func() {
  40. err := c.Request.Body.Close()
  41. if err != nil {
  42. logger.GetInstance().Error(err)
  43. c.AbortWithStatus(http.StatusBadGateway)
  44. }
  45. }()
  46. if bodyMapping.BodyMappingFunc != nil {
  47. newBody, err := bodyMapping.BodyMappingFunc(body)
  48. if err != nil {
  49. logger.GetInstance().Error(err)
  50. c.AbortWithStatus(http.StatusBadGateway)
  51. return nil, err
  52. }
  53. body = newBody
  54. }
  55. headers := make(map[string]string)
  56. for key, values := range c.Request.Header {
  57. headers[key] = strings.Join(values, ",")
  58. }
  59. var httpResponse *http_client.Response
  60. httpRequest := httpClient.
  61. NewRequest(http_client.WithNewRequestTimeout(time.Duration(timeoutSec) * time.Second))
  62. switch bodyMapping.HttpMethod {
  63. case http.MethodPost:
  64. resp, err := httpRequest.Post(bodyMapping.ToUrl, body, http_client.WithRequestHeaders(headers))
  65. if err != nil {
  66. logger.GetInstance().Error(err)
  67. c.AbortWithStatus(http.StatusBadGateway)
  68. return nil, err
  69. }
  70. httpResponse = resp
  71. case http.MethodPut:
  72. resp, err := httpRequest.Put(bodyMapping.ToUrl, body, http_client.WithRequestHeaders(headers))
  73. if err != nil {
  74. logger.GetInstance().Error(err)
  75. c.AbortWithStatus(http.StatusBadGateway)
  76. return nil, err
  77. }
  78. httpResponse = resp
  79. default:
  80. err := fserr.New("不支持Body传递参数")
  81. logger.GetInstance().Error(err)
  82. c.AbortWithStatus(http.StatusBadGateway)
  83. return nil, err
  84. }
  85. c.Status(http.StatusOK)
  86. _, err = c.Writer.Write(httpResponse.Body())
  87. if err != nil {
  88. logger.GetInstance().Error(err)
  89. c.AbortWithStatus(http.StatusBadGateway)
  90. return nil, err
  91. }
  92. c.Writer.Flush()
  93. return nil, nil
  94. },
  95. },
  96. }, middlewares...)
  97. }