@fctc/interface-logic 1.5.8 → 1.6.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/dist/configs.d.mts +0 -1
- package/dist/configs.d.ts +0 -1
- package/dist/configs.js +103 -116
- package/dist/configs.mjs +102 -117
- package/dist/constants.js +1 -0
- package/dist/environment.d.mts +3 -20
- package/dist/environment.d.ts +3 -20
- package/dist/environment.js +142 -159
- package/dist/environment.mjs +141 -162
- package/dist/hooks.d.mts +6 -1
- package/dist/hooks.d.ts +6 -1
- package/dist/hooks.js +1569 -1704
- package/dist/hooks.mjs +1523 -1663
- package/dist/provider.d.mts +1 -1
- package/dist/provider.d.ts +1 -1
- package/dist/provider.js +528 -583
- package/dist/provider.mjs +527 -586
- package/dist/services.d.mts +1 -0
- package/dist/services.d.ts +1 -0
- package/dist/services.js +1388 -1541
- package/dist/services.mjs +1387 -1544
- package/dist/store.d.mts +155 -127
- package/dist/store.d.ts +155 -127
- package/dist/store.js +4 -15
- package/dist/store.mjs +3 -18
- package/dist/types.js +1 -0
- package/dist/utils.d.mts +2 -2
- package/dist/utils.d.ts +2 -2
- package/dist/utils.js +95 -116
- package/dist/utils.mjs +94 -119
- package/package.json +81 -82
package/dist/configs.d.mts
CHANGED
package/dist/configs.d.ts
CHANGED
package/dist/configs.js
CHANGED
|
@@ -1,10 +1,10 @@
|
|
|
1
|
+
"use strict";
|
|
1
2
|
var __create = Object.create;
|
|
2
3
|
var __defProp = Object.defineProperty;
|
|
3
4
|
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
4
5
|
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
5
6
|
var __getProtoOf = Object.getPrototypeOf;
|
|
6
7
|
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
|
7
|
-
var __pow = Math.pow;
|
|
8
8
|
var __export = (target, all) => {
|
|
9
9
|
for (var name in all)
|
|
10
10
|
__defProp(target, name, { get: all[name], enumerable: true });
|
|
@@ -26,26 +26,6 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
|
|
|
26
26
|
mod
|
|
27
27
|
));
|
|
28
28
|
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
|
|
29
|
-
var __async = (__this, __arguments, generator) => {
|
|
30
|
-
return new Promise((resolve, reject) => {
|
|
31
|
-
var fulfilled = (value) => {
|
|
32
|
-
try {
|
|
33
|
-
step(generator.next(value));
|
|
34
|
-
} catch (e) {
|
|
35
|
-
reject(e);
|
|
36
|
-
}
|
|
37
|
-
};
|
|
38
|
-
var rejected = (value) => {
|
|
39
|
-
try {
|
|
40
|
-
step(generator.throw(value));
|
|
41
|
-
} catch (e) {
|
|
42
|
-
reject(e);
|
|
43
|
-
}
|
|
44
|
-
};
|
|
45
|
-
var step = (x) => x.done ? resolve(x.value) : Promise.resolve(x.value).then(fulfilled, rejected);
|
|
46
|
-
step((generator = generator.apply(__this, __arguments)).next());
|
|
47
|
-
});
|
|
48
|
-
};
|
|
49
29
|
|
|
50
30
|
// src/configs.ts
|
|
51
31
|
var configs_exports = {};
|
|
@@ -1138,6 +1118,22 @@ var PyRelativeDelta = class _PyRelativeDelta {
|
|
|
1138
1118
|
this.microsecond = params.microsecond;
|
|
1139
1119
|
this.weekday = params.weekday;
|
|
1140
1120
|
}
|
|
1121
|
+
years;
|
|
1122
|
+
months;
|
|
1123
|
+
days;
|
|
1124
|
+
hours;
|
|
1125
|
+
minutes;
|
|
1126
|
+
seconds;
|
|
1127
|
+
microseconds;
|
|
1128
|
+
leapDays;
|
|
1129
|
+
year;
|
|
1130
|
+
month;
|
|
1131
|
+
day;
|
|
1132
|
+
hour;
|
|
1133
|
+
minute;
|
|
1134
|
+
second;
|
|
1135
|
+
microsecond;
|
|
1136
|
+
weekday;
|
|
1141
1137
|
negate() {
|
|
1142
1138
|
return new _PyRelativeDelta(this, -1);
|
|
1143
1139
|
}
|
|
@@ -1252,7 +1248,7 @@ function execOnIterable(iterable, func) {
|
|
|
1252
1248
|
if (typeof iterable === "object" && !Array.isArray(iterable) && !(iterable instanceof Set)) {
|
|
1253
1249
|
iterable = Object.keys(iterable);
|
|
1254
1250
|
}
|
|
1255
|
-
if (typeof
|
|
1251
|
+
if (typeof iterable?.[Symbol.iterator] !== "function") {
|
|
1256
1252
|
throw new EvaluationError("value not iterable");
|
|
1257
1253
|
}
|
|
1258
1254
|
return func(iterable);
|
|
@@ -1575,7 +1571,7 @@ function applyBinaryOp(ast, context) {
|
|
|
1575
1571
|
}
|
|
1576
1572
|
return Math.floor(left / right);
|
|
1577
1573
|
case "**":
|
|
1578
|
-
return
|
|
1574
|
+
return left ** right;
|
|
1579
1575
|
case "==":
|
|
1580
1576
|
return isEqual(left, right);
|
|
1581
1577
|
case "<>":
|
|
@@ -1697,7 +1693,7 @@ function evaluate(ast, context = {}) {
|
|
|
1697
1693
|
const dicts = /* @__PURE__ */ new Set();
|
|
1698
1694
|
let pyContext;
|
|
1699
1695
|
const evalContext = Object.create(context);
|
|
1700
|
-
if (!
|
|
1696
|
+
if (!evalContext?.context) {
|
|
1701
1697
|
Object.defineProperty(evalContext, "context", {
|
|
1702
1698
|
get() {
|
|
1703
1699
|
if (!pyContext) {
|
|
@@ -1708,18 +1704,17 @@ function evaluate(ast, context = {}) {
|
|
|
1708
1704
|
});
|
|
1709
1705
|
}
|
|
1710
1706
|
function _innerEvaluate(ast2) {
|
|
1711
|
-
|
|
1712
|
-
switch (ast2 == null ? void 0 : ast2.type) {
|
|
1707
|
+
switch (ast2?.type) {
|
|
1713
1708
|
case 0:
|
|
1714
1709
|
// Number
|
|
1715
1710
|
case 1:
|
|
1716
1711
|
return ast2.value;
|
|
1717
1712
|
case 5:
|
|
1718
1713
|
if (ast2.value in evalContext) {
|
|
1719
|
-
if (typeof evalContext[ast2.value] === "object" &&
|
|
1720
|
-
return
|
|
1714
|
+
if (typeof evalContext[ast2.value] === "object" && evalContext[ast2.value]?.id) {
|
|
1715
|
+
return evalContext[ast2.value]?.id;
|
|
1721
1716
|
}
|
|
1722
|
-
return
|
|
1717
|
+
return evalContext[ast2.value] ?? false;
|
|
1723
1718
|
} else if (ast2.value in BUILTINS) {
|
|
1724
1719
|
return BUILTINS[ast2.value];
|
|
1725
1720
|
} else {
|
|
@@ -1756,7 +1751,7 @@ function evaluate(ast, context = {}) {
|
|
|
1756
1751
|
const args = ast2.args.map(_evaluate);
|
|
1757
1752
|
const kwargs = {};
|
|
1758
1753
|
for (const kwarg in ast2.kwargs) {
|
|
1759
|
-
kwargs[kwarg] = _evaluate(ast2
|
|
1754
|
+
kwargs[kwarg] = _evaluate(ast2?.kwargs[kwarg]);
|
|
1760
1755
|
}
|
|
1761
1756
|
if (fnValue === PyDate || fnValue === PyDateTime || fnValue === PyTime || fnValue === PyRelativeDelta || fnValue === PyTimeDelta) {
|
|
1762
1757
|
return fnValue.create(...args, kwargs);
|
|
@@ -1835,25 +1830,9 @@ function escapeRegExp(str) {
|
|
|
1835
1830
|
var InvalidDomainError = class extends Error {
|
|
1836
1831
|
};
|
|
1837
1832
|
var Domain = class _Domain {
|
|
1838
|
-
|
|
1839
|
-
|
|
1840
|
-
|
|
1841
|
-
return new _Domain(descr.toString());
|
|
1842
|
-
} else {
|
|
1843
|
-
let rawAST;
|
|
1844
|
-
try {
|
|
1845
|
-
rawAST = typeof descr === "string" ? parseExpr(descr) : toAST(descr);
|
|
1846
|
-
} catch (error) {
|
|
1847
|
-
throw new InvalidDomainError(
|
|
1848
|
-
`Invalid domain representation: ${descr}`,
|
|
1849
|
-
{
|
|
1850
|
-
cause: error
|
|
1851
|
-
}
|
|
1852
|
-
);
|
|
1853
|
-
}
|
|
1854
|
-
this.ast = normalizeDomainAST(rawAST);
|
|
1855
|
-
}
|
|
1856
|
-
}
|
|
1833
|
+
ast = { type: -1, value: null };
|
|
1834
|
+
static TRUE;
|
|
1835
|
+
static FALSE;
|
|
1857
1836
|
static combine(domains, operator) {
|
|
1858
1837
|
if (domains.length === 0) {
|
|
1859
1838
|
return new _Domain([]);
|
|
@@ -1932,6 +1911,24 @@ var Domain = class _Domain {
|
|
|
1932
1911
|
processLeaf(d.ast.value, 0, "&", newDomain);
|
|
1933
1912
|
return newDomain;
|
|
1934
1913
|
}
|
|
1914
|
+
constructor(descr = []) {
|
|
1915
|
+
if (descr instanceof _Domain) {
|
|
1916
|
+
return new _Domain(descr.toString());
|
|
1917
|
+
} else {
|
|
1918
|
+
let rawAST;
|
|
1919
|
+
try {
|
|
1920
|
+
rawAST = typeof descr === "string" ? parseExpr(descr) : toAST(descr);
|
|
1921
|
+
} catch (error) {
|
|
1922
|
+
throw new InvalidDomainError(
|
|
1923
|
+
`Invalid domain representation: ${descr}`,
|
|
1924
|
+
{
|
|
1925
|
+
cause: error
|
|
1926
|
+
}
|
|
1927
|
+
);
|
|
1928
|
+
}
|
|
1929
|
+
this.ast = normalizeDomainAST(rawAST);
|
|
1930
|
+
}
|
|
1931
|
+
}
|
|
1935
1932
|
contains(record) {
|
|
1936
1933
|
const expr = evaluate(this.ast, record);
|
|
1937
1934
|
return matchDomain(record, expr);
|
|
@@ -1950,7 +1947,7 @@ var Domain = class _Domain {
|
|
|
1950
1947
|
return evaluatedAsList;
|
|
1951
1948
|
}
|
|
1952
1949
|
return this.toString();
|
|
1953
|
-
} catch
|
|
1950
|
+
} catch {
|
|
1954
1951
|
return this.toString();
|
|
1955
1952
|
}
|
|
1956
1953
|
}
|
|
@@ -2173,22 +2170,22 @@ var updateTokenParamInOriginalRequest = (originalRequest, newAccessToken) => {
|
|
|
2173
2170
|
|
|
2174
2171
|
// src/utils/storage/local-storage.ts
|
|
2175
2172
|
var localStorageUtils = () => {
|
|
2176
|
-
const setToken = (access_token) =>
|
|
2173
|
+
const setToken = async (access_token) => {
|
|
2177
2174
|
localStorage.setItem("accessToken", access_token);
|
|
2178
|
-
}
|
|
2179
|
-
const setRefreshToken = (refresh_token) =>
|
|
2175
|
+
};
|
|
2176
|
+
const setRefreshToken = async (refresh_token) => {
|
|
2180
2177
|
localStorage.setItem("refreshToken", refresh_token);
|
|
2181
|
-
}
|
|
2182
|
-
const getAccessToken = () =>
|
|
2178
|
+
};
|
|
2179
|
+
const getAccessToken = async () => {
|
|
2183
2180
|
return localStorage.getItem("accessToken");
|
|
2184
|
-
}
|
|
2185
|
-
const getRefreshToken = () =>
|
|
2181
|
+
};
|
|
2182
|
+
const getRefreshToken = async () => {
|
|
2186
2183
|
return localStorage.getItem("refreshToken");
|
|
2187
|
-
}
|
|
2188
|
-
const clearToken = () =>
|
|
2184
|
+
};
|
|
2185
|
+
const clearToken = async () => {
|
|
2189
2186
|
localStorage.removeItem("accessToken");
|
|
2190
2187
|
localStorage.removeItem("refreshToken");
|
|
2191
|
-
}
|
|
2188
|
+
};
|
|
2192
2189
|
return {
|
|
2193
2190
|
setToken,
|
|
2194
2191
|
setRefreshToken,
|
|
@@ -2200,9 +2197,9 @@ var localStorageUtils = () => {
|
|
|
2200
2197
|
|
|
2201
2198
|
// src/utils/storage/session-storage.ts
|
|
2202
2199
|
var sessionStorageUtils = () => {
|
|
2203
|
-
const getBrowserSession = () =>
|
|
2200
|
+
const getBrowserSession = async () => {
|
|
2204
2201
|
return sessionStorage.getItem("browserSession");
|
|
2205
|
-
}
|
|
2202
|
+
};
|
|
2206
2203
|
return {
|
|
2207
2204
|
getBrowserSession
|
|
2208
2205
|
};
|
|
@@ -2211,14 +2208,13 @@ var sessionStorageUtils = () => {
|
|
|
2211
2208
|
// src/configs/axios-client.ts
|
|
2212
2209
|
var axiosClient = {
|
|
2213
2210
|
init(config) {
|
|
2214
|
-
|
|
2215
|
-
const
|
|
2216
|
-
const sessionStorage2 = (_b = config.sessionStorageUtils) != null ? _b : sessionStorageUtils();
|
|
2211
|
+
const localStorage2 = config.localStorageUtils ?? localStorageUtils();
|
|
2212
|
+
const sessionStorage2 = config.sessionStorageUtils ?? sessionStorageUtils();
|
|
2217
2213
|
const db = config.db;
|
|
2218
2214
|
let isRefreshing = false;
|
|
2219
2215
|
let failedQueue = [];
|
|
2220
2216
|
const processQueue = (error, token = null) => {
|
|
2221
|
-
failedQueue
|
|
2217
|
+
failedQueue?.forEach((prom) => {
|
|
2222
2218
|
if (error) {
|
|
2223
2219
|
prom.reject(error);
|
|
2224
2220
|
} else {
|
|
@@ -2233,38 +2229,33 @@ var axiosClient = {
|
|
|
2233
2229
|
timeout: 5e4,
|
|
2234
2230
|
paramsSerializer: (params) => new URLSearchParams(params).toString()
|
|
2235
2231
|
});
|
|
2236
|
-
instance.interceptors.request.use(
|
|
2237
|
-
|
|
2238
|
-
|
|
2239
|
-
|
|
2240
|
-
if (token) {
|
|
2241
|
-
config2.headers["Authorization"] = "Bearer " + token;
|
|
2242
|
-
}
|
|
2243
|
-
return config2;
|
|
2244
|
-
}),
|
|
2245
|
-
(error) => {
|
|
2246
|
-
Promise.reject(error);
|
|
2232
|
+
instance.interceptors.request.use(async (config2) => {
|
|
2233
|
+
const { useRefreshToken, useActionToken, actionToken } = config2;
|
|
2234
|
+
if (useActionToken && actionToken) {
|
|
2235
|
+
config2.headers["Action-Token"] = actionToken;
|
|
2247
2236
|
}
|
|
2248
|
-
|
|
2237
|
+
const getToken = useRefreshToken ? localStorage2.getRefreshToken : localStorage2.getAccessToken;
|
|
2238
|
+
const token = await getToken?.();
|
|
2239
|
+
if (token) config2.headers["Authorization"] = `Bearer ${token}`;
|
|
2240
|
+
return config2;
|
|
2241
|
+
}, Promise.reject);
|
|
2249
2242
|
instance.interceptors.response.use(
|
|
2250
2243
|
(response) => {
|
|
2251
2244
|
return handleResponse(response);
|
|
2252
2245
|
},
|
|
2253
|
-
(error) =>
|
|
2254
|
-
|
|
2255
|
-
const handleError3 = (error2) => __async(null, null, function* () {
|
|
2256
|
-
var _a3;
|
|
2246
|
+
async (error) => {
|
|
2247
|
+
const handleError3 = async (error2) => {
|
|
2257
2248
|
if (!error2.response) {
|
|
2258
2249
|
return error2;
|
|
2259
2250
|
}
|
|
2260
2251
|
const { data } = error2.response;
|
|
2261
|
-
if (data && data.code === 400 && ["invalid_grant"].includes(
|
|
2262
|
-
|
|
2252
|
+
if (data && data.code === 400 && ["invalid_grant"].includes(data.data?.error)) {
|
|
2253
|
+
await clearAuthToken();
|
|
2263
2254
|
}
|
|
2264
2255
|
return data;
|
|
2265
|
-
}
|
|
2256
|
+
};
|
|
2266
2257
|
const originalRequest = error.config;
|
|
2267
|
-
if ((
|
|
2258
|
+
if ((error.response?.status === 403 || error.response?.status === 401 || error.response?.status === 404) && ["TOKEN_EXPIRED", "AUTHEN_FAIL", 401, "ERR_2FA_006"].includes(
|
|
2268
2259
|
error.response.data.code
|
|
2269
2260
|
)) {
|
|
2270
2261
|
if (isRefreshing) {
|
|
@@ -2277,19 +2268,18 @@ var axiosClient = {
|
|
|
2277
2268
|
token
|
|
2278
2269
|
);
|
|
2279
2270
|
return instance.request(originalRequest);
|
|
2280
|
-
}).catch((err) =>
|
|
2281
|
-
|
|
2282
|
-
|
|
2283
|
-
yield clearAuthToken();
|
|
2271
|
+
}).catch(async (err) => {
|
|
2272
|
+
if ((err.response?.status === 400 || err.response?.status === 401) && ["invalid_grant"].includes(err.response.data.error)) {
|
|
2273
|
+
await clearAuthToken();
|
|
2284
2274
|
}
|
|
2285
|
-
})
|
|
2275
|
+
});
|
|
2286
2276
|
}
|
|
2287
|
-
const browserSession =
|
|
2288
|
-
const refreshToken =
|
|
2289
|
-
const accessTokenExp =
|
|
2277
|
+
const browserSession = await sessionStorage2.getBrowserSession();
|
|
2278
|
+
const refreshToken = await localStorage2.getRefreshToken();
|
|
2279
|
+
const accessTokenExp = await localStorage2.getAccessToken();
|
|
2290
2280
|
isRefreshing = true;
|
|
2291
2281
|
if (!refreshToken && (!browserSession || browserSession == "unActive")) {
|
|
2292
|
-
|
|
2282
|
+
await clearAuthToken();
|
|
2293
2283
|
} else {
|
|
2294
2284
|
const payload = Object.fromEntries(
|
|
2295
2285
|
Object.entries({
|
|
@@ -2300,9 +2290,8 @@ var axiosClient = {
|
|
|
2300
2290
|
}).filter(([_, value]) => !!value)
|
|
2301
2291
|
);
|
|
2302
2292
|
return new Promise(function(resolve) {
|
|
2303
|
-
var _a3;
|
|
2304
2293
|
import_axios.default.post(
|
|
2305
|
-
`${config.baseUrl}${
|
|
2294
|
+
`${config.baseUrl}${config.refreshTokenEndpoint ?? "/authentication/oauth2/token" /* AUTH_TOKEN_PATH */}`,
|
|
2306
2295
|
payload,
|
|
2307
2296
|
{
|
|
2308
2297
|
headers: {
|
|
@@ -2310,10 +2299,10 @@ var axiosClient = {
|
|
|
2310
2299
|
Authorization: `Bearer ${accessTokenExp}`
|
|
2311
2300
|
}
|
|
2312
2301
|
}
|
|
2313
|
-
).then((res) =>
|
|
2302
|
+
).then(async (res) => {
|
|
2314
2303
|
const data = res.data;
|
|
2315
|
-
|
|
2316
|
-
|
|
2304
|
+
await localStorage2.setToken(data.access_token);
|
|
2305
|
+
await localStorage2.setRefreshToken(data.refresh_token);
|
|
2317
2306
|
import_axios.default.defaults.headers.common["Authorization"] = "Bearer " + data.access_token;
|
|
2318
2307
|
originalRequest.headers["Authorization"] = "Bearer " + data.access_token;
|
|
2319
2308
|
originalRequest.data = updateTokenParamInOriginalRequest(
|
|
@@ -2322,26 +2311,25 @@ var axiosClient = {
|
|
|
2322
2311
|
);
|
|
2323
2312
|
processQueue(null, data.access_token);
|
|
2324
2313
|
resolve(instance.request(originalRequest));
|
|
2325
|
-
})
|
|
2326
|
-
|
|
2327
|
-
|
|
2328
|
-
yield clearAuthToken();
|
|
2314
|
+
}).catch(async (err) => {
|
|
2315
|
+
if (err && (err?.error_code === "AUTHEN_FAIL" || err?.error_code === "TOKEN_EXPIRED" || err?.error_code === "TOKEN_INCORRECT" || err?.code === "ERR_BAD_REQUEST") || err?.error_code === "ERR_2FA_006") {
|
|
2316
|
+
await clearAuthToken();
|
|
2329
2317
|
}
|
|
2330
2318
|
if (err && err.response) {
|
|
2331
|
-
const { error_code } =
|
|
2319
|
+
const { error_code } = err.response?.data || {};
|
|
2332
2320
|
if (error_code === "AUTHEN_FAIL") {
|
|
2333
|
-
|
|
2321
|
+
await clearAuthToken();
|
|
2334
2322
|
}
|
|
2335
2323
|
}
|
|
2336
2324
|
processQueue(err, null);
|
|
2337
|
-
})
|
|
2325
|
+
}).finally(() => {
|
|
2338
2326
|
isRefreshing = false;
|
|
2339
2327
|
});
|
|
2340
2328
|
});
|
|
2341
2329
|
}
|
|
2342
2330
|
}
|
|
2343
|
-
return Promise.reject(
|
|
2344
|
-
}
|
|
2331
|
+
return Promise.reject(await handleError3(error));
|
|
2332
|
+
}
|
|
2345
2333
|
);
|
|
2346
2334
|
const handleResponse = (res) => {
|
|
2347
2335
|
if (res && res.data) {
|
|
@@ -2350,7 +2338,6 @@ var axiosClient = {
|
|
|
2350
2338
|
return res;
|
|
2351
2339
|
};
|
|
2352
2340
|
const handleError2 = (error) => {
|
|
2353
|
-
var _a2, _b2, _c;
|
|
2354
2341
|
if (error.isAxiosError && error.code === "ECONNABORTED") {
|
|
2355
2342
|
console.error("Request Timeout Error:", error);
|
|
2356
2343
|
return "Request Timeout Error";
|
|
@@ -2358,17 +2345,17 @@ var axiosClient = {
|
|
|
2358
2345
|
console.error("Network Error:", error);
|
|
2359
2346
|
return "Network Error";
|
|
2360
2347
|
} else {
|
|
2361
|
-
console.error("Other Error:", error
|
|
2362
|
-
const errorMessage =
|
|
2363
|
-
return { message: errorMessage, status:
|
|
2348
|
+
console.error("Other Error:", error?.response);
|
|
2349
|
+
const errorMessage = error?.response?.data?.message || "An error occurred";
|
|
2350
|
+
return { message: errorMessage, status: error?.response?.status };
|
|
2364
2351
|
}
|
|
2365
2352
|
};
|
|
2366
|
-
const clearAuthToken = () =>
|
|
2367
|
-
|
|
2353
|
+
const clearAuthToken = async () => {
|
|
2354
|
+
await localStorage2.clearToken();
|
|
2368
2355
|
if (typeof window !== "undefined") {
|
|
2369
2356
|
window.location.href = `/login`;
|
|
2370
2357
|
}
|
|
2371
|
-
}
|
|
2358
|
+
};
|
|
2372
2359
|
function formatUrl(url, db2) {
|
|
2373
2360
|
return url + (db2 ? "?db=" + db2 : "");
|
|
2374
2361
|
}
|