@effect-ak/tg-bot-client 0.3.1 → 0.3.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.ts +49 -63
- package/dist/index.js +205 -225
- package/dist/index.mjs +203 -225
- package/package.json +1 -1
package/dist/index.d.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
import * as Context from 'effect/Context';
|
|
2
|
-
import * as Micro from 'effect/Micro';
|
|
3
1
|
import * as effect_Cause from 'effect/Cause';
|
|
4
2
|
import * as effect_Types from 'effect/Types';
|
|
3
|
+
import * as Micro from 'effect/Micro';
|
|
4
|
+
import * as Context from 'effect/Context';
|
|
5
5
|
|
|
6
6
|
type ErrorReason = {
|
|
7
7
|
readonly type: "NotOkResponse";
|
|
@@ -31,11 +31,6 @@ type TgBotClientSettingsInput = {
|
|
|
31
31
|
base_url?: string;
|
|
32
32
|
};
|
|
33
33
|
|
|
34
|
-
type TgBotClientConfigObject = Required<TgBotClientSettingsInput>;
|
|
35
|
-
declare const TgBotClientConfig_base: Context.TagClass<TgBotClientConfig, "TgBotClientConfig", Required<TgBotClientSettingsInput>>;
|
|
36
|
-
declare class TgBotClientConfig extends TgBotClientConfig_base {
|
|
37
|
-
}
|
|
38
|
-
|
|
39
34
|
interface AffiliateInfo {
|
|
40
35
|
commission_per_mille: number;
|
|
41
36
|
amount: number;
|
|
@@ -2730,39 +2725,6 @@ interface UploadStickerFileInput {
|
|
|
2730
2725
|
sticker_format: "static" | "animated" | "video";
|
|
2731
2726
|
}
|
|
2732
2727
|
|
|
2733
|
-
type ClientExecuteRequestServiceInterface = Micro.Micro.Success<typeof ClientExecuteRequestServiceDefault>;
|
|
2734
|
-
declare const ClientExecuteRequestServiceDefault: Micro.Micro<{
|
|
2735
|
-
readonly execute: <M extends keyof Api>(method: M, input: Parameters<Api[M]>[0]) => Micro.Micro<ReturnType<Api[M]>, TgBotClientError, never>;
|
|
2736
|
-
}, never, TgBotClientConfig>;
|
|
2737
|
-
|
|
2738
|
-
declare const getFile: (fileId: string, config: TgBotClientConfigObject, execute: ClientExecuteRequestServiceInterface) => Micro.Micro<File, TgBotClientError>;
|
|
2739
|
-
|
|
2740
|
-
type ClientFileServiceInterface = Context.Tag.Service<typeof ClientFileService>;
|
|
2741
|
-
declare const ClientFileService_base: Context.TagClass<ClientFileService, "ClientFileService", {
|
|
2742
|
-
getFile: (input: {
|
|
2743
|
-
file_id: string;
|
|
2744
|
-
}) => ReturnType<typeof getFile>;
|
|
2745
|
-
}>;
|
|
2746
|
-
declare class ClientFileService extends ClientFileService_base {
|
|
2747
|
-
}
|
|
2748
|
-
|
|
2749
|
-
type TgBotClient = ReturnType<typeof makeTgBotClient>;
|
|
2750
|
-
declare const makeTgBotClient: (input: TgBotClientSettingsInput) => {
|
|
2751
|
-
execute: <M extends keyof Api>(method: M, input: Parameters<Api[M]>[0]) => Promise<ReturnType<Api[M]>>;
|
|
2752
|
-
getFile: (input: Parameters<ClientFileServiceInterface["getFile"]>[0]) => Promise<File>;
|
|
2753
|
-
};
|
|
2754
|
-
|
|
2755
|
-
type PollAndHandleInput = {
|
|
2756
|
-
settings: BotMessageHandlerSettings;
|
|
2757
|
-
execute: ClientExecuteRequestServiceInterface["execute"];
|
|
2758
|
-
};
|
|
2759
|
-
type PollAndHandleResult = Micro.Micro.Success<ReturnType<typeof pollAndHandle>>;
|
|
2760
|
-
declare const pollAndHandle: (input: PollAndHandleInput) => Micro.Micro<{
|
|
2761
|
-
updates: Update[];
|
|
2762
|
-
lastSuccessId: number | undefined;
|
|
2763
|
-
hasError: boolean;
|
|
2764
|
-
}, TgBotClientError, never>;
|
|
2765
|
-
|
|
2766
2728
|
type AvailableUpdateTypes = Exclude<keyof Update, 'update_id'>;
|
|
2767
2729
|
type LogLevel = "info" | "debug";
|
|
2768
2730
|
type BotResponse = {
|
|
@@ -2773,30 +2735,23 @@ type BotResponse = {
|
|
|
2773
2735
|
type BotMessageHandlers = {
|
|
2774
2736
|
[K in AvailableUpdateTypes as `on_${K}`]?: (update: NonNullable<Update[K]>) => BotResponse | undefined;
|
|
2775
2737
|
};
|
|
2776
|
-
|
|
2738
|
+
|
|
2739
|
+
type BotMessageHandlerShape = Context.Tag.Service<BotMessageHandler>;
|
|
2740
|
+
declare const BotMessageHandler_base: Context.TagClass<BotMessageHandler, "BotMessageHandler", {
|
|
2777
2741
|
readonly log_level?: LogLevel;
|
|
2778
2742
|
readonly update_types?: AvailableUpdateTypes[];
|
|
2779
2743
|
readonly batch_size?: number;
|
|
2780
2744
|
readonly timeout?: number;
|
|
2781
2745
|
readonly max_empty_responses?: number;
|
|
2782
|
-
} & BotMessageHandlers
|
|
2783
|
-
|
|
2784
|
-
};
|
|
2785
|
-
|
|
2786
|
-
declare const BotUpdatePollerService_base: Context.TagClass<BotUpdatePollerService, "BotUpdatePollerService", {
|
|
2787
|
-
readonly runBot: (messageHandler: BotMessageHandlerSettings) => Micro.Micro<Micro.MicroFiber<unknown, TgBotClientError>, never, never>;
|
|
2788
|
-
}>;
|
|
2789
|
-
declare class BotUpdatePollerService extends BotUpdatePollerService_base {
|
|
2746
|
+
} & BotMessageHandlers>;
|
|
2747
|
+
declare class BotMessageHandler extends BotMessageHandler_base {
|
|
2790
2748
|
}
|
|
2791
2749
|
|
|
2792
2750
|
type BotInstance = Micro.Micro.Success<ReturnType<typeof BotFactoryServiceDefault["runBot"]>>;
|
|
2793
2751
|
declare const BotFactoryService_base: Context.TagClass<BotFactoryService, "BotFactoryService", {
|
|
2794
|
-
makeBot: (messageHandler: BotMessageHandlerSettings) => Micro.Micro<{
|
|
2795
|
-
fiber: Micro.MicroFiber<unknown, TgBotClientError>;
|
|
2796
|
-
runBot: (messageHandler: BotMessageHandlerSettings) => Micro.Micro<Micro.MicroFiber<unknown, TgBotClientError>, never, never>;
|
|
2797
|
-
}, never, BotUpdatePollerService>;
|
|
2798
2752
|
runBot: (input: RunBotInput) => Micro.Micro<{
|
|
2799
|
-
readonly reload: (input: Partial<RunBotInput>) => Promise<
|
|
2753
|
+
readonly reload: (input: Partial<RunBotInput>) => Promise<void>;
|
|
2754
|
+
readonly fiber: () => Micro.MicroFiber<unknown, TgBotClientError> | undefined;
|
|
2800
2755
|
}, string, never>;
|
|
2801
2756
|
}>;
|
|
2802
2757
|
declare class BotFactoryService extends BotFactoryService_base {
|
|
@@ -2805,20 +2760,51 @@ type RunBotInput = ({
|
|
|
2805
2760
|
type: "fromJsonFile";
|
|
2806
2761
|
} | {
|
|
2807
2762
|
type: "config";
|
|
2808
|
-
} & TgBotClientSettingsInput) &
|
|
2763
|
+
} & TgBotClientSettingsInput) & BotMessageHandlerShape;
|
|
2809
2764
|
declare const BotFactoryServiceDefault: {
|
|
2810
|
-
makeBot: (messageHandler: BotMessageHandlerSettings) => Micro.Micro<{
|
|
2811
|
-
fiber: Micro.MicroFiber<unknown, TgBotClientError>;
|
|
2812
|
-
runBot: (messageHandler: BotMessageHandlerSettings) => Micro.Micro<Micro.MicroFiber<unknown, TgBotClientError>, never, never>;
|
|
2813
|
-
}, never, BotUpdatePollerService>;
|
|
2814
2765
|
runBot: (input: RunBotInput) => Micro.Micro<{
|
|
2815
|
-
readonly reload: (input: Partial<RunBotInput>) => Promise<
|
|
2766
|
+
readonly reload: (input: Partial<RunBotInput>) => Promise<void>;
|
|
2767
|
+
readonly fiber: () => Micro.MicroFiber<unknown, TgBotClientError> | undefined;
|
|
2816
2768
|
}, string, never>;
|
|
2817
2769
|
};
|
|
2818
2770
|
|
|
2819
|
-
declare const
|
|
2820
|
-
|
|
2771
|
+
declare const TgBotClientConfig_base: Context.TagClass<TgBotClientConfig, "TgBotClientConfig", Required<TgBotClientSettingsInput>>;
|
|
2772
|
+
declare class TgBotClientConfig extends TgBotClientConfig_base {
|
|
2773
|
+
}
|
|
2774
|
+
|
|
2775
|
+
type BotUpdatePollerServiceInterface = Micro.Micro.Success<typeof BotUpdatesPollerServiceDefault>;
|
|
2776
|
+
declare const BotUpdatePollerService_base: Context.TagClass<BotUpdatePollerService, "BotUpdatePollerService", {
|
|
2777
|
+
readonly runBot: Micro.Micro<void, never, BotMessageHandler | TgBotClientConfig>;
|
|
2778
|
+
readonly getFiber: () => Micro.MicroFiber<unknown, TgBotClientError> | undefined;
|
|
2821
2779
|
}>;
|
|
2780
|
+
declare class BotUpdatePollerService extends BotUpdatePollerService_base {
|
|
2781
|
+
}
|
|
2782
|
+
declare const BotUpdatesPollerServiceDefault: Micro.Micro<{
|
|
2783
|
+
readonly runBot: Micro.Micro<void, never, BotMessageHandler | TgBotClientConfig>;
|
|
2784
|
+
readonly getFiber: () => Micro.MicroFiber<unknown, TgBotClientError> | undefined;
|
|
2785
|
+
}, never, never>;
|
|
2786
|
+
|
|
2787
|
+
declare const runTgChatBot: (input: RunBotInput) => Promise<{
|
|
2788
|
+
readonly reload: (input: Partial<RunBotInput>) => Promise<void>;
|
|
2789
|
+
readonly fiber: () => Micro.MicroFiber<unknown, TgBotClientError> | undefined;
|
|
2790
|
+
}>;
|
|
2791
|
+
|
|
2792
|
+
declare const getFile: (fileId: string) => Micro.Micro<File, TgBotClientError, TgBotClientConfig>;
|
|
2793
|
+
|
|
2794
|
+
type ClientFileServiceInterface = Context.Tag.Service<typeof ClientFileService>;
|
|
2795
|
+
declare const ClientFileService_base: Context.TagClass<ClientFileService, "ClientFileService", {
|
|
2796
|
+
getFile: (input: {
|
|
2797
|
+
file_id: string;
|
|
2798
|
+
}) => ReturnType<typeof getFile>;
|
|
2799
|
+
}>;
|
|
2800
|
+
declare class ClientFileService extends ClientFileService_base {
|
|
2801
|
+
}
|
|
2802
|
+
|
|
2803
|
+
type TgBotClient = ReturnType<typeof makeTgBotClient>;
|
|
2804
|
+
declare const makeTgBotClient: (input: TgBotClientSettingsInput) => {
|
|
2805
|
+
execute: <M extends keyof Api>(method: M, input: Parameters<Api[M]>[0]) => Promise<ReturnType<Api[M]>>;
|
|
2806
|
+
getFile: (input: Parameters<ClientFileServiceInterface["getFile"]>[0]) => Promise<File>;
|
|
2807
|
+
};
|
|
2822
2808
|
|
|
2823
2809
|
declare const defaultBaseUrl = "https://api.telegram.org";
|
|
2824
2810
|
declare const MESSAGE_EFFECTS: {
|
|
@@ -2833,4 +2819,4 @@ type MessageEffect = keyof typeof MESSAGE_EFFECTS;
|
|
|
2833
2819
|
declare const messageEffectIdCodes: MessageEffect[];
|
|
2834
2820
|
declare const isMessageEffect: (input: unknown) => input is MessageEffect;
|
|
2835
2821
|
|
|
2836
|
-
export { type AddStickerToSetInput, type AffiliateInfo, type Animation, type AnswerCallbackQueryInput, type AnswerInlineQueryInput, type AnswerPreCheckoutQueryInput, type AnswerShippingQueryInput, type AnswerWebAppQueryInput, type Api, type ApproveChatJoinRequestInput, type Audio, type AvailableUpdateTypes, type BackgroundFill, type BackgroundFillFreeformGradient, type BackgroundFillGradient, type BackgroundFillSolid, type BackgroundType, type BackgroundTypeChatTheme, type BackgroundTypeFill, type BackgroundTypePattern, type BackgroundTypeWallpaper, type BanChatMemberInput, type BanChatSenderChatInput, type Birthdate, type BotCommand, type BotCommandScope, type BotCommandScopeAllChatAdministrators, type BotCommandScopeAllGroupChats, type BotCommandScopeAllPrivateChats, type BotCommandScopeChat, type BotCommandScopeChatAdministrators, type BotCommandScopeChatMember, type BotCommandScopeDefault, type BotDescription, BotFactoryService, BotFactoryServiceDefault, type BotInstance, type
|
|
2822
|
+
export { type AddStickerToSetInput, type AffiliateInfo, type Animation, type AnswerCallbackQueryInput, type AnswerInlineQueryInput, type AnswerPreCheckoutQueryInput, type AnswerShippingQueryInput, type AnswerWebAppQueryInput, type Api, type ApproveChatJoinRequestInput, type Audio, type AvailableUpdateTypes, type BackgroundFill, type BackgroundFillFreeformGradient, type BackgroundFillGradient, type BackgroundFillSolid, type BackgroundType, type BackgroundTypeChatTheme, type BackgroundTypeFill, type BackgroundTypePattern, type BackgroundTypeWallpaper, type BanChatMemberInput, type BanChatSenderChatInput, type Birthdate, type BotCommand, type BotCommandScope, type BotCommandScopeAllChatAdministrators, type BotCommandScopeAllGroupChats, type BotCommandScopeAllPrivateChats, type BotCommandScopeChat, type BotCommandScopeChatAdministrators, type BotCommandScopeChatMember, type BotCommandScopeDefault, type BotDescription, BotFactoryService, BotFactoryServiceDefault, type BotInstance, type BotMessageHandlers, type BotName, type BotResponse, type BotShortDescription, BotUpdatePollerService, type BotUpdatePollerServiceInterface, BotUpdatesPollerServiceDefault, type BusinessConnection, type BusinessIntro, type BusinessLocation, type BusinessMessagesDeleted, type BusinessOpeningHours, type BusinessOpeningHoursInterval, type CallbackGame, type CallbackQuery, type Chat, type ChatAdministratorRights, type ChatBackground, type ChatBoost, type ChatBoostAdded, type ChatBoostRemoved, type ChatBoostSource, type ChatBoostSourceGiftCode, type ChatBoostSourceGiveaway, type ChatBoostSourcePremium, type ChatBoostUpdated, type ChatFullInfo, type ChatInviteLink, type ChatJoinRequest, type ChatLocation, type ChatMember, type ChatMemberAdministrator, type ChatMemberBanned, type ChatMemberLeft, type ChatMemberMember, type ChatMemberOwner, type ChatMemberRestricted, type ChatMemberUpdated, type ChatPermissions, type ChatPhoto, type ChatShared, type ChosenInlineResult, type CloseForumTopicInput, type CloseGeneralForumTopicInput, type CloseInput, type Contact, type CopyMessageInput, type CopyMessagesInput, type CopyTextButton, type CreateChatInviteLinkInput, type CreateChatSubscriptionInviteLinkInput, type CreateForumTopicInput, type CreateInvoiceLinkInput, type CreateNewStickerSetInput, type DeclineChatJoinRequestInput, type DeleteChatPhotoInput, type DeleteChatStickerSetInput, type DeleteForumTopicInput, type DeleteMessageInput, type DeleteMessagesInput, type DeleteMyCommandsInput, type DeleteStickerFromSetInput, type DeleteStickerSetInput, type DeleteWebhookInput, type Dice, type Document, type EditChatInviteLinkInput, type EditChatSubscriptionInviteLinkInput, type EditForumTopicInput, type EditGeneralForumTopicInput, type EditMessageCaptionInput, type EditMessageLiveLocationInput, type EditMessageMediaInput, type EditMessageReplyMarkupInput, type EditMessageTextInput, type EditUserStarSubscriptionInput, type EncryptedCredentials, type EncryptedPassportElement, type ExportChatInviteLinkInput, type ExternalReplyInfo, type File$1 as File, type ForceReply, type ForumTopic, type ForumTopicClosed, type ForumTopicCreated, type ForumTopicEdited, type ForumTopicReopened, type ForwardMessageInput, type ForwardMessagesInput, type Game, type GameHighScore, type GeneralForumTopicHidden, type GeneralForumTopicUnhidden, type GetAvailableGiftsInput, type GetBusinessConnectionInput, type GetChatAdministratorsInput, type GetChatInput, type GetChatMemberCountInput, type GetChatMemberInput, type GetChatMenuButtonInput, type GetCustomEmojiStickersInput, type GetFileInput, type GetForumTopicIconStickersInput, type GetGameHighScoresInput, type GetMeInput, type GetMyCommandsInput, type GetMyDefaultAdministratorRightsInput, type GetMyDescriptionInput, type GetMyNameInput, type GetMyShortDescriptionInput, type GetStarTransactionsInput, type GetStickerSetInput, type GetUpdatesInput, type GetUserChatBoostsInput, type GetUserProfilePhotosInput, type GetWebhookInfoInput, type Gift, type Gifts, type Giveaway, type GiveawayCompleted, type GiveawayCreated, type GiveawayWinners, type HideGeneralForumTopicInput, type InaccessibleMessage, type InlineKeyboardButton, type InlineKeyboardMarkup, type InlineQuery, type InlineQueryResult, type InlineQueryResultArticle, type InlineQueryResultAudio, type InlineQueryResultCachedAudio, type InlineQueryResultCachedDocument, type InlineQueryResultCachedGif, type InlineQueryResultCachedMpeg4Gif, type InlineQueryResultCachedPhoto, type InlineQueryResultCachedSticker, type InlineQueryResultCachedVideo, type InlineQueryResultCachedVoice, type InlineQueryResultContact, type InlineQueryResultDocument, type InlineQueryResultGame, type InlineQueryResultGif, type InlineQueryResultLocation, type InlineQueryResultMpeg4Gif, type InlineQueryResultPhoto, type InlineQueryResultVenue, type InlineQueryResultVideo, type InlineQueryResultVoice, type InlineQueryResultsButton, type InputContactMessageContent, type InputFile, type InputInvoiceMessageContent, type InputLocationMessageContent, type InputMedia, type InputMediaAnimation, type InputMediaAudio, type InputMediaDocument, type InputMediaPhoto, type InputMediaVideo, type InputMessageContent, type InputPaidMedia, type InputPaidMediaPhoto, type InputPaidMediaVideo, type InputPollOption, type InputSticker, type InputTextMessageContent, type InputVenueMessageContent, type Invoice, type KeyboardButton, type KeyboardButtonPollType, type KeyboardButtonRequestChat, type KeyboardButtonRequestUsers, type LabeledPrice, type LeaveChatInput, type LinkPreviewOptions, type Location, type LogLevel, type LogOutInput, type LoginUrl, MESSAGE_EFFECTS, type MaskPosition, type MaybeInaccessibleMessage, type MenuButton, type MenuButtonCommands, type MenuButtonDefault, type MenuButtonWebApp, type Message, type MessageAutoDeleteTimerChanged, type MessageEffect, type MessageEntity, type MessageId, type MessageOrigin, type MessageOriginChannel, type MessageOriginChat, type MessageOriginHiddenUser, type MessageOriginUser, type MessageReactionCountUpdated, type MessageReactionUpdated, type OrderInfo, type PaidMedia, type PaidMediaInfo, type PaidMediaPhoto, type PaidMediaPreview, type PaidMediaPurchased, type PaidMediaVideo, type PassportData, type PassportElementError, type PassportElementErrorDataField, type PassportElementErrorFile, type PassportElementErrorFiles, type PassportElementErrorFrontSide, type PassportElementErrorReverseSide, type PassportElementErrorSelfie, type PassportElementErrorTranslationFile, type PassportElementErrorTranslationFiles, type PassportElementErrorUnspecified, type PassportFile, type PhotoSize, type PinChatMessageInput, type Poll, type PollAnswer, type PollOption, type PreCheckoutQuery, type PreparedInlineMessage, type PromoteChatMemberInput, type ProximityAlertTriggered, type ReactionCount, type ReactionType, type ReactionTypeCustomEmoji, type ReactionTypeEmoji, type ReactionTypePaid, type RefundStarPaymentInput, type RefundedPayment, type ReopenForumTopicInput, type ReopenGeneralForumTopicInput, type ReplaceStickerInSetInput, type ReplyKeyboardMarkup, type ReplyKeyboardRemove, type ReplyParameters, type ResponseParameters, type RestrictChatMemberInput, type RevenueWithdrawalState, type RevenueWithdrawalStateFailed, type RevenueWithdrawalStatePending, type RevenueWithdrawalStateSucceeded, type RevokeChatInviteLinkInput, type RunBotInput, type SavePreparedInlineMessageInput, type SendAnimationInput, type SendAudioInput, type SendChatActionInput, type SendContactInput, type SendDiceInput, type SendDocumentInput, type SendGameInput, type SendGiftInput, type SendInvoiceInput, type SendLocationInput, type SendMediaGroupInput, type SendMessageInput, type SendPaidMediaInput, type SendPhotoInput, type SendPollInput, type SendStickerInput, type SendVenueInput, type SendVideoInput, type SendVideoNoteInput, type SendVoiceInput, type SentWebAppMessage, type SetChatAdministratorCustomTitleInput, type SetChatDescriptionInput, type SetChatMenuButtonInput, type SetChatPermissionsInput, type SetChatPhotoInput, type SetChatStickerSetInput, type SetChatTitleInput, type SetCustomEmojiStickerSetThumbnailInput, type SetGameScoreInput, type SetMessageReactionInput, type SetMyCommandsInput, type SetMyDefaultAdministratorRightsInput, type SetMyDescriptionInput, type SetMyNameInput, type SetMyShortDescriptionInput, type SetPassportDataErrorsInput, type SetStickerEmojiListInput, type SetStickerKeywordsInput, type SetStickerMaskPositionInput, type SetStickerPositionInSetInput, type SetStickerSetThumbnailInput, type SetStickerSetTitleInput, type SetUserEmojiStatusInput, type SetWebhookInput, type SharedUser, type ShippingAddress, type ShippingOption, type ShippingQuery, type StarTransaction, type StarTransactions, type Sticker, type StickerSet, type StopMessageLiveLocationInput, type StopPollInput, type Story, type SuccessfulPayment, type SwitchInlineQueryChosenChat, type TextQuote, type TgBotClient, type TransactionPartner, type TransactionPartnerAffiliateProgram, type TransactionPartnerFragment, type TransactionPartnerOther, type TransactionPartnerTelegramAds, type TransactionPartnerTelegramApi, type TransactionPartnerUser, type UnbanChatMemberInput, type UnbanChatSenderChatInput, type UnhideGeneralForumTopicInput, type UnpinAllChatMessagesInput, type UnpinAllForumTopicMessagesInput, type UnpinAllGeneralForumTopicMessagesInput, type UnpinChatMessageInput, type Update, type UploadStickerFileInput, type User, type UserChatBoosts, type UserProfilePhotos, type UsersShared, type Venue, type Video, type VideoChatEnded, type VideoChatParticipantsInvited, type VideoChatScheduled, type VideoChatStarted, type VideoNote, type Voice, type WebAppData, type WebAppInfo, type WebhookInfo, type WriteAccessAllowed, defaultBaseUrl, isMessageEffect, makeTgBotClient, messageEffectIdCodes, runTgChatBot };
|
package/dist/index.js
CHANGED
|
@@ -32,6 +32,8 @@ var src_exports = {};
|
|
|
32
32
|
__export(src_exports, {
|
|
33
33
|
BotFactoryService: () => BotFactoryService,
|
|
34
34
|
BotFactoryServiceDefault: () => BotFactoryServiceDefault,
|
|
35
|
+
BotUpdatePollerService: () => BotUpdatePollerService,
|
|
36
|
+
BotUpdatesPollerServiceDefault: () => BotUpdatesPollerServiceDefault,
|
|
35
37
|
MESSAGE_EFFECTS: () => MESSAGE_EFFECTS,
|
|
36
38
|
defaultBaseUrl: () => defaultBaseUrl,
|
|
37
39
|
isMessageEffect: () => isMessageEffect,
|
|
@@ -41,11 +43,95 @@ __export(src_exports, {
|
|
|
41
43
|
});
|
|
42
44
|
module.exports = __toCommonJS(src_exports);
|
|
43
45
|
|
|
44
|
-
// src/
|
|
45
|
-
var
|
|
46
|
+
// src/bot/factory/_service.ts
|
|
47
|
+
var Micro6 = __toESM(require("effect/Micro"));
|
|
48
|
+
var Context4 = __toESM(require("effect/Context"));
|
|
46
49
|
|
|
47
|
-
// src/
|
|
50
|
+
// src/bot/message-handler/_service.ts
|
|
48
51
|
var Context = __toESM(require("effect/Context"));
|
|
52
|
+
var BotMessageHandler = class extends Context.Tag("BotMessageHandler")() {
|
|
53
|
+
};
|
|
54
|
+
|
|
55
|
+
// src/bot/update-poller/_service.ts
|
|
56
|
+
var Micro4 = __toESM(require("effect/Micro"));
|
|
57
|
+
var Context3 = __toESM(require("effect/Context"));
|
|
58
|
+
|
|
59
|
+
// src/bot/update-poller/poll-and-handle.ts
|
|
60
|
+
var Micro3 = __toESM(require("effect/Micro"));
|
|
61
|
+
|
|
62
|
+
// src/bot/update-poller/settings.ts
|
|
63
|
+
var makeSettingsFrom = (input) => {
|
|
64
|
+
let limit = input.batch_size ?? 10;
|
|
65
|
+
let timeout = input.timeout ?? 10;
|
|
66
|
+
let max_empty_responses = input.max_empty_responses;
|
|
67
|
+
let update_types = input.update_types;
|
|
68
|
+
let log_level = input.log_level;
|
|
69
|
+
if (limit < 10 || limit > 100) {
|
|
70
|
+
console.warn("Wrong limit, must be in [10..100], using 10 instead");
|
|
71
|
+
limit = 10;
|
|
72
|
+
}
|
|
73
|
+
if (timeout < 2 || timeout > 10) {
|
|
74
|
+
console.warn("Wrong timeout, must be in [2..10], using 2 instead");
|
|
75
|
+
limit = 10;
|
|
76
|
+
}
|
|
77
|
+
if (max_empty_responses && max_empty_responses < 2) {
|
|
78
|
+
console.warn("Wrong max_empty_responses, must be in [2..infinity], using infinity");
|
|
79
|
+
max_empty_responses = void 0;
|
|
80
|
+
}
|
|
81
|
+
if (max_empty_responses && max_empty_responses < 2) {
|
|
82
|
+
console.warn("Wrong max_empty_responses, must be in [2..infinity], using infinity");
|
|
83
|
+
max_empty_responses = void 0;
|
|
84
|
+
}
|
|
85
|
+
if (!update_types) {
|
|
86
|
+
console.info("Handling only messages, ignoring others");
|
|
87
|
+
update_types = ["message"];
|
|
88
|
+
}
|
|
89
|
+
if (!log_level) {
|
|
90
|
+
log_level = "info";
|
|
91
|
+
}
|
|
92
|
+
return {
|
|
93
|
+
limit,
|
|
94
|
+
timeout,
|
|
95
|
+
max_empty_responses,
|
|
96
|
+
update_types,
|
|
97
|
+
log_level
|
|
98
|
+
};
|
|
99
|
+
};
|
|
100
|
+
|
|
101
|
+
// src/bot/update-poller/fetch-updates.ts
|
|
102
|
+
var Micro2 = __toESM(require("effect/Micro"));
|
|
103
|
+
|
|
104
|
+
// src/bot/message-handler/utils.ts
|
|
105
|
+
var extractUpdate = (input) => {
|
|
106
|
+
for (const [field, value] of Object.entries(input)) {
|
|
107
|
+
if (field == "update_id") {
|
|
108
|
+
continue;
|
|
109
|
+
}
|
|
110
|
+
return {
|
|
111
|
+
type: field,
|
|
112
|
+
...value
|
|
113
|
+
};
|
|
114
|
+
}
|
|
115
|
+
return;
|
|
116
|
+
};
|
|
117
|
+
|
|
118
|
+
// src/client/execute-request/execute.ts
|
|
119
|
+
var Micro = __toESM(require("effect/Micro"));
|
|
120
|
+
var String = __toESM(require("effect/String"));
|
|
121
|
+
|
|
122
|
+
// src/client/errors.ts
|
|
123
|
+
var Data = __toESM(require("effect/Data"));
|
|
124
|
+
var TgBotClientError = class _TgBotClientError extends Data.TaggedError("TgBotClientError") {
|
|
125
|
+
static missingSuccess = new _TgBotClientError({
|
|
126
|
+
reason: {
|
|
127
|
+
type: "ClientInternalError",
|
|
128
|
+
cause: "Expected 'success' to be defined"
|
|
129
|
+
}
|
|
130
|
+
});
|
|
131
|
+
};
|
|
132
|
+
|
|
133
|
+
// src/client/config.ts
|
|
134
|
+
var Context2 = __toESM(require("effect/Context"));
|
|
49
135
|
|
|
50
136
|
// src/const.ts
|
|
51
137
|
var defaultBaseUrl = "https://api.telegram.org";
|
|
@@ -67,26 +153,7 @@ var makeTgBotClientConfig = (input) => TgBotClientConfig.of({
|
|
|
67
153
|
...input,
|
|
68
154
|
base_url: input.base_url ?? defaultBaseUrl
|
|
69
155
|
});
|
|
70
|
-
var TgBotClientConfig = class extends
|
|
71
|
-
};
|
|
72
|
-
|
|
73
|
-
// src/client/execute-request/_service.ts
|
|
74
|
-
var Micro2 = __toESM(require("effect/Micro"));
|
|
75
|
-
var Context2 = __toESM(require("effect/Context"));
|
|
76
|
-
|
|
77
|
-
// src/client/execute-request/execute.ts
|
|
78
|
-
var Micro = __toESM(require("effect/Micro"));
|
|
79
|
-
var String = __toESM(require("effect/String"));
|
|
80
|
-
|
|
81
|
-
// src/client/errors.ts
|
|
82
|
-
var Data = __toESM(require("effect/Data"));
|
|
83
|
-
var TgBotClientError = class _TgBotClientError extends Data.TaggedError("TgBotClientError") {
|
|
84
|
-
static missingSuccess = new _TgBotClientError({
|
|
85
|
-
reason: {
|
|
86
|
-
type: "ClientInternalError",
|
|
87
|
-
cause: "Expected 'success' to be defined"
|
|
88
|
-
}
|
|
89
|
-
});
|
|
156
|
+
var TgBotClientConfig = class extends Context2.Tag("TgBotClientConfig")() {
|
|
90
157
|
};
|
|
91
158
|
|
|
92
159
|
// src/client/guards.ts
|
|
@@ -113,7 +180,8 @@ var makePayload = (body) => {
|
|
|
113
180
|
};
|
|
114
181
|
|
|
115
182
|
// src/client/execute-request/execute.ts
|
|
116
|
-
var execute = (
|
|
183
|
+
var execute = (method, input) => Micro.gen(function* () {
|
|
184
|
+
const config = yield* Micro.service(TgBotClientConfig);
|
|
117
185
|
const httpResponse = yield* Micro.tryPromise({
|
|
118
186
|
try: () => fetch(
|
|
119
187
|
`${config.base_url}/bot${config.bot_token}/${String.snakeToCamel(method)}`,
|
|
@@ -149,160 +217,17 @@ var execute = (config, method, input) => Micro.gen(function* () {
|
|
|
149
217
|
return response.result;
|
|
150
218
|
});
|
|
151
219
|
|
|
152
|
-
// src/client/execute-request/_service.ts
|
|
153
|
-
var ClientExecuteRequestService = class extends Context2.Tag("ClientExecuteRequestService")() {
|
|
154
|
-
};
|
|
155
|
-
var ClientExecuteRequestServiceDefault = Micro2.gen(function* () {
|
|
156
|
-
const config = yield* Micro2.service(TgBotClientConfig);
|
|
157
|
-
return {
|
|
158
|
-
execute: (method, input) => execute(config, method, input)
|
|
159
|
-
};
|
|
160
|
-
});
|
|
161
|
-
|
|
162
|
-
// src/client/file/_service.ts
|
|
163
|
-
var Micro4 = __toESM(require("effect/Micro"));
|
|
164
|
-
var Context3 = __toESM(require("effect/Context"));
|
|
165
|
-
|
|
166
|
-
// src/client/file/get-file.ts
|
|
167
|
-
var Micro3 = __toESM(require("effect/Micro"));
|
|
168
|
-
var getFile = (fileId, config, execute2) => Micro3.gen(function* () {
|
|
169
|
-
const response = yield* execute2.execute("get_file", { file_id: fileId });
|
|
170
|
-
const file_path = response.file_path;
|
|
171
|
-
if (!file_path || file_path.length == 0) {
|
|
172
|
-
return yield* Micro3.fail(
|
|
173
|
-
new TgBotClientError({
|
|
174
|
-
reason: {
|
|
175
|
-
type: "UnableToGetFile",
|
|
176
|
-
cause: "File path not defined"
|
|
177
|
-
}
|
|
178
|
-
})
|
|
179
|
-
);
|
|
180
|
-
}
|
|
181
|
-
const file_name = file_path.replaceAll("/", "-");
|
|
182
|
-
const url = `${config.base_url}/file/bot${config.bot_token}/${file_path}`;
|
|
183
|
-
const fileContent = yield* Micro3.tryPromise({
|
|
184
|
-
try: () => fetch(url).then((_) => _.arrayBuffer()),
|
|
185
|
-
catch: (cause) => new TgBotClientError({
|
|
186
|
-
reason: { type: "UnableToGetFile", cause }
|
|
187
|
-
})
|
|
188
|
-
});
|
|
189
|
-
const file = new File([new Uint8Array(fileContent)], file_name);
|
|
190
|
-
return file;
|
|
191
|
-
});
|
|
192
|
-
|
|
193
|
-
// src/client/file/_service.ts
|
|
194
|
-
var ClientFileService = class extends Context3.Tag("ClientFileService")() {
|
|
195
|
-
};
|
|
196
|
-
var ClientFileServiceDefault = Micro4.gen(function* () {
|
|
197
|
-
const config = yield* Micro4.service(TgBotClientConfig);
|
|
198
|
-
const execute2 = yield* Micro4.service(ClientExecuteRequestService);
|
|
199
|
-
return {
|
|
200
|
-
getFile: (input) => getFile(input.file_id, config, execute2)
|
|
201
|
-
};
|
|
202
|
-
}).pipe(
|
|
203
|
-
Micro4.provideServiceEffect(ClientExecuteRequestService, ClientExecuteRequestServiceDefault)
|
|
204
|
-
);
|
|
205
|
-
|
|
206
|
-
// src/client/_client.ts
|
|
207
|
-
var makeTgBotClient = (input) => {
|
|
208
|
-
const config = makeTgBotClientConfig(input);
|
|
209
|
-
const client = Micro5.gen(function* () {
|
|
210
|
-
const execute2 = yield* Micro5.service(ClientExecuteRequestService);
|
|
211
|
-
const file = yield* Micro5.service(ClientFileService);
|
|
212
|
-
return {
|
|
213
|
-
execute: (method, input2) => execute2.execute(method, input2).pipe(Micro5.runPromise),
|
|
214
|
-
getFile: (input2) => file.getFile(input2).pipe(Micro5.runPromise)
|
|
215
|
-
};
|
|
216
|
-
}).pipe(
|
|
217
|
-
Micro5.provideServiceEffect(ClientExecuteRequestService, ClientExecuteRequestServiceDefault),
|
|
218
|
-
Micro5.provideServiceEffect(ClientFileService, ClientFileServiceDefault),
|
|
219
|
-
Micro5.provideService(TgBotClientConfig, config),
|
|
220
|
-
Micro5.runSync
|
|
221
|
-
);
|
|
222
|
-
return client;
|
|
223
|
-
};
|
|
224
|
-
|
|
225
|
-
// src/bot/run.ts
|
|
226
|
-
var Micro12 = __toESM(require("effect/Micro"));
|
|
227
|
-
|
|
228
|
-
// src/bot/factory/_service.ts
|
|
229
|
-
var Micro11 = __toESM(require("effect/Micro"));
|
|
230
|
-
var Context5 = __toESM(require("effect/Context"));
|
|
231
|
-
|
|
232
|
-
// src/bot/update-poller/_service.ts
|
|
233
|
-
var Micro8 = __toESM(require("effect/Micro"));
|
|
234
|
-
var Context4 = __toESM(require("effect/Context"));
|
|
235
|
-
|
|
236
|
-
// src/bot/update-poller/poll-and-handle.ts
|
|
237
|
-
var Micro7 = __toESM(require("effect/Micro"));
|
|
238
|
-
|
|
239
|
-
// src/bot/update-poller/settings.ts
|
|
240
|
-
var makeSettingsFrom = (input) => {
|
|
241
|
-
let limit = input.batch_size ?? 10;
|
|
242
|
-
let timeout = input.timeout ?? 10;
|
|
243
|
-
let max_empty_responses = input.max_empty_responses;
|
|
244
|
-
let update_types = input.update_types;
|
|
245
|
-
let log_level = input.log_level;
|
|
246
|
-
if (limit < 10 || limit > 100) {
|
|
247
|
-
console.warn("Wrong limit, must be in [10..100], using 10 instead");
|
|
248
|
-
limit = 10;
|
|
249
|
-
}
|
|
250
|
-
if (timeout < 2 || timeout > 10) {
|
|
251
|
-
console.warn("Wrong timeout, must be in [2..10], using 2 instead");
|
|
252
|
-
limit = 10;
|
|
253
|
-
}
|
|
254
|
-
if (max_empty_responses && max_empty_responses < 2) {
|
|
255
|
-
console.warn("Wrong max_empty_responses, must be in [2..infinity], using infinity");
|
|
256
|
-
max_empty_responses = void 0;
|
|
257
|
-
}
|
|
258
|
-
if (max_empty_responses && max_empty_responses < 2) {
|
|
259
|
-
console.warn("Wrong max_empty_responses, must be in [2..infinity], using infinity");
|
|
260
|
-
max_empty_responses = void 0;
|
|
261
|
-
}
|
|
262
|
-
if (!update_types) {
|
|
263
|
-
console.info("Handling only messages, ignoring others");
|
|
264
|
-
update_types = ["message"];
|
|
265
|
-
}
|
|
266
|
-
if (!log_level) {
|
|
267
|
-
log_level = "info";
|
|
268
|
-
}
|
|
269
|
-
return {
|
|
270
|
-
limit,
|
|
271
|
-
timeout,
|
|
272
|
-
max_empty_responses,
|
|
273
|
-
update_types,
|
|
274
|
-
log_level
|
|
275
|
-
};
|
|
276
|
-
};
|
|
277
|
-
|
|
278
220
|
// src/bot/update-poller/fetch-updates.ts
|
|
279
|
-
var
|
|
280
|
-
|
|
281
|
-
// src/bot/message-handler/utils.ts
|
|
282
|
-
var extractUpdate = (input) => {
|
|
283
|
-
for (const [field, value] of Object.entries(input)) {
|
|
284
|
-
if (field == "update_id") {
|
|
285
|
-
continue;
|
|
286
|
-
}
|
|
287
|
-
return {
|
|
288
|
-
type: field,
|
|
289
|
-
...value
|
|
290
|
-
};
|
|
291
|
-
}
|
|
292
|
-
return;
|
|
293
|
-
};
|
|
294
|
-
|
|
295
|
-
// src/bot/update-poller/fetch-updates.ts
|
|
296
|
-
var fetchUpdates = ({ state, settings, execute: execute2, handlers }) => Micro6.gen(function* () {
|
|
221
|
+
var fetchUpdates = ({ state, settings, handlers }) => Micro2.gen(function* () {
|
|
297
222
|
const updateId = state.lastUpdateId;
|
|
298
223
|
if (settings.log_level == "debug") {
|
|
299
224
|
console.debug("getting updates", state);
|
|
300
225
|
}
|
|
301
|
-
const updates = yield*
|
|
226
|
+
const updates = yield* execute("get_updates", {
|
|
302
227
|
...settings,
|
|
303
228
|
...updateId ? { offset: updateId } : void 0
|
|
304
229
|
}).pipe(
|
|
305
|
-
|
|
230
|
+
Micro2.andThen((_) => _.sort((_2) => _2.update_id))
|
|
306
231
|
);
|
|
307
232
|
let lastSuccessId = void 0;
|
|
308
233
|
let hasError = false;
|
|
@@ -336,7 +261,7 @@ var fetchUpdates = ({ state, settings, execute: execute2, handlers }) => Micro6.
|
|
|
336
261
|
}
|
|
337
262
|
const handleResult = handler(update);
|
|
338
263
|
if ("chat" in update && handleResult) {
|
|
339
|
-
const response = yield*
|
|
264
|
+
const response = yield* execute(`send_${handleResult.type}`, {
|
|
340
265
|
...handleResult,
|
|
341
266
|
chat_id: update.chat.id
|
|
342
267
|
});
|
|
@@ -351,7 +276,7 @@ var fetchUpdates = ({ state, settings, execute: execute2, handlers }) => Micro6.
|
|
|
351
276
|
lastSuccessId = updateObject.update_id;
|
|
352
277
|
}
|
|
353
278
|
if (hasError && lastSuccessId) {
|
|
354
|
-
yield*
|
|
279
|
+
yield* execute("get_updates", {
|
|
355
280
|
offset: lastSuccessId,
|
|
356
281
|
limit: 0
|
|
357
282
|
});
|
|
@@ -369,15 +294,14 @@ var pollAndHandle = (input) => {
|
|
|
369
294
|
emptyResponses: 0
|
|
370
295
|
};
|
|
371
296
|
const settings = makeSettingsFrom(input.settings);
|
|
372
|
-
return
|
|
297
|
+
return Micro3.delay(1e3)(
|
|
373
298
|
fetchUpdates({
|
|
374
299
|
state,
|
|
375
300
|
settings,
|
|
376
|
-
execute: input.execute,
|
|
377
301
|
handlers: input.settings
|
|
378
302
|
})
|
|
379
303
|
).pipe(
|
|
380
|
-
|
|
304
|
+
Micro3.repeat({
|
|
381
305
|
while: ({ updates, lastSuccessId, hasError }) => {
|
|
382
306
|
if (hasError) {
|
|
383
307
|
console.info("error in handler, quitting");
|
|
@@ -403,109 +327,165 @@ var pollAndHandle = (input) => {
|
|
|
403
327
|
};
|
|
404
328
|
|
|
405
329
|
// src/bot/update-poller/_service.ts
|
|
406
|
-
var BotUpdatePollerService = class extends
|
|
330
|
+
var BotUpdatePollerService = class extends Context3.Tag("BotUpdatePollerService")() {
|
|
407
331
|
};
|
|
408
|
-
var BotUpdatesPollerServiceDefault =
|
|
332
|
+
var BotUpdatesPollerServiceDefault = Micro4.gen(function* () {
|
|
409
333
|
console.log("Initiating BotUpdatesPollerServiceDefault");
|
|
410
334
|
const state = {
|
|
411
335
|
fiber: void 0
|
|
412
336
|
};
|
|
413
|
-
const
|
|
414
|
-
|
|
415
|
-
|
|
337
|
+
const runBot = Micro4.gen(function* () {
|
|
338
|
+
console.log("run bot");
|
|
339
|
+
const messageHandler = yield* Micro4.service(BotMessageHandler);
|
|
416
340
|
const startFiber = pollAndHandle({
|
|
417
|
-
settings: messageHandler
|
|
418
|
-
execute: client.execute
|
|
341
|
+
settings: messageHandler
|
|
419
342
|
}).pipe(
|
|
420
|
-
|
|
421
|
-
|
|
343
|
+
Micro4.forkDaemon,
|
|
344
|
+
Micro4.tap(
|
|
422
345
|
(fiber) => fiber.addObserver((exit) => {
|
|
423
346
|
console.log("bot's fiber has been closed", exit);
|
|
424
|
-
if (messageHandler.onExit) {
|
|
425
|
-
messageHandler.onExit(exit);
|
|
426
|
-
}
|
|
427
347
|
})
|
|
428
348
|
)
|
|
429
349
|
);
|
|
430
350
|
if (state.fiber) {
|
|
431
351
|
console.log("killing previous bot's fiber");
|
|
432
|
-
yield*
|
|
352
|
+
yield* Micro4.fiberInterrupt(state.fiber);
|
|
433
353
|
}
|
|
434
354
|
state.fiber = yield* startFiber;
|
|
435
|
-
console.log("
|
|
436
|
-
return state.fiber;
|
|
355
|
+
console.log("Fetching bot updates via long polling...");
|
|
437
356
|
});
|
|
438
357
|
return {
|
|
439
|
-
runBot
|
|
358
|
+
runBot,
|
|
359
|
+
getFiber: () => state.fiber
|
|
440
360
|
};
|
|
441
|
-
})
|
|
442
|
-
Micro8.provideServiceEffect(ClientExecuteRequestService, ClientExecuteRequestServiceDefault)
|
|
443
|
-
);
|
|
361
|
+
});
|
|
444
362
|
|
|
445
363
|
// src/bot/factory/client-config.ts
|
|
446
|
-
var
|
|
447
|
-
var makeClientConfigFrom = (input) =>
|
|
364
|
+
var Micro5 = __toESM(require("effect/Micro"));
|
|
365
|
+
var makeClientConfigFrom = (input) => Micro5.gen(function* () {
|
|
448
366
|
if (input.type == "config") {
|
|
449
367
|
return makeTgBotClientConfig(input);
|
|
450
368
|
}
|
|
451
|
-
const config = yield*
|
|
369
|
+
const config = yield* Micro5.tryPromise({
|
|
452
370
|
try: async () => {
|
|
453
371
|
const { readFileSync } = await import("fs");
|
|
454
372
|
return JSON.parse(await readFileSync("config.json", "utf-8"));
|
|
455
373
|
},
|
|
456
374
|
catch: (error) => {
|
|
457
|
-
console.warn(error);
|
|
375
|
+
console.warn("invalid tg bot config", error);
|
|
458
376
|
return "ReadingConfigError";
|
|
459
377
|
}
|
|
460
378
|
});
|
|
461
379
|
if (!isTgBotClientSettingsInput(config)) {
|
|
462
|
-
return yield*
|
|
380
|
+
return yield* Micro5.fail("InvalidConfig");
|
|
463
381
|
}
|
|
464
382
|
return makeTgBotClientConfig(config);
|
|
465
383
|
});
|
|
466
384
|
|
|
467
|
-
// src/bot/factory/make-bot.ts
|
|
468
|
-
var Micro10 = __toESM(require("effect/Micro"));
|
|
469
|
-
var makeBot = (messageHandler) => Micro10.gen(function* () {
|
|
470
|
-
const { runBot } = yield* Micro10.service(BotUpdatePollerService);
|
|
471
|
-
return {
|
|
472
|
-
fiber: yield* runBot(messageHandler),
|
|
473
|
-
runBot
|
|
474
|
-
};
|
|
475
|
-
}).pipe(
|
|
476
|
-
Micro10.tapError((error) => {
|
|
477
|
-
console.error(error);
|
|
478
|
-
return Micro10.void;
|
|
479
|
-
})
|
|
480
|
-
);
|
|
481
|
-
|
|
482
385
|
// src/bot/factory/_service.ts
|
|
483
|
-
var BotFactoryService = class extends
|
|
386
|
+
var BotFactoryService = class extends Context4.Tag("BotFactoryService")() {
|
|
484
387
|
};
|
|
485
388
|
var BotFactoryServiceDefault = {
|
|
486
|
-
|
|
487
|
-
|
|
488
|
-
console.log("client");
|
|
489
|
-
const client = yield* makeClientConfigFrom(input);
|
|
389
|
+
runBot: (input) => Micro6.gen(function* () {
|
|
390
|
+
const client = Context4.make(TgBotClientConfig, yield* makeClientConfigFrom(input));
|
|
490
391
|
const poller = yield* BotUpdatesPollerServiceDefault.pipe(
|
|
491
|
-
|
|
392
|
+
Micro6.provideContext(client)
|
|
393
|
+
);
|
|
394
|
+
yield* poller.runBot.pipe(
|
|
395
|
+
Micro6.provideService(BotMessageHandler, input),
|
|
396
|
+
Micro6.provideContext(client)
|
|
492
397
|
);
|
|
493
|
-
const
|
|
494
|
-
|
|
398
|
+
const reload = (input2) => poller.runBot.pipe(
|
|
399
|
+
Micro6.provideService(BotMessageHandler, input2),
|
|
400
|
+
Micro6.provideContext(client),
|
|
401
|
+
Micro6.runPromise
|
|
495
402
|
);
|
|
496
|
-
const reload = (input2) => bot.runBot(input2).pipe(Micro11.runPromise);
|
|
497
403
|
return {
|
|
498
|
-
reload
|
|
404
|
+
reload,
|
|
405
|
+
fiber: poller.getFiber
|
|
499
406
|
};
|
|
500
407
|
})
|
|
501
408
|
};
|
|
502
409
|
|
|
503
410
|
// src/bot/run.ts
|
|
504
|
-
var
|
|
411
|
+
var Micro7 = __toESM(require("effect/Micro"));
|
|
412
|
+
var runTgChatBot = (input) => BotFactoryServiceDefault.runBot(input).pipe(
|
|
413
|
+
Micro7.provideService(BotMessageHandler, input),
|
|
414
|
+
Micro7.runPromise
|
|
415
|
+
);
|
|
416
|
+
|
|
417
|
+
// src/client/_client.ts
|
|
418
|
+
var Micro10 = __toESM(require("effect/Micro"));
|
|
419
|
+
|
|
420
|
+
// src/client/file/_service.ts
|
|
421
|
+
var Micro9 = __toESM(require("effect/Micro"));
|
|
422
|
+
var Context5 = __toESM(require("effect/Context"));
|
|
423
|
+
|
|
424
|
+
// src/client/file/get-file.ts
|
|
425
|
+
var Micro8 = __toESM(require("effect/Micro"));
|
|
426
|
+
var getFile = (fileId) => Micro8.gen(function* () {
|
|
427
|
+
const response = yield* execute("get_file", { file_id: fileId });
|
|
428
|
+
const config = yield* Micro8.service(TgBotClientConfig);
|
|
429
|
+
const file_path = response.file_path;
|
|
430
|
+
if (!file_path || file_path.length == 0) {
|
|
431
|
+
return yield* Micro8.fail(
|
|
432
|
+
new TgBotClientError({
|
|
433
|
+
reason: {
|
|
434
|
+
type: "UnableToGetFile",
|
|
435
|
+
cause: "File path not defined"
|
|
436
|
+
}
|
|
437
|
+
})
|
|
438
|
+
);
|
|
439
|
+
}
|
|
440
|
+
const file_name = file_path.replaceAll("/", "-");
|
|
441
|
+
const url = `${config.base_url}/file/bot${config.bot_token}/${file_path}`;
|
|
442
|
+
const fileContent = yield* Micro8.tryPromise({
|
|
443
|
+
try: () => fetch(url).then((_) => _.arrayBuffer()),
|
|
444
|
+
catch: (cause) => new TgBotClientError({
|
|
445
|
+
reason: { type: "UnableToGetFile", cause }
|
|
446
|
+
})
|
|
447
|
+
});
|
|
448
|
+
const file = new File([new Uint8Array(fileContent)], file_name);
|
|
449
|
+
return file;
|
|
450
|
+
});
|
|
451
|
+
|
|
452
|
+
// src/client/file/_service.ts
|
|
453
|
+
var ClientFileService = class extends Context5.Tag("ClientFileService")() {
|
|
454
|
+
};
|
|
455
|
+
var ClientFileServiceDefault = Micro9.gen(function* () {
|
|
456
|
+
return {
|
|
457
|
+
getFile: (input) => getFile(input.file_id)
|
|
458
|
+
};
|
|
459
|
+
});
|
|
460
|
+
|
|
461
|
+
// src/client/_client.ts
|
|
462
|
+
var makeTgBotClient = (input) => {
|
|
463
|
+
const config = makeTgBotClientConfig(input);
|
|
464
|
+
const client = Micro10.gen(function* () {
|
|
465
|
+
const file = yield* Micro10.service(ClientFileService);
|
|
466
|
+
return {
|
|
467
|
+
execute: (method, input2) => execute(method, input2).pipe(
|
|
468
|
+
Micro10.provideService(TgBotClientConfig, config),
|
|
469
|
+
Micro10.runPromise
|
|
470
|
+
),
|
|
471
|
+
getFile: (input2) => file.getFile(input2).pipe(
|
|
472
|
+
Micro10.provideService(TgBotClientConfig, config),
|
|
473
|
+
Micro10.runPromise
|
|
474
|
+
)
|
|
475
|
+
};
|
|
476
|
+
}).pipe(
|
|
477
|
+
Micro10.provideServiceEffect(ClientFileService, ClientFileServiceDefault),
|
|
478
|
+
Micro10.provideService(TgBotClientConfig, config),
|
|
479
|
+
Micro10.runSync
|
|
480
|
+
);
|
|
481
|
+
return client;
|
|
482
|
+
};
|
|
505
483
|
// Annotate the CommonJS export names for ESM import in node:
|
|
506
484
|
0 && (module.exports = {
|
|
507
485
|
BotFactoryService,
|
|
508
486
|
BotFactoryServiceDefault,
|
|
487
|
+
BotUpdatePollerService,
|
|
488
|
+
BotUpdatesPollerServiceDefault,
|
|
509
489
|
MESSAGE_EFFECTS,
|
|
510
490
|
defaultBaseUrl,
|
|
511
491
|
isMessageEffect,
|
package/dist/index.mjs
CHANGED
|
@@ -1,8 +1,92 @@
|
|
|
1
|
-
// src/
|
|
2
|
-
import * as
|
|
1
|
+
// src/bot/factory/_service.ts
|
|
2
|
+
import * as Micro6 from "effect/Micro";
|
|
3
|
+
import * as Context4 from "effect/Context";
|
|
3
4
|
|
|
4
|
-
// src/
|
|
5
|
+
// src/bot/message-handler/_service.ts
|
|
5
6
|
import * as Context from "effect/Context";
|
|
7
|
+
var BotMessageHandler = class extends Context.Tag("BotMessageHandler")() {
|
|
8
|
+
};
|
|
9
|
+
|
|
10
|
+
// src/bot/update-poller/_service.ts
|
|
11
|
+
import * as Micro4 from "effect/Micro";
|
|
12
|
+
import * as Context3 from "effect/Context";
|
|
13
|
+
|
|
14
|
+
// src/bot/update-poller/poll-and-handle.ts
|
|
15
|
+
import * as Micro3 from "effect/Micro";
|
|
16
|
+
|
|
17
|
+
// src/bot/update-poller/settings.ts
|
|
18
|
+
var makeSettingsFrom = (input) => {
|
|
19
|
+
let limit = input.batch_size ?? 10;
|
|
20
|
+
let timeout = input.timeout ?? 10;
|
|
21
|
+
let max_empty_responses = input.max_empty_responses;
|
|
22
|
+
let update_types = input.update_types;
|
|
23
|
+
let log_level = input.log_level;
|
|
24
|
+
if (limit < 10 || limit > 100) {
|
|
25
|
+
console.warn("Wrong limit, must be in [10..100], using 10 instead");
|
|
26
|
+
limit = 10;
|
|
27
|
+
}
|
|
28
|
+
if (timeout < 2 || timeout > 10) {
|
|
29
|
+
console.warn("Wrong timeout, must be in [2..10], using 2 instead");
|
|
30
|
+
limit = 10;
|
|
31
|
+
}
|
|
32
|
+
if (max_empty_responses && max_empty_responses < 2) {
|
|
33
|
+
console.warn("Wrong max_empty_responses, must be in [2..infinity], using infinity");
|
|
34
|
+
max_empty_responses = void 0;
|
|
35
|
+
}
|
|
36
|
+
if (max_empty_responses && max_empty_responses < 2) {
|
|
37
|
+
console.warn("Wrong max_empty_responses, must be in [2..infinity], using infinity");
|
|
38
|
+
max_empty_responses = void 0;
|
|
39
|
+
}
|
|
40
|
+
if (!update_types) {
|
|
41
|
+
console.info("Handling only messages, ignoring others");
|
|
42
|
+
update_types = ["message"];
|
|
43
|
+
}
|
|
44
|
+
if (!log_level) {
|
|
45
|
+
log_level = "info";
|
|
46
|
+
}
|
|
47
|
+
return {
|
|
48
|
+
limit,
|
|
49
|
+
timeout,
|
|
50
|
+
max_empty_responses,
|
|
51
|
+
update_types,
|
|
52
|
+
log_level
|
|
53
|
+
};
|
|
54
|
+
};
|
|
55
|
+
|
|
56
|
+
// src/bot/update-poller/fetch-updates.ts
|
|
57
|
+
import * as Micro2 from "effect/Micro";
|
|
58
|
+
|
|
59
|
+
// src/bot/message-handler/utils.ts
|
|
60
|
+
var extractUpdate = (input) => {
|
|
61
|
+
for (const [field, value] of Object.entries(input)) {
|
|
62
|
+
if (field == "update_id") {
|
|
63
|
+
continue;
|
|
64
|
+
}
|
|
65
|
+
return {
|
|
66
|
+
type: field,
|
|
67
|
+
...value
|
|
68
|
+
};
|
|
69
|
+
}
|
|
70
|
+
return;
|
|
71
|
+
};
|
|
72
|
+
|
|
73
|
+
// src/client/execute-request/execute.ts
|
|
74
|
+
import * as Micro from "effect/Micro";
|
|
75
|
+
import * as String from "effect/String";
|
|
76
|
+
|
|
77
|
+
// src/client/errors.ts
|
|
78
|
+
import * as Data from "effect/Data";
|
|
79
|
+
var TgBotClientError = class _TgBotClientError extends Data.TaggedError("TgBotClientError") {
|
|
80
|
+
static missingSuccess = new _TgBotClientError({
|
|
81
|
+
reason: {
|
|
82
|
+
type: "ClientInternalError",
|
|
83
|
+
cause: "Expected 'success' to be defined"
|
|
84
|
+
}
|
|
85
|
+
});
|
|
86
|
+
};
|
|
87
|
+
|
|
88
|
+
// src/client/config.ts
|
|
89
|
+
import * as Context2 from "effect/Context";
|
|
6
90
|
|
|
7
91
|
// src/const.ts
|
|
8
92
|
var defaultBaseUrl = "https://api.telegram.org";
|
|
@@ -24,26 +108,7 @@ var makeTgBotClientConfig = (input) => TgBotClientConfig.of({
|
|
|
24
108
|
...input,
|
|
25
109
|
base_url: input.base_url ?? defaultBaseUrl
|
|
26
110
|
});
|
|
27
|
-
var TgBotClientConfig = class extends
|
|
28
|
-
};
|
|
29
|
-
|
|
30
|
-
// src/client/execute-request/_service.ts
|
|
31
|
-
import * as Micro2 from "effect/Micro";
|
|
32
|
-
import * as Context2 from "effect/Context";
|
|
33
|
-
|
|
34
|
-
// src/client/execute-request/execute.ts
|
|
35
|
-
import * as Micro from "effect/Micro";
|
|
36
|
-
import * as String from "effect/String";
|
|
37
|
-
|
|
38
|
-
// src/client/errors.ts
|
|
39
|
-
import * as Data from "effect/Data";
|
|
40
|
-
var TgBotClientError = class _TgBotClientError extends Data.TaggedError("TgBotClientError") {
|
|
41
|
-
static missingSuccess = new _TgBotClientError({
|
|
42
|
-
reason: {
|
|
43
|
-
type: "ClientInternalError",
|
|
44
|
-
cause: "Expected 'success' to be defined"
|
|
45
|
-
}
|
|
46
|
-
});
|
|
111
|
+
var TgBotClientConfig = class extends Context2.Tag("TgBotClientConfig")() {
|
|
47
112
|
};
|
|
48
113
|
|
|
49
114
|
// src/client/guards.ts
|
|
@@ -70,7 +135,8 @@ var makePayload = (body) => {
|
|
|
70
135
|
};
|
|
71
136
|
|
|
72
137
|
// src/client/execute-request/execute.ts
|
|
73
|
-
var execute = (
|
|
138
|
+
var execute = (method, input) => Micro.gen(function* () {
|
|
139
|
+
const config = yield* Micro.service(TgBotClientConfig);
|
|
74
140
|
const httpResponse = yield* Micro.tryPromise({
|
|
75
141
|
try: () => fetch(
|
|
76
142
|
`${config.base_url}/bot${config.bot_token}/${String.snakeToCamel(method)}`,
|
|
@@ -106,160 +172,17 @@ var execute = (config, method, input) => Micro.gen(function* () {
|
|
|
106
172
|
return response.result;
|
|
107
173
|
});
|
|
108
174
|
|
|
109
|
-
// src/client/execute-request/_service.ts
|
|
110
|
-
var ClientExecuteRequestService = class extends Context2.Tag("ClientExecuteRequestService")() {
|
|
111
|
-
};
|
|
112
|
-
var ClientExecuteRequestServiceDefault = Micro2.gen(function* () {
|
|
113
|
-
const config = yield* Micro2.service(TgBotClientConfig);
|
|
114
|
-
return {
|
|
115
|
-
execute: (method, input) => execute(config, method, input)
|
|
116
|
-
};
|
|
117
|
-
});
|
|
118
|
-
|
|
119
|
-
// src/client/file/_service.ts
|
|
120
|
-
import * as Micro4 from "effect/Micro";
|
|
121
|
-
import * as Context3 from "effect/Context";
|
|
122
|
-
|
|
123
|
-
// src/client/file/get-file.ts
|
|
124
|
-
import * as Micro3 from "effect/Micro";
|
|
125
|
-
var getFile = (fileId, config, execute2) => Micro3.gen(function* () {
|
|
126
|
-
const response = yield* execute2.execute("get_file", { file_id: fileId });
|
|
127
|
-
const file_path = response.file_path;
|
|
128
|
-
if (!file_path || file_path.length == 0) {
|
|
129
|
-
return yield* Micro3.fail(
|
|
130
|
-
new TgBotClientError({
|
|
131
|
-
reason: {
|
|
132
|
-
type: "UnableToGetFile",
|
|
133
|
-
cause: "File path not defined"
|
|
134
|
-
}
|
|
135
|
-
})
|
|
136
|
-
);
|
|
137
|
-
}
|
|
138
|
-
const file_name = file_path.replaceAll("/", "-");
|
|
139
|
-
const url = `${config.base_url}/file/bot${config.bot_token}/${file_path}`;
|
|
140
|
-
const fileContent = yield* Micro3.tryPromise({
|
|
141
|
-
try: () => fetch(url).then((_) => _.arrayBuffer()),
|
|
142
|
-
catch: (cause) => new TgBotClientError({
|
|
143
|
-
reason: { type: "UnableToGetFile", cause }
|
|
144
|
-
})
|
|
145
|
-
});
|
|
146
|
-
const file = new File([new Uint8Array(fileContent)], file_name);
|
|
147
|
-
return file;
|
|
148
|
-
});
|
|
149
|
-
|
|
150
|
-
// src/client/file/_service.ts
|
|
151
|
-
var ClientFileService = class extends Context3.Tag("ClientFileService")() {
|
|
152
|
-
};
|
|
153
|
-
var ClientFileServiceDefault = Micro4.gen(function* () {
|
|
154
|
-
const config = yield* Micro4.service(TgBotClientConfig);
|
|
155
|
-
const execute2 = yield* Micro4.service(ClientExecuteRequestService);
|
|
156
|
-
return {
|
|
157
|
-
getFile: (input) => getFile(input.file_id, config, execute2)
|
|
158
|
-
};
|
|
159
|
-
}).pipe(
|
|
160
|
-
Micro4.provideServiceEffect(ClientExecuteRequestService, ClientExecuteRequestServiceDefault)
|
|
161
|
-
);
|
|
162
|
-
|
|
163
|
-
// src/client/_client.ts
|
|
164
|
-
var makeTgBotClient = (input) => {
|
|
165
|
-
const config = makeTgBotClientConfig(input);
|
|
166
|
-
const client = Micro5.gen(function* () {
|
|
167
|
-
const execute2 = yield* Micro5.service(ClientExecuteRequestService);
|
|
168
|
-
const file = yield* Micro5.service(ClientFileService);
|
|
169
|
-
return {
|
|
170
|
-
execute: (method, input2) => execute2.execute(method, input2).pipe(Micro5.runPromise),
|
|
171
|
-
getFile: (input2) => file.getFile(input2).pipe(Micro5.runPromise)
|
|
172
|
-
};
|
|
173
|
-
}).pipe(
|
|
174
|
-
Micro5.provideServiceEffect(ClientExecuteRequestService, ClientExecuteRequestServiceDefault),
|
|
175
|
-
Micro5.provideServiceEffect(ClientFileService, ClientFileServiceDefault),
|
|
176
|
-
Micro5.provideService(TgBotClientConfig, config),
|
|
177
|
-
Micro5.runSync
|
|
178
|
-
);
|
|
179
|
-
return client;
|
|
180
|
-
};
|
|
181
|
-
|
|
182
|
-
// src/bot/run.ts
|
|
183
|
-
import * as Micro12 from "effect/Micro";
|
|
184
|
-
|
|
185
|
-
// src/bot/factory/_service.ts
|
|
186
|
-
import * as Micro11 from "effect/Micro";
|
|
187
|
-
import * as Context5 from "effect/Context";
|
|
188
|
-
|
|
189
|
-
// src/bot/update-poller/_service.ts
|
|
190
|
-
import * as Micro8 from "effect/Micro";
|
|
191
|
-
import * as Context4 from "effect/Context";
|
|
192
|
-
|
|
193
|
-
// src/bot/update-poller/poll-and-handle.ts
|
|
194
|
-
import * as Micro7 from "effect/Micro";
|
|
195
|
-
|
|
196
|
-
// src/bot/update-poller/settings.ts
|
|
197
|
-
var makeSettingsFrom = (input) => {
|
|
198
|
-
let limit = input.batch_size ?? 10;
|
|
199
|
-
let timeout = input.timeout ?? 10;
|
|
200
|
-
let max_empty_responses = input.max_empty_responses;
|
|
201
|
-
let update_types = input.update_types;
|
|
202
|
-
let log_level = input.log_level;
|
|
203
|
-
if (limit < 10 || limit > 100) {
|
|
204
|
-
console.warn("Wrong limit, must be in [10..100], using 10 instead");
|
|
205
|
-
limit = 10;
|
|
206
|
-
}
|
|
207
|
-
if (timeout < 2 || timeout > 10) {
|
|
208
|
-
console.warn("Wrong timeout, must be in [2..10], using 2 instead");
|
|
209
|
-
limit = 10;
|
|
210
|
-
}
|
|
211
|
-
if (max_empty_responses && max_empty_responses < 2) {
|
|
212
|
-
console.warn("Wrong max_empty_responses, must be in [2..infinity], using infinity");
|
|
213
|
-
max_empty_responses = void 0;
|
|
214
|
-
}
|
|
215
|
-
if (max_empty_responses && max_empty_responses < 2) {
|
|
216
|
-
console.warn("Wrong max_empty_responses, must be in [2..infinity], using infinity");
|
|
217
|
-
max_empty_responses = void 0;
|
|
218
|
-
}
|
|
219
|
-
if (!update_types) {
|
|
220
|
-
console.info("Handling only messages, ignoring others");
|
|
221
|
-
update_types = ["message"];
|
|
222
|
-
}
|
|
223
|
-
if (!log_level) {
|
|
224
|
-
log_level = "info";
|
|
225
|
-
}
|
|
226
|
-
return {
|
|
227
|
-
limit,
|
|
228
|
-
timeout,
|
|
229
|
-
max_empty_responses,
|
|
230
|
-
update_types,
|
|
231
|
-
log_level
|
|
232
|
-
};
|
|
233
|
-
};
|
|
234
|
-
|
|
235
175
|
// src/bot/update-poller/fetch-updates.ts
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
// src/bot/message-handler/utils.ts
|
|
239
|
-
var extractUpdate = (input) => {
|
|
240
|
-
for (const [field, value] of Object.entries(input)) {
|
|
241
|
-
if (field == "update_id") {
|
|
242
|
-
continue;
|
|
243
|
-
}
|
|
244
|
-
return {
|
|
245
|
-
type: field,
|
|
246
|
-
...value
|
|
247
|
-
};
|
|
248
|
-
}
|
|
249
|
-
return;
|
|
250
|
-
};
|
|
251
|
-
|
|
252
|
-
// src/bot/update-poller/fetch-updates.ts
|
|
253
|
-
var fetchUpdates = ({ state, settings, execute: execute2, handlers }) => Micro6.gen(function* () {
|
|
176
|
+
var fetchUpdates = ({ state, settings, handlers }) => Micro2.gen(function* () {
|
|
254
177
|
const updateId = state.lastUpdateId;
|
|
255
178
|
if (settings.log_level == "debug") {
|
|
256
179
|
console.debug("getting updates", state);
|
|
257
180
|
}
|
|
258
|
-
const updates = yield*
|
|
181
|
+
const updates = yield* execute("get_updates", {
|
|
259
182
|
...settings,
|
|
260
183
|
...updateId ? { offset: updateId } : void 0
|
|
261
184
|
}).pipe(
|
|
262
|
-
|
|
185
|
+
Micro2.andThen((_) => _.sort((_2) => _2.update_id))
|
|
263
186
|
);
|
|
264
187
|
let lastSuccessId = void 0;
|
|
265
188
|
let hasError = false;
|
|
@@ -293,7 +216,7 @@ var fetchUpdates = ({ state, settings, execute: execute2, handlers }) => Micro6.
|
|
|
293
216
|
}
|
|
294
217
|
const handleResult = handler(update);
|
|
295
218
|
if ("chat" in update && handleResult) {
|
|
296
|
-
const response = yield*
|
|
219
|
+
const response = yield* execute(`send_${handleResult.type}`, {
|
|
297
220
|
...handleResult,
|
|
298
221
|
chat_id: update.chat.id
|
|
299
222
|
});
|
|
@@ -308,7 +231,7 @@ var fetchUpdates = ({ state, settings, execute: execute2, handlers }) => Micro6.
|
|
|
308
231
|
lastSuccessId = updateObject.update_id;
|
|
309
232
|
}
|
|
310
233
|
if (hasError && lastSuccessId) {
|
|
311
|
-
yield*
|
|
234
|
+
yield* execute("get_updates", {
|
|
312
235
|
offset: lastSuccessId,
|
|
313
236
|
limit: 0
|
|
314
237
|
});
|
|
@@ -326,15 +249,14 @@ var pollAndHandle = (input) => {
|
|
|
326
249
|
emptyResponses: 0
|
|
327
250
|
};
|
|
328
251
|
const settings = makeSettingsFrom(input.settings);
|
|
329
|
-
return
|
|
252
|
+
return Micro3.delay(1e3)(
|
|
330
253
|
fetchUpdates({
|
|
331
254
|
state,
|
|
332
255
|
settings,
|
|
333
|
-
execute: input.execute,
|
|
334
256
|
handlers: input.settings
|
|
335
257
|
})
|
|
336
258
|
).pipe(
|
|
337
|
-
|
|
259
|
+
Micro3.repeat({
|
|
338
260
|
while: ({ updates, lastSuccessId, hasError }) => {
|
|
339
261
|
if (hasError) {
|
|
340
262
|
console.info("error in handler, quitting");
|
|
@@ -360,108 +282,164 @@ var pollAndHandle = (input) => {
|
|
|
360
282
|
};
|
|
361
283
|
|
|
362
284
|
// src/bot/update-poller/_service.ts
|
|
363
|
-
var BotUpdatePollerService = class extends
|
|
285
|
+
var BotUpdatePollerService = class extends Context3.Tag("BotUpdatePollerService")() {
|
|
364
286
|
};
|
|
365
|
-
var BotUpdatesPollerServiceDefault =
|
|
287
|
+
var BotUpdatesPollerServiceDefault = Micro4.gen(function* () {
|
|
366
288
|
console.log("Initiating BotUpdatesPollerServiceDefault");
|
|
367
289
|
const state = {
|
|
368
290
|
fiber: void 0
|
|
369
291
|
};
|
|
370
|
-
const
|
|
371
|
-
|
|
372
|
-
|
|
292
|
+
const runBot = Micro4.gen(function* () {
|
|
293
|
+
console.log("run bot");
|
|
294
|
+
const messageHandler = yield* Micro4.service(BotMessageHandler);
|
|
373
295
|
const startFiber = pollAndHandle({
|
|
374
|
-
settings: messageHandler
|
|
375
|
-
execute: client.execute
|
|
296
|
+
settings: messageHandler
|
|
376
297
|
}).pipe(
|
|
377
|
-
|
|
378
|
-
|
|
298
|
+
Micro4.forkDaemon,
|
|
299
|
+
Micro4.tap(
|
|
379
300
|
(fiber) => fiber.addObserver((exit) => {
|
|
380
301
|
console.log("bot's fiber has been closed", exit);
|
|
381
|
-
if (messageHandler.onExit) {
|
|
382
|
-
messageHandler.onExit(exit);
|
|
383
|
-
}
|
|
384
302
|
})
|
|
385
303
|
)
|
|
386
304
|
);
|
|
387
305
|
if (state.fiber) {
|
|
388
306
|
console.log("killing previous bot's fiber");
|
|
389
|
-
yield*
|
|
307
|
+
yield* Micro4.fiberInterrupt(state.fiber);
|
|
390
308
|
}
|
|
391
309
|
state.fiber = yield* startFiber;
|
|
392
|
-
console.log("
|
|
393
|
-
return state.fiber;
|
|
310
|
+
console.log("Fetching bot updates via long polling...");
|
|
394
311
|
});
|
|
395
312
|
return {
|
|
396
|
-
runBot
|
|
313
|
+
runBot,
|
|
314
|
+
getFiber: () => state.fiber
|
|
397
315
|
};
|
|
398
|
-
})
|
|
399
|
-
Micro8.provideServiceEffect(ClientExecuteRequestService, ClientExecuteRequestServiceDefault)
|
|
400
|
-
);
|
|
316
|
+
});
|
|
401
317
|
|
|
402
318
|
// src/bot/factory/client-config.ts
|
|
403
|
-
import * as
|
|
404
|
-
var makeClientConfigFrom = (input) =>
|
|
319
|
+
import * as Micro5 from "effect/Micro";
|
|
320
|
+
var makeClientConfigFrom = (input) => Micro5.gen(function* () {
|
|
405
321
|
if (input.type == "config") {
|
|
406
322
|
return makeTgBotClientConfig(input);
|
|
407
323
|
}
|
|
408
|
-
const config = yield*
|
|
324
|
+
const config = yield* Micro5.tryPromise({
|
|
409
325
|
try: async () => {
|
|
410
326
|
const { readFileSync } = await import("fs");
|
|
411
327
|
return JSON.parse(await readFileSync("config.json", "utf-8"));
|
|
412
328
|
},
|
|
413
329
|
catch: (error) => {
|
|
414
|
-
console.warn(error);
|
|
330
|
+
console.warn("invalid tg bot config", error);
|
|
415
331
|
return "ReadingConfigError";
|
|
416
332
|
}
|
|
417
333
|
});
|
|
418
334
|
if (!isTgBotClientSettingsInput(config)) {
|
|
419
|
-
return yield*
|
|
335
|
+
return yield* Micro5.fail("InvalidConfig");
|
|
420
336
|
}
|
|
421
337
|
return makeTgBotClientConfig(config);
|
|
422
338
|
});
|
|
423
339
|
|
|
424
|
-
// src/bot/factory/make-bot.ts
|
|
425
|
-
import * as Micro10 from "effect/Micro";
|
|
426
|
-
var makeBot = (messageHandler) => Micro10.gen(function* () {
|
|
427
|
-
const { runBot } = yield* Micro10.service(BotUpdatePollerService);
|
|
428
|
-
return {
|
|
429
|
-
fiber: yield* runBot(messageHandler),
|
|
430
|
-
runBot
|
|
431
|
-
};
|
|
432
|
-
}).pipe(
|
|
433
|
-
Micro10.tapError((error) => {
|
|
434
|
-
console.error(error);
|
|
435
|
-
return Micro10.void;
|
|
436
|
-
})
|
|
437
|
-
);
|
|
438
|
-
|
|
439
340
|
// src/bot/factory/_service.ts
|
|
440
|
-
var BotFactoryService = class extends
|
|
341
|
+
var BotFactoryService = class extends Context4.Tag("BotFactoryService")() {
|
|
441
342
|
};
|
|
442
343
|
var BotFactoryServiceDefault = {
|
|
443
|
-
|
|
444
|
-
|
|
445
|
-
console.log("client");
|
|
446
|
-
const client = yield* makeClientConfigFrom(input);
|
|
344
|
+
runBot: (input) => Micro6.gen(function* () {
|
|
345
|
+
const client = Context4.make(TgBotClientConfig, yield* makeClientConfigFrom(input));
|
|
447
346
|
const poller = yield* BotUpdatesPollerServiceDefault.pipe(
|
|
448
|
-
|
|
347
|
+
Micro6.provideContext(client)
|
|
348
|
+
);
|
|
349
|
+
yield* poller.runBot.pipe(
|
|
350
|
+
Micro6.provideService(BotMessageHandler, input),
|
|
351
|
+
Micro6.provideContext(client)
|
|
449
352
|
);
|
|
450
|
-
const
|
|
451
|
-
|
|
353
|
+
const reload = (input2) => poller.runBot.pipe(
|
|
354
|
+
Micro6.provideService(BotMessageHandler, input2),
|
|
355
|
+
Micro6.provideContext(client),
|
|
356
|
+
Micro6.runPromise
|
|
452
357
|
);
|
|
453
|
-
const reload = (input2) => bot.runBot(input2).pipe(Micro11.runPromise);
|
|
454
358
|
return {
|
|
455
|
-
reload
|
|
359
|
+
reload,
|
|
360
|
+
fiber: poller.getFiber
|
|
456
361
|
};
|
|
457
362
|
})
|
|
458
363
|
};
|
|
459
364
|
|
|
460
365
|
// src/bot/run.ts
|
|
461
|
-
|
|
366
|
+
import * as Micro7 from "effect/Micro";
|
|
367
|
+
var runTgChatBot = (input) => BotFactoryServiceDefault.runBot(input).pipe(
|
|
368
|
+
Micro7.provideService(BotMessageHandler, input),
|
|
369
|
+
Micro7.runPromise
|
|
370
|
+
);
|
|
371
|
+
|
|
372
|
+
// src/client/_client.ts
|
|
373
|
+
import * as Micro10 from "effect/Micro";
|
|
374
|
+
|
|
375
|
+
// src/client/file/_service.ts
|
|
376
|
+
import * as Micro9 from "effect/Micro";
|
|
377
|
+
import * as Context5 from "effect/Context";
|
|
378
|
+
|
|
379
|
+
// src/client/file/get-file.ts
|
|
380
|
+
import * as Micro8 from "effect/Micro";
|
|
381
|
+
var getFile = (fileId) => Micro8.gen(function* () {
|
|
382
|
+
const response = yield* execute("get_file", { file_id: fileId });
|
|
383
|
+
const config = yield* Micro8.service(TgBotClientConfig);
|
|
384
|
+
const file_path = response.file_path;
|
|
385
|
+
if (!file_path || file_path.length == 0) {
|
|
386
|
+
return yield* Micro8.fail(
|
|
387
|
+
new TgBotClientError({
|
|
388
|
+
reason: {
|
|
389
|
+
type: "UnableToGetFile",
|
|
390
|
+
cause: "File path not defined"
|
|
391
|
+
}
|
|
392
|
+
})
|
|
393
|
+
);
|
|
394
|
+
}
|
|
395
|
+
const file_name = file_path.replaceAll("/", "-");
|
|
396
|
+
const url = `${config.base_url}/file/bot${config.bot_token}/${file_path}`;
|
|
397
|
+
const fileContent = yield* Micro8.tryPromise({
|
|
398
|
+
try: () => fetch(url).then((_) => _.arrayBuffer()),
|
|
399
|
+
catch: (cause) => new TgBotClientError({
|
|
400
|
+
reason: { type: "UnableToGetFile", cause }
|
|
401
|
+
})
|
|
402
|
+
});
|
|
403
|
+
const file = new File([new Uint8Array(fileContent)], file_name);
|
|
404
|
+
return file;
|
|
405
|
+
});
|
|
406
|
+
|
|
407
|
+
// src/client/file/_service.ts
|
|
408
|
+
var ClientFileService = class extends Context5.Tag("ClientFileService")() {
|
|
409
|
+
};
|
|
410
|
+
var ClientFileServiceDefault = Micro9.gen(function* () {
|
|
411
|
+
return {
|
|
412
|
+
getFile: (input) => getFile(input.file_id)
|
|
413
|
+
};
|
|
414
|
+
});
|
|
415
|
+
|
|
416
|
+
// src/client/_client.ts
|
|
417
|
+
var makeTgBotClient = (input) => {
|
|
418
|
+
const config = makeTgBotClientConfig(input);
|
|
419
|
+
const client = Micro10.gen(function* () {
|
|
420
|
+
const file = yield* Micro10.service(ClientFileService);
|
|
421
|
+
return {
|
|
422
|
+
execute: (method, input2) => execute(method, input2).pipe(
|
|
423
|
+
Micro10.provideService(TgBotClientConfig, config),
|
|
424
|
+
Micro10.runPromise
|
|
425
|
+
),
|
|
426
|
+
getFile: (input2) => file.getFile(input2).pipe(
|
|
427
|
+
Micro10.provideService(TgBotClientConfig, config),
|
|
428
|
+
Micro10.runPromise
|
|
429
|
+
)
|
|
430
|
+
};
|
|
431
|
+
}).pipe(
|
|
432
|
+
Micro10.provideServiceEffect(ClientFileService, ClientFileServiceDefault),
|
|
433
|
+
Micro10.provideService(TgBotClientConfig, config),
|
|
434
|
+
Micro10.runSync
|
|
435
|
+
);
|
|
436
|
+
return client;
|
|
437
|
+
};
|
|
462
438
|
export {
|
|
463
439
|
BotFactoryService,
|
|
464
440
|
BotFactoryServiceDefault,
|
|
441
|
+
BotUpdatePollerService,
|
|
442
|
+
BotUpdatesPollerServiceDefault,
|
|
465
443
|
MESSAGE_EFFECTS,
|
|
466
444
|
defaultBaseUrl,
|
|
467
445
|
isMessageEffect,
|