---
id: wiki-2026-0508-stylecounsel
title: StyleCounsel
category: 10_Wiki/Topics
status: verified
canonical_id: self
aliases: [Style Counsel, Brand Style Consistency Tool]
duplicate_of: none
source_trust_level: B
confidence_score: 0.75
verification_status: applied
tags: [style-guide, brand-consistency, design-system, ai-tooling]
raw_sources: []
last_reinforced: 2026-05-10
github_commit: pending
tech_stack:
  language: typescript
  framework: design-system-tooling
---

# StyleCounsel

## 매 한 줄
> **"매 brand/style guide 의 enforcement 의 AI counsel"**. 매 design token, voice/tone, visual identity 의 multi-surface consistency 의 검증/제안 layer. 2026 의 맥락 = 매 Figma Variables + Storybook + LLM critic — 매 Cursor/Claude 가 매 PR 의 styleguide drift 를 review.

## 매 핵심

### 매 의도 / 정의
- **StyleCounsel** = 매 brand/style consistency 의 AI-augmented enforcement tool (project-internal naming).
- 매 deliverable: design token compliance, copy voice/tone check, asset spec validation.
- 매 distinct from: ESLint (code style), Prettier (formatting), Stylelint (CSS) — 매 brand layer 의 위.

### 매 layer
- **Design tokens** (W3C Design Tokens spec): color, typography, spacing — 매 single source.
- **Voice/Tone**: 매 brand guideline (Mailchimp/IBM/Atlassian 의 공개 guide 참조).
- **Visual assets**: logo placement, image filters, illustration style.
- **UX copy**: 매 micro-copy consistency (button labels, error msgs).

### 매 응용 / target use
1. 매 monorepo 에서 매 multi-product brand drift 의 방지.
2. 매 marketing/blog/docs 의 voice consistency 의 LLM check.
3. 매 generated asset (DALL-E 4, FLUX Pro 1.5) 의 brand spec 의 validation.
4. 매 PR review 의 automated suggestions.
5. 매 onboarding 의 brand training material.

## 💻 패턴

### Design tokens (W3C spec, 2026)
```json
{
  "color": {
    "brand": {
      "primary":   { "$value": "#0A66FF", "$type": "color" },
      "secondary": { "$value": "#FF5C39", "$type": "color" }
    }
  },
  "typography": {
    "heading-xl": {
      "$value": { "fontFamily": "Inter", "fontWeight": 700, "fontSize": "48px", "lineHeight": "1.1" },
      "$type": "typography"
    }
  }
}
```

### Style Dictionary export → CSS / Tailwind
```javascript
// style-dictionary.config.js
export default {
  source: ["tokens/**/*.json"],
  platforms: {
    css: { transformGroup: "css", buildPath: "build/css/", files: [{ destination: "tokens.css", format: "css/variables" }] },
    tailwind: { transformGroup: "js", buildPath: "build/tw/", files: [{ destination: "tokens.js", format: "javascript/es6" }] },
  },
};
```

### Voice/tone LLM critic (Claude Opus 4.7)
```typescript
import Anthropic from "@anthropic-ai/sdk";
const client = new Anthropic();

const BRAND_VOICE = `
- Friendly but professional (no slang)
- Active voice; sentences <= 20 words
- Use "you" not "users"
- Avoid jargon; explain acronyms first time
`;

export async function styleCounselReview(copy: string) {
  const res = await client.messages.create({
    model: "claude-opus-4-7",
    max_tokens: 1024,
    system: `You are StyleCounsel. Check copy against brand voice:\n${BRAND_VOICE}\nReturn JSON: {issues: [{line, problem, suggestion}], score: 0-1}`,
    messages: [{ role: "user", content: copy }],
  });
  return JSON.parse(res.content[0].type === "text" ? res.content[0].text : "{}");
}
```

### PR review GitHub Action
```yaml
# .github/workflows/stylecounsel.yml
name: StyleCounsel
on: [pull_request]
jobs:
  review:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - uses: actions/setup-node@v4
        with: { node-version: 22 }
      - run: npm ci
      - run: npx stylecounsel review --base origin/${{ github.base_ref }}
        env:
          ANTHROPIC_API_KEY: ${{ secrets.ANTHROPIC_API_KEY }}
      - uses: actions/github-script@v7
        with:
          script: |
            const fs = require('fs');
            const report = JSON.parse(fs.readFileSync('stylecounsel.json', 'utf8'));
            await github.rest.issues.createComment({
              ...context.repo, issue_number: context.payload.pull_request.number,
              body: `## StyleCounsel\nScore: ${report.score}\n\n${report.issues.map(i=>`- L${i.line}: ${i.problem} — ${i.suggestion}`).join('\n')}`,
            });
