Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 0 additions & 1 deletion .codesandbox/Dockerfile

This file was deleted.

5 changes: 5 additions & 0 deletions .dev.vars.example
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
BETTER_AUTH_SECRET=
GITHUB_CLIENT_ID=
GITHUB_CLIENT_SECRET=
TURNSTILE_SECRET_KEY=
ADMIN_GITHUB_IDS=
11 changes: 11 additions & 0 deletions .github/pull_request_template.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
## 改动

描述用户可见行为和相关约束。

## 验证

填写运行过的检查与结果。

## 文档影响

更新映射中的相关文档;无影响时使用 `docs-impact: none — 具体说明原因(至少十个字符)`,由审查者确认。
125 changes: 125 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,125 @@
name: Quality and release
run-name: ${{ github.event_name }} · ${{ github.ref_name }} · ${{ github.sha }}
on:
pull_request:
push:
branches: [main]
workflow_dispatch:
inputs:
target:
description: "发布目标(仅 main;生产发布会先验证预发布)"
type: choice
default: staging
options:
- staging
- production
permissions:
contents: read
concurrency:
group: portal-${{ github.ref }}
cancel-in-progress: ${{ github.event_name == 'pull_request' }}
jobs:
quality:
name: Quality checks
runs-on: ubuntu-latest
timeout-minutes: 15
steps:
- name: Require main for manual releases
if: github.event_name == 'workflow_dispatch' && github.ref != 'refs/heads/main'
run: |
echo "::error::手动发布请在 Run workflow 中选择 main 分支。"
exit 1
- uses: actions/checkout@v4
with:
fetch-depth: 0
persist-credentials: false
- uses: actions/setup-node@v4
with:
node-version: "24"
- uses: oven-sh/setup-bun@v2
with:
bun-version: 1.4.2
- name: Install dependencies
run: bun install --frozen-lockfile
- name: Generate content and Worker types
run: bun run prepare
- run: bun run check
- run: bun run test
- run: bun run test:workers
- run: bun run build
- run: bun run build:check
- run: git diff --exit-code -- src/routeTree.gen.ts
- name: Documentation impact
if: github.event_name == 'pull_request'
run: bun run docs:impact
env:
DOCS_BASE_SHA: ${{ github.event.pull_request.base.sha }}
PR_BODY: ${{ github.event.pull_request.body }}
staging:
name: Deploy staging
if: github.ref == 'refs/heads/main' && github.event_name != 'pull_request'
needs: quality
runs-on: ubuntu-latest
timeout-minutes: 20
environment:
name: staging
url: https://staging.semicoder.dev
steps:
- name: Check deployment credentials
env:
CLOUDFLARE_API_TOKEN: ${{ secrets.CLOUDFLARE_API_TOKEN }}
CLOUDFLARE_ACCOUNT_ID: ${{ secrets.CLOUDFLARE_ACCOUNT_ID }}
run: |
: "${CLOUDFLARE_API_TOKEN:?请在 staging environment 中配置 CLOUDFLARE_API_TOKEN}"
: "${CLOUDFLARE_ACCOUNT_ID:?请在 staging environment 中配置 CLOUDFLARE_ACCOUNT_ID}"
- uses: actions/checkout@v4
with:
persist-credentials: false
- uses: actions/setup-node@v4
with:
node-version: "24"
- uses: oven-sh/setup-bun@v2
with:
bun-version: 1.4.2
- run: bun install --frozen-lockfile
- name: Generate content and Worker types
run: bun run prepare
- name: Build, migrate, deploy and smoke test staging
run: bun run deploy:staging
env:
CLOUDFLARE_API_TOKEN: ${{ secrets.CLOUDFLARE_API_TOKEN }}
CLOUDFLARE_ACCOUNT_ID: ${{ secrets.CLOUDFLARE_ACCOUNT_ID }}
production:
name: Deploy production
if: github.ref == 'refs/heads/main' && (github.event_name == 'push' || inputs.target == 'production')
needs: staging
runs-on: ubuntu-latest
timeout-minutes: 20
environment:
name: production
url: https://semicoder.dev
steps:
- name: Check deployment credentials
env:
CLOUDFLARE_API_TOKEN: ${{ secrets.CLOUDFLARE_API_TOKEN }}
CLOUDFLARE_ACCOUNT_ID: ${{ secrets.CLOUDFLARE_ACCOUNT_ID }}
run: |
: "${CLOUDFLARE_API_TOKEN:?请在 production environment 中配置 CLOUDFLARE_API_TOKEN}"
: "${CLOUDFLARE_ACCOUNT_ID:?请在 production environment 中配置 CLOUDFLARE_ACCOUNT_ID}"
- uses: actions/checkout@v4
with:
persist-credentials: false
- uses: actions/setup-node@v4
with:
node-version: "24"
- uses: oven-sh/setup-bun@v2
with:
bun-version: 1.4.2
- run: bun install --frozen-lockfile
- name: Generate content and Worker types
run: bun run prepare
- name: Build, migrate, deploy and smoke test production
run: bun run deploy:production
env:
CLOUDFLARE_API_TOKEN: ${{ secrets.CLOUDFLARE_API_TOKEN }}
CLOUDFLARE_ACCOUNT_ID: ${{ secrets.CLOUDFLARE_ACCOUNT_ID }}
35 changes: 13 additions & 22 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,24 +1,15 @@
# build output
dist/
# generated types
.astro/

