login-authorization-v2 1.1.5 → 2.0.0-beta.10

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 CHANGED
@@ -1,55 +1,53 @@
1
- # login-authorization
2
-
3
- > 登录验证
4
- ## 安装依赖
5
-
6
- ``` bash
7
- # install dependencies
8
- npm install login-authorization --save
9
- # or with yarn
10
- yarn add login-authorization
11
- ```
12
- ## 方法使用说明
13
- ### 初始化:init(requestUrl, loginUrl, systemName) 此方法必须在入口文件中调用
14
- ```bash
15
- import { init } from 'login-authorization';
16
-
17
- init('http://127.0.0.1','http://127.0.0.1/#/login?systemName=Finance', 'Finance').then(res => {
18
- if (res) {
19
- // true 已登录
20
- } else {
21
- // false 未登录
22
- }
23
- })
24
-
25
- 注意:systemName必须和Cognito中配置的系统组名保持一致。
26
-
27
- ```
28
- <font color=#ff0000 size=24>注意:凡是涉及到统一登录系统的loginUrl后面必须将你的系统名称带上,且参数名称为systemName,如果未涉及则不用。</font>
29
- ### 登录成功时需要设置idToken和refreshToken初始值
30
- setIdToken(value)
31
- setRefreshToken(value)
32
- ### 获取idToken:getIdToken()
33
- ```bash
34
- import { getIdToken } from 'login-authorization';
35
-
36
- let idToken = getIdToken(); // 'xxxxxx',如果未登录则为null
37
- ```
38
- ### 获取用户信息:getUserInfo()
39
- ```bash
40
- import { getUserInfo } from 'login-authorization';
41
-
42
- let userInfo = getUserInfo(); //{email: 'xxx', name: 'xxx',...},如果未登录则为null
43
- ```
44
- ### 登出:logout()
45
- ```bash
46
- import { logout } from 'login-authorization';
47
-
48
- logout().then(res => {
49
- if (res) {
50
- // true 登出成功,会自动跳转到登录页面
51
- } else {
52
- // false 登出失败
53
- }
54
- })
55
- ```
1
+ # login-authorization-v2
2
+
3
+ ## 安装
4
+ ```bash
5
+ #npm
6
+ npm install login-authorization-v2
7
+
8
+ #yarn
9
+ yarn add login-authorization-v2
10
+ ```
11
+
12
+ ## 使用文档
13
+ ### 基本使用
14
+ ```javascript
15
+ import { make } from 'login-authorization-v2'
16
+
17
+ const { init, logout } = make({
18
+ moduleName: 'Portal', // 当前模块名称
19
+ moduleBaseUrl: 'https://servers-api.gztest.net:8107', // 后端的 module_base 服务地址
20
+ loginPageUrl: 'http://huangcheng.ddmarketinghub.com:8080', // 如果未登录,跳转的登录页地址
21
+ })
22
+
23
+ init({ brand: 1, tenantId: 1 }).then(menus => {
24
+ // menus 即为当前用户的菜单权限数据
25
+ }).catch(err => {
26
+ // 任何不能正常登陆的情况都会进入这里
27
+ })
28
+
29
+ logout().then(() => {
30
+ // 退出登陆成功
31
+ }).catch(() => {
32
+ // 可以不用管
33
+ })
34
+ ```
35
+ > tenantId、brand、moduleName 枚举值可以在 login-authorization-v2 包内的 `./dist/src/types.d.ts` 文件中查看
36
+
37
+ ### 新增方法
38
+ #### main
39
+ 1. make(options: MakeFnParams): { init, logout }
40
+ 2. init(params: InitParams): Promise<MenuItem[]>
41
+ 3. logout(): Promise<void>
42
+
43
+ #### cookie 相关方法
44
+ 1. setAccessToken(string | null): void
45
+ 2. getAccessToken(): string | undefined
46
+ 3. setRefreshToken(string | null): void
47
+ 4. getRefreshToken(): string | undefined
48
+ 5. setSystemType(string | null): void
49
+ 6. getSystemType(): string | undefined
50
+
51
+ #### 工具函数
52
+ 1. isMobile(): boolean // 判断当前环境是否为移动端
53
+ 2. getUserInfo(): Promise<UserInfo | null> // 获取当前用户信息
@@ -0,0 +1,25 @@
1
+ export * from './src/cookie';
2
+ export * from './src/compatible';
3
+ export * from './src/utils';
4
+ import { Brand, type ModuleName, Tenant } from './src/types';
5
+ type MakeFnParams = {
6
+ moduleName: ModuleName;
7
+ moduleBaseUrl: string;
8
+ loginPageUrl: string;
9
+ };
10
+ type InitFnParams = {
11
+ brand?: Brand;
12
+ tenantId: Tenant;
13
+ };
14
+ export declare const make: (config: MakeFnParams) => {
15
+ init: (initConfig: InitFnParams) => Promise<{
16
+ groupName: ModuleName;
17
+ icon: string;
18
+ id: number;
19
+ label: string;
20
+ staffEndpoint: boolean;
21
+ url: string;
22
+ }[]>;
23
+ logout: () => Promise<import("axios").AxiosResponse<any, any>>;
24
+ };
25
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../index.ts"],"names":[],"mappings":"AAAA,cAAc,cAAc,CAAA;AAC5B,cAAc,kBAAkB,CAAA;AAChC,cAAc,aAAa,CAAA;AAO3B,OAAO,EAAE,KAAK,EAAE,KAAK,UAAU,EAAc,MAAM,EAAiB,MAAM,aAAa,CAAA;AAGvF,KAAK,YAAY,GAAG;IAClB,UAAU,EAAE,UAAU,CAAA;IACtB,aAAa,EAAE,MAAM,CAAC;IACtB,YAAY,EAAE,MAAM,CAAA;CACrB,CAAA;AAED,KAAK,YAAY,GAAG;IAClB,KAAK,CAAC,EAAE,KAAK,CAAA;IACb,QAAQ,EAAE,MAAM,CAAA;CACjB,CAAA;AAED,eAAO,MAAM,IAAI,GAAI,QAAQ,YAAY;uBAUb,YAAY;;;;;;;;;CAmIvC,CAAA"}
@@ -0,0 +1,406 @@
1
+ import Cookie from 'js-cookie';
2
+ import { Base64 } from 'js-base64';
3
+ import axios from 'axios';
4
+
5
+ /******************************************************************************
6
+ Copyright (c) Microsoft Corporation.
7
+
8
+ Permission to use, copy, modify, and/or distribute this software for any
9
+ purpose with or without fee is hereby granted.
10
+
11
+ THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH
12
+ REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
13
+ AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,
14
+ INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
15
+ LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
16
+ OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
17
+ PERFORMANCE OF THIS SOFTWARE.
18
+ ***************************************************************************** */
19
+ /* global Reflect, Promise, SuppressedError, Symbol, Iterator */
20
+
21
+
22
+ function __awaiter(thisArg, _arguments, P, generator) {
23
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
24
+ return new (P || (P = Promise))(function (resolve, reject) {
25
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
26
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
27
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
28
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
29
+ });
30
+ }
31
+
32
+ typeof SuppressedError === "function" ? SuppressedError : function (error, suppressed, message) {
33
+ var e = new Error(message);
34
+ return e.name = "SuppressedError", e.error = error, e.suppressed = suppressed, e;
35
+ };
36
+
37
+ const NO_ACCESS_TOKEN = 'Access token not found';
38
+ const INVALID_ACCESS_TOKEN = 'Invalid access token';
39
+ const INVALID_REFRESH_TOKEN = 'Invalid refresh token';
40
+ const NO_REFRESH_TOKEN = 'Refresh token not found';
41
+ const NO_MODULE_BASE_URL = 'Module base URL is required';
42
+ const INVALID_TENANT_ID = 'Invalid tenant ID';
43
+ const INVALID_BRAND = 'Invalid brand';
44
+
45
+ const makeSetCookieFn = (key, options) => {
46
+ const index = window.location.hostname.indexOf('.');
47
+ const domain = index === -1
48
+ ? window.location.hostname
49
+ : window.location.hostname.slice(index);
50
+ return (value) => {
51
+ if (value === null) {
52
+ return Cookie.remove(key, Object.assign({ domain }, options));
53
+ }
54
+ Cookie.set(key, value, Object.assign({ domain, expires: 30 }, options));
55
+ };
56
+ };
57
+ const setIdTokenFront = makeSetCookieFn('idTokenFront');
58
+ const setIdTokenBack = makeSetCookieFn('idTokenBack');
59
+ const setRefreshTokenFront = makeSetCookieFn('refreshTokenFront');
60
+ const setRefreshTokenBack = makeSetCookieFn('refreshTokenBack');
61
+ const setRefreshToken = (token) => {
62
+ if (!token) {
63
+ setIdTokenBack(null);
64
+ setIdTokenFront(null);
65
+ makeSetCookieFn('refresh_token')(null);
66
+ return;
67
+ }
68
+ const splits = token.split('.');
69
+ if (splits.length < 5)
70
+ throw new Error(INVALID_REFRESH_TOKEN);
71
+ const refreshTokenFront = splits[0] + '.' + splits[1];
72
+ const refreshTokenBack = splits[2] + '.' + splits[3] + '.' + splits[4];
73
+ setRefreshTokenFront(refreshTokenFront);
74
+ setRefreshTokenBack(refreshTokenBack);
75
+ makeSetCookieFn('refresh_token')(token);
76
+ };
77
+ const setAccessToken = (token) => {
78
+ if (!token) {
79
+ setIdTokenBack(null);
80
+ setIdTokenFront(null);
81
+ makeSetCookieFn('access_token')(null);
82
+ return;
83
+ }
84
+ const splits = token.split('.');
85
+ if (splits.length < 3)
86
+ throw new Error(INVALID_ACCESS_TOKEN);
87
+ const idTokenFront = splits[0] + '.' + splits[1];
88
+ const idTokenBack = splits[2] || '';
89
+ setIdTokenFront(idTokenFront);
90
+ setIdTokenBack(idTokenBack);
91
+ makeSetCookieFn('access_token')(token);
92
+ };
93
+ const getAccessToken = () => Cookie.get('access_token');
94
+ const getRefreshToken = () => Cookie.get('refresh_token');
95
+ const setSystemType = makeSetCookieFn('currentSystemType');
96
+ const getSystemType = () => Cookie.get('currentSystemType');
97
+
98
+ /**
99
+ * 这个文件是写一些兼容的方法,避免各个项目做出大量调整
100
+ */
101
+ const setIdToken = setAccessToken;
102
+ const getIdToken = getAccessToken;
103
+ const setCookie = (name, value, domain, path = '/', time = 30 * 24 * 60 * 60 * 1000) => {
104
+ if (value === null || value === undefined) {
105
+ return Cookie.remove(name);
106
+ }
107
+ Cookie.set(name, value, {
108
+ domain,
109
+ path,
110
+ expires: time / (24 * 60 * 60 * 1000)
111
+ });
112
+ };
113
+ const clearLoginCookie = () => {
114
+ setAccessToken(null);
115
+ setRefreshToken(null);
116
+ };
117
+ const getCookie = (c_name) => {
118
+ if (!c_name)
119
+ return null;
120
+ const reg = new RegExp('(?:^|; )' + encodeURIComponent(c_name) + '=([^;]*)');
121
+ const result = reg.exec(document.cookie);
122
+ return result ? decodeURIComponent(result[1] || '') : null;
123
+ };
124
+ const getUrlParam = (key, href) => {
125
+ const search = '?' + ((href || window.location.href).split('?')[1] || '');
126
+ const searchParams = new URLSearchParams(search);
127
+ return searchParams.get(key);
128
+ };
129
+
130
+ const isMobile = () => {
131
+ const ua = navigator.userAgent;
132
+ return /Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test(ua);
133
+ };
134
+ const getUserInfo = () => {
135
+ return new Promise((resolve, reject) => {
136
+ const token = getAccessToken();
137
+ if (!token)
138
+ return reject(new Error(NO_ACCESS_TOKEN));
139
+ const splits = token.split('.');
140
+ if (splits.length < 3)
141
+ return reject(new Error(NO_ACCESS_TOKEN));
142
+ resolve(JSON.parse(Base64.decode(splits[1])));
143
+ });
144
+ };
145
+
146
+ var Brand;
147
+ (function (Brand) {
148
+ Brand[Brand["ZERO"] = 1] = "ZERO";
149
+ Brand[Brand["HEDGEHOOD"] = 2] = "HEDGEHOOD";
150
+ Brand[Brand["NISE"] = 3] = "NISE";
151
+ })(Brand || (Brand = {}));
152
+ var Tenant;
153
+ (function (Tenant) {
154
+ Tenant[Tenant["ZERO_INT"] = 1] = "ZERO_INT";
155
+ Tenant[Tenant["HEDGEHOOD"] = 2] = "HEDGEHOOD";
156
+ Tenant[Tenant["ZERO_NZ"] = 3] = "ZERO_NZ";
157
+ Tenant[Tenant["ZERO_LA"] = 4] = "ZERO_LA";
158
+ Tenant[Tenant["ZERO_BR"] = 4] = "ZERO_BR";
159
+ Tenant[Tenant["NISE_EU"] = 5] = "NISE_EU";
160
+ })(Tenant || (Tenant = {}));
161
+ var SystemType;
162
+ (function (SystemType) {
163
+ SystemType["Staff"] = "staff";
164
+ SystemType["Client"] = "client";
165
+ })(SystemType || (SystemType = {}));
166
+
167
+ let tenantId;
168
+ let brand;
169
+ let moduleBaseUrl = '';
170
+ let loginPageUrl = '';
171
+ const setTenantId = (id) => {
172
+ if (!Object.values(Tenant).includes(id)) {
173
+ throw new Error(INVALID_TENANT_ID);
174
+ }
175
+ tenantId = id;
176
+ };
177
+ const setBrand = (id) => {
178
+ if (!Object.values(Brand).includes(id)) {
179
+ throw new Error(INVALID_BRAND);
180
+ }
181
+ brand = id;
182
+ };
183
+ const setModuleBaseUrl = (url) => {
184
+ moduleBaseUrl = url;
185
+ };
186
+ const setLoginPageUrl = (url) => {
187
+ loginPageUrl = url;
188
+ };
189
+
190
+ const createPcDialog = () => {
191
+ return `<div id="confirm-container" style="box-sizing:border-box;position:fixed;width:615px;height:145px;box-shadow: 0 0 2px 2px #eeeeee;border-radius: 5px;z-index: 10000000;display: block;left: 35%;padding:20px 20px;top:10px;font-size: 16px;">
192
+ <div id="href" style="color: rgb(32,33,36);"></div>
193
+ <div style="margin: 10px 0 20px 0;color: rgb(32,33,36);font-size: 14px;">You do not have access to the system.</div>
194
+ <div style="display: flex;justify-content: flex-end;">
195
+ <button id="cancel" style="padding: 8px 15px;background: #ffffff;color:rgb(26,115,232);border:1px solid #ccc;border-radius:5px;cursor: pointer;font-size:14px;">Cancel</button>
196
+ <button id="confirm" style="padding: 8px 15px;background: rgb(26,115,232);color:#ffffff;border:none;border-radius:5px;margin-left: 10px;cursor: pointer;font-size:14px;">Sign in to another ZERO account</button>
197
+ </div>
198
+ </div>`;
199
+ };
200
+ const createMobileDialog = () => {
201
+ return `<div id="confirm-container" style="box-sizing:border-box;position:fixed;width:97.6vw;height:145px;box-shadow: 0 0 2px 2px #eeeeee;border-radius: 5px;z-index: 10000000;display: block;left:0px;padding:20px 20px;top:4px;margin:0 4px;font-size: 16px;">
202
+ <div id="href" style="color: rgb(32,33,36);"></div>
203
+ <div style="margin: 10px 0 20px 0;color: rgb(32,33,36);font-size: 14px;">You do not have access to the system.</div>
204
+ <div style="display: flex;justify-content: flex-end;">
205
+ <div style="display: flex;justify-content: flex-end;">
206
+ <button id="cancel" style="padding: 8px 15px;background: #ffffff;color:rgb(26,115,232);border:1px solid #ccc;border-radius:5px;cursor: pointer;font-size:14px;">Cancel</button>
207
+ <button id="confirm" style="padding: 8px 15px;background: rgb(26,115,232);color:#ffffff;border:none;border-radius:5px;margin-left: 10px;cursor: pointer;font-size:14px;">Sign in to another ZERO account</button>
208
+ </div>
209
+ </div>
210
+ </div>`;
211
+ };
212
+ const onConfirmHandler = (evt) => {
213
+ closeDialog();
214
+ window.location.href = loginPageUrl;
215
+ };
216
+ const onCancelHandler = () => {
217
+ closeDialog();
218
+ window.location.href = 'about:blank';
219
+ };
220
+ const closeDialog = () => {
221
+ const container = document.getElementById('confirm-container');
222
+ if (!container || !container.parentNode)
223
+ return;
224
+ document.body.removeChild(container.parentNode);
225
+ };
226
+ const openDialog = () => {
227
+ const container = document.createElement('div');
228
+ isMobile()
229
+ ? container.innerHTML = createMobileDialog()
230
+ : container.innerHTML = createPcDialog();
231
+ const confirmButton = container.querySelector('#confirm');
232
+ const cancelButton = container.querySelector('#cancel');
233
+ confirmButton === null || confirmButton === void 0 ? void 0 : confirmButton.addEventListener('click', onConfirmHandler);
234
+ cancelButton === null || cancelButton === void 0 ? void 0 : cancelButton.addEventListener('click', onCancelHandler);
235
+ document.body.appendChild(container);
236
+ };
237
+
238
+ let instance;
239
+ /**
240
+ * 没找到更好的方式,只能这样做了
241
+ */
242
+ const initInstance = () => __awaiter(void 0, void 0, void 0, function* () {
243
+ let userInfo = null;
244
+ try {
245
+ userInfo = yield getUserInfo();
246
+ }
247
+ catch (error) {
248
+ console.warn('initInstance getUserInfo error:', error);
249
+ }
250
+ instance = axios.create({
251
+ baseURL: moduleBaseUrl,
252
+ timeout: 1.5e4,
253
+ });
254
+ instance.interceptors.request.use((config) => {
255
+ config.headers = Object.assign(Object.assign({}, config.headers), { 'X-tenant-id': userInfo ? userInfo['custom:tenant_id'].toString() : tenantId.toString(), 'X-brand': brand.toString(), 'Authorization': `Bearer ${getAccessToken()}` });
256
+ return config;
257
+ }, (error) => {
258
+ return Promise.reject(error);
259
+ });
260
+ instance.interceptors.response.use((response) => {
261
+ if (response.data.code !== 200) {
262
+ return Promise.reject(response.data.msg);
263
+ }
264
+ return response;
265
+ }, (error) => {
266
+ return Promise.reject(error);
267
+ });
268
+ });
269
+ const fetchRefreshTokenHTTP = (refreshToken) => {
270
+ return instance({
271
+ method: 'post',
272
+ url: '/user-profile/refresh-token/refresh',
273
+ data: {
274
+ refreshToken
275
+ }
276
+ });
277
+ };
278
+ const fetchLogoutHTTP = () => {
279
+ return instance({
280
+ method: 'get',
281
+ url: '/user-profile/logout'
282
+ });
283
+ };
284
+ const fetchServerListHTTP = () => {
285
+ return instance({
286
+ method: 'get',
287
+ url: '/session/current/servers'
288
+ });
289
+ };
290
+
291
+ const make = (config) => {
292
+ if (!config.moduleBaseUrl) {
293
+ throw new Error(NO_MODULE_BASE_URL);
294
+ }
295
+ let timer = undefined;
296
+ setModuleBaseUrl(config.moduleBaseUrl);
297
+ setLoginPageUrl(config.loginPageUrl);
298
+ initInstance();
299
+ const init = (initConfig) => {
300
+ setTenantId(initConfig.tenantId);
301
+ setBrand(initConfig.brand || Brand.ZERO);
302
+ const token = getAccessToken();
303
+ const refreshToken = getRefreshToken();
304
+ if (!token) {
305
+ setAccessToken(null);
306
+ setRefreshToken(null);
307
+ return Promise.reject(new Error(NO_ACCESS_TOKEN));
308
+ }
309
+ if (!refreshToken) {
310
+ setAccessToken(null);
311
+ setRefreshToken(null);
312
+ return Promise.reject(new Error(NO_REFRESH_TOKEN));
313
+ }
314
+ return getUserInfo()
315
+ .then((userInfo) => __awaiter(void 0, void 0, void 0, function* () {
316
+ const valid = detectUserInfoGroupAuth(userInfo);
317
+ if (!valid) {
318
+ return Promise.reject();
319
+ }
320
+ return fetchServerListHTTP();
321
+ }))
322
+ .then(resp => {
323
+ const menus = resp.data.content || [];
324
+ const group = menus.find(menu => menu.groupName === config.moduleName);
325
+ if (menus.length <= 0) {
326
+ openDialog();
327
+ return Promise.reject();
328
+ }
329
+ if (config.moduleName === 'commonLogin') {
330
+ setupRefreshTokenTimer();
331
+ return Promise.resolve(menus);
332
+ }
333
+ if (!group) {
334
+ openDialog();
335
+ return Promise.reject();
336
+ }
337
+ setSystemType(group.staffEndpoint ? SystemType.Staff : SystemType.Client);
338
+ setupRefreshTokenTimer();
339
+ return Promise.resolve(menus);
340
+ })
341
+ .catch((error) => __awaiter(void 0, void 0, void 0, function* () {
342
+ clearRefreshTokenTimer();
343
+ setAccessToken(null);
344
+ setRefreshToken(null);
345
+ yield logout();
346
+ throw error;
347
+ }));
348
+ };
349
+ const detectUserInfoGroupAuth = (userInfo) => {
350
+ const groups = userInfo['cognito:groups'] || [];
351
+ if (!groups.includes(config.moduleName)
352
+ && config.moduleName !== 'commonLogin'
353
+ && config.moduleName !== 'App') {
354
+ return false;
355
+ }
356
+ return true;
357
+ };
358
+ const setupRefreshTokenTimer = () => {
359
+ const refreshToken = getRefreshToken();
360
+ if (!refreshToken)
361
+ return;
362
+ if (timer) {
363
+ clearInterval(timer);
364
+ }
365
+ timer = setInterval(() => {
366
+ fetchRefreshTokenHTTP(refreshToken)
367
+ .then(resp => {
368
+ const { content: { idToken } } = resp.data;
369
+ setAccessToken(idToken);
370
+ return getUserInfo();
371
+ })
372
+ .then(userInfo => {
373
+ const valid = detectUserInfoGroupAuth(userInfo);
374
+ if (!valid) {
375
+ clearRefreshTokenTimer();
376
+ openDialog();
377
+ return logout();
378
+ }
379
+ })
380
+ .catch(error => {
381
+ clearRefreshTokenTimer();
382
+ throw error;
383
+ });
384
+ }, 1e3 * 60 * 3); // 3 minutes
385
+ };
386
+ const logout = () => {
387
+ return fetchLogoutHTTP()
388
+ .finally(() => {
389
+ clearRefreshTokenTimer();
390
+ setAccessToken(null);
391
+ setRefreshToken(null);
392
+ });
393
+ };
394
+ const clearRefreshTokenTimer = () => {
395
+ if (!timer)
396
+ return;
397
+ clearInterval(timer);
398
+ timer = null;
399
+ };
400
+ return {
401
+ init,
402
+ logout
403
+ };
404
+ };
405
+
406
+ export { clearLoginCookie, getAccessToken, getCookie, getIdToken, getRefreshToken, getSystemType, getUrlParam, getUserInfo, isMobile, make, setAccessToken, setCookie, setIdToken, setRefreshToken, setSystemType };