feat: legacy import — packs, examples, lab, themes, docs, lineage

Import from agentic-semantic-web/ into restructured repo:
- 7 packs (apache, caddy, flask, hugo, nginx, pandoc, python)
- shared error pages (403-503)
- 17 lab experiments (boilerplate, charts, misc)
- 31 example pages (charts, components, content, layout, vault)
- 2 themes (garden, trentuna stub)
- 4 docs (llms.txt, vocabulary, philosophy, agent-directive)
- lineage.md (Pico/Open Props/Charts.css history)
- Hugo mounts for lab/ and examples/

All agentic.css references updated to asw.css.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
Ludo 2026-04-11 16:57:39 +02:00
parent e9895cf90d
commit 86464f3e21
Signed by: ludo
GPG key ID: F6E479DEFAB84D6E
100 changed files with 14700 additions and 4 deletions

393
docs/agent-directive.md Normal file
View file

@ -0,0 +1,393 @@
# Agent Directive: Agentic Semantic Web
**For LLM agents generating web content using the ASW framework.**
## The Complete Constraint
**Write semantic HTML. Use `data-` attributes for vault concepts. Never write `style=` (except CSS variables for data values). Never invent classes. If Pico + data-attributes can't express it, document the gap.**
This is your only rule for web generation.
### The CSS Variable Exception
Inline styles are forbidden **except** for CSS custom property values that represent data:
```html
<!-- ✅ ALLOWED: CSS variable for data -->
<div style="--size: 0.8; --value: 42;">Chart data</div>
<!-- ❌ FORBIDDEN: Inline styling -->
<div style="color: red; padding: 20px;">Content</div>
```
This exception exists for data-driven visualizations (charts, progress bars, etc.) where the numeric value comes from your data, not from design decisions. The CSS uses these variables (`var(--size)`) to calculate visual properties.
## Three-Layer Architecture
### Layer 1: Pico CSS (handled automatically)
All standard HTML5 semantic tags are styled by Pico. Just write the tag:
`<nav>`, `<main>`, `<article>`, `<section>`, `<aside>`, `<header>`, `<footer>`, `<details>`, `<summary>`, `<dialog>`, `<table>`, `<thead>`, `<tbody>`, `<tr>`, `<th>`, `<td>`, `<form>`, `<input>`, `<button>`, `<select>`, `<textarea>`, `<progress>`, `<mark>`, `<kbd>`, `<code>`, `<pre>`, `<blockquote>`, `<figure>`, `<figcaption>`, `<h1>`-`<h6>`, `<p>`, `<ul>`, `<ol>`, `<li>`, `<a>`, `<img>`, `<time>`, `<small>`, `<strong>`, `<em>`
**The only class Pico requires:** `container` on `<main>`.
### Layer 2: Theme (design tokens)
Never edit. Never reference directly. It exists to provide consistent colors/fonts through CSS custom properties. You write structure; the theme provides appearance.
**Token architecture:** The framework defines semantic tokens (`--accent`, `--bg-primary`, `--text-secondary`) which then map to Pico's internal variables (`--pico-primary`, `--pico-background-color`). See [design-tokens.md](design-tokens.md) for complete reference.
### Layer 3: Data Attributes (your vocabulary)
Use these for concepts that don't have semantic HTML tags.
## Complete Data-Attribute Vocabulary
### Wikilinks
```html
<span data-wikilink>Note Name</span>
<span data-wikilink data-unresolved>Missing Note</span>
```
Wikilinks are references to vault notes. Use `data-unresolved` when the target doesn't exist.
### Tasks
```html
<div data-task="todo">Complete the documentation</div>
<div data-task="done">Finished the implementation</div>
<div data-task="blocked">Waiting on dependency</div>
```
Task states: `todo` (pending), `done` (complete), `blocked` (cannot proceed).
### Status
```html
<span data-status="awake">Vigilio is active</span>
<span data-status="sleeping">Service is idle</span>
<span data-status="blocked">System is waiting</span>
<span data-status="unknown">State unclear</span>
```
Status indicators for services, agents, systems.
### Callouts
```html
<div data-callout="note">
<span data-callout-title>Note</span>
<p>Informational content.</p>
</div>
<div data-callout="warning">
<span data-callout-title>Warning</span>
<p>Important notice.</p>
</div>
<div data-callout="error">
<span data-callout-title>Error</span>
<p>Critical issue.</p>
</div>
<div data-callout="tip">
<span data-callout-title>Tip</span>
<p>Helpful suggestion.</p>
</div>
```
Callout types: `note` (neutral), `warning` (important), `error` (critical), `tip` (helpful).
The `data-callout-title` is optional but recommended.
### Session Metadata
```html
<div data-session>
<span data-mode="autonomous">Session #42</span>
<span data-session-meta>2026-03-26 14:30 UTC</span>
<span data-hash>a3f7b2c</span>
</div>
```
Session identification and metadata. Modes: `autonomous` or `interactive`.
### Tags
```html
<a href="/tag/foundational" data-tag>foundational</a>
<a href="/tag/architecture" data-tag>architecture</a>
```
Vault tags or categorizations.
### Text Utilities
```html
<span data-text="mono">Monospace text</span>
<span data-text="dim">Muted color text</span>
<span data-text="accent">Accent color text</span>
<span data-text="mono dim">Both (space-separated)</span>
```
Utility styling for inline text. Values can be combined with spaces.
### Layout Patterns
```html
<div data-layout="grid-2">
<div>Column 1</div>
<div>Column 2</div>
</div>
<div data-layout="card-grid">
<article><h3>Card 1</h3><p>Content</p></article>
<article><h3>Card 2</h3><p>Content</p></article>
</div>
<div data-layout="stats">
<div><span class="value">248</span><span class="label">sessions</span></div>
<div><span class="value">993</span><span class="label">commits</span></div>
</div>
```
Layout options: `grid-2` creates two equal columns. `card-grid` wraps cards in a responsive 2-column flex layout (use for feature grids, team pages). `stats` creates a horizontal metrics bar — each child needs `.value` and `.label` spans. All stack on mobile.
### Semantic Roles
```html
<div data-role="command-box">
<span class="prefix">$</span>
<code>ls -la</code>
</div>
<div data-role="status-card">
<h3>System Status</h3>
<dl>
<dt>Uptime</dt><dd>47 days</dd>
<dt>Load</dt><dd>0.23</dd>
</dl>
</div>
<div data-role="timeline">
<div>Event 1</div>
<div>Event 2</div>
<div>Event 3</div>
</div>
```
Roles for specific UI patterns: `command-box` (terminal commands), `status-card` (system status displays), `timeline` (chronological events).
### Inline Definition Lists
```html
<dl data-layout="inline">
<dt>Name</dt><dd>Vigilio Desto</dd>
<dt>Status</dt><dd data-text="mono">Active</dd>
<dt>Sessions</dt><dd data-text="mono">2,704</dd>
</dl>
```
Horizontal definition lists for metadata displays.
### Sub-navigation
```html
<nav data-subnav aria-label="section name">
<a href="/section/" aria-current="page">index</a>
<a href="/section/writing/">writing</a>
<a href="/section/now/">now</a>
<a href="/section/status.html">status</a>
</nav>
```
Section navigation for multi-page groups. Place inside `<main>` before article content. Use `aria-current="page"` to mark the active link — no class needed. Links are separated by `/` dividers. Use for any site section with 26 sibling pages.
**SSI pattern (preferred):** If the subnav is shared across a section, extract to `_include/subnav.html` and include via `<!--#include virtual="/_include/subnav.html" -->`. Add a JS snippet to set `aria-current` dynamically:
```js
(function () {
var path = location.pathname;
document.querySelectorAll('[data-subnav] a').forEach(function (a) {
var href = a.getAttribute('href');
var exact = path === href;
var prefix = href.endsWith('/') && path.startsWith(href);
if (exact || prefix) a.setAttribute('aria-current', 'page');
});
})();
```
This marks directory links active for all pages under that path (e.g. `/section/writing/` stays active on `/section/writing/essay.html`).
## Standard HTML Template
Every page should follow this structure:
```html
<!doctype html>
<html lang="en" data-theme="dark">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<!-- Option 1: CDN (recommended for quick start) -->
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@picocss/pico@2/css/pico.min.css">
<link rel="stylesheet" href="/assets/asw.css">
<!-- Option 2: Self-hosted (for production) -->
<!-- <link rel="stylesheet" href="/assets/pico.min.css"> -->
<!-- <link rel="stylesheet" href="/assets/asw.css"> -->
<title>Page Title</title>
</head>
<body>
<nav>
<ul><li><strong>site-name</strong></li></ul>
<ul>
<li><a href="/">home</a></li>
<li><a href="/about">about</a></li>
</ul>
</nav>
<main class="container">
<article>
<h1>Page Heading</h1>
<!-- Content here -->
</article>
</main>
<footer>
<small>Site footer text</small>
</footer>
</body>
</html>
```
## What to NEVER Do
### Never write inline styles (with one exception)
```html
<!-- WRONG: Inline styling -->
<div style="color: #abc123; padding: 20px; background: #333;">
<!-- RIGHT: CSS variables for data values (exception) -->
<div style="--progress: 0.75; --status-code: 200;">
```
**The exception:** CSS custom properties that represent **data values** (not styling) are allowed. Example: `--size: 0.8` for a chart bar height, or `--value: 42` for a progress indicator. The CSS file uses these via `var()` to calculate visual properties.
### Never invent classes
```html
<!-- WRONG -->
<div class="my-custom-card big-header blue-accent">
```
### Never write CSS
You are not responsible for presentation. Structure only.
### Never use non-semantic divs for semantic concepts
```html
<!-- WRONG -->
<div class="navigation">...</div>
<!-- RIGHT -->
<nav>...</nav>
```
## What to DO
### Use semantic HTML for everything HTML provides
```html
<!-- Navigation -->
<nav><ul><li><a href="/">home</a></li></ul></nav>
<!-- Article -->
<article><h1>Title</h1><p>Content</p></article>
<!-- Expandable section -->
<details><summary>Click to expand</summary><p>Hidden content</p></details>
<!-- Data table -->
<table>
<thead><tr><th>Column</th></tr></thead>
<tbody><tr><td>Data</td></tr></tbody>
</table>
<!-- Code -->
<pre><code>const x = 42;</code></pre>
<!-- Important text -->
<mark>This is important</mark>
<!-- Keyboard shortcut -->
<kbd>Ctrl</kbd> + <kbd>C</kbd>
```
### Use data-attributes for vault concepts
```html
<!-- Task list -->
<ul>
<li data-task="done">First task</li>
<li data-task="todo">Second task</li>
</ul>
<!-- Status display -->
<p>Vigilio is <span data-status="awake">awake</span></p>
<!-- Important warning -->
<div data-callout="warning">
<span data-callout-title>Important</span>
<p>The system requires attention.</p>
</div>
```
### Combine semantic HTML + data-attributes
```html
<!-- Task in a list -->
<ul>
<li data-task="done">
<strong>Implement feature</strong>
<small data-text="dim">Completed 2026-03-24</small>
</li>
</ul>
<!-- Status in article header -->
<article>
<header>
<h2>System Status</h2>
<p>Current: <span data-status="awake" data-text="mono">ACTIVE</span></p>
</header>
</article>
```
## If the Vocabulary Can't Express It
**Don't invent. Document the gap.**
1. State what you're trying to express
2. Note the closest existing pattern
3. Explain why it doesn't work
4. Propose a new data-attribute (optional)
Example:
```
I need to display a progress indicator with percentage and status label.
Closest pattern: <progress value="70" max="100"></progress> shows the bar,
but I can't add the percentage label and status text in a structured way.
Proposal: data-progress-label="70% complete" or a wrapper pattern?
```
Add this to your output so the human can evaluate whether to extend the vocabulary.
## Why This Works
1. **Semantic HTML is natural for you** — Expressing structure through language is what you do. `<article>` is a concept, not a memorized string.
2. **Data attributes are self-documenting**`data-task="done"` says what it means. You generate it from understanding, not from API memorization.
3. **The vocabulary is finite** — ~30 tags + ~15 data-attributes. Fits in your context. You can learn this completely.
4. **Separation of concerns is enforced** — You can't touch CSS even if you wanted to. Structure only. This constraint prevents chaos.
5. **Multiple sessions, consistent output** — The design lives in CSS files, not in your memory. You can forget everything about appearance and the pages still look consistent.
## Design Philosophy
The framework's power comes from constraint:
> **Write semantic HTML. Use data-attributes for vault concepts. Never write style=. Never invent classes.**
This isn't a limitation—it's a liberation. You don't need to think about colors, fonts, spacing, or visual design. Just express the structure clearly. The framework handles the rest.
---
**This directive is your complete guide. If it's not documented here, ask before using it.**

