style: 优化一些css样式
This commit is contained in:
1 parent
8b5b44363f
commit
bfc3f089a8
5 files changed
+190
-32
No files matched your search
@@ -11,12 +11,12 @@
|
||||
|
||||
[**Demo演示**](https://2fa.nezha.pp.ua) https://2fa.nezha.pp.ua
|
||||
|
||||
- 演示站配置了 `OAUTH_ALLOW_ALL=true`变量, 默认允许任何用户登录,正常部署切记 **不要配置OAUTH_ALLOW_ALL变量** | **不要配置OAUTH_ALLOW_ALL变量** | **不要配置OAUTH_ALLOW_ALL变量**
|
||||
- 演示站配置了 `OAUTH_ALLOW_ALL=true`变量, 默认允许任何用户登录,正常部署切记 **不要主动配置OAUTH_ALLOW_ALL变量** | **不要主动配置OAUTH_ALLOW_ALL变量** | **不要主动配置OAUTH_ALLOW_ALL变量**
|
||||
- 演示站数据可以任意修改、删除
|
||||
|
||||
---
|
||||
|
||||
**2FAuth Worker** 是一个轻量级、安全、无服务器的 TOTP 二步验证管理工具。它让你完全掌控自己的 2FA 数据,支持多端跨平台使用,无需购买任何服务器,**完全免费部署在 Cloudflare 边缘网络上**。
|
||||
**2FAuth Worker** 是一个安全、轻量级、无服务器的 TOTP 二步验证管理工具。它让你完全掌控自己的 2FA 数据,支持多端跨平台使用,无需购买任何服务器,**完全免费部署在 Cloudflare 边缘网络上**。
|
||||
|
||||
## ✨ 核心优势与功能
|
||||
|
||||
@@ -51,17 +51,7 @@
|
||||
|
||||
---
|
||||
|
||||
## 🏗️ 全栈项目架构
|
||||
|
||||
本项目遵循现代化的 **Feature-based 垂直模块化架构**:
|
||||
|
||||
- **Frontend (Vue 3 + Vite)**:完全模块化,包含 `vault` (账户管理), `backup` (云端灾备), `auth` (身份验证), `tools` (工具箱) 等独立领域模块。状态管理由 Pinia 驱动。
|
||||
- **Backend (Hono.js)**:极其轻量的边缘框架。配合 `Drizzle ORM` 丝滑读写 D1 数据库。
|
||||
- **前后端天然一体**:由单代码库 (Monorepo) 管理,GitHub Actions 一次触发,同时构建前端产物并以 `Asset/SPA` 模式挂载至 Worker。
|
||||
|
||||
---
|
||||
|
||||
## 🚀 极速部署指南
|
||||
## 🚀 详细部署指南
|
||||
|
||||
本项目设计为通过 **GitHub Actions** 自动化一键部署到你的 Cloudflare 账号下。只需几分钟即可获得你专属的 2FA 管理器。
|
||||
|
||||
@@ -69,23 +59,40 @@
|
||||
1. 注册一个 [Cloudflare](https://dash.cloudflare.com/) 账号。
|
||||
2. **Fork** 本仓库到你的 GitHub 账户。
|
||||
|
||||
### 第二步:配置 Cloudflare D1 数据库
|
||||
### 第二步:获取 Cloudflare Worker部署令牌
|
||||
1. 登录 Cloudflare Dashboard
|
||||
2. [前往获取](https://dash.cloudflare.com/profile/api-tokens)
|
||||
3. 点击“创建令牌”
|
||||
4. 选择使用模版 “编辑 Cloudflare Workers”
|
||||
5. 配置”帐户资源“和”区域资源“
|
||||
6. 依次点击”继续以显示摘要“,点击”创建令牌“
|
||||
7. 复制生成的令牌
|
||||
|
||||
<img width="500" alt="image" src="https://github.com/user-attachments/assets/6487aa6e-e505-4980-aef4-e08172116746" /><br />
|
||||
|
||||
<img width="800" alt="image" src="https://github.com/user-attachments/assets/d4c737f7-2d9f-4cfb-a712-b1af416c8ef6" />
|
||||
|
||||
### 第三步:配置 Cloudflare D1 数据库
|
||||
1. 登录 Cloudflare Dashboard。
|
||||
2. 依次点击左侧菜单的 **存储和数据库** -> **D1 SQL 数据库**。
|
||||
3. 点击 **创建数据库**,命名为 `2fauth-db` (或自定义名称)。
|
||||
4. 创建成功后,复制数据库详情页提供的 **`Database ID`**,备用。
|
||||
|
||||
### 第三步:配置第三方登录
|
||||
*注:系统支持 6 种登录方式,你**至少需要配置一种***。
|
||||
### 第四步:配置第三方登录
|
||||
*注:系统支持 6 种登录方式,你**至少需要配置一种***。推荐使用 `GitHub登录`
|
||||
|
||||
#### 方案一:使用 GitHub 登录
|
||||
#### 使用 GitHub 登录
|
||||
1. 访问 GitHub `Settings` -> `Developer Settings` -> `OAuth Apps` -> **New OAuth App**。
|
||||
|
||||
2. 填写应用信息:
|
||||
- **名称**: `2FAuth`
|
||||
- **Homepage URL**: 填入你预期的站点域名,例如 `https://2fa.yourdomain.workers.dev` (部署后可绑定自定义域名)
|
||||
- **Authorization callback URL**: 重点!必须填写 `https://<你的域名>/oauth/callback`
|
||||
- **Authorization callback URL**: 重点!必须填写 `https://<Homepage URL>/oauth/callback`
|
||||
|
||||
3. 保存生成的 **`Client ID`** 和 **`Client Secret`**。
|
||||
|
||||
<img width="800" alt="image" src="https://github.com/user-attachments/assets/aa03b15f-deb2-4e48-bf4b-e57be342adbb" />
|
||||
|
||||
#### 方案二:使用 Telegram 登录
|
||||
1. 在 Telegram 中搜索并添加官方机器人 **[@BotFather](https://t.me/BotFather)**。
|
||||
2. 发送 `/newbot` 指令,按照提示为你的 2FAuth 创建一个机器人,并获取它的 **`Bot Token`**(如 `123456:ABC-DEF1234ghIkl-zyx57W2v1u123ew11`)。
|
||||
@@ -96,14 +103,14 @@
|
||||
curl "https://api.telegram.org/bot<你的BotToken>/setWebhook?url=https://<你设置的setdomain>/api/telegram/webhook"
|
||||
```
|
||||
|
||||
### 第四步:配置 GitHub Actions Secrets
|
||||
### 第五步:配置 GitHub Actions Secrets
|
||||
前往你 Fork 的 GitHub 仓库的 **Settings** -> **Secrets and variables** -> **Actions** -> **New repository secret**,添加以下必填环境变量:
|
||||
|
||||
#### ☁️ 必填:Cloudflare 资源授权
|
||||
| Secret Name | 说明 | 示例值 |
|
||||
| :--- | :--- | :--- |
|
||||
| `CLOUDFLARE_ACCOUNT_ID` | 你的 CF 账户 ID | `a1b2c3d4e5f6g7h8i9j0` (CF 面板的概述页右下角) |
|
||||
| `CLOUDFLARE_API_TOKEN` | CF 部署令牌 [前往获取](https://dash.cloudflare.com/profile/api-tokens) <br> 点击“创建令牌” -> “创建自定义令牌” <br/> 权限 1: **账户** -> **D1** -> **编辑** <br/>权限 2: **账户** -> **Workers 脚本** -> **编辑** | `r4_xyz...` |
|
||||
| `CLOUDFLARE_API_TOKEN` | CF 部署令牌 | `r4_xyz...` |
|
||||
|
||||
#### 🔐 必填:系统安全参数
|
||||
|
||||
@@ -136,6 +143,8 @@ curl "https://api.telegram.org/bot<你的BotToken>/setWebhook?url=https://<你
|
||||
| **Gitee** | `OAUTH_GITEE_CLIENT_ID`<br>`bcd...` | `OAUTH_GITEE_CLIENT_SECRET`<br>`efg...` | `OAUTH_GITEE_REDIRECT_URI`<br>`https://xxx.workers.dev/oauth/callback` |
|
||||
| **NodeLoc** | `OAUTH_NODELOC_CLIENT_ID`<br>`cde...` | `OAUTH_NODELOC_CLIENT_SECRET`<br>`fgh...` | `OAUTH_NODELOC_REDIRECT_URI`<br>`https://xxx.workers.dev/oauth/callback` |
|
||||
|
||||
<img width="800" alt="image" src="https://github.com/user-attachments/assets/ef907021-303d-4fd5-ba3e-913e8b0014a5" />
|
||||
|
||||
### 第五步:触发自动化部署
|
||||
1. 进入你的 GitHub 仓库的 **Actions** 页面。
|
||||
2. 找到 `Deploy to Cloudflare Workers` 工作流。
|
||||
@@ -146,6 +155,9 @@ curl "https://api.telegram.org/bot<你的BotToken>/setWebhook?url=https://<你
|
||||
- ⚡ 自动将带有静态前端的后端服务绑定至 Cloudflare 边缘节点。
|
||||
5. 部署成功后,控制台会输出你的 `xxx.workers.dev` 链接。登录进去,开始你的私有化 2FA 之旅!
|
||||
|
||||
<img width="800" height="1350" alt="image" src="https://github.com/user-attachments/assets/b2891365-5c1a-4a46-83c6-5cd53dd4b895" />
|
||||
|
||||
|
||||
---
|
||||
|
||||
## 💻 本地极客开发 (Local Development)
|
||||
@@ -170,6 +182,16 @@ npx wrangler d1 execute 2fauth-db-dev --local --env dev --file=schema.sql
|
||||
npm run dev
|
||||
```
|
||||
|
||||
## 🏗️ 全栈项目架构
|
||||
|
||||
本项目遵循现代化的 **Feature-based 垂直模块化架构**:
|
||||
|
||||
- **Frontend (Vue 3 + Vite)**:完全模块化,包含 `vault` (账户管理), `backup` (云端灾备), `auth` (身份验证), `tools` (工具箱) 等独立领域模块。状态管理由 Pinia 驱动。
|
||||
- **Backend (Hono.js)**:极其轻量的边缘框架。配合 `Drizzle ORM` 丝滑读写 D1 数据库。
|
||||
- **前后端天然一体**:由单代码库 (Monorepo) 管理,GitHub Actions 一次触发,同时构建前端产物并以 `Asset/SPA` 模式挂载至 Worker。
|
||||
|
||||
---
|
||||
|
||||
---
|
||||
|
||||
## 🛡️ 安全性声明 (Security Policy)
|
||||
|
||||
@@ -1,5 +1,9 @@
|
||||
{
|
||||
"name": "backend",
|
||||
"name": "2FAuth Worker",
|
||||
"version": "1.0.2",
|
||||
"description": "A Secure 2FA Management Tool running on Cloudflare Workers",
|
||||
"author": "nap0o",
|
||||
"license": "AGPL-3.0",
|
||||
"type": "module",
|
||||
"scripts": {
|
||||
"dev": "wrangler dev --config wrangler.dev.toml --host 0.0.0.0 --port 8787 --test-scheduled",
|
||||
|
||||
@@ -56,11 +56,29 @@
|
||||
<el-drawer
|
||||
v-model="layoutStore.showMobileMenu"
|
||||
direction="ltr"
|
||||
size="240px"
|
||||
size="280px"
|
||||
:with-header="false"
|
||||
:lock-scroll="false"
|
||||
>
|
||||
<div class="drawer-content">
|
||||
<!-- 移动端用户信息卡片 -->
|
||||
<div class="user-info-card" v-if="authUserStore.userInfo">
|
||||
<div class="user-card-content">
|
||||
<el-avatar :size="40" :src="authUserStore.userInfo?.avatar" class="user-avatar">
|
||||
{{ authUserStore.userInfo?.username?.charAt(0)?.toUpperCase() }}
|
||||
</el-avatar>
|
||||
<div class="user-detail">
|
||||
<div class="user-name-row">
|
||||
<span class="user-name">{{ authUserStore.userInfo?.username }}</span>
|
||||
<i class="status-dot" :class="{ 'is-online': authUserStore.userInfo?.online !== false }"></i>
|
||||
</div>
|
||||
<div class="user-provider" v-if="authUserStore.userInfo?.provider">
|
||||
{{ authUserStore.userInfo?.provider }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<el-menu
|
||||
:default-active="activeTab"
|
||||
class="side-menu"
|
||||
@@ -166,3 +184,67 @@ const handleLogout = async () => {
|
||||
ElMessage.success(t('auth.logout_success'))
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
.user-info-card {
|
||||
margin: 0px 20px 0px 20px;
|
||||
padding-bottom: 20px;
|
||||
border-bottom: 0.2px solid var(--el-border-color-lighter);
|
||||
}
|
||||
|
||||
.user-card-content {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 15px;
|
||||
}
|
||||
|
||||
.user-avatar {
|
||||
border: 2px solid var(--el-color-primary-light-8);
|
||||
box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
|
||||
}
|
||||
|
||||
.user-detail {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.user-name-row {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 6px;
|
||||
margin-bottom: 2px;
|
||||
}
|
||||
|
||||
.user-name {
|
||||
font-size: 15px;
|
||||
font-weight: 600;
|
||||
color: var(--el-text-color-primary);
|
||||
line-height: 1.2;
|
||||
}
|
||||
|
||||
.status-dot {
|
||||
width: 7px;
|
||||
height: 7px;
|
||||
border-radius: 50%;
|
||||
background-color: #909399; /* 默认灰色 */
|
||||
display: inline-block;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.status-dot.is-online {
|
||||
background-color: #67C23A; /* 在线绿色 */
|
||||
box-shadow: 0 0 4px rgba(103, 194, 58, 0.5);
|
||||
}
|
||||
|
||||
.user-provider {
|
||||
font-size: 11px;
|
||||
color: var(--el-text-color-secondary);
|
||||
background: var(--el-fill-color);
|
||||
padding: 1px;
|
||||
border-radius: 2px;
|
||||
display: inline-block;
|
||||
width: fit-content;
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 0.5px;
|
||||
}
|
||||
</style>
|
||||
@@ -1,7 +1,9 @@
|
||||
<template>
|
||||
<div class="vault-list-wrapper" style="min-height: 400px;">
|
||||
<div class="vault-content">
|
||||
<div class="toolbar" style="margin-bottom: 20px; display: flex; gap: 15px; align-items: center; justify-content: space-between; flex-wrap: wrap;">
|
||||
<!-- 移动端偏移 45px (Header2), PC端偏移 61px (Header1) -->
|
||||
<el-affix :offset="layoutStore.isMobile ? 45 : 61" @change="(val) => isToolbarFixed = val">
|
||||
<div class="toolbar" :class="{ 'is-affixed': isToolbarFixed }" style="margin-bottom: 20px; display: flex; gap: 15px; align-items: center; justify-content: space-between; flex-wrap: wrap;">
|
||||
<div style="display: flex; align-items: center; gap: 10px; flex: 1;">
|
||||
<el-input
|
||||
v-model="searchQuery"
|
||||
@@ -27,6 +29,7 @@
|
||||
<el-button v-else @click="selectAllLoaded" plain>{{ $t('common.select_all_loaded') }}</el-button>
|
||||
</div>
|
||||
</div>
|
||||
</el-affix>
|
||||
|
||||
<!-- 1. 加载状态 -->
|
||||
<div v-if="(isInitializing || isLoading || isFetching) && vault.length === 0" class="loading-state" style="display: flex; flex-direction: column; justify-content: center; align-items: center; min-height: 400px; color: var(--el-text-color-secondary);">
|
||||
@@ -226,6 +229,7 @@ const {
|
||||
|
||||
// mount 到 handleUnlocked 完成前保持 true,确保本地缓存读取期间显示 loading 动画
|
||||
const isInitializing = ref(true)
|
||||
const isToolbarFixed = ref(false)
|
||||
|
||||
// --- 解锁回调:离线优先,秒开首屏 ---
|
||||
const handleUnlocked = async () => {
|
||||
@@ -248,3 +252,49 @@ defineExpose({ fetchVault })
|
||||
onMounted(handleUnlocked)
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
/* 搜索栏吸顶过渡动画 */
|
||||
.toolbar {
|
||||
transition: padding 0.3s ease, background-color 0.3s ease;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
/* 共有吸顶属性 */
|
||||
.toolbar.is-affixed {
|
||||
z-index: 2000;
|
||||
margin-bottom: 0 !important;
|
||||
}
|
||||
|
||||
/* 移动端吸顶效果:全屏、背景、边框 */
|
||||
@media (max-width: 767px) {
|
||||
.toolbar.is-affixed {
|
||||
position: fixed !important;
|
||||
left: 0 !important;
|
||||
right: 0 !important;
|
||||
width: 100vw !important;
|
||||
background-color: var(--glass-card-bg, rgba(255, 255, 255, 0.95));
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--el-border-color-light);
|
||||
padding: 10px 20px !important;
|
||||
border-radius: 0 !important;
|
||||
}
|
||||
}
|
||||
|
||||
/* PC 端吸顶效果:保持原有宽度,无背景色和下边框 */
|
||||
@media (min-width: 768px) {
|
||||
.toolbar.is-affixed {
|
||||
background-color: var(--el-bg-color-page) !important;
|
||||
border-bottom: none !important;
|
||||
padding: 10px 0px 20px 0px !important;
|
||||
}
|
||||
}
|
||||
|
||||
/* 适配暗黑模式 (仅移动端需要背景) */
|
||||
@media (max-width: 767px) {
|
||||
html.dark .toolbar.is-affixed {
|
||||
background-color: rgba(30, 30, 30, 0.85);
|
||||
border-bottom: 1px solid var(--el-border-color-dark);
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -512,15 +512,15 @@
|
||||
}
|
||||
},
|
||||
"suggestions": {
|
||||
"encryption_key_suggestion": "请复制下方为您预生成的高强度随机密钥。随后前往 Cloudflare 后台 -> Workers 和 Pages -> 2fauth-worker -> 设置 -> 变量和机密,将其填入 ENCRYPTION_KEY。",
|
||||
"jwt_secret_suggestion": "请复制下方为您预生成的高强度随机密钥。前往 Cloudflare 后台 -> Workers 和 Pages -> 2fauth-worker -> 设置 -> 变量和机密, 将其填入 JWT_SECRET",
|
||||
"oauth_allow_all_suggestion": "请立刻前往 Cloudflare 后台 -> Workers 和 Pages -> 2fauth-worker -> 设置 -> 变量和机密,将环境变量 OAUTH_ALLOW_ALL 删除,或将其值修改为 false。",
|
||||
"allowed_users_suggestion": "请在 Cloudflare 后台 -> Workers 和 Pages -> 2fauth-worker -> 设置 -> 变量和机密中添加 OAUTH_ALLOWED_USERS,并填入您在 GitHub(或其它平台)上对应的注册邮箱地址(多个以英文逗号分隔)。",
|
||||
"github_config_suggestion": "请核对获取的 GitHub OAuth Apps 密钥信息,然后前往 Cloudflare 后台 -> Workers 和 Pages -> 2fauth-worker -> 设置 -> 变量和机密,将环境变量 OAUTH_GITHUB_CLIENT_ID、OAUTH_GITHUB_CLIENT_SECRET、OAUTH_GITHUB_REDIRECT_URI 填入",
|
||||
"telegram_config_suggestion": "请在 BotFather 检查机器人配置,确保信息填全,然后前往 Cloudflare 后台 -> Workers 和 Pages -> 2fauth-worker -> 设置 -> 变量和机密,将环境变量 OAUTH_TELEGRAM_BOT_NAME、OAUTH_TELEGRAM_BOT_TOKEN、OAUTH_TELEGRAM_REDIRECT_URI 填入",
|
||||
"google_config_suggestion": "请前往 Google Cloud Console 检查凭据配置,然后前往 Cloudflare 后台 -> Workers 和 Pages -> 2fauth-worker -> 设置 -> 变量和机密,将环境变量 OAUTH_GOOGLE_CLIENT_ID、OAUTH_GOOGLE_CLIENT_SECRET、OAUTH_GOOGLE_REDIRECT_URI 填入",
|
||||
"nodeloc_config_suggestion": "请前往 NodeLoc 面板检查您的开发者凭据,然后前往 Cloudflare 后台 -> Workers 和 Pages -> 2fauth-worker -> 设置 -> 变量和机密,将环境变量 OAUTH_NODELOC_CLIENT_ID、OAUTH_NODELOC_CLIENT_SECRET、OAUTH_NODELOC_REDIRECT_URI 填入",
|
||||
"gitee_config_suggestion": "请核对 Gitee 开发者凭据,然后前往 Cloudflare 后台 -> Workers 和 Pages -> 2fauth-worker -> 设置 -> 变量和机密,将环境变量 OAUTH_GITEE_CLIENT_ID、OAUTH_GITEE_CLIENT_SECRET、OAUTH_GITEE_REDIRECT_URI 填入",
|
||||
"encryption_key_suggestion": "请复制下方为您预生成的高强度随机密钥。请立刻前往 Fork的Github仓库 -> Settings -> Secrets and variables -> Actions -> 将其填入 ENCRYPTION_KEY",
|
||||
"jwt_secret_suggestion": "请复制下方为您预生成的高强度随机密钥。请立刻前往 Fork的Github仓库 -> Settings -> Secrets and variables -> Actions -> 将其填入 JWT_SECRET",
|
||||
"oauth_allow_all_suggestion": "请立刻前往 Fork的Github仓库 -> Settings -> Secrets and variables -> Actions,将环境变量 OAUTH_ALLOW_ALL 删除,或将其值修改为 false。",
|
||||
"allowed_users_suggestion": "请在 Fork的Github仓库 -> Settings -> Secrets and variables -> Actions中添加 OAUTH_ALLOWED_USERS,并填入您在 GitHub(或其它平台)上对应的注册邮箱地址(多个以英文逗号分隔)。",
|
||||
"github_config_suggestion": "请核对获取的 GitHub OAuth Apps 密钥信息,然后前往 Fork的Github仓库 -> Settings -> Secrets and variables -> Actions,将环境变量 OAUTH_GITHUB_CLIENT_ID、OAUTH_GITHUB_CLIENT_SECRET、OAUTH_GITHUB_REDIRECT_URI 填入",
|
||||
"telegram_config_suggestion": "请在 BotFather 检查机器人配置,确保信息填全,然后前往 Fork的Github仓库 -> Settings -> Secrets and variables -> Actions,将环境变量 OAUTH_TELEGRAM_BOT_NAME、OAUTH_TELEGRAM_BOT_TOKEN、OAUTH_TELEGRAM_REDIRECT_URI 填入",
|
||||
"google_config_suggestion": "请前往 Google Cloud Console 检查凭据配置,然后前往 Fork的Github仓库 -> Settings -> Secrets and variables -> Actions,将环境变量 OAUTH_GOOGLE_CLIENT_ID、OAUTH_GOOGLE_CLIENT_SECRET、OAUTH_GOOGLE_REDIRECT_URI 填入",
|
||||
"nodeloc_config_suggestion": "请前往 NodeLoc 面板检查您的开发者凭据,然后前往 Fork的Github仓库 -> Settings -> Secrets and variables -> Actions,将环境变量 OAUTH_NODELOC_CLIENT_ID、OAUTH_NODELOC_CLIENT_SECRET、OAUTH_NODELOC_REDIRECT_URI 填入",
|
||||
"gitee_config_suggestion": "请核对 Gitee 开发者凭据,然后前往 Fork的Github仓库 -> Settings -> Secrets and variables -> Actions,将环境变量 OAUTH_GITEE_CLIENT_ID、OAUTH_GITEE_CLIENT_SECRET、OAUTH_GITEE_REDIRECT_URI 填入",
|
||||
"cloudflare_config_suggestion": "需要四位一体的参数:Client ID, Secret, Org Domain, Redirect URI,然后前往 Cloudflare 后台 -> Workers 和 Pages -> 2fauth-worker -> 设置 -> 变量和机密,将环境变量 OAUTH_CLOUDFLARE_CLIENT_ID、OAUTH_CLOUDFLARE_CLIENT_SECRET、OAUTH_CLOUDFLARE_REDIRECT_URI 填入",
|
||||
"no_provider_suggestion": "阅读2Fauth Worker 的 README,挑选最适合您且配置最简单的一种登录方式,按照其说明获取 Client ID 与 Secret 并在云端配置。"
|
||||
}
|
||||
|
||||
Reference in new issue
Block a user