message-verify 0.0.37-beta.0 → 0.0.39-beta.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.
@@ -8,12 +8,13 @@ const Button = ({ disabled, onClick, children, style }) => {
8
8
  }
9
9
  };
10
10
  return (_jsx("button", { disabled: disabled, onClick: handleClick, style: {
11
- padding: '6px 16px',
12
- borderRadius: 4,
11
+ padding: '6px 6px',
12
+ borderRadius: 5,
13
13
  border: '1px solid #d9d9d9',
14
- background: disabled ? '#f5f5f5' : '#1677ff',
15
- color: disabled ? '#aaa' : '#fff',
14
+ background: disabled ? '#f5f5f5' : '#fff',
15
+ color: disabled ? '#aaa' : '#333',
16
16
  cursor: disabled ? 'not-allowed' : 'pointer',
17
+ whiteSpace: 'nowrap',
17
18
  ...style,
18
19
  }, children: children }));
19
20
  };
@@ -1,4 +1,5 @@
1
1
  import Modal from "./modal.js";
2
2
  import Input from "./input.js";
3
3
  import Button from "./button.js";
4
- export { Modal, Input, Button };
4
+ import { message } from "./message.js";
5
+ export { Modal, Input, Button, message };
@@ -1,4 +1,5 @@
1
1
  import Modal from "./modal.js";
2
2
  import Input from "./input.js";
3
3
  import Button from "./button.js";
4
- export { Modal, Input, Button };
4
+ import { message } from "./message.js";
5
+ export { Modal, Input, Button, message };
@@ -4,6 +4,7 @@ interface CustomInputProps {
4
4
  onChange?: (val: string) => void;
5
5
  placeholder?: string;
6
6
  type?: string;
7
+ style?: React.CSSProperties;
7
8
  }
8
9
  declare const Input: React.FC<CustomInputProps>;
9
10
  export default Input;
@@ -1,5 +1,5 @@
1
1
  import { jsx as _jsx } from "react/jsx-runtime";
