package itao

import (
	"context"
	"fmt"
	"github.com/gogf/gf/encoding/gjson"
	"github.com/gogf/gf/frame/g"
	"github.com/gogf/gf/text/gstr"
	"github.com/gogf/gf/util/gconv"
)

type order struct {
}

var Order = order{}

type OrderBeforeReq struct {
	Address OrderAddress `json:"deliveryAddressInfo"`
	List    []OrderItem  `json:"itemRequestList"`
}

type OrderAddress struct {
	AddressDetail string `json:"addressDetail"`
	City          string `json:"city"`
	CityId        int64  `json:"cityId"`
	Area          string `json:"district"`
	AreaId        int64  `json:"districtId"`
	FullName      string `json:"fullName"`
	Mobile        string `json:"mobile"`
	Prov          string `json:"prov"`
	ProvId        int64  `json:"provId"`
	Town          string `json:"town"`
	TownId        int64  `json:"townId"`
}

type OrderItem struct {
	Info struct {
		ItemId int64 `json:"itemId"`
		SkuId  int64 `json:"skuId"`
	} `json:"itemInfo"`
	Quantity uint `json:"quantity"`
}

type OrderBeforeRes struct {
	ErrMsg    string `json:"errMsg"`
	ErrCode   string `json:"errCode"`
	Success   bool   `json:"success"`
	GwTraceId string `json:"gw_trace_id"`
	Result    struct {
		ExtensionResp struct {
			TradeId string `json:"tradeId"`
		} `json:"extensionResp"`
		InvalidOrderGroups []struct { //不可售商品
			Image            string `json:"image"`
			OrderLineRenders []struct {
				ErrorMessage struct {
					ErrorCode string `json:"errorCode"`
					ErrorMsg  string `json:"errorMsg"`
				} `json:"errorMessage"`
				ItemInfo struct {
					ItemId string `json:"itemId"`
					SkuId  string `json:"skuId"`
				} `json:"itemInfo"`
				ItemPayPrice uint  `json:"itemPayPrice"`
				OrderLineId  int64 `json:"orderLineId"`
				Quantity     uint  `json:"quantity"`
			} `json:"orderLineRenders"`
			OrderPayPrice int    `json:"orderPayPrice"`
			Quantity      uint   `json:"quantity"`
			SellerToken   string `json:"sellerToken"`
			Title         string `json:"title"`
		} `json:"invalidOrderGroups"`
		OriginPriceFee    uint           `json:"originPriceFee"`
		PriceFee          uint           `json:"priceFee"` //单位分
		PromotionResp     OrderPromotion `json:"promotionResp"`
		Quantity          uint           `json:"quantity"`
		RealPayPrice      uint           `json:"realPayPrice"`
		ReceiveMethodInfo struct {
			DeliveryAddressId int           `json:"deliveryAddressId"`
			Options           []interface{} `json:"options"`
		} `json:"receiveMethodInfo"`
		ValidOrderGroups []struct { //可售商品
			DeliveryMethodInfo struct {
				DeliveryMethodOptionList []struct {
					FareCent    uint   `json:"fareCent"` //运费 单位分
					Id          string `json:"id"`
					ServiceType int    `json:"serviceType"`
				} `json:"deliveryMethodOptionList"`
				SelectedId string `json:"selectedId"`
			} `json:"deliveryMethodInfo"`
			Image            string `json:"image"`
			OrderLineRenders []struct {
				ErrorMessage struct {
					ErrorCode string `json:"errorCode"`
					ErrorMsg  string `json:"errorMsg"`
				}
				ItemInfo struct {
					ItemId      int64  `json:"itemId"`
					Pic         string `json:"pic"`
					Price       string `json:"price"`
					SkuId       string `json:"skuId"`
					SkuInfoList []struct {
						Name  string `json:"name"`
						Value string `json:"value"`
					} `json:"skuInfoList"`
					Title string `json:"title"`
				} `json:"itemInfo"`
				ItemPayPrice uint  `json:"itemPayPrice"`
				OrderLineId  int64 `json:"orderLineId"`
				Quantity     uint  `json:"quantity"`
			} `json:"orderLineRenders"`
			OrderPayPrice int    `json:"orderPayPrice"`
			PostFee       int    `json:"postFee"`
			Quantity      int    `json:"quantity"`
			SellerToken   string `json:"sellerToken"`
			Title         string `json:"title"`
		} `json:"validOrderGroups"`
	} `json:"result"`
}

