mirror of
https://github.com/labring/FastGPT.git
synced 2025-07-23 05:12:39 +00:00
feat: 手机验证码作为用户凭证
This commit is contained in:
@@ -11,6 +11,9 @@
|
||||
"format": "prettier --config \"./.prettierrc.js\" --write \"./src/**/*.{ts,tsx,scss}\""
|
||||
},
|
||||
"dependencies": {
|
||||
"@alicloud/dysmsapi20170525": "^2.0.23",
|
||||
"@alicloud/openapi-client": "^0.4.5",
|
||||
"@alicloud/tea-util": "^1.4.5",
|
||||
"@chakra-ui/icons": "^2.0.17",
|
||||
"@chakra-ui/react": "^2.5.1",
|
||||
"@emotion/react": "^11.10.6",
|
||||
|
179
pnpm-lock.yaml
generated
179
pnpm-lock.yaml
generated
@@ -1,6 +1,9 @@
|
||||
lockfileVersion: 5.4
|
||||
|
||||
specifiers:
|
||||
'@alicloud/dysmsapi20170525': ^2.0.23
|
||||
'@alicloud/openapi-client': ^0.4.5
|
||||
'@alicloud/tea-util': ^1.4.5
|
||||
'@chakra-ui/icons': ^2.0.17
|
||||
'@chakra-ui/react': ^2.5.1
|
||||
'@emotion/react': ^11.10.6
|
||||
@@ -61,6 +64,9 @@ specifiers:
|
||||
zustand: ^4.3.5
|
||||
|
||||
dependencies:
|
||||
'@alicloud/dysmsapi20170525': registry.npmmirror.com/@alicloud/dysmsapi20170525/2.0.23
|
||||
'@alicloud/openapi-client': registry.npmmirror.com/@alicloud/openapi-client/0.4.5
|
||||
'@alicloud/tea-util': registry.npmmirror.com/@alicloud/tea-util/1.4.5
|
||||
'@chakra-ui/icons': registry.npmmirror.com/@chakra-ui/icons/2.0.17_react@18.2.0
|
||||
'@chakra-ui/react': registry.npmmirror.com/@chakra-ui/react/2.5.1_e6pzu3hsaqmql4fl7jx73ckiym
|
||||
'@emotion/react': registry.npmmirror.com/@emotion/react/11.10.6_pmekkgnqduwlme35zpnqhenc34
|
||||
@@ -124,6 +130,117 @@ devDependencies:
|
||||
|
||||
packages:
|
||||
|
||||
registry.npmmirror.com/@alicloud/credentials/2.2.6:
|
||||
resolution: {integrity: sha512-jG+msY77dHmAF3x+8VTy7fEgORyXLHmDci8t92HeipBdCHsPptDegA++GEwKgR7f6G4wvafYt+aqMZ1iligdrQ==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@alicloud/credentials/-/credentials-2.2.6.tgz}
|
||||
name: '@alicloud/credentials'
|
||||
version: 2.2.6
|
||||
dependencies:
|
||||
'@alicloud/tea-typescript': registry.npmmirror.com/@alicloud/tea-typescript/1.8.0
|
||||
httpx: registry.npmmirror.com/httpx/2.2.7
|
||||
ini: registry.npmmirror.com/ini/1.3.8
|
||||
kitx: registry.npmmirror.com/kitx/2.1.0
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/@alicloud/dysmsapi20170525/2.0.23:
|
||||
resolution: {integrity: sha512-C02xj9S2ZPL13SciChlIY3s5+PiOM13jEGZSn+L92aiWYCBqTlpx9UMwNKBNWImMSOlG71IOSYfsQggaoIY+4Q==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@alicloud/dysmsapi20170525/-/dysmsapi20170525-2.0.23.tgz}
|
||||
name: '@alicloud/dysmsapi20170525'
|
||||
version: 2.0.23
|
||||
dependencies:
|
||||
'@alicloud/endpoint-util': registry.npmmirror.com/@alicloud/endpoint-util/0.0.1
|
||||
'@alicloud/openapi-client': registry.npmmirror.com/@alicloud/openapi-client/0.4.5
|
||||
'@alicloud/openapi-util': registry.npmmirror.com/@alicloud/openapi-util/0.3.1
|
||||
'@alicloud/tea-typescript': registry.npmmirror.com/@alicloud/tea-typescript/1.8.0
|
||||
'@alicloud/tea-util': registry.npmmirror.com/@alicloud/tea-util/1.4.5
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/@alicloud/endpoint-util/0.0.1:
|
||||
resolution: {integrity: sha512-+pH7/KEXup84cHzIL6UJAaPqETvln4yXlD9JzlrqioyCSaWxbug5FUobsiI6fuUOpw5WwoB3fWAtGbFnJ1K3Yg==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@alicloud/endpoint-util/-/endpoint-util-0.0.1.tgz}
|
||||
name: '@alicloud/endpoint-util'
|
||||
version: 0.0.1
|
||||
dependencies:
|
||||
'@alicloud/tea-typescript': registry.npmmirror.com/@alicloud/tea-typescript/1.8.0
|
||||
kitx: registry.npmmirror.com/kitx/2.1.0
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/@alicloud/gateway-spi/0.0.8:
|
||||
resolution: {integrity: sha512-KM7fu5asjxZPmrz9sJGHJeSU+cNQNOxW+SFmgmAIrITui5hXL2LB+KNRuzWmlwPjnuA2X3/keq9h6++S9jcV5g==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@alicloud/gateway-spi/-/gateway-spi-0.0.8.tgz}
|
||||
name: '@alicloud/gateway-spi'
|
||||
version: 0.0.8
|
||||
dependencies:
|
||||
'@alicloud/credentials': registry.npmmirror.com/@alicloud/credentials/2.2.6
|
||||
'@alicloud/tea-typescript': registry.npmmirror.com/@alicloud/tea-typescript/1.8.0
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/@alicloud/openapi-client/0.4.5:
|
||||
resolution: {integrity: sha512-x1blwhfPOVkH/JCLWFssFRWDL0C75RToun9AwhNV+84gqJB2/GUipm3quHGLon8JiQ0DQ9YBUho2rukSoAvhJQ==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@alicloud/openapi-client/-/openapi-client-0.4.5.tgz}
|
||||
name: '@alicloud/openapi-client'
|
||||
version: 0.4.5
|
||||
dependencies:
|
||||
'@alicloud/credentials': registry.npmmirror.com/@alicloud/credentials/2.2.6
|
||||
'@alicloud/gateway-spi': registry.npmmirror.com/@alicloud/gateway-spi/0.0.8
|
||||
'@alicloud/openapi-util': registry.npmmirror.com/@alicloud/openapi-util/0.3.1
|
||||
'@alicloud/tea-typescript': registry.npmmirror.com/@alicloud/tea-typescript/1.8.0
|
||||
'@alicloud/tea-util': registry.npmmirror.com/@alicloud/tea-util/1.4.5
|
||||
'@alicloud/tea-xml': registry.npmmirror.com/@alicloud/tea-xml/0.0.2
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/@alicloud/openapi-util/0.3.1:
|
||||
resolution: {integrity: sha512-6mGT+hs+SXismZi/CEkjPhhbn2U3qTT/Qv/RXAYFA1DC3Jk4/YaX3N7RtpgdzOhdD7uI8XtNkaULKHZY3BrtxQ==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@alicloud/openapi-util/-/openapi-util-0.3.1.tgz}
|
||||
name: '@alicloud/openapi-util'
|
||||
version: 0.3.1
|
||||
dependencies:
|
||||
'@alicloud/tea-typescript': registry.npmmirror.com/@alicloud/tea-typescript/1.8.0
|
||||
'@alicloud/tea-util': registry.npmmirror.com/@alicloud/tea-util/1.4.5
|
||||
kitx: registry.npmmirror.com/kitx/2.1.0
|
||||
sm3: registry.npmmirror.com/sm3/1.0.3
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/@alicloud/tea-typescript/1.8.0:
|
||||
resolution: {integrity: sha512-CWXWaquauJf0sW30mgJRVu9aaXyBth5uMBCUc+5vKTK1zlgf3hIqRUjJZbjlwHwQ5y9anwcu18r48nOZb7l2QQ==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@alicloud/tea-typescript/-/tea-typescript-1.8.0.tgz}
|
||||
name: '@alicloud/tea-typescript'
|
||||
version: 1.8.0
|
||||
dependencies:
|
||||
'@types/node': registry.npmmirror.com/@types/node/12.20.55
|
||||
httpx: registry.npmmirror.com/httpx/2.2.7
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/@alicloud/tea-util/1.4.5:
|
||||
resolution: {integrity: sha512-7NuThYUi90/ivT/ORKusm0NVKlc1khPTtlzTR77xEqSBt7d24Ee/Lo70hx9PWP28nHpIZ1gM0NKYBtpq7HUDlg==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@alicloud/tea-util/-/tea-util-1.4.5.tgz}
|
||||
name: '@alicloud/tea-util'
|
||||
version: 1.4.5
|
||||
dependencies:
|
||||
'@alicloud/tea-typescript': registry.npmmirror.com/@alicloud/tea-typescript/1.8.0
|
||||
kitx: registry.npmmirror.com/kitx/2.1.0
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/@alicloud/tea-xml/0.0.2:
|
||||
resolution: {integrity: sha512-Xs7v5y7YSNSDDYmiDWAC0/013VWPjS3dQU4KezSLva9VGiTVPaL3S7Nk4NrTmAYCG6MKcrRj/nGEDIWL5KRoPg==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@alicloud/tea-xml/-/tea-xml-0.0.2.tgz}
|
||||
name: '@alicloud/tea-xml'
|
||||
version: 0.0.2
|
||||
dependencies:
|
||||
'@alicloud/tea-typescript': registry.npmmirror.com/@alicloud/tea-typescript/1.8.0
|
||||
'@types/xml2js': registry.npmmirror.com/@types/xml2js/0.4.11
|
||||
xml2js: registry.npmmirror.com/xml2js/0.4.23
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/@ampproject/remapping/2.2.0:
|
||||
resolution: {integrity: sha512-qRmjj8nj9qmLTQXXmaR1cck3UXSRMPrbsLJAasZpF+t3riI71BXed5ebIOYwQntykeZuhjsdweEc9BxH5Jc26w==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@ampproject/remapping/-/remapping-2.2.0.tgz}
|
||||
name: '@ampproject/remapping'
|
||||
@@ -5031,6 +5148,18 @@ packages:
|
||||
version: 0.7.31
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/@types/node/12.20.55:
|
||||
resolution: {integrity: sha512-J8xLz7q2OFulZ2cyGTLE1TbbZcjpno7FaN6zdJNrgAdrJ+DZzh/uFR6YrTb4C+nXakvud8Q4+rbhoIWlYQbUFQ==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@types/node/-/node-12.20.55.tgz}
|
||||
name: '@types/node'
|
||||
version: 12.20.55
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/@types/node/14.18.42:
|
||||
resolution: {integrity: sha512-xefu+RBie4xWlK8hwAzGh3npDz/4VhF6icY/shU+zv/1fNn+ZVG7T7CRwe9LId9sAYRPxI+59QBPuKL3WpyGRg==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@types/node/-/node-14.18.42.tgz}
|
||||
name: '@types/node'
|
||||
version: 14.18.42
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/@types/node/18.14.0:
|
||||
resolution: {integrity: sha512-5EWrvLmglK+imbCJY0+INViFWUHg1AHel1sq4ZVSfdcNqGy9Edv3UB9IIzzg+xPaUcAgZYcfVs2fBcwDeZzU0A==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@types/node/-/node-18.14.0.tgz}
|
||||
name: '@types/node'
|
||||
@@ -5133,6 +5262,14 @@ packages:
|
||||
'@types/webidl-conversions': registry.npmmirror.com/@types/webidl-conversions/7.0.0
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/@types/xml2js/0.4.11:
|
||||
resolution: {integrity: sha512-JdigeAKmCyoJUiQljjr7tQG3if9NkqGUgwEUqBvV0N7LM4HyQk7UXCnusRa1lnvXAEYJ8mw8GtZWioagNztOwA==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@types/xml2js/-/xml2js-0.4.11.tgz}
|
||||
name: '@types/xml2js'
|
||||
version: 0.4.11
|
||||
dependencies:
|
||||
'@types/node': registry.npmmirror.com/@types/node/18.14.0
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/@typescript-eslint/parser/5.52.0_7kw3g6rralp5ps6mg3uyzz6azm:
|
||||
resolution: {integrity: sha512-e2KiLQOZRo4Y0D/b+3y08i3jsekoSkOYStROYmPUnGMEoA0h+k2qOH5H6tcjIc68WDvGwH+PaOrP1XRzLJ6QlA==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@typescript-eslint/parser/-/parser-5.52.0.tgz}
|
||||
id: registry.npmmirror.com/@typescript-eslint/parser/5.52.0
|
||||
@@ -7650,6 +7787,17 @@ packages:
|
||||
- supports-color
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/httpx/2.2.7:
|
||||
resolution: {integrity: sha512-Wjh2JOAah0pdczfqL8NC5378G7jMt0Zcpn8U+yyxAiejjlagzSTQgJHuVvka2VNPQlKfoGehYRc79WKq9E4gDw==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/httpx/-/httpx-2.2.7.tgz}
|
||||
name: httpx
|
||||
version: 2.2.7
|
||||
dependencies:
|
||||
'@types/node': registry.npmmirror.com/@types/node/14.18.42
|
||||
debug: registry.npmmirror.com/debug/4.3.4
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/human-signals/3.0.1:
|
||||
resolution: {integrity: sha512-rQLskxnM/5OCldHo+wNXbpVgDn5A17CUoKX+7Sokwaknlq7CdSnphy0W39GU8dw59XiCXmFXDg4fRuckQRKewQ==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/human-signals/-/human-signals-3.0.1.tgz}
|
||||
name: human-signals
|
||||
@@ -8284,6 +8432,14 @@ packages:
|
||||
commander: registry.npmmirror.com/commander/8.3.0
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/kitx/2.1.0:
|
||||
resolution: {integrity: sha512-C/5v9MtIX7aHGOjwn5BmrrbNkJSf7i0R5mRzmh13GSAdRqQ7bYQo/Su2pTYNylFicqKNTVX3HML9k1u8k51+pQ==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/kitx/-/kitx-2.1.0.tgz}
|
||||
name: kitx
|
||||
version: 2.1.0
|
||||
dependencies:
|
||||
'@types/node': registry.npmmirror.com/@types/node/12.20.55
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/kleur/4.1.5:
|
||||
resolution: {integrity: sha512-o+NO+8WrRiQEE4/7nwRJhN1HWpVmJm511pBHUxPLtp0BUISzlBplORYSmTclCnJvQq2tKu/sgl3xVpkc7ZWuQQ==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/kleur/-/kleur-4.1.5.tgz}
|
||||
name: kleur
|
||||
@@ -10598,6 +10754,12 @@ packages:
|
||||
is-fullwidth-code-point: registry.npmmirror.com/is-fullwidth-code-point/4.0.0
|
||||
dev: true
|
||||
|
||||
registry.npmmirror.com/sm3/1.0.3:
|
||||
resolution: {integrity: sha512-KyFkIfr8QBlFG3uc3NaljaXdYcsbRy1KrSfc4tsQV8jW68jAktGeOcifu530Vx/5LC+PULHT0Rv8LiI8Gw+c1g==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/sm3/-/sm3-1.0.3.tgz}
|
||||
name: sm3
|
||||
version: 1.0.3
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/smart-buffer/4.2.0:
|
||||
resolution: {integrity: sha512-94hK0Hh8rPqQl2xXc3HsaBoOXKV20MToPkcXvwbISWLEs+64sBq5kFgn2kJDHb1Pry9yrP0dxrCI9RRci7RXKg==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/smart-buffer/-/smart-buffer-4.2.0.tgz}
|
||||
name: smart-buffer
|
||||
@@ -11618,6 +11780,16 @@ packages:
|
||||
- supports-color
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/xml2js/0.4.23:
|
||||
resolution: {integrity: sha512-ySPiMjM0+pLDftHgXY4By0uswI3SPKLDw/i3UXbnO8M/p28zqexCUoPmQFrYD+/1BzhGJSs2i1ERWKJAtiLrug==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/xml2js/-/xml2js-0.4.23.tgz}
|
||||
name: xml2js
|
||||
version: 0.4.23
|
||||
engines: {node: '>=4.0.0'}
|
||||
dependencies:
|
||||
sax: registry.npmmirror.com/sax/1.1.6
|
||||
xmlbuilder: registry.npmmirror.com/xmlbuilder/11.0.1
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/xmlbuilder/10.1.1:
|
||||
resolution: {integrity: sha512-OyzrcFLL/nb6fMGHbiRDuPup9ljBycsdCypwuyg5AAHvyWzGfChJpCXMG88AGTIMFhGZ9RccFN1e6lhg3hkwKg==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/xmlbuilder/-/xmlbuilder-10.1.1.tgz}
|
||||
name: xmlbuilder
|
||||
@@ -11625,6 +11797,13 @@ packages:
|
||||
engines: {node: '>=4.0'}
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/xmlbuilder/11.0.1:
|
||||
resolution: {integrity: sha512-fDlsI/kFEx7gLvbecc0/ohLG50fugQp8ryHzMTuW9vSa1GJ0XYWKnhsUx7oie3G98+r56aTQIUB4kht42R3JvA==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/xmlbuilder/-/xmlbuilder-11.0.1.tgz}
|
||||
name: xmlbuilder
|
||||
version: 11.0.1
|
||||
engines: {node: '>=4.0'}
|
||||
dev: false
|
||||
|
||||
registry.npmmirror.com/xregexp/2.0.0:
|
||||
resolution: {integrity: sha512-xl/50/Cf32VsGq/1R8jJE5ajH1yMCQkpmoS10QbFZWl2Oor4H0Me64Pu2yxvsRWK3m6soJbmGfzSR7BYmDcWAA==, registry: https://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/xregexp/-/xregexp-2.0.0.tgz}
|
||||
name: xregexp
|
||||
|
@@ -9,7 +9,7 @@ wx号: fastgpt123
|
||||
|
||||
|
||||
### 快速开始
|
||||
1. 使用邮箱注册账号。
|
||||
1. 使用手机号注册账号。
|
||||
2. 进入账号页面,添加关联账号,目前只有 openai 的账号可以添加,直接去 openai 官网,把 API Key 粘贴过来。
|
||||
3. 如果填写了自己的 openai 账号,使用时会直接用你的账号。如果没有填写,需要付费使用平台的账号。
|
||||
4. 进入模型页,创建一个模型,建议直接用 ChatGPT。
|
||||
|
@@ -1,50 +1,55 @@
|
||||
import { GET, POST, PUT } from './request';
|
||||
import { createHashPassword, Obj2Query } from '@/utils/tools';
|
||||
import { ResLogin } from './response/user';
|
||||
import { EmailTypeEnum } from '@/constants/common';
|
||||
import { UserAuthTypeEnum } from '@/constants/common';
|
||||
import { UserType, UserUpdateParams } from '@/types/user';
|
||||
import type { PagingData, RequestPaging } from '@/types';
|
||||
import { BillSchema, PaySchema } from '@/types/mongoSchema';
|
||||
import { adaptBill } from '@/utils/adapt';
|
||||
|
||||
export const sendCodeToEmail = ({ email, type }: { email: string; type: `${EmailTypeEnum}` }) =>
|
||||
GET('/user/sendEmail', { email, type });
|
||||
export const sendAuthCode = ({
|
||||
username,
|
||||
type
|
||||
}: {
|
||||
username: string;
|
||||
type: `${UserAuthTypeEnum}`;
|
||||
}) => GET('/user/sendAuthCode', { username, type });
|
||||
|
||||
export const getTokenLogin = () => GET<UserType>('/user/tokenLogin');
|
||||
|
||||
export const postRegister = ({
|
||||
email,
|
||||
phone,
|
||||
password,
|
||||
code
|
||||
}: {
|
||||
email: string;
|
||||
phone: string;
|
||||
code: string;
|
||||
password: string;
|
||||
}) =>
|
||||
POST<ResLogin>('/user/register', {
|
||||
email,
|
||||
phone,
|
||||
code,
|
||||
password: createHashPassword(password)
|
||||
});
|
||||
|
||||
export const postFindPassword = ({
|
||||
email,
|
||||
username,
|
||||
code,
|
||||
password
|
||||
}: {
|
||||
email: string;
|
||||
username: string;
|
||||
code: string;
|
||||
password: string;
|
||||
}) =>
|
||||
POST<ResLogin>('/user/updatePasswordByCode', {
|
||||
email,
|
||||
username,
|
||||
code,
|
||||
password: createHashPassword(password)
|
||||
});
|
||||
|
||||
export const postLogin = ({ email, password }: { email: string; password: string }) =>
|
||||
export const postLogin = ({ username, password }: { username: string; password: string }) =>
|
||||
POST<ResLogin>('/user/loginByPassword', {
|
||||
email,
|
||||
username,
|
||||
password: createHashPassword(password)
|
||||
});
|
||||
|
||||
|
@@ -1,4 +1,4 @@
|
||||
export enum EmailTypeEnum {
|
||||
export enum UserAuthTypeEnum {
|
||||
register = 'register',
|
||||
findPassword = 'findPassword'
|
||||
}
|
||||
|
@@ -1,6 +1,6 @@
|
||||
import { useState, useMemo, useCallback } from 'react';
|
||||
import { sendCodeToEmail } from '@/api/user';
|
||||
import { EmailTypeEnum } from '@/constants/common';
|
||||
import { sendAuthCode } from '@/api/user';
|
||||
import { UserAuthTypeEnum } from '@/constants/common';
|
||||
let timer: any;
|
||||
import { useToast } from './useToast';
|
||||
|
||||
@@ -19,11 +19,11 @@ export const useSendCode = () => {
|
||||
}, [codeCountDown]);
|
||||
|
||||
const sendCode = useCallback(
|
||||
async ({ email, type }: { email: string; type: `${EmailTypeEnum}` }) => {
|
||||
async ({ username, type }: { username: string; type: `${UserAuthTypeEnum}` }) => {
|
||||
setCodeSending(true);
|
||||
try {
|
||||
await sendCodeToEmail({
|
||||
email,
|
||||
await sendAuthCode({
|
||||
username,
|
||||
type
|
||||
});
|
||||
setCodeCountDown(60);
|
||||
|
@@ -7,24 +7,24 @@ import { generateToken } from '@/service/utils/tools';
|
||||
|
||||
export default async function handler(req: NextApiRequest, res: NextApiResponse) {
|
||||
try {
|
||||
const { email, password } = req.body;
|
||||
const { username, password } = req.body;
|
||||
|
||||
if (!email || !password) {
|
||||
if (!username || !password) {
|
||||
throw new Error('缺少参数');
|
||||
}
|
||||
|
||||
await connectToDatabase();
|
||||
|
||||
// 检测邮箱是否存在
|
||||
const authEmail = await User.findOne({
|
||||
email
|
||||
// 检测用户是否存在
|
||||
const authUser = await User.findOne({
|
||||
username
|
||||
});
|
||||
if (!authEmail) {
|
||||
throw new Error('邮箱未注册');
|
||||
if (!authUser) {
|
||||
throw new Error('用户未注册');
|
||||
}
|
||||
|
||||
const user = await User.findOne({
|
||||
email,
|
||||
username,
|
||||
password
|
||||
});
|
||||
|
||||
|
@@ -5,23 +5,29 @@ import { User } from '@/service/models/user';
|
||||
import { AuthCode } from '@/service/models/authCode';
|
||||
import { connectToDatabase } from '@/service/mongo';
|
||||
import { generateToken } from '@/service/utils/tools';
|
||||
import { EmailTypeEnum } from '@/constants/common';
|
||||
import { UserAuthTypeEnum } from '@/constants/common';
|
||||
|
||||
export default async function handler(req: NextApiRequest, res: NextApiResponse<any>) {
|
||||
try {
|
||||
const { email, code, password } = req.body;
|
||||
const { phone, code, password } = req.body;
|
||||
|
||||
if (!email || !code || !password) {
|
||||
if (!phone || !code || !password) {
|
||||
throw new Error('缺少参数');
|
||||
}
|
||||
|
||||
const reg = /^1[3456789]\d{9}$/;
|
||||
|
||||
if (!reg.test(phone)) {
|
||||
throw new Error('手机号格式错误');
|
||||
}
|
||||
|
||||
await connectToDatabase();
|
||||
|
||||
// 验证码校验
|
||||
// 验证码校验. 注册只接收手机号
|
||||
const authCode = await AuthCode.findOne({
|
||||
email,
|
||||
username: phone,
|
||||
code,
|
||||
type: EmailTypeEnum.register,
|
||||
type: UserAuthTypeEnum.register,
|
||||
expiredTime: { $gte: Date.now() }
|
||||
});
|
||||
|
||||
@@ -31,15 +37,15 @@ export default async function handler(req: NextApiRequest, res: NextApiResponse<
|
||||
|
||||
// 重名校验
|
||||
const authRepeat = await User.findOne({
|
||||
email
|
||||
username: phone
|
||||
});
|
||||
|
||||
if (authRepeat) {
|
||||
throw new Error('邮箱已被注册');
|
||||
throw new Error('手机号已被注册');
|
||||
}
|
||||
|
||||
const response = await User.create({
|
||||
email,
|
||||
username: phone,
|
||||
password
|
||||
});
|
||||
|
||||
@@ -50,6 +56,11 @@ export default async function handler(req: NextApiRequest, res: NextApiResponse<
|
||||
throw new Error('获取用户信息异常');
|
||||
}
|
||||
|
||||
// 删除验证码记录
|
||||
await AuthCode.deleteMany({
|
||||
username: phone
|
||||
});
|
||||
|
||||
jsonRes(res, {
|
||||
data: {
|
||||
token: generateToken(user._id),
|
||||
|
@@ -2,28 +2,27 @@
|
||||
import type { NextApiRequest, NextApiResponse } from 'next';
|
||||
import { jsonRes } from '@/service/response';
|
||||
import { AuthCode } from '@/service/models/authCode';
|
||||
import { connectToDatabase, User } from '@/service/mongo';
|
||||
import { sendCode } from '@/service/utils/sendEmail';
|
||||
import { EmailTypeEnum } from '@/constants/common';
|
||||
import { connectToDatabase } from '@/service/mongo';
|
||||
import { sendPhoneCode, sendEmailCode } from '@/service/utils/sendNote';
|
||||
import { UserAuthTypeEnum } from '@/constants/common';
|
||||
import { customAlphabet } from 'nanoid';
|
||||
const nanoid = customAlphabet('1234567890', 6);
|
||||
|
||||
export default async function handler(req: NextApiRequest, res: NextApiResponse) {
|
||||
try {
|
||||
const { email, type } = req.query as { email: string; type: `${EmailTypeEnum}` };
|
||||
const { username, type } = req.query as { username: string; type: `${UserAuthTypeEnum}` };
|
||||
|
||||
if (!email || !type) {
|
||||
if (!username || !type) {
|
||||
throw new Error('缺少参数');
|
||||
}
|
||||
|
||||
await connectToDatabase();
|
||||
|
||||
let code = '';
|
||||
for (let i = 0; i < 6; i++) {
|
||||
code += Math.floor(Math.random() * 10);
|
||||
}
|
||||
let code = nanoid();
|
||||
|
||||
// 判断 1 分钟内是否有重复数据
|
||||
const authCode = await AuthCode.findOne({
|
||||
email,
|
||||
username,
|
||||
type,
|
||||
expiredTime: { $gte: Date.now() + 4 * 60 * 1000 } // 如果有一个记录的过期时间,大于当前+4分钟,说明距离上次发送还没到1分钟。(因为默认创建时,过期时间是未来5分钟)
|
||||
});
|
||||
@@ -34,13 +33,17 @@ export default async function handler(req: NextApiRequest, res: NextApiResponse)
|
||||
|
||||
// 创建 auth 记录
|
||||
await AuthCode.create({
|
||||
email,
|
||||
username,
|
||||
type,
|
||||
code
|
||||
});
|
||||
|
||||
if (username.includes('@')) {
|
||||
await sendEmailCode(username, code, type);
|
||||
} else {
|
||||
// 发送验证码
|
||||
await sendCode(email as string, code, type as `${EmailTypeEnum}`);
|
||||
await sendPhoneCode(username, code);
|
||||
}
|
||||
|
||||
jsonRes(res, {
|
||||
message: '发送验证码成功'
|
@@ -5,13 +5,13 @@ import { User } from '@/service/models/user';
|
||||
import { AuthCode } from '@/service/models/authCode';
|
||||
import { connectToDatabase } from '@/service/mongo';
|
||||
import { generateToken } from '@/service/utils/tools';
|
||||
import { EmailTypeEnum } from '@/constants/common';
|
||||
import { UserAuthTypeEnum } from '@/constants/common';
|
||||
|
||||
export default async function handler(req: NextApiRequest, res: NextApiResponse<any>) {
|
||||
try {
|
||||
const { email, code, password } = req.body;
|
||||
const { username, code, password } = req.body;
|
||||
|
||||
if (!email || !code || !password) {
|
||||
if (!username || !code || !password) {
|
||||
throw new Error('缺少参数');
|
||||
}
|
||||
|
||||
@@ -19,9 +19,9 @@ export default async function handler(req: NextApiRequest, res: NextApiResponse<
|
||||
|
||||
// 验证码校验
|
||||
const authCode = await AuthCode.findOne({
|
||||
email,
|
||||
username,
|
||||
code,
|
||||
type: EmailTypeEnum.findPassword,
|
||||
type: UserAuthTypeEnum.findPassword,
|
||||
expiredTime: { $gte: Date.now() }
|
||||
});
|
||||
|
||||
@@ -32,16 +32,16 @@ export default async function handler(req: NextApiRequest, res: NextApiResponse<
|
||||
// 更新对应的记录
|
||||
await User.updateOne(
|
||||
{
|
||||
email
|
||||
username
|
||||
},
|
||||
{
|
||||
password
|
||||
}
|
||||
);
|
||||
|
||||
// 根据 email 获取用户信息
|
||||
// 根据 username 获取用户信息
|
||||
const user = await User.findOne({
|
||||
email
|
||||
username
|
||||
});
|
||||
|
||||
if (!user) {
|
||||
|
@@ -14,7 +14,7 @@ interface Props {
|
||||
}
|
||||
|
||||
interface RegisterType {
|
||||
email: string;
|
||||
username: string;
|
||||
code: string;
|
||||
password: string;
|
||||
password2: string;
|
||||
@@ -36,10 +36,10 @@ const RegisterForm = ({ setPageType, loginSuccess }: Props) => {
|
||||
const { codeSending, sendCodeText, sendCode, codeCountDown } = useSendCode();
|
||||
|
||||
const onclickSendCode = useCallback(async () => {
|
||||
const check = await trigger('email');
|
||||
const check = await trigger('username');
|
||||
if (!check) return;
|
||||
sendCode({
|
||||
email: getValues('email'),
|
||||
username: getValues('username'),
|
||||
type: 'findPassword'
|
||||
});
|
||||
}, [getValues, sendCode, trigger]);
|
||||
@@ -47,12 +47,12 @@ const RegisterForm = ({ setPageType, loginSuccess }: Props) => {
|
||||
const [requesting, setRequesting] = useState(false);
|
||||
|
||||
const onclickFindPassword = useCallback(
|
||||
async ({ email, code, password }: RegisterType) => {
|
||||
async ({ username, code, password }: RegisterType) => {
|
||||
setRequesting(true);
|
||||
try {
|
||||
loginSuccess(
|
||||
await postFindPassword({
|
||||
email,
|
||||
username,
|
||||
code,
|
||||
password
|
||||
})
|
||||
@@ -78,23 +78,24 @@ const RegisterForm = ({ setPageType, loginSuccess }: Props) => {
|
||||
找回 FastGPT 账号
|
||||
</Box>
|
||||
<form onSubmit={handleSubmit(onclickFindPassword)}>
|
||||
<FormControl mt={8} isInvalid={!!errors.email}>
|
||||
<FormControl mt={8} isInvalid={!!errors.username}>
|
||||
<Input
|
||||
placeholder="邮箱"
|
||||
placeholder="邮箱/手机号"
|
||||
size={mediaLgMd}
|
||||
{...register('email', {
|
||||
required: '邮箱不能为空',
|
||||
{...register('username', {
|
||||
required: '邮箱/手机号不能为空',
|
||||
pattern: {
|
||||
value: /^[A-Za-z0-9]+([_\.][A-Za-z0-9]+)*@([A-Za-z0-9\-]+\.)+[A-Za-z]{2,6}$/,
|
||||
message: '邮箱错误'
|
||||
value:
|
||||
/(^1[3456789]\d{9}$)|(^[A-Za-z0-9]+([_\.][A-Za-z0-9]+)*@([A-Za-z0-9\-]+\.)+[A-Za-z]{2,6}$)/,
|
||||
message: '邮箱/手机号格式错误'
|
||||
}
|
||||
})}
|
||||
></Input>
|
||||
<FormErrorMessage position={'absolute'} fontSize="xs">
|
||||
{!!errors.email && errors.email.message}
|
||||
{!!errors.username && errors.username.message}
|
||||
</FormErrorMessage>
|
||||
</FormControl>
|
||||
<FormControl mt={8} isInvalid={!!errors.email}>
|
||||
<FormControl mt={8} isInvalid={!!errors.username}>
|
||||
<Flex>
|
||||
<Input
|
||||
flex={1}
|
||||
|
@@ -13,7 +13,7 @@ interface Props {
|
||||
}
|
||||
|
||||
interface LoginFormType {
|
||||
email: string;
|
||||
username: string;
|
||||
password: string;
|
||||
}
|
||||
|
||||
@@ -29,12 +29,12 @@ const LoginForm = ({ setPageType, loginSuccess }: Props) => {
|
||||
const [requesting, setRequesting] = useState(false);
|
||||
|
||||
const onclickLogin = useCallback(
|
||||
async ({ email, password }: LoginFormType) => {
|
||||
async ({ username, password }: LoginFormType) => {
|
||||
setRequesting(true);
|
||||
try {
|
||||
loginSuccess(
|
||||
await postLogin({
|
||||
email,
|
||||
username,
|
||||
password
|
||||
})
|
||||
);
|
||||
@@ -59,20 +59,21 @@ const LoginForm = ({ setPageType, loginSuccess }: Props) => {
|
||||
登录 FastGPT
|
||||
</Box>
|
||||
<form onSubmit={handleSubmit(onclickLogin)}>
|
||||
<FormControl mt={8} isInvalid={!!errors.email}>
|
||||
<FormControl mt={8} isInvalid={!!errors.username}>
|
||||
<Input
|
||||
placeholder="邮箱"
|
||||
placeholder="邮箱/手机号"
|
||||
size={mediaLgMd}
|
||||
{...register('email', {
|
||||
required: '邮箱不能为空',
|
||||
{...register('username', {
|
||||
required: '邮箱/手机号不能为空',
|
||||
pattern: {
|
||||
value: /^[A-Za-z0-9]+([_\.][A-Za-z0-9]+)*@([A-Za-z0-9\-]+\.)+[A-Za-z]{2,6}$/,
|
||||
message: '邮箱错误'
|
||||
value:
|
||||
/(^1[3456789]\d{9}$)|(^[A-Za-z0-9]+([_\.][A-Za-z0-9]+)*@([A-Za-z0-9\-]+\.)+[A-Za-z]{2,6}$)/,
|
||||
message: '邮箱/手机号格式错误'
|
||||
}
|
||||
})}
|
||||
></Input>
|
||||
<FormErrorMessage position={'absolute'} fontSize="xs">
|
||||
{!!errors.email && errors.email.message}
|
||||
{!!errors.username && errors.username.message}
|
||||
</FormErrorMessage>
|
||||
</FormControl>
|
||||
<FormControl mt={8} isInvalid={!!errors.password}>
|
||||
|
@@ -14,7 +14,7 @@ interface Props {
|
||||
}
|
||||
|
||||
interface RegisterType {
|
||||
email: string;
|
||||
phone: string;
|
||||
password: string;
|
||||
password2: string;
|
||||
code: string;
|
||||
@@ -36,10 +36,10 @@ const RegisterForm = ({ setPageType, loginSuccess }: Props) => {
|
||||
const { codeSending, sendCodeText, sendCode, codeCountDown } = useSendCode();
|
||||
|
||||
const onclickSendCode = useCallback(async () => {
|
||||
const check = await trigger('email');
|
||||
const check = await trigger('phone');
|
||||
if (!check) return;
|
||||
sendCode({
|
||||
email: getValues('email'),
|
||||
username: getValues('phone'),
|
||||
type: 'register'
|
||||
});
|
||||
}, [getValues, sendCode, trigger]);
|
||||
@@ -47,12 +47,12 @@ const RegisterForm = ({ setPageType, loginSuccess }: Props) => {
|
||||
const [requesting, setRequesting] = useState(false);
|
||||
|
||||
const onclickRegister = useCallback(
|
||||
async ({ email, password, code }: RegisterType) => {
|
||||
async ({ phone, password, code }: RegisterType) => {
|
||||
setRequesting(true);
|
||||
try {
|
||||
loginSuccess(
|
||||
await postRegister({
|
||||
email,
|
||||
phone,
|
||||
code,
|
||||
password
|
||||
})
|
||||
@@ -78,23 +78,23 @@ const RegisterForm = ({ setPageType, loginSuccess }: Props) => {
|
||||
注册 FastGPT 账号
|
||||
</Box>
|
||||
<form onSubmit={handleSubmit(onclickRegister)}>
|
||||
<FormControl mt={8} isInvalid={!!errors.email}>
|
||||
<FormControl mt={8} isInvalid={!!errors.phone}>
|
||||
<Input
|
||||
placeholder="邮箱"
|
||||
placeholder="手机号"
|
||||
size={mediaLgMd}
|
||||
{...register('email', {
|
||||
required: '邮箱不能为空',
|
||||
{...register('phone', {
|
||||
required: '手机号不能为空',
|
||||
pattern: {
|
||||
value: /^[A-Za-z0-9]+([_\.][A-Za-z0-9]+)*@([A-Za-z0-9\-]+\.)+[A-Za-z]{2,6}$/,
|
||||
message: '邮箱错误'
|
||||
value: /^1[3456789]\d{9}$/,
|
||||
message: '手机号格式错误'
|
||||
}
|
||||
})}
|
||||
></Input>
|
||||
<FormErrorMessage position={'absolute'} fontSize="xs">
|
||||
{!!errors.email && errors.email.message}
|
||||
{!!errors.phone && errors.phone.message}
|
||||
</FormErrorMessage>
|
||||
</FormControl>
|
||||
<FormControl mt={8} isInvalid={!!errors.email}>
|
||||
<FormControl mt={8} isInvalid={!!errors.phone}>
|
||||
<Flex>
|
||||
<Input
|
||||
flex={1}
|
||||
|
@@ -51,8 +51,8 @@ const NumberSetting = () => {
|
||||
账号信息
|
||||
</Box>
|
||||
<Flex mt={6} alignItems={'center'}>
|
||||
<Box flex={'0 0 60px'}>邮箱:</Box>
|
||||
<Box>{userInfo?.email}</Box>
|
||||
<Box flex={'0 0 60px'}>用户账号:</Box>
|
||||
<Box>{userInfo?.username}</Box>
|
||||
</Flex>
|
||||
<Box mt={6}>
|
||||
<Flex alignItems={'center'}>
|
||||
|
@@ -2,7 +2,7 @@ import { Schema, model, models, Model } from 'mongoose';
|
||||
import { AuthCodeSchema as AuthCodeType } from '@/types/mongoSchema';
|
||||
|
||||
const AuthCodeSchema = new Schema({
|
||||
email: {
|
||||
username: {
|
||||
type: String,
|
||||
required: true
|
||||
},
|
||||
|
@@ -3,7 +3,8 @@ import { hashPassword } from '@/service/utils/tools';
|
||||
import { PRICE_SCALE } from '@/constants/common';
|
||||
import { UserModelSchema } from '@/types/mongoSchema';
|
||||
const UserSchema = new Schema({
|
||||
email: {
|
||||
username: {
|
||||
// 可以是手机/邮箱,新的验证都只用手机
|
||||
type: String,
|
||||
required: true,
|
||||
unique: true // 唯一
|
||||
|
@@ -1,63 +0,0 @@
|
||||
import * as nodemailer from 'nodemailer';
|
||||
import { EmailTypeEnum } from '@/constants/common';
|
||||
import dayjs from 'dayjs';
|
||||
|
||||
const myEmail = process.env.MY_MAIL;
|
||||
let mailTransport = nodemailer.createTransport({
|
||||
// host: 'smtp.qq.email',
|
||||
service: 'qq',
|
||||
secure: true, //安全方式发送,建议都加上
|
||||
auth: {
|
||||
user: myEmail,
|
||||
pass: process.env.MAILE_CODE
|
||||
}
|
||||
});
|
||||
|
||||
const emailMap: { [key: string]: any } = {
|
||||
[EmailTypeEnum.register]: {
|
||||
subject: '注册 FastGPT 账号',
|
||||
html: (code: string) => `<div>您正在注册 FastGPT 账号,验证码为:${code}</div>`
|
||||
},
|
||||
[EmailTypeEnum.findPassword]: {
|
||||
subject: '修改 FastGPT 密码',
|
||||
html: (code: string) => `<div>您正在修改 FastGPT 账号密码,验证码为:${code}</div>`
|
||||
}
|
||||
};
|
||||
|
||||
export const sendCode = (email: string, code: string, type: `${EmailTypeEnum}`) => {
|
||||
return new Promise((resolve, reject) => {
|
||||
const options = {
|
||||
from: `"FastGPT" ${myEmail}`,
|
||||
to: email,
|
||||
subject: emailMap[type]?.subject,
|
||||
html: emailMap[type]?.html(code)
|
||||
};
|
||||
mailTransport.sendMail(options, function (err, msg) {
|
||||
if (err) {
|
||||
console.log('send email error->', err);
|
||||
reject('邮箱异常');
|
||||
} else {
|
||||
resolve('');
|
||||
}
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
export const sendTrainSucceed = (email: string, modelName: string) => {
|
||||
return new Promise((resolve, reject) => {
|
||||
const options = {
|
||||
from: `"FastGPT" ${myEmail}`,
|
||||
to: email,
|
||||
subject: '模型训练完成通知',
|
||||
html: `你的模型 ${modelName} 已于 ${dayjs().format('YYYY-MM-DD HH:mm')} 训练完成!`
|
||||
};
|
||||
mailTransport.sendMail(options, function (err, msg) {
|
||||
if (err) {
|
||||
console.log('send email error->', err);
|
||||
reject('邮箱异常');
|
||||
} else {
|
||||
resolve('');
|
||||
}
|
||||
});
|
||||
});
|
||||
};
|
72
src/service/utils/sendNote.ts
Normal file
72
src/service/utils/sendNote.ts
Normal file
@@ -0,0 +1,72 @@
|
||||
import * as nodemailer from 'nodemailer';
|
||||
import { UserAuthTypeEnum } from '@/constants/common';
|
||||
import dayjs from 'dayjs';
|
||||
import Dysmsapi, * as dysmsapi from '@alicloud/dysmsapi20170525';
|
||||
// @ts-ignore
|
||||
import * as OpenApi from '@alicloud/openapi-client';
|
||||
// @ts-ignore
|
||||
import * as Util from '@alicloud/tea-util';
|
||||
|
||||
const myEmail = process.env.MY_MAIL;
|
||||
const mailTransport = nodemailer.createTransport({
|
||||
// host: 'smtp.qq.phone',
|
||||
service: 'qq',
|
||||
secure: true, //安全方式发送,建议都加上
|
||||
auth: {
|
||||
user: myEmail,
|
||||
pass: process.env.MAILE_CODE
|
||||
}
|
||||
});
|
||||
|
||||
const emailMap: { [key: string]: any } = {
|
||||
[UserAuthTypeEnum.register]: {
|
||||
subject: '注册 FastGPT 账号',
|
||||
html: (code: string) => `<div>您正在注册 FastGPT 账号,验证码为:${code}</div>`
|
||||
},
|
||||
[UserAuthTypeEnum.findPassword]: {
|
||||
subject: '修改 FastGPT 密码',
|
||||
html: (code: string) => `<div>您正在修改 FastGPT 账号密码,验证码为:${code}</div>`
|
||||
}
|
||||
};
|
||||
|
||||
export const sendEmailCode = (email: string, code: string, type: `${UserAuthTypeEnum}`) => {
|
||||
return new Promise((resolve, reject) => {
|
||||
const options = {
|
||||
from: `"FastGPT" ${myEmail}`,
|
||||
to: email,
|
||||
subject: emailMap[type]?.subject,
|
||||
html: emailMap[type]?.html(code)
|
||||
};
|
||||
mailTransport.sendMail(options, function (err, msg) {
|
||||
if (err) {
|
||||
console.log('send email error->', err);
|
||||
reject('发生邮件异常');
|
||||
} else {
|
||||
resolve('');
|
||||
}
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
export const sendPhoneCode = async (phone: string, code: string) => {
|
||||
const accessKeyId = process.env.aliAccessKeyId;
|
||||
const accessKeySecret = process.env.aliAccessKeySecret;
|
||||
const signName = process.env.aliSignName;
|
||||
const templateCode = process.env.aliTemplateCode;
|
||||
const endpoint = 'dysmsapi.aliyuncs.com';
|
||||
|
||||
const sendSmsRequest = new dysmsapi.SendSmsRequest({
|
||||
phoneNumbers: phone,
|
||||
signName,
|
||||
templateCode,
|
||||
templateParam: `{"code":${code}}`
|
||||
});
|
||||
|
||||
const config = new OpenApi.Config({ accessKeyId, accessKeySecret, endpoint });
|
||||
const client = new Dysmsapi(config);
|
||||
const runtime = new Util.RuntimeOptions({});
|
||||
const res = await client.sendSmsWithOptions(sendSmsRequest, runtime);
|
||||
if (res.body.code !== 'OK') {
|
||||
return Promise.reject(res.body.message || '发送短信失败');
|
||||
}
|
||||
};
|
4
src/types/mongoSchema.d.ts
vendored
4
src/types/mongoSchema.d.ts
vendored
@@ -11,7 +11,7 @@ export type ServiceName = 'openai';
|
||||
|
||||
export interface UserModelSchema {
|
||||
_id: string;
|
||||
email: string;
|
||||
username: string;
|
||||
password: string;
|
||||
balance: number;
|
||||
openaiKey: string;
|
||||
@@ -20,7 +20,7 @@ export interface UserModelSchema {
|
||||
|
||||
export interface AuthCodeSchema {
|
||||
_id: string;
|
||||
email: string;
|
||||
username: string;
|
||||
code: string;
|
||||
type: 'register' | 'findPassword';
|
||||
expiredTime: number;
|
||||
|
7
src/types/user.d.ts
vendored
7
src/types/user.d.ts
vendored
@@ -1,11 +1,6 @@
|
||||
export enum UserNumberEnum {
|
||||
phone = 'phone',
|
||||
wx = 'wx'
|
||||
}
|
||||
|
||||
export interface UserType {
|
||||
_id: string;
|
||||
email: string;
|
||||
username: string;
|
||||
openaiKey: string;
|
||||
balance: number;
|
||||
}
|
||||
|
Reference in New Issue
Block a user