mg-bot-api-client-go/v1/client_test.go

1196 lines
26 KiB
Go
Raw Normal View History

2018-08-03 18:11:37 +03:00
package v1
import (
2021-11-25 12:51:29 +03:00
"bytes"
"compress/gzip"
"encoding/base64"
2019-03-07 12:58:09 +03:00
"encoding/json"
2018-09-01 00:41:29 +03:00
"fmt"
"io"
2018-08-29 02:44:06 +03:00
"log"
2018-09-20 11:41:20 +03:00
"math/rand"
2018-08-29 02:44:06 +03:00
"net/http"
2018-08-03 18:11:37 +03:00
"os"
2018-08-29 02:44:06 +03:00
"strconv"
2018-09-01 00:41:29 +03:00
"strings"
2018-08-29 02:44:06 +03:00
"testing"
2018-09-20 11:41:20 +03:00
"time"
2018-08-29 02:44:06 +03:00
"github.com/joho/godotenv"
"github.com/stretchr/testify/assert"
2021-06-11 14:33:44 +03:00
"gopkg.in/h2non/gock.v1"
2018-08-03 18:11:37 +03:00
)
2018-09-20 11:41:20 +03:00
const (
letterBytes = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ"
letterIdxBits = 6 // 6 bits to represent a letter index
letterIdxMask = 1<<letterIdxBits - 1 // All 1-bits, as many as letterIdxBits
letterIdxMax = 63 / letterIdxBits // # of letter indices fitting in 63 bits
)
var src = rand.NewSource(time.Now().UnixNano())
2018-08-29 02:44:06 +03:00
func TestMain(m *testing.M) {
if os.Getenv("DEVELOPER_NODE") == "1" {
err := godotenv.Load("../.env")
if err != nil {
log.Fatal("Error loading .env file")
}
}
2019-03-07 12:58:09 +03:00
os.Exit(m.Run())
2018-08-29 02:44:06 +03:00
}
2018-08-03 18:11:37 +03:00
var (
2019-03-07 12:58:09 +03:00
mgURL = "https://api.example.com"
mgToken = "test_token"
debug, _ = strconv.ParseBool(os.Getenv("DEBUG"))
2018-08-03 18:11:37 +03:00
)
2024-02-09 09:44:36 +03:00
func client(opts ...Option) *MgClient {
2019-03-07 12:58:09 +03:00
if debug != false {
2024-02-09 09:44:36 +03:00
opts = append(opts, OptionDebug())
2019-03-07 12:58:09 +03:00
}
2018-12-26 17:38:41 +03:00
2024-02-09 09:44:36 +03:00
return New(mgURL, mgToken, opts...)
2018-08-03 18:11:37 +03:00
}
2018-08-29 02:44:06 +03:00
func TestMgClient_Bots(t *testing.T) {
c := client()
2019-03-07 12:58:09 +03:00
defer gock.Off()
gock.New(mgURL).
Get("/api/bot/v1/bots").
Reply(200).
BodyString(`[{"id": 1, "name": "Test Bot", "created_at": "2018-01-01T00:00:00.000000Z", "is_active": true, "is_self": true}]`)
2018-08-29 02:44:06 +03:00
req := BotsRequest{Active: 1}
data, status, err := c.Bots(req)
if err != nil {
t.Errorf("%d %v", status, err)
}
assert.NoError(t, err)
assert.NotEmpty(t, data)
for _, bot := range data {
assert.NotEmpty(t, bot.CreatedAt)
}
}
func TestMgClient_Channels(t *testing.T) {
c := client()
2019-03-07 12:58:09 +03:00
defer gock.Off()
gock.New(mgURL).
Get("/api/bot/v1/channels").
Reply(200).
2021-02-03 14:27:53 +03:00
BodyString(`[
{
"id": 1,
"type": "custom",
"name": "Test custom channel",
"settings": {
"customer_external_id": "phone",
"sending_policy": {
"new_customer": "no",
"after_reply_timeout": "template"
},
"status": {
"delivered": "both",
"read": "receive"
},
"text": {
"creating": "both",
"editing": "receive",
"quoting": "send",
"deleting": "receive",
"max_chars_count": 777
},
"product": {
"creating": "receive",
"editing": "receive",
"deleting": "receive"
},
"order": {
"creating": "receive",
"editing": "receive",
"deleting": "receive"
},
"image": {
"creating": "both",
"quoting": "receive",
"editing": "none",
"deleting": "receive",
"max_items_count": 1,
"note_max_chars_count": 777
},
"file": {
"creating": "both",
"quoting": "receive",
"editing": "none",
"deleting": "receive",
"max_items_count": 1,
"note_max_chars_count": 777
},
"suggestions": {
"text": "receive",
"email": "receive",
"phone": "receive"
}
},
"created_at": "2018-01-01T00:00:00.000000Z",
"updated_at": null,
"activated_at": "2018-01-01T00:00:00.000000Z",
"deactivated_at": null,
"is_active": true
}
]`)
channels, status, err := c.Channels(ChannelsRequest{Active: 1})
2018-08-29 02:44:06 +03:00
assert.NoError(t, err)
2021-02-03 14:27:53 +03:00
assert.Equal(t, 200, status)
assert.Len(t, channels, 1)
ch := channels[0]
assert.Equal(t, uint64(1), ch.ID)
assert.Equal(t, ChannelTypeCustom, ch.Type)
assert.Equal(t, "Test custom channel", ch.Name)
assert.Equal(t, "2018-01-01T00:00:00.000000Z", ch.CreatedAt)
assert.Empty(t, ch.UpdatedAt)
assert.Equal(t, "2018-01-01T00:00:00.000000Z", ch.ActivatedAt)
assert.Empty(t, ch.DeactivatedAt)
assert.True(t, ch.IsActive)
chs := ch.Settings
assert.Equal(t, "phone", chs.CustomerExternalID)
assert.Equal(t, "no", chs.SendingPolicy.NewCustomer)
assert.Equal(t, "template", chs.SendingPolicy.AfterReplyTimeout)
assert.Equal(t, ChannelFeatureBoth, chs.Status.Delivered)
assert.Equal(t, ChannelFeatureReceive, chs.Status.Read)
assert.Equal(t, ChannelFeatureBoth, chs.Text.Creating)
assert.Equal(t, ChannelFeatureReceive, chs.Text.Editing)
assert.Equal(t, ChannelFeatureSend, chs.Text.Quoting)
assert.Equal(t, ChannelFeatureReceive, chs.Text.Deleting)
assert.Equal(t, uint16(777), chs.Text.MaxCharsCount)
assert.Equal(t, ChannelFeatureReceive, chs.Product.Creating)
assert.Equal(t, ChannelFeatureReceive, chs.Product.Editing)
assert.Equal(t, ChannelFeatureReceive, chs.Product.Deleting)
assert.Equal(t, ChannelFeatureReceive, chs.Order.Creating)
assert.Equal(t, ChannelFeatureReceive, chs.Order.Editing)
assert.Equal(t, ChannelFeatureReceive, chs.Order.Deleting)
assert.Equal(t, ChannelFeatureBoth, chs.Image.Creating)
assert.Equal(t, ChannelFeatureNone, chs.Image.Editing)
assert.Equal(t, ChannelFeatureReceive, chs.Image.Quoting)
assert.Equal(t, ChannelFeatureReceive, chs.Image.Deleting)
assert.Equal(t, 1, chs.Image.MaxItemsCount)
assert.Equal(t, uint16(777), chs.Image.NoteMaxCharsCount)
assert.Equal(t, ChannelFeatureBoth, chs.File.Creating)
assert.Equal(t, ChannelFeatureNone, chs.File.Editing)
assert.Equal(t, ChannelFeatureReceive, chs.File.Quoting)
assert.Equal(t, ChannelFeatureReceive, chs.File.Deleting)
assert.Equal(t, 1, chs.File.MaxItemsCount)
assert.Equal(t, uint16(777), chs.File.NoteMaxCharsCount)
assert.Equal(t, ChannelFeatureReceive, chs.Suggestions.Text)
assert.Equal(t, ChannelFeatureReceive, chs.Suggestions.Email)
assert.Equal(t, ChannelFeatureReceive, chs.Suggestions.Phone)
2018-08-29 02:44:06 +03:00
}
func TestMgClient_Users(t *testing.T) {
c := client()
2019-03-07 12:58:09 +03:00
defer gock.Off()
gock.New(mgURL).
Get("/api/bot/v1/users").
Reply(200).
BodyString(`[{"id": 1, "external_id":"1", "username": "Test", "first_name":"Test", "last_name":"Test", "created_at": "2018-01-01T00:00:00.000000Z", "is_active": true, "is_online": true, "is_technical_account": true}]`)
2019-03-07 12:58:09 +03:00
2018-08-29 02:44:06 +03:00
req := UsersRequest{Active: 1}
data, status, err := c.Users(req)
if err != nil {
t.Errorf("%d %v", status, err)
}
assert.NoError(t, err)
assert.NotEmpty(t, data)
for _, user := range data {
assert.Equal(t, uint64(1), user.ID)
assert.Equal(t, "1", user.ExternalID)
assert.Equal(t, "Test", user.Username)
assert.Equal(t, "Test", user.FirstName)
assert.Equal(t, "Test", user.LastName)
assert.Equal(t, "2018-01-01T00:00:00.000000Z", user.CreatedAt)
assert.Equal(t, true, user.IsActive)
assert.Equal(t, true, user.IsOnline)
assert.Equal(t, true, user.IsTechnicalAccount)
2018-08-29 02:44:06 +03:00
}
}
func TestMgClient_Customers(t *testing.T) {
c := client()
2019-03-07 12:58:09 +03:00
defer gock.Off()
response := `
[
{
"id": 1,
"channel_id": 1,
"created_at":
"2018-01-01T00:00:00.000000Z",
"utm": {
"source": "test"
}
},
{
"id": 2,
"channel_id": 1,
"created_at":
"2018-01-01T00:00:00.000000Z",
"utm": {
"source": null
}
},
{
"id": 3,
"channel_id": 1,
"created_at":
"2018-01-01T00:00:00.000000Z",
"utm": null
},
{
"id": 4,
"channel_id": 1,
"created_at": "2018-01-01T00:00:00.000000Z"
}
]`
2019-03-07 12:58:09 +03:00
gock.New(mgURL).
Get("/api/bot/v1/customers").
Reply(200).
BodyString(response)
2019-03-07 12:58:09 +03:00
2018-08-29 02:44:06 +03:00
req := CustomersRequest{}
data, status, err := c.Customers(req)
if err != nil {
t.Errorf("%d %v", status, err)
}
assert.NoError(t, err)
assert.NotEmpty(t, data)
for _, customer := range data {
assert.NotEmpty(t, customer.ChannelId)
}
assert.Equal(t, "test", data[0].Utm.Source)
assert.Equal(t, "", data[1].Utm.Source)
assert.Nil(t, data[2].Utm)
assert.Nil(t, data[3].Utm)
2018-08-29 02:44:06 +03:00
}
func TestMgClient_Chats(t *testing.T) {
c := client()
2019-03-07 12:58:09 +03:00
defer gock.Off()
gock.New(mgURL).
Get("/api/bot/v1/chats").
Reply(200).
2024-07-16 11:40:08 +03:00
BodyString(`[
{"id": 2,"customer": {"id": 2, "name": "Foo"}, "created_at": "2018-01-01T00:00:00.000000Z"},
{"id": 3,"customer": {"id": 3, "name": "Bar"}, "created_at": "2018-01-02T00:00:00.000000Z"}
]`)
2019-03-07 12:58:09 +03:00
2024-07-16 11:40:08 +03:00
req := ChatsRequest{
ChannelType: ChannelTypeTelegram,
SinceID: 1,
}
2018-08-29 02:44:06 +03:00
data, status, err := c.Chats(req)
if err != nil {
t.Errorf("%d %v", status, err)
}
assert.NoError(t, err)
assert.NotEmpty(t, data)
for _, chat := range data {
assert.NotEmpty(t, chat.Customer.Name)
}
}
func TestMgClient_Members(t *testing.T) {
c := client()
2019-03-07 12:58:09 +03:00
defer gock.Off()
gock.New(mgURL).
Get("/api/bot/v1/members").
Reply(200).
BodyString(`[{"id": 1,"user_id": 1, "chat_id": 1, "created_at": "2018-01-01T00:00:00.000000Z"}]`)
2018-08-29 02:44:06 +03:00
req := MembersRequest{State: ChatMemberStateLeaved}
data, status, err := c.Members(req)
if err != nil {
t.Errorf("%d %v", status, err)
}
assert.NoError(t, err)
for _, member := range data {
assert.NotEmpty(t, member.ChatID)
}
}
func TestMgClient_Dialogs(t *testing.T) {
c := client()
2019-03-07 12:58:09 +03:00
defer gock.Off()
gock.New(mgURL).
Get("/api/bot/v1/dialogs").
Reply(200).
BodyString(`[{"id": 1, "chat_id": 1, "created_at": "2018-01-01T00:00:00.000000Z"}]`)
2023-08-15 15:43:53 +03:00
req := DialogsRequest{Active: 0, SinceID: 1}
2018-08-29 02:44:06 +03:00
data, status, err := c.Dialogs(req)
if err != nil {
t.Errorf("%d %v", status, err)
}
assert.NoError(t, err)
assert.NotEmpty(t, data)
for _, dialog := range data {
assert.NotEmpty(t, dialog.ChatID)
}
}
func TestMgClient_DialogAssign(t *testing.T) {
c := client()
2019-03-07 12:58:09 +03:00
d := 1
u := 1
req := DialogAssignRequest{DialogID: uint64(d), UserID: uint64(u)}
r, _ := json.Marshal(req)
defer gock.Off()
gock.New(mgURL).
Patch("/api/bot/v1/dialogs/1/assign").
JSON(r).
Reply(400).
BodyString(`{"errors": ["dialog is not the latest in the chat"]}`)
2018-08-29 02:44:06 +03:00
_, status, err := c.DialogAssign(req)
assert.Error(t, err)
assert.Equal(t, http.StatusBadRequest, status)
}
2020-07-14 14:37:46 +03:00
func TestMgClient_DialogUnassign(t *testing.T) {
c := client()
defer gock.Off()
t.Run("success", func(t *testing.T) {
gock.New(mgURL).
Patch("/api/bot/v1/dialogs/777/unassign").
Reply(200).
BodyString(`{"previous_responsible": {"id": 111, "type": "bot", "assigned_at": "2020-07-14T14:11:44.000000Z"}}`)
resp, status, err := c.DialogUnassign(777)
assert.NoError(t, err)
assert.Equal(t, http.StatusOK, status)
assert.Equal(t, int64(111), resp.PreviousResponsible.ID)
assert.Equal(t, "bot", resp.PreviousResponsible.Type)
assert.Equal(t, "2020-07-14T14:11:44.000000Z", resp.PreviousResponsible.AssignAt)
})
t.Run("dialog not latest in chat", func(t *testing.T) {
gock.New(mgURL).
Patch("/api/bot/v1/dialogs/666/unassign").
Reply(400).
BodyString(`{"errors": ["dialog is not the latest in the chat"]}`)
_, status, err := c.DialogUnassign(666)
assert.Error(t, err, "dialog is not the latest in the chat")
assert.Equal(t, http.StatusBadRequest, status)
})
t.Run("dialog is not assigned", func(t *testing.T) {
gock.New(mgURL).
Patch("/api/bot/v1/dialogs/555/unassign").
Reply(400).
BodyString(`{"errors": ["dialog is not assigned"]}`)
_, status, err := c.DialogUnassign(555)
assert.Error(t, err)
assert.Equal(t, http.StatusBadRequest, status)
})
t.Run("dialog not found", func(t *testing.T) {
gock.New(mgURL).
Patch("/api/bot/v1/dialogs/444/unassign").
Reply(404).
BodyString(`{"errors": ["dialog #444 not found"]}`)
_, status, err := c.DialogUnassign(444)
assert.Error(t, err)
assert.Equal(t, http.StatusNotFound, status)
})
}
2018-08-29 02:44:06 +03:00
func TestMgClient_DialogClose(t *testing.T) {
c := client()
2019-03-07 12:58:09 +03:00
i := 1
defer gock.Off()
gock.New(mgURL).
Delete("/api/bot/v1/dialogs/1/close").
Reply(400).
BodyString(`{"errors": ["dialog #1 not found"]}`)
_, status, err := c.DialogClose(uint64(i))
2018-08-29 02:44:06 +03:00
assert.Error(t, err)
assert.Equal(t, http.StatusBadRequest, status)
}
func TestMgClient_DialogsTagsAdd(t *testing.T) {
c := client()
color := ColorBlue
req := DialogTagsAddRequest{
DialogID: uint64(1),
Tags: []TagsAdd{
{Name: "foo", ColorCode: nil},
{Name: "bar", ColorCode: &color},
},
}
r, _ := json.Marshal(req)
defer gock.Off()
gock.New(mgURL).
Patch("/api/bot/v1/dialogs/1/tags/add").
JSON(r).
Reply(200).
BodyString(`{}`)
status, err := c.DialogsTagsAdd(req)
assert.NoError(t, err)
assert.Equal(t, http.StatusOK, status)
}
func TestMgClient_DialogsTagsDelete(t *testing.T) {
c := client()
req := DialogTagsDeleteRequest{
DialogID: uint64(1),
Tags: []TagsDelete{
{Name: "foo"},
{Name: "bar"},
},
}
r, _ := json.Marshal(req)
defer gock.Off()
gock.New(mgURL).
Patch("/api/bot/v1/dialogs/1/tags/delete").
JSON(r).
Reply(200).
BodyString(`{}`)
status, err := c.DialogTagsDelete(req)
assert.NoError(t, err)
assert.Equal(t, http.StatusOK, status)
}
2018-08-29 02:44:06 +03:00
func TestMgClient_Messages(t *testing.T) {
c := client()
2019-03-07 12:58:09 +03:00
defer gock.Off()
gock.New(mgURL).
Get("/api/bot/v1/messages").
Reply(200).
BodyString(`[{"id": 1, "time": "2018-01-01T00:00:00+03:00", "type": "text", "scope": "public", "chat_id": 1, "is_read": false, "is_edit": false, "status": "received", "created_at": "2018-01-01T00:00:00.000000Z"}]`)
2018-08-29 02:44:06 +03:00
req := MessagesRequest{ChannelType: ChannelTypeTelegram, Scope: MessageScopePublic}
data, status, err := c.Messages(req)
if err != nil {
t.Errorf("%d %v", status, err)
}
assert.NoError(t, err)
assert.NotEmpty(t, data)
for _, message := range data {
2018-12-26 17:38:41 +03:00
assert.NotEmpty(t, message.ID)
2018-08-29 02:44:06 +03:00
}
}
func TestMgClient_MessagesDialog(t *testing.T) {
t.Parallel()
c := client()
defer gock.Off()
gock.New(mgURL).
Get("/api/bot/v1/messages").
Reply(200).
BodyString(`[
{
"id": 1,
"time": "2024-11-14T20:48:21Z",
"type": "system",
"scope": "private",
"chat_id": 1,
"is_read": false,
"is_edit": false,
"status": "received",
"dialog": {
"id": 2054
},
"action": "dialog_closed",
"channel_id": 71,
"created_at": "2024-11-14T20:48:21.907566Z",
"updated_at": "2024-11-14T20:48:21.907566Z"
},
{
"id": 2,
"time": "2024-11-14T19:58:42Z",
"type": "text",
"scope": "public",
"chat_id": 1,
"is_read": false,
"is_edit": false,
"status": "failed",
"from": {
"id": 1,
"external_id": "1",
"type": "user",
"avatar": "http://avatars-test.jpeg",
"name": "John Smith",
"first_name": "John",
"last_name": "Smith",
"available": true
},
"dialog": {
"id": 2054
},
"error": {
"code": "malformed_response"
},
"content": "Message from user John Smith",
"quote": null,
"channel_id": 71,
"created_at": "2024-11-14T19:58:42.933025Z",
"updated_at": "2024-11-14T19:58:45.01619Z"
}
]`)
req := MessagesRequest{}
data, status, err := c.Messages(req)
if err != nil {
t.Errorf("%d %v", status, err)
}
assert.NoError(t, err)
assert.Len(t, data, 2)
for _, m := range data {
assert.NotNil(t, m.Message.Dialog)
assert.Equal(t, uint64(2054), m.Message.Dialog.ID)
}
}
2018-09-13 11:38:13 +03:00
func TestMgClient_MessageSendText(t *testing.T) {
2018-08-29 02:44:06 +03:00
c := client()
2019-03-07 12:58:09 +03:00
i := uint64(1)
2018-08-29 02:44:06 +03:00
message := MessageSendRequest{
2018-09-13 11:38:13 +03:00
Type: MsgTypeText,
2018-08-29 02:44:06 +03:00
Scope: "public",
Content: "test",
ChatID: i,
}
2019-03-07 12:58:09 +03:00
defer gock.Off()
gock.New(mgURL).
Post("/api/bot/v1/messages").
JSON(message).
Reply(200).
BodyString(`{"message_id": 1, "time": "2018-01-01T00:00:00+03:00"}`)
2018-08-29 02:44:06 +03:00
data, status, err := c.MessageSend(message)
if err != nil {
t.Errorf("%d %v", status, err)
}
assert.NoError(t, err)
assert.NotEmpty(t, data.MessageID)
}
2018-09-20 11:41:20 +03:00
func TestMgClient_MessageSendTextWithSuggestions(t *testing.T) {
c := client()
i := uint64(1)
message := MessageSendRequest{
Type: MsgTypeText,
Scope: "public",
Content: "test message with suggestions",
ChatID: i,
TransportAttachments: &TransportAttachments{
Suggestions: []Suggestion{
{
Type: SuggestionTypeText,
Title: "text suggestion",
},
{Type: SuggestionTypeEmail},
{Type: SuggestionTypePhone},
},
},
}
defer gock.Off()
gock.New(mgURL).
Post("/api/bot/v1/messages").
JSON(message).
Reply(200).
BodyString(`{"message_id": 1, "time": "2018-01-01T00:00:00+03:00"}`)
data, status, err := c.MessageSend(message)
if err != nil {
t.Errorf("%d %v", status, err)
}
assert.NoError(t, err)
assert.NotEmpty(t, data.MessageID)
}
2018-09-13 11:38:13 +03:00
func TestMgClient_MessageSendProduct(t *testing.T) {
c := client()
2019-03-07 12:58:09 +03:00
message := MessageSendRequest{
2018-09-13 11:38:13 +03:00
Type: MsgTypeProduct,
ChatID: 5,
Scope: "public",
Product: &MessageProduct{
ID: 1,
Name: "Some Product",
Article: "Art-111",
Url: "https://example.com",
Img: "http://example.com/pic.jpg",
Cost: &MessageOrderCost{
Value: 29900,
Currency: "rub",
},
Quantity: &MessageOrderQuantity{
Value: 1,
},
},
2019-03-07 12:58:09 +03:00
}
defer gock.Off()
gock.New(mgURL).
Post("/api/bot/v1/messages").
JSON(message).
Reply(200).
BodyString(`{"message_id": 1, "time": "2018-01-01T00:00:00+03:00"}`)
msg, _, err := c.MessageSend(message)
2018-09-13 11:38:13 +03:00
if err != nil {
t.Errorf("%v", err)
}
assert.NoError(t, err)
t.Logf("%v", msg)
}
2018-08-29 02:44:06 +03:00
2018-09-20 11:41:20 +03:00
func TestMgClient_MessageSendOrder(t *testing.T) {
c := client()
2019-03-07 12:58:09 +03:00
message := MessageSendRequest{
2018-09-20 11:41:20 +03:00
Type: MsgTypeOrder,
ChatID: 5,
Scope: "public",
Order: &MessageOrder{
Number: RandStringBytesMaskImprSrc(7),
Cost: &MessageOrderCost{
Value: 29900,
Currency: MsgCurrencyRub,
},
Status: &MessageOrderStatus{
Code: MsgOrderStatusCodeNew,
Name: "Новый",
},
Delivery: &MessageOrderDelivery{
Name: "Курьерская доставка",
Address: "г. Москва, Проспект Мира, 9",
Price: &MessageOrderCost{
2018-09-20 11:41:20 +03:00
Value: 1100,
Currency: MsgCurrencyRub,
},
},
Items: []MessageOrderItem{
{
Name: "iPhone 6",
Url: "https://example.com/product.html",
Img: "https://example.com/picture.png",
2018-09-20 11:41:20 +03:00
Price: &MessageOrderCost{
Value: 29900,
Currency: MsgCurrencyRub,
},
Quantity: &MessageOrderQuantity{
Value: 1,
},
},
},
},
2019-03-07 12:58:09 +03:00
}
defer gock.Off()
gock.New(mgURL).
Post("/api/bot/v1/messages").
JSON(message).
Reply(200).
BodyString(`{"message_id": 1, "time": "2018-01-01T00:00:00+03:00"}`)
msg, _, err := c.MessageSend(message)
2018-09-20 11:41:20 +03:00
if err != nil {
t.Errorf("%v", err)
}
assert.NoError(t, err)
t.Logf("%v", msg)
}
func TestMgClient_RandomStringGenerator(t *testing.T) {
rnd := RandStringBytesMaskImprSrc(7)
assert.NotEmpty(t, rnd)
t.Logf("%v", rnd)
}
2018-08-29 02:44:06 +03:00
func TestMgClient_MessageEdit(t *testing.T) {
c := client()
2019-03-07 12:58:09 +03:00
message := MessageEditRequest{
ID: uint64(1),
2018-08-29 02:44:06 +03:00
Content: "test",
}
2019-03-07 12:58:09 +03:00
defer gock.Off()
2018-08-29 02:44:06 +03:00
2019-03-07 12:58:09 +03:00
gock.New(mgURL).
Patch("/api/bot/v1/messages/1").
JSON(message).
Reply(200).
BodyString(`{"message_id": 1, "time": "2018-01-01T00:00:00+03:00"}`)
2018-08-29 02:44:06 +03:00
2019-03-07 12:58:09 +03:00
e, status, err := c.MessageEdit(message)
2018-08-29 02:44:06 +03:00
if err != nil {
t.Errorf("%d %v", status, err)
}
t.Logf("Message edit: %v", e)
}
func TestMgClient_MessageDelete(t *testing.T) {
c := client()
2019-03-07 12:58:09 +03:00
defer gock.Off()
2018-08-29 02:44:06 +03:00
2019-03-07 12:58:09 +03:00
gock.New(mgURL).
Delete("/api/bot/v1/messages/1").
Reply(200).
BodyString(`{}`)
2018-08-29 02:44:06 +03:00
2019-03-07 12:58:09 +03:00
d, status, err := c.MessageDelete(1)
2018-08-29 02:44:06 +03:00
if err != nil {
t.Errorf("%d %v", status, err)
}
t.Logf("Message delete: %v", d)
}
func TestMgClient_Info(t *testing.T) {
c := client()
2019-03-07 12:58:09 +03:00
req := InfoRequest{Name: "AWESOME", Avatar: "https://test.com/awesome_bot_avatar"}
defer gock.Off()
gock.New(mgURL).
Patch("/api/bot/v1/my/info").
JSON(req).
Reply(200).
BodyString(`{}`)
2018-08-29 02:44:06 +03:00
_, status, err := c.Info(req)
if err != nil {
t.Errorf("%d %v", status, err)
}
assert.NoError(t, err)
}
func TestMgClient_Commands(t *testing.T) {
c := client()
2019-03-07 12:58:09 +03:00
defer gock.Off()
gock.New(mgURL).
Get("/api/bot/v1/my/commands").
Reply(200).
BodyString(`[{"id": 1, "name": "command_name", "description": "Command description", "created_at": "2018-01-01T00:00:00.000000Z"}]`)
2018-08-29 02:44:06 +03:00
req := CommandsRequest{}
data, status, err := c.Commands(req)
if err != nil {
t.Errorf("%d %v", status, err)
}
assert.NoError(t, err)
assert.NotEmpty(t, data)
for _, command := range data {
assert.NotEmpty(t, command.Description)
}
}
func TestMgClient_CommandEditDelete(t *testing.T) {
c := client()
req := CommandEditRequest{
2019-03-07 12:58:09 +03:00
Name: "test_command",
Description: "Test command",
2018-08-29 02:44:06 +03:00
}
2019-03-07 12:58:09 +03:00
defer gock.Off()
gock.New(mgURL).
Put("/api/bot/v1/my/commands/test_command").
JSON(req).
Reply(200).
BodyString(`{"id": 1, "name": "test_command", "description": "Test description"}`)
2018-08-29 02:44:06 +03:00
n, status, err := c.CommandEdit(req)
if err != nil {
t.Errorf("%d %v", status, err)
}
assert.NoError(t, err)
assert.NotEmpty(t, n.ID)
2019-03-07 12:58:09 +03:00
gock.New(mgURL).
Delete("/api/bot/v1/my/commands/test_command").
Reply(200).
BodyString(`{}`)
2018-08-29 02:44:06 +03:00
d, status, err := c.CommandDelete(n.Name)
if err != nil {
t.Errorf("%d %v", status, err)
}
assert.NoError(t, err)
t.Logf("%v", d)
}
2018-09-01 00:41:29 +03:00
2024-06-28 18:04:49 +03:00
func TestMgClient_WsMeta_With_Options(t *testing.T) {
c := client()
events := []string{"user_updated", "user_join_chat"}
2024-07-11 14:02:42 +03:00
params := []WsParams{WsOptionIncludeMassCommunication}
2024-06-28 18:04:49 +03:00
2024-07-11 14:02:42 +03:00
url, headers, err := c.WsMeta(events, params...)
2024-06-28 18:04:49 +03:00
if err != nil {
t.Errorf("%v", err)
}
2024-07-11 13:49:29 +03:00
resURL := "wss://api.example.com/api/bot/v1/ws?events=user_updated,user_join_chat&options=include_mass_communication"
2024-06-28 18:04:49 +03:00
resToken := c.Token
2024-07-11 13:49:29 +03:00
assert.Equal(t, resURL, url)
2024-06-28 18:04:49 +03:00
assert.Equal(t, resToken, headers["X-Bot-Token"][0])
}
2018-09-01 00:41:29 +03:00
func TestMgClient_WsMeta(t *testing.T) {
c := client()
events := []string{"user_updated", "user_join_chat"}
url, headers, err := c.WsMeta(events)
if err != nil {
t.Errorf("%v", err)
}
2024-07-11 13:49:29 +03:00
resURL := fmt.Sprintf("%s%s%s%s", strings.Replace(c.URL, "https", "wss", 1), prefix, "/ws?events=", strings.Join(events[:], ","))
2018-09-01 00:41:29 +03:00
resToken := c.Token
2024-07-11 13:49:29 +03:00
assert.Equal(t, resURL, url)
2018-09-01 00:41:29 +03:00
assert.Equal(t, resToken, headers["X-Bot-Token"][0])
}
2018-09-20 11:41:20 +03:00
2018-12-26 17:38:41 +03:00
func TestMgClient_UploadFile(t *testing.T) {
c := client()
defer gock.Off()
gock.New("https://via.placeholder.com").
Get("/300").
Reply(http.StatusOK).
SetHeader("Content-Type", "image/jpeg").
Body(func() io.Reader {
res, err := base64.StdEncoding.DecodeString(`
H4sIAAAAAAACA/t/4/8DBgEvN083BkZGBgZGIGT4f5vBmYGVmYWFhZkVSLCysrKx83CwAwE/Nzcn
jyC/kJAgv6CgsJiMuLCIlKigoISihJSsrLy8vLC4koqSnIqMnLwcyBBGoFZ2NnY+Dg4+ORFBETmS
wf8DDIIcDAoMCsyMSgxMgozMgoz/jzDIA93JyggGDFDAyMTMAnQlBycXN1DBVgEGJkZmZiag+4Ee
AMrWAuUZWARZhRQNHdmEAxPZlQpFjBonLuRQdtp4UDTo4gcV46SiJk4uMXEJSSlVNXUNTS0TUzNz
C0srZxdXN3cPT6/gkNCw8IjIqOSU1LT0jMys4pLSsvKKyqrmlta29o7OrkmTp0ydNn3GzFmLFi9Z
umz5ipWrNm3esnXb9h07dx06fOToseMnTp66dPnK1WvXb9y89fDR4ydPnz1/8fLVx0+fv3z99v3H
z18gfzEyMDPCAFZ/CQL9xQSMFhZ2kL8YmcpBCgRZWBUN2YQcA9kTC4WVjBo5RJwmLtx4kFPZOOiD
aFLRRS4xFZOHqh9BXgP7jDiPNZHlM7jHEP66xcDDzAiMPGZBBnuGH/fuKWs3sItefBlWa7FqV+h8
P+01l9b8KnQQ27Labk545NLIL49WZwLl1m322vzyKEPFu6npl7temwAlQ3O1zi8XvQaSXMBtBdcZ
itDYYP//JgDowAia0AIAAA==`)
if err != nil {
t.Errorf("%v", err)
t.FailNow()
return nil
}
unpacker, err := gzip.NewReader(bytes.NewReader(res))
if err != nil {
t.Errorf("%v", err)
t.FailNow()
return nil
}
return unpacker
}())
2018-12-26 17:38:41 +03:00
resp, err := http.Get("https://via.placeholder.com/300")
if err != nil {
t.Errorf("%v", err)
t.FailNow()
2018-12-26 17:38:41 +03:00
}
defer resp.Body.Close()
2019-03-07 12:58:09 +03:00
gock.New(mgURL).
Post("/api/bot/v1/files/upload").
Reply(200).
BodyString(`{"created_at": "2018-01-01T00:00:00.000000Z", "hash": "hash", "id": "1"}`)
2018-12-26 17:38:41 +03:00
data, status, err := c.UploadFile(resp.Body)
if status != http.StatusOK {
t.Errorf("%v", err)
}
t.Logf("File %+v is upload", data)
}
2019-03-07 12:58:09 +03:00
func TestMgClient_UploadFileByUrl(t *testing.T) {
2018-12-26 17:38:41 +03:00
c := client()
2019-03-07 12:58:09 +03:00
file := UploadFileByUrlRequest{
2018-12-26 17:38:41 +03:00
Url: "https://via.placeholder.com/300",
2019-03-07 12:58:09 +03:00
}
defer gock.Off()
gock.New(mgURL).
Post("/api/bot/v1/files/upload_by_url").
JSON(file).
Reply(200).
BodyString(`{"created_at": "2018-01-01T00:00:00.000000Z", "hash": "hash", "id": "1"}`)
uploadFileResponse, st, err := c.UploadFileByURL(file)
2018-12-26 17:38:41 +03:00
if st != http.StatusOK {
t.Errorf("%v", err)
}
t.Logf("File %+v is upload", uploadFileResponse.ID)
assert.NoError(t, err)
}
2018-09-20 11:41:20 +03:00
func RandStringBytesMaskImprSrc(n int) string {
b := make([]byte, n)
// A src.Int63() generates 63 random bits, enough for letterIdxMax characters!
for i, cache, remain := n-1, src.Int63(), letterIdxMax; i >= 0; {
if remain == 0 {
cache, remain = src.Int63(), letterIdxMax
}
if idx := int(cache & letterIdxMask); idx < len(letterBytes) {
b[i] = letterBytes[idx]
i--
}
cache >>= letterIdxBits
remain--
}
return string(b)
}
2021-11-25 12:51:29 +03:00
func TestMgClient_DebugNoLogger(t *testing.T) {
c := client()
c.Debug = true
var buf bytes.Buffer
log.SetOutput(&buf)
defer func() {
log.SetOutput(os.Stderr)
}()
c.writeLog("Test log string")
assert.Contains(t, buf.String(), "Test log string")
}
func TestMgClient_DebugWithLogger(t *testing.T) {
var buf bytes.Buffer
logger := log.New(&buf, "Custom log prefix ", 0)
2024-02-09 09:44:36 +03:00
c := client(OptionDebug(), OptionLogger(logger))
2021-11-25 12:51:29 +03:00
c.writeLog("Test log string")
assert.Contains(t, buf.String(), "Custom log prefix Test log string")
}
2022-11-16 15:27:37 +03:00
func TestMgClient_SuccessChatsByCustomerId(t *testing.T) {
defer gock.Off()
customerID := uint64(191140)
gock.New(mgURL).
Path("/api/bot/v1/chats").
MatchParam("customer_id", fmt.Sprintf("%d", customerID)).
MatchHeader("X-Bot-Token", mgToken).
Reply(http.StatusOK).
JSON(getJSONResponseChats())
apiClient := client()
chatsRequest := ChatsRequest{
CustomerID: customerID,
}
resp, statusCode, err := apiClient.Chats(chatsRequest)
assert.NoError(t, err)
assert.Equal(t, http.StatusOK, statusCode)
assert.Equal(t, 1, len(resp))
assert.Equal(t, uint64(9000), resp[0].ID)
assert.Equal(t, uint64(8000), resp[0].Channel.ID)
assert.Equal(t, customerID, resp[0].Customer.ID)
assert.Equal(t, "Имя Фамилия", resp[0].Customer.Name)
assert.Equal(t, "Имя", resp[0].Customer.FirstName)
assert.Equal(t, "Фамилия", resp[0].Customer.LastName)
}
func getJSONResponseChats() string {
return `[
{
"id": 9000,
"channel": {
"id": 8000,
"avatar": "",
"transport_id": 555,
"type": "transport",
"settings": {
"status": {
"delivered": "send"
},
"text": {
"creating": "both",
"editing": "both",
"quoting": "both",
"deleting": "receive",
"max_chars_count": 4096
},
"product": {
"creating": "receive",
"editing": "receive"
},
"order": {
"creating": "receive",
"editing": "receive"
},
"image": {
"creating": "both",
"editing": "both",
"quoting": "both",
"deleting": "receive",
"max_items_count": 10
},
"file": {
"creating": "both",
"editing": "both",
"quoting": "both",
"deleting": "receive",
"max_items_count": 1
},
"audio": {
"creating": "both",
"quoting": "both",
"deleting": "receive",
"max_items_count": 1
},
"suggestions": {
"text": "both",
"email": "both",
"phone": "both"
}
},
"name": "@test_bot123",
"is_active": false
},
"customer": {
"id": 191140,
"external_id": "",
"type": "customer",
"avatar": "",
"name": "Имя Фамилия",
"username": "Имя",
"first_name": "Имя",
"last_name": "Фамилия"
},
"last_activity": "2022-10-28T13:17:38+03:00",
"created_at": "2022-10-07T14:00:24.795382Z",
"updated_at": "2022-10-28T12:19:04.834592Z"
}
]`
}