@pnt-team/pnt-component-frontend 0.0.136 → 0.0.138
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/lib/cjs/components/PntRegionSelect/index.scss +14 -10
- package/package.json +1 -1
- package/lib/cjs/api/cos.d.ts +0 -103
- package/lib/cjs/api/cos.js +0 -146
- package/lib/cjs/api/index.d.ts +0 -23
- package/lib/cjs/api/index.js +0 -38
- package/lib/cjs/api/types/index.d.ts +0 -117
- package/lib/cjs/api/types/index.js +0 -17
- package/lib/cjs/assets/css/tdesign-theme.css +0 -584
- package/lib/cjs/assets/images/uploadImg.png +0 -0
- package/lib/cjs/assets/svg/inputSearch.svg +0 -4
- package/lib/cjs/assets/svg/inputTip.svg +0 -5
- package/lib/esm/api/cos.d.ts +0 -103
- package/lib/esm/api/cos.js +0 -189
- package/lib/esm/api/index.d.ts +0 -23
- package/lib/esm/api/index.js +0 -23
- package/lib/esm/api/types/index.d.ts +0 -117
- package/lib/esm/api/types/index.js +0 -1
- package/lib/esm/assets/css/tdesign-theme.css +0 -584
- package/lib/esm/assets/images/uploadImg.png +0 -0
- package/lib/esm/assets/svg/inputSearch.svg +0 -4
- package/lib/esm/assets/svg/inputTip.svg +0 -5
- package/lib/esm/assets/svg/inputWarnTip.svg +0 -5
- package/lib/esm/components/PntBusinessSelect/index.d.ts +0 -192
- package/lib/esm/components/PntBusinessSelect/index.js +0 -513
- package/lib/esm/components/PntBusinessSelect/index.scss +0 -27
- package/lib/esm/components/PntCosUploader/index.d.ts +0 -134
- package/lib/esm/components/PntCosUploader/index.js +0 -300
- package/lib/esm/components/PntGeneralLayout/index.d.ts +0 -114
- package/lib/esm/components/PntGeneralLayout/index.js +0 -103
- package/lib/esm/components/PntGeneralLayout/index.scss +0 -121
- package/lib/esm/components/PntImage/index.d.ts +0 -93
- package/lib/esm/components/PntImage/index.js +0 -200
- package/lib/esm/components/PntImage/index.scss +0 -61
- package/lib/esm/components/PntRegionSelect/ImportDialog.d.ts +0 -29
- package/lib/esm/components/PntRegionSelect/ImportDialog.js +0 -244
- package/lib/esm/components/PntRegionSelect/index.d.ts +0 -39
- package/lib/esm/components/PntRegionSelect/index.js +0 -471
- package/lib/esm/components/PntRegionSelect/index.scss +0 -170
- package/lib/esm/components/PntRegionSelect/types.d.ts +0 -181
- package/lib/esm/components/PntRegionSelect/types.js +0 -77
- package/lib/esm/components/PntSecureBox/index.d.ts +0 -122
- package/lib/esm/components/PntSecureBox/index.js +0 -166
- package/lib/esm/components/PntSecureBox/index.scss +0 -23
- package/lib/esm/components/PntTable/index.d.ts +0 -14
- package/lib/esm/components/PntTable/index.js +0 -404
- package/lib/esm/components/PntTable/index.scss +0 -290
- package/lib/esm/components/PntTable/types.d.ts +0 -250
- package/lib/esm/components/PntTable/types.js +0 -81
- package/lib/esm/components/PntTable/useTableCore.d.ts +0 -38
- package/lib/esm/components/PntTable/useTableCore.js +0 -499
- package/lib/esm/components/PntUpload/index.d.ts +0 -149
- package/lib/esm/components/PntUpload/index.js +0 -276
- package/lib/esm/components/PntUpload/index.scss +0 -101
- package/lib/esm/config.d.ts +0 -97
- package/lib/esm/config.js +0 -60
- package/lib/esm/global.css +0 -2
- package/lib/esm/global.d.ts +0 -39
- package/lib/esm/hooks/useHighSecurity.d.ts +0 -88
- package/lib/esm/hooks/useHighSecurity.js +0 -250
- package/lib/esm/index.d.ts +0 -16
- package/lib/esm/index.js +0 -33
- package/lib/esm/utils/const.d.ts +0 -13
- package/lib/esm/utils/const.js +0 -23
- package/lib/esm/utils/index.d.ts +0 -6
- package/lib/esm/utils/index.js +0 -22
- package/lib/umd/pnt-component-frontend.min.css +0 -1
- package/lib/umd/pnt-component-frontend.min.js +0 -1
|
@@ -1,276 +0,0 @@
|
|
|
1
|
-
import usePntCosUploader from "../PntCosUploader";
|
|
2
|
-
import PntImage from "../PntImage";
|
|
3
|
-
import React, { useMemo, useState } from 'react';
|
|
4
|
-
import { DeleteIcon, FileIcon, UploadIcon } from 'tdesign-icons-react';
|
|
5
|
-
import { Progress, Upload } from 'tdesign-react';
|
|
6
|
-
import "./index.scss";
|
|
7
|
-
|
|
8
|
-
// ==========================================
|
|
9
|
-
// 类型定义
|
|
10
|
-
// ==========================================
|
|
11
|
-
|
|
12
|
-
/**
|
|
13
|
-
* PntUpload 文案集合
|
|
14
|
-
* @description 所有内部展示文案均可通过 texts prop 自定义,用于多语言场景
|
|
15
|
-
*/
|
|
16
|
-
|
|
17
|
-
/**
|
|
18
|
-
* 校验/上传失败阶段
|
|
19
|
-
*/
|
|
20
|
-
import { jsx as _jsx } from "react/jsx-runtime";
|
|
21
|
-
import { jsxs as _jsxs } from "react/jsx-runtime";
|
|
22
|
-
// ==========================================
|
|
23
|
-
// 常量与工具
|
|
24
|
-
// ==========================================
|
|
25
|
-
|
|
26
|
-
const DEFAULT_TEXTS = {
|
|
27
|
-
uploading: '上传中',
|
|
28
|
-
uploadFailed: '上传失败,请重试',
|
|
29
|
-
sizeInvalid: '文件大小超出限制',
|
|
30
|
-
typeInvalid: '文件类型不支持',
|
|
31
|
-
selectFile: '选择文件',
|
|
32
|
-
reselect: '重新选择'
|
|
33
|
-
};
|
|
34
|
-
|
|
35
|
-
/**
|
|
36
|
-
* 将 accept 归一化为小写 token 列表
|
|
37
|
-
*/
|
|
38
|
-
const toAcceptList = accept => {
|
|
39
|
-
const raw = Array.isArray(accept) ? accept : accept ? accept.split(',') : [];
|
|
40
|
-
return raw.map(item => item.trim().toLowerCase()).filter(Boolean);
|
|
41
|
-
};
|
|
42
|
-
|
|
43
|
-
/**
|
|
44
|
-
* 校验文件类型是否匹配 accept
|
|
45
|
-
*/
|
|
46
|
-
const matchAccept = (file, acceptList) => {
|
|
47
|
-
if (!acceptList.length) {
|
|
48
|
-
return true;
|
|
49
|
-
}
|
|
50
|
-
const name = file.name.toLowerCase();
|
|
51
|
-
const type = file.type.toLowerCase();
|
|
52
|
-
return acceptList.some(token => {
|
|
53
|
-
if (token.startsWith('.')) {
|
|
54
|
-
return name.endsWith(token);
|
|
55
|
-
}
|
|
56
|
-
if (token.endsWith('/*')) {
|
|
57
|
-
return !!type && type.startsWith(token.slice(0, -1));
|
|
58
|
-
}
|
|
59
|
-
return type === token;
|
|
60
|
-
});
|
|
61
|
-
};
|
|
62
|
-
|
|
63
|
-
/** 从 URL 中提取文件名(用于编辑态回显) */
|
|
64
|
-
const getFileNameFromUrl = url => {
|
|
65
|
-
if (!url) {
|
|
66
|
-
return '';
|
|
67
|
-
}
|
|
68
|
-
const lastSeg = url.split('?')[0].split('/').pop() || '';
|
|
69
|
-
try {
|
|
70
|
-
return decodeURIComponent(lastSeg);
|
|
71
|
-
} catch {
|
|
72
|
-
return lastSeg;
|
|
73
|
-
}
|
|
74
|
-
};
|
|
75
|
-
|
|
76
|
-
// ==========================================
|
|
77
|
-
// PntUpload 组件
|
|
78
|
-
// ==========================================
|
|
79
|
-
|
|
80
|
-
/**
|
|
81
|
-
* PntUpload 业务上传组件
|
|
82
|
-
* @description 基于 TDesign Upload + PntImage + usePntCosUploader,
|
|
83
|
-
* 内置 COS 凭证获取、直传、进度、校验、错误处理;支持图片预览 / 文件两种模式
|
|
84
|
-
*
|
|
85
|
-
* @example
|
|
86
|
-
* ```tsx
|
|
87
|
-
* <PntUpload
|
|
88
|
-
* scene="default"
|
|
89
|
-
* pathKey="marketing_icon"
|
|
90
|
-
* context={{ gameId }}
|
|
91
|
-
* accept="image/png"
|
|
92
|
-
* sizeLimit={500 * 1024}
|
|
93
|
-
* imagePreview
|
|
94
|
-
* value={iconUrl}
|
|
95
|
-
* onChange={(url) => setIconUrl(url)}
|
|
96
|
-
* onRemove={() => setIconUrl('')}
|
|
97
|
-
* />
|
|
98
|
-
* ```
|
|
99
|
-
*/
|
|
100
|
-
const PntUpload = ({
|
|
101
|
-
value,
|
|
102
|
-
onChange,
|
|
103
|
-
onRemove,
|
|
104
|
-
onError,
|
|
105
|
-
scene,
|
|
106
|
-
pathKey,
|
|
107
|
-
context,
|
|
108
|
-
audience,
|
|
109
|
-
accept,
|
|
110
|
-
sizeLimit,
|
|
111
|
-
imagePreview = true,
|
|
112
|
-
previewStyle,
|
|
113
|
-
defaultImg,
|
|
114
|
-
fileNameStrategy,
|
|
115
|
-
useCdn,
|
|
116
|
-
getCredential,
|
|
117
|
-
normalizeCredential,
|
|
118
|
-
texts,
|
|
119
|
-
disabled = false,
|
|
120
|
-
style,
|
|
121
|
-
className
|
|
122
|
-
}) => {
|
|
123
|
-
const [uploading, setUploading] = useState(false);
|
|
124
|
-
const [percent, setPercent] = useState(0);
|
|
125
|
-
const [errorText, setErrorText] = useState('');
|
|
126
|
-
const [lastFile, setLastFile] = useState(null);
|
|
127
|
-
const finalTexts = useMemo(() => ({
|
|
128
|
-
...DEFAULT_TEXTS,
|
|
129
|
-
...texts
|
|
130
|
-
}), [texts]);
|
|
131
|
-
const acceptList = useMemo(() => toAcceptList(accept), [accept]);
|
|
132
|
-
const acceptString = useMemo(() => acceptList.join(', '), [acceptList]);
|
|
133
|
-
const uploader = usePntCosUploader({
|
|
134
|
-
scene,
|
|
135
|
-
pathKey,
|
|
136
|
-
context,
|
|
137
|
-
audience,
|
|
138
|
-
fileNameStrategy,
|
|
139
|
-
useCdn,
|
|
140
|
-
getCredential,
|
|
141
|
-
normalizeCredential
|
|
142
|
-
});
|
|
143
|
-
const reportError = (message, phase, file) => {
|
|
144
|
-
setErrorText(message);
|
|
145
|
-
onError?.(new Error(message), phase, file);
|
|
146
|
-
};
|
|
147
|
-
|
|
148
|
-
/**
|
|
149
|
-
* 自定义上传:TDesign 选好文件后回调,内部完成校验 + COS 直传
|
|
150
|
-
*/
|
|
151
|
-
const requestMethod = async files => {
|
|
152
|
-
const tdFile = Array.isArray(files) ? files[0] : files;
|
|
153
|
-
const file = tdFile?.raw;
|
|
154
|
-
if (!file) {
|
|
155
|
-
return {
|
|
156
|
-
status: 'fail',
|
|
157
|
-
error: 'no file',
|
|
158
|
-
response: {}
|
|
159
|
-
};
|
|
160
|
-
}
|
|
161
|
-
|
|
162
|
-
// 1. 本地校验:类型 / 大小
|
|
163
|
-
if (!matchAccept(file, acceptList)) {
|
|
164
|
-
reportError(finalTexts.typeInvalid, 'validate', file);
|
|
165
|
-
return {
|
|
166
|
-
status: 'fail',
|
|
167
|
-
error: finalTexts.typeInvalid,
|
|
168
|
-
response: {}
|
|
169
|
-
};
|
|
170
|
-
}
|
|
171
|
-
if (typeof sizeLimit === 'number' && file.size > sizeLimit) {
|
|
172
|
-
reportError(finalTexts.sizeInvalid, 'validate', file);
|
|
173
|
-
return {
|
|
174
|
-
status: 'fail',
|
|
175
|
-
error: finalTexts.sizeInvalid,
|
|
176
|
-
response: {}
|
|
177
|
-
};
|
|
178
|
-
}
|
|
179
|
-
|
|
180
|
-
// 2. COS 直传
|
|
181
|
-
setUploading(true);
|
|
182
|
-
setPercent(0);
|
|
183
|
-
setErrorText('');
|
|
184
|
-
try {
|
|
185
|
-
const result = await uploader.upload(file, setPercent);
|
|
186
|
-
setLastFile(file);
|
|
187
|
-
onChange?.(result.fileUrl, result.cosKey, file);
|
|
188
|
-
return {
|
|
189
|
-
status: 'success',
|
|
190
|
-
response: {
|
|
191
|
-
url: result.fileUrl
|
|
192
|
-
}
|
|
193
|
-
};
|
|
194
|
-
} catch (e) {
|
|
195
|
-
const err = e instanceof Error ? e : new Error(String(e));
|
|
196
|
-
setErrorText(finalTexts.uploadFailed);
|
|
197
|
-
onError?.(err, 'upload', file);
|
|
198
|
-
return {
|
|
199
|
-
status: 'fail',
|
|
200
|
-
error: err.message,
|
|
201
|
-
response: {}
|
|
202
|
-
};
|
|
203
|
-
} finally {
|
|
204
|
-
setUploading(false);
|
|
205
|
-
}
|
|
206
|
-
};
|
|
207
|
-
const handleRemove = e => {
|
|
208
|
-
// 阻止冒泡到 Upload 触发文件选择(DeleteIcon 与 PntImage 移除按钮均为 SVG 点击事件)
|
|
209
|
-
e.stopPropagation();
|
|
210
|
-
if (disabled || uploading) {
|
|
211
|
-
return;
|
|
212
|
-
}
|
|
213
|
-
setLastFile(null);
|
|
214
|
-
setErrorText('');
|
|
215
|
-
onRemove?.();
|
|
216
|
-
};
|
|
217
|
-
const wrapperClassName = ['pnt-upload', imagePreview ? 'pnt-upload--image' : 'pnt-upload--file', disabled ? 'pnt-upload--disabled' : '', className || ''].filter(Boolean).join(' ');
|
|
218
|
-
const displayName = lastFile?.name || getFileNameFromUrl(value);
|
|
219
|
-
return /*#__PURE__*/_jsxs("div", {
|
|
220
|
-
className: wrapperClassName,
|
|
221
|
-
style: style,
|
|
222
|
-
children: [/*#__PURE__*/_jsx(Upload, {
|
|
223
|
-
theme: "custom",
|
|
224
|
-
requestMethod: requestMethod,
|
|
225
|
-
accept: acceptString || undefined,
|
|
226
|
-
allowUploadDuplicateFile: true,
|
|
227
|
-
disabled: disabled || uploading,
|
|
228
|
-
className: "pnt-upload__trigger",
|
|
229
|
-
children: imagePreview ? /*#__PURE__*/_jsx(PntImage, {
|
|
230
|
-
src: value,
|
|
231
|
-
loading: uploading,
|
|
232
|
-
defaultImg: defaultImg,
|
|
233
|
-
style: previewStyle,
|
|
234
|
-
texts: {
|
|
235
|
-
uploading: finalTexts.uploading
|
|
236
|
-
},
|
|
237
|
-
onRemove: disabled ? undefined : handleRemove
|
|
238
|
-
}) : /*#__PURE__*/_jsx("div", {
|
|
239
|
-
className: "pnt-upload-file",
|
|
240
|
-
children: value && !uploading ? /*#__PURE__*/_jsxs("div", {
|
|
241
|
-
className: "pnt-upload-file__row",
|
|
242
|
-
children: [/*#__PURE__*/_jsx(FileIcon, {
|
|
243
|
-
className: "pnt-upload-file__icon"
|
|
244
|
-
}), /*#__PURE__*/_jsx("span", {
|
|
245
|
-
className: "pnt-upload-file__name",
|
|
246
|
-
title: displayName,
|
|
247
|
-
children: displayName
|
|
248
|
-
}), !disabled && /*#__PURE__*/_jsx(DeleteIcon, {
|
|
249
|
-
className: "pnt-upload-file__delete",
|
|
250
|
-
onClick: handleRemove
|
|
251
|
-
})]
|
|
252
|
-
}) : uploading ? /*#__PURE__*/_jsxs("div", {
|
|
253
|
-
className: "pnt-upload-file__row pnt-upload-file__row--progress",
|
|
254
|
-
children: [/*#__PURE__*/_jsx(Progress, {
|
|
255
|
-
percentage: percent,
|
|
256
|
-
className: "pnt-upload-file__progress"
|
|
257
|
-
}), /*#__PURE__*/_jsxs("span", {
|
|
258
|
-
className: "pnt-upload-file__percent",
|
|
259
|
-
children: [finalTexts.uploading, " ", percent, "%"]
|
|
260
|
-
})]
|
|
261
|
-
}) : /*#__PURE__*/_jsxs("div", {
|
|
262
|
-
className: "pnt-upload-file__row pnt-upload-file__row--empty",
|
|
263
|
-
children: [/*#__PURE__*/_jsx(UploadIcon, {
|
|
264
|
-
className: "pnt-upload-file__icon"
|
|
265
|
-
}), /*#__PURE__*/_jsx("span", {
|
|
266
|
-
children: value ? finalTexts.reselect : finalTexts.selectFile
|
|
267
|
-
})]
|
|
268
|
-
})
|
|
269
|
-
})
|
|
270
|
-
}), errorText && /*#__PURE__*/_jsx("p", {
|
|
271
|
-
className: "pnt-upload__error",
|
|
272
|
-
children: errorText
|
|
273
|
-
})]
|
|
274
|
-
});
|
|
275
|
-
};
|
|
276
|
-
export default PntUpload;
|
|
@@ -1,101 +0,0 @@
|
|
|
1
|
-
.pnt-upload {
|
|
2
|
-
display: inline-block;
|
|
3
|
-
|
|
4
|
-
// TDesign Upload custom 触发器外层
|
|
5
|
-
.pnt-upload__trigger {
|
|
6
|
-
display: inline-block;
|
|
7
|
-
cursor: pointer;
|
|
8
|
-
}
|
|
9
|
-
|
|
10
|
-
// 错误文案(图片 / 文件模式共用)
|
|
11
|
-
.pnt-upload__error {
|
|
12
|
-
margin: 4px 0 0;
|
|
13
|
-
color: var(--td-error-color, #d54941);
|
|
14
|
-
font-size: 12px;
|
|
15
|
-
line-height: 20px;
|
|
16
|
-
}
|
|
17
|
-
|
|
18
|
-
&--disabled {
|
|
19
|
-
.pnt-upload__trigger {
|
|
20
|
-
cursor: not-allowed;
|
|
21
|
-
}
|
|
22
|
-
}
|
|
23
|
-
|
|
24
|
-
// ========== 文件模式 ==========
|
|
25
|
-
.pnt-upload-file {
|
|
26
|
-
box-sizing: border-box;
|
|
27
|
-
min-width: 320px;
|
|
28
|
-
padding: 12px 16px;
|
|
29
|
-
border: 1px dashed var(--td-component-border, #dcdcdc);
|
|
30
|
-
border-radius: var(--td-radius-default, 6px);
|
|
31
|
-
background-color: var(--td-bg-color-container, #fff);
|
|
32
|
-
transition: border-color 0.2s;
|
|
33
|
-
|
|
34
|
-
&:hover {
|
|
35
|
-
border-color: var(--td-brand-color, #165dff);
|
|
36
|
-
}
|
|
37
|
-
|
|
38
|
-
&__row {
|
|
39
|
-
display: flex;
|
|
40
|
-
align-items: center;
|
|
41
|
-
gap: 8px;
|
|
42
|
-
color: var(--td-text-color-primary, #1f2329);
|
|
43
|
-
font-size: 14px;
|
|
44
|
-
line-height: 22px;
|
|
45
|
-
|
|
46
|
-
&--empty {
|
|
47
|
-
justify-content: flex-start;
|
|
48
|
-
color: var(--td-text-color-secondary, #6b7280);
|
|
49
|
-
}
|
|
50
|
-
|
|
51
|
-
&--progress {
|
|
52
|
-
align-items: center;
|
|
53
|
-
}
|
|
54
|
-
}
|
|
55
|
-
|
|
56
|
-
&__icon {
|
|
57
|
-
flex: none;
|
|
58
|
-
font-size: 20px;
|
|
59
|
-
color: var(--td-text-color-secondary, #6b7280);
|
|
60
|
-
}
|
|
61
|
-
|
|
62
|
-
&__name {
|
|
63
|
-
flex: 1;
|
|
64
|
-
overflow: hidden;
|
|
65
|
-
white-space: nowrap;
|
|
66
|
-
text-overflow: ellipsis;
|
|
67
|
-
}
|
|
68
|
-
|
|
69
|
-
&__delete {
|
|
70
|
-
flex: none;
|
|
71
|
-
font-size: 18px;
|
|
72
|
-
color: var(--td-text-color-secondary, #6b7280);
|
|
73
|
-
cursor: pointer;
|
|
74
|
-
|
|
75
|
-
&:hover {
|
|
76
|
-
color: var(--td-error-color, #d54941);
|
|
77
|
-
}
|
|
78
|
-
}
|
|
79
|
-
|
|
80
|
-
&__progress {
|
|
81
|
-
flex: 1;
|
|
82
|
-
min-width: 0;
|
|
83
|
-
}
|
|
84
|
-
|
|
85
|
-
&__percent {
|
|
86
|
-
flex: none;
|
|
87
|
-
color: var(--td-text-color-secondary, #6b7280);
|
|
88
|
-
font-size: 12px;
|
|
89
|
-
}
|
|
90
|
-
}
|
|
91
|
-
|
|
92
|
-
&--disabled {
|
|
93
|
-
.pnt-upload-file {
|
|
94
|
-
background-color: var(--td-bg-color-component-disabled, #f3f3f3);
|
|
95
|
-
|
|
96
|
-
&:hover {
|
|
97
|
-
border-color: var(--td-component-border, #dcdcdc);
|
|
98
|
-
}
|
|
99
|
-
}
|
|
100
|
-
}
|
|
101
|
-
}
|
package/lib/esm/config.d.ts
DELETED
|
@@ -1,97 +0,0 @@
|
|
|
1
|
-
/// <reference types="react" />
|
|
2
|
-
/**
|
|
3
|
-
* 统一响应结构(与后端 commonEesType 对齐)
|
|
4
|
-
*/
|
|
5
|
-
export interface commonEesType<T> {
|
|
6
|
-
code: number;
|
|
7
|
-
msg: string;
|
|
8
|
-
data: T;
|
|
9
|
-
ret?: number;
|
|
10
|
-
}
|
|
11
|
-
/**
|
|
12
|
-
* 库所需的最小 HTTP 能力(仅 post)。
|
|
13
|
-
* 用结构化类型而非直接依赖 AxiosInstance,
|
|
14
|
-
* 避免与消费方 axios 版本的类型定义强耦合(如 1.13 vs 1.20 的 query 方法差异)。
|
|
15
|
-
* 任何具备 axios 兼容 post 签名的实例均可注入。
|
|
16
|
-
*/
|
|
17
|
-
export interface PntHttpLike {
|
|
18
|
-
get<R = unknown>(url: string, config?: any): Promise<R>;
|
|
19
|
-
post<R = unknown, D = unknown>(url: string, data?: D, config?: any): Promise<R>;
|
|
20
|
-
}
|
|
21
|
-
/**
|
|
22
|
-
* 高敏信息解锁接口配置(可选,全局覆盖)
|
|
23
|
-
*/
|
|
24
|
-
export interface PntHighSecurityConfig {
|
|
25
|
-
/**
|
|
26
|
-
* 业务级解密接口 URL,覆盖默认 /api/v3/business/game_info/high-security-decrypt?audience=/laas-pnt
|
|
27
|
-
* @description scope='business'(默认)时使用
|
|
28
|
-
*/
|
|
29
|
-
decryptUrl?: string;
|
|
30
|
-
/**
|
|
31
|
-
* 平台级解密接口 URL,覆盖默认 /api/v3/business/game_info/plat-high-security-decrypt?audience=/laas-pnt
|
|
32
|
-
* @description scope='platform' 时使用(发布记录页等平台级权限校验场景)
|
|
33
|
-
*/
|
|
34
|
-
decryptPlatUrl?: string;
|
|
35
|
-
/** 成功码字段:'code'(默认)或 'ret'(account-business 现状) */
|
|
36
|
-
successCodeField?: 'code' | 'ret';
|
|
37
|
-
/** audience 覆盖(默认 /laas-pnt) */
|
|
38
|
-
audience?: string;
|
|
39
|
-
}
|
|
40
|
-
/**
|
|
41
|
-
* 地区查询接口配置(可选,全局覆盖)
|
|
42
|
-
*/
|
|
43
|
-
export interface PntRegionQueryConfig {
|
|
44
|
-
/**
|
|
45
|
-
* 业务级地区查询接口 URL,覆盖默认 /api/v5/business/region/query?audience=/laas-pnt
|
|
46
|
-
* @description scope='business'(默认)时使用
|
|
47
|
-
*/
|
|
48
|
-
queryUrl?: string;
|
|
49
|
-
/**
|
|
50
|
-
* 平台级地区查询接口 URL,覆盖默认 /api/v5/business/region/plat-query?audience=/laas-pnt
|
|
51
|
-
* @description scope='platform' 时使用
|
|
52
|
-
*/
|
|
53
|
-
queryPlatUrl?: string;
|
|
54
|
-
}
|
|
55
|
-
/**
|
|
56
|
-
* 组件库运行时配置:由消费方通过 PntProvider 注入
|
|
57
|
-
*/
|
|
58
|
-
export interface PntConfig {
|
|
59
|
-
/** 消费方已配置好的 axios 实例(含拦截器、鉴权、baseURL 等) */
|
|
60
|
-
http: PntHttpLike;
|
|
61
|
-
/** 高敏信息解锁接口全局配置(可选) */
|
|
62
|
-
highSecurity?: PntHighSecurityConfig;
|
|
63
|
-
/** 地区查询接口全局配置(可选) */
|
|
64
|
-
regionQuery?: PntRegionQueryConfig;
|
|
65
|
-
/**
|
|
66
|
-
* 全局语言设置 @default 'zh'
|
|
67
|
-
* - zh: 中文(默认文案)
|
|
68
|
-
* - en: 英文(内置英文文案)
|
|
69
|
-
* @description 组件内部文案(全选、反选、批量导入等)会根据此值自动切换
|
|
70
|
-
*/
|
|
71
|
-
locale?: 'zh' | 'en';
|
|
72
|
-
}
|
|
73
|
-
/**
|
|
74
|
-
* 配置 Provider:消费方在应用根入口包裹一次即可
|
|
75
|
-
* @example
|
|
76
|
-
* ```tsx
|
|
77
|
-
* import { PntProvider } from '@pnt-team/pnt-component-frontend';
|
|
78
|
-
* import http from './utils/request';
|
|
79
|
-
*
|
|
80
|
-
* <PntProvider value={{ http }}>
|
|
81
|
-
* <App />
|
|
82
|
-
* </PntProvider>
|
|
83
|
-
* ```
|
|
84
|
-
*/
|
|
85
|
-
export declare const PntProvider: import("react").Provider<PntConfig | null>;
|
|
86
|
-
/**
|
|
87
|
-
* 获取组件库运行时配置(内部使用)
|
|
88
|
-
* @internal
|
|
89
|
-
*/
|
|
90
|
-
export declare const usePntConfig: () => PntConfig;
|
|
91
|
-
/**
|
|
92
|
-
* 获取组件库运行时配置(可选版本,内部使用)
|
|
93
|
-
* @description 供「外部受控数据」模式的组件使用:未注入 Provider 时返回 null,
|
|
94
|
-
* 组件自行降级(不发起内部请求),不抛错
|
|
95
|
-
* @internal
|
|
96
|
-
*/
|
|
97
|
-
export declare const usePntConfigOptional: () => PntConfig | null;
|
package/lib/esm/config.js
DELETED
|
@@ -1,60 +0,0 @@
|
|
|
1
|
-
import { createContext, useContext } from 'react';
|
|
2
|
-
|
|
3
|
-
/**
|
|
4
|
-
* 统一响应结构(与后端 commonEesType 对齐)
|
|
5
|
-
*/
|
|
6
|
-
|
|
7
|
-
/**
|
|
8
|
-
* 库所需的最小 HTTP 能力(仅 post)。
|
|
9
|
-
* 用结构化类型而非直接依赖 AxiosInstance,
|
|
10
|
-
* 避免与消费方 axios 版本的类型定义强耦合(如 1.13 vs 1.20 的 query 方法差异)。
|
|
11
|
-
* 任何具备 axios 兼容 post 签名的实例均可注入。
|
|
12
|
-
*/
|
|
13
|
-
|
|
14
|
-
/**
|
|
15
|
-
* 高敏信息解锁接口配置(可选,全局覆盖)
|
|
16
|
-
*/
|
|
17
|
-
|
|
18
|
-
/**
|
|
19
|
-
* 地区查询接口配置(可选,全局覆盖)
|
|
20
|
-
*/
|
|
21
|
-
|
|
22
|
-
/**
|
|
23
|
-
* 组件库运行时配置:由消费方通过 PntProvider 注入
|
|
24
|
-
*/
|
|
25
|
-
|
|
26
|
-
const PntContext = /*#__PURE__*/createContext(null);
|
|
27
|
-
|
|
28
|
-
/**
|
|
29
|
-
* 配置 Provider:消费方在应用根入口包裹一次即可
|
|
30
|
-
* @example
|
|
31
|
-
* ```tsx
|
|
32
|
-
* import { PntProvider } from '@pnt-team/pnt-component-frontend';
|
|
33
|
-
* import http from './utils/request';
|
|
34
|
-
*
|
|
35
|
-
* <PntProvider value={{ http }}>
|
|
36
|
-
* <App />
|
|
37
|
-
* </PntProvider>
|
|
38
|
-
* ```
|
|
39
|
-
*/
|
|
40
|
-
export const PntProvider = PntContext.Provider;
|
|
41
|
-
|
|
42
|
-
/**
|
|
43
|
-
* 获取组件库运行时配置(内部使用)
|
|
44
|
-
* @internal
|
|
45
|
-
*/
|
|
46
|
-
export const usePntConfig = () => {
|
|
47
|
-
const cfg = useContext(PntContext);
|
|
48
|
-
if (!cfg) {
|
|
49
|
-
throw new Error('[pnt-component-frontend] 未注入配置:请在应用根入口用 <PntProvider value={{ http }}> 包裹');
|
|
50
|
-
}
|
|
51
|
-
return cfg;
|
|
52
|
-
};
|
|
53
|
-
|
|
54
|
-
/**
|
|
55
|
-
* 获取组件库运行时配置(可选版本,内部使用)
|
|
56
|
-
* @description 供「外部受控数据」模式的组件使用:未注入 Provider 时返回 null,
|
|
57
|
-
* 组件自行降级(不发起内部请求),不抛错
|
|
58
|
-
* @internal
|
|
59
|
-
*/
|
|
60
|
-
export const usePntConfigOptional = () => useContext(PntContext);
|
package/lib/esm/global.css
DELETED
package/lib/esm/global.d.ts
DELETED
|
@@ -1,39 +0,0 @@
|
|
|
1
|
-
// src/global.d.ts
|
|
2
|
-
declare module '*.png' {
|
|
3
|
-
const src: string;
|
|
4
|
-
export default src;
|
|
5
|
-
}
|
|
6
|
-
|
|
7
|
-
declare module '*.jpg' {
|
|
8
|
-
const src: string;
|
|
9
|
-
export default src;
|
|
10
|
-
}
|
|
11
|
-
|
|
12
|
-
declare module '*.svg' {
|
|
13
|
-
const src: string;
|
|
14
|
-
export default src;
|
|
15
|
-
}
|
|
16
|
-
|
|
17
|
-
// 字体文件
|
|
18
|
-
declare module '*.woff' {
|
|
19
|
-
const src: string;
|
|
20
|
-
export default src;
|
|
21
|
-
}
|
|
22
|
-
declare module '*.woff2' {
|
|
23
|
-
const src: string;
|
|
24
|
-
export default src;
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
declare module '*.json' {
|
|
28
|
-
const value: any;
|
|
29
|
-
export default value;
|
|
30
|
-
}
|
|
31
|
-
|
|
32
|
-
// use-sync-external-store shim(兼容 React 16/17,包本身未提供 .d.ts)
|
|
33
|
-
declare module 'use-sync-external-store/shim' {
|
|
34
|
-
export function useSyncExternalStore<A>(
|
|
35
|
-
subscribe: (callback: () => void) => () => void,
|
|
36
|
-
getSnapshot: () => A,
|
|
37
|
-
getServerSnapshot?: () => A,
|
|
38
|
-
): A;
|
|
39
|
-
}
|
|
@@ -1,88 +0,0 @@
|
|
|
1
|
-
import type { PntHighSecurityConfig } from "../config";
|
|
2
|
-
/** 单个解锁项 */
|
|
3
|
-
export interface HighSecurityParamItem {
|
|
4
|
-
/** 字段标识(与后端约定) */
|
|
5
|
-
key: string;
|
|
6
|
-
/** 参数密文(_high_security_: 前缀) */
|
|
7
|
-
value: string;
|
|
8
|
-
/**
|
|
9
|
-
* 缓存别名(可选)
|
|
10
|
-
* @description 当后端 key 相同但密文不同时(如两组 SDK 密钥),
|
|
11
|
-
* 用 cacheKey 区分缓存,请求体仍用 key。默认 cacheKey=key
|
|
12
|
-
*/
|
|
13
|
-
cacheKey?: string;
|
|
14
|
-
}
|
|
15
|
-
/** 单次请求的接口配置覆盖(优先级 > PntProvider 全局配置) */
|
|
16
|
-
export type HighSecurityApiConfig = PntHighSecurityConfig;
|
|
17
|
-
/**
|
|
18
|
-
* 高敏接口变体
|
|
19
|
-
* - 'business'(默认):业务级,走 /api/v3/business/game_info/high-security-decrypt
|
|
20
|
-
* - 'platform':平台级(发布记录页场景),走 /api/v3/business/game_info/plat-high-security-decrypt
|
|
21
|
-
*/
|
|
22
|
-
export type HighSecurityScope = 'business' | 'platform';
|
|
23
|
-
/** 高敏数据解锁请求参数(组件层友好命名,库内部转换为后端 snake_case) */
|
|
24
|
-
export interface HighSecurityRequestParams {
|
|
25
|
-
/** 业务 ID */
|
|
26
|
-
gameId: string | number;
|
|
27
|
-
/** 环境标识(可缺省,默认 0;以各业务现有约定为准) */
|
|
28
|
-
env?: string | number;
|
|
29
|
-
/** 页面 ID(不传则默认取 location.pathname),用于操作日志和权限校验 */
|
|
30
|
-
pageId?: string;
|
|
31
|
-
/** 需要解锁的参数列表,支持批量 */
|
|
32
|
-
param: HighSecurityParamItem[];
|
|
33
|
-
/** 强制刷新:忽略缓存,每次都调接口(默认 false) */
|
|
34
|
-
forceRefresh?: boolean;
|
|
35
|
-
/** 本次请求的接口配置覆盖(可选) */
|
|
36
|
-
apiConfig?: HighSecurityApiConfig;
|
|
37
|
-
/** 本次请求的接口变体,覆盖 hook 初始化时的 scope */
|
|
38
|
-
scope?: HighSecurityScope;
|
|
39
|
-
}
|
|
40
|
-
/** hook 初始化 scope:传入后 securityData/isUnlocked 自动按该业务+环境过滤 */
|
|
41
|
-
export interface UseHighSecurityOptions {
|
|
42
|
-
/** 当前业务 ID */
|
|
43
|
-
gameId?: string | number;
|
|
44
|
-
/** 当前环境(可缺省,默认 0) */
|
|
45
|
-
env?: string | number;
|
|
46
|
-
/** 接口变体(默认 'business');发布记录页等平台级场景传 'platform' */
|
|
47
|
-
scope?: HighSecurityScope;
|
|
48
|
-
}
|
|
49
|
-
/** 清缓存过滤条件 */
|
|
50
|
-
export interface ClearSecurityDataFilter {
|
|
51
|
-
gameId?: string | number;
|
|
52
|
-
env?: string | number;
|
|
53
|
-
}
|
|
54
|
-
export interface UseHighSecurityResult {
|
|
55
|
-
/**
|
|
56
|
-
* 当前 scope 下已解锁的明文;未传 scope 时为空对象
|
|
57
|
-
* @description key 为请求时入参的 cacheKey(未传 cacheKey 时为字段名)
|
|
58
|
-
*/
|
|
59
|
-
securityData: Record<string, string>;
|
|
60
|
-
/**
|
|
61
|
-
* 发起解锁
|
|
62
|
-
* @description
|
|
63
|
-
* - 已缓存的 key 直接返回缓存值,不再请求
|
|
64
|
-
* - 同一参数的在途请求自动去重
|
|
65
|
-
* - 成功:写入模块缓存并返回当次解密数组(含已缓存项)
|
|
66
|
-
* - 失败/部分失败:仅返回拿到的项(可能为空数组),不抛错
|
|
67
|
-
*/
|
|
68
|
-
requestSecurityData: (params: HighSecurityRequestParams) => Promise<HighSecurityParamItem[]>;
|
|
69
|
-
/**
|
|
70
|
-
* 清缓存:不传参清空全部;传 gameId 清空该业务所有环境;
|
|
71
|
-
* 同时传 gameId+env 只清空该业务指定环境;仅传 env 清空所有业务该环境
|
|
72
|
-
*/
|
|
73
|
-
clearSecurityData: (filter?: ClearSecurityDataFilter) => void;
|
|
74
|
-
/** 当前 scope 下某字段是否已解锁(两步式"查看 → 复制"UI 用) */
|
|
75
|
-
isUnlocked: (key: string) => boolean;
|
|
76
|
-
}
|
|
77
|
-
/**
|
|
78
|
-
* 高敏数据解锁 Hook(PntSecureBox 内部依赖,同时对外导出供"复制"等非展示场景使用)
|
|
79
|
-
*
|
|
80
|
-
* @example
|
|
81
|
-
* ```tsx
|
|
82
|
-
* // 展示场景请直接用 PntSecureBox;两步式"查看 → 复制":
|
|
83
|
-
* const { isUnlocked, requestSecurityData, securityData } = useHighSecurity({ gameId, env });
|
|
84
|
-
* const res = await requestSecurityData({ gameId, env, param: [{ key: 'SDK_KEY', value }] });
|
|
85
|
-
* if (res.length) copy(securityData.SDK_KEY);
|
|
86
|
-
* ```
|
|
87
|
-
*/
|
|
88
|
-
export declare const useHighSecurity: (options?: UseHighSecurityOptions) => UseHighSecurityResult;
|