```

### Image asset spec validation
```typescript
import sharp from "sharp";

const SPEC = {
  hero: { minWidth: 1920, aspect: 16/9, colorspace: "srgb" },
  thumb: { minWidth: 800, aspect: 1, colorspace: "srgb" },
};

export async function validateAsset(path: string, kind: keyof typeof SPEC) {
  const meta = await sharp(path).metadata();
  const spec = SPEC[kind];
  const aspect = (meta.width ?? 0) / (meta.height ?? 1);
  const issues: string[] = [];
  if ((meta.width ?? 0) < spec.minWidth) issues.push(`width < ${spec.minWidth}`);
  if (Math.abs(aspect - spec.aspect) > 0.02) issues.push(`aspect ${aspect.toFixed(2)} != ${spec.aspect}`);
  if (meta.space !== spec.colorspace) issues.push(`colorspace ${meta.space} != ${spec.colorspace}`);
  return { ok: issues.length === 0, issues };
}
```

### Storybook brand-token a11y check
```typescript
// .storybook/preview.ts
import { themes } from "@storybook/theming";
import "../build/css/tokens.css";

export const parameters = {
  a11y: { config: { rules: [{ id: "color-contrast", enabled: true }] } },
  backgrounds: {
    values: [
      { name: "brand-primary", value: "var(--color-brand-primary)" },
      { name: "brand-bg", value: "var(--color-bg)" },
    ],
  },
};
```

### Generated image brand-spec gate (FLUX Pro 1.5)
```typescript
import { Replicate } from "replicate";
const replicate = new Replicate();

async function brandedImage(prompt: string) {
  const out = await replicate.run("black-forest-labs/flux-pro-1.5", {
    input: {
      prompt: `${prompt}, brand style: minimal, sans-serif, blue-orange palette, no text`,
      aspect_ratio: "16:9",
      output_format: "png",
    },
  });
  // 매 then run validateAsset() before publish
  return out;
}
```

## 매 결정 기준
| 상황 | Approach |
|---|---|
| 매 small team / single product | 매 design tokens + Storybook 만 |
| 매 multi-product / monorepo | 매 StyleCounsel pipeline (tokens + LLM critic + CI gate) |
| 매 marketing copy 일관성 | 매 LLM voice critic + 매 weekly editor review |
| 매 generated asset (AI image) | 매 spec gate + manual approval |

**기본값**: 매 design tokens (W3C) + Style Dictionary + LLM voice critic via PR Action — 매 매 light-weight 시작.

## 🔗 Graph
- 부모: [[Design-Systems]]
- 변형: [[Design-Tokens]]
- 응용: [[Storybook]] · [[Style-Dictionary]] · [[Figma-Variables]]
- Adjacent: [[ESLint-Static-Analysis]] · [[Prettier]]

## 🤖 LLM 활용
**언제**: 매 voice/tone review, 매 multi-surface copy consistency, 매 asset spec interpretation, 매 brand violation suggestion.
**언제 X**: 매 strict legal/compliance copy — 매 final human review 필수. 매 LLM 의 brand creativity 의 generation 의 over-trust X.

## ❌ 안티패턴
- **Token X / 매 hardcoded color**: 매 #0A66FF 의 매 30곳 hard-code → 매 brand refresh 시 hell.
- **매 LLM 의 final 결정**: 매 voice critic 의 false positive — 매 human review gate 필요.
- **매 over-strict gate**: 매 PR 의 모든 brand drift block — 매 velocity 죽음. 매 warning 우선.
- **매 brand guide 의 stale**: 매 1년 X update — 매 quarterly 의 refresh 필요.

## 🧪 검증 / 중복
- 신뢰도 B (project-internal naming, 매 공개 standard X — W3C Design Tokens / Style Dictionary / Storybook 은 매 검증된 공개 standard).
- 매 외부 source 의 추가 검증 시 A 로 승격.

## 🕓 Changelog
| 날짜 | 변경 |
|---|---|
| 2026-05-08 | Phase 1 |
| 2026-05-10 | Manual cleanup — StyleCounsel 의 brand consistency tooling 정의 + W3C design tokens / LLM critic pipeline |