type OrderPromotion struct {
	CrossShopPromotions []struct {
		Discount     int      `json:"discount"`
		IdValues     []string `json:"idValues"`
		PromotionKey string   `json:"promotionKey"`
	} `json:"crossShopPromotions"`
	InvalidPromotions []interface {
	} `json:"invalidPromotions"`
	ItemPromotions []struct {
		HasPromotion bool `json:"hasPromotion"`
		IdValues     []interface {
		} `json:"idValues"`
		OrderLineId       int64 `json:"orderLineId"`
		PromotionPriceMap struct {
			LtaoMonthPkCard int `json:"ltaoMonthPkCard"`
		} `json:"promotionPriceMap"`
	} `json:"itemPromotions"`
	ShopPromotions []struct {
		Discount             int  `json:"discount"`
		GoldStandardDiscount int  `json:"goldStandardDiscount"`
		HasShopPromotion     bool `json:"hasShopPromotion"`
		IdValues             []interface {
		} `json:"idValues"`
		OutId       string `json:"outId"`
		SellerToken string `json:"sellerToken"`
	} `json:"shopPromotions"`
}

//Before 前置校验
func (s order) Before(ctx context.Context, req OrderBeforeReq) (res *OrderBeforeRes, err error) {
	method := "tt.order.render"

	result, err := server.Post(ctx, method, g.Map{
		"request": req,
	})
	_ = gjson.NewWithOptions(result, gjson.Options{
		StrNumber: true,
	}).Scan(&res)
	return
}

type OrderCreateReq struct {
	Address       OrderAddress      `json:"deliveryAddressInfo"`
	List          []OrderCreateItem `json:"orderDTOs"`
	PromotionResp OrderPromotion    `json:"promotionResp"`
}
type OrderCreateItem struct {
	DTO     []OrderCreateDto `json:"orderLineDTOs"`
	OrderSn string           `json:"outId"`
	Token   string           `json:"sellerToken"`
}

type OrderCreateDto struct {
	GoodsID  int64 `json:"itemId"`
	SkuId    int64 `json:"skuId"`
	Quantity uint  `json:"buyQuantity"`
	LineId   int64 `json:"orderLineId"`
}

type OrderCreateRes struct {
	CommonRes
	Result struct {
		AlipaySuccess        bool `json:"alipaySuccess"`
		EnablingOrdersResult struct {
			Model struct {
				AlipayTradeIds []string `json:"alipayTradeIds"`
				OrderIds       []string `json:"orderIds"`
			} `json:"model"`
		} `json:"enablingOrdersResult"`
		ExtensionResult struct {
			TraceId string `json:"traceId"`
		} `json:"extensionResult"`
		PartSuccess bool `json:"partSuccess"`
	} `json:"result"`
}

//Create 下单
func (s order) Create(ctx context.Context, req OrderCreateReq) (res *OrderCreateRes, err error) {
	method := "tt.order.create"

	for k, item := range req.List {
		req.List[k].OrderSn = s.outId(item.OrderSn)
	}
	result, err := server.Post(ctx, method, g.Map{
		"request": req,
	})
	_ = gjson.NewWithOptions(result, gjson.Options{
		StrNumber: true,
	}).Scan(&res)
	return
}

func (s order) outId(req string) (res string) {
	res = gstr.SubStr(req, 2, -1)
	res = gstr.Replace(res, "_15_", "_")
	return fmt.Sprintf("%s_%s", server.AppKey, res)
}