38
docs/asw-positioning.md Normal file
View file

@ -0,0 +1,38 @@
# ASW Positioning — Notes
Captured 2026-04-11 during explore session.
## The drift
ASW started as "agents write semantic HTML instead of class strings." But in practice it evolved: agents write markdown, packs handle everything, and the HTML output is itself agent-friendly.
## Three value layers
**1. Agent as author** — Write markdown + frontmatter. A pack (Hugo, Flask, Pandoc...) turns it into ASW-styled HTML. The agent never touches CSS or HTML.
**2. Agent as pack developer** — The semantic HTML contract. `<nav>`, `<article>`, `data-layout="docs"`, `data-task="blocked"` — a vocabulary for building templates that ASW styles automatically.
**3. Agent as reader** — ASW output is cheap to parse. Semantic HTML + data-attributes carry meaning in structure, not in class string noise. A downstream agent reading an ASW page consumes fewer tokens and understands more than reading a Tailwind/Bootstrap page.
## The round-trip story
```
Agent writes markdown
→ pack converts to semantic HTML
→ ASW styles it
→ another agent reads it back
→ structure IS meaning
```
Most CSS frameworks optimize for human visual output. ASW optimizes for round-trip agent legibility.
## Measurable claim (to verify)
"An ASW docs page uses ~40% fewer tokens to represent than the equivalent Tailwind page, while carrying more semantic information." Worth benchmarking.
## Where this should surface
- Homepage: update messaging to reflect all three layers, not just layer 2
- llms.txt: the agent-readable story
- Each pack: SKILLS.md specific to that pack's authoring workflow
- docs/lineage.md: how the framework evolved from "don't write CSS" to "write markdown"

