add d1kt SSO integration: OAuth2 login via WebView + phone binding

This commit is contained in:
2026-08-31 16:50:49 +08:00
parent 3652ebda07
commit daa73e2b98
6 changed files with 454 additions and 0 deletions

View File

@@ -0,0 +1,60 @@
#!/usr/bin/env node
/**
* 在第一课堂 MongoDB 中注册口语训练 App 的 OAuth2 客户端。
* 在第一课堂服务器上运行:
* cd /path/to/typing_practiceweb
* MONGODB_URI=<uri> node scripts/register_oral_trainer_oauth_client.js
*/
const mongoose = require('mongoose');
const CLIENT_ID = 'oral-trainer-app';
const CLIENT_SECRET = 'oral-trainer-secret-2024';
const CLIENT_NAME = '口语训练 App';
async function main() {
const uri = process.env.MONGODB_URI;
if (!uri) {
console.error('MONGODB_URI is required.');
process.exit(1);
}
await mongoose.connect(uri);
const db = mongoose.connection.db;
const collection = db.collection('oauth2clients');
const existing = await collection.findOne({ clientId: CLIENT_ID });
if (existing) {
console.log(`Client "${CLIENT_ID}" already exists. Updating redirect URIs...`);
await collection.updateOne(
{ clientId: CLIENT_ID },
{ $set: { clientSecret: CLIENT_SECRET, name: CLIENT_NAME } }
);
} else {
console.log(`Creating OAuth2 client "${CLIENT_ID}"...`);
await collection.insertOne({
clientId: CLIENT_ID,
clientSecret: CLIENT_SECRET,
name: CLIENT_NAME,
redirectUris: [
'oraltrainer://oauth/callback',
],
grants: ['authorization_code'],
scope: ['openid', 'profile', 'email', 'firstname', 'lastname', 'username'],
createdAt: new Date(),
linkedUsers: [],
});
}
console.log('Done. Client config:');
console.log(` client_id: ${CLIENT_ID}`);
console.log(` client_secret: ${CLIENT_SECRET}`);
console.log(` redirect_uri: oraltrainer://oauth/callback`);
await mongoose.disconnect();
}
main().catch((err) => {
console.error(err);
process.exit(1);
});