Acme

贡献指南

了解如何为项目贡献代码、组件和文档

欢迎为私有 Registry 项目做出贡献!本指南将帮助您了解项目结构、开发规范和贡献流程。

项目结构

核心目录

registry-fumadocs/
├── app/                          # Next.js App Router
│   ├── (home)/                   # 首页
│   ├── api/
│   │   └── registry/[name]/      # 🔒 认证 API 路由
│   │       └── route.ts
│   ├── docs/[[...slug]]/         # 文档页面
│   └── layout.tsx

├── content/docs/                 # 📚 MDX 文档
│   ├── index.mdx                 # 文档首页
│   ├── registry/                 # 用户文档
│   │   ├── getting-started.mdx
│   │   ├── authentication.mdx
│   │   ├── namespace.mdx
│   │   └── quick-reference.mdx
│   └── guides/                   # 维护者文档
│       ├── deployment.mdx
│       ├── contributing.mdx
│       └── client-setup.mdx

├── registry/                     # 📦 组件源码
│   └── new-york/
│       ├── blocks/               # 复杂组件
│       ├── ui/                   # UI 组件
│       └── lib/                  # 工具库

├── public/r/                     # 🔒 生成的 JSON(需保护)
│   ├── registry.json
│   └── [component].json

├── lib/                          # 共享工具
│   ├── source.ts                 # 文档源配置
│   ├── utils.ts
│   └── layout.shared.tsx

├── components/                   # React 组件
├── scripts/                      # 工具脚本
│   └── test-auth.sh

├── middleware.ts                 # 🔒 静态文件保护
├── registry.json                 # Registry 配置
└── source.config.ts              # Fumadocs 配置

关键文件说明

文件说明作用
app/api/registry/[name]/route.tsAPI 认证路由处理组件请求和认证
middleware.tsNext.js Middleware保护静态文件访问
registry.jsonRegistry 配置定义所有组件
source.config.tsFumadocs 配置文档系统配置
public/r/*.json组件 JSON 文件由构建脚本生成

开发环境设置

克隆仓库

git clone https://github.com/your-org/registry-fumadocs.git
cd registry-fumadocs

安装依赖

pnpm install

配置环境变量

# 复制环境变量模板
cp .env.example .env.local

# 生成令牌
node -e "console.log(require('crypto').randomBytes(32).toString('hex'))"

# 编辑 .env.local,添加生成的令牌
.env.local
REGISTRY_TOKEN=your_development_token_here

构建 Registry

pnpm registry:build

启动开发服务器

pnpm dev

访问 http://localhost:3000 查看项目。

贡献流程

Fork 和分支

# Fork 项目到你的 GitHub 账号,然后:
git clone https://github.com/YOUR_USERNAME/registry-fumadocs.git
cd registry-fumadocs

# 创建功能分支
git checkout -b feature/amazing-feature

开发和测试

# 开发过程中持续测试
pnpm dev

# 如果修改了组件,重新构建
pnpm registry:build

# 运行认证测试
chmod +x scripts/test-auth.sh
./scripts/test-auth.sh

提交更改

遵循 提交规范

git add .
git commit -m "feat: add amazing feature"

推送和 PR

# 推送到你的 fork
git push origin feature/amazing-feature

# 在 GitHub 上创建 Pull Request

组件开发

添加新组件

创建组件文件

registry/new-york/ui/my-button.tsx
import * as React from "react"
import { cn } from "@/lib/utils"

export interface MyButtonProps
  extends React.ButtonHTMLAttributes<HTMLButtonElement> {
  variant?: "default" | "primary"
}

export function MyButton({
  className,
  variant = "default",
  ...props
}: MyButtonProps) {
  return (
    <button
      className={cn(
        "px-4 py-2 rounded",
        variant === "primary" && "bg-blue-500 text-white",
        className
      )}
      {...props}
    />
  )
}

更新 registry.json

registry.json
{
  "$schema": "https://ui.shadcn.com/schema/registry.json",
  "name": "acme",
  "items": [
    {
      "name": "my-button",
      "type": "registry:ui",
      "title": "My Button",
      "description": "A customizable button component with variants",
      "files": [
        {
          "path": "registry/new-york/ui/my-button.tsx",
          "type": "registry:ui"
        }
      ],
      "dependencies": []
    }
  ]
}

构建并测试

# 重新构建 Registry
pnpm registry:build

# 检查生成的 JSON
cat public/r/my-button.json

# 测试 API
curl -H "Authorization: Bearer $REGISTRY_TOKEN" \
  http://localhost:3000/api/registry/my-button

组件开发规范

命名规范

  • 文件名kebab-case.tsx(例如:my-button.tsx
  • 组件名PascalCase(例如:MyButton
  • 导出:使用具名导出
// ✅ 正确
export function MyButton() { ... }

// ❌ 错误
export default function() { ... }

类型定义

始终提供 TypeScript 类型:

// ✅ 正确
export interface ButtonProps extends React.ButtonHTMLAttributes<HTMLButtonElement> {
  variant?: "default" | "primary"
}

export function Button({ variant = "default", ...props }: ButtonProps) {
  return <button {...props} />
}

组件文档

添加 JSDoc 注释:

/**
 * MyButton - 一个可定制的按钮组件
 *
 * @example
 * ```tsx
 * <MyButton variant="primary">点击我</MyButton>
 * ```
 */
export function MyButton(props: MyButtonProps) {
  return <button {...props} />
}

Registry 配置规范

