Skip to content

Instantly share code, notes, and snippets.

@threadedstream
Created March 31, 2021 06:56
Show Gist options
  • Save threadedstream/9e57b8904435c520a2cc86dedfed320c to your computer and use it in GitHub Desktop.
Save threadedstream/9e57b8904435c520a2cc86dedfed320c to your computer and use it in GitHub Desktop.
package tinkoff
import(
"time"
"context"
"encoding/json"
"encoding/base64"
"bytes"
."github.com/medods/online_payments_service/structs"
."github.com/medods/online_payments_service/configuration"
"github.com/valyala/fasthttp"
)
type TinkoffPayment struct{
Amount Amount `json:"amount,omitempty"`
IdempotenceKey string `json:"idempotence_key,omitempty"`
ShopId string `json:"shop_id,omitempty"`
SecretKey string `json:"secret_key,omitempty"`
Description string `json:"description,omitempty"`
ReturnUrl string `json:"return_url,omitempty"`
MD MedodsData `json:"medods_data,omitempty"`
}
type Amount struct{
Value string `json:"value,omitempty"`
Currency string `json:"currency,omitempty"`
}
type PaymentMethodData struct{
Type string `json:"type,omitempty"`
}
type ConfirmationReq struct{
Type string `json:"type,omitempty"`
ReturnUrl string `json:"return_url,omitempty"`
}
type ConfirmationResp struct{
Type string `json:"type,omitempty"`
ConfirmationUrl string `json:"confirmation_url,omitempty"`
}
type TinkoffPaymentRequest struct{
Amount Amount `json:"amount,omitempty"`
PaymentMethodData PaymentMethodData `json:"payment_method_data,omitempty"`
Capture bool `json:"capture,omitempty"`
Confirmation ConfirmationReq `json:"confirmation,omitempty"`
Description string `json:"description,omitempty"`
}
type PaymentMethod struct{
Type string `json:"type,omitempty"`
Id string `json:"id,omitempty"`
Saved bool `json:"saved,omitempty"`
}
type Recipient struct{
AccountId string `json:"account_id,omitempty"`
GatewayId string `json:"gateway_id,omitempty"`
}
type TinkoffPaymentResponse struct{
Id string `json:"id,omitempty"`
Status string `json:"status,omitempty"`
Paid bool `json:"paid,omitempty"`
Amount Amount `json:"amount,omitempty"`
Confirmation ConfirmationResp `json:"confirmation,omitempty"`
CreatedAt time.Time `json:"created_at,omitempty"`
Description string `json:"description,omitempty"`
PaymentMethod PaymentMethod `json:"payment_method,omitempty"`
Recipient Recipient `json:"recipient,omitempty"`
Refundable bool `json:"refundable,omitempty"`
Test bool `json:"test,omitempty"`
MD MedodsData `json:"medods_data,omitempty"`
}
func (tp TinkoffPayment) Register(resp *OutputStructure, ctx context.Context){
defer ctx.Done()
// Constructing payment request
var paymentRequest = TinkoffPaymentRequest{
Amount: tp.Amount,
PaymentMethodData: PaymentMethodData{
Type: "tinkoff_bank",
},
Capture: true,
Confirmation: ConfirmationReq{
Type: "redirect",
ReturnUrl: tp.ReturnUrl,
},
Description: tp.Description,
}
//Turn it into bytes stream
bs, err := json.Marshal(paymentRequest); if err != nil{
resp.Err = err
resp.Done <- true
return
}
var bodyReader = bytes.NewReader(bs)
//Prepare request data
requestMethod := "POST"
endpoint := GetConfig().KassaBaseURL + "payments"
authData := base64.StdEncoding.EncodeToString([]byte(tp.ShopId+":"+tp.SecretKey))
//Acquire request and response objects from request and response pool, respectively
var request = fasthttp.AcquireRequest()
var response = fasthttp.AcquireResponse()
//The following methods return objects to the pool for further usage.
defer fasthttp.ReleaseRequest(request)
defer fasthttp.ReleaseResponse(response)
request.URI().Update(endpoint)
request.Header.SetMethodBytes([]byte(requestMethod))
//Set mandatory headers
request.Header.Set("Content-Type", "application/json")
request.Header.Set("Idempotence-Key", tp.IdempotenceKey)
request.Header.Set("Authorization", "Basic " + authData)
request.SetBodyStream(bodyReader, len(bs))
var client = fasthttp.Client{
ReadTimeout: 10 * time.Second,
}
//The slowest part(takes about 10-13 seconds to complete)
client.Do(request, response)
var respBodyStream = bytes.NewReader(response.Body())
var paymentResponse TinkoffPaymentResponse
err = json.NewDecoder(respBodyStream).Decode(&paymentResponse)
if err != nil{
resp.Err = err
resp.Done <- true
return
}
paymentResponse.MD = tp.MD
resp.UUID = tp.IdempotenceKey; resp.Data = paymentResponse
resp.Done <- true
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment