@anjianshi/utils 3.0.7 → 3.0.8

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@anjianshi/utils",
3
- "version": "3.0.7",
3
+ "version": "3.0.8",
4
4
  "description": "Common JavaScript Utils",
5
5
  "homepage": "https://github.com/anjianshi/js-packages/utils",
6
6
  "bugs": {
@@ -31,12 +31,12 @@
31
31
  "redis": "^5.5.6",
32
32
  "typescript": "^5.8.3",
33
33
  "vconsole": "^3.15.1",
34
- "@anjianshi/presets-prettier": "3.0.5",
34
+ "@anjianshi/presets-eslint-base": "6.0.0",
35
35
  "@anjianshi/presets-eslint-node": "6.0.0",
36
36
  "@anjianshi/presets-eslint-react": "6.0.0",
37
+ "@anjianshi/presets-eslint-typescript": "6.0.0",
37
38
  "@anjianshi/presets-typescript": "3.2.5",
38
- "@anjianshi/presets-eslint-base": "6.0.0",
39
- "@anjianshi/presets-eslint-typescript": "6.0.0"
39
+ "@anjianshi/presets-prettier": "3.0.5"
40
40
  },
41
41
  "peerDependencies": {
42
42
  "@emotion/react": "^11.14.0",
package/safe-request.d.ts CHANGED
@@ -15,8 +15,10 @@ interface Options {
15
15
  data?: FormData | Record<string, any>;
16
16
  /** 超时时间,不指定或设为 0 代表不限 */
17
17
  timeout?: number;
18
+ /** 是否把响应内容作为二进制处理(结果是 blob) */
19
+ binary?: boolean;
18
20
  }
19
- type FormattedOptions = Required<Pick<Options, 'url' | 'method' | 'headers' | 'body' | 'timeout'>>;
21
+ type FormattedOptions = Required<Pick<Options, 'url' | 'method' | 'headers' | 'body' | 'timeout' | 'binary'>>;
20
22
  type PredefinedOptions = Pick<Options, 'urlPrefix' | 'method' | 'headers' | 'timeout'>;
21
23
  /**
22
24
  * 建立一个请求发起器,并可预设部分选项。
@@ -37,6 +39,13 @@ export declare class SafeRequestClient {
37
39
  formatOptions(input: Options): Promise<FormattedOptions>;
38
40
  /** 请求发起前调用此方法补充 Headers 内容 */
39
41
  protected getHeaders(options: FormattedOptions, inputOptions: Options): Record<string, string> | undefined | Promise<Record<string, string> | undefined>;
42
+ /**
43
+ * 解析响应内容
44
+ * - 若 options.binary 为 true,返回二进制结果
45
+ * - 若 response Content-Type 为 'text/' 开头,返回文本结果
46
+ * - 若 response Content-Type 为 'application/json' 开头,返回 JSON 结构
47
+ * - 其他情况,尝试解析成 JSON,成功则返回 JSON 否则返回纯文本
48
+ */
40
49
  protected parseResponse<T>(options: FormattedOptions, response: Response): Promise<Result<T>>;
41
50
  /** 若请求未成功发起,会触发此回调来生成失败信息 */
42
51
  protected onRequestError(error: Error, url: string): import("./lang/result.js").Failed<undefined>;
package/safe-request.js CHANGED
@@ -1,5 +1,5 @@
1
1
  import { sleep } from './lang/async.js';
2
- import { failed, handleException } from './lang/result.js';
2
+ import { success, failed, handleException } from './lang/result.js';
3
3
  import { getLogger } from './logging/index.js';
4
4
  import { combineUrl } from './url.js';
5
5
  /**
@@ -60,7 +60,7 @@ export class SafeRequestClient {
60
60
  }
61
61
  async formatOptions(input) {
62
62
  const predefined = this.prefefinedOptions;
63
- const { urlPrefix = predefined.urlPrefix ?? '', url: rawUrl, query = {}, method = predefined.method ?? 'GET', headers: rawHeaders = {}, body: rawBody = null, data, timeout = predefined.timeout ?? 0, } = input;
63
+ const { urlPrefix = predefined.urlPrefix ?? '', url: rawUrl, query = {}, method = predefined.method ?? 'GET', headers: rawHeaders = {}, body: rawBody = null, data, timeout = predefined.timeout ?? 0, binary = false, } = input;
64
64
  const headers = {
65
65
  ...(predefined.headers ?? {}),
66
66
  ...rawHeaders,
@@ -82,6 +82,7 @@ export class SafeRequestClient {
82
82
  headers,
83
83
  body,
84
84
  timeout,
85
+ binary,
85
86
  };
86
87
  Object.assign(options.headers, await this.getHeaders(options, input));
87
88
  return options;
@@ -94,19 +95,31 @@ export class SafeRequestClient {
94
95
  inputOptions) {
95
96
  return undefined;
96
97
  }
98
+ /**
99
+ * 解析响应内容
100
+ * - 若 options.binary 为 true,返回二进制结果
101
+ * - 若 response Content-Type 为 'text/' 开头,返回文本结果
102
+ * - 若 response Content-Type 为 'application/json' 开头,返回 JSON 结构
103
+ * - 其他情况,尝试解析成 JSON,成功则返回 JSON 否则返回纯文本
104
+ */
97
105
  async parseResponse(options, response) {
98
- let result;
99
- result = await handleException(response.json());
100
- if (result.success)
101
- return result;
106
+ if (options.binary) {
107
+ return (await handleException(response.blob()));
108
+ }
102
109
  const contentType = (response.headers.get('Content-Type') ?? '').toLowerCase().trim();
103
- if (contentType.startsWith('text/') || contentType === '') {
104
- result = (await handleException(response.text()));
105
- if (result.success)
106
- return result;
110
+ const textResult = await handleException(response.text());
111
+ if (contentType.startsWith('text/') || !textResult.success)
112
+ return textResult;
113
+ let jsonResult;
114
+ try {
115
+ jsonResult = success(JSON.parse(textResult.data));
116
+ }
117
+ catch (error) {
118
+ jsonResult = failed(error.message);
107
119
  }
108
- result = (await handleException(response.blob()));
109
- return result;
120
+ if (contentType.startsWith('application/json') || jsonResult.success)
121
+ return jsonResult;
122
+ return textResult;
110
123
  }
111
124
  /** 若请求未成功发起,会触发此回调来生成失败信息 */
112
125
  onRequestError(error, url) {