docs(16): add pattern map
This commit is contained in:
@@ -0,0 +1,278 @@
|
||||
# Phase 16: grzybyfunkcjonalne.pl on reusable blog views - Pattern Map
|
||||
|
||||
**Mapped:** 2026-10-09
|
||||
**Files analyzed:** 26 (grouped where they share an analog)
|
||||
**Analogs found:** 21 / 26
|
||||
|
||||
Paths are relative to `/media/nvme/dev/golem15/summercms.io/summercms/`. All analogs are git-tracked source (no `.msd` mirrors). D-20 (author endpoint) and D-21 (category content field) are pre-execution quick tasks in `sm-journal-plugin` and are **not** mapped here; only their consumption by the layer is.
|
||||
|
||||
## File Classification
|
||||
|
||||
| New/Modified File | Plan | Role | Data Flow | Closest Analog | Match |
|
||||
|---|---|---|---|---|---|
|
||||
| `vue-journal-layer/package.json` | 1 | config | build | `sm-summercmsio-app/vue-summercmsio-app/package.json` | exact (move nuxt/vue to devDeps) |
|
||||
| `vue-journal-layer/nuxt.config.ts` | 1 | config | build | `vue-summercmsio-app/nuxt.config.ts` | role-match (layer: absolute paths) |
|
||||
| `vue-journal-layer/modules/journal.ts` | 1 | module | build-time route registration | none in repo; RESEARCH Pattern 1 | no analog |
|
||||
| `vue-journal-layer/app/composables/useJournalApi.ts`, `app/utils/client.ts`, `types.ts`, `query.ts` | 1 | service/client | request-response | none (summercms.io has no data fetch); RESEARCH Pattern 2 | no analog |
|
||||
| `vue-journal-layer/app/utils/{pagination,htmlGate,routes}.ts` | 1 | utility | transform | `vue-summercmsio-app/app/utils/scrollSpy.ts` | role-match (pure TS, node --test) |
|
||||
| `vue-journal-layer/app/journal-pages/*.vue` (PostIndex, Post, Category, Tag, Author) | 1 | page | request-response (SSR) | `vue-summercmsio-app/app/pages/index.vue` | partial |
|
||||
| `vue-journal-layer/app/components/Journal/*.vue` | 1 | component | render | `vue-summercmsio-app/app/components/*` | role-match |
|
||||
| `vue-journal-layer/app/assets/css/journal-tokens.css`, `journal-base.css` | 1 | config (style) | — | `vue-summercmsio-app/app/assets/css/tokens.css`, `base.css` | exact |
|
||||
| `vue-journal-layer/i18n/locales/{pl,en}.json` | 1 | config (i18n) | — | `vue-summercmsio-app/i18n/locales/en.json` | exact |
|
||||
| `vue-journal-layer/server/api/__sitemap__/journal.ts` | 1 | server route | request-response | none; RESEARCH Pattern 5 | no analog |
|
||||
| `vue-journal-layer/README.md` | 1 | docs | — | `vue-summercmsio-app/README.md` (neutral names: `blog`/`acme`) | role-match |
|
||||
| `vue-grzybyfunkcjonalne-app/package.json` | 2 | config | build | `vue-summercmsio-app/package.json` | exact (+ git dep) |
|
||||
| `vue-grzybyfunkcjonalne-app/nuxt.config.ts` | 2 | config | build | `vue-summercmsio-app/nuxt.config.ts` | exact (SSR instead of generate) |
|
||||
| `vue-grzybyfunkcjonalne-app/app/pages/{index,kontakt,trwaja-prace}.vue`, `app/error.vue` | 2 | page | render | `vue-summercmsio-app/app/pages/index.vue` | exact |
|
||||
| `vue-grzybyfunkcjonalne-app/app/components/*` (Hero, About, Cta, Services, Faq, SiteHeader, SiteFooter, Journal overrides) | 2 | component | render | `vue-summercmsio-app/app/components/*` | exact |
|
||||
| `vue-grzybyfunkcjonalne-app/app/data/{menu.ts,faq.pl.json}` | 2 | config/data | — | `vue-summercmsio-app/app/data/terminal.json` | role-match |
|
||||
| `vue-grzybyfunkcjonalne-app/app/assets/css/tokens.css` | 2 | config (style) | — | `vue-summercmsio-app/app/assets/css/tokens.css` | exact |
|
||||
| `vue-grzybyfunkcjonalne-app/i18n/locales/pl.json` | 2 | config (i18n) | — | `vue-summercmsio-app/i18n/locales/en.json` | exact |
|
||||
| `sm-grzybyfunkcjonalne-app/.gitmodules` (add submodule) | 2/3 | config | — | `sm-summercmsio-app/.gitmodules` | exact |
|
||||
| `sm-grzybyfunkcjonalne-app/config/backend.yaml` | 3 | config | — | itself (currently `uri: /backend`) | exact |
|
||||
| app-local plugin `sm-grzybyfunkcjonalne-app/plugins/golem15/grzyby/plugin.go` (hosts the command) + `summer.yaml` entry | 3 | plugin | — | `sm-journal-plugin/plugin.go:60-65` (`Commands()`), `sm-summercmsio-app/plugins/golem15/summercms/plugin.go` | role-match |
|
||||
| `.../console/import_featured_images.go` (D-22) | 3 | command | file-I/O + CRUD | `sm-journal-plugin/console/import_posts.go` | exact |
|
||||
| `sm-grzybyfunkcjonalne-app/deploy/nginx/*.conf` | 3 | config | request routing | `sm-summercmsio-app/deploy/nginx/summercms.io.conf` | role-match (two upstreams) |
|
||||
| `sm-grzybyfunkcjonalne-app/deploy/supervisor/*.conf` (Go + Nuxt) | 3 | config | process | `sm-summercmsio-app/deploy/supervisor/summercms-io.conf` | exact (x2) |
|
||||
| `sm-grzybyfunkcjonalne-app/deploy/env.example` | 3 | config | — | `sm-summercmsio-app/deploy/env.example` | exact (+ `SUMMER_URL`, `NUXT_*`) |
|
||||
| `sm-grzybyfunkcjonalne-app/scripts/{build.sh,smoke.sh,check-deploy.sh,urls.txt,migrate.sh}` | 3/4 | script | batch | `sm-summercmsio-app/scripts/{build.sh,smoke.sh,check-deploy.sh}` | role-match |
|
||||
| Tests: layer/app `tests/*.test.ts`, Go `console/*_test.go` | 5 | test | — | `vue-summercmsio-app/tests/scrollSpy.test.ts`, `sm-grzybyfunkcjonalne-app/boot_test.go` | exact |
|
||||
|
||||
## Pattern Assignments
|
||||
|
||||
### `vue-journal-layer/package.json` and `vue-grzybyfunkcjonalne-app/package.json`
|
||||
|
||||
**Analog:** `sm-summercmsio-app/vue-summercmsio-app/package.json` (whole file)
|
||||
```json
|
||||
{
|
||||
"name": "vue-summercmsio-app",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"scripts": {
|
||||
"build": "nuxt build", "dev": "nuxt dev", "generate": "nuxt generate",
|
||||
"preview": "nuxt preview", "prepare": "nuxt prepare",
|
||||
"test": "node --test --test-reporter=tap tests/*.test.ts"
|
||||
},
|
||||
"engines": { "node": ">=22.18" },
|
||||
"dependencies": {
|
||||
"@nuxt/fonts": "0.14.0", "@nuxtjs/i18n": "10.4.0", "@nuxtjs/seo": "5.2.1",
|
||||
"nuxt": "4.4.8", "vue": "3.5.35"
|
||||
},
|
||||
"devDependencies": { "typescript": "5.9.3" }
|
||||
}
|
||||
```
|
||||
Adapt: layer keeps the three modules in `dependencies`, moves `nuxt`/`vue` to `devDependencies` (RESEARCH Installation). App adds `"vue-journal-layer": "git+https://git.golem15.com/golem15/vue-journal-layer.git#v0.1.0"` and does not re-list modules at other versions (Pitfall 4). Drop `generate` from the app (SSR, D-07). Copy `.nvmrc` (22.22.0), `pnpm-workspace.yaml`, `tsconfig.json` from the same directory.
|
||||
|
||||
### `nuxt.config.ts` (layer and app)
|
||||
|
||||
**Analog:** `vue-summercmsio-app/nuxt.config.ts` (lines 1-66)
|
||||
```ts
|
||||
export default defineNuxtConfig({
|
||||
compatibilityDate: '2025-07-15',
|
||||
devtools: { enabled: false },
|
||||
modules: ['@nuxt/fonts', '@nuxtjs/i18n', '@nuxtjs/seo'],
|
||||
css: ['~/assets/css/tokens.css', '~/assets/css/base.css'],
|
||||
fonts: { families: [ { name: 'Roboto', weights: [300,400,500,700], styles: ['normal'], subsets: ['latin','latin-ext'], global: true } ] },
|
||||
i18n: {
|
||||
strategy: 'prefix_except_default',
|
||||
defaultLocale: 'en',
|
||||
locales: [{ code: 'en', language: 'en-US', file: 'en.json', name: 'English' }],
|
||||
langDir: 'locales/',
|
||||
baseUrl: 'https://summercms.io',
|
||||
},
|
||||
site: { url: 'https://summercms.io', name: 'SummerCMS', description: '...', defaultLocale: 'en' },
|
||||
ogImage: { enabled: false },
|
||||
sitemap: { autoI18n: false },
|
||||
})
|
||||
```
|
||||
- **Layer:** keep `modules`, replace `~/` css paths with `fileURLToPath(new URL('./app/assets/css/journal-tokens.css', import.meta.url))` (anti-pattern: relative/`~` paths resolve to the consumer); add `resolve('./modules/journal')` to modules; locales pl+en; `sitemap: { sources: ['/api/__sitemap__/journal'] }`; declare `runtimeConfig.journal.apiBase` and `runtimeConfig.public.journal.apiBase` (`/_journal/api/v1`).
|
||||
- **App:** `extends: ['vue-journal-layer']`, `journal.routes` (RESEARCH Pattern 1 app excerpt: `category: '/:category'`, `author: '/autor/:author'`, `tag: false`), `defaultLocale: 'pl'` with pl only, `site.url` grzyby, `routeRules: { '/**': { swr: 300 } }`, `runtimeConfig.public.gaId` empty (D-23 `NUXT_PUBLIC_GA_ID`). Fonts: Open Sans/Jost/Poppins family list in the same shape. Remove the `nitro.prerender` / `/docs` link-checker blocks; add `linkChecker.excludeLinks` for `/gfadmin`, `/_journal/**`, `/storage/**`.
|
||||
- Comment style: short explanatory comments above each block, as the analog does.
|
||||
|
||||
### `vue-journal-layer/modules/journal.ts`, `app/composables/useJournalApi.ts`, `server/api/__sitemap__/journal.ts`
|
||||
|
||||
**No codebase analog.** Use RESEARCH.md Pattern 1 (`defineNuxtModule` + `extendPages`, route names `journal-<key>`, `path === false` skips), Pattern 2 (server `apiBase` + forwarded `x-forwarded-for`), Pattern 3 (category resolves against `GET /categories?include_empty=1`, 404 via `createError({ statusCode: 404, fatal: true })`, D-24; render D-21 category `content` above the list), Pattern 5 (sitemap source paging `per_page=30` until `meta.last_page`). Author page consumes the D-20 endpoint; plan 1 checkpoints if absent. Put the pure logic (query building, page parsing, route-path validation, html gate, sitemap loc building from `journal.routes`) in `app/utils/*.ts` so it is `node --test`-able like `scrollSpy.ts`.
|
||||
|
||||
### `app/utils/*.ts` (pure TS, both repos)
|
||||
|
||||
**Analog:** `vue-summercmsio-app/app/utils/scrollSpy.ts` paired with `tests/scrollSpy.test.ts`. Exported constants + pure functions, no Nuxt imports, so tests import with an explicit `.ts` extension:
|
||||
```ts
|
||||
import { test } from 'node:test'
|
||||
import assert from 'node:assert/strict'
|
||||
import { activeSection, SPY_SECTIONS, SPY_THRESHOLD } from '../app/utils/scrollSpy.ts'
|
||||
|
||||
test('no sections means no active link', () => {
|
||||
assert.equal(activeSection([]), '')
|
||||
})
|
||||
```
|
||||
|
||||
### CSS tokens (layer `journal-tokens.css`, app `tokens.css`)
|
||||
|
||||
**Analog:** `vue-summercmsio-app/app/assets/css/tokens.css` (lines 1-20): single `:root { ... }` block, grouped by family with a trailing comment per variable naming its use:
|
||||
```css
|
||||
/* Design tokens from the summercms.io handoff. Component styles use these. */
|
||||
:root {
|
||||
--navy-900: #18223a; /* terminal background */
|
||||
--yellow-500: #f5c55a; /* accent */
|
||||
--text: #e9edf3; /* body text */
|
||||
```
|
||||
Layer uses the `--journal-color-*`, `--journal-font-*`, `--journal-space-*`, `--journal-radius-*` prefix (D-03). App overrides on `:root:root` or `html` (RESEARCH Pattern 4), seeded with `#0D705D/#27AE60/#138C74/#1AAC8F/#444444`.
|
||||
|
||||
### Pages and components (both repos)
|
||||
|
||||
**Analog:** `vue-summercmsio-app/app/pages/index.vue` and `app/components/*` (SFCs consuming i18n keys from `i18n/locales/*.json`, tokens only, no hard-coded colors). Layer pages live in `app/journal-pages/` (not `app/pages/`, anti-pattern); layer components under `app/components/Journal/` so the app overrides by the same name. Links via `useLocalePath()` with route names.
|
||||
|
||||
### i18n locale files
|
||||
|
||||
**Analog:** `vue-summercmsio-app/i18n/locales/en.json`, plus the leaf-walk check in `tests/output.test.ts` (lines 34-45: `type Messages = { [key: string]: string | Messages }`, `loadMessages()`, `leaves(tree, prefix)`). Reuse that helper in plan 5 to assert pl/en key parity in the layer.
|
||||
|
||||
### `sm-grzybyfunkcjonalne-app/.gitmodules`
|
||||
|
||||
**Analog:** `sm-summercmsio-app/.gitmodules` lines 1-3:
|
||||
```
|
||||
[submodule "vue-summercmsio-app"]
|
||||
path = vue-summercmsio-app
|
||||
url = git@git.golem15.com:golem15/vue-summercmsio-app.git
|
||||
```
|
||||
Submodule rule: commit and push inside the submodule first, then bump the gitlink as a separate commit.
|
||||
|
||||
### `sm-grzybyfunkcjonalne-app/config/backend.yaml`
|
||||
|
||||
Current content:
|
||||
```yaml
|
||||
# Admin mount path. Override with SUMMER_BACKEND__URI.
|
||||
uri: /backend
|
||||
```
|
||||
Change to `uri: /gfadmin` (D-09). Also review `config/http.yaml` (trusted proxy `127.0.0.1/32` at lines 15-16) - keep as is.
|
||||
|
||||
### App-local plugin + `import_featured_images.go` (D-22)
|
||||
|
||||
**Command analog:** `sm-journal-plugin/console/import_posts.go`
|
||||
|
||||
Imports (lines 3-21) - stdlib first, then framework modules, then gorm:
|
||||
```go
|
||||
import (
|
||||
"context"
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"os"
|
||||
"path/filepath"
|
||||
|
||||
"git.golem15.com/golem15/summercms/modules/backpack"
|
||||
"git.golem15.com/golem15/summercms/modules/bonfire"
|
||||
"gorm.io/gorm"
|
||||
)
|
||||
```
|
||||
Command declaration (lines 38-63): a constructor returning `bonfire.Command` that delegates to a testable function taking `*gorm.DB`:
|
||||
```go
|
||||
func ImportPosts(app *backpack.App) bonfire.Command {
|
||||
return bonfire.Command{
|
||||
Name: "journal:import-posts",
|
||||
Description: "Import journal posts with translations from JSON files.",
|
||||
Flags: []bonfire.Flag{
|
||||
{Name: "path", Description: "Import directory (default: journal-export)"},
|
||||
{Name: "force", Description: "Update existing posts (default: skip existing)", Bare: true},
|
||||
{Name: "dry-run", Description: "Show what would be imported without making changes", Bare: true},
|
||||
},
|
||||
Run: func(ctx context.Context, in bonfire.Input, out bonfire.Output) error {
|
||||
path := flagOrDefault(in, "path", defaultExportPath)
|
||||
...
|
||||
stats, err := ImportFromDir(ctx, mustDB(app), path, force, dry, out, nil)
|
||||
...
|
||||
out.Info(fmt.Sprintf("Results: %d created, %d updated, %d skipped, %d failed", ...))
|
||||
return nil
|
||||
},
|
||||
}
|
||||
}
|
||||
```
|
||||
Core loop + error handling (lines 66-120): nil-DB guard, `os.Stat` dir check, per-item failures counted into a stats struct with `out.Error(...)` and `continue`, fatal DB errors returned; whole run in one transaction (`work := func(tx *gorm.DB) error`). Copy this shape for `grzyby:import-featured-images --map map.json --source <dir> [--dry-run]` with `Created/Skipped/Failed` stats; idempotency = skip when an `attach.File` row with the same `disk_name` + `attachment_id` + `field` exists. Helpers `flagOrDefault`, `flagOn`, `mustDB` are unexported in the journal console package - re-declare locally.
|
||||
|
||||
**Attachment API** (`summercms.go/modules/lagoon/attach`):
|
||||
- `attach.BlobKey(diskName)` = `PartitionDirectory(diskName) + diskName` (thumb.go:54-69) - the blob key under bucket `file://./storage/app/uploads/public` (host `config/storage.yaml`).
|
||||
- `attach.File` struct (file.go:26-45): set `DiskName, FileName, FileSize, ContentType, Field: "featured_images", AttachmentID: strconv(postID), AttachmentType: "Golem15\\Journal\\Models\\Post"`; `IsPublic` is `*bool` (nil = DEFAULT TRUE).
|
||||
- Look up post id by host `slug` (which is the pl slug after D-25).
|
||||
|
||||
**Plugin host analog:** `sm-journal-plugin/plugin.go:60-65`:
|
||||
```go
|
||||
func (p *Plugin) Commands() []bonfire.Command {
|
||||
return []bonfire.Command{
|
||||
console.ExportPosts(p.app),
|
||||
console.ImportPosts(p.app),
|
||||
}
|
||||
}
|
||||
```
|
||||
Plugin skeleton: `sm-summercmsio-app/plugins/golem15/summercms/plugin.go` lines 9-40 and 76-78 (`ID()`, `Requires()`, `Register`, `Boot`, `func init() { party.Register(&Plugin{}) }`). Here implement `pact.HasCommands` instead of `HasRoutes`; store `app` in `Register`. Register in `summer.yaml` `plugins:` list (`id: golem15.grzyby`, module path) and regenerate `plugins.gen.go`/`main.go` with `summer build` (main.go is generated - do not hand-edit; it already appends `pact.HasCommands` commands). Whether the plugin lives as an in-repo directory (no separate module) is a planner decision; `go.work` must include it.
|
||||
|
||||
### `deploy/supervisor/*.conf`
|
||||
|
||||
**Analog:** `sm-summercmsio-app/deploy/supervisor/summercms-io.conf` (whole file):
|
||||
```ini
|
||||
[program:summercms-io]
|
||||
command=/srv/summercms-io/bin/summercms-io serve --addr 127.0.0.1:8095
|
||||
directory=/srv/summercms-io
|
||||
user=summercms
|
||||
environment=SUMMER_ENV="production"
|
||||
autostart=true
|
||||
autorestart=true
|
||||
startsecs=3
|
||||
stopsignal=TERM
|
||||
stopwaitsecs=15
|
||||
redirect_stderr=true
|
||||
stdout_logfile=/var/log/supervisor/summercms-io.log
|
||||
stdout_logfile_maxbytes=10MB
|
||||
stdout_logfile_backups=5
|
||||
```
|
||||
Duplicate for `[program:grzyby-nuxt]` with `command=node .output/server/index.mjs`, `environment=NITRO_HOST="127.0.0.1",NITRO_PORT="...",NUXT_JOURNAL_API_BASE="http://127.0.0.1:<go>/_journal/api/v1"`. Keep the header comment style (path on server, why `directory=` matters).
|
||||
|
||||
### `deploy/nginx/*.conf`
|
||||
|
||||
**Analog:** `sm-summercmsio-app/deploy/nginx/summercms.io.conf` - copy the HTTP→HTTPS + ACME block, the ssl/HSTS/gzip lines, and the per-path `location ^~` style (analog uses `location ^~ /backend { return 404; }`). New: `location ^~ /gfadmin` and `^~ /_journal` → Go upstream, `= /rss.xml` → Go `/_journal/api/v1/rss`, `^~ /storage/app/uploads/public/` and `^~ /storage/app/media/` → `alias` disk with `nosniff`, `/` → Nuxt upstream; `proxy_set_header Host $host` and `X-Forwarded-For` (Pitfalls 5, 6). Staging `server_name`, not the apex (D-10).
|
||||
|
||||
### `deploy/env.example`
|
||||
|
||||
**Analog:** `sm-summercmsio-app/deploy/env.example` (whole file: header with owner/mode, one commented line per key, `SUMMER_DATABASE__DSN`, `SUMMER_APP__KEY`, `SUMMER_ADMIN__JWT__SECRET`, `SUMMER_GOLEM15__USER__JWT__SECRET`). Add `SUMMER_URL=https://<staging host>` and the Nuxt keys (`NUXT_JOURNAL_API_BASE`, `NUXT_PUBLIC_GA_ID`), either in this file or a second `nuxt.env.example`.
|
||||
|
||||
### `scripts/build.sh`, `scripts/smoke.sh`, `scripts/check-deploy.sh`
|
||||
|
||||
**Analog:** `sm-summercmsio-app/scripts/*`. Conventions to copy:
|
||||
- Header usage comment, `set -euo pipefail`, `ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"`, `die()`/`fail()` to stderr, tool presence loop (`for tool in pnpm go ...; do command -v ...`), submodule presence check (`[[ -f "$SITE/package.json" ]] || die "... run git submodule update --init"`), `SUMMERCMS_FRAMEWORK` override, `release|dev` mode (build.sh lines 1-50).
|
||||
- smoke.sh (lines 1-60): postgres:15 via `docker run -d --rm -p 127.0.0.1::5432`, `pg_isready` loop, `trap cleanup EXIT` killing PID and container, env-overridable port. Extend: start Nuxt too, run migrate → set pl default (D-25 SQL `UPDATE golem15_translate_locales SET is_default = (code = 'pl')`) → import, then curl every line of `scripts/urls.txt` (71 sitemap URLs + static routes) for expected status.
|
||||
- build.sh adapts `nuxt generate` + embed to `pnpm build` producing `.output/` shipped next to the binary.
|
||||
|
||||
### Tests (plan 5)
|
||||
|
||||
- Layer/app TS: `node --test` per `tests/scrollSpy.test.ts` pattern above.
|
||||
- Go: plain `func TestX(t *testing.T)` per `sm-grzybyfunkcjonalne-app/boot_test.go` (lines 1-30: `compass.Load("config")`, `cfg.Set("admin.jwt.secret", ...)`, `backpack.New(cfg)`, `party.Activate(app, PluginIDs)`). Extend boot test to assert `/gfadmin` mount and the new command is in the catalog. Featured-image command tests use a temp source dir and an in-memory/`mem://` bucket (comment in `config/storage.yaml`: "mem:// in unit tests") and assert idempotency on second run.
|
||||
|
||||
## Shared Patterns
|
||||
|
||||
### Pinned toolchain
|
||||
**Source:** `vue-summercmsio-app/package.json`, `.nvmrc`. **Apply to:** both Nuxt repos. Exact versions, no carets.
|
||||
|
||||
### node --test with `.ts` imports
|
||||
**Source:** `vue-summercmsio-app/tests/*.test.ts`. **Apply to:** all TS unit tests; logic lives in `app/utils/*.ts` with no Nuxt auto-imports.
|
||||
|
||||
### Bonfire command + testable core
|
||||
**Source:** `sm-journal-plugin/console/import_posts.go:38-120`. **Apply to:** any app-local Go command.
|
||||
|
||||
### Deploy file headers
|
||||
**Source:** `sm-summercmsio-app/deploy/*`. **Apply to:** all deploy files: first comment names the server path and the reason for non-obvious settings; secrets never committed.
|
||||
|
||||
### Neutral README
|
||||
**Apply to:** `vue-journal-layer/README.md` - never name grzybyfunkcjonalne; use `blog`/`acme`.
|
||||
|
||||
## No Analog Found
|
||||
|
||||
| File | Role | Data Flow | Reason |
|
||||
|---|---|---|---|
|
||||
| `vue-journal-layer/modules/journal.ts` | Nuxt module | build-time | No Nuxt module or layer exists in the workspace; use RESEARCH Pattern 1 |
|
||||
| `useJournalApi.ts` / `client.ts` | client | request-response | summercms.io app is static and fetches nothing; RESEARCH Pattern 2 |
|
||||
| `server/api/__sitemap__/journal.ts` | server route | request-response | No Nitro server routes exist; RESEARCH Pattern 5 |
|
||||
| `app/utils/htmlGate.ts` | utility | transform | Port of Go `FormatHTML` gate regexes from `sm-journal-plugin/classes`; no TS precedent |
|
||||
| `scripts/migrate.sh` / runbook (D-25 order) | script | batch | No migration runbook script precedent; build from smoke.sh conventions |
|
||||
|
||||
## Metadata
|
||||
|
||||
**Analog search scope:** `sm-summercmsio-app/` (vue app, deploy, scripts, site plugin), `sm-grzybyfunkcjonalne-app/`, `sm-journal-plugin/console` and `plugin.go`, `summercms.go/modules/lagoon/attach`
|
||||
**Files scanned:** ~25
|
||||
**Pattern extraction date:** 2026-10-09
|
||||
Reference in New Issue
Block a user