rework with files upload in amo

This commit is contained in:
Pavel 2024-05-11 19:42:58 +03:00
parent 74dfb8d4be
commit 6dd5085bf6
3 changed files with 33 additions and 15 deletions

@ -77,6 +77,7 @@ func Run(ctx context.Context, config initialize.Config, logger *zap.Logger) erro
IntegrationID: config.IntegrationID,
IntegrationSecret: config.IntegrationSecret,
RateLimiter: rateLimiter,
AmoStorageURL: config.AmoStorageURL,
})
redisRepo := repository.NewRepository(repository.Deps{

@ -26,6 +26,7 @@ type Config struct {
IntegrationID string `env:"INTEGRATION_ID" envDefault:"2dbd6329-9be6-41f2-aa5f-964b9e723e49"`
// секрет интеграции
IntegrationSecret string `env:"INTEGRATION_SECRET" envDefault:"tNK3LwL4ovP0OBK4jKDHJ3646PqRJDOKQYgY6P2t6DCuV8LEzDzszTDY0Fhwmzc8"`
AmoStorageURL string `env:"AMO_STORAGE_URL" envDefault:"https://drive-b.amocrm.ru"`
}
func LoadConfig() (*Config, error) {

@ -11,6 +11,7 @@ import (
"net/url"
"os"
"penahub.gitlab.yandexcloud.net/backend/quiz/common.git/model"
"strings"
"time"
"github.com/gofiber/fiber/v2"
@ -25,6 +26,7 @@ type Amo struct {
integrationID string
integrationSecret string
rateLimiter *limiter.RateLimiter
amoStorageURL string
}
type AmoDeps struct {
@ -35,6 +37,7 @@ type AmoDeps struct {
IntegrationID string
IntegrationSecret string
RateLimiter *limiter.RateLimiter
AmoStorageURL string
}
func NewAmoClient(deps AmoDeps) *Amo {
@ -49,6 +52,7 @@ func NewAmoClient(deps AmoDeps) *Amo {
integrationSecret: deps.IntegrationSecret,
integrationID: deps.IntegrationID,
rateLimiter: deps.RateLimiter,
amoStorageURL: deps.AmoStorageURL,
}
}
@ -560,11 +564,11 @@ func (a *Amo) downloadFile(urlFile string) (*os.File, error) {
return nil, fmt.Errorf(errorMessage)
}
tmpFile, err := os.CreateTemp("", "downloaded_file_*")
fileName := strings.Split(urlFile, "/")
tmpFile, err := os.Create(fileName[len(fileName)-1])
if err != nil {
return nil, err
}
defer tmpFile.Close()
_, err = io.Copy(tmpFile, bytes.NewReader(resBody))
if err != nil {
@ -575,7 +579,6 @@ func (a *Amo) downloadFile(urlFile string) (*os.File, error) {
}
func (a *Amo) UploadFileToAmo(urlFile string, accessToken string) (*models.ValuesFile, error) {
fmt.Println(urlFile)
localFile, err := a.downloadFile(urlFile)
if err != nil {
return nil, err
@ -590,11 +593,11 @@ func (a *Amo) UploadFileToAmo(urlFile string, accessToken string) (*models.Value
fileSize := fileInfo.Size()
createSessionData := &models.CreateSession{
FileName: urlFile,
FileName: localFile.Name(),
FileSize: fileSize,
}
uri := fmt.Sprintf("%s/v1.0/sessions", "https://drive-b.amocrm.ru")
uri := fmt.Sprintf("%s/v1.0/sessions", a.amoStorageURL)
bodyBytes, err := json.Marshal(createSessionData)
if err != nil {
a.logger.Error("error marshal create session data:", zap.Error(err))
@ -627,6 +630,10 @@ func (a *Amo) UploadFileToAmo(urlFile string, accessToken string) (*models.Value
}
response, err := a.createPart(resp, localFile)
if err != nil {
a.logger.Error("error create part file sending to amo:", zap.Error(err))
return nil, err
}
return &models.ValuesFile{
Value: models.ValueFile{
@ -639,6 +646,7 @@ func (a *Amo) UploadFileToAmo(urlFile string, accessToken string) (*models.Value
}
func (a *Amo) createPart(uploadData models.UploadSession, file *os.File) (*models.UploadedFile, error) {
defer file.Close()
fileInfo, err := file.Stat()
if err != nil {
return nil, err
@ -647,11 +655,12 @@ func (a *Amo) createPart(uploadData models.UploadSession, file *os.File) (*model
fileSize := fileInfo.Size()
var uploadedFile models.UploadedFile
maxSize := uploadData.MaxPartSize
var remainingSize = fileSize
var start int64 = 0
for remainingSize > 0 {
end := start + uploadData.MaxPartSize
end := start + maxSize
if end > fileSize {
end = fileSize
}
@ -688,23 +697,30 @@ func (a *Amo) createPart(uploadData models.UploadSession, file *os.File) (*model
return nil, fmt.Errorf("request failed: %v", errs[0])
}
if statusCode != http.StatusOK {
return nil, fmt.Errorf("failed to upload part file to amo, status: %d", statusCode)
if statusCode != http.StatusOK && statusCode != http.StatusAccepted {
return nil, fmt.Errorf("failed to upload part file to amo, status: %d, respBody: %s", statusCode, string(resBody))
}
start = end
remainingSize -= partSize
var newUploadData models.UploadSession
if err := json.Unmarshal(resBody, &newUploadData); err == nil {
uploadData = newUploadData
} else {
if err := json.Unmarshal(resBody, &uploadedFile); err != nil {
if statusCode == http.StatusAccepted {
var next struct {
NextUrl string `json:"next_url"`
SessionID int `json:"session_id"`
}
if err := json.Unmarshal(resBody, &next); err != nil {
return nil, err
}
break
uploadData.UploadURL = next.NextUrl
continue
}
if err := json.Unmarshal(resBody, &uploadedFile); err != nil {
return nil, err
}
return &uploadedFile, nil
}
return &uploadedFile, nil
return nil, nil
}