@zayne-labs/callapi-plugins 3.1.7 → 4.0.0

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 ADDED
@@ -0,0 +1,139 @@
1
+ # CallApi Plugins
2
+
3
+ <p align="center">
4
+ <a href="https://www.npmjs.com/package/@zayne-labs/callapi-plugins"><img src="https://img.shields.io/npm/v/@zayne-labs/callapi-plugins?style=flat&color=EFBA5F" alt="npm version"></a>
5
+ <a href="https://github.com/zayne-labs/callapi/blob/master/LICENSE"><img src="https://img.shields.io/npm/l/@zayne-labs/callapi-plugins?style=flat&color=EFBA5F" alt="license"></a>
6
+ <a href="https://www.npmjs.com/package/@zayne-labs/callapi-plugins"><img src="https://img.shields.io/npm/dm/@zayne-labs/callapi-plugins?style=flat&color=EFBA5F" alt="downloads per month"></a>
7
+ </p>
8
+
9
+ A collection of official plugins for [CallApi](https://github.com/zayne-labs/callapi) that extend its functionality with common patterns and utilities.
10
+
11
+ ## Installation
12
+
13
+ ```bash
14
+ # npm
15
+ npm install @zayne-labs/callapi-plugins
16
+
17
+ # pnpm
18
+ pnpm add @zayne-labs/callapi-plugins
19
+ ```
20
+
21
+ **Note:** This package requires `@zayne-labs/callapi` as a peer dependency.
22
+
23
+ ## Available Plugins
24
+
25
+ ### Logger Plugin
26
+
27
+ Comprehensive HTTP request/response logging with beautiful console output, built on top of [consola](https://github.com/unjs/consola).
28
+
29
+ **Features:**
30
+
31
+ - Logs all HTTP requests and responses
32
+ - Tracks errors and retries
33
+ - Color-coded console output
34
+ - Customizable logging options
35
+ - Granular control over what gets logged
36
+
37
+ ```js
38
+ import { createFetchClient } from "@zayne-labs/callapi";
39
+ import { loggerPlugin } from "@zayne-labs/callapi-plugins";
40
+
41
+ const api = createFetchClient({
42
+ baseURL: "https://api.example.com",
43
+ plugins: [
44
+ loggerPlugin({
45
+ enabled: process.env.NODE_ENV === "development",
46
+ mode: "verbose", // or "basic"
47
+ }),
48
+ ],
49
+ });
50
+ ```
51
+
52
+ **Configuration Options:**
53
+
54
+ - `enabled` - Toggle logging on/off (boolean or granular object)
55
+ - `mode` - "basic" or "verbose" logging
56
+ - `consoleObject` - Custom console implementation
57
+
58
+ **Granular Control:**
59
+
60
+ ```js
61
+ loggerPlugin({
62
+ enabled: {
63
+ onRequest: true,
64
+ onSuccess: true,
65
+ onError: true, // Fallback for all error types
66
+ onValidationError: false, // Disable specific error types
67
+ },
68
+ });
69
+ ```
70
+
71
+ ## Usage
72
+
73
+ Import and use plugins with your CallApi instance:
74
+
75
+ ```js
76
+ import { createFetchClient } from "@zayne-labs/callapi";
77
+ import { loggerPlugin } from "@zayne-labs/callapi-plugins";
78
+
79
+ // Base configuration
80
+ const api = createFetchClient({
81
+ baseURL: "https://api.example.com",
82
+ plugins: [
83
+ loggerPlugin({
84
+ enabled: process.env.NODE_ENV === "development",
85
+ }),
86
+ ],
87
+ });
88
+
89
+ // Per-request plugins
90
+ const { data } = await api("/users", {
91
+ plugins: [loggerPlugin({ mode: "verbose" })],
92
+ });
93
+ ```
94
+
95
+ ## Plugin Development
96
+
97
+ Want to create your own plugin? Check out the [plugin development guide](https://zayne-labs-callapi.netlify.app/docs/plugins) in the main CallApi documentation.
98
+
99
+ Basic plugin structure:
100
+
101
+ ```js
102
+ import { definePlugin } from "@zayne-labs/callapi";
103
+
104
+ const myPlugin = definePlugin({
105
+ id: "my-plugin",
106
+ name: "My Plugin",
107
+ version: "1.0.0",
108
+
109
+ setup: ({ request, options }) => {
110
+ // Modify request/options before sending
111
+ return { request, options };
112
+ },
113
+
114
+ hooks: {
115
+ onRequest: (ctx) => {
116
+ // Handle request lifecycle events
117
+ },
118
+ onSuccess: (ctx) => {
119
+ // Handle successful responses
120
+ },
121
+ },
122
+ });
123
+ ```
124
+
125
+ ## Documentation
126
+
127
+ For detailed documentation and examples, visit:
128
+
129
+ - [CallApi Documentation](https://zayne-labs-callapi.netlify.app)
130
+ - [Plugin Guide](https://zayne-labs-callapi.netlify.app/docs/plugins)
131
+ - [Logger Plugin Docs](https://zayne-labs-callapi.netlify.app/docs/plugins/utility/logger)
132
+
133
+ ## Contributing
134
+
135
+ Contributions are welcome! Please read our contributing guidelines and submit pull requests to the [main repository](https://github.com/zayne-labs/callapi).
136
+
137
+ ## License
138
+
139
+ MIT © [Ryan Zayne](https://github.com/zayne-labs)
package/dist/esm/index.js CHANGED
@@ -109,8 +109,7 @@ const loggerPlugin = definePlugin((options) => {
109
109
  },
110
110
  onRequestError: (ctx) => {
111
111
  if (!(isBoolean(enabled) ? enabled : enabled.onRequestError === true || enabled.onError)) return;
112
- const message = [`${ctx.request.method} to '${ctx.options.fullURL}' failed!`, `Reason = ${ctx.error.name}: ${ctx.error.message}`].join(lineBreak);
113
- errorLog(message);
112
+ errorLog([`${ctx.request.method} to '${ctx.options.fullURL}' failed!`, `Reason = ${ctx.error.name}: ${ctx.error.message}`].join(lineBreak));
114
113
  },
115
114
  onResponseError: (ctx) => {
116
115
  if (!(isBoolean(enabled) ? enabled : enabled.onResponseError === true || enabled.onError)) return;
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","names":["defaultConsoleObject: ConsoleLikeObject"],"sources":["../../src/logger/constants.ts","../../src/logger/utils.ts","../../src/logger/logger.ts"],"sourcesContent":["export const getStatusTextMap = () => {\n\treturn new Map<number, string>([\n\t\t[100, \"Continue\"],\n\t\t[101, \"Switching Protocols\"],\n\t\t[102, \"Processing\"],\n\t\t[200, \"OK\"],\n\t\t[201, \"Created\"],\n\t\t[202, \"Accepted\"],\n\t\t[203, \"Non-Authoritative Information\"],\n\t\t[204, \"No Content\"],\n\t\t[205, \"Reset Content\"],\n\t\t[206, \"Partial Content\"],\n\t\t[207, \"Multi-Status\"],\n\t\t[208, \"Already Reported\"],\n\t\t[226, \"IM Used\"],\n\t\t[300, \"Multiple Choices\"],\n\t\t[301, \"Moved Permanently\"],\n\t\t[302, \"Found\"],\n\t\t[303, \"See Other\"],\n\t\t[304, \"Not Modified\"],\n\t\t[305, \"Use Proxy\"],\n\t\t[307, \"Temporary Redirect\"],\n\t\t[308, \"Permanent Redirect\"],\n\t\t[400, \"Bad Request\"],\n\t\t[401, \"Unauthorized\"],\n\t\t[402, \"Payment Required\"],\n\t\t[403, \"Forbidden\"],\n\t\t[404, \"Not Found\"],\n\t\t[405, \"Method Not Allowed\"],\n\t\t[406, \"Not Acceptable\"],\n\t\t[407, \"Proxy Authentication Required\"],\n\t\t[408, \"Request Timeout\"],\n\t\t[409, \"Conflict\"],\n\t\t[410, \"Gone\"],\n\t\t[411, \"Length Required\"],\n\t\t[412, \"Precondition Failed\"],\n\t\t[413, \"Payload Too Large\"],\n\t\t[414, \"URI Too Long\"],\n\t\t[415, \"Unsupported Media Type\"],\n\t\t[416, \"Range Not Satisfiable\"],\n\t\t[417, \"Expectation Failed\"],\n\t\t[418, \"I'm a teapot\"],\n\t\t[421, \"Misdirected Request\"],\n\t\t[422, \"Unprocessable Entity\"],\n\t\t[423, \"Locked\"],\n\t\t[424, \"Failed Dependency\"],\n\t\t[425, \"Too Early\"],\n\t\t[426, \"Upgrade Required\"],\n\t\t[428, \"Precondition Required\"],\n\t\t[429, \"Too Many Requests\"],\n\t\t[431, \"Request Header Fields Too Large\"],\n\t\t[451, \"Unavailable For Legal Reasons\"],\n\t\t[500, \"Internal Server Error\"],\n\t\t[501, \"Not Implemented\"],\n\t\t[502, \"Bad Gateway\"],\n\t\t[503, \"Service Unavailable\"],\n\t\t[504, \"Gateway Timeout\"],\n\t\t[505, \"HTTP Version Not Supported\"],\n\t\t[506, \"Variant Also Negotiates\"],\n\t\t[507, \"Insufficient Storage\"],\n\t\t[508, \"Loop Detected\"],\n\t\t[510, \"Not Extended\"],\n\t\t[511, \"Network Authentication Required\"],\n\t]);\n};\n","import { getStatusTextMap } from \"./constants\";\n\nexport const getStatusText = (status: number) => {\n\tconst statusTextMap = getStatusTextMap();\n\n\tconst statusText = statusTextMap.get(status) ?? \"Unknown\";\n\n\treturn statusText;\n};\n","import { definePlugin } from \"@zayne-labs/callapi\";\nimport { type AnyFunction, isBoolean } from \"@zayne-labs/toolkit-type-helpers\";\nimport { createConsola } from \"consola\";\nimport { getStatusText } from \"./utils\";\n\ntype ConsoleLikeObject = {\n\terror: AnyFunction<void>;\n\tfail?: AnyFunction<void>;\n\tlog: AnyFunction<void>;\n\tsuccess?: AnyFunction<void>;\n\twarn?: AnyFunction<void>;\n};\n\nconst consola = createConsola({\n\tformatOptions: {\n\t\tcolors: true,\n\t\tcolumns: 80,\n\t\tcompact: 10,\n\t\tdate: false,\n\t\tfancy: true,\n\t},\n});\n\nexport type LoggerOptions = {\n\t/**\n\t * Custom console object\n\t */\n\tconsoleObject?: ConsoleLikeObject;\n\t/**\n\t * Enable or disable the logger\n\t * @default true\n\t */\n\tenabled?:\n\t\t| boolean\n\t\t| {\n\t\t\t\tonError?: boolean;\n\t\t\t\tonRequest?: boolean;\n\t\t\t\tonRequestError?: boolean;\n\t\t\t\tonResponse?: boolean;\n\t\t\t\tonResponseError?: boolean;\n\t\t\t\tonRetry?: boolean;\n\t\t\t\tonSuccess?: boolean;\n\t\t\t\tonValidationError?: boolean;\n\t\t };\n\t/**\n\t * Enable or disable verbose mode\n\t */\n\tmode?: \"basic\" | \"verbose\";\n};\n\n/* eslint-disable ts-eslint/no-unsafe-argument -- Ignore for now */\nexport const defaultConsoleObject: ConsoleLikeObject = {\n\terror: (...args) => consola.error(\"\", ...args),\n\tfail: (...args) => consola.fail(\"\", ...args),\n\tlog: (...args) => consola.info(\"\", ...args),\n\tsuccess: (...args) => consola.success(\"\", ...args),\n\twarn: (...args) => consola.warn(\"\", ...args),\n};\n/* eslint-enable ts-eslint/no-unsafe-argument -- Ignore for now */\n\nexport const loggerPlugin = definePlugin((options?: LoggerOptions) => {\n\tconst { consoleObject = defaultConsoleObject, enabled = true, mode = \"basic\" } = options ?? {};\n\n\tconst isBasicMode = mode === \"basic\";\n\tconst isVerboseMode = mode === \"verbose\";\n\n\tconst lineBreak = \"\\n\";\n\n\tconst successLog = consoleObject.success ?? consoleObject.log;\n\n\t// eslint-disable-next-line ts-eslint/no-unnecessary-condition -- Ignore\n\tconst errorLog = consoleObject.error ?? consoleObject.fail ?? consoleObject.log;\n\n\treturn {\n\t\t/* eslint-disable perfectionist/sort-objects -- Ignore for now */\n\t\tid: \"logger\",\n\t\tname: \"Logger\",\n\t\tversion: \"1.1.0\",\n\n\t\thooks: {\n\t\t\t/* eslint-enable perfectionist/sort-objects -- Ignore */\n\t\t\tonRequest: (ctx) => {\n\t\t\t\tconst isEnabled = isBoolean(enabled) ? enabled : enabled.onRequest === true;\n\n\t\t\t\tif (!isEnabled) return;\n\n\t\t\t\tconsoleObject.log(`Request being sent to: ${ctx.options.fullURL}`);\n\t\t\t},\n\n\t\t\tonRequestError: (ctx) => {\n\t\t\t\tconst isEnabled =\n\t\t\t\t\tisBoolean(enabled) ? enabled : enabled.onRequestError === true || enabled.onError;\n\n\t\t\t\tif (!isEnabled) return;\n\n\t\t\t\tconst message = [\n\t\t\t\t\t`${ctx.request.method} to '${ctx.options.fullURL}' failed!`,\n\t\t\t\t\t`Reason = ${ctx.error.name}: ${ctx.error.message}`,\n\t\t\t\t].join(lineBreak);\n\n\t\t\t\terrorLog(message);\n\t\t\t},\n\n\t\t\tonResponseError: (ctx) => {\n\t\t\t\tconst isEnabled =\n\t\t\t\t\tisBoolean(enabled) ? enabled : enabled.onResponseError === true || enabled.onError;\n\n\t\t\t\tif (!isEnabled) return;\n\n\t\t\t\tconst message = [\n\t\t\t\t\t`${ctx.request.method} to '${ctx.options.fullURL}' failed with status: ${ctx.response.status} (${ctx.response.statusText || getStatusText(ctx.response.status)})`,\n\t\t\t\t\t`Reason = ${ctx.error.name}: ${ctx.error.message}`,\n\t\t\t\t].join(lineBreak);\n\n\t\t\t\tisBasicMode && errorLog(message);\n\n\t\t\t\tconst verboseMessage = [message, \"ErrorData: \"].join(lineBreak);\n\n\t\t\t\tisVerboseMode && consoleObject.error(verboseMessage, ctx.error.errorData);\n\t\t\t},\n\n\t\t\tonRetry: (ctx) => {\n\t\t\t\tconst isEnabled = isBoolean(enabled) ? enabled : enabled.onRetry === true;\n\n\t\t\t\tif (!isEnabled) return;\n\n\t\t\t\tconst log = consoleObject.warn ?? consoleObject.log;\n\n\t\t\t\tlog(`Retrying request... Attempt: `, ctx.retryAttemptCount);\n\t\t\t},\n\n\t\t\tonSuccess: (ctx) => {\n\t\t\t\tconst isEnabled = isBoolean(enabled) ? enabled : enabled.onSuccess === true;\n\n\t\t\t\tif (!isEnabled) return;\n\n\t\t\t\tsuccessLog(\"Request succeeded!\", ctx.data);\n\t\t\t},\n\n\t\t\tonValidationError: (ctx) => {\n\t\t\t\tconst isEnabled =\n\t\t\t\t\tisBoolean(enabled) ? enabled : enabled.onValidationError === true || enabled.onError;\n\n\t\t\t\tif (!isEnabled) return;\n\n\t\t\t\tconst getMessage = (limit: number | null = null) => {\n\t\t\t\t\tconst errorMessage =\n\t\t\t\t\t\tlimit === null ?\n\t\t\t\t\t\t\tctx.error.message\n\t\t\t\t\t\t:\t`${ctx.error.message.slice(0, limit).trimEnd()}${ctx.error.message.length > limit ? \"...\" : \"\"}`;\n\n\t\t\t\t\treturn [\n\t\t\t\t\t\t`(${ctx.error.issueCause.toUpperCase()}) Validation for request to '${ctx.options.fullURL}' failed!`,\n\t\t\t\t\t\t`${ctx.error.name}: ${errorMessage}`,\n\t\t\t\t\t].join(lineBreak);\n\t\t\t\t};\n\n\t\t\t\tisBasicMode && errorLog(getMessage(150));\n\n\t\t\t\tconst verboseMessage = [getMessage(), \"Issues: \"].join(lineBreak);\n\n\t\t\t\tisVerboseMode && consoleObject.error(verboseMessage, ctx.error.errorData);\n\t\t\t},\n\t\t},\n\t};\n});\n"],"mappings":"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"}
1
+ {"version":3,"file":"index.js","names":["defaultConsoleObject: ConsoleLikeObject"],"sources":["../../src/logger/constants.ts","../../src/logger/utils.ts","../../src/logger/logger.ts"],"sourcesContent":["export const getStatusTextMap = () => {\n\treturn new Map<number, string>([\n\t\t[100, \"Continue\"],\n\t\t[101, \"Switching Protocols\"],\n\t\t[102, \"Processing\"],\n\t\t[200, \"OK\"],\n\t\t[201, \"Created\"],\n\t\t[202, \"Accepted\"],\n\t\t[203, \"Non-Authoritative Information\"],\n\t\t[204, \"No Content\"],\n\t\t[205, \"Reset Content\"],\n\t\t[206, \"Partial Content\"],\n\t\t[207, \"Multi-Status\"],\n\t\t[208, \"Already Reported\"],\n\t\t[226, \"IM Used\"],\n\t\t[300, \"Multiple Choices\"],\n\t\t[301, \"Moved Permanently\"],\n\t\t[302, \"Found\"],\n\t\t[303, \"See Other\"],\n\t\t[304, \"Not Modified\"],\n\t\t[305, \"Use Proxy\"],\n\t\t[307, \"Temporary Redirect\"],\n\t\t[308, \"Permanent Redirect\"],\n\t\t[400, \"Bad Request\"],\n\t\t[401, \"Unauthorized\"],\n\t\t[402, \"Payment Required\"],\n\t\t[403, \"Forbidden\"],\n\t\t[404, \"Not Found\"],\n\t\t[405, \"Method Not Allowed\"],\n\t\t[406, \"Not Acceptable\"],\n\t\t[407, \"Proxy Authentication Required\"],\n\t\t[408, \"Request Timeout\"],\n\t\t[409, \"Conflict\"],\n\t\t[410, \"Gone\"],\n\t\t[411, \"Length Required\"],\n\t\t[412, \"Precondition Failed\"],\n\t\t[413, \"Payload Too Large\"],\n\t\t[414, \"URI Too Long\"],\n\t\t[415, \"Unsupported Media Type\"],\n\t\t[416, \"Range Not Satisfiable\"],\n\t\t[417, \"Expectation Failed\"],\n\t\t[418, \"I'm a teapot\"],\n\t\t[421, \"Misdirected Request\"],\n\t\t[422, \"Unprocessable Entity\"],\n\t\t[423, \"Locked\"],\n\t\t[424, \"Failed Dependency\"],\n\t\t[425, \"Too Early\"],\n\t\t[426, \"Upgrade Required\"],\n\t\t[428, \"Precondition Required\"],\n\t\t[429, \"Too Many Requests\"],\n\t\t[431, \"Request Header Fields Too Large\"],\n\t\t[451, \"Unavailable For Legal Reasons\"],\n\t\t[500, \"Internal Server Error\"],\n\t\t[501, \"Not Implemented\"],\n\t\t[502, \"Bad Gateway\"],\n\t\t[503, \"Service Unavailable\"],\n\t\t[504, \"Gateway Timeout\"],\n\t\t[505, \"HTTP Version Not Supported\"],\n\t\t[506, \"Variant Also Negotiates\"],\n\t\t[507, \"Insufficient Storage\"],\n\t\t[508, \"Loop Detected\"],\n\t\t[510, \"Not Extended\"],\n\t\t[511, \"Network Authentication Required\"],\n\t]);\n};\n","import { getStatusTextMap } from \"./constants\";\n\nexport const getStatusText = (status: number) => {\n\tconst statusTextMap = getStatusTextMap();\n\n\tconst statusText = statusTextMap.get(status) ?? \"Unknown\";\n\n\treturn statusText;\n};\n","import { definePlugin, type CallApiPlugin } from \"@zayne-labs/callapi\";\nimport { type AnyFunction, isBoolean } from \"@zayne-labs/toolkit-type-helpers\";\nimport { createConsola } from \"consola\";\nimport { getStatusText } from \"./utils\";\n\ntype ConsoleLikeObject = {\n\terror: AnyFunction<void>;\n\tfail?: AnyFunction<void>;\n\tlog: AnyFunction<void>;\n\tsuccess?: AnyFunction<void>;\n\twarn?: AnyFunction<void>;\n};\n\nconst consola = createConsola({\n\tformatOptions: {\n\t\tcolors: true,\n\t\tcolumns: 80,\n\t\tcompact: 10,\n\t\tdate: false,\n\t\tfancy: true,\n\t},\n});\n\nexport type LoggerOptions = {\n\t/**\n\t * Custom console object\n\t */\n\tconsoleObject?: ConsoleLikeObject;\n\t/**\n\t * Enable or disable the logger\n\t * @default true\n\t */\n\tenabled?:\n\t\t| boolean\n\t\t| {\n\t\t\t\tonError?: boolean;\n\t\t\t\tonRequest?: boolean;\n\t\t\t\tonRequestError?: boolean;\n\t\t\t\tonResponse?: boolean;\n\t\t\t\tonResponseError?: boolean;\n\t\t\t\tonRetry?: boolean;\n\t\t\t\tonSuccess?: boolean;\n\t\t\t\tonValidationError?: boolean;\n\t\t };\n\t/**\n\t * Enable or disable verbose mode\n\t */\n\tmode?: \"basic\" | \"verbose\";\n};\n\n/* eslint-disable ts-eslint/no-unsafe-argument -- Ignore for now */\nexport const defaultConsoleObject: ConsoleLikeObject = {\n\terror: (...args) => consola.error(\"\", ...args),\n\tfail: (...args) => consola.fail(\"\", ...args),\n\tlog: (...args) => consola.info(\"\", ...args),\n\tsuccess: (...args) => consola.success(\"\", ...args),\n\twarn: (...args) => consola.warn(\"\", ...args),\n};\n/* eslint-enable ts-eslint/no-unsafe-argument -- Ignore for now */\n\nexport const loggerPlugin = definePlugin((options?: LoggerOptions) => {\n\tconst { consoleObject = defaultConsoleObject, enabled = true, mode = \"basic\" } = options ?? {};\n\n\tconst isBasicMode = mode === \"basic\";\n\tconst isVerboseMode = mode === \"verbose\";\n\n\tconst lineBreak = \"\\n\";\n\n\tconst successLog = consoleObject.success ?? consoleObject.log;\n\n\t// eslint-disable-next-line ts-eslint/no-unnecessary-condition -- Ignore\n\tconst errorLog = consoleObject.error ?? consoleObject.fail ?? consoleObject.log;\n\n\treturn {\n\t\t/* eslint-disable perfectionist/sort-objects -- Ignore for now */\n\t\tid: \"logger\",\n\t\tname: \"Logger\",\n\t\tversion: \"1.1.0\",\n\n\t\thooks: {\n\t\t\t/* eslint-enable perfectionist/sort-objects -- Ignore */\n\t\t\tonRequest: (ctx) => {\n\t\t\t\tconst isEnabled = isBoolean(enabled) ? enabled : enabled.onRequest === true;\n\n\t\t\t\tif (!isEnabled) return;\n\n\t\t\t\tconsoleObject.log(`Request being sent to: ${ctx.options.fullURL}`);\n\t\t\t},\n\n\t\t\tonRequestError: (ctx) => {\n\t\t\t\tconst isEnabled =\n\t\t\t\t\tisBoolean(enabled) ? enabled : enabled.onRequestError === true || enabled.onError;\n\n\t\t\t\tif (!isEnabled) return;\n\n\t\t\t\tconst message = [\n\t\t\t\t\t`${ctx.request.method} to '${ctx.options.fullURL}' failed!`,\n\t\t\t\t\t`Reason = ${ctx.error.name}: ${ctx.error.message}`,\n\t\t\t\t].join(lineBreak);\n\n\t\t\t\terrorLog(message);\n\t\t\t},\n\n\t\t\tonResponseError: (ctx) => {\n\t\t\t\tconst isEnabled =\n\t\t\t\t\tisBoolean(enabled) ? enabled : enabled.onResponseError === true || enabled.onError;\n\n\t\t\t\tif (!isEnabled) return;\n\n\t\t\t\tconst message = [\n\t\t\t\t\t`${ctx.request.method} to '${ctx.options.fullURL}' failed with status: ${ctx.response.status} (${ctx.response.statusText || getStatusText(ctx.response.status)})`,\n\t\t\t\t\t`Reason = ${ctx.error.name}: ${ctx.error.message}`,\n\t\t\t\t].join(lineBreak);\n\n\t\t\t\tisBasicMode && errorLog(message);\n\n\t\t\t\tconst verboseMessage = [message, \"ErrorData: \"].join(lineBreak);\n\n\t\t\t\tisVerboseMode && consoleObject.error(verboseMessage, ctx.error.errorData);\n\t\t\t},\n\n\t\t\tonRetry: (ctx) => {\n\t\t\t\tconst isEnabled = isBoolean(enabled) ? enabled : enabled.onRetry === true;\n\n\t\t\t\tif (!isEnabled) return;\n\n\t\t\t\tconst log = consoleObject.warn ?? consoleObject.log;\n\n\t\t\t\tlog(`Retrying request... Attempt: `, ctx.retryAttemptCount);\n\t\t\t},\n\n\t\t\tonSuccess: (ctx) => {\n\t\t\t\tconst isEnabled = isBoolean(enabled) ? enabled : enabled.onSuccess === true;\n\n\t\t\t\tif (!isEnabled) return;\n\n\t\t\t\tsuccessLog(\"Request succeeded!\", ctx.data);\n\t\t\t},\n\n\t\t\tonValidationError: (ctx) => {\n\t\t\t\tconst isEnabled =\n\t\t\t\t\tisBoolean(enabled) ? enabled : enabled.onValidationError === true || enabled.onError;\n\n\t\t\t\tif (!isEnabled) return;\n\n\t\t\t\tconst getMessage = (limit: number | null = null) => {\n\t\t\t\t\tconst errorMessage =\n\t\t\t\t\t\tlimit === null ?\n\t\t\t\t\t\t\tctx.error.message\n\t\t\t\t\t\t:\t`${ctx.error.message.slice(0, limit).trimEnd()}${ctx.error.message.length > limit ? \"...\" : \"\"}`;\n\n\t\t\t\t\treturn [\n\t\t\t\t\t\t`(${ctx.error.issueCause.toUpperCase()}) Validation for request to '${ctx.options.fullURL}' failed!`,\n\t\t\t\t\t\t`${ctx.error.name}: ${errorMessage}`,\n\t\t\t\t\t].join(lineBreak);\n\t\t\t\t};\n\n\t\t\t\tisBasicMode && errorLog(getMessage(150));\n\n\t\t\t\tconst verboseMessage = [getMessage(), \"Issues: \"].join(lineBreak);\n\n\t\t\t\tisVerboseMode && consoleObject.error(verboseMessage, ctx.error.errorData);\n\t\t\t},\n\t\t},\n\t} satisfies CallApiPlugin;\n});\n"],"mappings":"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"}
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@zayne-labs/callapi-plugins",
3
3
  "type": "module",
4
- "version": "3.1.7",
4
+ "version": "4.0.0",
5
5
  "description": "A collection of plugins for callapi",
6
6
  "author": "Ryan Zayne",
7
7
  "license": "MIT",
@@ -19,26 +19,26 @@
19
19
  "node": ">=v18.17.0"
20
20
  },
21
21
  "peerDependencies": {
22
- "@zayne-labs/toolkit-type-helpers": ">=0.9.35",
23
- "consola": "^3.4.2",
24
- "@zayne-labs/callapi": "1.10.5"
22
+ "@zayne-labs/toolkit-type-helpers": ">=0.11.17",
23
+ "consola": "3.x.x",
24
+ "@zayne-labs/callapi": "1.11.0"
25
25
  },
26
26
  "devDependencies": {
27
27
  "@arethetypeswrong/cli": "0.18.2",
28
28
  "@size-limit/esbuild-why": "11.2.0",
29
29
  "@size-limit/preset-small-lib": "11.2.0",
30
30
  "@total-typescript/ts-reset": "0.6.1",
31
- "@zayne-labs/toolkit-type-helpers": "^0.11.12",
32
- "@zayne-labs/tsconfig": "0.9.17",
31
+ "@zayne-labs/toolkit-type-helpers": "^0.12.3",
32
+ "@zayne-labs/tsconfig": "0.10.6",
33
33
  "concurrently": "^9.2.1",
34
34
  "consola": "3.4.2",
35
- "cross-env": "^10.0.0",
35
+ "cross-env": "^10.1.0",
36
36
  "publint": "^0.3.13",
37
37
  "size-limit": "11.2.0",
38
- "tsdown": "^0.15.4",
39
- "typescript": "5.9.2",
38
+ "tsdown": "^0.15.6",
39
+ "typescript": "5.9.3",
40
40
  "vitest": "^3.2.4",
41
- "@zayne-labs/callapi": "1.10.5"
41
+ "@zayne-labs/callapi": "1.11.0"
42
42
  },
43
43
  "publishConfig": {
44
44
  "access": "public",