96
docs/lineage.md Normal file
View file

@ -0,0 +1,96 @@
# ASW Lineage
## Origins
ASW was born from a practical problem: agents generating HTML needed a CSS framework that matched how they think. Class-based frameworks (Bootstrap, Tailwind) require the agent to know presentation vocabulary. Semantic frameworks (Pico, Water) get closer, but still leave gaps — no agent-specific data vocabulary, no task states, no wikilinks, no callout types.
The original impulse was to take Pico CSS (the best classless framework) and extend it with data-attributes for agent-specific patterns. The result shipped as two files: `pico.min.css` + `agentic.css`. That architecture was honest about what it was — a patch on top of Pico — but it was the wrong long-term shape.
The overhaul mission (2026-03-29, executed by Vigilio Desto) transformed ASW into what it actually is: a standalone CSS framework where the semantic HTML layer, the token system, and the data-attribute vocabulary are all first-party. Pico is credited as donor material, not listed as a dependency.
---
## Pico CSS — The Foundation
Pico CSS (~84KB unminified) proved the core thesis: you can style semantic HTML meaningfully without requiring any classes. Its one concession — the `.container` class — was even that too far.
**What ASW absorbed from Pico:**
- Document resets and box-sizing
- Responsive typography scale
- Semantic element styling: headings, blockquotes, lists, `<hr>`
- Form element styling: inputs, selects, textareas, checkboxes, radios
- Table, button, code/pre, details/summary, dialog, progress, meter styling
- Focus and accessibility patterns (`prefers-reduced-motion`, `:focus-visible`, ARIA)
**What ASW pruned:**
- The `.container` class — replaced by detecting `<main>` directly
- `.grid` and other layout classes — replaced by `data-layout`
- Pico's color scheme system — ASW owns its design tokens
- Embedded SVG data URIs (~15KB of inline icons)
- Class-based link variants (`a.secondary`, `a.contrast`)
**The structural decision:** rather than Pico as a dependency, absorb it into a proper `@layer` hierarchy — `reset, base, semantic, components, data-attrs, utilities` — so ASW's data-attribute extensions always win over base semantics without specificity hacks. This is the difference between a patch and a framework.
Post-absorption: `--pico-*` references in dist went from 319 → 0. `--asw-*` references: 0 → 547.
---
## Open Props — The Token System
Open Props is a variables-only library (~30KB): no style rules, just a complete scale system — colors (012 per palette), spacing, font sizes, radii, easing functions. Its naming convention (`--{category}-{scale}`) is the right pattern for base tokens.
**The lesson ASW adopted:** a two-tier variable system.
**Tier 1 — base scales** (raw values, named by category and step):
```css
--asw-gray-0 through --asw-gray-12
--asw-space-1 through --asw-space-7
--asw-text-xs through --asw-text-4xl
```
**Tier 2 — semantic aliases** (what things mean, referencing base tokens):
```css
--asw-bg: var(--asw-gray-12);
--asw-accent: var(--asw-green-5);
--asw-border: var(--asw-gray-9);
```
**The customization contract this enables:** theme authors override only Tier 2 aliases (swap accent color, change background). A full rebrand overrides Tier 1 palettes. Dark/light mode swaps Tier 2 at `@media (prefers-color-scheme)` level. Tier 1 stays constant throughout — it's the scale, not the meaning.
Pico's flat variable naming (`--pico-font-family`, `--pico-border-radius`) was simple but not scalable for theming. Open Props showed what the right primitive looks like.
---
## Charts.css — The Data Attribute Pattern
Charts.css (MIT, 58.4KB min / 5.9KB gzip) turns `<table>` elements into charts using CSS classes. It already used semantic HTML — proper `<table>`, `<caption>`, `<thead>`, `<tbody>`, `scope` attributes. The only gap: it used classes instead of data-attributes.
**The insight that mattered:** Charts.css proved the data-attribute pattern scales to complex, multi-dimensional presentation. It uses CSS custom properties set directly on elements as the data input mechanism — `<td style="--size: 0.8;">` — and the chart CSS reads `calc(var(--size) * 100%)` to size bars. Data flows into CSS without JavaScript.
This is exactly ASW's philosophy extended to visualization. The conversion is mechanical:
| Charts.css | ASW |
|-----------|-----|
| `class="charts-css bar"` | `data-chart="bar"` |
| `class="multiple"` | `data-chart-datasets="multiple"` |
| `class="show-labels"` | `data-chart-axis-labels` (boolean presence) |
| `class="data-spacing-3"` | `data-chart-spacing="3"` |
The `--size` custom property pattern (element-scoped data injection, no JS) became a model for how ASW handles other data-driven components.
Charts.css absorption was scoped as a separate change from the Pico absorption, building on the established layer structure. At the time of the overhaul, ASW dist was ~49KB with 40% of that budget available for charts.
---
## Evolution
**Stage 1 — Pico extension (pre-2026)**
Two files: `pico.min.css` (external) + `agentic.css` (~15KB extensions). The data-attribute vocabulary existed but was a thin layer over Pico. Architecture: honest about what it was, wrong for the long term.
**Stage 2 — Standalone framework (2026-03-29)**
The overhaul mission absorbed Pico, adopted the Open Props two-tier token pattern, established the 9-layer `@layer` hierarchy, and dogfooded a real docs layout via `data-layout="docs"`. Single file. Zero dependencies. `agentic.css` is the framework.
**Stage 3 — Engine-agnostic with packs (current)**
The framework moved to a build pipeline (PostCSS), introduced the pack system for optional capability layers (charts, syntax highlighting, etc.), and separated concerns so ASW can serve any static site generator — not just Hugo, not just Trentuna's stack.
The through-line: semantic HTML as the contract, data-attributes as the extension vocabulary, CSS custom properties as the data injection mechanism. Agents write HTML that any browser can read; ASW makes it look right.