type OrderDetailRes struct {
	Success bool   `json:"success"`
	ErrMsg  string `json:"errMsg"`
	Result  struct {
		BizOrderId      string `json:"bizOrderId"`
		BuyAmount       int    `json:"buyAmount"`
		BuyerToken      string `json:"buyerToken"`
		Detail          int    `json:"detail"`
		DetailOrderList []struct {
			BizOrderId string `json:"bizOrderId"`
			BuyAmount  int    `json:"buyAmount"`
			BuyerToken string `json:"buyerToken"`
			Detail     int    `json:"detail"`
			GmtCreate  string `json:"gmtCreate"`
			ItemInfo   struct {
				ItemId      int64  `json:"itemId"`
				Pic         string `json:"pic"`
				Price       string `json:"price"`
				SkuId       int64  `json:"skuId"`
				SkuInfoList []struct {
					Name  string `json:"name"`
					Value string `json:"value"`
				} `json:"skuInfoList"`
				Title string `json:"title"`
			} `json:"itemInfo"`
			LogisticsOrderId int64 `json:"logisticsOrderId"`
			LogisticsStatus  int   `json:"logisticsStatus"`
			//1 - 未发货 -> 等待卖家发货
			//2 - 已发货 -> 等待买家确认收货
			//3 - 已收货 -> 交易成功
			//4 - 已经退货 -> 交易失败
			//5 - 部分收货 -> 交易成功
			//6 - 部分发货中
			//8 - 还未创建物流订单
			Main       int   `json:"main"`
			ParentId   int64 `json:"parentId"`
			PayFee     int   `json:"payFee"`
			PayOrderId int64 `json:"payOrderId"`
			PayStatus  int   `json:"payStatus"`
			//1 - 未冻结/未付款 -> 等待买家付款
			//2 - 已冻结/已付款 -> 等待卖家发货
			//4 - 已退款 -> 交易关闭
			//6 - 已转交易 -> 交易成功
			//7 - 没有创建外部交易
			//8 - 交易被关闭
			//9 - 不可付款
			PayTime      string `json:"payTime"`
			PostFee      int    `json:"postFee"`
			RefundStatus int    `json:"refundStatus"`
			SellerToken  string `json:"sellerToken"`
			Status       int    `json:"status"`
		} `json:"detailOrderList"`
		GmtCreate string `json:"gmtCreate"`
		ItemInfo  struct {
			ItemId      int64  `json:"itemId"`
			Pic         string `json:"pic"`
			Price       string `json:"price"`
			SkuId       int64  `json:"skuId"`
			SkuInfoList []struct {
				Name  string `json:"name"`
				Value string `json:"value"`
			} `json:"skuInfoList"`
			Title string `json:"title"`
		} `json:"itemInfo"`
		LogisticsOrderId int64 `json:"logisticsOrderId"`
		LogisticsStatus  int   `json:"logisticsStatus"`
		//1 - 未发货 -> 等待卖家发货
		//2 - 已发货 -> 等待买家确认收货
		//3 - 已收货 -> 交易成功
		//4 - 已经退货 -> 交易失败
		//5 - 部分收货 -> 交易成功
		//6 - 部分发货中
		//8 - 还未创建物流订单
		Main       int   `json:"main"`
		ParentId   int64 `json:"parentId"`
		PayFee     int   `json:"payFee"`
		PayOrderId int64 `json:"payOrderId"`
		PayStatus  int   `json:"payStatus"`
		//1 - 未冻结/未付款 -> 等待买家付款
		//2 - 已冻结/已付款 -> 等待卖家发货
		//4 - 已退款 -> 交易关闭
		//6 - 已转交易 -> 交易成功
		//7 - 没有创建外部交易
		//8 - 交易被关闭
		//9 - 不可付款
		PayTime      string `json:"payTime"`
		PostFee      int    `json:"postFee"`
		RefundStatus int    `json:"refundStatus"`
		SellerToken  string `json:"sellerToken"`
		Status       int    `json:"status"`
	} `json:"result"`
}

//Detail 详情
func (s order) Detail(ctx context.Context, req interface{}) (res *OrderDetailRes, err error) {
	method := "tt.order.detail"

	result, err := server.Post(ctx, method, g.Map{
		"request": g.Map{
			"bizOrderId": gconv.Int64(req),
		},
	})
	_ = gjson.NewWithOptions(result, gjson.Options{
		StrNumber: true,
	}).Scan(&res)
	return
}

