关于 development
面向 Edge Delivery Services 项目开发者的技能,用于分析代码库并生成开发者技术指南。流程涵盖架构、组件与配置分析,并要求输出 PDF 指南。
主要功能
- 01分析项目结构与架构
- 02整理自定义文件与核心脚本
- 03记录组件、模型和模板
- 04从 Config Service 获取站点信息
- 05生成开发者指南 PDF
适用场景
- 01为新开发者准备项目入门资料
- 02向维护团队移交技术文档
- 03记录项目架构与设计系统
- 04整理 blocks、models 和 templates
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ adobe/ skills --skill development安装后在 Claude Code 中输入/development确认已加载。
包含的文件
除 SKILL.md 外,安装时一起下载的参考资料和脚本。
.releaserc.jsonCHANGELOG.mdpackage.json详细介绍
项目交接——开发
为开发者生成完整的技术指南。此技能会分析代码库,并生成可执行的文档,帮助开发者理解、维护和扩展项目。
使用此技能的场景
- 帮助新开发者熟悉项目
- 向维护团队进行技术交接
- 代码审查和架构文档编写
- 创建面向开发者的文档
步骤 0:导航至项目根目录并验证 Edge Delivery Services 项目(有条件)
如果设置了 allGuides 标志,请跳过此步骤(编排器已完成验证并导航)。
重要:如果不跳过此步骤,必须执行 cd 命令。不要使用绝对路径——请实际切换目录。
ALL_GUIDES=$(cat .claude-plugin/project-config.json 2>/dev/null | node -e "
const d = require('fs').readFileSync(0,'utf8');
try { console.log(JSON.parse(d).allGuides ? 'true' : ''); } catch(e) { console.log(''); }
")
if [ -z "$ALL_GUIDES" ]; then
# Navigate to git project root (works from any subdirectory)
cd "$(git rev-parse --show-toplevel)"
# Verify it's an Edge Delivery Services project
ls scripts/aem.js
fi
重要:
- 必须使用 Bash 工具运行上面的
cd命令 - 后续所有步骤均从项目根目录执行
- 不要使用绝对路径进行验证——请实际导航
- 指南将在
project-root/project-guides/中创建
如果未跳过此步骤,且 scripts/aem.js 不存在,请回复:
"此技能适用于 AEM Edge Delivery Services 项目。当前目录似乎不是 Edge Delivery Services 项目(未找到
scripts/aem.js)。请导航至 Edge Delivery Services 项目后重试。"
如果检查失败,请停止。否则继续——此时你已位于项目根目录。
沟通指南
- **生成的任何文档或聊天回复中,绝不能使用“EDS”**作为 Edge Delivery Services 的缩写
- 始终使用完整名称“Edge Delivery Services”或“AEM Edge Delivery Services”
- 这适用于所有输出文件(PDF、HTML、Markdown)以及与用户的所有交流
⚠️ 关键路径要求
必须将文件保存到此确切路径:
project-guides/DEVELOPER-GUIDE.md
写入任何文件之前:
- 首先创建目录:
mkdir -p project-guides - 然后写入:
project-guides/DEVELOPER-GUIDE.md
**为何重要:**文件必须位于 project-guides/ 中,才能正确组织并转换为 PDF。
❌ 错误:DEVELOPER-GUIDE.md(根目录)
❌ 错误:docs/DEVELOPER-GUIDE.md
❌ 错误:/workspace/DEVELOPER-GUIDE.md
✅ 正确:project-guides/DEVELOPER-GUIDE.md
输出格式
必须输出:project-guides/DEVELOPER-GUIDE.pdf
严格禁止:
- ❌ 不要读取或分析
fstab.yaml——大多数项目中都不存在此文件,且它无法显示所有站点 - ❌ 不要创建
.plain.html文件 - ❌ 不要使用
convert_markdown_to_html工具——此工具会将完整指南转换为 HTML,并显示原始 frontmatter,这不是我们需要的结果 - ❌ 不要告诉用户“手动将 Markdown 转换为 PDF”
- ❌ 不要将 Markdown 保存到根目录或
project-guides/以外的任何路径 - ❌ 不要说“稍后生成 PDF”或“在会话结束时生成”——现在就生成
必须遵循的工作流:
- 运行
mkdir -p project-guides,确保目录存在 - 生成带有 YAML frontmatter(标题、日期)的 Markdown 内容
- 保存到
project-guides/DEVELOPER-GUIDE.md(确切路径——不得例外) - 立即调用 PDF 转换(参见阶段 5.1)
- 清理所有源文件(仅保留 PDF)
- 最终输出:
project-guides/DEVELOPER-GUIDE.pdf
执行检查清单
- [ ] Phase 1: Gather Project Information
- [ ] Phase 2: Analyze Project Architecture
- [ ] Phase 3: Document Design System
- [ ] Phase 4: Document Blocks, Models, and Templates
- [ ] Phase 5: Generate Professional PDF
阶段 0:获取组织名称(必须首先执行)
每次运行此技能时——无论是用户直接触发(例如“生成开发者指南”),还是通过交接流程触发——在执行其他操作之前,都必须先获取 Config Service 组织名称。不要跳过此阶段。
0.1 检查已保存的组织名称
# Check if org name is already saved
cat .claude-plugin/project-config.json 2>/dev/null | node -e "
const d = require('fs').readFileSync(0,'utf8');
try { const o = JSON.parse(d).org; if(o) console.log('org: ' + o); } catch(e) {}
"
0.2 如果未保存组织名称,则提示用户提供
如果没有保存组织名称,你必须暂停并直接询问用户:
“你的 Config Service 组织名称是什么?这是 Edge Delivery Services URL 中的
{org}部分(例如:https://main--site--{org}.aem.page)。组织名称可能与 GitHub 组织不同。”
重要规则:
- 不要使用带预设选项的
AskUserQuestion—— 以纯文本问题的形式询问 - 组织名称是必填项 —— 不要提供“跳过”选项
- 等待用户输入组织名称后再继续
- 如果用户未提供有效的组织名称,请再次询问
0.3 保存组织名称
获取组织名称后(来自已保存的配置或用户输入),将其保存以供后续使用:
# Create config directory if needed
mkdir -p .claude-plugin
# Ensure .claude-plugin is in .gitignore (contains project config)
grep -qxF '.claude-plugin/' .gitignore 2>/dev/null || echo '.claude-plugin/' >> .gitignore
# Save org name to config file (create or update)
if [ -f .claude-plugin/project-config.json ]; then
cat .claude-plugin/project-config.json | sed 's/"org"[[:space:]]*:[[:space:]]*"[^"]*"/"org": "{ORG_NAME}"/' > /tmp/project-config.json && mv /tmp/project-config.json .claude-plugin/project-config.json
else
echo '{"org": "{ORG_NAME}"}' > .claude-plugin/project-config.json
fi
将 {ORG_NAME} 替换为用户提供的实际组织名称。
阶段 1:收集项目信息
1.1 获取项目 URL 和仓库
# Get repository info
git remote -v | head -1
# Get branch info
git branch -a | head -10
提取:
- 仓库所有者和名称
- 主分支名称
1.2 检查配置方式
# Check for helix-config (very old projects)
ls helix-config.yaml 2>/dev/null && echo "Uses legacy helix-config" || echo "Uses Config Service (modern)"
记录: 项目配置方式(现代项目使用 Config Service)。
1.3 通过 Config Service API 获取站点
⚠️ 必需数据源——不允许使用其他来源
你必须调用 Config Service API。这是唯一可接受的站点信息来源。
❌ 禁止的做法(会导致结果不正确):
- 分析
fstab.yaml—— 无法显示 repoless 设置中的所有站点 - 阅读
README.md—— 内容可能已过时或不完整 - 根据代码库结构推断 —— 会遗漏 CDN 配置和其他站点
- 使用 git 远程 URL —— 组织名称可能与 Config Service 组织不同
- 根据项目文件夹名称进行假设
✅ 必须执行并保存响应:
ORG=$(cat .claude-plugin/project-config.json | node -e "
const d = require('fs').readFileSync(0,'utf8');
console.log(JSON.parse(d).org || '');
")
# Save response to file - Phase 2 depends on this file
curl -s -H "Accept: application/json" "https://admin.hlx.page/config/${ORG}/sites.json" > .claude-plugin/sites-config.json
📁 必需的产物: .claude-plugin/sites-config.json
API 参考: https://www.aem.live/docs/admin.html#tag/siteConfig/operation/getConfigSites
响应是一个包含 sites 数组的 JSON 对象(每个条目都有一个 name 字段)。提取站点名称并构造各站点的 URL:
- 预览:
https://main--{site-name}--{org}.aem.page/ - 线上:
https://main--{site-name}--{org}.aem.live/
多个站点 = repoless 设置。单个站点 = 标准设置。
然后获取各个站点的配置,以了解代码和内容详情。
首先,检查有效的身份验证令牌:
IMS_TOKEN=$(node -e "
const fs = require('fs');
try {
const t = JSON.parse(fs.readFileSync(process.env.HOME + '/.aem/ims-token.json', 'utf8'));
if (t.imsToken && t.imsTokenExpiry > Math.floor(Date.now()/1000) + 60) {
process.stdout.write(t.imsToken);
}
} catch (e) {}
")
if [ -z "$IMS_TOKEN" ]; then
echo "AUTH_REQUIRED"
fi
如果出现 AUTH_REQUIRED,请先调用身份验证技能再继续:
Skill({ skill: "project-management:auth" })
然后获取站点配置:
IMS_TOKEN=$(node -e "
const fs = require('fs');
try {
const t = JSON.parse(fs.readFileSync(process.env.HOME + '/.aem/ims-token.json', 'utf8'));
process.stdout.write(t.imsToken || '');
} catch (e) {}
")
curl -s -H "Authorization: Bearer ${IMS_TOKEN}" "https://admin.hlx.page/config/${ORG}/sites/{site-name}.json"
响应示例:
{
"code": {
"owner": "github-owner",
"repo": "repo-name",
"source": { "type": "github", "url": "https://github.com/owner/repo" }
},
"content": {
"source": {
"url": "https://content.da.live/org-name/site-name/",
"type": "markup"
}
}
}
从响应中提取:
code.owner/code.repo—— GitHub 仓库content.source.url—— 内容挂载路径(例如:https://content.da.live/org/site/)content.source.type—— 内容源类型(markup、onedrive、google)
⚠️ 不要使用 fstab.yaml —— 应改用 Config Service API。
记录结果(repoless 或标准设置)—— 此结果用于“本地开发设置”部分,以判断是否在 aem up 中包含 --pages-url 标志。
1.4 检查 Node.js 要求
# Check for Node version requirements
cat .nvmrc 2>/dev/null || cat package.json | grep -A2 '"engines"'
阶段 2:分析项目架构
读取阶段 1 中的站点配置:
cat .claude-plugin/sites-config.json
2.1 梳理项目结构
# List top-level structure
ls -la
# List blocks
ls -la blocks/
# List scripts
ls -la scripts/
# List styles
ls -la styles/
# Check for templates
ls -la templates/ 2>/dev/null || echo "No templates folder"
2.2 区分样板文件与自定义文件
关键: 仅记录实际经过自定义的文件。
# Check commit history for a file (skip if only "Initial commit")
git log --oneline --follow {file_path} | head -5
# Check who modified a file (skip aem-aemy[bot] only files)
git log --format="%an - %s" --follow {file_path} | head -5
筛选规则:
| Git 历史 | 操作 |
|---|---|
| 仅有“Initial commit” | 跳过——默认样板文件,从未修改 |
仅有 aem-aemy[bot] 提交 | 跳过——自动生成 |
| 团队成员有多个提交 | 记录——已自定义 |
| 包含功能说明的提交 | 记录——已自定义 |
重要: 只有“initial commit”的文件是从未修改过的默认样板文件。不要记录这些文件——它们对开发者指南没有帮助。
2.3 分析 scripts/aem.js(核心库)
# List what aem.js exports (DO NOT MODIFY this file)
grep -E "^export" scripts/aem.js
记录项目从 aem.js 导入的函数(例如,sampleRUM、loadHeader、loadFooter、decorateBlock、loadBlock、loadCSS)。这有助于开发者了解可用的核心工具。
2.4 分析 scripts/scripts.js(Eager + Lazy 阶段)
# Extract imports and key function signatures
grep -E "^import|^export|^function|^async function|buildAutoBlocks|loadTemplate|getLanguage|getSiteRoot|decorateMain|loadEager|loadLazy|loadDelayed" scripts/scripts.js
记录以下自定义内容:
| 要查找的模式 | 要记录的内容 |
|---|---|
import 语句 | 从 aem.js 和 utils.js 导入了什么 |
loadEager / loadLazy 函数 | E-L-D 阶段中添加的任何自定义逻辑 |
buildAutoBlocks 函数 | 自动添加区块的逻辑 |
loadTemplate 或模板处理 | 模板系统 |
getLanguage 或语言检测 | 多语言设置 |
getSiteRoot 或站点检测 | 多站点配置(另请参阅第 1.3 阶段) |
自定义 decorateMain 扩展 | 页面装饰扩展 |
| 外部脚本加载 | 加载脚本的阶段——如果在 eager 阶段加载,请标记(存在性能风险) |
**E-L-D 检查:**记录添加到 loadEager 或 loadLazy 中、可能影响 LCP 的任何第三方脚本或繁重逻辑。这些内容通常应放在 delayed.js 中。
2.5 分析 scripts/delayed.js(延迟阶段)
# Extract imports and function calls to identify integrations
grep -E "^import|function|google|analytics|gtag|alloy|martech|OneTrust|launch|chatbot|widget" scripts/delayed.js
记录:
- 分析集成(Google Analytics、Adobe Analytics 等)
- 营销工具(OneTrust、聊天小组件等)
- 性能监控
- 任何自定义延迟功能
- 确认此文件中没有渲染关键代码(它会在页面加载约 3 秒后加载)
2.6 检查工具函数
# Extract exported functions from utils
grep -E "^export|^function" scripts/utils.js 2>/dev/null || echo "No utils.js"
# List all script files
ls scripts/*.js
# Check which blocks/scripts import from utils
grep -rl "utils.js" blocks/ scripts/ 2>/dev/null
**记录:**共享工具函数、它们的用途,以及哪些区块/脚本导入了它们。
2.7 检查外部依赖项
# Check package.json for dependencies
grep -A 20 '"dependencies"' package.json 2>/dev/null | head -25
# Check for CDN imports in code
grep -r "cdn\|unpkg\|jsdelivr" scripts/ blocks/ --include="*.js" 2>/dev/null
第 3 阶段:记录设计系统
4.1 提取 CSS 自定义属性
# Get all CSS variables from styles.css
grep -E "^\s*--" styles/styles.css
按类别整理:
| 类别 | 属性示例 |
|---|---|
| 字体排版 | --body-font-family、--heading-font-family、--font-size-* |
| 颜色 | --primary-color、--background-color、--text-color |
| 间距 | --spacing-*、--nav-height、--section-padding |
| 布局 | --content-width、--grid-gap |
4.2 记录字体设置
# Extract font-face declarations (font names, weights, formats)
grep -E "@font-face|font-family|font-weight|src:" styles/fonts.css 2>/dev/null
# Check fonts directory
ls fonts/ 2>/dev/null
记录:
- 字体文件和格式
- 字体系列名称
- 可用的字体粗细
- 后备字体
4.3 记录断点
# Find media query breakpoints
grep -E "@media.*min-width|@media.*max-width" styles/styles.css | sort -u
EDS 标准断点:
- 移动端:< 600px
- 平板:600px - 899px
- 桌面端:900px+
- 大屏:1200px+
记录任何偏离标准的情况。
4.4 记录区段样式
# Find section-related styles
grep -A 5 "\.section\." styles/styles.css
grep -A 5 "\.section\[" styles/styles.css
记录可用的区段样式(深色、高亮、窄版等)
第 4 阶段:记录区块、模型和模板
样板代码筛选(适用于区块、模型和模板)
静默执行所有筛选——不要向用户显示输出。
- 纳入:提交次数不少于 2 次,且至少有一次提交发生在“initial commit”之后的项目
- 排除:仅有 1 次提交,且该提交为“Initial commit”或类似样板设置的项目
- 排除:仅有
aem-aemy[bot]提交的项目(自动生成) - 仅有一次“initial commit”的项目从未经过自定义——请勿记录。
4.1 识别并分析自定义区块
对于每个通过筛选的区块,运行:
# Get block purpose from JS comments/structure
head -30 blocks/{blockname}/{blockname}.js
# Get block variants from CSS
grep -E "^\." blocks/{blockname}/{blockname}.css | head -30
# Check for variant handling
grep -E "classList\.contains|classList\.add" blocks/{blockname}/{blockname}.js
为每个自定义区块记录:
| 字段 | 记录内容 |
|---|---|
| 名称 | 区块文件夹名称 |
| 用途 | 功能说明(根据代码分析) |
| DOM 输入 | CMS 中预期的 HTML 结构 |
| DOM 输出 | 装饰后转换成的结构 |
| 变体 | 用于修改行为的 CSS 类 |
| 依赖项 | 外部库、其他区块、工具 |
| 关键函数 | 重要的内部函数 |
4.2 记录区块依赖关系
grep "^import" blocks/{blockname}/{blockname}.js
4.3 记录通用编辑器模型(如有自定义)
对 models/*.json 应用相同的样板内容过滤规则。如果标准样板模型(_page.json、_section.json、_button.json、_image.json、_text.json、_title.json)未发生更改,也应排除。如果所有模型都是样板内容,则在输出中跳过此部分。
4.4 记录自定义模板
对 templates/*/ 应用相同的样板内容过滤规则。对于每个自定义模板,记录其用途、应用方式(元数据中的 template: name)以及它所做的更改。
阶段 5:生成开发者指南
输出文件:project-guides/DEVELOPER-GUIDE.md
生成一个包含以下结构的 Markdown 文档:
# [Project Name] - Developer Guide
## Quick Reference
| Resource | URL |
|----------|-----|
| Code Repository | {code.owner}/{code.repo} (from Config Service — may be GitHub or Cloud Manager) |
| Preview | https://main--{repo}--{owner}.aem.page/ |
| Live | https://main--{repo}--{owner}.aem.live/ |
| Local Dev | http://localhost:3000 |
## Architecture Overview
### Tech Stack
- Vanilla JavaScript (ES6+)
- CSS3 with Custom Properties
- No build step - files served directly
- Content from Document Authoring (DA)
### Project Structure
├── blocks/ # 已实现 [X] 个区块 ├── templates/ # [Y] 个模板(或 N/A) ├── scripts/ │ ├── aem.js # 核心库(请勿修改) │ ├── scripts.js # 自定义页面装饰 │ ├── delayed.js # 分析、营销工具 │ └── utils.js # 共享实用工具 ├── styles/ │ ├── styles.css # 关键样式 + 设计令牌 │ ├── fonts.css # 字体定义 │ └── lazy-styles.css # 非关键样式 └── icons/ # SVG 图标
### Three-Phase Loading (E-L-D)
Edge Delivery Services uses a strict Eager-Lazy-Delayed loading strategy to achieve a Lighthouse score of 100. Every file and script must be placed in the correct phase.
| Phase | Purpose | What Loads | Performance Impact |
|-------|---------|------------|-------------------|
| **Eager** | Render above-the-fold content as fast as possible (LCP) | `styles/styles.css`, first section's blocks, `scripts/scripts.js` | Blocks LCP — keep minimal |
| **Lazy** | Load remaining page content after first paint | Remaining blocks, header, footer, `fonts.css`, `lazy-styles.css` | Runs after Eager completes — safe for non-critical UI |
| **Delayed** | Load non-essential third-party scripts | `scripts/delayed.js` (analytics, marketing tags, chat widgets) | Runs ~3s after page load — never blocks rendering |
**Rules for developers:**
- **Never add third-party scripts to `scripts.js`** — they block LCP. Always use `delayed.js`.
- **Never load fonts eagerly** — `fonts.css` is loaded lazily to avoid render-blocking.
- Blocks in the first section load eagerly; all others load lazily. This is automatic based on DOM position.
- The header and footer are loaded in the lazy phase via `loadHeader()` / `loadFooter()` from `aem.js`.
### Key Files & How They Connect
| File | Role | Connects To |
|------|------|-------------|
| `scripts/aem.js` | Core library — `loadBlock`, `loadCSS`, `decorateBlock`, `sampleRUM`, `loadHeader`/`loadFooter`. **DO NOT MODIFY.** | Imported by `scripts.js` and blocks |
| `scripts/scripts.js` | Entry point — orchestrates E-L-D phases (`loadEager` → `loadLazy` → `loadDelayed`). Contains `buildAutoBlocks`, `decorateMain`, template loading. | Imports from `aem.js`; may import `utils.js` |
| `scripts/delayed.js` | Loaded last via `loadDelayed()` — analytics, marketing tags, third-party scripts. | Called by `scripts.js` in delayed phase |
| `scripts/utils.js` | Shared helpers used across blocks and scripts. | Imported by blocks and `scripts.js` |
| `styles/styles.css` | Critical CSS + design tokens (CSS custom properties). Loaded eagerly. | Referenced by all blocks and pages |
| `styles/fonts.css` | Font `@font-face` declarations. Loaded lazily. | Font families referenced in `styles.css` |
| `styles/lazy-styles.css` | Non-critical global styles. Loaded lazily. | Supplements `styles.css` |
| `blocks/{name}/{name}.js` | Block logic — exports `default function decorate(block)`. Auto-loaded when the block class appears in DOM. | May import from `utils.js` or `aem.js` |
| `blocks/{name}/{name}.css` | Block styles — auto-loaded alongside block JS. | May use CSS custom properties from `styles.css` |
| `templates/{name}/{name}.js` | Template logic — loaded when page metadata has matching `template` value. Customizes page structure before blocks load. | Called by `scripts.js` via `loadTemplate()` |
**Execution flow:** page load → `scripts.js` → `loadEager()` (first section + eager blocks) → `loadLazy()` (remaining blocks, header, footer, `fonts.css`, `lazy-styles.css`) → `loadDelayed()` (loads `delayed.js`)
## Local Development Setup
### Prerequisites
- Node.js [version from .nvmrc]
- AEM CLI: `npm install -g @adobe/aem-cli`
### Setup Steps
```bash
# Clone repository (use the code repo URL from Config Service)
git clone {code-repo-url}
cd {repo}
# Install dependencies
npm install
# Start local server
aem up
本地服务
- URL: http://localhost:3000
- 文件更改时自动重新加载
- 默认使用预览内容
如果在阶段 1.3 中检测到 repoless/多站点,还应在输出中包含以下小节:
本地服务 — Repoless/多站点
对于多个站点共用一个仓库的 repoless 设置,启动本地服务时必须指定该站点的预览 URL:
aem up --pages-url=https://main--{site}--{org}.aem.page将
{site}和{org}替换为 Config Service 中的实际站点名称和组织名称。如果不指定
--pages-url,AEM CLI 将无法解析正确站点的内容,本地预览会失败或显示错误的内容。
如果项目是标准的单站点设置,则完全省略 repoless 小节,以免让开发者困惑。
代码检查
npm run lint
设计系统
CSS 自定义属性
排版
--body-font-family: [value];
--heading-font-family: [value];
颜色
--primary-color: [value];
--secondary-color: [value];
--background-color: [value];
--text-color: [value];
间距
--spacing-s: [value];
--spacing-m: [value];
--spacing-l: [value];
--nav-height: [value];
断点
| 名称 | 最小宽度 | 用途 |
|---|---|---|
| 移动端 | 0 | 默认样式 |
| 平板 | 600px | @media (min-width: 600px) |
| 桌面端 | 900px | @media (min-width: 900px) |
| 大屏幕 | 1200px | @media (min-width: 1200px) |
字体
| 字体系列 | 字重 | 用途 |
|---|---|---|
| [Font Name] | [weights] | [body/headings] |
区块参考
| 区块 | 用途 | 变体 | 主要特性 |
|---|---|---|---|
| [block-name] | [功能说明] | variant1、variant2 | [重要细节、注意事项] |
[每个自定义区块生成一行]
模板
| 模板 | 用途 | 应用方式 | 特殊行为 |
|---|---|---|---|
| [template-name] | [页面类型] | template: [name] | [不同之处] |
[每个自定义模板生成一行。仅有“initial commit”的模板除外。]
常见开发任务
添加新区块
- 创建
blocks/{name}/{name}.js - 创建
blocks/{name}/{name}.css - 实现
export default function decorate(block) - 在 http://localhost:3000 本地测试
- 推送到功能分支
修改全局样式
- 编辑
styles/styles.css - 使用 CSS 自定义属性
- 在多个页面上测试
- 注意 CLS 影响
添加分析/营销工具
- 添加到
scripts/delayed.js - 切勿添加到
scripts.js(会影响性能) - 使用 Network 面板测试,确认是否延迟加载
调试区块
- 检查浏览器控制台中的错误
- 检查 DOM:预期结构与实际结构
- 检查是否已应用变体类
- 验证 CSS 优先级
环境
| 环境 | URL 模式 | 用途 |
|---|---|---|
| 本地 | http://localhost:3000 | 开发 |
| 功能分支 | https://{branch}--{repo}--{owner}.aem.page | PR 测试 |
| 预览 | https://main--{repo}--{owner}.aem.page | 预发布 |
| 线上 | https://main--{repo}--{owner}.aem.live | 生产环境 |
Git 工作流
分支命名
- 功能:
feature/description - 修复:
fix/description - 名称尽量简短(URL 长度有限制)
PR 要求
- 在 PR 描述中包含预览 URL
- 通过 lint 检查
- 在功能分支预览环境中测试
- 不得有控制台错误
故障排查
区块未加载?
- 检查区块文件夹名称是否与类名一致
- 确认 JS 导出
default function decorate - 检查浏览器 Network 标签页中是否有 404 错误
样式未生效?
- 检查 CSS 优先级
- 确认文件已加载(Network 标签页)
- 检查是否存在 CSS 语法错误
内容未更新?
- 清除浏览器缓存
- 检查是否已在 DA 中触发预览
- 等待 CDN 缓存更新(1-2 分钟)
资源
支持联系人
[添加项目专属联系人]
---
### 5.1 Convert to Professional PDF (MANDATORY)
**THIS STEP IS NOT OPTIONAL. YOU MUST GENERATE THE PDF NOW.**
1. Save markdown to: `project-guides/DEVELOPER-GUIDE.md`
- File MUST start with YAML frontmatter:
```yaml
---
title: "[Project Name] - Developer Guide"
date: "[Full Date - e.g., February 17, 2026]"
---
```
- **Date format**: Always use full date with day, month, and year (e.g., "February 17, 2026"), NOT just month and year
2. **IMMEDIATELY after saving the markdown**, invoke the PDF conversion skill:
Skill({ skill: "project-management:whitepaper", args: "project-guides/DEVELOPER-GUIDE.md project-guides/DEVELOPER-GUIDE.pdf" })
3. Wait for PDF generation to complete (whitepaper skill auto-cleans source files)
**DO NOT:**
- Skip the PDF conversion step
- Tell user "PDF will be generated later" — generate it NOW
### 5.2 Deliver to User
After PDF is generated, inform the user:
"✓ 开发者指南已完成:project-guides/DEVELOPER-GUIDE.pdf"
---
## Output
**FINAL OUTPUT:** `project-guides/DEVELOPER-GUIDE.pdf`
All source files (.md, .html, .plain.html) are deleted after PDF generation. Only the PDF remains.
**Location:** `project-guides/` folder
---
## Success Criteria
**Data Source Validation (CRITICAL):**
- [ ] Config Service API was called (`https://admin.hlx.page/config/{ORG}/sites.json`)
- [ ] Site list came from API response, NOT from fstab.yaml or codebase analysis
- [ ] Repoless/standard determination came from Config Service, NOT inferred from code
**Content Validation:**
- [ ] Quick Reference with all project URLs
- [ ] Architecture overview accurate to project
- [ ] Design system fully documented (tokens, fonts, breakpoints)
- [ ] Project-specific blocks documented
- [ ] Custom scripts.js functions documented
- [ ] delayed.js integrations documented
- [ ] Templates documented (if applicable)
- [ ] Local development setup verified
- [ ] Common tasks have clear instructions
- [ ] Troubleshooting section covers common issues
- [ ] Resources linked
**Output Validation:**
- [ ] PDF generated successfully
- [ ] All source files cleaned up (only PDF remains)
---
## Tips for Clear Documentation
1. **Focus on what's unique** - Document project-specific implementations
2. **Use code examples** - Show actual code from the project
3. **Document the "why"** - Explain reasoning behind custom implementations
4. **Include gotchas** - Note any tricky behavior or edge cases
5. **Test the setup instructions** - Verify they work from scratch
6. **Keep it maintainable** - Don't over-document things that change often