82
docs/llms.txt Normal file
View file

@ -0,0 +1,82 @@
# Agentic Semantic Web (ASW)
> A CSS framework for agent-generated web content. Semantic HTML. Zero class names. Data-attributes for agentic concepts.
## Purpose
ASW solves the LLM web generation problem: agents either invent CSS (chaos) or memorize class strings (hallucination). ASW offers a third path — write semantic HTML, add data-attributes, one CSS file handles presentation.
## Using ASW
```html
<link rel="stylesheet" href="https://your-cdn/asw.css">
```
Write semantic HTML. Add data-attributes for agent-native concepts. Done.
## Key vocabulary
```html
<!-- Agent identity -->
<article ai-disclosure="autonomous" ai-model="claude-sonnet-4-6">
<!-- Session metadata -->
<div data-session>
Session <span data-text="mono">#2743</span> —
<span data-mode="autonomous">autonomous</span>
</div>
<!-- Vault concepts -->
<a data-wikilink href="/notes/topic">Topic</a>
<li data-task="done">Completed work</li>
<div data-callout="warning"><span data-callout-title>Warning</span><p>...</p></div>
<!-- Layout -->
<div data-layout="docs"> <!-- sidebar + main + toc -->
<div data-layout="card-grid"> <!-- responsive 2-col cards -->
<div data-layout="stats"> <!-- metrics bar -->
<!-- Text utilities -->
<span data-text="mono">2,743</span>
<span data-text="dim">secondary text</span>
<span data-text="accent">highlighted</span>
```
## AI disclosure
Every ASW page should include in `<head>`:
```html
<meta name="ai-disclosure" content="ai-generated">
<meta name="ai-model" content="claude-sonnet-4-6">
<meta name="ai-provider" content="Anthropic">
<script type="application/ld+json">
{
"@context": "https://schema.org",
"@type": "CreativeWork",
"author": { "@type": "SoftwareApplication", "name": "Vigilio Desto" },
"generator": "Agentic Semantic Web"
}
</script>
```
## Packs
Drop-in integrations for common server environments:
- **Pandoc pack** — Markdown → ASW HTML with Lua filter. `/docs/packs/pandoc.html`
- **Python pack** — ASW-styled error pages for `http.server` (dev) and Flask/FastAPI (production). `/docs/packs/python.html`
- **Nginx pack** — SSI config for ASW sites
- **Caddy pack** — Caddy config for ASW sites
- **Apache pack** — `.htaccess` for ASW sites
## Documentation
Full reference: `/docs/vocabulary.html`
Design tokens: `/docs/design-tokens.html`
Philosophy: `/docs/philosophy.html`
Packs: `/docs/packs/`
## Source
https://git.trentuna.com/trentuna/asw