# dependencies
node_modules/

# logs
npm-debug.log*
yarn-debug.log*
yarn-error.log*
pnpm-debug.log*


# environment variables
.env
.env.production

# macOS-specific files
dist/
.wrangler/
.tanstack/
.output/
coverage/
.env*
!.env.example
.dev.vars*
!.dev.vars.example
worker-configuration.d.ts
src/generated/
public/pagefind/
.DS_Store

# jetbrains setting folder
.idea/
*.log
20 changes: 20 additions & 0 deletions .oxfmtrc.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
{
"$schema": "./node_modules/oxfmt/configuration_schema.json",
"printWidth": 100,
"tabWidth": 2,
"useTabs": false,
"semi": true,
"singleQuote": false,
"endOfLine": "lf",
"proseWrap": "preserve",
"ignorePatterns": [
"src/generated/**",
"src/routeTree.gen.ts",
"worker-configuration.d.ts",
"docs/generated.md",
"public/pagefind/**",
"dist/**",
".wrangler/**",
"bun.lock"
]
}
22 changes: 22 additions & 0 deletions .oxlintrc.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
{
"$schema": "./node_modules/oxlint/configuration_schema.json",
"plugins": ["typescript", "react", "jsx-a11y", "import", "unicorn", "oxc"],
"categories": { "correctness": "error" },
"rules": {
"react/rules-of-hooks": "error",
"react/exhaustive-deps": "warn",
"jsx-a11y/alt-text": "error",
"jsx-a11y/anchor-has-content": "error",
"jsx-a11y/label-has-associated-control": "error",
"no-unused-vars": "error"
},
"ignorePatterns": [
"src/generated/**",
"src/routeTree.gen.ts",
"worker-configuration.d.ts",
"dist/**",
"public/pagefind/**",
"node_modules/**",
".wrangler/**"
]
}
5 changes: 1 addition & 4 deletions .vscode/extensions.json
Original file line number Diff line number Diff line change
@@ -1,4 +1 @@
{
"recommendations": ["astro-build.astro-vscode"],
"unwantedRecommendations": []
}
{ "recommendations": ["oxc.oxc-vscode"] }
5 changes: 5 additions & 0 deletions .vscode/settings.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
{
"editor.defaultFormatter": "oxc.oxc-vscode",
"editor.formatOnSave": true,
"editor.codeActionsOnSave": { "source.fixAll.oxc": "explicit" }
}
30 changes: 30 additions & 0 deletions AGENTS.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
# 新手程序员 · Agent 工作约定

## 开始工作

阅读 [工程文档](docs/README.md)、[架构](docs/architecture.md) 和相关模块文档。网站内容在 `content/`,工程说明在 `docs/`,不要混用。旧 Astro 基线保存在 `archive/astro-before-rebuild`。

## 架构边界

- 单应用 TanStack Start / React,Cloudflare Workers 运行服务端,D1 保存动态数据。
- Bun 负责工具链;Workers 代码不得依赖 Bun API、文件系统或进程内持久状态。
- 数据库、密钥和权限检查放在 `src/server/`,客户端只能通过服务端函数访问。
- 服务端每次写入校验会话、输入、权限;不得相信前端管理员标记。
- 内容稳定 ID 不随 URL 改变;生产构建不能包含草稿或私有数据。
- 数据库采用提交到 Git 的增量迁移,禁止生产 schema push。
- 当前使用 Cloudflare 免费套餐;不得自动升级或添加付费服务。公开内容优先由 Assets 提供,避免消耗动态请求额度;不配置付费版 CPU 上限。

## 质量标准