{
  "name": "component-name",              // kebab-case
  "type": "registry:ui",                 // 正确的类型
  "title": "Component Title",            // 友好的标题
  "description": "清晰描述组件用途和特性", // 详细描述
  "dependencies": ["package@version"],    // NPM 依赖
  "registryDependencies": ["button"],     // Registry 依赖
  "files": [
    {
      "path": "registry/new-york/ui/component.tsx",
      "type": "registry:ui"
    }
  ]
}

文档贡献

添加新文档

创建 MDX 文件

content/docs/registry/new-guide.mdx
---
title: 新指南标题
description: 简短的描述,用于 SEO 和预览
---

## 主要内容

你的文档内容...

### 代码示例

\`\`\`typescript
// 示例代码
\`\`\`

<Callout type="warning">
  重要提示内容
</Callout>

文档命名规范

  • 使用 kebab-case.mdx
  • 必须包含 frontmatter(title、description)
  • 使用清晰的标题层级

可用组件

<!-- 提示框 -->
<Callout type="warning">
  警告内容
</Callout>

<Callout type="info">
  提示内容
</Callout>

<!-- 卡片网格 -->
<Cards>
  <Card title="标题" href="/link" />
  <Card title="标题" href="/link" />
</Cards>

代码规范

TypeScript

// ✅ 正确:明确的类型定义
interface ComponentProps {
  name: string;
  type: "registry:ui" | "registry:lib";
}

function getComponent(name: string): Promise<Component | null> {
  // ...
}

// ❌ 错误:使用 any
function getComponent(name: any): any {
  // ...
}

导入顺序

// 1. React 相关
import React from "react";
import { useState } from "react";

// 2. Next.js 相关
import { NextRequest, NextResponse } from "next/server";

// 3. 第三方库
import { clsx } from "clsx";

// 4. 项目内部导入
import { cn } from "@/lib/utils";
import { Button } from "@/components/ui/button";

// 5. 类型导入
import type { Component } from "@/types";

错误处理

// ✅ 正确:完善的错误处理
try {
  const data = await fetchData();
  return NextResponse.json(data);
} catch (error) {
  console.error("Error fetching data:", error);
  return NextResponse.json(
    { error: "Internal Server Error" },
    { status: 500 }
  );
}

提交规范

提交信息格式

<type>(<scope>): <subject>

<body>

<footer>

类型(Type)

  • feat: 新功能
  • fix: 修复 bug
  • docs: 文档更新
  • style: 代码格式(不影响功能)
  • refactor: 重构
  • test: 测试相关
  • chore: 构建/工具变动
  • security: 安全修复

示例

# 好的提交信息 ✅
feat(auth): 添加 JWT 认证支持

实现了 JWT 令牌验证,提升安全性:
- 添加 jose 依赖
- 实现令牌验证函数
- 更新 API 路由
- 添加测试用例

Closes #123

# 好的提交信息 ✅
fix(middleware): 修复静态文件绕过认证的安全漏洞

添加 middleware.ts 拦截 /r/* 路径请求

Security: CVE-2024-XXXX

# 不好的提交信息 ❌
update files
fix bug
改了一些东西

分支命名

  • main - 生产分支
  • develop - 开发分支
  • feature/[name] - 功能分支
  • fix/[name] - 修复分支
  • docs/[name] - 文档分支

测试

运行测试

# 认证测试
export REGISTRY_TOKEN=your_token
./scripts/test-auth.sh

# 构建测试
pnpm build

# Lint 检查
pnpm lint

测试覆盖

新功能应该测试:

  • ✅ 成功路径
  • ✅ 错误处理
  • ✅ 边界条件
  • ✅ 认证/授权

Pull Request 检查清单

提交 PR 前确认:

代码质量

  • 代码遵循项目规范
  • 添加了适当的注释
  • 类型定义完整
  • 无 TypeScript 错误
  • 无 ESLint 警告

功能

  • 功能完整实现
  • 边界条件处理
  • 错误处理完善

测试

  • 本地测试通过
  • 添加了测试(如适用)
  • 认证测试通过

文档

  • 更新了相关文档
  • 添加了使用示例
  • README 已更新(如需要)

安全

  • 无硬编码密钥
  • 环境变量使用正确
  • 敏感信息不在日志中

PR 模板

## 变更描述
简要描述本次变更

## 变更类型
- [ ] 新功能
- [ ] Bug 修复
- [ ] 文档更新
- [ ] 重构
- [ ] 性能优化

## 测试
描述如何测试这些变更

## 截图(如适用)
添加截图

## 检查清单
- [ ] 代码遵循项目规范
- [ ] 添加了必要的测试
- [ ] 更新了相关文档
- [ ] 所有测试通过

常见任务

添加新的认证方法

  1. 修改 app/api/registry/[name]/route.ts
  2. 更新认证逻辑
  3. 更新文档 content/docs/registry/authentication.mdx
  4. 添加测试到 scripts/test-auth.sh

更新组件

  1. 修改 registry/new-york/[type]/[component].tsx
  2. 运行 pnpm registry:build
  3. 测试 API 返回
  4. 提交更改

添加新文档页面

  1. 创建 content/docs/[category]/[page].mdx
  2. 添加 frontmatter
  3. 编写内容
  4. 测试渲染

获取帮助

  • 📚 查看 文档
  • 🐛 提交 Issue
  • 💬 加入讨论

行为准则

  • 尊重所有贡献者
  • 提供建设性反馈
  • 欢迎新手提问
  • 遵循项目规范

感谢您的贡献!每一个 PR 都让项目变得更好。 🎉