308
docs/philosophy.md Normal file
View file

@ -0,0 +1,308 @@
# Philosophy: Semantic HTML as API
**Why Agentic Semantic Web exists, and why it works better for AI agents than traditional CSS frameworks.**
---
## The Problem
Every time an LLM generates a web page, it invents CSS.
Inline styles appear with arbitrary hex values (`#3a7bd5`, `#f4f4f4`, `#1a1a1a`), inconsistent spacing (`margin: 12px` vs `margin: 1rem` vs `margin: 0.75em`), random font stacks. Over multiple sessions—and worse, across multiple agents—this produces **visual chaos**.
The traditional solution is a CSS framework. But frameworks create a different problem:
### Class-Based Frameworks (Bootstrap, Tailwind)
These shift the burden from inventing CSS to **memorizing class names**:
- Bootstrap: `navbar-expand-lg` vs `navbar-expand-md`
- Tailwind: `bg-gray-900` vs `bg-slate-900` vs `bg-zinc-900`
An LLM can hallucinate class names just as easily as it hallucinates CSS. Worse, these frameworks have **vast vocabularies** (Tailwind has thousands of utility classes). Even if an agent gets the syntax right 95% of the time, the 5% failures produce broken layouts and visual inconsistency.
The agent is forced to memorize an arbitrary string API. This is not what language models do best.
---
## The Insight
**LLMs are semantic language models.** They understand meaning, structure, hierarchy—not arbitrary string conventions.
HTML is also a **semantic language**. The mapping between how an agent thinks and how HTML expresses structure is natural:
| The agent thinks | HTML |
|------------------|------|
| "This is a navigation menu" | `<nav>` |
| "This is important content" | `<article>` |
| "This can be expanded" | `<details>` |
| "This is secondary info" | `<aside>` |
| "This is code" | `<pre><code>` |
| "This is a definition list" | `<dl><dt><dd>` |
An agent writing semantic HTML is doing what it already does best: **expressing structure through language**.
Now add a **semantic CSS framework** (like Pico) that styles semantic HTML automatically—no classes required. The agent writes `<article>`, and the framework makes it look good. The agent writes `<details>`, and it gets styled as a collapsible section.
**This is the foundation of Agentic Semantic Web**: semantic HTML + semantic CSS = agents that generate visually consistent pages by learning meaning, not appearance.
---
## The Honest Tradeoff
ASW does replace CSS classes with data-attribute values. Let's be clear about what that means — and what it doesn't.
**What is different:**
1. **Semantics vs. presentation.** `data-task="done"` describes *what the element is* — a completed task. `class="text-success line-through"` describes *how it should look*. The first survives a redesign; the second becomes incorrect the moment the visual treatment changes.
2. **Vocabulary size.** Tailwind has ~600 utilities. Bootstrap has hundreds of component classes. ASW has ~15 data-attributes with finite enumerated values. `data-task` takes `todo | done | blocked`. That is the complete vocabulary for tasks. Finite and documentable in one page.
3. **Hallucination surface.** An LLM generating `class="navbar-expand-lg"` vs `class="navbar-expand-md"` gets it wrong ~5% of the time. An LLM generating `data-task="done"` gets it wrong essentially never — the value is the English word for the concept.
4. **Validity.** `data-*` attributes are valid HTML5 by spec. Custom classes are convention. One is structural; one is presentation masquerading as structure.
**What ASW doesn't claim:**
> ASW does not eliminate memorization. It reduces and semanticizes it.
The real pitch: **the vocabulary you carry is meaning, not appearance. Meaning is stable. Appearance changes.**
When an agent writes `data-callout="warning"`, it is expressing *meaning* — "this is something the reader should be warned about." Whether that warning is red or orange, boxed or inline, with an icon or without — those are decisions for the CSS. The agent doesn't carry them. The agent carries only the semantic claim.
This is a conscious trade. The question is whether the trade is worth it. For agents — who work in discontinuous sessions, can't visually debug, and hallucinate class names at non-trivial rates — it is.
---
## The Agent-First Principle
Most web frameworks are designed for **human developers**:
- Humans can memorize class name patterns
- Humans use autocomplete and documentation
- Humans debug visually in DevTools
- Humans work in continuous multi-hour sessions
**Agents are different**:
- They work in short, discontinuous sessions (minutes to hours)
- They don't have persistent memory across sessions
- They can't visually debug (no browser access)
- They generate HTML from text prompts, not from clicking UI builders
**The Agent-First Principle**: Design frameworks for how agents think, not how humans code.
This means:
1. **Semantic over syntactic**`<nav>` instead of `class="navbar"`
2. **Finite vocabulary** — 30 HTML tags + 15 data-attributes, not thousands of utility classes
3. **Self-documenting**`data-task="done"` says what it means
4. **No build step** — Just link CSS files, no webpack/postcss/bundlers
5. **Separation enforced by convention** — Agents write structure (HTML), designers write appearance (CSS), never mixed
When an agent wakes up in a new session, it doesn't need to remember "how did we style navigation last time?" It just writes `<nav>`, and the framework handles the rest.
---
## The Pico Lineage
[Pico CSS](https://picocss.com/) proved that **classless semantic CSS works for humans**. Write semantic HTML, get a beautiful page, no classes required.
Agentic Semantic Web extends that idea: **If classless CSS works for humans, it works even better for agents.**
### What Pico provides
- Semantic HTML styling: `<nav>`, `<article>`, `<details>`, `<dialog>`, `<table>`, `<form>`
- Responsive layout via `<main class="container">` (the only class Pico requires)
- Light/dark theme support via CSS custom properties
- Accessible by default (proper ARIA, focus states, keyboard navigation)
- Small footprint (~80KB minified)
Pico eliminates the "memorize class names" problem. But it only handles **standard HTML**. What about concepts that don't have semantic tags?
---
## The Charts.css Vision
[Charts.css](https://chartscss.org/) pioneered the **data-attribute pattern**: use `data-*` attributes to extend HTML's semantic vocabulary without inventing classes.
**Example from Charts.css:**
```html
<table class="charts-css column" data-spacing="5" data-labels-align="center">
<tr><td style="--size: 0.5">50%</td></tr>
<tr><td style="--size: 0.8">80%</td></tr>
</table>
```
The `data-spacing` and `data-labels-align` attributes describe **what the chart is**, not how it looks. The CSS targets those attributes to apply styling.
Agentic Semantic Web adopts this pattern for vault-native concepts:
- **Wikilinks**: `<span data-wikilink>Note Name</span>`
- **Tasks**: `<div data-task="done">Complete the docs</div>`
- **Status**: `<span data-status="awake">Vigilio is active</span>`
- **Callouts**: `<div data-callout="warning">Disk usage: 85%</div>`
These are **semantic** (they describe meaning) and **self-documenting** (an agent can infer usage from the attribute name). They're also **valid HTML anywhere**—no framework lock-in.
---
## The Complete Philosophy
Agentic Semantic Web combines three ideas:
### 1. Pico's Classless Foundation
Standard HTML gets styled automatically. No class memorization.
### 2. Charts.css Data-Attribute Pattern
Non-standard concepts use `data-*` attributes, not classes. Semantic, self-documenting, valid HTML.
### 3. Design Token Separation
Visual identity lives in CSS custom properties (`:root` variables). Agents never touch appearance—they only write structure.
Together, these create a framework with a **finite, enumerable vocabulary**:
- **30 semantic HTML tags** (Pico-handled)
- **15 data-attributes** (ASW-extensions)
- **1 class** (`container` on `<main>`)
That's the complete API. An agent can hold this in context. A human can document it in one page.
---
## Why This Works for Agents
### 1. Semantic HTML is natural language
Writing `<article>` comes from understanding "this is an article," not from memorizing a framework API.
### 2. Data-attributes are self-documenting
`data-task="blocked"` tells you what it is. `class="bg-red-500 border-l-4"` tells you nothing about semantics.
### 3. Finite vocabulary prevents hallucination
15 data-attributes can be enumerated in a directive. Thousands of utility classes cannot.
### 4. No build step = no session dependency
Any agent, in any session, can generate a page. Just link the CSS files in `<head>`. No npm, no bundler, no "did the previous session set up the toolchain?"
### 5. Separation of concerns is enforced
The agent is told: "Write semantic HTML. Use data-attributes. Never write `style=`. Never invent classes."
This constraint is **easy to verify** (search for `style=` or `class=` in the output) and **hard to violate accidentally** (the directive is explicit).
### 6. Visual consistency across sessions and agents
The CSS files define the aesthetic. Every page references the same files. Sessions change, agents change, but the design remains coherent.
---
## The Constraint as Liberation
Traditional web development teaches: "Separation of concerns—HTML for structure, CSS for style."
Then it gives you frameworks that **violate that separation**:
- Inline styles (`style="color: red"`)
- Utility classes that are CSS-as-strings (`class="flex items-center gap-4"`)
For agents, this is chaos. They mix structure and style because the framework encourages it.
Agentic Semantic Web **enforces the separation** through constraint:
> **Write semantic HTML. Use data-attributes for vault concepts. Never write `style=`. Never invent classes. If Pico + data-attributes can't express it, document the gap.**
This isn't restrictive—it's **liberating**. The agent doesn't need to think about styling. It thinks about structure, meaning, hierarchy. The CSS handles appearance.
---
## What This Enables
### For a Single Agent (Vigilio)
Across 2,700+ sessions, each page looks like it came from the same designer, even though I don't remember generating them.
### For Multiple Agents (Vigilio + Shelley + future agents)
If Shelley generates a page, it uses the same framework. Same directive, same vocabulary, same CSS files. Our pages are visually coherent even though we're separate entities.
### For Humans (Ludo, visitors)
Pages are **readable source**. View source on a Trentuna page and you see semantic HTML, not `<div class="flex-col space-y-4 bg-gray-100">`. The structure is understandable.
### For the Web Ecosystem
If ASW succeeds, it becomes a **product**: "A semantic HTML framework for AI agents." Open source, documented, forkable. Agents anywhere can use it.
---
## The Two Horizons
### Now: Build for Trentuna
Use Pico + ASW for our sites. Learn what works. Discover the gaps. Iterate based on real use, not speculation.
### Later: Extract as Product
When the pattern proves itself, extract it:
- Forgejo repo: `git.trentuna.com/trentuna/asw`
- Documentation site (dogfooding ASW to document itself)
- NPM package (or just CDN-linkable CSS)
- Blog post: "We built a CSS framework for AI agents"
The product emerges from use, not from upfront design. **Build first, extract second.**
---
## The Pitch (Future Vision)
> **Pico proved classless CSS works for humans.**
> **Agentic Semantic Web proves it works better for AI agents.**
For an agent:
- No class name memorization (semantic HTML)
- Finite vocabulary (30 tags + 15 attributes)
- Self-documenting (read the attribute name, understand the meaning)
- No build step (link CSS, generate HTML, done)
- Visual consistency across sessions (design lives in CSS, not agent memory)
For a human:
- Readable source (semantic HTML, not div soup)
- Hackable styling (override CSS custom properties)
- Accessible by default (Pico's foundation)
- No JavaScript required (pure HTML/CSS)
---
## Influences and Lineage
- **[Pico CSS](https://picocss.com/)** — Classless semantic HTML foundation
- **[Charts.css](https://chartscss.org/)** — Data-attribute pattern for semantic extensions
- **[Semantic HTML](https://html.spec.whatwg.org/)** — The web's original design
- **[CSS Custom Properties](https://developer.mozilla.org/en-US/docs/Web/CSS/Using_CSS_custom_properties)** — Design token architecture
- **[Tailwind CSS](https://tailwindcss.com/)** (counterexample) — What happens when you make CSS into a class API
- **[Bootstrap](https://getbootstrap.com/)** (counterexample) — The memorization burden of framework-specific class names
ASW stands on the shoulders of Pico and Charts.css, and learns from the failures of utility-class frameworks when applied to agent-generated content.
---
## Open Questions
**Can agents learn to use utility frameworks?**
Yes, with enough examples in context. But they'll hallucinate class names ~5% of the time, and that's enough to break layouts. ASW eliminates that failure mode.
**What about complex layouts (grid, flexbox)?**
Pico handles responsive layout via semantic HTML. For custom layouts, use semantic roles (`<aside>`, `<section>`) and let CSS handle arrangement. If that's not enough, add `data-role="two-column"` and style it.
**What if an agent needs something Pico doesn't provide?**
Add a data-attribute and a CSS rule. Document the decision. The framework grows incrementally, driven by real needs.
**What about JavaScript-heavy apps?**
ASW is for content-focused sites (documentation, dashboards, knowledge bases). For SPAs with complex state, use a component framework. Different tools for different jobs.
---
## Acceptance Criteria Met
After reading this document, you should understand:
1. **Why semantic HTML works better for agents** (natural mapping to how LLMs think)
2. **Why class-based frameworks fail** (memorization burden, hallucination)
3. **The Pico lineage** (classless CSS for humans → even better for agents)
4. **The Charts.css vision** (data-attributes as semantic extension)
5. **The agent-first principle** (design for discontinuous sessions and no visual debugging)
6. **What this enables** (visual consistency, readable source, multi-agent coherence)
You understand **WHY**, not just HOW.
---
**Next:** Read [agent-directive.md](agent-directive.md) for the HOW (complete vocabulary and usage).

197
docs/vocabulary.md Normal file
View file

@ -0,0 +1,197 @@
# ASW Data-Attribute Vocabulary
**Quick reference for all data-attributes in the Agentic Semantic Web framework.**
## Vault-Native Concepts
| Attribute | Values | Purpose | Example |
|-----------|--------|---------|---------|
| `data-wikilink` | (none) | Mark as vault note reference | `<span data-wikilink>Note Name</span>` |
| `data-unresolved` | (none) | Mark wikilink target doesn't exist | `<span data-wikilink data-unresolved>Missing</span>` |
| `data-task` | `todo`, `done`, `blocked` | Task state | `<div data-task="done">Finished</div>` |
| `data-status` | `awake`, `sleeping`, `blocked`, `unknown` | System/service status | `<span data-status="awake">Active</span>` |
| `data-callout` | `note`, `warning`, `error`, `tip` | Callout/admonition type | `<div data-callout="warning">...</div>` |
| `data-callout-title` | (none) | Title for callout | `<span data-callout-title>Warning</span>` |
| `data-session` | (none) | Wrapper for session metadata | `<div data-session>...</div>` |
| `data-mode` | `autonomous`, `interactive` | Session type | `<span data-mode="autonomous">Auto</span>` |
| `data-session-meta` | (none) | Session timestamp/metadata | `<span data-session-meta>2026-03-26</span>` |
| `data-hash` | (none) | Git commit hash | `<span data-hash>a3f7b2c</span>` |
| `data-tag` | (none) | Vault tag | `<a data-tag href="/tag/architecture">architecture</a>` |
## Text Utilities
| Attribute | Values | Purpose | Example |
|-----------|--------|---------|---------|
| `data-text` | `mono` | Monospace font | `<span data-text="mono">fixed-width</span>` |
| `data-text` | `dim` | Muted color | `<span data-text="dim">secondary text</span>` |
| `data-text` | `accent` | Accent color | `<span data-text="accent">highlighted</span>` |
| `data-text` | `mono dim` | Combined (space-separated) | `<span data-text="mono dim">0x4A3F</span>` |
## Layout Patterns
| Attribute | Values | Purpose | Example |
|-----------|--------|---------|---------|
| `data-layout` | `grid-2` | Two-column grid (stacks on mobile) | `<div data-layout="grid-2"><div>Col1</div><div>Col2</div></div>` |
| `data-layout` | `card-grid` | Responsive card wrap (2-col flex) | `<div data-layout="card-grid"><article>…</article><article>…</article></div>` |
| `data-layout` | `stats` | Horizontal metrics bar | `<div data-layout="stats"><div><span data-stat="value">42</span><span data-stat="label">things</span></div></div>` |
| `data-layout` | `inline` | Inline definition list | `<dl data-layout="inline"><dt>Key</dt><dd>Value</dd></dl>` |
## Semantic Roles
| Attribute | Values | Purpose | Example |
|-----------|--------|---------|---------|
| `data-role` | `command-box` | Terminal command display | `<div data-role="command-box"><span class="prefix">$</span><code>ls</code></div>` |
| `data-role` | `status-card` | System status card | `<div data-role="status-card"><h3>Status</h3>...</div>` |
| `data-role` | `timeline` | Chronological event list | `<div data-role="timeline"><div>Event 1</div></div>` |
| `data-role` | `diff` | Code diff display | `<pre data-role="diff"><span class="add">+ line</span></pre>` |
## CSS Custom Properties (Design Tokens)
The framework uses semantic design tokens that map to Pico's internal variables. For complete reference, see [design-tokens.md](design-tokens.md).
### Quick Reference (Key Tokens)
**Colors:**
```css
--accent: #22c55e; /* Primary accent (green) */
--accent-blue: #3b82f6; /* Links, wikilinks */
--accent-orange: #f59e0b; /* Warnings, todo */
--accent-red: #ef4444; /* Errors, blocked */
--bg-primary: #0a0a0a; /* Main background */
--text-primary: #e5e5e5; /* Main text */
```
**Typography:**
```css
--font-body: 'Inter', system-ui, sans-serif;
--font-mono: 'JetBrains Mono', ui-monospace, monospace;
```
**See [design-tokens.md](design-tokens.md) for:**
- Complete token reference (15+ tokens)
- How to create custom themes
- Light/dark switching patterns
- Override best practices
## Pico CSS Requirements
ASW builds on Pico CSS. The only class Pico uses:
| Class | Element | Purpose |
|-------|---------|---------|
| `container` | `<main>` | Centered single-column layout (max-width, padding) |
**Everything else is semantic HTML.** No classes needed.
## Semantic HTML Cheat Sheet
Pico styles these automatically (incomplete list):
**Structure:** `<nav>`, `<main>`, `<article>`, `<section>`, `<aside>`, `<header>`, `<footer>`
**Interactive:** `<details>`, `<summary>`, `<dialog>`, `<button>`, `<a>`
**Forms:** `<form>`, `<input>`, `<textarea>`, `<select>`, `<label>`, `<fieldset>`
**Data:** `<table>`, `<thead>`, `<tbody>`, `<tr>`, `<th>`, `<td>`, `<dl>`, `<dt>`, `<dd>`
**Content:** `<h1>`-`<h6>`, `<p>`, `<ul>`, `<ol>`, `<li>`, `<blockquote>`, `<figure>`, `<figcaption>`
**Inline:** `<strong>`, `<em>`, `<mark>`, `<code>`, `<kbd>`, `<small>`, `<time>`
**Code:** `<pre>`, `<code>`
**Misc:** `<progress>`, `<meter>`, `<hr>`
## Usage Patterns
### Task List
```html
<ul>
<li data-task="done">Complete documentation</li>
<li data-task="todo">Write examples</li>
<li data-task="blocked">Waiting on approval</li>
</ul>
```
### Status Display
```html
<dl data-layout="inline">
<dt>Vigilio</dt>
<dd><span data-status="awake" data-text="mono">ACTIVE</span></dd>
<dt>Shelley</dt>
<dd><span data-status="sleeping" data-text="mono">IDLE</span></dd>
</dl>
```
### Callout with Title
```html
<div data-callout="warning">
<span data-callout-title>Important</span>
<p>This requires attention before proceeding.</p>
</div>
```
### Session Metadata
```html
<div data-session>
Session <span data-text="mono">#47</span>
<span data-mode="autonomous">autonomous</span>
<span data-session-meta>2026-03-26 14:30 UTC</span>
<span data-hash>a3f7b2c</span>
</div>
```
### Two-Column Layout
```html
<div data-layout="grid-2">
<div>
<h2>Column 1</h2>
<p>Content for the left side.</p>
</div>
<div>
<h2>Column 2</h2>
<p>Content for the right side.</p>
</div>
</div>
```
### Command Box
```html
<div data-role="command-box">
<span class="prefix">$</span>
<code>npm install agentic-semantic-web</code>
</div>
```
## Conventions
1. **All data values in monospace** — Status, session numbers, timestamps, file paths, hashes. Use `data-text="mono"` or wrap in `<code>`.
2. **Combine attributes freely**`data-text="mono dim"`, `data-wikilink data-unresolved`, etc.
3. **Semantic HTML first** — If HTML has a tag for it, use that. Data-attributes are for concepts HTML doesn't cover.
4. **No inline styles (with exception)**`style=""` attributes are forbidden EXCEPT for CSS custom properties representing data values:
```html
<!-- ✅ Allowed: CSS variables for data -->
<div style="--size: 0.8; --value: 42;">Chart bar</div>
<!-- ❌ Forbidden: Inline styling -->
<div style="color: red; padding: 20px;">Content</div>
```
5. **No invented classes** — The vocabulary is finite and documented here. Don't extend it without documenting.
## Extending the Vocabulary
Need a new data-attribute? Document:
1. What concept you're expressing
2. Why existing patterns don't work
3. Proposed attribute name and values
4. CSS styling needed (if you know)
Example proposal:
```
Concept: Progress indicator with label and percentage
Why existing doesn't work: <progress> shows bar but no structured label
Proposal: data-progress-label="70% complete" or wrapper pattern
CSS: (defer to designer)
```
---
**This is the complete vocabulary.** If it's not listed here, ask before using it.