Compare commits
	
		
			3 Commits
		
	
	
		
			master
			...
			integrate-
		
	
	| Author | SHA1 | Date | 
|---|---|---|
| 
							
							
								 | 
						d33f3d7063 | |
| 
							
							
								 | 
						8c519bbab7 | |
| 
							
							
								 | 
						09f5647319 | 
| 
						 | 
					@ -167,7 +167,7 @@ func (c *Client) GetOrder(orderCode string) (*GetOrderResponseDecoded, error) {
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func (c *Client) requestNats(subject string, data interface{}) (*nats.Msg, error) {
 | 
					func (c *Client) requestNats(subject string, data interface{}) (*nats.Msg, error) {
 | 
				
			||||||
	b := toBytes(data)
 | 
						b := pjson.ToBytes(data)
 | 
				
			||||||
	return c.natsClient.Request(subject, b)
 | 
						return c.natsClient.Request(subject, b)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -3,27 +3,10 @@ package globalcare
 | 
				
			||||||
import (
 | 
					import (
 | 
				
			||||||
	"crypto/rsa"
 | 
						"crypto/rsa"
 | 
				
			||||||
	"crypto/x509"
 | 
						"crypto/x509"
 | 
				
			||||||
	"encoding/json"
 | 
					 | 
				
			||||||
	"encoding/pem"
 | 
						"encoding/pem"
 | 
				
			||||||
	"fmt"
 | 
						"fmt"
 | 
				
			||||||
 | 
					 | 
				
			||||||
	"git.selly.red/Selly-Modules/logger"
 | 
					 | 
				
			||||||
)
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// toBytes ...
 | 
					 | 
				
			||||||
func toBytes(data interface{}) []byte {
 | 
					 | 
				
			||||||
	b, err := json.Marshal(data)
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		logger.Error("pjson.toBytes", logger.LogData{"payload": data})
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	return b
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// toJSONString ...
 | 
					 | 
				
			||||||
func toJSONString(data interface{}) string {
 | 
					 | 
				
			||||||
	return string(toBytes(data))
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// GeneratePublicKeyFromBytes ...
 | 
					// GeneratePublicKeyFromBytes ...
 | 
				
			||||||
func generatePublicKeyFromBytes(b []byte) (*rsa.PublicKey, error) {
 | 
					func generatePublicKeyFromBytes(b []byte) (*rsa.PublicKey, error) {
 | 
				
			||||||
	pubPem, _ := pem.Decode(b)
 | 
						pubPem, _ := pem.Decode(b)
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -0,0 +1,54 @@
 | 
				
			||||||
 | 
					package shiip
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					const (
 | 
				
			||||||
 | 
						TimeLayout = "2006-01-02 15:04:05"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						apiPathCreateOutboundRequest             = "/v1/api/external/vietful/outbound/requests"
 | 
				
			||||||
 | 
						apiPathGetOutboundRequest                = "/v1/api/external/vietful/outbound/requests/%d"
 | 
				
			||||||
 | 
						apiPathCancelOutboundRequest             = "/v1/api/external/vietful/outbound/requests/%d/cancel"
 | 
				
			||||||
 | 
						apiPathUpdateLogisticInfoOutboundRequest = "/v1/api/external/vietful/outbound/requests/%d/logistic-info"
 | 
				
			||||||
 | 
						apiPathAuth                              = "/v1/api/external/vietful/auth/access-token"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						PriorityUrgent = 3
 | 
				
			||||||
 | 
						PriorityHigh   = 2
 | 
				
			||||||
 | 
						PriorityNormal = 1
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						TPLCodeGHN          = "GHN"
 | 
				
			||||||
 | 
						TPLCodeGHTK         = "GHTK"
 | 
				
			||||||
 | 
						TPLCodeBest         = "BEST"
 | 
				
			||||||
 | 
						TPLCodeSnappy       = "SPY"
 | 
				
			||||||
 | 
						TPLCodeViettelPost  = "VTP"
 | 
				
			||||||
 | 
						TPLCodeSellyExpress = "SE"
 | 
				
			||||||
 | 
						TPLCodeJTExpress    = "JTE"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						ShippingServiceCodeSTD = "STD"
 | 
				
			||||||
 | 
						ORTypeOrder            = 1
 | 
				
			||||||
 | 
						ShippingTypeSelfShip   = 1
 | 
				
			||||||
 | 
						PackTypeNormal         = 1
 | 
				
			||||||
 | 
						BizTypeB2C             = 1
 | 
				
			||||||
 | 
						ConditionTypeCodeNew   = "NEW"
 | 
				
			||||||
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					const (
 | 
				
			||||||
 | 
						baseURLAuthStaging = "https://api.shiip.vn"
 | 
				
			||||||
 | 
						baseURLStaging     = "https://api.shiip.vn"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// TODO: add base URL
 | 
				
			||||||
 | 
						baseURLAuthProd = ""
 | 
				
			||||||
 | 
						baseURLProd     = ""
 | 
				
			||||||
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					const (
 | 
				
			||||||
 | 
						ErrCodeExistPartnerCode = "exist_partner_code"
 | 
				
			||||||
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					var (
 | 
				
			||||||
 | 
						baseURLENVMapping = map[ENV]string{
 | 
				
			||||||
 | 
							EnvProd:    baseURLProd,
 | 
				
			||||||
 | 
							EnvStaging: baseURLStaging,
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						baseURLAuthENVMapping = map[ENV]string{
 | 
				
			||||||
 | 
							EnvProd:    baseURLAuthProd,
 | 
				
			||||||
 | 
							EnvStaging: baseURLAuthStaging,
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					)
 | 
				
			||||||
| 
						 | 
					@ -0,0 +1,9 @@
 | 
				
			||||||
 | 
					package shiip
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// ENV ...
 | 
				
			||||||
 | 
					type ENV string
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					const (
 | 
				
			||||||
 | 
						EnvStaging ENV = "STAGING"
 | 
				
			||||||
 | 
						EnvProd    ENV = "PROD"
 | 
				
			||||||
 | 
					)
 | 
				
			||||||
| 
						 | 
					@ -0,0 +1,22 @@
 | 
				
			||||||
 | 
					package shiip
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					import (
 | 
				
			||||||
 | 
						"fmt"
 | 
				
			||||||
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// Error ...
 | 
				
			||||||
 | 
					type Error struct {
 | 
				
			||||||
 | 
						Code    string `json:"code"`
 | 
				
			||||||
 | 
						Message string `json:"errorMessage"`
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// Error ...
 | 
				
			||||||
 | 
					func (e Error) Error() string {
 | 
				
			||||||
 | 
						return fmt.Sprintf("tnc_err: code %s, messsage %s", e.Code, e.Message)
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// IsErrExistPartnerCode ...
 | 
				
			||||||
 | 
					func IsErrExistPartnerCode(err error) bool {
 | 
				
			||||||
 | 
						e, ok := err.(Error)
 | 
				
			||||||
 | 
						return ok && e.Code == ErrCodeExistPartnerCode
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
| 
						 | 
					@ -0,0 +1,62 @@
 | 
				
			||||||
 | 
					package shiip
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// Product ...
 | 
				
			||||||
 | 
					type Product struct {
 | 
				
			||||||
 | 
						PartnerSKU        string `json:"partnerSKU"`
 | 
				
			||||||
 | 
						UnitCode          string `json:"unitCode"`
 | 
				
			||||||
 | 
						ConditionTypeCode string `json:"conditionTypeCode"`
 | 
				
			||||||
 | 
						Quantity          int64  `json:"quantity"`
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// Address ...
 | 
				
			||||||
 | 
					type Address struct {
 | 
				
			||||||
 | 
						AddressNo    string `json:"addressNo"`
 | 
				
			||||||
 | 
						ProvinceCode string `json:"provinceCode,omitempty"`
 | 
				
			||||||
 | 
						DistrictCode string `json:"districtCode,omitempty"`
 | 
				
			||||||
 | 
						WardCode     string `json:"wardCode,omitempty"`
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// OutboundRequestPayload ...
 | 
				
			||||||
 | 
					type OutboundRequestPayload struct {
 | 
				
			||||||
 | 
						WarehouseCode       string    `json:"warehouseCode"`
 | 
				
			||||||
 | 
						ShippingServiceCode string    `json:"shippingServiceCode"`
 | 
				
			||||||
 | 
						PartnerORCode       string    `json:"partnerORCode"`
 | 
				
			||||||
 | 
						PartnerRefId        string    `json:"partnerRefId"`
 | 
				
			||||||
 | 
						RefCode             string    `json:"refCode"`
 | 
				
			||||||
 | 
						CodAmount           float64   `json:"codAmount"`
 | 
				
			||||||
 | 
						PriorityType        int       `json:"priorityType"`
 | 
				
			||||||
 | 
						CustomerName        string    `json:"customerName"`
 | 
				
			||||||
 | 
						CustomerPhoneNumber string    `json:"customerPhoneNumber"`
 | 
				
			||||||
 | 
						Type                int       `json:"type"`
 | 
				
			||||||
 | 
						ShippingType        int       `json:"shippingType"`
 | 
				
			||||||
 | 
						VehicleNumber       string    `json:"vehicleNumber"`
 | 
				
			||||||
 | 
						ContainerNumber     string    `json:"containerNumber"`
 | 
				
			||||||
 | 
						PackType            int       `json:"packType"`
 | 
				
			||||||
 | 
						PackingNote         string    `json:"packingNote"`
 | 
				
			||||||
 | 
						CustomLabel         bool      `json:"customLabel"`
 | 
				
			||||||
 | 
						BizType             int       `json:"bizType"`
 | 
				
			||||||
 | 
						Note                string    `json:"note"`
 | 
				
			||||||
 | 
						ShippingAddress     Address   `json:"shippingAddress"`
 | 
				
			||||||
 | 
						Products            []Product `json:"products"`
 | 
				
			||||||
 | 
						PartnerCreationTime string    `json:"partnerCreationTime"`
 | 
				
			||||||
 | 
						TPLCode             string    `json:"tplCode"`
 | 
				
			||||||
 | 
						TrackingCode        string    `json:"trackingCode"`
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// UpdateORLogisticInfoPayload ...
 | 
				
			||||||
 | 
					type UpdateORLogisticInfoPayload struct {
 | 
				
			||||||
 | 
						OrID           int     `json:"orId"`
 | 
				
			||||||
 | 
						TrackingCode   string  `json:"trackingCode"`
 | 
				
			||||||
 | 
						ShippingLabels []Label `json:"shippingLabels"`
 | 
				
			||||||
 | 
						TPLCode        string  `json:"tplCode"`
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					type Label struct {
 | 
				
			||||||
 | 
						Caption string `json:"caption"`
 | 
				
			||||||
 | 
						URI     string `json:"uri"`
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					type AuthPayload struct {
 | 
				
			||||||
 | 
						ClientID     string `json:"clientId"`
 | 
				
			||||||
 | 
						ClientSecret string `json:"clientSecret"`
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
| 
						 | 
					@ -0,0 +1,57 @@
 | 
				
			||||||
 | 
					package shiip
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// OutboundRequestRes ...
 | 
				
			||||||
 | 
					type OutboundRequestRes struct {
 | 
				
			||||||
 | 
						OrID          int    `json:"orId"`
 | 
				
			||||||
 | 
						OrCode        string `json:"orCode"`
 | 
				
			||||||
 | 
						PartnerORCode string `json:"partnerORCode"`
 | 
				
			||||||
 | 
						Error         *Error `json:"error"`
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					type authRes struct {
 | 
				
			||||||
 | 
						AccessToken      string `json:"access_token"`
 | 
				
			||||||
 | 
						ExpiresIn        int    `json:"expires_in"`
 | 
				
			||||||
 | 
						RefreshExpiresIn int    `json:"refresh_expires_in"`
 | 
				
			||||||
 | 
						RefreshToken     string `json:"refresh_token"`
 | 
				
			||||||
 | 
						TokenType        string `json:"token_type"`
 | 
				
			||||||
 | 
						NotBeforePolicy  int    `json:"not-before-policy"`
 | 
				
			||||||
 | 
						SessionState     string `json:"session_state"`
 | 
				
			||||||
 | 
						Scope            string `json:"scope"`
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// Webhook ...
 | 
				
			||||||
 | 
					type Webhook struct {
 | 
				
			||||||
 | 
						OrId          int    `json:"orId"`
 | 
				
			||||||
 | 
						PartnerORCode string `json:"partnerORCode"`
 | 
				
			||||||
 | 
						ErrorCode     string `json:"errorCode"`
 | 
				
			||||||
 | 
						ErrorMessage  string `json:"errorMessage"`
 | 
				
			||||||
 | 
						Event         string `json:"event"`
 | 
				
			||||||
 | 
						Id            string `json:"id"`
 | 
				
			||||||
 | 
						Timestamp     int64  `json:"timestamp"`
 | 
				
			||||||
 | 
						Note          string `json:"note"`
 | 
				
			||||||
 | 
						OrCode        string `json:"orCode"`
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// OutboundRequestInfo ...
 | 
				
			||||||
 | 
					type OutboundRequestInfo struct {
 | 
				
			||||||
 | 
						OrId                  int     `json:"orId"`
 | 
				
			||||||
 | 
						OrCode                string  `json:"orCode"`
 | 
				
			||||||
 | 
						PartnerORCode         string  `json:"partnerORCode"`
 | 
				
			||||||
 | 
						OriginalPartnerOrCode string  `json:"originalPartnerOrCode"`
 | 
				
			||||||
 | 
						PartnerRefId          string  `json:"partnerRefId"`
 | 
				
			||||||
 | 
						RefCode               string  `json:"refCode"`
 | 
				
			||||||
 | 
						WarehouseCode         string  `json:"warehouseCode"`
 | 
				
			||||||
 | 
						Status                string  `json:"status"`
 | 
				
			||||||
 | 
						Note                  string  `json:"note"`
 | 
				
			||||||
 | 
						ShippingType          int     `json:"shippingType"`
 | 
				
			||||||
 | 
						PriorityType          int     `json:"priorityType"`
 | 
				
			||||||
 | 
						PackType              int     `json:"packType"`
 | 
				
			||||||
 | 
						BizType               int     `json:"bizType"`
 | 
				
			||||||
 | 
						CustomerName          string  `json:"customerName"`
 | 
				
			||||||
 | 
						CustomerPhoneNumber   string  `json:"customerPhoneNumber"`
 | 
				
			||||||
 | 
						ShippingFullAddress   string  `json:"shippingFullAddress"`
 | 
				
			||||||
 | 
						CodAmount             float64 `json:"codAmount"`
 | 
				
			||||||
 | 
						ExpectedDeliveryTime  string  `json:"expectedDeliveryTime"`
 | 
				
			||||||
 | 
						CreatedDate           string  `json:"createdDate"`
 | 
				
			||||||
 | 
						ErrorMessage          string  `json:"errorMessage"`
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
| 
						 | 
					@ -0,0 +1,295 @@
 | 
				
			||||||
 | 
					package shiip
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					import (
 | 
				
			||||||
 | 
						"fmt"
 | 
				
			||||||
 | 
						"log"
 | 
				
			||||||
 | 
						"net/http"
 | 
				
			||||||
 | 
						"time"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						"git.selly.red/Selly-Modules/natsio"
 | 
				
			||||||
 | 
						"git.selly.red/Selly-Modules/natsio/model"
 | 
				
			||||||
 | 
						"git.selly.red/Selly-Modules/natsio/subject"
 | 
				
			||||||
 | 
						"github.com/nats-io/nats.go"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						"git.selly.red/Selly-Modules/3pl/util/httputil"
 | 
				
			||||||
 | 
						"git.selly.red/Selly-Modules/3pl/util/pjson"
 | 
				
			||||||
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// Client ...
 | 
				
			||||||
 | 
					type Client struct {
 | 
				
			||||||
 | 
						realm        string
 | 
				
			||||||
 | 
						clientID     string
 | 
				
			||||||
 | 
						clientSecret string
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						env        ENV
 | 
				
			||||||
 | 
						natsClient natsio.Server
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						token         string
 | 
				
			||||||
 | 
						tokenExpireAt time.Time
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// NewClient ...
 | 
				
			||||||
 | 
					func NewClient(env ENV, clientID, clientSecret, realm string, natsClient natsio.Server) (*Client, error) {
 | 
				
			||||||
 | 
						if env != EnvProd && env != EnvStaging {
 | 
				
			||||||
 | 
							return nil, fmt.Errorf("shiip.NewClient: invalid_env %s", env)
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						return &Client{
 | 
				
			||||||
 | 
							realm:        realm,
 | 
				
			||||||
 | 
							clientID:     clientID,
 | 
				
			||||||
 | 
							clientSecret: clientSecret,
 | 
				
			||||||
 | 
							token:        "",
 | 
				
			||||||
 | 
							env:          env,
 | 
				
			||||||
 | 
							natsClient:   natsClient,
 | 
				
			||||||
 | 
						}, nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// CreateOutboundRequest ...
 | 
				
			||||||
 | 
					func (c *Client) CreateOutboundRequest(p OutboundRequestPayload) (*OutboundRequestRes, error) {
 | 
				
			||||||
 | 
						apiURL := c.getBaseURL() + apiPathCreateOutboundRequest
 | 
				
			||||||
 | 
						natsPayload := model.CommunicationRequestHttp{
 | 
				
			||||||
 | 
							ResponseImmediately: true,
 | 
				
			||||||
 | 
							Payload: model.HttpRequest{
 | 
				
			||||||
 | 
								URL:    apiURL,
 | 
				
			||||||
 | 
								Method: http.MethodPost,
 | 
				
			||||||
 | 
								Data:   pjson.ToJSONString([]OutboundRequestPayload{p}),
 | 
				
			||||||
 | 
								Header: c.getRequestHeader(),
 | 
				
			||||||
 | 
							},
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						msg, err := c.requestHttpViaNats(natsPayload)
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							log.Printf("shiip.Client.CreateOutboundRequest - requestHttpViaNats: %v, %+v\n", err, natsPayload)
 | 
				
			||||||
 | 
							return nil, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						var (
 | 
				
			||||||
 | 
							r       model.CommunicationHttpResponse
 | 
				
			||||||
 | 
							errRes  Error
 | 
				
			||||||
 | 
							dataRes []OutboundRequestRes
 | 
				
			||||||
 | 
						)
 | 
				
			||||||
 | 
						if err = pjson.Unmarshal(msg.Data, &r); err != nil {
 | 
				
			||||||
 | 
							return nil, fmt.Errorf("shiip.Client.CreateOutboundRequest: parse_data %v", err)
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						res := r.Response
 | 
				
			||||||
 | 
						if res == nil {
 | 
				
			||||||
 | 
							return nil, fmt.Errorf("shiip.Client.CreateOutboundRequest: empty_response")
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if res.StatusCode >= http.StatusBadRequest {
 | 
				
			||||||
 | 
							if err = r.ParseResponseData(&errRes); err != nil {
 | 
				
			||||||
 | 
								return nil, fmt.Errorf("shiip.Client.CreateOutboundRequest: parse_response_err: %v", err)
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							return nil, errRes
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if err = r.ParseResponseData(&dataRes); err != nil {
 | 
				
			||||||
 | 
							return nil, fmt.Errorf("shiip.Client.CreateOutboundRequest: parse_response_data: %v", err)
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if len(dataRes) == 0 {
 | 
				
			||||||
 | 
							return nil, fmt.Errorf("shiip.Client.CreateOutboundRequest: empty_result")
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						item := &dataRes[0]
 | 
				
			||||||
 | 
						e := item.Error
 | 
				
			||||||
 | 
						if e != nil {
 | 
				
			||||||
 | 
							return nil, errRes
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return item, err
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// UpdateOutboundRequestLogisticInfo ...
 | 
				
			||||||
 | 
					func (c *Client) UpdateOutboundRequestLogisticInfo(p UpdateORLogisticInfoPayload) error {
 | 
				
			||||||
 | 
						apiURL := c.getBaseURL() + fmt.Sprintf(apiPathUpdateLogisticInfoOutboundRequest, p.OrID)
 | 
				
			||||||
 | 
						natsPayload := model.CommunicationRequestHttp{
 | 
				
			||||||
 | 
							ResponseImmediately: true,
 | 
				
			||||||
 | 
							Payload: model.HttpRequest{
 | 
				
			||||||
 | 
								URL:    apiURL,
 | 
				
			||||||
 | 
								Method: http.MethodPost,
 | 
				
			||||||
 | 
								Header: c.getRequestHeader(),
 | 
				
			||||||
 | 
								Data:   pjson.ToJSONString(p),
 | 
				
			||||||
 | 
							},
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						msg, err := c.requestHttpViaNats(natsPayload)
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							log.Printf("shiip.Client.UpdateOutboundRequestLogisticInfo - requestHttpViaNats: %v, %+v\n", err, natsPayload)
 | 
				
			||||||
 | 
							return err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						var (
 | 
				
			||||||
 | 
							r      model.CommunicationHttpResponse
 | 
				
			||||||
 | 
							errRes Error
 | 
				
			||||||
 | 
						)
 | 
				
			||||||
 | 
						if err = pjson.Unmarshal(msg.Data, &r); err != nil {
 | 
				
			||||||
 | 
							return fmt.Errorf("shiip.Client.UpdateOutboundRequestLogisticInfo: parse_data %v", err)
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						res := r.Response
 | 
				
			||||||
 | 
						if res == nil {
 | 
				
			||||||
 | 
							return fmt.Errorf("shiip.Client.UpdateOutboundRequestLogisticInfo: empty_response")
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if res.StatusCode >= http.StatusBadRequest {
 | 
				
			||||||
 | 
							if err = r.ParseResponseData(&errRes); err != nil {
 | 
				
			||||||
 | 
								return fmt.Errorf("shiip.Client.UpdateOutboundRequestLogisticInfo: parse_response_err: %v", err)
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							return errRes
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						return nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// GetOutboundRequestByID ...
 | 
				
			||||||
 | 
					func (c *Client) GetOutboundRequestByID(requestID int) (*OutboundRequestInfo, error) {
 | 
				
			||||||
 | 
						apiURL := c.getBaseURL() + fmt.Sprintf(apiPathGetOutboundRequest, requestID)
 | 
				
			||||||
 | 
						natsPayload := model.CommunicationRequestHttp{
 | 
				
			||||||
 | 
							ResponseImmediately: true,
 | 
				
			||||||
 | 
							Payload: model.HttpRequest{
 | 
				
			||||||
 | 
								URL:    apiURL,
 | 
				
			||||||
 | 
								Method: http.MethodGet,
 | 
				
			||||||
 | 
								Header: c.getRequestHeader(),
 | 
				
			||||||
 | 
							},
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						msg, err := c.requestHttpViaNats(natsPayload)
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							log.Printf("shiip.Client.GetOutboundRequestByID - requestHttpViaNats: %v, %+v\n", err, natsPayload)
 | 
				
			||||||
 | 
							return nil, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						var (
 | 
				
			||||||
 | 
							r               model.CommunicationHttpResponse
 | 
				
			||||||
 | 
							errRes          Error
 | 
				
			||||||
 | 
							outboundRequest OutboundRequestInfo
 | 
				
			||||||
 | 
						)
 | 
				
			||||||
 | 
						if err = pjson.Unmarshal(msg.Data, &r); err != nil {
 | 
				
			||||||
 | 
							return nil, fmt.Errorf("shiip.Client.GetOutboundRequestByID: parse_data %v", err)
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						res := r.Response
 | 
				
			||||||
 | 
						if res == nil {
 | 
				
			||||||
 | 
							return nil, fmt.Errorf("shiip.Client.GetOutboundRequestByID: empty_response")
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if res.StatusCode >= http.StatusBadRequest {
 | 
				
			||||||
 | 
							if err = r.ParseResponseData(&errRes); err != nil {
 | 
				
			||||||
 | 
								return nil, fmt.Errorf("shiip.Client.GetOutboundRequestByID: parse_response_err: %v", err)
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							return nil, errRes
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if err = r.ParseResponseData(&outboundRequest); err != nil {
 | 
				
			||||||
 | 
							return nil, fmt.Errorf("shiip.Client.GetOutboundRequestByID: parse_response_data: %v", err)
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						return &outboundRequest, nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// CancelOutboundRequest ...
 | 
				
			||||||
 | 
					func (c *Client) CancelOutboundRequest(requestID int, note string) error {
 | 
				
			||||||
 | 
						apiURL := c.getBaseURL() + fmt.Sprintf(apiPathCancelOutboundRequest, requestID)
 | 
				
			||||||
 | 
						data := map[string]string{"note": note}
 | 
				
			||||||
 | 
						natsPayload := model.CommunicationRequestHttp{
 | 
				
			||||||
 | 
							ResponseImmediately: true,
 | 
				
			||||||
 | 
							Payload: model.HttpRequest{
 | 
				
			||||||
 | 
								URL:    apiURL,
 | 
				
			||||||
 | 
								Method: http.MethodPost,
 | 
				
			||||||
 | 
								Header: c.getRequestHeader(),
 | 
				
			||||||
 | 
								Data:   pjson.ToJSONString(data),
 | 
				
			||||||
 | 
							},
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						msg, err := c.requestHttpViaNats(natsPayload)
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							log.Printf("shiip.Client.CancelOutboundRequest - requestHttpViaNats: %v, %+v\n", err, natsPayload)
 | 
				
			||||||
 | 
							return err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						var (
 | 
				
			||||||
 | 
							r      model.CommunicationHttpResponse
 | 
				
			||||||
 | 
							errRes Error
 | 
				
			||||||
 | 
						)
 | 
				
			||||||
 | 
						if err = pjson.Unmarshal(msg.Data, &r); err != nil {
 | 
				
			||||||
 | 
							return fmt.Errorf("shiip.Client.CancelOutboundRequest: parse_data %v", err)
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						res := r.Response
 | 
				
			||||||
 | 
						if res == nil {
 | 
				
			||||||
 | 
							return fmt.Errorf("shiip.Client.CancelOutboundRequest: empty_response")
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if res.StatusCode >= http.StatusBadRequest {
 | 
				
			||||||
 | 
							if err = r.ParseResponseData(&errRes); err != nil {
 | 
				
			||||||
 | 
								return fmt.Errorf("shiip.Client.CancelOutboundRequest: parse_response_err: %v", err)
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							return errRes
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						return nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func (c *Client) auth() (*authRes, error) {
 | 
				
			||||||
 | 
						b := AuthPayload{
 | 
				
			||||||
 | 
							ClientID:     c.clientID,
 | 
				
			||||||
 | 
							ClientSecret: c.clientSecret,
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						header := map[string]string{
 | 
				
			||||||
 | 
							httputil.HeaderKeyContentType: httputil.HeaderValueApplicationJSON,
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						apiURL := baseURLAuthENVMapping[c.env] + apiPathAuth
 | 
				
			||||||
 | 
						natsPayload := model.CommunicationRequestHttp{
 | 
				
			||||||
 | 
							ResponseImmediately: true,
 | 
				
			||||||
 | 
							Payload: model.HttpRequest{
 | 
				
			||||||
 | 
								URL:    apiURL,
 | 
				
			||||||
 | 
								Method: http.MethodPost,
 | 
				
			||||||
 | 
								Data:   pjson.ToJSONString(b),
 | 
				
			||||||
 | 
								Header: header,
 | 
				
			||||||
 | 
							},
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						msg, err := c.requestHttpViaNats(natsPayload)
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							log.Printf("shiip.Client.auth - requestHttpViaNats: %v, %+v\n", err, natsPayload)
 | 
				
			||||||
 | 
							return nil, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						var (
 | 
				
			||||||
 | 
							r      model.CommunicationHttpResponse
 | 
				
			||||||
 | 
							errRes Error
 | 
				
			||||||
 | 
							data   authRes
 | 
				
			||||||
 | 
						)
 | 
				
			||||||
 | 
						if err = pjson.Unmarshal(msg.Data, &r); err != nil {
 | 
				
			||||||
 | 
							return nil, fmt.Errorf("shiip.Client.auth: parse_data %v", err)
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						res := r.Response
 | 
				
			||||||
 | 
						if res == nil {
 | 
				
			||||||
 | 
							return nil, fmt.Errorf("shiip.Client.auth: empty_response")
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if res.StatusCode >= http.StatusBadRequest {
 | 
				
			||||||
 | 
							if err = r.ParseResponseData(&errRes); err != nil {
 | 
				
			||||||
 | 
								return nil, fmt.Errorf("shiip.Client.auth: parse_response_err: %v", err)
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							return nil, errRes
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if err = r.ParseResponseData(&data); err != nil {
 | 
				
			||||||
 | 
							return nil, fmt.Errorf("shiip.Client.auth: parse_response_data: %v", err)
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						return &data, nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func (c *Client) getRequestHeader() map[string]string {
 | 
				
			||||||
 | 
						m := map[string]string{
 | 
				
			||||||
 | 
							httputil.HeaderKeyContentType: httputil.HeaderValueApplicationJSON,
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						token, err := c.getToken()
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							log.Printf("shiip.Client.getToken: %v\n", err)
 | 
				
			||||||
 | 
						} else {
 | 
				
			||||||
 | 
							m["Authorization"] = fmt.Sprintf("Bearer %s", token)
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						return m
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func (c *Client) requestHttpViaNats(data model.CommunicationRequestHttp) (*nats.Msg, error) {
 | 
				
			||||||
 | 
						b := pjson.ToBytes(data)
 | 
				
			||||||
 | 
						return c.natsClient.Request(subject.Communication.RequestHTTP, b)
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func (c *Client) getBaseURL() string {
 | 
				
			||||||
 | 
						return baseURLENVMapping[c.env]
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func (c *Client) getToken() (string, error) {
 | 
				
			||||||
 | 
						if c.token != "" || c.tokenExpireAt.After(time.Now()) {
 | 
				
			||||||
 | 
							return c.token, nil
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						data, err := c.auth()
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return "", err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						c.token = data.AccessToken
 | 
				
			||||||
 | 
						d := time.Duration(data.ExpiresIn) * time.Second
 | 
				
			||||||
 | 
						if d.Minutes() > 30 {
 | 
				
			||||||
 | 
							d -= 30 * time.Minute
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						c.tokenExpireAt = time.Now().Add(d)
 | 
				
			||||||
 | 
						return c.token, nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
| 
						 | 
					@ -2,15 +2,14 @@ package pjson
 | 
				
			||||||
 | 
					
 | 
				
			||||||
import (
 | 
					import (
 | 
				
			||||||
	"encoding/json"
 | 
						"encoding/json"
 | 
				
			||||||
 | 
						"log"
 | 
				
			||||||
	"git.selly.red/Selly-Modules/logger"
 | 
					 | 
				
			||||||
)
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// ToBytes ...
 | 
					// ToBytes ...
 | 
				
			||||||
func ToBytes(data interface{}) []byte {
 | 
					func ToBytes(data interface{}) []byte {
 | 
				
			||||||
	b, err := json.Marshal(data)
 | 
						b, err := json.Marshal(data)
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
		logger.Error("pjson.ToBytes", logger.LogData{"payload": data})
 | 
							log.Printf("3pl/util/pjson.ToBytes.Marshal: %v\n", err)
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	return b
 | 
						return b
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
		Reference in New Issue