vinext-vite-nextjs
Vite plugin that reimplements the Next.js API surface for deploying anywhere, including Cloudflare Workers
Best use case
vinext-vite-nextjs is best used when you need a repeatable AI agent workflow instead of a one-off prompt.
Vite plugin that reimplements the Next.js API surface for deploying anywhere, including Cloudflare Workers
Teams using vinext-vite-nextjs should expect a more consistent output, faster repeated execution, less prompt rewriting.
When to use this skill
- You want a reusable workflow that can be run more than once with consistent structure.
When not to use this skill
- You only need a quick one-off answer and do not need a reusable workflow.
- You cannot install or maintain the underlying files, dependencies, or repository context.
Installation
Claude Code / Cursor / Codex
Manual Installation
- Download SKILL.md from GitHub
- Place it in
.claude/skills/vinext-vite-nextjs/SKILL.mdinside your project - Restart your AI agent — it will auto-discover the skill
How vinext-vite-nextjs Compares
| Feature / Agent | vinext-vite-nextjs | Standard Approach |
|---|---|---|
| Platform Support | Not specified | Limited / Varies |
| Context Awareness | High | Baseline |
| Installation Complexity | Unknown | N/A |
Frequently Asked Questions
What does this skill do?
Vite plugin that reimplements the Next.js API surface for deploying anywhere, including Cloudflare Workers
Where can I find the source code?
You can find the source code on GitHub using the link provided at the top of the page.
Related Guides
AI Agents for Marketing
Discover AI agents for marketing workflows, from SEO and content production to campaign research, outreach, and analytics.
AI Agents for Startups
Explore AI agent skills for startup validation, product research, growth experiments, documentation, and fast execution with small teams.
AI Agents for Coding
Browse AI agent skills for coding, debugging, testing, refactoring, code review, and developer workflows across Claude, Cursor, and Codex.
SKILL.md Source
# vinext — Next.js API on Vite, Deploy Anywhere
> Skill by [ara.so](https://ara.so) — Daily 2026 Skills collection.
vinext is a Vite plugin that reimplements the Next.js public API surface (routing, SSR, RSC, `next/*` imports, CLI) so existing Next.js apps run on Vite instead of the Next.js compiler. It targets ~94% API coverage, supports both Pages Router and App Router, and deploys natively to Cloudflare Workers with optional Nitro support for AWS, Netlify, Vercel, and more.
## Installation
### New project (migrate from Next.js)
```bash
# Automated one-command migration
npx vinext init
```
This will:
1. Run compatibility check (`vinext check`)
2. Install `vite`, `@vitejs/plugin-react` as devDependencies
3. Install `@vitejs/plugin-rsc`, `react-server-dom-webpack` for App Router
4. Add `"type": "module"` to `package.json`
5. Rename CJS config files (e.g. `postcss.config.js` → `postcss.config.cjs`)
6. Add `dev:vinext` and `build:vinext` scripts
7. Generate a minimal `vite.config.ts`
Migration is **non-destructive** — Next.js still works alongside vinext.
### Manual installation
```bash
npm install -D vinext vite @vitejs/plugin-react
# App Router only:
npm install -D @vitejs/plugin-rsc react-server-dom-webpack
```
Update `package.json` scripts:
```json
{
"scripts": {
"dev": "vinext dev",
"build": "vinext build",
"start": "vinext start",
"deploy": "vinext deploy"
}
}
```
### Agent Skill (AI-assisted migration)
```bash
npx skills add cloudflare/vinext
# Then in your AI tool: "migrate this project to vinext"
```
## CLI Reference
| Command | Description |
|---|---|
| `vinext dev` | Start dev server with HMR |
| `vinext build` | Production build |
| `vinext start` | Local production server for testing |
| `vinext deploy` | Build + deploy to Cloudflare Workers |
| `vinext init` | Automated migration from Next.js |
| `vinext check` | Scan for compatibility issues before migrating |
| `vinext lint` | Delegate to eslint or oxlint |
### CLI Options
```bash
vinext dev -p 3001 -H 0.0.0.0
vinext deploy --preview
vinext deploy --env staging --name my-app
vinext deploy --skip-build --dry-run
vinext deploy --experimental-tpr
vinext init --port 3001 --skip-check --force
```
## Configuration
vinext auto-detects `app/` or `pages/` directory and loads `next.config.js` automatically. No `vite.config.ts` is required for basic usage.
### Minimal `vite.config.ts`
```typescript
import { defineConfig } from 'vite'
import react from '@vitejs/plugin-react'
import { vinext } from 'vinext/vite'
export default defineConfig({
plugins: [
react(),
vinext(),
],
})
```
### App Router `vite.config.ts`
```typescript
import { defineConfig } from 'vite'
import react from '@vitejs/plugin-react'
import rsc from '@vitejs/plugin-rsc'
import { vinext } from 'vinext/vite'
export default defineConfig({
plugins: [
react(),
rsc(),
vinext(),
],
})
```
### Cloudflare Workers with bindings
```typescript
import { defineConfig } from 'vite'
import react from '@vitejs/plugin-react'
import { vinext } from 'vinext/vite'
import { cloudflare } from '@cloudflare/vite-plugin'
export default defineConfig({
plugins: [
cloudflare(),
react(),
vinext(),
],
})
```
### Other platforms via Nitro
```typescript
import { defineConfig } from 'vite'
import react from '@vitejs/plugin-react'
import { vinext } from 'vinext/vite'
import nitro from 'vite-plugin-nitro'
export default defineConfig({
plugins: [
react(),
vinext(),
nitro({ preset: 'vercel' }), // or 'netlify', 'aws-amplify', 'deno-deploy', etc.
],
})
```
## Project Structure
vinext uses the same directory conventions as Next.js — no changes required:
```
my-app/
├── app/ # App Router (auto-detected)
│ ├── layout.tsx
│ ├── page.tsx
│ └── api/route.ts
├── pages/ # Pages Router (auto-detected)
│ ├── index.tsx
│ └── api/hello.ts
├── public/ # Static assets
├── next.config.js # Loaded automatically
├── package.json
└── vite.config.ts # Optional for basic usage
```
## Code Examples
### Pages Router — SSR page
```typescript
// pages/index.tsx
import type { GetServerSideProps, InferGetServerSidePropsType } from 'next'
type Props = { data: string }
export const getServerSideProps: GetServerSideProps<Props> = async (ctx) => {
return { props: { data: 'Hello from SSR' } }
}
export default function Home({ data }: InferGetServerSidePropsType<typeof getServerSideProps>) {
return <h1>{data}</h1>
}
```
### Pages Router — Static generation
```typescript
// pages/posts/[id].tsx
import type { GetStaticPaths, GetStaticProps } from 'next'
export const getStaticPaths: GetStaticPaths = async () => {
return {
paths: [{ params: { id: '1' } }, { params: { id: '2' } }],
fallback: false,
}
}
export const getStaticProps: GetStaticProps = async ({ params }) => {
return { props: { id: params?.id } }
}
export default function Post({ id }: { id: string }) {
return <p>Post {id}</p>
}
```
### Pages Router — API route
```typescript
// pages/api/hello.ts
import type { NextApiRequest, NextApiResponse } from 'next'
export default function handler(req: NextApiRequest, res: NextApiResponse) {
res.status(200).json({ message: 'Hello from vinext' })
}
```
### App Router — Server Component
```typescript
// app/page.tsx
export default async function Page() {
const data = await fetch('https://api.example.com/data').then(r => r.json())
return <main>{data.title}</main>
}
```
### App Router — Route Handler
```typescript
// app/api/route.ts
import { NextRequest, NextResponse } from 'next/server'
export async function GET(request: NextRequest) {
return NextResponse.json({ status: 'ok' })
}
export async function POST(request: NextRequest) {
const body = await request.json()
return NextResponse.json({ received: body })
}
```
### App Router — Server Action
```typescript
// app/actions.ts
'use server'
export async function submitForm(formData: FormData) {
const name = formData.get('name')
// server-side logic here
return { success: true, name }
}
```
```typescript
// app/form.tsx
'use client'
import { submitForm } from './actions'
export function Form() {
return (
<form action={submitForm}>
<input name="name" />
<button type="submit">Submit</button>
</form>
)
}
```
### Middleware
```typescript
// middleware.ts
import { NextResponse } from 'next/server'
import type { NextRequest } from 'next/server'
export function middleware(request: NextRequest) {
const token = request.cookies.get('token')
if (!token && request.nextUrl.pathname.startsWith('/dashboard')) {
return NextResponse.redirect(new URL('/login', request.url))
}
return NextResponse.next()
}
export const config = {
matcher: ['/dashboard/:path*'],
}
```
### Cloudflare Workers — Bindings access
```typescript
// app/api/kv/route.ts
import { NextRequest, NextResponse } from 'next/server'
import { getCloudflareContext } from 'cloudflare:workers'
export async function GET(request: NextRequest) {
const { env } = getCloudflareContext()
const value = await env.MY_KV.get('key')
return NextResponse.json({ value })
}
```
### Image optimization
```typescript
// app/page.tsx
import Image from 'next/image'
export default function Page() {
return (
<Image
src="/hero.png"
alt="Hero"
width={800}
height={400}
priority
/>
)
}
```
### Link and navigation
```typescript
// app/nav.tsx
'use client'
import Link from 'next/link'
import { useRouter, usePathname } from 'next/navigation'
export function Nav() {
const router = useRouter()
const pathname = usePathname()
return (
<nav>
<Link href="/">Home</Link>
<Link href="/about">About</Link>
<button onClick={() => router.push('/dashboard')}>Dashboard</button>
</nav>
)
}
```
## Deployment
### Cloudflare Workers
```bash
# Authenticate (once)
wrangler login
# Deploy
vinext deploy
# Deploy to preview
vinext deploy --preview
# Deploy to named environment
vinext deploy --env production --name my-production-app
```
For CI/CD, set `CLOUDFLARE_API_TOKEN` environment variable instead of `wrangler login`.
### `wrangler.toml` (Cloudflare config)
```toml
name = "my-app"
compatibility_date = "2024-01-01"
compatibility_flags = ["nodejs_compat"]
[[kv_namespaces]]
binding = "MY_KV"
id = "your-kv-namespace-id"
[[r2_buckets]]
binding = "MY_BUCKET"
bucket_name = "my-bucket"
```
### Netlify / Vercel / AWS via Nitro
```bash
npm install -D vite-plugin-nitro
# Then add nitro plugin to vite.config.ts with your target preset
# nitro({ preset: 'netlify' })
# nitro({ preset: 'vercel' })
# nitro({ preset: 'aws-amplify' })
```
## `next.config.js` Support
vinext loads your existing `next.config.js` automatically:
```javascript
// next.config.js
/** @type {import('next').NextConfig} */
const nextConfig = {
images: {
remotePatterns: [
{ protocol: 'https', hostname: 'images.example.com' },
],
},
env: {
MY_VAR: process.env.MY_VAR,
},
redirects: async () => [
{ source: '/old', destination: '/new', permanent: true },
],
rewrites: async () => [
{ source: '/api/:path*', destination: 'https://backend.example.com/:path*' },
],
}
module.exports = nextConfig
```
## Compatibility Check
Run before migrating to identify unsupported features:
```bash
npx vinext check
```
This scans for:
- Unsupported `next.config.js` options
- Deprecated Pages Router APIs
- Experimental Next.js features not yet supported
- CJS config file conflicts
## Common Patterns
### Environment variables
Works the same as Next.js — `.env`, `.env.local`, `.env.production`:
```bash
# .env.local
NEXT_PUBLIC_API_URL=https://api.example.com
DATABASE_URL=$DATABASE_URL
```
```typescript
// Accessible in client code (NEXT_PUBLIC_ prefix)
const apiUrl = process.env.NEXT_PUBLIC_API_URL
// Server-only
const dbUrl = process.env.DATABASE_URL
```
### TypeScript path aliases
```json
// tsconfig.json — works as-is
{
"compilerOptions": {
"paths": {
"@/*": ["./src/*"]
}
}
}
```
### Tailwind CSS
```bash
npm install -D tailwindcss postcss autoprefixer
# Rename postcss.config.js → postcss.config.cjs (vinext init does this automatically)
```
```javascript
// postcss.config.cjs
module.exports = {
plugins: {
tailwindcss: {},
autoprefixer: {},
},
}
```
## Troubleshooting
### ESM conflicts with CJS config files
```bash
# vinext init handles this automatically, or rename manually:
mv postcss.config.js postcss.config.cjs
mv tailwind.config.js tailwind.config.cjs
```
Ensure `package.json` has `"type": "module"`.
### `vinext init` overwrites existing `vite.config.ts`
```bash
vinext init --force
```
### Skip compatibility check during init
```bash
vinext init --skip-check
```
### Custom port
```bash
vinext dev -p 3001
vinext init --port 3001
```
### `wrangler` not authenticated for deploy
```bash
wrangler login
# or set env var:
export CLOUDFLARE_API_TOKEN=your_token_here
```
### Dry-run deploy to verify config
```bash
vinext deploy --dry-run
```
### App Router multi-environment build issues
App Router builds produce three environments (RSC + SSR + client). If you see build errors, ensure all three plugins are installed:
```bash
npm install -D @vitejs/plugin-rsc react-server-dom-webpack
```
And your `vite.config.ts` includes both `react()` and `rsc()` plugins in the correct order.
## What's Supported (~94% of Next.js API)
- ✅ Pages Router (SSR, SSG, ISR, API routes)
- ✅ App Router (RSC, Server Actions, Route Handlers, Layouts, Loading, Error boundaries)
- ✅ Middleware
- ✅ `next/image`, `next/link`, `next/router`, `next/navigation`, `next/head`
- ✅ `next/font`, `next/dynamic`
- ✅ `next.config.js` (redirects, rewrites, headers, env, images)
- ✅ Cloudflare Workers native deployment with bindings
- ✅ HMR in development
- ✅ TypeScript, Tailwind CSS, CSS Modules
- ⚠️ Experimental Next.js features — lower priority
- ❌ Undocumented Vercel-specific behavior — intentionally not supportedRelated Skills
vitest-testing
Vitest testing framework patterns and best practices. Use when writing unit tests, integration tests, configuring vitest.config, mocking with vi.mock/vi.fn, using snapshots, or setting up test coverage. Triggers on describe, it, expect, vi.mock, vi.fn, beforeEach, afterEach, vitest.
---
name: article-factory-wechat
humanizer
Remove signs of AI-generated writing from text. Use when editing or reviewing text to make it sound more natural and human-written. Based on Wikipedia's comprehensive "Signs of AI writing" guide. Detects and fixes patterns including: inflated symbolism, promotional language, superficial -ing analyses, vague attributions, em dash overuse, rule of three, AI vocabulary words, negative parallelisms, and excessive conjunctive phrases.
find-skills
Helps users discover and install agent skills when they ask questions like "how do I do X", "find a skill for X", "is there a skill that can...", or express interest in extending capabilities. This skill should be used when the user is looking for functionality that might exist as an installable skill.
tavily-search
Use Tavily API for real-time web search and content extraction. Use when: user needs real-time web search results, research, or current information from the web. Requires Tavily API key.
baidu-search
Search the web using Baidu AI Search Engine (BDSE). Use for live information, documentation, or research topics.
agent-autonomy-kit
Stop waiting for prompts. Keep working.
Meeting Prep
Never walk into a meeting unprepared again. Your agent researches all attendees before calendar events—pulling LinkedIn profiles, recent company news, mutual connections, and conversation starters. Generates a briefing doc with talking points, icebreakers, and context so you show up informed and confident. Triggered automatically before meetings or on-demand. Configure research depth, advance timing, and output format. Walking into meetings blind is amateur hour—missed connections, generic small talk, zero leverage. Use when setting up meeting intelligence, researching specific attendees, generating pre-meeting briefs, or automating your prep workflow.
self-improvement
Captures learnings, errors, and corrections to enable continuous improvement. Use when: (1) A command or operation fails unexpectedly, (2) User corrects Claude ('No, that's wrong...', 'Actually...'), (3) User requests a capability that doesn't exist, (4) An external API or tool fails, (5) Claude realizes its knowledge is outdated or incorrect, (6) A better approach is discovered for a recurring task. Also review learnings before major tasks.
botlearn-healthcheck
botlearn-healthcheck — BotLearn autonomous health inspector for OpenClaw instances across 5 domains (hardware, config, security, skills, autonomy); triggers on system check, health report, diagnostics, or scheduled heartbeat inspection.
linkedin-cli
A bird-like LinkedIn CLI for searching profiles, checking messages, and summarizing your feed using session cookies.
notebooklm
Google NotebookLM 非官方 Python API 的 OpenClaw Skill。支持内容生成(播客、视频、幻灯片、测验、思维导图等)、文档管理和研究自动化。当用户需要使用 NotebookLM 生成音频概述、视频、学习材料或管理知识库时触发。