slack-logs 3.0.2 → 3.0.4
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/README.md +147 -8
- package/dist/index.d.ts +8 -25
- package/dist/index.js +1 -1
- package/dist/shared.d.ts +40 -0
- package/dist/slack-bot.d.ts +15 -0
- package/dist/webhook.d.ts +12 -0
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -26,6 +26,16 @@ npm install slack-logs
|
|
|
26
26
|
yarn add slack-logs
|
|
27
27
|
```
|
|
28
28
|
|
|
29
|
+
### Demo
|
|
30
|
+
|
|
31
|
+
[StackBlitz Demo](https://stackblitz.com/edit/stackblitz-starters-minuqbqu?file=index.js)
|
|
32
|
+
|
|
33
|
+
<!--  -->
|
|
34
|
+
|
|
35
|
+
### Try payload experiments here:
|
|
36
|
+
|
|
37
|
+
[Slack Block Kit Builder](https://app.slack.com/block-kit-builder/T9D4GM7L0)
|
|
38
|
+
|
|
29
39
|
### Configuration:
|
|
30
40
|
|
|
31
41
|
Before you start, ensure you have created an Incoming Webhook in Slack and have the webhook URL ready. For more information on setting up Incoming Webhooks in Slack, visit [Slack's API documentation.](https://api.slack.com/messaging/webhooks)
|
|
@@ -208,12 +218,6 @@ Contributions are welcome! If you have a feature request, bug report, or a pull
|
|
|
208
218
|
|
|
209
219
|
This package is licensed under the MIT License - see the LICENSE file for details.
|
|
210
220
|
|
|
211
|
-
### Demo
|
|
212
|
-
|
|
213
|
-
[StackBlitz Demo](https://stackblitz.com/edit/stackblitz-starters-minuqbqu?file=index.js)
|
|
214
|
-
|
|
215
|
-
<!--  -->
|
|
216
|
-
|
|
217
221
|
### Raw body
|
|
218
222
|
|
|
219
223
|
Use `slack.rawBody(...)` when you want to send a custom Slack payload as-is.
|
|
@@ -264,6 +268,141 @@ slack.rawBody(payload);
|
|
|
264
268
|
|
|
265
269
|
If payload is invalid or sending fails, it logs a console error.
|
|
266
270
|
|
|
267
|
-
|
|
271
|
+
---
|
|
268
272
|
|
|
269
|
-
|
|
273
|
+
## Slack Bot
|
|
274
|
+
|
|
275
|
+
Use `slackbot` when you want the same logging helpers with bot-token based multi-channel support.
|
|
276
|
+
|
|
277
|
+
### Configuration
|
|
278
|
+
|
|
279
|
+
```
|
|
280
|
+
import { slackbot, slackBotConfig } from "slack-logs";
|
|
281
|
+
or
|
|
282
|
+
const { slackbot, slackBotConfig } = require("slack-logs");
|
|
283
|
+
|
|
284
|
+
slackBotConfig({
|
|
285
|
+
botToken: "xoxb-XXXXXXXXXX-XXXXXXXXXX-XXXXXXXXXXXXXXXXXXXXXXXX",
|
|
286
|
+
defaultChannelId: "C0123456789",
|
|
287
|
+
enableAlerts: true,
|
|
288
|
+
});
|
|
289
|
+
```
|
|
290
|
+
|
|
291
|
+
`slackBotConfig(...)` rules:
|
|
292
|
+
|
|
293
|
+
- `botToken` and `enableAlerts` are required
|
|
294
|
+
- `defaultChannelId` is optional if you pass `channelId` in method calls
|
|
295
|
+
- if `defaultChannelId` is not set in config, package falls back to `SLACK_BOT_DEFAULT_CHANNEL_ID`
|
|
296
|
+
|
|
297
|
+
### Environment variables
|
|
298
|
+
|
|
299
|
+
Use env values only when `slackBotConfig(...)` is not called.
|
|
300
|
+
|
|
301
|
+
`.env` 🚨
|
|
302
|
+
|
|
303
|
+
```
|
|
304
|
+
...
|
|
305
|
+
SLACK_BOT_TOKEN="xoxb-XXXXXXXXXX-XXXXXXXXXX-XXXXXXXXXXXXXXXXXXXXXXXX"
|
|
306
|
+
SLACK_BOT_DEFAULT_CHANNEL_ID="C0123456789"
|
|
307
|
+
|
|
308
|
+
# Optional field.
|
|
309
|
+
# If not defined, logs are sent by default.
|
|
310
|
+
# true / True / TRUE sends logs.
|
|
311
|
+
# false / False / FALSE skips logs.
|
|
312
|
+
ENABLE_SLACK_BOT_LOGS=true
|
|
313
|
+
...
|
|
314
|
+
```
|
|
315
|
+
|
|
316
|
+
### Methods
|
|
317
|
+
|
|
318
|
+
```
|
|
319
|
+
slackbot.log(label, data, channelId?);
|
|
320
|
+
slackbot.logBlockMessage(label, payload, errorType?, channelId?);
|
|
321
|
+
slackbot.rawBody(payload, channelId?);
|
|
322
|
+
```
|
|
323
|
+
|
|
324
|
+
### `slackbot.log(...)`
|
|
325
|
+
|
|
326
|
+
`slackbot.log(...)` uses the same payload format as `slack.log(...)`, so the output style is the same.
|
|
327
|
+
|
|
328
|
+
```
|
|
329
|
+
import { slackbot } from "slack-logs";
|
|
330
|
+
|
|
331
|
+
slackbot.log("Data Log with bold", "Here is *BOLD* message", "C0123456789");
|
|
332
|
+
slackbot.log("Highlight Log", "`Message`", "C0123456789");
|
|
333
|
+
slackbot.log("Emoji :rocket: Log", "Yeah :female-technologist::skin-tone-2:");
|
|
334
|
+
slackbot.log("Object Log", {id:"123", value:"Lorem Impulse"});
|
|
335
|
+
```
|
|
336
|
+
|
|
337
|
+

|
|
338
|
+
|
|
339
|
+
### `slackbot.logBlockMessage(...)`
|
|
340
|
+
|
|
341
|
+
`slackbot.logBlockMessage(...)` uses the same payload format as `slack.logBlockMessage(...)`, so the same output examples apply.
|
|
342
|
+
|
|
343
|
+
```
|
|
344
|
+
import { LogLevel, slackbot } from "slack-logs";
|
|
345
|
+
|
|
346
|
+
const payload = [
|
|
347
|
+
{ title: "Title 1", value: "1234" },
|
|
348
|
+
{ title: "Title 2", value: 123 },
|
|
349
|
+
{ title: "Title 3", value: { id: 12 } },
|
|
350
|
+
{ title: "Title 4", value: [{ id: 12 }] },
|
|
351
|
+
];
|
|
352
|
+
|
|
353
|
+
slackbot.logBlockMessage("Custom Logs!", payload, LogLevel.DEFAULT, "C0123456789");
|
|
354
|
+
slackbot.logBlockMessage("Some Information Logs!", payload, LogLevel.INFO);
|
|
355
|
+
slackbot.logBlockMessage("Critical Alert!", payload, LogLevel.ERROR);
|
|
356
|
+
```
|
|
357
|
+
|
|
358
|
+

|
|
359
|
+
|
|
360
|
+
### `slackbot.rawBody(...)`
|
|
361
|
+
|
|
362
|
+
Use `slackbot.rawBody(...)` when you want to send a custom Slack payload with an optional `channelId`.
|
|
363
|
+
|
|
364
|
+
```
|
|
365
|
+
import { slackbot } from "slack-logs";
|
|
366
|
+
|
|
367
|
+
const payload = {
|
|
368
|
+
blocks: [
|
|
369
|
+
{
|
|
370
|
+
type: "section",
|
|
371
|
+
text: {
|
|
372
|
+
type: "mrkdwn",
|
|
373
|
+
text: "Hello from custom payload",
|
|
374
|
+
},
|
|
375
|
+
},
|
|
376
|
+
{
|
|
377
|
+
type: "divider",
|
|
378
|
+
},
|
|
379
|
+
{
|
|
380
|
+
type: "actions",
|
|
381
|
+
elements: [
|
|
382
|
+
{
|
|
383
|
+
type: "button",
|
|
384
|
+
text: {
|
|
385
|
+
type: "plain_text",
|
|
386
|
+
text: "Open",
|
|
387
|
+
emoji: true,
|
|
388
|
+
},
|
|
389
|
+
value: "click_me_123",
|
|
390
|
+
url: "https://google.com",
|
|
391
|
+
},
|
|
392
|
+
],
|
|
393
|
+
},
|
|
394
|
+
],
|
|
395
|
+
};
|
|
396
|
+
|
|
397
|
+
slackbot.rawBody(payload, "C0123456789");
|
|
398
|
+
```
|
|
399
|
+
|
|
400
|
+
`slackbot.rawBody(...)` expects a plain object payload like:
|
|
401
|
+
|
|
402
|
+
```
|
|
403
|
+
{
|
|
404
|
+
"blocks": [...]
|
|
405
|
+
}
|
|
406
|
+
```
|
|
407
|
+
|
|
408
|
+
If payload is invalid or sending fails, it logs a console error.
|
package/dist/index.d.ts
CHANGED
|
@@ -1,30 +1,13 @@
|
|
|
1
|
+
import type { BlocksInterface, LogLevel } from "./shared";
|
|
1
2
|
interface Slack {
|
|
2
3
|
log(label: string, data: any): Promise<null | undefined>;
|
|
3
|
-
logBlockMessage(label: string, objectData: BlocksInterface[],
|
|
4
|
+
logBlockMessage(label: string, objectData: BlocksInterface[], errorType?: LogLevel): Promise<null | undefined>;
|
|
4
5
|
rawBody(payload: Record<string, any>): Promise<null | undefined>;
|
|
5
6
|
}
|
|
6
|
-
export
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
}
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
value: any;
|
|
13
|
-
}
|
|
14
|
-
export declare enum LogLevel {
|
|
15
|
-
DEFAULT = "DEFAULT",
|
|
16
|
-
SUCCESS = "SUCCESS",
|
|
17
|
-
INFO = "INFO",
|
|
18
|
-
WARN = "WARN",
|
|
19
|
-
ERROR = "ERROR"
|
|
20
|
-
}
|
|
21
|
-
export declare enum LogColor {
|
|
22
|
-
DEFAULT = "#B4B4B8",
|
|
23
|
-
SUCCESS = "#65B741",
|
|
24
|
-
INFO = "#40A2D8",
|
|
25
|
-
WARN = "#E3651D",
|
|
26
|
-
ERROR = "#FF0000"
|
|
27
|
-
}
|
|
28
|
-
export declare function slackLogConfig(config: SlackLogConfigOptions): void;
|
|
7
|
+
export type { SlackBotConfigOptions } from "./slack-bot";
|
|
8
|
+
export { slackBotConfig, slackbot } from "./slack-bot";
|
|
9
|
+
export type { BlocksInterface } from "./shared";
|
|
10
|
+
export { LogColor, LogLevel } from "./shared";
|
|
11
|
+
export type { SlackLogConfigOptions } from "./webhook";
|
|
12
|
+
export { slackLogConfig } from "./webhook";
|
|
29
13
|
export declare const slack: Slack;
|
|
30
|
-
export {};
|
package/dist/index.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
"use strict";function e(e){return e&&"object"==typeof e&&"default"in e?e:{default:e}}Object.defineProperty(exports,"__esModule",{value:!0});var o,t,
|
|
1
|
+
"use strict";function e(e){return e&&"object"==typeof e&&"default"in e?e:{default:e}}Object.defineProperty(exports,"__esModule",{value:!0});var o,t,n=e(require("axios"));exports.LogLevel=void 0,(o=exports.LogLevel||(exports.LogLevel={})).DEFAULT="DEFAULT",o.SUCCESS="SUCCESS",o.INFO="INFO",o.WARN="WARN",o.ERROR="ERROR",exports.LogColor=void 0,(t=exports.LogColor||(exports.LogColor={})).DEFAULT="#B4B4B8",t.SUCCESS="#65B741",t.INFO="#40A2D8",t.WARN="#E3651D",t.ERROR="#FF0000";const r={};function s(){const e=l();if(!e)return!1;return!!/^https:\/\/hooks\.slack\.com\/services\/[A-Za-z0-9]+\/[A-Za-z0-9]+\/[A-Za-z0-9]+$/.test(e)||(console.error(`🚨 Slack webhook URL does not look in correct format. Current value is "${e}", expected format is "https://hooks.slack.com/services/T00000000/B00000000/XXXXXXXXXXXXXXXXXXXXXXXX". 🚨`),!1)}function l(){return r.webhookUrl??process.env.SLACK_WEBHOOK_URL}async function a(e){if(!function(){if("boolean"==typeof r.enableAlerts)return r.enableAlerts;const e=(process?.env?.ENABLE_SLACK_LOGS??"").toString().trim();return!e||"true"===e.toLowerCase()||(e.toLowerCase(),!1)}())return null;const o=l();await n.default.post(o,JSON.stringify(e),{headers:{"Content-Type":"application/json"}}).catch((e=>{const o=e?.response?.data?.error||e?.response?.statusText||e?.message||"Unknown error";console.error(`🚨 Error sending log message to Slack: ${o}`)}))}const c={};const i={log:async(e,o,t)=>(await p(function(e,o){return{text:`*${e}:* ${JSON.stringify(o)}`}}(e,o),t),null),logBlockMessage:async(e,o,t=exports.LogLevel.DEFAULT,n)=>(await p(function(e,o,t=exports.LogLevel.DEFAULT){const n=[];return o?.length&&o.forEach((e=>{n.push({type:"section",text:{type:"mrkdwn",text:`*${e.title}:* ${JSON.stringify(e.value)}`}})})),{text:e,blocks:[{type:"divider"},{type:"header",text:{type:"plain_text",text:e,emoji:!0}},{type:"divider"}],attachments:[{color:exports.LogColor[t],blocks:n}]}}(e,o,t),n),null),rawBody:async(e,o)=>function(e){return!!e&&"object"==typeof e&&!Array.isArray(e)}(e)?(await p(e,o),null):(console.error('🚨 Invalid Slack payload for slackbot.rawBody(...). Expected an object like { "blocks": [...] } 🚨'),null)};function u(e,o){const t=("string"==typeof e.channel?e.channel:void 0)??o??c.defaultChannelId??process.env.SLACK_BOT_DEFAULT_CHANNEL_ID;return function(e){return!!e&&/^[CGD][A-Z0-9]+$/.test(e)}(t)?t:(console.error("🚨 Invalid Slack channel ID. Kindly pass a valid channelId or set 'defaultChannelId' in slackBotConfig(...) / 'SLACK_BOT_DEFAULT_CHANNEL_ID' in your .env file! 🚨"),null)}async function p(e,o){if(!function(){if("boolean"==typeof c.enableAlerts)return c.enableAlerts;const e=(process?.env?.ENABLE_SLACK_BOT_LOGS??process?.env?.ENABLE_SLACK_LOGS??"").toString().trim();return!e||"true"===e.toLowerCase()||(e.toLowerCase(),!1)}())return null;const t=c.botToken??process.env.SLACK_BOT_TOKEN;if(!function(e){return!!e&&/^xoxb-[A-Za-z0-9-]+$/.test(e)}(t))return console.error("🚨 Invalid Slack bot token. Kindly check slackBotConfig(...) or 'SLACK_BOT_TOKEN' in your .env file! 🚨"),null;const r=u(e,o);return r?await n.default.post("https://slack.com/api/chat.postMessage",{...e,channel:r},{headers:{Authorization:`Bearer ${t}`,"Content-Type":"application/json; charset=utf-8"}}).then((e=>{e?.data?.ok||console.error(`🚨 Error sending bot message to Slack: ${e?.data?.error||"Unknown error"}`)})).catch((e=>{const o=e?.response?.data?.error||e?.response?.statusText||e?.message||"Unknown error";console.error(`🚨 Error sending bot message to Slack: ${o}`)})):null}const d={...{async log(e,o){const t=JSON.stringify(o);if(!s())return console.error("🚨 Invalid Slack webhook URL. Kindly check slackLogConfig(...) or 'SLACK_WEBHOOK_URL' in your .env file! 🚨"),null;const n={text:`*${e}:* ${t}`};await a(n)},async logBlockMessage(e,o,t=exports.LogLevel.DEFAULT){if(!s())return console.error("🚨 Invalid Slack webhook URL. Kindly check slackLogConfig(...) or 'SLACK_WEBHOOK_URL' in your .env file! 🚨"),null;const n=exports.LogColor[t],r=[],l=[],c=[];r.push({type:"divider"}),r.push({type:"header",text:{type:"plain_text",text:e,emoji:!0}}),r.push({type:"divider"}),o?.length&&o.forEach((e=>{const o=JSON.stringify(e.value);c.push({type:"section",text:{type:"mrkdwn",text:`*${e.title}:* ${o}`}})})),l.push({color:n,blocks:c});const i={text:e,blocks:r,attachments:l};await a(i)},rawBody:async e=>s()?function(e){return!!e&&"object"==typeof e&&!Array.isArray(e)}(e)?void await a(e):(console.error('🚨 Invalid Slack payload for rawBody(...). Expected an object like { "blocks": [...] } 🚨'),null):(console.error("🚨 Invalid Slack webhook URL. Kindly check slackLogConfig(...) or 'SLACK_WEBHOOK_URL' in your .env file! 🚨"),null)}};exports.slack=d,exports.slackBotConfig=function(e){c.botToken=e.botToken,c.defaultChannelId=e.defaultChannelId,c.enableAlerts=e.enableAlerts},exports.slackLogConfig=function(e){r.webhookUrl=e.webhookUrl,r.enableAlerts=e.enableAlerts},exports.slackbot=i;
|
package/dist/shared.d.ts
ADDED
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
export interface BlocksInterface {
|
|
2
|
+
title: string;
|
|
3
|
+
value: any;
|
|
4
|
+
}
|
|
5
|
+
export declare enum LogLevel {
|
|
6
|
+
DEFAULT = "DEFAULT",
|
|
7
|
+
SUCCESS = "SUCCESS",
|
|
8
|
+
INFO = "INFO",
|
|
9
|
+
WARN = "WARN",
|
|
10
|
+
ERROR = "ERROR"
|
|
11
|
+
}
|
|
12
|
+
export declare enum LogColor {
|
|
13
|
+
DEFAULT = "#B4B4B8",
|
|
14
|
+
SUCCESS = "#65B741",
|
|
15
|
+
INFO = "#40A2D8",
|
|
16
|
+
WARN = "#E3651D",
|
|
17
|
+
ERROR = "#FF0000"
|
|
18
|
+
}
|
|
19
|
+
export declare function buildLogPayload(label: string, data: any): {
|
|
20
|
+
text: string;
|
|
21
|
+
};
|
|
22
|
+
export declare function buildLogBlockPayload(label: string, objectData: BlocksInterface[], errorType?: LogLevel): {
|
|
23
|
+
text: string;
|
|
24
|
+
blocks: ({
|
|
25
|
+
type: string;
|
|
26
|
+
text?: undefined;
|
|
27
|
+
} | {
|
|
28
|
+
type: string;
|
|
29
|
+
text: {
|
|
30
|
+
type: string;
|
|
31
|
+
text: string;
|
|
32
|
+
emoji: boolean;
|
|
33
|
+
};
|
|
34
|
+
})[];
|
|
35
|
+
attachments: {
|
|
36
|
+
color: LogColor;
|
|
37
|
+
blocks: object[];
|
|
38
|
+
}[];
|
|
39
|
+
};
|
|
40
|
+
export declare function isValidRawPayload(payload: Record<string, any>): boolean;
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import type { BlocksInterface } from "./shared";
|
|
2
|
+
import { LogLevel } from "./shared";
|
|
3
|
+
export interface SlackBotConfigOptions {
|
|
4
|
+
botToken: string;
|
|
5
|
+
defaultChannelId?: string;
|
|
6
|
+
enableAlerts: boolean;
|
|
7
|
+
}
|
|
8
|
+
interface SlackBot {
|
|
9
|
+
log(label: string, data: any, channelId?: string): Promise<null | undefined>;
|
|
10
|
+
logBlockMessage(label: string, objectData: BlocksInterface[], errorType?: LogLevel, channelId?: string): Promise<null | undefined>;
|
|
11
|
+
rawBody(payload: Record<string, any>, channelId?: string): Promise<null | undefined>;
|
|
12
|
+
}
|
|
13
|
+
export declare function slackBotConfig(config: SlackBotConfigOptions): void;
|
|
14
|
+
export declare const slackbot: SlackBot;
|
|
15
|
+
export {};
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import { LogLevel } from "./shared";
|
|
2
|
+
import type { BlocksInterface } from "./shared";
|
|
3
|
+
export interface SlackLogConfigOptions {
|
|
4
|
+
webhookUrl: string;
|
|
5
|
+
enableAlerts: boolean;
|
|
6
|
+
}
|
|
7
|
+
export declare function slackLogConfig(config: SlackLogConfigOptions): void;
|
|
8
|
+
export declare const slackWebhook: {
|
|
9
|
+
log(label: string, data: any): Promise<null | undefined>;
|
|
10
|
+
logBlockMessage(label: string, objectData: BlocksInterface[], errorType?: LogLevel): Promise<null | undefined>;
|
|
11
|
+
rawBody(payload: Record<string, any>): Promise<null | undefined>;
|
|
12
|
+
};
|