65 lines
2.0 KiB
TypeScript
65 lines
2.0 KiB
TypeScript
import { checkParamsNeeded } from 'zutils/utils/net.util'
|
|
import { IPlat } from './IPlat'
|
|
import { ZError } from 'zutils'
|
|
import { NonceRecord } from 'modules/NonceRecord'
|
|
import { SiweMessage } from 'siwe'
|
|
import { DocumentType } from '@typegoose/typegoose'
|
|
import { AccountClass } from 'modules/Account'
|
|
import { Wallet } from 'modules/Wallet'
|
|
|
|
// check if none is hex string with 24 length, or is timestamp within 5 minutes
|
|
export const checkNonce = (nonce: string) => {
|
|
if (!nonce) {
|
|
throw new ZError(11, 'Invalid nonce')
|
|
}
|
|
// use regex to check if nonce is 24 length hex string
|
|
if (nonce.length === 13) {
|
|
const timestamp = parseInt(nonce)
|
|
if (Date.now() - timestamp > 5 * 60 * 1000) {
|
|
throw new ZError(13, 'nonce expired')
|
|
}
|
|
} else {
|
|
if (!/^[0-9a-f]{24}$/.test(nonce)) {
|
|
throw new ZError(11, 'Invalid nonce.')
|
|
}
|
|
}
|
|
}
|
|
export class PlatExternalWallet implements IPlat {
|
|
async verifyToken(req: any): Promise<any> {
|
|
// here code is signature
|
|
let { code, message } = req.params
|
|
checkParamsNeeded(code, message)
|
|
checkNonce(message.nonce)
|
|
if (message.nonce.length === 24) {
|
|
let record = await NonceRecord.findById(message.nonce)
|
|
if (!record || record.status !== 0) {
|
|
throw new ZError(12, 'nonce invalid')
|
|
}
|
|
if (record.expired < Date.now()) {
|
|
throw new ZError(13, 'nonce expired')
|
|
}
|
|
record.status = 1
|
|
await record.save()
|
|
}
|
|
const msgSign = new SiweMessage(message)
|
|
try {
|
|
await msgSign.verify({ signature: code, nonce: message.nonce })
|
|
} catch (e) {
|
|
throw new ZError(14, 'signature invalid')
|
|
}
|
|
|
|
const openId = message.address
|
|
let data: any = {}
|
|
const { api_platform } = req.headers
|
|
if (api_platform) {
|
|
data.platform = api_platform
|
|
}
|
|
|
|
return { openId, data }
|
|
}
|
|
|
|
async afterLogin(user: DocumentType<AccountClass>) {
|
|
await Wallet.insertOrUpdate({ account: user.id }, { address: user.openId, nweRecord: false })
|
|
}
|
|
}
|