@kevisual/api 0.0.51 → 0.0.53
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/query-ai.js +61 -32
- package/dist/query-app.js +61 -32
- package/dist/query-config.js +59 -30
- package/dist/query-login-node.d.ts +340 -0
- package/dist/query-login-node.js +1374 -0
- package/dist/query-login.js +62 -43
- package/dist/query-mark.js +59 -30
- package/dist/query-proxy.js +7809 -1125
- package/dist/query-resources.js +21 -17
- package/dist/query-secret.js +59 -30
- package/dist/query-shop.js +61 -32
- package/dist/store-mark.js +58 -29
- package/package.json +6 -6
- package/query/query-login/login-node-cache.ts +50 -25
- package/query/query-login/query-login-node.ts +8 -3
- package/query/query-login/query-login.ts +3 -3
- package/query/query-proxy/router-api-proxy.ts +1 -1
package/dist/query-ai.js
CHANGED
|
@@ -1,20 +1,14 @@
|
|
|
1
|
-
// node_modules
|
|
1
|
+
// node_modules/@kevisual/query/dist/query-browser.js
|
|
2
2
|
var isTextForContentType = (contentType) => {
|
|
3
3
|
if (!contentType)
|
|
4
4
|
return false;
|
|
5
|
-
const textTypes = ["text/", "xml", "html", "javascript", "css", "csv", "plain", "x-www-form-urlencoded", "md"];
|
|
5
|
+
const textTypes = ["text/", "xml", "html", "javascript", "css", "csv", "plain", "x-www-form-urlencoded", "md", "json"];
|
|
6
6
|
return textTypes.some((type) => contentType.includes(type));
|
|
7
7
|
};
|
|
8
8
|
var adapter = async (opts = {}, overloadOpts) => {
|
|
9
9
|
const controller = new AbortController;
|
|
10
10
|
const signal = controller.signal;
|
|
11
11
|
const isPostFile = opts.isPostFile || false;
|
|
12
|
-
let responseType = opts.responseType || "json";
|
|
13
|
-
if (opts.isBlob) {
|
|
14
|
-
responseType = "blob";
|
|
15
|
-
} else if (opts.isText) {
|
|
16
|
-
responseType = "text";
|
|
17
|
-
}
|
|
18
12
|
const timeout = opts.timeout || 60000 * 3;
|
|
19
13
|
const timer = setTimeout(() => {
|
|
20
14
|
controller.abort();
|
|
@@ -26,7 +20,7 @@ var adapter = async (opts = {}, overloadOpts) => {
|
|
|
26
20
|
if (opts?.url?.startsWith("http")) {
|
|
27
21
|
url = new URL(opts.url);
|
|
28
22
|
} else {
|
|
29
|
-
origin =
|
|
23
|
+
origin = globalThis?.location?.origin || "http://localhost:51515";
|
|
30
24
|
url = new URL(opts?.url || "", origin);
|
|
31
25
|
}
|
|
32
26
|
const isGet = method === "GET";
|
|
@@ -73,21 +67,31 @@ var adapter = async (opts = {}, overloadOpts) => {
|
|
|
73
67
|
headers
|
|
74
68
|
}).then(async (response) => {
|
|
75
69
|
const contentType = response.headers.get("Content-Type");
|
|
76
|
-
if (responseType === "blob") {
|
|
77
|
-
return await response.blob();
|
|
78
|
-
}
|
|
79
|
-
const isText = responseType === "text";
|
|
80
70
|
const isJson = contentType && contentType.includes("application/json");
|
|
81
|
-
|
|
82
|
-
|
|
71
|
+
const isSuccess = response.ok;
|
|
72
|
+
if (isJson) {
|
|
73
|
+
const json = await response.json();
|
|
74
|
+
if (json?.code) {
|
|
75
|
+
return json;
|
|
76
|
+
}
|
|
77
|
+
return {
|
|
78
|
+
code: isSuccess ? 200 : response.status,
|
|
79
|
+
status: response.status,
|
|
80
|
+
data: json
|
|
81
|
+
};
|
|
83
82
|
} else if (isTextForContentType(contentType)) {
|
|
84
83
|
return {
|
|
85
|
-
code: response.status,
|
|
84
|
+
code: isSuccess ? 200 : response.status,
|
|
86
85
|
status: response.status,
|
|
87
86
|
data: await response.text()
|
|
88
87
|
};
|
|
89
88
|
} else {
|
|
90
|
-
return
|
|
89
|
+
return {
|
|
90
|
+
code: isSuccess ? 200 : response.status,
|
|
91
|
+
status: response.status,
|
|
92
|
+
data: "非文本非JSON响应, 请手动处理response。",
|
|
93
|
+
response
|
|
94
|
+
};
|
|
91
95
|
}
|
|
92
96
|
}).catch((err) => {
|
|
93
97
|
if (err.name === "AbortError") {
|
|
@@ -107,16 +111,14 @@ var adapter = async (opts = {}, overloadOpts) => {
|
|
|
107
111
|
var wrapperError = ({ code, message }) => {
|
|
108
112
|
const result = {
|
|
109
113
|
code: code || 500,
|
|
110
|
-
|
|
111
|
-
message: message || "api request error",
|
|
112
|
-
showError: (fn) => {},
|
|
113
|
-
noMsg: true
|
|
114
|
+
message: message || "请求错误"
|
|
114
115
|
};
|
|
115
116
|
return result;
|
|
116
117
|
};
|
|
117
118
|
|
|
118
119
|
class Query {
|
|
119
120
|
adapter;
|
|
121
|
+
baseURL;
|
|
120
122
|
url;
|
|
121
123
|
beforeRequest;
|
|
122
124
|
afterResponse;
|
|
@@ -124,11 +126,20 @@ class Query {
|
|
|
124
126
|
timeout;
|
|
125
127
|
stop;
|
|
126
128
|
qws;
|
|
127
|
-
|
|
129
|
+
tokenName;
|
|
130
|
+
storage;
|
|
131
|
+
token;
|
|
128
132
|
constructor(opts) {
|
|
129
133
|
this.adapter = opts?.adapter || adapter;
|
|
134
|
+
this.tokenName = opts?.tokenName || "token";
|
|
135
|
+
this.storage = opts?.storage || globalThis?.localStorage;
|
|
130
136
|
const defaultURL = opts?.isClient ? "/client/router" : "/api/router";
|
|
131
137
|
this.url = opts?.url || defaultURL;
|
|
138
|
+
if (this.url.startsWith("http")) {
|
|
139
|
+
const urlObj = new URL(this.url);
|
|
140
|
+
this.baseURL = urlObj.origin;
|
|
141
|
+
}
|
|
142
|
+
this.baseURL = opts?.baseURL || this.baseURL;
|
|
132
143
|
this.headers = opts?.headers || {
|
|
133
144
|
"Content-Type": "application/json"
|
|
134
145
|
};
|
|
@@ -137,7 +148,7 @@ class Query {
|
|
|
137
148
|
this.beforeRequest = opts.beforeRequest;
|
|
138
149
|
} else {
|
|
139
150
|
this.beforeRequest = async (opts2) => {
|
|
140
|
-
const token =
|
|
151
|
+
const token = this.token || this.storage?.getItem?.(this.tokenName);
|
|
141
152
|
if (token) {
|
|
142
153
|
opts2.headers = {
|
|
143
154
|
...opts2.headers,
|
|
@@ -172,13 +183,20 @@ class Query {
|
|
|
172
183
|
timeout: _timeout,
|
|
173
184
|
...rest
|
|
174
185
|
};
|
|
186
|
+
const isStartsWithHttp = req.url.startsWith("http");
|
|
187
|
+
if (!isStartsWithHttp) {
|
|
188
|
+
if (this.baseURL) {
|
|
189
|
+
const baseURL = new URL(this.baseURL || globalThis?.location?.origin).origin;
|
|
190
|
+
req.url = baseURL + req.url;
|
|
191
|
+
}
|
|
192
|
+
}
|
|
175
193
|
try {
|
|
176
194
|
if (_beforeRequest) {
|
|
177
195
|
const res = await _beforeRequest(req);
|
|
178
196
|
if (res === false) {
|
|
179
197
|
return wrapperError({
|
|
180
198
|
code: 500,
|
|
181
|
-
message: "
|
|
199
|
+
message: "请求取消",
|
|
182
200
|
req
|
|
183
201
|
});
|
|
184
202
|
}
|
|
@@ -187,12 +205,13 @@ class Query {
|
|
|
187
205
|
console.error("request beforeFn error", e, req);
|
|
188
206
|
return wrapperError({
|
|
189
207
|
code: 500,
|
|
190
|
-
message: "
|
|
208
|
+
message: "请求在请求前处理时发生错误",
|
|
209
|
+
req
|
|
191
210
|
});
|
|
192
211
|
}
|
|
193
212
|
if (this.stop && !options?.noStop) {
|
|
194
213
|
const that = this;
|
|
195
|
-
await new Promise((resolve) => {
|
|
214
|
+
const res = await new Promise((resolve) => {
|
|
196
215
|
let timer = 0;
|
|
197
216
|
const detect = setInterval(() => {
|
|
198
217
|
if (!that.stop) {
|
|
@@ -200,11 +219,20 @@ class Query {
|
|
|
200
219
|
resolve(true);
|
|
201
220
|
}
|
|
202
221
|
timer++;
|
|
203
|
-
if (timer >
|
|
204
|
-
console.error("
|
|
222
|
+
if (timer > 5) {
|
|
223
|
+
console.error("等待请求失败:", req.url, timer);
|
|
224
|
+
clearInterval(detect);
|
|
225
|
+
resolve(false);
|
|
205
226
|
}
|
|
206
227
|
}, 1000);
|
|
207
228
|
});
|
|
229
|
+
if (!res) {
|
|
230
|
+
return wrapperError({
|
|
231
|
+
code: 500,
|
|
232
|
+
message: "请求取消,可能是因为用户未登录或者token过期",
|
|
233
|
+
req
|
|
234
|
+
});
|
|
235
|
+
}
|
|
208
236
|
}
|
|
209
237
|
return _adapter(req).then(async (res) => {
|
|
210
238
|
try {
|
|
@@ -217,10 +245,11 @@ class Query {
|
|
|
217
245
|
}
|
|
218
246
|
return res;
|
|
219
247
|
} catch (e) {
|
|
220
|
-
console.error("
|
|
248
|
+
console.error("请求在响应后处理时发生错误", e, req);
|
|
221
249
|
return wrapperError({
|
|
222
250
|
code: 500,
|
|
223
|
-
message: "
|
|
251
|
+
message: "请求在响应后处理时发生错误",
|
|
252
|
+
req
|
|
224
253
|
});
|
|
225
254
|
}
|
|
226
255
|
});
|
|
@@ -257,7 +286,7 @@ class Query {
|
|
|
257
286
|
}
|
|
258
287
|
}
|
|
259
288
|
|
|
260
|
-
// node_modules
|
|
289
|
+
// node_modules/@kevisual/router/dist/router-define.js
|
|
261
290
|
class Chain {
|
|
262
291
|
object;
|
|
263
292
|
app;
|
|
@@ -391,7 +420,7 @@ var appDefine = QueryUtil.create({
|
|
|
391
420
|
}
|
|
392
421
|
});
|
|
393
422
|
|
|
394
|
-
// node_modules
|
|
423
|
+
// node_modules/@kevisual/query/dist/query.js
|
|
395
424
|
class BaseQuery {
|
|
396
425
|
query;
|
|
397
426
|
queryDefine;
|
package/dist/query-app.js
CHANGED
|
@@ -1,20 +1,14 @@
|
|
|
1
|
-
// node_modules
|
|
1
|
+
// node_modules/@kevisual/query/dist/query-browser.js
|
|
2
2
|
var isTextForContentType = (contentType) => {
|
|
3
3
|
if (!contentType)
|
|
4
4
|
return false;
|
|
5
|
-
const textTypes = ["text/", "xml", "html", "javascript", "css", "csv", "plain", "x-www-form-urlencoded", "md"];
|
|
5
|
+
const textTypes = ["text/", "xml", "html", "javascript", "css", "csv", "plain", "x-www-form-urlencoded", "md", "json"];
|
|
6
6
|
return textTypes.some((type) => contentType.includes(type));
|
|
7
7
|
};
|
|
8
8
|
var adapter = async (opts = {}, overloadOpts) => {
|
|
9
9
|
const controller = new AbortController;
|
|
10
10
|
const signal = controller.signal;
|
|
11
11
|
const isPostFile = opts.isPostFile || false;
|
|
12
|
-
let responseType = opts.responseType || "json";
|
|
13
|
-
if (opts.isBlob) {
|
|
14
|
-
responseType = "blob";
|
|
15
|
-
} else if (opts.isText) {
|
|
16
|
-
responseType = "text";
|
|
17
|
-
}
|
|
18
12
|
const timeout = opts.timeout || 60000 * 3;
|
|
19
13
|
const timer = setTimeout(() => {
|
|
20
14
|
controller.abort();
|
|
@@ -26,7 +20,7 @@ var adapter = async (opts = {}, overloadOpts) => {
|
|
|
26
20
|
if (opts?.url?.startsWith("http")) {
|
|
27
21
|
url = new URL(opts.url);
|
|
28
22
|
} else {
|
|
29
|
-
origin =
|
|
23
|
+
origin = globalThis?.location?.origin || "http://localhost:51515";
|
|
30
24
|
url = new URL(opts?.url || "", origin);
|
|
31
25
|
}
|
|
32
26
|
const isGet = method === "GET";
|
|
@@ -73,21 +67,31 @@ var adapter = async (opts = {}, overloadOpts) => {
|
|
|
73
67
|
headers
|
|
74
68
|
}).then(async (response) => {
|
|
75
69
|
const contentType = response.headers.get("Content-Type");
|
|
76
|
-
if (responseType === "blob") {
|
|
77
|
-
return await response.blob();
|
|
78
|
-
}
|
|
79
|
-
const isText = responseType === "text";
|
|
80
70
|
const isJson = contentType && contentType.includes("application/json");
|
|
81
|
-
|
|
82
|
-
|
|
71
|
+
const isSuccess = response.ok;
|
|
72
|
+
if (isJson) {
|
|
73
|
+
const json = await response.json();
|
|
74
|
+
if (json?.code) {
|
|
75
|
+
return json;
|
|
76
|
+
}
|
|
77
|
+
return {
|
|
78
|
+
code: isSuccess ? 200 : response.status,
|
|
79
|
+
status: response.status,
|
|
80
|
+
data: json
|
|
81
|
+
};
|
|
83
82
|
} else if (isTextForContentType(contentType)) {
|
|
84
83
|
return {
|
|
85
|
-
code: response.status,
|
|
84
|
+
code: isSuccess ? 200 : response.status,
|
|
86
85
|
status: response.status,
|
|
87
86
|
data: await response.text()
|
|
88
87
|
};
|
|
89
88
|
} else {
|
|
90
|
-
return
|
|
89
|
+
return {
|
|
90
|
+
code: isSuccess ? 200 : response.status,
|
|
91
|
+
status: response.status,
|
|
92
|
+
data: "非文本非JSON响应, 请手动处理response。",
|
|
93
|
+
response
|
|
94
|
+
};
|
|
91
95
|
}
|
|
92
96
|
}).catch((err) => {
|
|
93
97
|
if (err.name === "AbortError") {
|
|
@@ -107,16 +111,14 @@ var adapter = async (opts = {}, overloadOpts) => {
|
|
|
107
111
|
var wrapperError = ({ code, message }) => {
|
|
108
112
|
const result = {
|
|
109
113
|
code: code || 500,
|
|
110
|
-
|
|
111
|
-
message: message || "api request error",
|
|
112
|
-
showError: (fn) => {},
|
|
113
|
-
noMsg: true
|
|
114
|
+
message: message || "请求错误"
|
|
114
115
|
};
|
|
115
116
|
return result;
|
|
116
117
|
};
|
|
117
118
|
|
|
118
119
|
class Query {
|
|
119
120
|
adapter;
|
|
121
|
+
baseURL;
|
|
120
122
|
url;
|
|
121
123
|
beforeRequest;
|
|
122
124
|
afterResponse;
|
|
@@ -124,11 +126,20 @@ class Query {
|
|
|
124
126
|
timeout;
|
|
125
127
|
stop;
|
|
126
128
|
qws;
|
|
127
|
-
|
|
129
|
+
tokenName;
|
|
130
|
+
storage;
|
|
131
|
+
token;
|
|
128
132
|
constructor(opts) {
|
|
129
133
|
this.adapter = opts?.adapter || adapter;
|
|
134
|
+
this.tokenName = opts?.tokenName || "token";
|
|
135
|
+
this.storage = opts?.storage || globalThis?.localStorage;
|
|
130
136
|
const defaultURL = opts?.isClient ? "/client/router" : "/api/router";
|
|
131
137
|
this.url = opts?.url || defaultURL;
|
|
138
|
+
if (this.url.startsWith("http")) {
|
|
139
|
+
const urlObj = new URL(this.url);
|
|
140
|
+
this.baseURL = urlObj.origin;
|
|
141
|
+
}
|
|
142
|
+
this.baseURL = opts?.baseURL || this.baseURL;
|
|
132
143
|
this.headers = opts?.headers || {
|
|
133
144
|
"Content-Type": "application/json"
|
|
134
145
|
};
|
|
@@ -137,7 +148,7 @@ class Query {
|
|
|
137
148
|
this.beforeRequest = opts.beforeRequest;
|
|
138
149
|
} else {
|
|
139
150
|
this.beforeRequest = async (opts2) => {
|
|
140
|
-
const token =
|
|
151
|
+
const token = this.token || this.storage?.getItem?.(this.tokenName);
|
|
141
152
|
if (token) {
|
|
142
153
|
opts2.headers = {
|
|
143
154
|
...opts2.headers,
|
|
@@ -172,13 +183,20 @@ class Query {
|
|
|
172
183
|
timeout: _timeout,
|
|
173
184
|
...rest
|
|
174
185
|
};
|
|
186
|
+
const isStartsWithHttp = req.url.startsWith("http");
|
|
187
|
+
if (!isStartsWithHttp) {
|
|
188
|
+
if (this.baseURL) {
|
|
189
|
+
const baseURL = new URL(this.baseURL || globalThis?.location?.origin).origin;
|
|
190
|
+
req.url = baseURL + req.url;
|
|
191
|
+
}
|
|
192
|
+
}
|
|
175
193
|
try {
|
|
176
194
|
if (_beforeRequest) {
|
|
177
195
|
const res = await _beforeRequest(req);
|
|
178
196
|
if (res === false) {
|
|
179
197
|
return wrapperError({
|
|
180
198
|
code: 500,
|
|
181
|
-
message: "
|
|
199
|
+
message: "请求取消",
|
|
182
200
|
req
|
|
183
201
|
});
|
|
184
202
|
}
|
|
@@ -187,12 +205,13 @@ class Query {
|
|
|
187
205
|
console.error("request beforeFn error", e, req);
|
|
188
206
|
return wrapperError({
|
|
189
207
|
code: 500,
|
|
190
|
-
message: "
|
|
208
|
+
message: "请求在请求前处理时发生错误",
|
|
209
|
+
req
|
|
191
210
|
});
|
|
192
211
|
}
|
|
193
212
|
if (this.stop && !options?.noStop) {
|
|
194
213
|
const that = this;
|
|
195
|
-
await new Promise((resolve) => {
|
|
214
|
+
const res = await new Promise((resolve) => {
|
|
196
215
|
let timer = 0;
|
|
197
216
|
const detect = setInterval(() => {
|
|
198
217
|
if (!that.stop) {
|
|
@@ -200,11 +219,20 @@ class Query {
|
|
|
200
219
|
resolve(true);
|
|
201
220
|
}
|
|
202
221
|
timer++;
|
|
203
|
-
if (timer >
|
|
204
|
-
console.error("
|
|
222
|
+
if (timer > 5) {
|
|
223
|
+
console.error("等待请求失败:", req.url, timer);
|
|
224
|
+
clearInterval(detect);
|
|
225
|
+
resolve(false);
|
|
205
226
|
}
|
|
206
227
|
}, 1000);
|
|
207
228
|
});
|
|
229
|
+
if (!res) {
|
|
230
|
+
return wrapperError({
|
|
231
|
+
code: 500,
|
|
232
|
+
message: "请求取消,可能是因为用户未登录或者token过期",
|
|
233
|
+
req
|
|
234
|
+
});
|
|
235
|
+
}
|
|
208
236
|
}
|
|
209
237
|
return _adapter(req).then(async (res) => {
|
|
210
238
|
try {
|
|
@@ -217,10 +245,11 @@ class Query {
|
|
|
217
245
|
}
|
|
218
246
|
return res;
|
|
219
247
|
} catch (e) {
|
|
220
|
-
console.error("
|
|
248
|
+
console.error("请求在响应后处理时发生错误", e, req);
|
|
221
249
|
return wrapperError({
|
|
222
250
|
code: 500,
|
|
223
|
-
message: "
|
|
251
|
+
message: "请求在响应后处理时发生错误",
|
|
252
|
+
req
|
|
224
253
|
});
|
|
225
254
|
}
|
|
226
255
|
});
|
|
@@ -257,7 +286,7 @@ class Query {
|
|
|
257
286
|
}
|
|
258
287
|
}
|
|
259
288
|
|
|
260
|
-
// node_modules
|
|
289
|
+
// node_modules/@kevisual/router/dist/router-define.js
|
|
261
290
|
class Chain {
|
|
262
291
|
object;
|
|
263
292
|
app;
|
|
@@ -465,7 +494,7 @@ var userAppDefine = QueryUtil.create({
|
|
|
465
494
|
}
|
|
466
495
|
});
|
|
467
496
|
|
|
468
|
-
// node_modules
|
|
497
|
+
// node_modules/@kevisual/query/dist/query.js
|
|
469
498
|
class BaseQuery {
|
|
470
499
|
query;
|
|
471
500
|
queryDefine;
|
package/dist/query-config.js
CHANGED
|
@@ -1,20 +1,14 @@
|
|
|
1
|
-
// node_modules
|
|
1
|
+
// node_modules/@kevisual/query/dist/query-browser.js
|
|
2
2
|
var isTextForContentType = (contentType) => {
|
|
3
3
|
if (!contentType)
|
|
4
4
|
return false;
|
|
5
|
-
const textTypes = ["text/", "xml", "html", "javascript", "css", "csv", "plain", "x-www-form-urlencoded", "md"];
|
|
5
|
+
const textTypes = ["text/", "xml", "html", "javascript", "css", "csv", "plain", "x-www-form-urlencoded", "md", "json"];
|
|
6
6
|
return textTypes.some((type) => contentType.includes(type));
|
|
7
7
|
};
|
|
8
8
|
var adapter = async (opts = {}, overloadOpts) => {
|
|
9
9
|
const controller = new AbortController;
|
|
10
10
|
const signal = controller.signal;
|
|
11
11
|
const isPostFile = opts.isPostFile || false;
|
|
12
|
-
let responseType = opts.responseType || "json";
|
|
13
|
-
if (opts.isBlob) {
|
|
14
|
-
responseType = "blob";
|
|
15
|
-
} else if (opts.isText) {
|
|
16
|
-
responseType = "text";
|
|
17
|
-
}
|
|
18
12
|
const timeout = opts.timeout || 60000 * 3;
|
|
19
13
|
const timer = setTimeout(() => {
|
|
20
14
|
controller.abort();
|
|
@@ -26,7 +20,7 @@ var adapter = async (opts = {}, overloadOpts) => {
|
|
|
26
20
|
if (opts?.url?.startsWith("http")) {
|
|
27
21
|
url = new URL(opts.url);
|
|
28
22
|
} else {
|
|
29
|
-
origin =
|
|
23
|
+
origin = globalThis?.location?.origin || "http://localhost:51515";
|
|
30
24
|
url = new URL(opts?.url || "", origin);
|
|
31
25
|
}
|
|
32
26
|
const isGet = method === "GET";
|
|
@@ -73,21 +67,31 @@ var adapter = async (opts = {}, overloadOpts) => {
|
|
|
73
67
|
headers
|
|
74
68
|
}).then(async (response) => {
|
|
75
69
|
const contentType = response.headers.get("Content-Type");
|
|
76
|
-
if (responseType === "blob") {
|
|
77
|
-
return await response.blob();
|
|
78
|
-
}
|
|
79
|
-
const isText = responseType === "text";
|
|
80
70
|
const isJson = contentType && contentType.includes("application/json");
|
|
81
|
-
|
|
82
|
-
|
|
71
|
+
const isSuccess = response.ok;
|
|
72
|
+
if (isJson) {
|
|
73
|
+
const json = await response.json();
|
|
74
|
+
if (json?.code) {
|
|
75
|
+
return json;
|
|
76
|
+
}
|
|
77
|
+
return {
|
|
78
|
+
code: isSuccess ? 200 : response.status,
|
|
79
|
+
status: response.status,
|
|
80
|
+
data: json
|
|
81
|
+
};
|
|
83
82
|
} else if (isTextForContentType(contentType)) {
|
|
84
83
|
return {
|
|
85
|
-
code: response.status,
|
|
84
|
+
code: isSuccess ? 200 : response.status,
|
|
86
85
|
status: response.status,
|
|
87
86
|
data: await response.text()
|
|
88
87
|
};
|
|
89
88
|
} else {
|
|
90
|
-
return
|
|
89
|
+
return {
|
|
90
|
+
code: isSuccess ? 200 : response.status,
|
|
91
|
+
status: response.status,
|
|
92
|
+
data: "非文本非JSON响应, 请手动处理response。",
|
|
93
|
+
response
|
|
94
|
+
};
|
|
91
95
|
}
|
|
92
96
|
}).catch((err) => {
|
|
93
97
|
if (err.name === "AbortError") {
|
|
@@ -107,16 +111,14 @@ var adapter = async (opts = {}, overloadOpts) => {
|
|
|
107
111
|
var wrapperError = ({ code, message }) => {
|
|
108
112
|
const result = {
|
|
109
113
|
code: code || 500,
|
|
110
|
-
|
|
111
|
-
message: message || "api request error",
|
|
112
|
-
showError: (fn) => {},
|
|
113
|
-
noMsg: true
|
|
114
|
+
message: message || "请求错误"
|
|
114
115
|
};
|
|
115
116
|
return result;
|
|
116
117
|
};
|
|
117
118
|
|
|
118
119
|
class Query {
|
|
119
120
|
adapter;
|
|
121
|
+
baseURL;
|
|
120
122
|
url;
|
|
121
123
|
beforeRequest;
|
|
122
124
|
afterResponse;
|
|
@@ -124,11 +126,20 @@ class Query {
|
|
|
124
126
|
timeout;
|
|
125
127
|
stop;
|
|
126
128
|
qws;
|
|
127
|
-
|
|
129
|
+
tokenName;
|
|
130
|
+
storage;
|
|
131
|
+
token;
|
|
128
132
|
constructor(opts) {
|
|
129
133
|
this.adapter = opts?.adapter || adapter;
|
|
134
|
+
this.tokenName = opts?.tokenName || "token";
|
|
135
|
+
this.storage = opts?.storage || globalThis?.localStorage;
|
|
130
136
|
const defaultURL = opts?.isClient ? "/client/router" : "/api/router";
|
|
131
137
|
this.url = opts?.url || defaultURL;
|
|
138
|
+
if (this.url.startsWith("http")) {
|
|
139
|
+
const urlObj = new URL(this.url);
|
|
140
|
+
this.baseURL = urlObj.origin;
|
|
141
|
+
}
|
|
142
|
+
this.baseURL = opts?.baseURL || this.baseURL;
|
|
132
143
|
this.headers = opts?.headers || {
|
|
133
144
|
"Content-Type": "application/json"
|
|
134
145
|
};
|
|
@@ -137,7 +148,7 @@ class Query {
|
|
|
137
148
|
this.beforeRequest = opts.beforeRequest;
|
|
138
149
|
} else {
|
|
139
150
|
this.beforeRequest = async (opts2) => {
|
|
140
|
-
const token =
|
|
151
|
+
const token = this.token || this.storage?.getItem?.(this.tokenName);
|
|
141
152
|
if (token) {
|
|
142
153
|
opts2.headers = {
|
|
143
154
|
...opts2.headers,
|
|
@@ -172,13 +183,20 @@ class Query {
|
|
|
172
183
|
timeout: _timeout,
|
|
173
184
|
...rest
|
|
174
185
|
};
|
|
186
|
+
const isStartsWithHttp = req.url.startsWith("http");
|
|
187
|
+
if (!isStartsWithHttp) {
|
|
188
|
+
if (this.baseURL) {
|
|
189
|
+
const baseURL = new URL(this.baseURL || globalThis?.location?.origin).origin;
|
|
190
|
+
req.url = baseURL + req.url;
|
|
191
|
+
}
|
|
192
|
+
}
|
|
175
193
|
try {
|
|
176
194
|
if (_beforeRequest) {
|
|
177
195
|
const res = await _beforeRequest(req);
|
|
178
196
|
if (res === false) {
|
|
179
197
|
return wrapperError({
|
|
180
198
|
code: 500,
|
|
181
|
-
message: "
|
|
199
|
+
message: "请求取消",
|
|
182
200
|
req
|
|
183
201
|
});
|
|
184
202
|
}
|
|
@@ -187,12 +205,13 @@ class Query {
|
|
|
187
205
|
console.error("request beforeFn error", e, req);
|
|
188
206
|
return wrapperError({
|
|
189
207
|
code: 500,
|
|
190
|
-
message: "
|
|
208
|
+
message: "请求在请求前处理时发生错误",
|
|
209
|
+
req
|
|
191
210
|
});
|
|
192
211
|
}
|
|
193
212
|
if (this.stop && !options?.noStop) {
|
|
194
213
|
const that = this;
|
|
195
|
-
await new Promise((resolve) => {
|
|
214
|
+
const res = await new Promise((resolve) => {
|
|
196
215
|
let timer = 0;
|
|
197
216
|
const detect = setInterval(() => {
|
|
198
217
|
if (!that.stop) {
|
|
@@ -200,11 +219,20 @@ class Query {
|
|
|
200
219
|
resolve(true);
|
|
201
220
|
}
|
|
202
221
|
timer++;
|
|
203
|
-
if (timer >
|
|
204
|
-
console.error("
|
|
222
|
+
if (timer > 5) {
|
|
223
|
+
console.error("等待请求失败:", req.url, timer);
|
|
224
|
+
clearInterval(detect);
|
|
225
|
+
resolve(false);
|
|
205
226
|
}
|
|
206
227
|
}, 1000);
|
|
207
228
|
});
|
|
229
|
+
if (!res) {
|
|
230
|
+
return wrapperError({
|
|
231
|
+
code: 500,
|
|
232
|
+
message: "请求取消,可能是因为用户未登录或者token过期",
|
|
233
|
+
req
|
|
234
|
+
});
|
|
235
|
+
}
|
|
208
236
|
}
|
|
209
237
|
return _adapter(req).then(async (res) => {
|
|
210
238
|
try {
|
|
@@ -217,10 +245,11 @@ class Query {
|
|
|
217
245
|
}
|
|
218
246
|
return res;
|
|
219
247
|
} catch (e) {
|
|
220
|
-
console.error("
|
|
248
|
+
console.error("请求在响应后处理时发生错误", e, req);
|
|
221
249
|
return wrapperError({
|
|
222
250
|
code: 500,
|
|
223
|
-
message: "
|
|
251
|
+
message: "请求在响应后处理时发生错误",
|
|
252
|
+
req
|
|
224
253
|
});
|
|
225
254
|
}
|
|
226
255
|
});
|