designpaca 초기 구현 — 스킬 · 설치 CLI · 배포 파이프라인

웹 디자인 파이프라인 스킬과 이를 5개 에이전트에 설치하는 CLI 를 담은 모노레포.

스킬 (packages/skill)
- SKILL.md 261줄 + 참조 문서 16개 3,349줄. progressive disclosure 로
  본문은 절차와 인덱스만, 지식은 references/ 로 분리
- 0~6단계 파이프라인. 규모에 따라 전체·연장·국소 세 경로로 분기
- 하드 게이트 12개는 grep·카운트로 검증 가능한 것만. 취향 판단은 제외
- 미학 프리셋 5종, AI 슬롭 지문 목록, 한글 조판 규칙,
  SVG 필터·three.js·인터랙티브 모션·HTML-in-Canvas 실전 지침

설치 CLI (packages/cli, packages/core)
- npx designpaca 온보딩 TUI. Claude Code · Codex · Cursor · Windsurf · AGENTS.md
- 매니페스트에 설치 시점 해시를 기록해 사용자가 고친 파일은 update 가 건너뛴다
- 타깃별로 본문의 references/ 경로를 실제 설치 위치로 재작성
- AGENTS.md 는 항상 로드되므로 본문 대신 303자 포인터만 주입
- Windsurf 는 12,000자 상한 초과 시 설치를 차단

배포 (build/ci, .forgejo/workflows)
- 태그 v* → 검사·테스트·빌드 → npmjs 배포 + Forgejo 레지스트리 미러
  → draft 릴리스 → Cloudflare Pages. 재실행 멱등

근거 (research/)
- 약 250개 웹 소스 조사 결과와 도그푸딩 검증 2건. 스킬의 모든 수치는 여기서 나온다

테스트 22개 통과 (core 16 · cli 6)
This commit is contained in:
Yun Chan 2026-08-20 10:48:00 +09:00
commit 8808c672dc
135 changed files with 38838 additions and 0 deletions

View file

@ -0,0 +1,50 @@
<!doctype html>
<meta charset="utf-8" />
<title>Demo of complex text in canvas</title>
<style>
canvas {
border: 1px solid blue;
width: 638px;
height: 318px;
}
</style>
<canvas id="canvas" width="638" height="318" layoutsubtree="true">
<div id="draw_element" style="width: 550px;">
Hello from <a href="https://github.com/WICG/html-in-canvas">html-in-canvas</a>!
<br>I'm multi-line, <b>formatted</b>,
rotated text with emoji (&#128512;), RTL text
<span dir=rtl>من فارسی صحبت میکنم</span>,
vertical text,
<p style="writing-mode: vertical-rl;">
这是垂直文本
</p>
an inline image (<img width="150" src="wolf.jpg">), and
<svg width="50" height="50">
<circle cx="25" cy="25" r="20" fill="green" />
<text x="25" y="30" font-size="15" text-anchor="middle" fill="#fff">
SVG
</text>
</svg>!
</div>
</canvas>
<script>
const canvas = document.getElementById('canvas');
const ctx = canvas.getContext('2d');
canvas.onpaint = (event) => {
ctx.reset();
ctx.rotate((15 * Math.PI) / 180);
ctx.translate(80 * devicePixelRatio, -20 * devicePixelRatio);
let transform = ctx.drawElementImage(draw_element, 0, 0);
draw_element.style.transform = transform.toString();
};
canvas.requestPaint(); // Request an initial paint event.
const observer = new ResizeObserver(([entry]) => {
canvas.width = entry.devicePixelContentBoxSize[0].inlineSize;
canvas.height = entry.devicePixelContentBoxSize[0].blockSize;
});
observer.observe(canvas, {box: 'device-pixel-content-box'});
</script>