一键导入
create-feature
Scaffold a complete feature module with types, service, hooks, schema, and constants
用 Codex 或 Claude 帮你安装 复制这段 Prompt,粘贴到 Codex、Claude 或其他助手里,让它检查 Skill 页面并帮你完成安装。
菜单
Scaffold a complete feature module with types, service, hooks, schema, and constants
用 Codex 或 Claude 帮你安装 复制这段 Prompt,粘贴到 Codex、Claude 或其他助手里,让它检查 Skill 页面并帮你完成安装。
基于 SOC 职业分类
Transform the base template into a specific application
Add or update i18n keys in both English and Arabic locale files
Scaffold a UI component with unistyles variants pattern
Generate a validated form with Zod schema, react-hook-form, and i18n
Add a new screen or tab to the app with routing and i18n
Review changed code against project conventions and rules
| name | create-feature |
| description | Scaffold a complete feature module with types, service, hooks, schema, and constants |
| auto-invocable | true |
| triggers | ["add a feature","build a module","create a feature","scaffold feature","new feature module"] |
Scaffold a complete feature module following the project's exact conventions.
Ask the user for:
/<feature-name>src/features/<name>/
├── types/index.ts
├── services/<name>Service.ts
├── hooks/use<Name>.ts
├── schemas/<name>Schema.ts
├── constants/index.ts
└── components/ (empty directory, ready for feature components)
// src/features/<name>/types/index.ts
export interface <Entity> {
id: string;
// ... fields from user input
createdAt: string;
updatedAt: string;
}
export interface Create<Entity>Data {
// ... writable fields (exclude id, createdAt, updatedAt)
}
export interface Update<Entity>Data extends Partial<Create<Entity>Data> {}
// src/features/<name>/services/<name>Service.ts
import { api } from '@/services/api';
import type { <Entity>, Create<Entity>Data, Update<Entity>Data } from '../types';
export async function fetch<Entities>(): Promise<<Entity>[]> {
const { data } = await api.get<<Entity>[]>('<endpoint>');
return data;
}
export async function fetch<Entity>(id: string): Promise<<Entity>> {
const { data } = await api.get<<Entity>>(`<endpoint>/${id}`);
return data;
}
export async function create<Entity>(payload: Create<Entity>Data): Promise<<Entity>> {
const { data } = await api.post<<Entity>>('<endpoint>', payload);
return data;
}
export async function update<Entity>(id: string, payload: Update<Entity>Data): Promise<<Entity>> {
const { data } = await api.patch<<Entity>>(`<endpoint>/${id}`, payload);
return data;
}
export async function delete<Entity>(id: string): Promise<void> {
await api.delete(`<endpoint>/${id}`);
}
// src/features/<name>/hooks/use<Name>.ts
import { useQuery, useMutation, useQueryClient } from '@tanstack/react-query';
import {
fetch<Entities>,
fetch<Entity>,
create<Entity>,
update<Entity>,
delete<Entity>,
} from '../services/<name>Service';
import type { Create<Entity>Data, Update<Entity>Data } from '../types';
export const <NAME>_KEYS = {
all: ['<name>'] as const,
list: (filters?: object) => [...<NAME>_KEYS.all, 'list', filters] as const,
detail: (id: string) => [...<NAME>_KEYS.all, 'detail', id] as const,
};
export function use<Entities>(filters?: object) {
return useQuery({
queryKey: <NAME>_KEYS.list(filters),
queryFn: fetch<Entities>,
});
}
export function use<Entity>(id: string) {
return useQuery({
queryKey: <NAME>_KEYS.detail(id),
queryFn: () => fetch<Entity>(id),
enabled: !!id,
});
}
export function useCreate<Entity>() {
const queryClient = useQueryClient();
return useMutation({
mutationFn: (data: Create<Entity>Data) => create<Entity>(data),
onSuccess: () => {
queryClient.invalidateQueries({ queryKey: <NAME>_KEYS.all });
},
});
}
export function useUpdate<Entity>() {
const queryClient = useQueryClient();
return useMutation({
mutationFn: ({ id, data }: { id: string; data: Update<Entity>Data }) =>
update<Entity>(id, data),
onSuccess: () => {
queryClient.invalidateQueries({ queryKey: <NAME>_KEYS.all });
},
});
}
export function useDelete<Entity>() {
const queryClient = useQueryClient();
return useMutation({
mutationFn: (id: string) => delete<Entity>(id),
onSuccess: () => {
queryClient.invalidateQueries({ queryKey: <NAME>_KEYS.all });
},
});
}
// src/features/<name>/schemas/<name>Schema.ts
import { z } from 'zod/v4';
export const create<Entity>Schema = z.object({
// Generate field validations based on entity fields
// Use i18n keys for ALL validation messages: 'validation.required', 'validation.<name>Min', etc.
});
export const update<Entity>Schema = create<Entity>Schema.partial();
export type Create<Entity>FormData = z.infer<typeof create<Entity>Schema>;
export type Update<Entity>FormData = z.infer<typeof update<Entity>Schema>;
Validation message rules:
z.string().min(1, 'validation.required') for required stringsz.email('validation.emailInvalid') for emailsvalidation.<name>Min, validation.<name>Max, etc.// src/features/<name>/constants/index.ts
// Add feature-specific constants as needed
Update BOTH src/i18n/locales/en.json and src/i18n/locales/ar.json with:
{
"<name>": {
"title": "<Name>",
"empty": "No <name> found",
"addNew": "Add <Entity>",
"edit": "Edit <Entity>",
"deleteConfirm": "Are you sure you want to delete this <entity>?",
"created": "<Entity> created successfully",
"updated": "<Entity> updated successfully",
"deleted": "<Entity> deleted successfully"
}
}
Also add any new validation keys under the "validation" namespace.
For Arabic translations: provide best-effort translations. Mark uncertain ones with a TODO comment in the commit message.
Run npm run validate to ensure no TypeScript or lint errors.
StyleSheet from react-native-unistyles, NOT react-nativez from zod/v4, NOT zodText from @/common/components/Text, NOT react-native@/ path aliases, never deep relative importssrc/)api from @/services/api for HTTP callsany types