docxTemplater/amo/api.go
Danil Solovyov 2683f95b82 Tasks:
- СПРИНТ BE 15.09.22-01.10.22 (#2zabn3t)
  - BE Yandex API common - навесить обработчик ошибок (#2vc86am)
Changes:
  - Удалены эндпоинты и шаблоны страниц, кроме 404
  - MiddlewareAmoJwt теперь является основным
2022-10-11 15:07:29 +05:00

278 lines
5.6 KiB
Go
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

package amo
import (
"context"
"encoding/json"
"errors"
"fmt"
"github.com/Pena-Co-Ltd/amocrm_templategen_back/tools"
"github.com/dgrijalva/jwt-go"
"golang.org/x/oauth2"
"net/http"
)
const (
OAUTH_URL = "https://www.amocrm.ru/oauth"
)
type Client struct {
App *ClientApp
HTTPClient *http.Client
Subdomain string // Субдомен с которым работаем
Code string // Код авторизации
Token *oauth2.Token
}
type ClientApp struct {
Config *oauth2.Config
}
func NewClientApp(clientID, clientSecret string, redirectUri string) *ClientApp {
return &ClientApp{
Config: &oauth2.Config{
ClientID: clientID,
ClientSecret: clientSecret,
Endpoint: oauth2.Endpoint{
AuthURL: OAUTH_URL,
TokenURL: OAUTH_URL + "/token",
},
RedirectURL: redirectUri,
Scopes: nil,
},
}
}
func (ca *ClientApp) GenerateOAuthUrl(userId, redirectUrl string) (string, error) {
state, err := tools.EncryptTokenRC4(tools.StateToken{
UserID: userId,
Service: "amo",
RedirectUrl: redirectUrl,
})
if err != nil {
return "", err
}
return ca.Config.AuthCodeURL(
state,
oauth2.SetAuthURLParam("mode", "popup"),
), nil
}
func (ca *ClientApp) DecodeJwt(r *http.Request) (*XAuthToken, error) {
tokenHeader := r.Header.Get("x-auth-token")
if tokenHeader == "" {
return nil, errors.New("empty jwt")
}
token, err := jwt.ParseWithClaims(tokenHeader, &XAuthToken{}, func(token *jwt.Token) (interface{}, error) {
return []byte(ca.Config.ClientSecret), nil
})
if err != nil {
return nil, err
}
claims, ok := token.Claims.(*XAuthToken)
if !ok || !token.Valid {
fmt.Println("token:", token)
fmt.Println("claims:", claims)
fmt.Println("valid:", token.Valid)
return nil, errors.New("invalid token")
}
return claims, nil
}
func (ca *ClientApp) NewClient(ctx context.Context, subdomain string, token *oauth2.Token, code string) (*Client,
error) {
var err error
subdomain = "https://" + subdomain
ca.Config.Endpoint.TokenURL = subdomain
if code != "" {
token, err = ca.Config.Exchange(ctx, code)
}
return &Client{
App: ca,
HTTPClient: ca.Config.Client(ctx, token),
Subdomain: subdomain,
Token: token,
}, err
}
// AuthCode - обменивает код авторизации на токен
//func (c *Client) AuthCode() (*oauth2.Token, error) {
// body := map[string]string{
// "client_id": c.App.ClientID,
// "client_secret": c.App.ClientSecret,
// "grant_type": "authorization_code",
// "code": c.Code,
// "redirect_uri": c.App.RedirectUri,
// }
//
// bytesBody, err := json.Marshal(body)
// if err != nil {
// return nil, err
// }
//
// req, err := http.NewRequest("POST", c.Subdomain+"/oauth2/access_token", bytes.NewBuffer(bytesBody))
// if err != nil {
// return nil, err
// }
//
// c.setHeaders(req)
//
// resp, err := c.HTTPClient.Do(req)
//
// if err != nil {
// return nil, err
// }
//
// var response RespAuthCode
// err = json.NewDecoder(resp.Body).Decode(&response)
// if err != nil {
// return nil, err
// }
//
// c.Token = &oauth2.Token{
// AccessToken: response.AccessToken,
// TokenType: response.TokenType,
// RefreshToken: response.RefreshToken,
// Expiry: time.Now().Add(time.Duration(response.ExpiresIn) * time.Second),
// }
//
// return c.Token, nil
//}
func (c *Client) GetAccount() (*Account, error) {
req, err := http.NewRequest("GET", c.Subdomain+"/api/v4/account", nil)
if err != nil {
fmt.Println("1")
return nil, err
}
c.setHeaders(req)
resp, err := c.HTTPClient.Do(req)
if err != nil {
fmt.Println("2")
return nil, err
}
var response Account
err = json.NewDecoder(resp.Body).Decode(&response)
if err != nil {
fmt.Println("3")
return nil, err
}
return &response, nil
}
func (c *Client) GetLeadById(id string) (*Lead, error) {
req, err := http.NewRequest("GET",
fmt.Sprintf("%v/api/v4/leads/%v?with=contacts,catalog_elements,is_price_modified_by_robot,loss_reason",
c.Subdomain, id),
nil,
)
fmt.Println("URL:", fmt.Sprintf("%v/api/v4/leads/%v?with=contacts,catalog_elements,is_price_modified_by_robot,"+
"loss_reason",
c.Subdomain, id))
if err != nil {
fmt.Println("1")
return nil, err
}
c.setHeaders(req)
resp, err := c.HTTPClient.Do(req)
if err != nil {
fmt.Println("2")
return nil, err
}
var response Lead
err = json.NewDecoder(resp.Body).Decode(&response)
if err != nil {
return nil, err
}
return &response, nil
}
func (c *Client) GetContactById(id string) (*Contact, error) {
req, err := http.NewRequest("GET",
fmt.Sprintf("%v/api/v4/contacts/%v?with=catalog_elements,leads,customers",
c.Subdomain, id),
nil,
)
if err != nil {
fmt.Println("1")
return nil, err
}
c.setHeaders(req)
resp, err := c.HTTPClient.Do(req)
if err != nil {
fmt.Println("2")
return nil, err
}
var response Contact
err = json.NewDecoder(resp.Body).Decode(&response)
if err != nil {
return nil, err
}
return &response, nil
}
func (c *Client) GetCompanyById(id string) (*Company, error) {
req, err := http.NewRequest("GET",
fmt.Sprintf("%v/api/v4/companies/%v?with=contacts,leads,catalog_elements,customers",
c.Subdomain, id),
nil,
)
if err != nil {
fmt.Println("1")
return nil, err
}
c.setHeaders(req)
resp, err := c.HTTPClient.Do(req)
if err != nil {
fmt.Println("2")
return nil, err
}
var response Company
err = json.NewDecoder(resp.Body).Decode(&response)
if err != nil {
return nil, err
}
return &response, nil
}
func (c *Client) setHeaders(req *http.Request) {
req.Header.Set("User-Agent", "amoCRM-oAuth-client/1.0")
req.Header.Set("Content-Type", "application/json")
//if c.Token != nil {
// c.Token.SetAuthHeader(req)
//}
}