#!/usr/bin/env bash # # development/_common.sh — shared helpers for the start-* dev launchers. # # Sourced by start-nvim.sh and start-vim.sh (not run directly). Owns the # pieces both launchers share so they stay in lockstep — most importantly # the sample-wiki fixture, which previously had to be edited in two # places. # # Exports: # REPO_ROOT / DEV_DIR / WIKI_DIR — common paths # log — prefixed status line # ensure_binary — build + symlink nuwiki-ls # write_sample_wiki DIR — lay down the feature-showcase wiki # reset_dirs DIR... — wipe + recreate owned state dirs # seed_wiki — (re)seed WIKI_DIR fresh each run; never # touches a user-supplied NUWIKI_DEV_WIKI; # respects NUWIKI_DEV_NO_SEED # Resolve paths relative to this file so it works regardless of which # launcher sources it. REPO_ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)" DEV_DIR="${XDG_CACHE_HOME:-$HOME/.cache}/nuwiki-dev" WIKI_DIR="${NUWIKI_DEV_WIKI:-$DEV_DIR/wiki}" log() { printf '\033[1;34m[nuwiki-dev]\033[0m %s\n' "$*"; } ensure_binary() { local bin="$REPO_ROOT/bin/nuwiki-ls" local built="$REPO_ROOT/target/release/nuwiki-ls" if [[ "${NUWIKI_DEV_SKIP_BUILD:-0}" == "1" ]]; then if [[ ! -x "$bin" ]]; then log "NUWIKI_DEV_SKIP_BUILD=1 but $bin is missing — building anyway" else log "NUWIKI_DEV_SKIP_BUILD=1 — using existing $bin" return fi fi log "building nuwiki-ls (release)…" cargo build --release -p nuwiki-ls --manifest-path "$REPO_ROOT/Cargo.toml" mkdir -p "$REPO_ROOT/bin" ln -sf "$built" "$bin" log "binary ready: $bin (built $(date -r "$built" '+%Y-%m-%d %H:%M:%S'))" } # write_sample_wiki DIR — lay down a fixture that exercises every vimwiki # feature nuwiki supports: one page per feature group plus a diary. # Heredocs use a quoted delimiter so `$math`, backticks, and backslashes # land verbatim. write_sample_wiki() { local root="$1" mkdir -p "$root" "$root/diary" cat > "$root/index.wiki" <<'EOF' = nuwiki sample wiki = %% Generated by the start-* dev launchers. A single fixture that exercises %% every vimwiki feature nuwiki supports — open the linked pages and run %% the plugin commands against them. One page per feature group: - [[Syntax]] — inline formatting, blocks, comments - [[Lists]] — bullets, ordering, checkbox states, nesting - [[Tables]] — alignment and spanning cells - [[Links]] — every wikilink and URL form - [[Notes]] — anchor targets for cross-page links - [[diary/diary]] — the diary index === Heading level 3 === ==== Heading level 4 ==== ===== Heading level 5 ===== ====== Heading level 6 ====== == Commands to try == - :NuwikiTOC - :NuwikiGenerateLinks - :NuwikiCheckLinks - :NuwikiMakeDiaryNote - :VimwikiColorize red — on a word in [[Syntax]] (or wc) :sample:smoke-test:sandbox: EOF cat > "$root/Syntax.wiki" <<'EOF' = Syntax showcase = Back to [[index]]. == Inline formatting == *bold*, _italic_, *_bold italic_*, ~~strikethrough~~, `inline code`, super^script^ and sub,,script,,, and inline math $e^{i\pi} + 1 = 0$. == Colour spans (:VimwikiColorize) == Put the cursor on a word and run `:VimwikiColorize red` (or press `wc` and type a colour); or visually select a phrase and press `wc`. Each wraps the target in an inline colour-span tag whose markup is concealed, so you see just the word painted in that colour (move the cursor onto it to reveal the raw markup). - colorize this important word - now select and colour this whole phrase - hex works too: paint deepskyblue on this token Already colorized: dodger blue. == Keywords == TODO STARTED FIXME XXX DONE FIXED STOPPED == Horizontal rule == ---- == Blockquote == > A quoted line. > A second quoted line. == Definition list == Term:: Definition of the term. Another:: Its definition. == Code block == {{{python def greet(name): return f"hello {name}" }}} == Math block == {{$ \sum_{i=1}^{n} i = \frac{n(n+1)}{2} }}$ == Comments == %% a single-line comment %%+ a multi-line comment block +%% == Transclusion == {{file:image.png}} {{image.png|alt text|width=120}} EOF cat > "$root/Lists.wiki" <<'EOF' = Lists = Back to [[index]]. == Unordered == - item with dash - second - nested under dash * item with star # item with hash == Ordered == 1. first 2. second 1. nested ordered 1) paren style a) alpha A) Alpha i) roman I) Roman == Checkbox states == - [ ] empty (0%) - [.] started (1-33%) - [o] in progress (34-66%) - [O] nearly done (67-99%) - [X] done (100%) - [-] rejected == Nested with checkboxes == - [ ] parent task - [X] done subtask - [ ] pending subtask - [ ] deep subtask EOF cat > "$root/Tables.wiki" <<'EOF' = Tables = Back to [[index]]. == Plain == | Name | Role | | Alice | Author | | Bob | Editor | == Aligned == | Left | Center | Right | |:-----|:------:|------:| | a | b | c | | d | e | f | == Spanning cells == | Header | Span | | cell | > | | rowspan | value | | \/ | value | EOF cat > "$root/Links.wiki" <<'EOF' = Links = Back to [[index]]. == Wikilinks == - [[Notes]] - [[Notes|described]] - [[Notes#Section one]] - [[Notes#Section one|anchored + described]] - [[/index]] - [[diary/]] - [[#Wikilinks]] == Diary and interwiki == - [[diary:2026-05-30]] - [[wiki1:index]] - [[wn.MyWiki:index]] == External and raw URLs == - [[https://example.com]] - [[https://example.com|Example]] - https://example.com - mailto:gffranco@gmail.com - file:///etc/hosts EOF cat > "$root/Notes.wiki" <<'EOF' = Notes = A page that other pages point at. Back to [[index]]. == Section one == Anchor target for cross-page links. == Section two == Another anchor target. EOF cat > "$root/diary/diary.wiki" <<'EOF' = Diary = Back to [[/index]]. - [[2026-05-30]] EOF cat > "$root/diary/2026-05-30.wiki" <<'EOF' = 2026-05-30 = A diary entry. Back to [[diary]]. - [X] set up sample wiki - [ ] review every feature page EOF } # reset_dirs DIR... — wipe and recreate each dir so a launch always starts # from clean editor state (swap/undo/viminfo, coc data, nvim XDG dirs). Only # ever called on dirs the launchers own under $DEV_DIR. reset_dirs() { local d for d in "$@"; do rm -rf "$d" mkdir -p "$d" done } # ensure_calendar_vim — clone calendar-vim into dev dir for testing ensure_calendar_vim() { local repo="$DEV_DIR/calendar-vim" if [[ -d "$repo/.git" ]]; then return fi if ! command -v git >/dev/null 2>&1; then log "git not found — skipping calendar-vim" return 1 fi log "cloning https://github.com/mattn/calendar-vim.git → $repo" git clone --depth 1 https://github.com/mattn/calendar-vim.git "$repo" >/dev/null 2>&1 } seed_wiki() { if [[ "${NUWIKI_DEV_NO_SEED:-0}" == "1" ]]; then log "NUWIKI_DEV_NO_SEED=1 — skipping wiki seed (using $WIKI_DIR as-is)" return fi # A user-pointed wiki (NUWIKI_DEV_WIKI) is never wiped — it might be a real # wiki. Seed the sample only when it has no index yet, so we don't clobber it. if [[ -n "${NUWIKI_DEV_WIKI:-}" ]]; then mkdir -p "$WIKI_DIR" "$WIKI_DIR/diary" if [[ -f "$WIKI_DIR/index.wiki" ]]; then log "using existing wiki at $WIKI_DIR (left untouched)" return fi write_sample_wiki "$WIKI_DIR" return fi # Managed scratch wiki under the dev cache: always start from a pristine # copy so stale edits from a previous run never leak into the next. log "reseeding scratch wiki (fresh copy): $WIKI_DIR" rm -rf "$WIKI_DIR" mkdir -p "$WIKI_DIR" "$WIKI_DIR/diary" write_sample_wiki "$WIKI_DIR" }