2
- const Input = ({ value, onChange, placeholder, type = 'text' }) => {
2
+ const Input = ({ value, onChange, placeholder, type = 'text', style }) => {
3
3
  return (_jsx("input", { type: type, value: value, placeholder: placeholder, onChange: e => onChange?.(e.target.value), style: {
4
4
  padding: '6px 12px',
5
5
  border: '1px solid #d9d9d9',
@@ -7,7 +7,9 @@ const Input = ({ value, onChange, placeholder, type = 'text' }) => {
7
7
  outline: 'none',
8
8
  fontSize: 14,
9
9
  width: '100%',
10
- boxSizing: 'border-box'
10
+ boxSizing: 'border-box',
11
+ height: 36,
12
+ ...style,
11
13
  } }));
12
14
  };
13
15
  export default Input;
@@ -0,0 +1,6 @@
1
+ import { ReactNode } from 'react';
2
+ export declare const message: {
3
+ success(content: ReactNode): void;
4
+ error(content: ReactNode): void;
5
+ info(content: ReactNode): void;
6
+ };
@@ -0,0 +1,53 @@
1
+ let messageContainer = null;
2
+ function createContainer() {
3
+ if (!messageContainer) {
4
+ messageContainer = document.createElement('div');
5
+ messageContainer.style.position = 'fixed';
6
+ messageContainer.style.top = '24px';
7
+ messageContainer.style.left = '50%';
8
+ messageContainer.style.transform = 'translateX(-50%)';
9
+ messageContainer.style.zIndex = '9999';
10
+ document.body.appendChild(messageContainer);
11
+ }
12
+ }
13
+ function showMessage(content, type) {
14
+ createContainer();
15
+ const msgDiv = document.createElement('div');
16
+ msgDiv.style.marginTop = '8px';
17
+ msgDiv.style.padding = '10px 24px';
18
+ msgDiv.style.borderRadius = '4px';
19
+ msgDiv.style.boxShadow = '0 2px 8px rgba(0,0,0,0.08)';
20
+ msgDiv.style.fontSize = '16px';
21
+ if (type === 'success') {
22
+ msgDiv.style.background = '#f6ffed';
23
+ msgDiv.style.color = '#52c41a';
24
+ }
25
+ else if (type === 'error') {
26
+ msgDiv.style.background = '#fff2f0';
27
+ msgDiv.style.color = '#ff4d4f';
28
+ }
29
+ else if (type === 'info') {
30
+ msgDiv.style.background = '#e6f4ff';
31
+ msgDiv.style.color = '#1677ff';
32
+ }
33
+ msgDiv.innerText = String(content);
34
+ messageContainer.appendChild(msgDiv);
35
+ setTimeout(() => {
36
+ msgDiv.remove();
37
+ if (messageContainer && messageContainer.childElementCount === 0) {
38
+ messageContainer.remove();
39
+ messageContainer = null;
40
+ }
41
+ }, 2000);
42
+ }
43
+ export const message = {
44
+ success(content) {
45
+ showMessage(content, 'success');
46
+ },
47
+ error(content) {
48
+ showMessage(content, 'error');
49
+ },
50
+ info(content) {
51
+ showMessage(content, 'info');
52
+ }
53
+ };
package/dist/index.js CHANGED
@@ -1,66 +1,13 @@
1
- import { jsxs as _jsxs, jsx as _jsx } from "react/jsx-runtime";
2
- import { Modal, Input, Button } from './compoments/index.js';
1
+ import { jsx as _jsx } from "react/jsx-runtime";
3
2
  import ReactDOM from 'react-dom/client';
4
- import { useEffect, useState } from 'react';
5
- import Api from './resource.js';
3
+ import VerifyModal from './verify-modal.js';
6
4
  let modalRoot = null;
7
- const ModalDom = ({ config }) => {
8
- const [visible, setVisible] = useState(true);
9
- const [countdown, setCountdown] = useState(60);
10
- const [captchaImage, setCaptchaImage] = useState('');
11
- const [captchCode, setCaptchCode] = useState('');
12
- const [captchaKey, setCaptchaKey] = useState('');
13
- const { data } = config || {};
14
- const { mobile } = data || {};
15
- const getKey = async () => {
16
- const res = await Api.getCaptchaKey();
17
- const { body: key } = res.data || {};
18
- setCaptchaKey(key);
19
- if (key) {
20
- console.log('res=>key', key);
21
- const image = Api.getCaptchaImgUrl(key);
22
- console.log('image', image);
23
- setCaptchaImage(image);
24
- }
25
- };
26
- useEffect(() => {
27
- let timer = null;
28
- if (visible && countdown > 0) {
29
- timer = setInterval(() => {
30
- setCountdown((prev) => prev - 1);
31
- }, 1000);
32
- }
33
- if (countdown === 0) {
34
- getKey();
35
- }
36
- return () => {
37
- if (timer)
38
- clearInterval(timer);
39
- };
40
- }, [visible, countdown]);
41
- useEffect(() => {
42
- console.log('mobile', mobile);
43
- }, []);
44
- const handleResend = async () => {
45
- setCountdown(60);
46
- const res = await Api.reSendCode({ captchaKey, captcha: captchCode });
47
- console.log('handleResend=>res', res);
48
- // message.success('发送成功');
49
- };
50
- return (_jsxs(Modal, { visible: visible, onClose: () => {
51
- setVisible(false);
52
- config.onClose?.();
53
- }, children: [_jsxs("div", { children: ["\u5DF2\u53D1\u9001\u77ED\u4FE1\u81F3\u60A8\u7684\u624B\u673A\uFF1A", mobile] }), countdown > 0 ? null : _jsxs("div", { style: { marginTop: 8, display: 'flex', alignItems: 'center', width: 300 }, children: [_jsx(Input, { onChange: (e) => {
54
- setCaptchCode(e);
55
- } }), captchaImage && _jsx("img", { src: captchaImage, alt: "\u9A8C\u8BC1\u7801", style: { width: 100, height: 30, marginLeft: 8 }, onClick: getKey })] }), countdown > 0 ? null : _jsx("div", { children: "\u8BF7\u8F93\u5165\u56FE\u5F62\u9A8C\u8BC1\u7801\u540E\uFF0C\u91CD\u65B0\u53D1\u9001\u9A8C\u8BC1\u7801" }), _jsxs("div", { style: { display: 'flex', alignItems: 'center', gap: 8, marginTop: 8 }, children: [_jsx(Input, { onChange: (val) => { console.log('change', val); } }), _jsx(Button, { disabled: countdown > 0 || !captchCode, onClick: handleResend, children: countdown > 0 ? `${countdown}秒` : '重新发送' })] })] }));
56
- };
57
- // ... existing code ...
58
5
  export const createMessageVerifyModal = (config) => {
59
6
  const container = document.createElement('div');
60
7
  container.id = 'antd-modal-container';
61
8
  document.body.appendChild(container);
62
9
  modalRoot = ReactDOM.createRoot(container);
63
- modalRoot.render(_jsx(ModalDom, { config: {
10
+ modalRoot.render(_jsx(VerifyModal, { config: {
64
11
  ...config,
65
12
  onClose: () => {
66
13
  config.onClose?.();
package/dist/resource.js CHANGED
@@ -1,5 +1,5 @@
1
1
  import { assign, axios as instance, customPost } from '@yqg/resource';
2
- // import { message } from 'antd';
2
+ import { message } from './compoments/index.js';
3
3
  import { YQG_SUCCESS } from './utils/status.js';
4
4
  const urlPrefix = '/admin/';
5
5
  // axios.defaults.headers.common['Access-Control-Allow-Origin'] = '*';
@@ -14,7 +14,7 @@ instance.interceptors.response.use((res) => {
14
14
  reader.readAsText(res.data, 'utf-8');
15
15
  reader.onload = () => {
16
16
  const parsedObj = JSON.parse(reader.result);
17
- // message.info(parsedObj?.status?.detail);
17
+ message.info(parsedObj?.status?.detail);
18
18
  };
19
19
  return Promise.reject();
20
20
  }
@@ -29,13 +29,13 @@ instance.interceptors.response.use((res) => {
29
29
  case YQG_SUCCESS:
30
30
  return Promise.resolve(res);
31
31
  default: {
32
- // message.error(detail);
32
+ message.error(detail);
33
33
  return Promise.reject(res);
34
34
  }
35
35
  }
36
36
  }, (err) => {
37
37
  const detail = err?.data?.status?.detail || 'Unknown error';
38
- // message.error(detail);
38
+ message.error(detail);
39
39
  return Promise.reject(err);
40
40
  });
41
41
  const api = {
@@ -1 +1 @@
1
- {"root":["../src/app.tsx","../src/index.tsx","../src/main.tsx","../src/resource.ts","../src/vite-env.d.ts","../src/compoments/button.tsx","../src/compoments/index.ts","../src/compoments/input.tsx","../src/compoments/modal.tsx","../src/utils/getfingerprint.ts","../src/utils/index.ts","../src/utils/status.ts"],"version":"5.7.3"}
1
+ {"root":["../src/index.tsx","../src/main.tsx","../src/resource.ts","../src/verify-modal.tsx","../src/vite-env.d.ts","../src/compoments/button.tsx","../src/compoments/index.ts","../src/compoments/input.tsx","../src/compoments/message.tsx","../src/compoments/modal.tsx","../src/utils/getfingerprint.ts","../src/utils/index.ts","../src/utils/status.ts"],"version":"5.7.3"}
@@ -0,0 +1,12 @@
1
+ type ModalConfig = {
2
+ data: {
3
+ mobile: string;
4
+ verifyCodeKey: string;
5
+ sendSuccess: boolean;
6
+ };
7
+ onClose?: () => void;
8
+ };
9
+ declare const ModalDom: ({ config }: {
10
+ config: ModalConfig;
11
+ }) => import("react/jsx-runtime.js").JSX.Element;
12
+ export default ModalDom;
@@ -0,0 +1,55 @@
1
+ import { jsxs as _jsxs, jsx as _jsx } from "react/jsx-runtime";
2
+ import { useEffect, useState } from 'react';
3
+ import { Modal, Input, Button, message } from './compoments/index.js';
4
+ import Api from './resource.js';
5
+ const ModalDom = ({ config }) => {
6
+ const [visible, setVisible] = useState(true);
7
+ const [countdown, setCountdown] = useState(3);
8
+ const [captchaImage, setCaptchaImage] = useState('');
9
+ const [captchCode, setCaptchCode] = useState('');
10
+ const [captchaKey, setCaptchaKey] = useState('');
11
+ const { data } = config || {};
12
+ const { mobile } = data || {};
13
+ const getKey = async () => {
14
+ const res = await Api.getCaptchaKey();
15
+ const { body: key } = res.data || {};
16
+ setCaptchaKey(key);
17
+ if (key) {
18
+ console.log('res=>key', key);
19
+ const image = Api.getCaptchaImgUrl(key);
20
+ console.log('image', image);
21
+ setCaptchaImage(image);
22
+ }
23
+ };
24
+ useEffect(() => {
25
+ let timer = null;
26
+ if (visible && countdown > 0) {
27
+ timer = setInterval(() => {
28
+ setCountdown((prev) => prev - 1);
29
+ }, 1000);
30
+ }
31
+ if (countdown === 0) {
32
+ getKey();
33
+ }
34
+ return () => {
35
+ if (timer)
36
+ clearInterval(timer);
37
+ };
38
+ }, [visible, countdown]);
39
+ useEffect(() => {
40
+ console.log('mobile', mobile);
41
+ }, [mobile]);
42
+ const handleResend = async () => {
43
+ setCountdown(60);
44
+ const res = await Api.reSendCode({ captchaKey, captcha: captchCode });
45
+ console.log('handleResend=>res', res);
46
+ message.success('发送成功');
47
+ };
48
+ return (_jsxs(Modal, { visible: visible, onClose: () => {
49
+ setVisible(false);
50
+ config.onClose?.();
51
+ }, children: [_jsxs("div", { style: { fontSize: 14, color: '#666' }, children: ["\u5DF2\u53D1\u9001\u77ED\u4FE1\u81F3\u60A8\u7684\u624B\u673A\uFF1A", mobile] }), countdown > 0 ? null : _jsxs("div", { style: { marginBlock: 8, display: 'flex', alignItems: 'center', width: 300 }, children: [_jsx(Input, { placeholder: "\u8BF7\u8F93\u5165\u56FE\u5F62\u9A8C\u8BC1\u7801", onChange: (e) => {
52
+ setCaptchCode(e);
53
+ } }), captchaImage && _jsx("img", { src: captchaImage, alt: "\u9A8C\u8BC1\u7801", style: { width: 100, height: 30, marginLeft: 8 }, onClick: getKey })] }), (countdown > 0 || captchCode) ? null : _jsx("div", { style: { fontSize: 14, color: 'red' }, children: "\u8BF7\u8F93\u5165\u56FE\u5F62\u9A8C\u8BC1\u7801\u540E\uFF0C\u91CD\u65B0\u53D1\u9001\u9A8C\u8BC1\u7801" }), _jsxs("div", { style: { display: 'flex', alignItems: 'center', gap: 8, marginTop: 8 }, children: [_jsx(Input, { placeholder: "\u8BF7\u8F93\u5165\u9A8C\u8BC1\u7801", onChange: (val) => { console.log('change', val); } }), _jsx(Button, { disabled: countdown > 0 || !captchCode, onClick: handleResend, children: countdown > 0 ? `${countdown}秒` : '重新发送' })] })] }));
54
+ };
55
+ export default ModalDom;
package/package.json CHANGED
@@ -1,10 +1,9 @@
1
1
  {
2
2
  "name": "message-verify",
3
- "version": "0.0.37-beta.0",
3
+ "version": "0.0.39-beta.0",
4
4
  "type": "module",
5
5
  "main": "dist/index.js",
6
6
  "dependencies": {
7
- "@ant-design/v5-patch-for-react-19": "^1.0.3",
8
7
  "@fingerprintjs/fingerprintjs": "^4.6.2",
9
8
  "@yqg/resource": "^1.3.8",
10
9
  "react": "^19.0.0",
@@ -21,12 +21,13 @@ const Button: React.FC<CustomButtonProps> = ({ disabled, onClick, children, styl
21
21
  disabled={disabled}
22
22
  onClick={handleClick}
23
23
  style={{
24
- padding: '6px 16px',
25
- borderRadius: 4,
24
+ padding: '6px 6px',
25
+ borderRadius: 5,
26
26
  border: '1px solid #d9d9d9',
27
- background: disabled ? '#f5f5f5' : '#1677ff',
28
- color: disabled ? '#aaa' : '#fff',
27
+ background: disabled ? '#f5f5f5' : '#fff',
28
+ color: disabled ? '#aaa' : '#333',
29
29
  cursor: disabled ? 'not-allowed' : 'pointer',
30
+ whiteSpace: 'nowrap',
30
31
  ...style,
31
32
  }}
32
33
  >
@@ -1,5 +1,6 @@
1
1
  import Modal from "./modal.js";
2
2
  import Input from "./input.js";
3
3
  import Button from "./button.js";
4
+ import { message } from "./message.js";
4
5
 
5
- export { Modal, Input, Button };
6
+ export { Modal, Input, Button, message };
@@ -5,9 +5,10 @@ interface CustomInputProps {
5
5
  onChange?: (val: string) => void;
6
6
  placeholder?: string;
7
7
  type?: string;
8
+ style?: React.CSSProperties;
8
9
  }
9
10
 
10
- const Input: React.FC<CustomInputProps> = ({ value, onChange, placeholder, type = 'text' }) => {
11
+ const Input: React.FC<CustomInputProps> = ({ value, onChange, placeholder, type = 'text', style }) => {
11
12
  return (
12
13
  <input
13
14
  type={type}
@@ -21,7 +22,9 @@ const Input: React.FC<CustomInputProps> = ({ value, onChange, placeholder, type
21
22
  outline: 'none',
22
23
  fontSize: 14,
23
24
  width: '100%',
24
- boxSizing: 'border-box'
25
+ boxSizing: 'border-box',
26
+ height: 36,
27
+ ...style,
25
28
  }}
26
29
  />
27
30
  );
@@ -0,0 +1,60 @@
1
+ import { ReactNode } from 'react';
2
+
3
+ let messageContainer: HTMLDivElement | null = null;
4
+
5
+ function createContainer() {
6
+ if (!messageContainer) {
7
+ messageContainer = document.createElement('div');
8
+ messageContainer.style.position = 'fixed';
9
+ messageContainer.style.top = '24px';
10
+ messageContainer.style.left = '50%';
11
+ messageContainer.style.transform = 'translateX(-50%)';
12
+ messageContainer.style.zIndex = '9999';
13
+ document.body.appendChild(messageContainer);
14
+ }
15
+ }
16
+
17
+ function showMessage(content: ReactNode, type: 'success' | 'error' | 'info') {
18
+ createContainer();
19
+ const msgDiv = document.createElement('div');
20
+ msgDiv.style.marginTop = '8px';
21
+ msgDiv.style.padding = '10px 24px';
22
+ msgDiv.style.borderRadius = '4px';
23
+ msgDiv.style.boxShadow = '0 2px 8px rgba(0,0,0,0.08)';
24
+ msgDiv.style.fontSize = '16px';
25
+
26
+ if (type === 'success') {
27
+ msgDiv.style.background = '#f6ffed';
28
+ msgDiv.style.color = '#52c41a';
29
+ } else if (type === 'error') {
30
+ msgDiv.style.background = '#fff2f0';
31
+ msgDiv.style.color = '#ff4d4f';
32
+ } else if (type === 'info') {
33
+ msgDiv.style.background = '#e6f4ff';
34
+ msgDiv.style.color = '#1677ff';
35
+ }
36
+
37
+ msgDiv.innerText = String(content);
38
+
39
+ messageContainer!.appendChild(msgDiv);
40
+
41
+ setTimeout(() => {
42
+ msgDiv.remove();
43
+ if (messageContainer && messageContainer.childElementCount === 0) {
44
+ messageContainer.remove();
45
+ messageContainer = null;
46
+ }
47
+ }, 2000);
48
+ }
49
+
50
+ export const message = {
51
+ success(content: ReactNode) {
52
+ showMessage(content, 'success');
53
+ },
54
+ error(content: ReactNode) {
55
+ showMessage(content, 'error');
56
+ },
57
+ info(content: ReactNode) {
58
+ showMessage(content, 'info');
59
+ }
60
+ };
package/src/index.tsx CHANGED
@@ -1,7 +1,5 @@
1
- import { Modal, Input, Button } from './compoments/index.js'
2
1
  import ReactDOM from 'react-dom/client'
3
- import { useEffect, useState } from'react'
4
- import Api from './resource.js'
2
+ import VerifyModal from './verify-modal.js'
5
3
 
6
4
  export type ModalConfig = {
7
5
  data: {
@@ -14,87 +12,6 @@ export type ModalConfig = {
14
12
 
15
13
  let modalRoot: ReactDOM.Root | null = null
16
14
 
17
- const ModalDom = ({ config }: { config: ModalConfig }) => {
18
- const [visible, setVisible] = useState(true);
19
- const [countdown, setCountdown] = useState(60);
20
- const [captchaImage, setCaptchaImage] = useState<string>('');
21
- const [captchCode, setCaptchCode] = useState<string>('');
22
- const [captchaKey, setCaptchaKey] = useState<string>('');
23
- const { data } = config || {};
24
- const { mobile } = data || {};
25
-
26
-
27
- const getKey = async () => {
28
- const res = await Api.getCaptchaKey();
29
- const { body: key } = res.data || {};
30
- setCaptchaKey(key);
31
- if(key) {
32
- console.log('res=>key', key);
33
- const image = Api.getCaptchaImgUrl(key) as unknown;
34
- console.log('image', image);
35
- setCaptchaImage(image as string);
36
- }
37
- }
38
-
39
- useEffect(() => {
40
- let timer: number | null = null;
41
- if (visible && countdown > 0) {
42
- timer = setInterval(() => {
43
- setCountdown((prev) => prev - 1);
44
- }, 1000);
45
- }
46
- if (countdown === 0) {
47
- getKey();
48
- }
49
- return () => {
50
- if (timer) clearInterval(timer);
51
- };
52
- }, [visible, countdown]);
53
-
54
- useEffect(() => {
55
- console.log('mobile', mobile);
56
- }, [])
57
-
58
- const handleResend = async() => {
59
- setCountdown(60);
60
- const res = await Api.reSendCode({captchaKey, captcha: captchCode});
61
- console.log('handleResend=>res', res);
62
- // message.success('发送成功');
63
- }
64
-
65
- return (
66
- <Modal
67
- visible={visible}
68
- onClose={() => {
69
- setVisible(false);
70
- config.onClose?.();
71
- }}
72
- >
73
- <div>已发送短信至您的手机:{mobile}</div>
74
- {countdown > 0 ? null : <div style={{ marginTop: 8, display: 'flex', alignItems: 'center', width: 300 }}>
75
- <Input onChange={(e) => {
76
- setCaptchCode(e as string)
77
- }} />
78
-
79
- {captchaImage && <img src={captchaImage} alt="验证码" style={{ width: 100, height: 30, marginLeft: 8 }} onClick={getKey} />}
80
- </div>}
81
- {countdown > 0 ? null : <div>请输入图形验证码后,重新发送验证码</div>}
82
- <div style={{ display: 'flex', alignItems: 'center', gap: 8, marginTop: 8 }}>
83
- <Input
84
- onChange={(val) => {console.log('change', val)}}
85
- />
86
- <Button
87
- disabled={countdown > 0 || !captchCode}
88
- onClick={handleResend}
89
- >
90
- {countdown > 0 ? `${countdown}秒` : '重新发送'}
91
- </Button>
92
- </div>
93
- </Modal>
94
- );
95
- };
96
- // ... existing code ...
97
-
98
15
  export const createMessageVerifyModal = (config: ModalConfig) => {
99
16
  const container = document.createElement('div')
100
17
  container.id = 'antd-modal-container'
@@ -102,7 +19,7 @@ export const createMessageVerifyModal = (config: ModalConfig) => {
102
19
 
103
20
  modalRoot = ReactDOM.createRoot(container)
104
21
  modalRoot.render(
105
- <ModalDom
22
+ <VerifyModal
106
23
  config={{
107
24
  ...config,
108
25
  onClose: () => {
package/src/resource.ts CHANGED
@@ -1,5 +1,5 @@
1
1
  import { assign, axios as instance, customPost } from '@yqg/resource';
2
- // import { message } from 'antd';
2
+ import { message } from './compoments/index.js';
3
3
  import { YQG_SUCCESS } from './utils/status.js';
4
4
 
5
5
  const urlPrefix = '/admin/';
@@ -16,7 +16,7 @@ instance.interceptors.response.use(
16
16
  reader.readAsText(res.data, 'utf-8');
17
17
  reader.onload = () => {
18
18
  const parsedObj = JSON.parse(reader.result as string);
19
- // message.info(parsedObj?.status?.detail);
19
+ message.info(parsedObj?.status?.detail);
20
20
  };
21
21
 
22
22
  return Promise.reject();
@@ -33,14 +33,14 @@ instance.interceptors.response.use(
33
33
  case YQG_SUCCESS:
34
34
  return Promise.resolve(res);
35
35
  default: {
36
- // message.error(detail);
36
+ message.error(detail);
37
37
  return Promise.reject(res);
38
38
  }
39
39
  }
40
40
  },
41
41
  (err: {data: {status: {detail: string}}}) => {
42
42
  const detail = err?.data?.status?.detail || 'Unknown error';
43
- // message.error(detail);
43
+ message.error(detail);
44
44
 
45
45
  return Promise.reject(err);
46
46
  },
@@ -0,0 +1,97 @@
1
+ import { useEffect, useState } from 'react'
2
+ import { Modal, Input, Button, message } from './compoments/index.js'
3
+ import Api from './resource.js'
4
+
5
+ type ModalConfig = {
6
+ data: {
7
+ mobile: string;
8
+ verifyCodeKey: string;
9
+ sendSuccess: boolean;
10
+ };
11
+ onClose?: () => void
12
+ }
13
+ const ModalDom = ({ config }: { config: ModalConfig }) => {
14
+ const [visible, setVisible] = useState(true);
15
+ const [countdown, setCountdown] = useState(3);
16
+ const [captchaImage, setCaptchaImage] = useState<string>('');
17
+ const [captchCode, setCaptchCode] = useState<string>('');
18
+ const [captchaKey, setCaptchaKey] = useState<string>('');
19
+ const { data } = config || {};
20
+ const { mobile } = data || {};
21
+
22
+
23
+ const getKey = async () => {
24
+ const res = await Api.getCaptchaKey();
25
+ const { body: key } = res.data || {};
26
+ setCaptchaKey(key);
27
+ if(key) {
28
+ console.log('res=>key', key);
29
+ const image = Api.getCaptchaImgUrl(key) as unknown;
30
+ console.log('image', image);
31
+ setCaptchaImage(image as string);
32
+ }
33
+ }
34
+
35
+ useEffect(() => {
36
+ let timer: number | null = null;
37
+ if (visible && countdown > 0) {
38
+ timer = setInterval(() => {
39
+ setCountdown((prev) => prev - 1);
40
+ }, 1000);
41
+ }
42
+ if (countdown === 0) {
43
+ getKey();
44
+ }
45
+ return () => {
46
+ if (timer) clearInterval(timer);
47
+ };
48
+ }, [visible, countdown]);
49
+
50
+ useEffect(() => {
51
+ console.log('mobile', mobile);
52
+ }, [mobile])
53
+
54
+ const handleResend = async() => {
55
+ setCountdown(60);
56
+ const res = await Api.reSendCode({captchaKey, captcha: captchCode});
57
+ console.log('handleResend=>res', res);
58
+ message.success('发送成功');
59
+ }
60
+
61
+ return (
62
+ <Modal
63
+ visible={visible}
64
+ onClose={() => {
65
+ setVisible(false);
66
+ config.onClose?.();
67
+ }}
68
+ >
69
+ <div style={{ fontSize: 14, color: '#666' }}>已发送短信至您的手机:{mobile}</div>
70
+ {countdown > 0 ? null : <div style={{ marginBlock: 8, display: 'flex', alignItems: 'center', width: 300 }}>
71
+ <Input
72
+ placeholder="请输入图形验证码"
73
+ onChange={(e) => {
74
+ setCaptchCode(e as string)
75
+ }}
76
+ />
77
+
78
+ {captchaImage && <img src={captchaImage} alt="验证码" style={{ width: 100, height: 30, marginLeft: 8 }} onClick={getKey} />}
79
+ </div>}
80
+ {(countdown > 0 || captchCode) ? null : <div style={{ fontSize: 14, color: 'red' }}>请输入图形验证码后,重新发送验证码</div>}
81
+ <div style={{ display: 'flex', alignItems: 'center', gap: 8, marginTop: 8 }}>
82
+ <Input
83
+ placeholder="请输入验证码"
84
+ onChange={(val) => {console.log('change', val)}}
85
+ />
86
+ <Button
87
+ disabled={countdown > 0 || !captchCode}
88
+ onClick={handleResend}
89
+ >
90
+ {countdown > 0 ? `${countdown}秒` : '重新发送'}
91
+ </Button>
92
+ </div>
93
+ </Modal>
94
+ );
95
+ };
96
+
97
+ export default ModalDom;
package/src/app.tsx DELETED
@@ -1,107 +0,0 @@
1
- // import { useEffect, useState } from 'react'
2
- // import { createPortal } from 'react-dom';
3
- // import { Input, Button, Modal, message } from 'antd';
4
- // import Api from './resource.js'
5
- import '@ant-design/v5-patch-for-react-19';
6
-
7
- interface Props {
8
- data: {
9
- mobile: string;
10
- verifyCodeKey: string;
11
- sendSuccess: boolean;
12
- };
13
- refresh: () => void;
14
- isShow: boolean;
15
- }
16
- const App: React.FC<Props> = () => {
17
- // const { mobile } = data || {};
18
- // const [countdown, setCountdown] = useState(3);
19
- // const [visible, setVisible] = useState(isShow || false);
20
- // const [captchaImage, setCaptchaImage] = useState<string>('');
21
- // const [captchCode, setCaptchCode] = useState<string>('');
22
- // const [captchaKey, setCaptchaKey] = useState<string>('');
23
-
24
- // const getKey = async () => {
25
- // const res = await Api.getCaptchaKey();
26
- // const { body: key } = res.data || {};
27
- // setCaptchaKey(key);
28
- // if(key) {
29
- // console.log('res=>key', key);
30
- // const image = Api.getCaptchaImgUrl(key) as unknown;
31
- // console.log('image', image);
32
- // setCaptchaImage(image as string);
33
- // }
34
- // }
35
-
36
- // useEffect(() => {
37
- // setVisible(true);
38
- // }, [])
39
-
40
- // useEffect(() => {
41
- // let timer: number | null = null;
42
- // if (visible && countdown > 0) {
43
- // timer = setInterval(() => {
44
- // setCountdown((prev) => prev - 1);
45
- // }, 1000);
46
- // }
47
- // if (countdown === 0) {
48
- // getKey();
49
- // }
50
- // return () => {
51
- // if (timer) clearInterval(timer);
52
- // };
53
- // }, [visible, countdown]);
54
-
55
- // const handleResend = async() => {
56
- // setCountdown(60);
57
- // const res = await Api.reSendCode({captchaKey, captcha: captchCode});
58
- // console.log('handleResend=>res', res);
59
- // // message.success('发送成功');
60
- // }
61
-
62
- // const renderModal = (
63
- // <Modal
64
- // open={visible}
65
- // onClose={() => setVisible(false)}
66
- // width={400}
67
- // footer={
68
- // <Button onClick={() => {/* 提交逻辑 */}}>
69
- // 提交
70
- // </Button>
71
- // }
72
- // >
73
- // <div>已发送短信至您的手机:{mobile}</div>
74
- // {countdown > 0 ? null : <div style={{ marginTop: 8, display: 'flex', alignItems: 'center', width: 300 }}>
75
- // <Input onChange={(e) => {
76
- // setCaptchCode(e.target.value as string)
77
- // }} />
78
-
79
- // {captchaImage && <img src={captchaImage} alt="验证码" style={{ width: 100, height: 30, marginLeft: 8 }} onClick={getKey} />}
80
- // </div>}
81
- // {countdown > 0 ? null : <div>请输入图形验证码后,重新发送验证码</div>}
82
- // <div style={{ display: 'flex', alignItems: 'center', gap: 8, marginTop: 8 }}>
83
- // <Input.OTP
84
- // disabled={!captchCode}
85
- // length={6}
86
- // onChange={(val) => {console.log('change', val)}}
87
- // />
88
- // <Button
89
- // disabled={countdown > 0 || !captchCode}
90
- // onClick={handleResend}
91
- // >
92
- // {countdown > 0 ? `${countdown}秒` : '重新发送'}
93
- // </Button>
94
- // </div>
95
- // </Modal>
96
-
97
- // )
98
-
99
- // console.log('captchCode', captchCode);
100
- // if(isShow) {
101
- // return createPortal(renderModal, document.body);
102
- // }
103
- // return null;
104
- return <div>111</div>
105
- }
106
-
107
- export default App;