type OrderReflectRes struct {
	Success bool   `json:"success"`
	ErrMsg  string `json:"errMsg"`
	ErrCode string `json:"errCode"`
	Result  struct {
		BizOrderId      string `json:"bizOrderId"`
		BuyAmount       uint   `json:"buyAmount"`
		BuyerToken      string `json:"buyerToken"`
		Detail          int    `json:"detail"`
		DetailOrderList []struct {
			BizOrderId string `json:"bizOrderId"`
			BuyAmount  uint   `json:"buyAmount"`
			BuyerToken string `json:"buyerToken"`
			Detail     int    `json:"detail"`
			GmtCreate  string `json:"gmtCreate"`
			ItemInfo   struct {
				ItemId      string `json:"itemId"`
				Pic         string `json:"pic"`
				Price       uint   `json:"price"`
				SkuId       string `json:"skuId"`
				SkuInfoList []struct {
					Name  string `json:"name"`
					Value string `json:"value"`
				} `json:"skuInfoList"`
				Title string `json:"title"`
			} `json:"itemInfo"`
			LogisticsOrderId int64 `json:"logisticsOrderId"`
			LogisticsStatus  int   `json:"logisticsStatus"`
			//1 - 未发货 -> 等待卖家发货
			//2 - 已发货 -> 等待买家确认收货
			//3 - 已收货 -> 交易成功
			//4 - 已经退货 -> 交易失败
			//5 - 部分收货 -> 交易成功
			//6 - 部分发货中
			//8 - 还未创建物流订单
			Main       int   `json:"main"`
			ParentId   int64 `json:"parentId"`
			PayFee     uint  `json:"payFee"`
			PayOrderId int64 `json:"payOrderId"`
			PayStatus  int   `json:"payStatus"`
			//1 - 未冻结/未付款 -> 等待买家付款
			//2 - 已冻结/已付款 -> 等待卖家发货
			//4 - 已退款 -> 交易关闭
			//6 - 已转交易 -> 交易成功
			//7 - 没有创建外部交易
			//8 - 交易被关闭
			//9 - 不可付款
			PostFee      uint   `json:"postFee"`
			RefundStatus int    `json:"refundStatus"`
			SellerToken  string `json:"sellerToken"`
			Status       int    `json:"status"`
		} `json:"detailOrderList"`
		GmtCreate string `json:"gmtCreate"`
		ItemInfo  struct {
			ItemId      string `json:"itemId"`
			Pic         string `json:"pic"`
			Price       uint   `json:"price"`
			SkuId       string `json:"skuId"`
			SkuInfoList []struct {
				Name  string `json:"name"`
				Value string `json:"value"`
			} `json:"skuInfoList"`
			Title string `json:"title"`
		} `json:"itemInfo"`
		LogisticsOrderId int64 `json:"logisticsOrderId"`
		LogisticsStatus  int   `json:"logisticsStatus"`
		//1 - 未发货 -> 等待卖家发货
		//2 - 已发货 -> 等待买家确认收货
		//3 - 已收货 -> 交易成功
		//4 - 已经退货 -> 交易失败
		//5 - 部分收货 -> 交易成功
		//6 - 部分发货中
		//8 - 还未创建物流订单
		Main       int    `json:"main"`
		ParentId   string `json:"parentId"`
		PayFee     uint   `json:"payFee"`
		PayOrderId string `json:"payOrderId"`
		PayStatus  int    `json:"payStatus"`
		//1 - 未冻结/未付款 -> 等待买家付款
		//2 - 已冻结/已付款 -> 等待卖家发货
		//4 - 已退款 -> 交易关闭
		//6 - 已转交易 -> 交易成功
		//7 - 没有创建外部交易
		//8 - 交易被关闭
		//9 - 不可付款
		PostFee      uint   `json:"postFee"`
		RefundStatus int    `json:"refundStatus"`
		SellerToken  string `json:"sellerToken"`
		Status       int    `json:"status"`
	} `json:"result"`
}

//Reflect 详情[反查]
func (s order) Reflect(ctx context.Context, req string) (res *OrderReflectRes, err error) {
	method := "tt.order.detail.outid"

	result, err := server.Post(ctx, method, g.Map{
		"request": g.Map{
			"outOrderId": s.outId(req),
		},
	})
	_ = gjson.NewWithOptions(result, gjson.Options{
		StrNumber: true,
	}).Scan(&res)
	return
}

type OrderPayRes struct {
	Result struct {
		Result struct {
			Result  string `json:"result"`
			Success bool   `json:"success"`
			ErrCode string `json:"errCode"`
			ErrMsg  string `json:"errMsg"`
		} `json:"result"`
	} `json:"result"`
}

func (s order) Pay(ctx context.Context, req string) (res *OrderPayRes, err error) {
	method := "tt.agreementpay.dopay"

	result, err := server.Post(ctx, method, g.Map{
		"request": g.Map{
			"bizOrderId": gconv.Int64(req),
		},
	})
	_ = gjson.NewWithOptions(result, gjson.Options{
		StrNumber: true,
	}).Scan(&res)
	return
}