- TypeScript strict;Oxlint 检查代码;Oxfmt 统一格式。不引入第二套 lint / format 工具链。
- 使用 `bun run fmt`、`bun run lint:fix` 本地修复,提交前执行 `bun run check`、`bun run test`、`bun run test:workers`、`bun run build`。
- 不关闭规则掩盖问题;局部禁用必须附具体理由。不手改生成文件。
- 测试验证行为、权限和失败场景;修改接口时更新相应测试。

## 文档维护与完成标准

- 每次变更根据 `docs/impact.json` 同步维护文档;无文档影响需在 PR 的 `docs-impact: none — 原因` 声明中解释。
- `bun run docs:generate` 生成技术清单,`bun run docs:check` 检查链接与一致性。生成器只写 `docs/generated.md`。
- 架构决策写 ADR;运行方式改变更新部署手册;本文件只记录长期规则,不追加开发日志。
- 交付须说明变更、验证和外部阻塞;未验证的登录、部署、生产数据不得声称成功。
- 不提交密钥、真实用户数据或测试会话。部署环境与 OAuth 应用分离。
57 changes: 22 additions & 35 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,47 +1,34 @@
# Astro Starter Kit: Minimal
# 新手程序员 · semicoder.dev

```sh
npm create astro@latest -- --template minimal
```

[![Open in StackBlitz](https://developer.stackblitz.com/img/open_in_stackblitz.svg)](https://stackblitz.com/github/withastro/astro/tree/latest/examples/minimal)
[![Open with CodeSandbox](https://assets.codesandbox.io/github/button-edit-lime.svg)](https://codesandbox.io/p/sandbox/github/withastro/astro/tree/latest/examples/minimal)
[![Open in GitHub Codespaces](https://github.com/codespaces/badge.svg)](https://codespaces.new/withastro/astro?devcontainer_path=.devcontainer/minimal/devcontainer.json)
中文个人技术门户:博客、项目展示、项目文档、中文搜索、GitHub 登录评论和审核后台。

> 🧑‍🚀 **Seasoned astronaut?** Delete this file. Have fun!
TanStack Start / React / Query · Bun · Cloudflare Workers / D1 · Drizzle · Better Auth · Oxlint / Oxfmt。

## 🚀 Project Structure
## 本地开发

Inside of your Astro project, you'll see the following folders and files:
需要 Bun 1.4.2 和 Node 24。

```text
/
├── public/
├── src/
│ └── pages/
│ └── index.astro
└── package.json
```bash
bun install --frozen-lockfile
bun run db:local
bun run dev
```

Astro looks for `.astro` or `.md` files in the `src/pages/` directory. Each page is exposed as a route based on its file name.

There's nothing special about `src/components/`, but that's where we like to put any Astro/React/Vue/Svelte/Preact components.
打开 http://localhost:3000 。无需密钥即可浏览示例内容;动态评论先初始化本地 D1。真实登录需将 `.dev.vars.example` 复制为 `.dev.vars` 并配置 GitHub OAuth、Turnstile 与管理员 ID。

Any static assets, like images, can be placed in the `public/` directory.
## 验证

## 🧞 Commands

All commands are run from the root of the project, from a terminal:
```bash
bun run fmt
bun run docs:generate
bun run check
bun run test
bun run test:workers
bun run build
```

| Command | Action |
| :------------------------ | :----------------------------------------------- |
| `npm install` | Installs dependencies |
| `npm run dev` | Starts local dev server at `localhost:4321` |
| `npm run build` | Build your production site to `./dist/` |
| `npm run preview` | Preview your build locally, before deploying |
| `npm run astro ...` | Run CLI commands like `astro add`, `astro check` |
| `npm run astro -- --help` | Get help using the Astro CLI |
工程约定见 [AGENTS.md](AGENTS.md),完整说明见 [docs](docs/README.md),环境资源和上线步骤见 [部署手册](docs/deployment.md)。网站内容在 `content/`,与工程文档分离。

## 👀 Want to learn more?
仓库中的文章和项目描述明确标为示例。正式部署前需替换为真实内容、配置 D1 ID、域名、GitHub OAuth 和 Turnstile,并完成预发布验收。没有凭据时不会把功能模拟声称为线上验证。

Feel free to check [our documentation](https://docs.astro.build) or jump into our [Discord server](https://astro.build/chat).
旧 Astro 实现保留在 Git 标签 `archive/astro-before-rebuild`。
11 changes: 0 additions & 11 deletions astro.config.mjs

This file was deleted.

Loading
Loading