andy-note-nuxt 0.2.0 → 0.2.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +49 -31
- package/app/app.config.ts +5 -6
- package/app/types/app-config.d.ts +0 -1
- package/content/index.md +1 -1
- package/content.config.ts +36 -0
- package/nuxt.config.ts +3 -3
- package/package.json +3 -1
package/README.md
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# andy-note-nuxt
|
|
2
2
|
|
|
3
|
-
Brutalist-terminal **Nuxt 4 + Nuxt Content v3 theme** packaged as a [Nuxt Layer](https://nuxt.com/docs/getting-started/layers). Stacked-column navigation (click a note → new column pushes from the right), warm-dark palette with
|
|
3
|
+
Brutalist-terminal **Nuxt 4 + Nuxt Content v3 theme** packaged as a [Nuxt Layer](https://nuxt.com/docs/getting-started/layers). Stacked-column navigation (click a note → new column pushes from the right), warm-dark palette with coral accent + flat 4px stamp shadows. Designed for personal notes, guides, and second-brain knowledge bases.
|
|
4
4
|
|
|
5
5
|
## Quick start — use as a layer
|
|
6
6
|
|
|
@@ -55,19 +55,53 @@ Edit `app/app.config.ts` for branding/menu, `nuxt.config.ts` for `<title>`, and
|
|
|
55
55
|
|
|
56
56
|
| Path | Purpose |
|
|
57
57
|
|---|---|
|
|
58
|
+
| `app/app.vue` | Root entry — `<NuxtLayout><NuxtPage /></NuxtLayout>` |
|
|
59
|
+
| `app/app.config.ts` | `site.*` config (title, description, themeColor, logo) |
|
|
60
|
+
| `app/types/app-config.d.ts` | TypeScript augmentation for `useAppConfig()` |
|
|
61
|
+
| `app/layouts/default.vue` | Full-height shell + `<Toaster>` host |
|
|
62
|
+
| `app/pages/[...slug].vue` | Single catch-all route — delegates to `<StackedColumns>` |
|
|
58
63
|
| `app/components/StackedColumns.vue` | Stacked-column shell — drives the whole UX |
|
|
59
|
-
| `app/components/
|
|
60
|
-
| `app/components/
|
|
61
|
-
| `app/
|
|
64
|
+
| `app/components/StackedColumn.vue` | Single column wrapper (click → push, scroll-to-focus) |
|
|
65
|
+
| `app/components/ContentView.vue` | Per-column renderer (auto-switches listing vs article view) |
|
|
66
|
+
| `app/components/LocalStorageChecklist.vue` | MDC component — persistent checklist embeddable in any markdown |
|
|
67
|
+
| `app/composables/useStack.ts` | Stack state machine (push/pop columns, URL sync, scroll geometry) |
|
|
62
68
|
| `app/assets/css/main.css` | Brutalist terminal theme — Tailwind v3 base + custom prose layers |
|
|
69
|
+
| `nuxt.config.ts` | Module wiring (`@nuxt/content`, `@nuxtjs/tailwindcss`, `vue-sonner/nuxt`, `vite-plugin-ai-annotator`) |
|
|
63
70
|
| `tailwind.config.js` | Color palette + stamp shadow tokens |
|
|
71
|
+
| `content.config.ts` | Minimal generic schema (7 fields — see "Schema" below) |
|
|
64
72
|
| `content/index.md` | Default landing page |
|
|
65
|
-
| `content/license.md` | Default license page
|
|
73
|
+
| `content/license.md` | Default license page |
|
|
74
|
+
| `content/quick-start.md`, `content/guides/`, `content/reference/` | Theme's own docs — override or delete in your child |
|
|
66
75
|
|
|
67
|
-
|
|
76
|
+
## Override anything
|
|
77
|
+
|
|
78
|
+
Nuxt Layers deep-merge child over parent. Override semantics:
|
|
79
|
+
|
|
80
|
+
- **Components / pages / layouts / composables** → create a file with the same path in your project (e.g. `app/components/ContentView.vue`) and it replaces the layer's.
|
|
81
|
+
- **`nuxt.config.ts`** → deep-merged. Your `app.head` keys override the layer's.
|
|
82
|
+
- **`app/app.config.ts`** → deep-merged. Override `site.*` (or add your own fields by re-declaring the `AppConfig` interface).
|
|
83
|
+
- **`tailwind.config.js`** → merged by `@nuxtjs/tailwindcss` across layers. Ship a `tailwind.config.js` in your project with the same shape (`theme.extend.colors`, `theme.extend.boxShadow`, etc.) and it overrides the layer's tokens. The module discovers all layer configs automatically.
|
|
84
|
+
- **`content.config.ts`** → fully replaced by the consumer's file (Nuxt Content reads only one). The layer ships a minimal schema so the SQLite cache has the columns its renderer queries (`document_type`, `updated`, `created`). Your override must include those columns or extend them.
|
|
85
|
+
- **Content** → child `content/<path>.md` overrides parent's same-path file (e.g. `content/license.md` in your project replaces the layer's default license page).
|
|
86
|
+
|
|
87
|
+
## Schema
|
|
88
|
+
|
|
89
|
+
The layer ships a minimal, generic `content.config.ts` covering only the fields its renderer actually reads:
|
|
90
|
+
|
|
91
|
+
| Field | Type | Used by |
|
|
92
|
+
|---|---|---|
|
|
93
|
+
| `title` | `string` | Column header, listing item, `<title>` |
|
|
94
|
+
| `description` | `string` | `<meta>`, OG tags, section listings |
|
|
95
|
+
| `document_type` | `string` | `"convention"` hides the file from listings |
|
|
96
|
+
| `tags` | `string[]` | Tag pills under H1 |
|
|
97
|
+
| `created` | `string` (ISO date) | Listing sort, recency badge |
|
|
98
|
+
| `updated` | `string` (ISO date) | Listing sort (preferred over `created`) |
|
|
99
|
+
| `rawbody` | `string` | Auto-populated — backs "Copy as Markdown" with byte-faithful source |
|
|
100
|
+
|
|
101
|
+
Every field is `.optional()` — you can write a `.md` with no frontmatter at all. To add domain-specific fields (`priority`, `owner`, `due_date`, anything project-specific), **override `content.config.ts` in your child project**:
|
|
68
102
|
|
|
69
103
|
```ts
|
|
70
|
-
// content.config.ts in YOUR project
|
|
104
|
+
// content.config.ts in YOUR project — replaces the layer's schema entirely
|
|
71
105
|
import { defineCollection, defineContentConfig, z } from '@nuxt/content'
|
|
72
106
|
|
|
73
107
|
export default defineContentConfig({
|
|
@@ -76,40 +110,24 @@ export default defineContentConfig({
|
|
|
76
110
|
type: 'page',
|
|
77
111
|
source: '**/*.md',
|
|
78
112
|
schema: z.object({
|
|
113
|
+
// Keep these — the renderer queries them
|
|
114
|
+
title: z.string().optional(),
|
|
79
115
|
description: z.string().optional(),
|
|
116
|
+
document_type: z.string().optional(),
|
|
80
117
|
tags: z.array(z.string()).optional(),
|
|
81
118
|
created: z.string().optional(),
|
|
82
119
|
updated: z.string().optional(),
|
|
83
|
-
|
|
120
|
+
rawbody: z.string().optional(),
|
|
121
|
+
// Add your own
|
|
122
|
+
priority: z.enum(['low', 'medium', 'high']).optional(),
|
|
123
|
+
owner: z.string().optional(),
|
|
84
124
|
}),
|
|
85
125
|
}),
|
|
86
126
|
},
|
|
87
127
|
})
|
|
88
128
|
```
|
|
89
129
|
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
Nuxt Layers deep-merge child over parent. Override semantics:
|
|
93
|
-
|
|
94
|
-
- **Components / pages / layouts / composables** → create a file with the same path in your project (e.g. `app/components/ContentView.vue`) and it replaces the layer's.
|
|
95
|
-
- **`nuxt.config.ts`** → deep-merged. Your `app.head` keys override the layer's.
|
|
96
|
-
- **`app/app.config.ts`** → deep-merged. Override `site.*` and `menu[]`.
|
|
97
|
-
- **`tailwind.config.js`** → NOT auto-merged by Nuxt. If you need a different palette, copy the file into your project; Tailwind picks up your project's config.
|
|
98
|
-
- **Content** → child `content/<path>.md` overrides parent's same-path file (e.g. `content/license.md` in your project replaces the layer's default license page).
|
|
99
|
-
|
|
100
|
-
## Schema
|
|
101
|
-
|
|
102
|
-
`content.config.ts` ships a permissive schema — every field is optional. Common fields available out of the box:
|
|
103
|
-
|
|
104
|
-
- Universal: `title`, `description`, `tags[]`, `status`, `created`, `updated`, `author`, `weight`
|
|
105
|
-
- Game / domain tagging: `game`, `league`, `patch` (renders as badges in headers)
|
|
106
|
-
- Build / recipe: `class`, `ascendancy`, `budget_tier`, `build_tags{}`, `ratings{}`, `pob_link`
|
|
107
|
-
- Economy: `strategy_tier`, `profit_per_hour`, `investment_tier`
|
|
108
|
-
- Skill / technique: `gem_color`, `skill_type`, `level_requirement`, `skill_tags[]`
|
|
109
|
-
- Instance / character: `level`, `progress_stage`
|
|
110
|
-
- Item / class / league: `rarity`, `item_class`, `class_type`, `complexity`, `league_type`
|
|
111
|
-
|
|
112
|
-
Unused fields cost nothing (null in cache). To replace the schema entirely, override `content.config.ts` in your child project.
|
|
130
|
+
Unused fields cost nothing (null in cache).
|
|
113
131
|
|
|
114
132
|
## Conventions baked in
|
|
115
133
|
|
package/app/app.config.ts
CHANGED
|
@@ -1,6 +1,11 @@
|
|
|
1
1
|
// Site-wide config consumed by components via `useAppConfig()`.
|
|
2
2
|
// Override every field in your child project by creating your own `app/app.config.ts`
|
|
3
3
|
// — Nuxt deep-merges child over parent layer.
|
|
4
|
+
//
|
|
5
|
+
// Note: this layer's UX is a single stacked-column shell — there is no fixed
|
|
6
|
+
// nav header rendering a menu. If your child project wants top-level nav,
|
|
7
|
+
// override `StackedColumns.vue` (or add a layout wrapper) and read your own
|
|
8
|
+
// menu structure from this config.
|
|
4
9
|
|
|
5
10
|
export default defineAppConfig({
|
|
6
11
|
site: {
|
|
@@ -11,10 +16,4 @@ export default defineAppConfig({
|
|
|
11
16
|
themeColor: '#ff7b6b',
|
|
12
17
|
logo: '/logo.png',
|
|
13
18
|
},
|
|
14
|
-
// Top-level navigation. Empty by default — child projects populate with
|
|
15
|
-
// their own categories. Each entry maps to a `content/<slug>/` folder
|
|
16
|
-
// (or any static route under `pages/`).
|
|
17
|
-
menu: [
|
|
18
|
-
{ name: 'License', url: '/license', weight: 99 },
|
|
19
|
-
],
|
|
20
19
|
})
|
package/content/index.md
CHANGED
|
@@ -19,7 +19,7 @@ updated: 2026-05-11
|
|
|
19
19
|
|
|
20
20
|
- **Menu & branding**: sửa `app/app.config.ts` để đổi `site.title`, `site.description`, và mảng `menu`.
|
|
21
21
|
- **Title trang web**: sửa `app.head.title` trong `nuxt.config.ts`.
|
|
22
|
-
- **Màu sắc**: palette terminal nằm trong `tailwind.config.js`. Token chính: `terminal.accent` (#
|
|
22
|
+
- **Màu sắc**: palette terminal nằm trong `tailwind.config.js`. Token chính: `terminal.accent` (#ff7b6b — coral), `terminal.bg` (#2a2a28 — warm dark).
|
|
23
23
|
- **Component**: mọi file trong `app/components/` đều override được bằng cách tạo file cùng tên ở child project.
|
|
24
24
|
|
|
25
25
|
Xem [License](/license) để biết điều khoản sử dụng.
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
// Default content schema shipped by the layer.
|
|
2
|
+
//
|
|
3
|
+
// Why this file exists in the LAYER even though CLAUDE.md says consumers own
|
|
4
|
+
// `content.config.ts`: the layer's `ContentView` component runs a children
|
|
5
|
+
// query that selects `document_type`, `updated`, and `created`. Without those
|
|
6
|
+
// columns in the SQLite schema, every page query would fail with
|
|
7
|
+
// `no such column`. So the layer ships a minimal generic schema covering only
|
|
8
|
+
// the fields its renderer actually reads. Consumers are still free — and
|
|
9
|
+
// encouraged — to override this file by shipping their own `content.config.ts`
|
|
10
|
+
// at their project root; Nuxt Layers gives the consumer's file priority and
|
|
11
|
+
// replaces this schema entirely.
|
|
12
|
+
//
|
|
13
|
+
// Keep the fields here generic. Anything domain-specific belongs in a
|
|
14
|
+
// consumer override, not in the layer.
|
|
15
|
+
import { defineCollection, defineContentConfig, z } from '@nuxt/content'
|
|
16
|
+
|
|
17
|
+
export default defineContentConfig({
|
|
18
|
+
collections: {
|
|
19
|
+
content: defineCollection({
|
|
20
|
+
type: 'page',
|
|
21
|
+
source: '**/*.md',
|
|
22
|
+
schema: z.object({
|
|
23
|
+
title: z.string().optional(),
|
|
24
|
+
description: z.string().optional(),
|
|
25
|
+
document_type: z.string().optional(),
|
|
26
|
+
tags: z.array(z.string()).optional(),
|
|
27
|
+
created: z.string().optional(),
|
|
28
|
+
updated: z.string().optional(),
|
|
29
|
+
// Opt into rawbody so the copy-as-markdown button gets byte-faithful
|
|
30
|
+
// source instead of stringified minimark. See
|
|
31
|
+
// https://content.nuxt.com/docs/integrations/llms.
|
|
32
|
+
rawbody: z.string().optional(),
|
|
33
|
+
}),
|
|
34
|
+
}),
|
|
35
|
+
},
|
|
36
|
+
})
|
package/nuxt.config.ts
CHANGED
|
@@ -2,8 +2,8 @@
|
|
|
2
2
|
//
|
|
3
3
|
// Base Nuxt config for `andy-note-nuxt` theme. Consumers extend this layer
|
|
4
4
|
// via `extends: ['github:nguyenvanduocit/andy-note-nuxt']` (or local path /
|
|
5
|
-
// npm package) and override `app.head
|
|
6
|
-
//
|
|
5
|
+
// npm package) and override `app.head` and `appConfig.site` in their child
|
|
6
|
+
// project. All values here are sensible defaults.
|
|
7
7
|
|
|
8
8
|
import { createResolver } from '@nuxt/kit'
|
|
9
9
|
|
|
@@ -66,7 +66,7 @@ export default defineNuxtConfig({
|
|
|
66
66
|
title: 'Andy Notes — Stacked-Column Knowledge Base',
|
|
67
67
|
meta: [
|
|
68
68
|
{ name: 'description', content: 'A brutalist-terminal Nuxt Content theme for personal notes, guides, and second-brain knowledge bases.' },
|
|
69
|
-
{ name: 'theme-color', content: '#
|
|
69
|
+
{ name: 'theme-color', content: '#ff7b6b' },
|
|
70
70
|
],
|
|
71
71
|
link: [
|
|
72
72
|
{ rel: 'icon', type: 'image/png', href: '/images/favicon.png' },
|
package/package.json
CHANGED
|
@@ -1,8 +1,9 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "andy-note-nuxt",
|
|
3
|
-
"version": "0.2.
|
|
3
|
+
"version": "0.2.2",
|
|
4
4
|
"description": "Brutalist-terminal Nuxt Content theme for personal notes, guides, and second-brain knowledge bases. Use as a Nuxt layer.",
|
|
5
5
|
"type": "module",
|
|
6
|
+
"main": "./nuxt.config.ts",
|
|
6
7
|
"license": "MIT",
|
|
7
8
|
"repository": {
|
|
8
9
|
"type": "git",
|
|
@@ -23,6 +24,7 @@
|
|
|
23
24
|
"public",
|
|
24
25
|
"content/index.md",
|
|
25
26
|
"content/license.md",
|
|
27
|
+
"content.config.ts",
|
|
26
28
|
"nuxt.config.ts",
|
|
27
29
|
"tailwind.config.js",
|
|
28
30
|
"tsconfig.json"
|