@ 模拟器/ 适应器- next
Next.js App路由器集成模拟. 在您的 Next.js app 中直接嵌入仿真器, 因此它们运行在相同的源头上, 解决了 Vercel 预览部署问题, OAuth 回调 URL 随每次部署而改变 .
部分 模拟 ——为CI和无网络沙盒提供本地出入口替换服务.
安装
npm install @emulators/adapter-next
只安装适配器旁所需的模拟器 :
npm install @emulators/adapter-next @emulators/github @emulators/google
路由处理器
创建一个服务于模拟器流量的包罗万象的路径 :
// app/emulate/[...path]/route.ts
import { createEmulateHandler } from '@emulators/adapter-next'
import * as github from '@emulators/github'
import * as google from '@emulators/google'
export const emulator = createEmulateHandler({
services: {
github: {
emulator: github,
seed: {
users: [{ login: 'octocat', name: 'The Octocat' }],
repos: [{ owner: 'octocat', name: 'hello-world', auto_init: true }],
},
},
google: {
emulator: google,
seed: {
users: [{ email: '[email protected]', name: 'Test User' }],
},
},
},
})
export const { GET, POST, PUT, PATCH, DELETE, OPTIONS } = emulator
GitHub 图像 App 种子可能会省略 private_key。仅用处理器的服务器读取生成的密钥 generatedSecrets() 方法。 明文密钥不在此列;持续快照包含生成的密钥并需要一个带有原子的私人后端 initialize。 。 。 .
检查薄荷安装存储元数据 /emulate/github/_emulate/installation-tokens。 。 。 .
Auth.js / 下一个 Auth 配置
将您的提供者指向同一来源的模拟路径 :
import GitHub from 'next-auth/providers/github'
const baseUrl = process.env.VERCEL_URL
? `https://${process.env.VERCEL_URL}`
: 'http://localhost:3000'
GitHub({
clientId: 'any-value',
clientSecret: 'any-value',
authorization: { url: `${baseUrl}/emulate/github/login/oauth/authorize` },
token: { url: `${baseUrl}/emulate/github/login/oauth/access_token` },
userinfo: { url: `${baseUrl}/emulate/github/user` },
})
没有 oauth_apps 需要播种。 没有配置时, 模拟器跳过 client_id, (中文(简体) ), client_secret,以及 redirect_uri 审定.
无服务器的字体文件
模拟UI页面使用捆绑字体. 将您的 Next.js 配置包成无服务器跟踪 :
// next.config.mjs
import { withEmulate } from '@emulators/adapter-next'
export default withEmulate({
// your normal Next.js config
})
如果您在自定义路径上挂载全部, 请通过匹配的前缀 :
export default withEmulate(nextConfig, { routePrefix: '/api/emulate' })
持久性
默认情况下,仿真器状态是内在的,并且在每个冷起步上重放. 要持续状态 整个重启,通过 persistence 适配器 :
import { createEmulateHandler } from '@emulators/adapter-next'
import * as github from '@emulators/github'
const kvAdapter = {
async load() { return await kv.get('emulate-state') },
async save(data: string) { await kv.set('emulate-state', data) },
}
export const { GET, POST, PUT, PATCH, DELETE, OPTIONS } = createEmulateHandler({
services: { github: { emulator: github } },
persistence: kvAdapter,
})
为了地方发展, @emulators/core 船舶 filePersistence数字 :
import { filePersistence } from '@emulators/core'
// ...
persistence: filePersistence('.emulate/state.json'),
链接
自定义仿真器
传递创建的定义 defineEmulator 从 emulate 改为 services[name].emulator 在框架适配器。 同一定义贯穿于国家综合指数和 createEmulator({ service: definition, listen: false }) 在测试。 自定义条目接受可选的检查员和持久性适配器. 导出 OPTIONS 因此飞行前请求和自定义的选择路线到达了模拟器. root- relative directory stay 在服务挂载下,而自定义的 HTML 机构通过不变. 保持状态 在定义的国营工厂, 并等待操作员 close() 在测试。 见 自定义仿真器指南。 。 。 .