chore: 拆分生产 ideship / 测试 nanafa 两套环境配置
All checks were successful
Build and Deploy Front / deploy (push) Successful in 5m39s
All checks were successful
Build and Deploy Front / deploy (push) Successful in 5m39s
生产用 .env.production 与 pnpm build;测试用 .env.nanafa 与 pnpm build:test;本地 pnpm dev / dev:ideship 可切换。 Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
parent
d52e10b09e
commit
c0c37a4eac
@ -1,11 +1,18 @@
|
||||
# VITE_API_BASE_URL='http://localhost:5173/'
|
||||
|
||||
# 本地开发统一走线上 Admin API(与 /rbac、/order 等 Vite 代理一致)
|
||||
VITE_OMS_ADMIN_URL=http://api.nanafa.com/admin
|
||||
# =============================================================================
|
||||
# 本地开发默认 → 测试环境 oms.nanafa.com / api.nanafa.com
|
||||
# 切换到生产 API:pnpm dev:ideship (加载 .env.ideship)
|
||||
# 发版构建:pnpm build(生产) / pnpm build:test(测试)
|
||||
# =============================================================================
|
||||
VITE_DEPLOY_TARGET=nanafa
|
||||
VITE_API_ORIGIN=http://api.nanafa.com
|
||||
VITE_API_ADMIN_URL=http://api.nanafa.com/admin
|
||||
VITE_OMS_ADMIN_URL=http://api.nanafa.com/admin
|
||||
VITE_API_ASSET_ORIGIN=http://api.nanafa.com/admin
|
||||
|
||||
# 企业微信客服
|
||||
VITE_WECOM_KF_URL=https://work.weixin.qq.com/kfid/kfcae09c206f6c7045a
|
||||
|
||||
# 智谱 AI(接口映射脚本生成)
|
||||
# 在 https://open.bigmodel.cn 申请 API Key
|
||||
VITE_ZHIPU_API_KEY=85bbbef6bafd4ca383eef04189decd07.lKVQHcLGtYE8oUn5
|
||||
VITE_ZHIPU_BASE_URL=/zhipu-api
|
||||
VITE_ZHIPU_MODEL=glm-5.1
|
||||
|
||||
11
.env.ideship
Normal file
11
.env.ideship
Normal file
@ -0,0 +1,11 @@
|
||||
# =============================================================================
|
||||
# 本地开发直连生产 API(ideship.com)— pnpm dev:ideship
|
||||
# 仅用于联调生产;正式发版请用 pnpm build(.env.production)
|
||||
# =============================================================================
|
||||
VITE_DEPLOY_TARGET=ideship
|
||||
VITE_API_ORIGIN=https://api.ideship.com
|
||||
VITE_API_ADMIN_URL=https://api.ideship.com/admin
|
||||
VITE_OMS_ADMIN_URL=https://api.ideship.com/admin
|
||||
VITE_API_ASSET_ORIGIN=https://api.ideship.com/admin
|
||||
|
||||
VITE_WECOM_KF_URL=https://work.weixin.qq.com/kfid/kfcae09c206f6c7045a
|
||||
12
.env.nanafa
Normal file
12
.env.nanafa
Normal file
@ -0,0 +1,12 @@
|
||||
# =============================================================================
|
||||
# 测试环境(oms.nanafa.com)— pnpm build:test → vite build --mode nanafa
|
||||
# 三套 API:http://api.nanafa.com/{admin|itfx|track}
|
||||
# 前端站点:https://oms.nanafa.com
|
||||
# =============================================================================
|
||||
VITE_DEPLOY_TARGET=nanafa
|
||||
VITE_API_ORIGIN=http://api.nanafa.com
|
||||
VITE_API_ADMIN_URL=http://api.nanafa.com/admin
|
||||
VITE_API_ASSET_ORIGIN=http://api.nanafa.com/admin
|
||||
VITE_OMS_ADMIN_URL=http://api.nanafa.com/admin
|
||||
|
||||
VITE_WECOM_KF_URL=https://work.weixin.qq.com/kfid/kfcae09c206f6c7045a
|
||||
@ -0,0 +1,13 @@
|
||||
# =============================================================================
|
||||
# 生产环境(ideship.com)— vite build / vite build --mode production
|
||||
# 三套 API:https://api.ideship.com/{admin|itfx|track}
|
||||
# 前端站点:https://ideship.com
|
||||
# =============================================================================
|
||||
VITE_DEPLOY_TARGET=ideship
|
||||
VITE_API_ORIGIN=https://api.ideship.com
|
||||
VITE_API_ADMIN_URL=https://api.ideship.com/admin
|
||||
VITE_API_ASSET_ORIGIN=https://api.ideship.com/admin
|
||||
VITE_OMS_ADMIN_URL=https://api.ideship.com/admin
|
||||
|
||||
# 企业微信客服
|
||||
VITE_WECOM_KF_URL=https://work.weixin.qq.com/kfid/kfcae09c206f6c7045a
|
||||
@ -202,7 +202,15 @@ flowchart TD
|
||||
|
||||
## 4. 接口说明
|
||||
|
||||
API 前缀:`https://api.nanafa.com/admin`(`ASPNETCORE_PATHBASE=/admin`)
|
||||
API 前缀:`https://api.ideship.com/admin`(`ASPNETCORE_PATHBASE=/admin`)
|
||||
|
||||
生产三套服务:
|
||||
|
||||
| 服务 | Swagger / PATHBASE |
|
||||
|------|-------------------|
|
||||
| Admin | https://api.ideship.com/admin/index.html |
|
||||
| Itfx | https://api.ideship.com/itfx/index.html |
|
||||
| Track | https://api.ideship.com/track/index.html |
|
||||
|
||||
### 4.1 获取登录二维码
|
||||
|
||||
@ -300,10 +308,10 @@ Content-Type: application/json
|
||||
**现网配置 URL:**
|
||||
|
||||
```
|
||||
https://oms.nanafa.com/api/apiwechat/verification
|
||||
https://api.ideship.com/admin/apiwechat/verification
|
||||
```
|
||||
|
||||
Nginx 反代至 `https://api.nanafa.com/admin/apiwechat/verification`。
|
||||
(旧站曾用 `https://oms.nanafa.com/api/apiwechat/verification` 反代到 Admin。)
|
||||
|
||||
| 方法 | 路径 | 说明 |
|
||||
|------|------|------|
|
||||
@ -410,7 +418,7 @@ src/SimpleAdmin.Api/
|
||||
|
||||
| 项 | 值 |
|
||||
|----|-----|
|
||||
| URL | `https://oms.nanafa.com/api/apiwechat/verification` |
|
||||
| URL | `https://api.ideship.com/admin/apiwechat/verification` |
|
||||
| Token | 与数据库/AppSettings 一致 |
|
||||
| 消息加解密 | **明文**(当前实现) |
|
||||
|
||||
@ -467,8 +475,9 @@ location ^~ /api/apiwechat/ {
|
||||
完整 URL 示例:
|
||||
|
||||
```
|
||||
GET https://api.nanafa.com/admin/wechat/mp/login-qrcode?loginUuid=abc123
|
||||
GET https://api.nanafa.com/admin/rbac/auth/wx-login/status?loginUuid=abc123
|
||||
POST https://api.nanafa.com/admin/rbac/auth/wx-login
|
||||
POST https://oms.nanafa.com/api/apiwechat/verification
|
||||
GET https://api.ideship.com/admin/wechat/mp/login-qrcode?loginUuid=abc123
|
||||
GET https://api.ideship.com/admin/rbac/auth/wx-login/status?loginUuid=abc123
|
||||
POST https://api.ideship.com/admin/rbac/auth/wx-login
|
||||
POST https://api.ideship.com/admin/apiwechat/verification
|
||||
GET https://api.ideship.com/admin/wechat/oauth/config
|
||||
```
|
||||
|
||||
@ -8,7 +8,8 @@
|
||||
# /etc/nginx/ssl/oms.nanafa.com.key
|
||||
# 4. 官网在 /(dist/site/index.html);客户登录 /login;管理端 /admin
|
||||
# 5. 静态资源使用 /login-assets/,勿使用 /login/ 目录名
|
||||
# 6. 微信公众号服务器 URL 请使用 https://oms.nanafa.com/api/apiwechat/verification
|
||||
# 6. 微信公众号服务器 URL 请使用 https://api.ideship.com/admin/apiwechat/verification
|
||||
# (生产三套:admin / itfx / track,均挂在 https://api.ideship.com/{pathbase})
|
||||
# ============================================================================
|
||||
|
||||
# HTTP → HTTPS
|
||||
|
||||
@ -11,7 +11,11 @@
|
||||
"preinstall": "node -e \"if (!process.env.npm_config_user_agent || !process.env.npm_config_user_agent.includes('pnpm')) { console.error('Please use pnpm to install dependencies.'); process.exit(1); }\"",
|
||||
"generate:order-template": "node scripts/generate-order-template.js",
|
||||
"dev": "vite",
|
||||
"dev:test": "vite --mode nanafa",
|
||||
"dev:ideship": "vite --mode ideship",
|
||||
"build": "cross-env BROWSERSLIST_IGNORE_OLD_DATA=1 node --max-old-space-size=4096 node_modules/vite/bin/vite.js build",
|
||||
"build:prod": "cross-env BROWSERSLIST_IGNORE_OLD_DATA=1 node --max-old-space-size=4096 node_modules/vite/bin/vite.js build --mode production",
|
||||
"build:test": "cross-env BROWSERSLIST_IGNORE_OLD_DATA=1 node --max-old-space-size=4096 node_modules/vite/bin/vite.js build --mode nanafa",
|
||||
"postbuild": "node scripts/postbuild-cleanup-dist.js",
|
||||
"report": "cross-env REPORT=true pnpm run build",
|
||||
"preview": "npm run build && vite preview --host",
|
||||
|
||||
@ -59,7 +59,10 @@ export async function getWeChatOAuthConfig(): Promise<WxOAuthConfigResult> {
|
||||
const data = unwrapOrSelf<WxOAuthConfigResult & Record<string, unknown>>(body);
|
||||
const appId = String(data.appId ?? data.AppId ?? '').trim();
|
||||
const oauthRedirectBase = String(
|
||||
data.oauthRedirectBase ?? data.OAuthRedirectBase ?? '',
|
||||
data.oauthRedirectBase ??
|
||||
data.oAuthRedirectBase ??
|
||||
data.OAuthRedirectBase ??
|
||||
'',
|
||||
).trim();
|
||||
return {
|
||||
appId,
|
||||
|
||||
37
src/config/deployTargets.ts
Normal file
37
src/config/deployTargets.ts
Normal file
@ -0,0 +1,37 @@
|
||||
/**
|
||||
* 部署目标(由 Vite mode / env 文件切换,勿在业务里写死域名)
|
||||
*
|
||||
* | 目标 | 前端 | API |
|
||||
* |------|------|-----|
|
||||
* | ideship(生产) | https://ideship.com | https://api.ideship.com/{admin,itfx,track} |
|
||||
* | nanafa(测试) | https://oms.nanafa.com | http://api.nanafa.com/{admin,itfx,track} |
|
||||
*
|
||||
* 本地:pnpm dev(测试) / pnpm dev:ideship(生产 API)
|
||||
* 构建:pnpm build(生产) / pnpm build:test(测试)
|
||||
*/
|
||||
export type DeployTarget = 'ideship' | 'nanafa'
|
||||
|
||||
export const DEPLOY_TARGETS = {
|
||||
ideship: {
|
||||
siteOrigin: 'https://ideship.com',
|
||||
apiOrigin: 'https://api.ideship.com',
|
||||
adminBase: 'https://api.ideship.com/admin',
|
||||
itfxBase: 'https://api.ideship.com/itfx',
|
||||
trackBase: 'https://api.ideship.com/track',
|
||||
},
|
||||
nanafa: {
|
||||
siteOrigin: 'https://oms.nanafa.com',
|
||||
apiOrigin: 'http://api.nanafa.com',
|
||||
adminBase: 'http://api.nanafa.com/admin',
|
||||
itfxBase: 'http://api.nanafa.com/itfx',
|
||||
trackBase: 'http://api.nanafa.com/track',
|
||||
},
|
||||
} as const
|
||||
|
||||
export function resolveDeployTarget(): DeployTarget {
|
||||
const raw = String(import.meta.env.VITE_DEPLOY_TARGET ?? '').trim().toLowerCase()
|
||||
if (raw === 'nanafa') return 'nanafa'
|
||||
if (raw === 'ideship') return 'ideship'
|
||||
// 未显式配置时:生产构建默认 ideship,开发默认 nanafa
|
||||
return import.meta.env.PROD ? 'ideship' : 'nanafa'
|
||||
}
|
||||
2
src/env.d.ts
vendored
2
src/env.d.ts
vendored
@ -31,6 +31,8 @@ declare module '*.vue' {
|
||||
interface ImportMetaEnv {
|
||||
readonly VITE_API_BASE_URL: string;
|
||||
readonly VITE_OMS_URL?: string;
|
||||
/** 部署目标:ideship(生产)| nanafa(测试) */
|
||||
readonly VITE_DEPLOY_TARGET?: 'ideship' | 'nanafa' | string;
|
||||
/** 生产 Admin 基址,默认 https://api.ideship.com/admin */
|
||||
readonly VITE_API_ADMIN_URL?: string;
|
||||
readonly VITE_OMS_ADMIN_URL?: string;
|
||||
|
||||
@ -3172,7 +3172,7 @@ export default {
|
||||
'system.otherConfig.form.remark': 'Remark',
|
||||
'system.otherConfig.placeholder.input': 'Please enter',
|
||||
'system.otherConfig.placeholder.configCode': 'e.g. track_service',
|
||||
'system.otherConfig.placeholder.baseUrl': 'e.g. http://api.idtms.com/track',
|
||||
'system.otherConfig.placeholder.baseUrl': 'e.g. https://api.ideship.com/track',
|
||||
'system.otherConfig.placeholder.appSecretEdit': 'Leave blank to keep unchanged',
|
||||
'system.otherConfig.modal.addTitle': 'Add Config',
|
||||
'system.otherConfig.modal.editTitle': 'Edit Config',
|
||||
|
||||
@ -3220,7 +3220,7 @@ export default {
|
||||
'system.otherConfig.form.remark': '备注',
|
||||
'system.otherConfig.placeholder.input': '请输入',
|
||||
'system.otherConfig.placeholder.configCode': '如 track_service',
|
||||
'system.otherConfig.placeholder.baseUrl': '如 http://api.idtms.com/track',
|
||||
'system.otherConfig.placeholder.baseUrl': '如 https://api.ideship.com/track',
|
||||
'system.otherConfig.placeholder.appSecretEdit': '留空则不修改',
|
||||
'system.otherConfig.modal.addTitle': '新增配置',
|
||||
'system.otherConfig.modal.editTitle': '编辑配置',
|
||||
|
||||
@ -1,7 +1,8 @@
|
||||
/**
|
||||
* Admin API 地址(方案 A)
|
||||
* - 开发:相对路径,Vite 代理到 Admin
|
||||
* - 生产:直连 https://api.ideship.com/admin(可用 VITE_API_ADMIN_URL 覆盖)
|
||||
* - 优先 VITE_API_ADMIN_URL(.env.production / .env.nanafa / .env.ideship 切换)
|
||||
* - 未配置且开发:相对路径走 Vite 代理
|
||||
* - 未配置且生产构建:默认 https://api.ideship.com/admin
|
||||
*/
|
||||
|
||||
function normalizeBase(base: string): string {
|
||||
@ -13,49 +14,58 @@ function ensureLeadingSlash(path: string): string {
|
||||
}
|
||||
|
||||
const DEFAULT_PROD_ADMIN = 'https://api.ideship.com/admin'
|
||||
const DEFAULT_TEST_ADMIN = 'http://api.nanafa.com/admin'
|
||||
|
||||
function prodAdminBase(): string {
|
||||
function configuredAdminBase(): string | undefined {
|
||||
const override = import.meta.env.VITE_API_ADMIN_URL as string | undefined
|
||||
if (override?.trim()) return normalizeBase(override)
|
||||
return DEFAULT_PROD_ADMIN
|
||||
return undefined
|
||||
}
|
||||
|
||||
function prodAdminBase(): string {
|
||||
return configuredAdminBase() ?? DEFAULT_PROD_ADMIN
|
||||
}
|
||||
|
||||
/** 浏览器请求 Admin API(OpenAPI.BASE 或 omsUrl/orderUrl 等) */
|
||||
export function resolveAdminApiPath(path: string): string {
|
||||
const p = ensureLeadingSlash(path)
|
||||
const configured = configuredAdminBase()
|
||||
if (configured) {
|
||||
return `${configured}${p}`
|
||||
}
|
||||
if (!import.meta.env.DEV) {
|
||||
return `${prodAdminBase()}${p}`
|
||||
return `${DEFAULT_PROD_ADMIN}${p}`
|
||||
}
|
||||
return p
|
||||
}
|
||||
|
||||
export function resolveOpenApiBase(): string {
|
||||
const configured = configuredAdminBase()
|
||||
if (configured) return configured
|
||||
if (!import.meta.env.DEV) {
|
||||
return prodAdminBase()
|
||||
return DEFAULT_PROD_ADMIN
|
||||
}
|
||||
return ''
|
||||
}
|
||||
|
||||
/** 桌面 Agent 等直连 Admin 网关 */
|
||||
export function resolveDirectAdminApiUrl(): string {
|
||||
const override = import.meta.env.VITE_API_ADMIN_URL as string | undefined
|
||||
if (override?.trim()) {
|
||||
return normalizeBase(override)
|
||||
}
|
||||
const configured = configuredAdminBase()
|
||||
if (configured) return configured
|
||||
if (import.meta.env.DEV) {
|
||||
return 'http://api.nanafa.com/admin'
|
||||
return DEFAULT_TEST_ADMIN
|
||||
}
|
||||
return DEFAULT_PROD_ADMIN
|
||||
}
|
||||
|
||||
/** 静态资源(uploads)在 Admin wwwroot,须带 `/admin`。
|
||||
* 生产默认 api 域名;开发空串走 Vite `/uploads` 代理。
|
||||
*/
|
||||
/** 静态资源(uploads)在 Admin wwwroot,须带 `/admin`。 */
|
||||
export function resolveAdminAssetOrigin(): string {
|
||||
const override = import.meta.env.VITE_API_ASSET_ORIGIN as string | undefined
|
||||
if (override?.trim()) {
|
||||
return normalizeBase(override)
|
||||
}
|
||||
const configured = configuredAdminBase()
|
||||
if (configured) return configured
|
||||
if (!import.meta.env.DEV) {
|
||||
return DEFAULT_PROD_ADMIN
|
||||
}
|
||||
|
||||
@ -1,5 +1,7 @@
|
||||
/**
|
||||
* 方案 A:生产直连 api.ideship.com PATHBASE;开发仍走 Vite 代理旧路径。
|
||||
* 方案 A:按 VITE_API_ORIGIN 改写到 {admin|itfx|track} PATHBASE。
|
||||
* 生产默认 https://api.ideship.com;测试用 .env.nanafa → http://api.nanafa.com。
|
||||
* 开发且未配置 VITE_API_ORIGIN 时不改写(走 Vite 代理)。
|
||||
*/
|
||||
|
||||
const SPA_API_PREFIXES = [
|
||||
@ -17,9 +19,11 @@ const SPA_API_PREFIXES = [
|
||||
|
||||
const DEFAULT_PROD_API = 'https://api.ideship.com'
|
||||
|
||||
function prodApiOrigin(): string {
|
||||
function prodApiOrigin(): string | null {
|
||||
const override = (import.meta.env.VITE_API_ORIGIN as string | undefined)?.trim()
|
||||
return (override || DEFAULT_PROD_API).replace(/\/$/, '')
|
||||
if (override) return override.replace(/\/$/, '')
|
||||
if (import.meta.env.DEV) return null
|
||||
return DEFAULT_PROD_API
|
||||
}
|
||||
|
||||
function isItfxSpaPath(afterApi: string): boolean {
|
||||
@ -29,15 +33,17 @@ function isItfxSpaPath(afterApi: string): boolean {
|
||||
)
|
||||
}
|
||||
|
||||
/** 生产:遗留路径 → https://api.ideship.com/{itfx|track|admin}/... */
|
||||
/** 遗留路径 → {apiOrigin}/{itfx|track|admin}/... */
|
||||
export function rewriteBrowserApiPath(url: string): string {
|
||||
if (!url || import.meta.env.DEV) return url
|
||||
if (!url) return url
|
||||
if (/^https?:\/\//i.test(url) || url.startsWith('data:') || url.startsWith('blob:')) {
|
||||
return url
|
||||
}
|
||||
|
||||
let path = url.startsWith('/') ? url : `/${url}`
|
||||
const origin = prodApiOrigin()
|
||||
if (!origin) return url
|
||||
|
||||
let path = url.startsWith('/') ? url : `/${url}`
|
||||
|
||||
// 已是绝对 PATHBASE 相对路径 → 挂到 api 域名
|
||||
if (
|
||||
|
||||
@ -207,7 +207,7 @@ const PRESET_DEFS: Array<{
|
||||
defaults: {
|
||||
configCode: TRACK_SERVICE_CONFIG_CODE,
|
||||
enabled: true,
|
||||
baseUrl: 'http://api.idtms.com/track',
|
||||
baseUrl: 'https://api.ideship.com/track',
|
||||
timeoutSeconds: 30,
|
||||
},
|
||||
meta: {
|
||||
@ -226,6 +226,7 @@ const PRESET_DEFS: Array<{
|
||||
defaults: {
|
||||
configCode: WECHAT_MP_CONFIG_CODE,
|
||||
enabled: true,
|
||||
baseUrl: 'https://ideship.com',
|
||||
timeoutSeconds: 30,
|
||||
},
|
||||
meta: {
|
||||
|
||||
Loading…
Reference in New Issue
Block a user