mirror of
https://github.com/microsoft/BCQuality.git
synced 2026-10-05 14:46:55 +01:00
v19: git-baseret konsumtion - forberedelse til privat repo
Beslutning: BCQuality skal vaere privat. En fork af et offentligt repo kan ikke goeres privat, saa flyttet sker via detach/nyoprettelse - men FOERST omlaegges al konsumtion fra tokenfri raw-URLs til git-baseret adgang, shippet mens kanalen stadig er offentlig, saa flaaden aldrig oplever et hul. GCM er token-haandteringen: udviklerne er allerede autentificeret. Kernen er KANAL-KLONEN: %USERPROFILE%\.claude\BCQuality, pinned til stable. Alt kopieres derfra (filsystem-kopi = raa bytes; ingen CDN-cache, ingen API-limits). - sync-bcquality-knowledge.ps1 v2: git-baseret (klon/fetch/checkout stable, mirror bygges lokalt, skriver selv versionsmarkoeren) - Install-CurabisMachine.ps1 v2: onboarding = git clone + script fra klonen; foerste GCM-login ER autentificeringen - curabis-standard.agent.md v19: SRC/BASE-tokens peger paa klonen; fetch betyder copy; Mode B Step 0 freshener klonen; ny Mode B- sektion opdaterer maskin-CLAUDE.md ved konsumtionsmodel-skift (gated, Identity bevares); CLAUDE.md-templatens self-heals er git-baserede - machine/CLAUDE.md v2: auto-update gater paa git fetch/rev-parse i stedet for GitHub API; setup laeses fra klonen - Ishikawa + al-triage + Francis: fallbacks peger paa mirror/klon; al-triages hardcodede URL-liste fjernet (samme sygdom som Ishikawa havde). Aerlig konsekvens: Copilot mister live custom-fallback - CONSUMPTION.md: Access model-sektion + to-linjers onboarding - Invoke-CurabisEvidence: RawBase markeret legacy/doed Nul raw.githubusercontent-referencer tilbage i forbrugerkritiske filer. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
parent
a95cf7f43f
commit
3ce08fe91e
9 changed files with 205 additions and 139 deletions
|
|
@ -38,22 +38,31 @@ future CI/PR-review integration:
|
|||
currently consumed by nothing. Keep it — but do not mistake it for active
|
||||
configuration of the session model.
|
||||
|
||||
## Access model: PRIVATE repo, git-based consumption
|
||||
|
||||
BCQuality is a **private** repository. All consumption is git-based through
|
||||
the **channel clone** at `%USERPROFILE%\.claude\BCQuality`, pinned to the
|
||||
`stable` branch. Authentication is Git Credential Manager — the developer's
|
||||
existing GitHub login; the first git contact opens a browser login, and that
|
||||
is the entire token story. `raw.githubusercontent.com` and unauthenticated
|
||||
GitHub-API calls are dead and must not appear in any consumer.
|
||||
|
||||
## Machine onboarding (new developer)
|
||||
|
||||
A fresh developer machine is made CURABIS-ready with ONE command
|
||||
(idempotent — safe to re-run):
|
||||
Two lines (idempotent — safe to re-run; the clone prompts the GCM login):
|
||||
|
||||
powershell -ExecutionPolicy Bypass -Command "Invoke-WebRequest -UseBasicParsing https://raw.githubusercontent.com/Curabis/BCQuality/stable/custom/setup/machine/Install-CurabisMachine.ps1 -OutFile $env:TEMP\icm.ps1; & $env:TEMP\icm.ps1"
|
||||
git clone --branch stable --single-branch https://github.com/Curabis/BCQuality.git "$env:USERPROFILE\.claude\BCQuality"
|
||||
powershell -ExecutionPolicy Bypass -File "$env:USERPROFILE\.claude\BCQuality\custom\setup\machine\Install-CurabisMachine.ps1"
|
||||
|
||||
It installs the global CLAUDE.md (identity substituted from git config),
|
||||
bc-mcp-bridge.js, the bc-mcp config template (the developer inserts their
|
||||
personal client secret), the knowledge sync script, and syncs the machine
|
||||
mirror. Per repo afterwards: "Opdater CURABIS Standard fra BCQuality" — it
|
||||
deploys `.vscode/find-altool.ps1` (a CURABIS template; no VS Code command
|
||||
generates it) and the AL MCP wiring itself. The AL Language extension from
|
||||
the Marketplace is the only per-machine prerequisite for AL MCP.
|
||||
mirror from the clone. Per repo afterwards: "Opdater CURABIS Standard fra
|
||||
BCQuality" — it deploys `.vscode/find-altool.ps1` and the AL MCP wiring
|
||||
itself. The AL Language extension from the Marketplace is the only
|
||||
per-machine prerequisite for AL MCP.
|
||||
|
||||
**Auto-trigger:** the command above rarely needs to be run by hand. Every
|
||||
**Auto-trigger:** the lines above rarely need to be run by hand. Every
|
||||
project CLAUDE.md (setup v15+) carries a machine self-heal: any Claude Code
|
||||
session in any configured CURABIS repo detects an un-onboarded machine
|
||||
(missing `~/.claude/CLAUDE.md` or bridge) and runs the onboarding itself —
|
||||
|
|
|
|||
|
|
@ -76,10 +76,9 @@ reviews what happened. He asks one question about every significant event:
|
|||
|
||||
> "Er der en BCQuality-regel der ville have fanget dette? Dækkede den fuldt ud?"
|
||||
|
||||
He compares against the full BCQuality knowledge base:
|
||||
```
|
||||
BASE = https://raw.githubusercontent.com/Curabis/BCQuality/stable/custom/knowledge
|
||||
```
|
||||
He compares against the full BCQuality knowledge base — the machine-local
|
||||
mirror at `%USERPROFILE%\.claude\bcquality-knowledge\custom\` (fallback: the
|
||||
channel clone `%USERPROFILE%\.claude\BCQuality\custom\knowledge\`).
|
||||
Domains: `architecture/`, `testing/`, `mcp/`
|
||||
|
||||
## The Two Proposal Types
|
||||
|
|
|
|||
|
|
@ -28,8 +28,10 @@ param(
|
|||
# Lokal BCQuality-klon. Default: proev ..\bcquality og .\.bcquality.
|
||||
[string]$BCQualityHome,
|
||||
|
||||
# Bruges naar der ikke er en lokal klon: knowledge-filer HTTP-tjekkes herfra.
|
||||
[string]$RawBase = 'https://raw.githubusercontent.com/Curabis/BCQuality/stable',
|
||||
# LEGACY: repoet er privat - raw-URLs virker ikke laengere. Brug altid en
|
||||
# lokal klon; kanal-klonen findes paa alle onboardede maskiner:
|
||||
# -BCQualityHome "$env:USERPROFILE\.claude\BCQuality"
|
||||
[string]$RawBase = '',
|
||||
|
||||
[switch]$Quiet
|
||||
)
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
---
|
||||
kind: action-skill
|
||||
id: curabis-standard-setup
|
||||
version: 18
|
||||
version: 19
|
||||
title: CURABIS Standard — Project Setup
|
||||
description: >
|
||||
Configures a new or existing repository to the CURABIS Standard development
|
||||
|
|
@ -34,14 +34,33 @@ This agent runs when the developer says any of:
|
|||
|
||||
Detect which mode based on the trigger phrase and proceed accordingly.
|
||||
|
||||
## Source URLs (BCQuality — always fetch fresh)
|
||||
## Source: the channel clone (BCQuality is PRIVATE — no raw URLs)
|
||||
|
||||
All artifacts come from the machine's **channel clone** — a git clone of
|
||||
`Curabis/BCQuality` pinned to the `stable` branch. Authentication is Git
|
||||
Credential Manager (the developer's existing GitHub login); there are NO
|
||||
tokenless raw.githubusercontent fetches anywhere — the repo is private.
|
||||
|
||||
```
|
||||
BASE = https://raw.githubusercontent.com/Curabis/BCQuality/stable/custom/setup
|
||||
AGENTS_BASE = https://raw.githubusercontent.com/Curabis/BCQuality/stable/custom/agents
|
||||
SRC = %USERPROFILE%\.claude\BCQuality (kanal-klonen, stable)
|
||||
BASE = {SRC}\custom\setup
|
||||
AGENTS_BASE = {SRC}\custom\agents
|
||||
```
|
||||
|
||||
| Artefakt | URL |
|
||||
**Before ANY Mode A/B work, ensure the channel clone is fresh:**
|
||||
|
||||
git -C "$env:USERPROFILE\.claude\BCQuality" fetch origin stable --quiet
|
||||
git -C "$env:USERPROFILE\.claude\BCQuality" checkout -B stable origin/stable --quiet
|
||||
|
||||
If the clone is missing entirely:
|
||||
|
||||
git clone --branch stable --single-branch https://github.com/Curabis/BCQuality.git "$env:USERPROFILE\.claude\BCQuality"
|
||||
|
||||
**Vocabulary:** wherever this document says "fetch", it means **copy the file
|
||||
from SRC** — a filesystem copy, which preserves raw bytes by definition (the
|
||||
old HTTP-encoding pitfalls do not exist here).
|
||||
|
||||
| Artefakt | Placering |
|
||||
|---|---|
|
||||
| bc-mcp-bridge.js | `{BASE}/bc-mcp-bridge.js` |
|
||||
| bc-mcp.config.template.json | `{BASE}/machine/bc-mcp.config.template.json` |
|
||||
|
|
@ -188,10 +207,13 @@ covers every repo, and the repo history stays free of upstream rule churn.
|
|||
|
||||
**Machine self-heal (auto-onboarding):** if this machine is not CURABIS-
|
||||
onboarded — `~/.claude/CLAUDE.md` or `~/.claude/bc-mcp-bridge.js` is missing —
|
||||
run the full onboarding NOW (idempotent; identity taken from git config):
|
||||
run the full onboarding NOW (idempotent; identity taken from git config; the
|
||||
first git contact may open a browser login — that IS the authentication):
|
||||
|
||||
powershell -ExecutionPolicy Bypass -Command "Invoke-WebRequest -UseBasicParsing https://raw.githubusercontent.com/Curabis/BCQuality/stable/custom/setup/machine/Install-CurabisMachine.ps1 -OutFile $env:TEMP\icm.ps1; & $env:TEMP\icm.ps1"
|
||||
git clone --branch stable --single-branch https://github.com/Curabis/BCQuality.git "$env:USERPROFILE\.claude\BCQuality"
|
||||
powershell -ExecutionPolicy Bypass -File "$env:USERPROFILE\.claude\BCQuality\custom\setup\machine\Install-CurabisMachine.ps1"
|
||||
|
||||
(Skip the clone line if `%USERPROFILE%\.claude\BCQuality` already exists.)
|
||||
Then report the manual leftovers it lists (personal client secret; the AL
|
||||
Language extension if VS Code lacks it) and ask the developer to restart
|
||||
Claude Code.
|
||||
|
|
@ -201,7 +223,9 @@ self-heal suffices:
|
|||
|
||||
powershell -ExecutionPolicy Bypass -File "$env:USERPROFILE\.claude\sync-bcquality-knowledge.ps1"
|
||||
|
||||
(If that sync script itself is missing, the full onboarding above installs it.)
|
||||
(If that sync script itself is missing, copy it from the channel clone:
|
||||
`%USERPROFILE%\.claude\BCQuality\custom\setup\sync-bcquality-knowledge.ps1` —
|
||||
or run the full onboarding above.)
|
||||
|
||||
These rules are always active.
|
||||
|
||||
|
|
@ -520,6 +544,10 @@ Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
|
|||
|
||||
Triggered by: "Opdater CURABIS Standard fra BCQuality"
|
||||
|
||||
**Step 0 — freshen the channel clone** (see Source section): fetch + checkout
|
||||
`origin/stable` in `%USERPROFILE%\.claude\BCQuality`; create the clone if
|
||||
missing. Every copy below reads from that clone.
|
||||
|
||||
Updates only the files that come directly from BCQuality.
|
||||
Never touches `CLAUDE.md`, `projectmemory/`, `docs/`, or `~/.bc-mcp.config.json`.
|
||||
|
||||
|
|
@ -600,10 +628,24 @@ Detect and clean up:
|
|||
- a reference to `.github/.agents/bcquality-knowledge/` (v6 repo-mirror era)
|
||||
- a literal per-developer path such as `C:\Users\<name>\.claude\...` — must be
|
||||
`~/.claude/...` / `%USERPROFILE%`, never one developer's username
|
||||
- ANY remaining `raw.githubusercontent.com`-based self-heal or onboarding
|
||||
command (v15-v18 era) — the repo is private; raw URLs are dead. The
|
||||
current form is git-based via the channel clone.
|
||||
If any match, propose replacing the section with the current template from
|
||||
Step 4a and ask for confirmation before editing CLAUDE.md (same confirmation
|
||||
gate as the agent-synligheds-check below).
|
||||
|
||||
### Machine CLAUDE.md refresh (Mode B)
|
||||
|
||||
The developer's global `~/.claude/CLAUDE.md` carries the CURABIS auto-update
|
||||
instructions. After a consumption-model change (like v19's git migration),
|
||||
those instructions go stale on every already-onboarded machine. Compare the
|
||||
machine file's CURABIS sections against `{BASE}/machine/CLAUDE.md` in the
|
||||
channel clone. If they diverge structurally (e.g. still reference raw URLs
|
||||
or GitHub-API SHA checks), propose the update — show the diff, preserve the
|
||||
Identity section verbatim, and ask for confirmation before editing: it is the
|
||||
developer's personal file.
|
||||
|
||||
### .mcp.json — hardcoded developer-path validation (Mode B)
|
||||
|
||||
`.mcp.json` is git-committed and shared — it must not contain a path baked in for
|
||||
|
|
@ -735,6 +777,9 @@ Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
|
|||
|
||||
## Invocation note
|
||||
|
||||
This agent is fetched on demand from BCQuality. Both commands work in any
|
||||
project — including one not yet configured — because Claude reads the URL
|
||||
from `~/.claude/CLAUDE.md` (global instructions, present on all CURABIS machines).
|
||||
This agent is read on demand from the machine's channel clone
|
||||
(`%USERPROFILE%\.claude\BCQuality\custom\setup\curabis-standard.agent.md`,
|
||||
after freshening — see Source section). Both commands work in any project —
|
||||
including one not yet configured — because the machine's `~/.claude/CLAUDE.md`
|
||||
(installed by onboarding) knows the clone location. On a machine without the
|
||||
clone, the two-line onboarding in Step 4a's self-heal is the entry point.
|
||||
|
|
@ -2,30 +2,54 @@
|
|||
# CURABIS — Global Claude Code Instructions
|
||||
|
||||
These instructions apply to every Claude Code session, regardless of project.
|
||||
BCQuality is a PRIVATE repo: all access is git-based via the channel clone at
|
||||
`%USERPROFILE%\.claude\BCQuality` (pinned to `stable`; auth = Git Credential
|
||||
Manager). No raw.githubusercontent URLs — they do not work and must not be used.
|
||||
|
||||
## Auto-update BCQuality (runs at every session start)
|
||||
|
||||
If the current project has `.github/.agents/bcquality.agent.md`:
|
||||
|
||||
1. Fetch the latest commit SHA for `custom/setup/` in BCQuality:
|
||||
`https://api.github.com/repos/Curabis/BCQuality/commits?path=custom/setup&sha=stable&per_page=1`
|
||||
1. Freshen the channel clone and read its SHA:
|
||||
`git -C "$env:USERPROFILE\.claude\BCQuality" fetch origin stable --quiet`
|
||||
`git -C "$env:USERPROFILE\.claude\BCQuality" rev-parse origin/stable`
|
||||
(If the clone is missing: run the machine self-heal from the project
|
||||
CLAUDE.md — two lines: git clone + Install-CurabisMachine.ps1.)
|
||||
2. Read stored SHA from `~/.claude/.bcquality-version` (may not exist yet)
|
||||
3. If SHA is different (or file missing):
|
||||
a. Fetch and execute Mode B from:
|
||||
`https://raw.githubusercontent.com/Curabis/BCQuality/stable/custom/setup/curabis-standard.agent.md`
|
||||
b. Write new SHA to `~/.claude/.bcquality-version`
|
||||
c. Report: "BCQuality opdateret til [short-sha] — [antal] filer tjekket"
|
||||
4. If SHA is unchanged: continue silently
|
||||
a. `git -C "$env:USERPROFILE\.claude\BCQuality" checkout -B stable origin/stable --quiet`
|
||||
b. Execute Mode B from the clone:
|
||||
`%USERPROFILE%\.claude\BCQuality\custom\setup\curabis-standard.agent.md`
|
||||
c. Refresh the local knowledge mirror:
|
||||
`powershell -ExecutionPolicy Bypass -File "$env:USERPROFILE\.claude\sync-bcquality-knowledge.ps1"`
|
||||
(git-based; also writes the new SHA to the version marker)
|
||||
d. Report: "BCQuality opdateret til [short-sha] — [antal] filer tjekket"
|
||||
4. If SHA is unchanged: continue silently — do NOT re-run the sync script. One
|
||||
sync per actual upstream change covers every project worked on until the next one.
|
||||
|
||||
Do this silently and quickly — do not ask for permission, do not explain the process
|
||||
unless something actually changed.
|
||||
|
||||
## BCQuality knowledge files — session start
|
||||
|
||||
At session start, read BCQuality rules from the local cache (fast — no network):
|
||||
|
||||
- **`custom/`** — always read in full: `%USERPROFILE%\.claude\bcquality-knowledge\custom\**\*.md`
|
||||
- **`community/`** and **`microsoft/`** — do NOT read in full (200+ files is too
|
||||
much to preload). Instead read `%USERPROFILE%\.claude\bcquality-knowledge\INDEX.md`
|
||||
first, and open only the files whose domain/keywords match the current task.
|
||||
|
||||
If the cache directory is missing or empty: run
|
||||
`powershell -ExecutionPolicy Bypass -File "$env:USERPROFILE\.claude\sync-bcquality-knowledge.ps1"`
|
||||
once, then proceed as above.
|
||||
|
||||
## CURABIS Standard project setup
|
||||
|
||||
When the user says either of these commands, fetch and follow the setup agent:
|
||||
When the user says either of these commands, freshen the channel clone (see
|
||||
Auto-update step 1) and follow the setup agent read from:
|
||||
|
||||
```
|
||||
https://raw.githubusercontent.com/Curabis/BCQuality/stable/custom/setup/curabis-standard.agent.md
|
||||
%USERPROFILE%\.claude\BCQuality\custom\setup\curabis-standard.agent.md
|
||||
```
|
||||
|
||||
- **"Konfigurer dette projekt til CURABIS Standard"** → fuld setup af nyt repo
|
||||
|
|
|
|||
|
|
@ -1,16 +1,16 @@
|
|||
# CURABIS maskin-onboarding - goer en frisk udviklermaskine klar til
|
||||
# CURABIS Standard. Koeres EEN gang pr. maskine; er idempotent (sikker at
|
||||
# koere igen). Alt hentes som raa bytes fra stable-kanalen.
|
||||
# CURABIS maskin-onboarding v2 (GIT-BASERET, privat repo) - goer en frisk
|
||||
# udviklermaskine CURABIS-klar. Idempotent; sikker at koere igen.
|
||||
#
|
||||
# Torsten (eller enhver ny udvikler) koerer:
|
||||
# powershell -ExecutionPolicy Bypass -File Install-CurabisMachine.ps1
|
||||
# Onboarding paa en ny maskine er TO linjer (GCM-login i browseren ved
|
||||
# foerste git-kontakt ER autentificeringen):
|
||||
#
|
||||
# Eller direkte fra BCQuality:
|
||||
# powershell -ExecutionPolicy Bypass -Command "Invoke-WebRequest -UseBasicParsing https://raw.githubusercontent.com/Curabis/BCQuality/stable/custom/setup/machine/Install-CurabisMachine.ps1 -OutFile $env:TEMP\icm.ps1; & $env:TEMP\icm.ps1"
|
||||
# git clone --branch stable --single-branch https://github.com/Curabis/BCQuality.git "$env:USERPROFILE\.claude\BCQuality"
|
||||
# powershell -ExecutionPolicy Bypass -File "$env:USERPROFILE\.claude\BCQuality\custom\setup\machine\Install-CurabisMachine.ps1"
|
||||
#
|
||||
# Hvad der IKKE haandteres her (personligt/manuel):
|
||||
# - din client secret i ~/.bc-mcp.config.json (scriptet lægger templaten
|
||||
# og siger til)
|
||||
# Alt kopieres fra kanal-klonen (filsystem-kopi = raa bytes; ingen raw-URLs).
|
||||
#
|
||||
# Haandteres IKKE her (personligt/manuelt):
|
||||
# - din client secret i ~/.bc-mcp.config.json (templaten laegges, du udfylder)
|
||||
# - VS Code + AL Language-extensionen (ms-dynamics-smb.al fra Marketplace)
|
||||
param(
|
||||
[string]$FullName,
|
||||
|
|
@ -18,11 +18,21 @@ param(
|
|||
)
|
||||
|
||||
$ErrorActionPreference = 'Stop'
|
||||
$raw = 'https://raw.githubusercontent.com/Curabis/BCQuality/stable/custom/setup'
|
||||
$claude = Join-Path $env:USERPROFILE '.claude'
|
||||
$clone = Join-Path $env:USERPROFILE '.claude\BCQuality'
|
||||
New-Item -ItemType Directory -Force $claude | Out-Null
|
||||
|
||||
# Identitet: default fra git config, ellers spoerg
|
||||
# Kilde: scriptet ligger i <klon>\custom\setup\machine → klonrod tre niveauer op
|
||||
$src = (Resolve-Path (Join-Path $PSScriptRoot '..\..\..')).Path
|
||||
|
||||
# Sikr kanal-klonen paa den kanoniske placering (scriptet KAN vaere koert fra en anden klon)
|
||||
if (-not (Test-Path (Join-Path $clone '.git'))) {
|
||||
if ($src -ne $clone) {
|
||||
git clone --branch stable --single-branch 'https://github.com/Curabis/BCQuality.git' $clone
|
||||
if ($LASTEXITCODE -ne 0) { throw 'git clone af kanal-klonen fejlede - tjek adgang/GCM.' }
|
||||
}
|
||||
}
|
||||
|
||||
if (-not $FullName) { $FullName = (git config user.name 2>$null) }
|
||||
if (-not $UserName) { $UserName = $env:USERNAME }
|
||||
if (-not $FullName) { $FullName = Read-Host 'Dit fulde navn' }
|
||||
|
|
@ -30,12 +40,12 @@ if (-not $FullName) { $FullName = Read-Host 'Dit fulde navn' }
|
|||
$done = @()
|
||||
$todo = @()
|
||||
|
||||
# 1. Global CLAUDE.md (fra template; overskriver ALDRIG en eksisterende)
|
||||
# 1. Global CLAUDE.md (fra template i klonen; overskriver ALDRIG en eksisterende)
|
||||
$gcm = Join-Path $claude 'CLAUDE.md'
|
||||
if (Test-Path $gcm) {
|
||||
$done += "CLAUDE.md fandtes allerede - ikke roert"
|
||||
$done += 'CLAUDE.md fandtes allerede - ikke roert'
|
||||
} else {
|
||||
Invoke-WebRequest -UseBasicParsing "$raw/machine/CLAUDE.md" -OutFile $gcm
|
||||
Copy-Item (Join-Path $src 'custom\setup\machine\CLAUDE.md') $gcm
|
||||
$t = [System.IO.File]::ReadAllText($gcm)
|
||||
$t = $t.Replace('[Your Name]', $FullName).Replace('[your-username]', $UserName)
|
||||
$t = $t -replace '<!-- Replace the two lines below with your own details -->\r?\n', ''
|
||||
|
|
@ -44,29 +54,22 @@ if (Test-Path $gcm) {
|
|||
}
|
||||
|
||||
# 2. BC MCP bridge (stable er autoritativ - overskriv)
|
||||
Invoke-WebRequest -UseBasicParsing "$raw/bc-mcp-bridge.js" -OutFile (Join-Path $claude 'bc-mcp-bridge.js')
|
||||
$done += "bc-mcp-bridge.js installeret"
|
||||
Copy-Item (Join-Path $src 'custom\setup\bc-mcp-bridge.js') (Join-Path $claude 'bc-mcp-bridge.js') -Force
|
||||
$done += 'bc-mcp-bridge.js installeret'
|
||||
|
||||
# 3. BC MCP config-template (personlig secret - aldrig overskrive)
|
||||
$cfg = Join-Path $env:USERPROFILE '.bc-mcp.config.json'
|
||||
if (Test-Path $cfg) {
|
||||
$done += "bc-mcp.config.json fandtes allerede - ikke roert"
|
||||
$done += 'bc-mcp.config.json fandtes allerede - ikke roert'
|
||||
} else {
|
||||
Invoke-WebRequest -UseBasicParsing "$raw/machine/bc-mcp.config.template.json" -OutFile $cfg
|
||||
Copy-Item (Join-Path $src 'custom\setup\machine\bc-mcp.config.template.json') $cfg
|
||||
$todo += "Aabn $cfg og indsaet din personlige client secret"
|
||||
}
|
||||
|
||||
# 4. Knowledge-sync-script + mirror
|
||||
Invoke-WebRequest -UseBasicParsing "$raw/sync-bcquality-knowledge.ps1" -OutFile (Join-Path $claude 'sync-bcquality-knowledge.ps1')
|
||||
# 4. Sync-script til maskinen + koer det (bygger mirror + saetter versionsmarkoer)
|
||||
Copy-Item (Join-Path $src 'custom\setup\sync-bcquality-knowledge.ps1') (Join-Path $claude 'sync-bcquality-knowledge.ps1') -Force
|
||||
& powershell -ExecutionPolicy Bypass -File (Join-Path $claude 'sync-bcquality-knowledge.ps1')
|
||||
$done += "bcquality-knowledge mirror synkroniseret"
|
||||
|
||||
# 5. Versionsmarkoer (stable-SHA)
|
||||
try {
|
||||
$sha = (Invoke-RestMethod 'https://api.github.com/repos/Curabis/BCQuality/commits?sha=stable&per_page=1')[0].sha
|
||||
Set-Content -Path (Join-Path $claude '.bcquality-version') -Value $sha -Encoding ascii
|
||||
$done += "versionsmarkoer sat ($($sha.Substring(0,7)))"
|
||||
} catch { $todo += "Kunne ikke saette versionsmarkoer (GitHub API) - foerste session goer det selv" }
|
||||
$done += 'bcquality-knowledge mirror synkroniseret (git-baseret)'
|
||||
|
||||
Write-Host ''
|
||||
Write-Host '=== CURABIS maskin-onboarding faerdig ===' -ForegroundColor Green
|
||||
|
|
@ -78,5 +81,4 @@ if ($todo) {
|
|||
}
|
||||
Write-Host ''
|
||||
Write-Host 'Pr. repo herefter: sig "Opdater CURABIS Standard fra BCQuality" i Claude'
|
||||
Write-Host 'Code - den deployer selv .vscode/find-altool.ps1 og AL MCP-opsaetningen.'
|
||||
Write-Host 'Genstart Claude Code efter foerste onboarding.'
|
||||
Write-Host 'Code - den henter alt fra kanal-klonen. Genstart Claude Code foerst.'
|
||||
|
|
|
|||
|
|
@ -1,36 +1,47 @@
|
|||
# Refresh the MACHINE-LOCAL mirror of the Curabis BCQuality knowledge base.
|
||||
#
|
||||
# Mirrors three layers from https://github.com/Curabis/BCQuality:
|
||||
# v2 - GIT-BASED (privat repo): al konsumtion sker via en kanal-klon i
|
||||
# %USERPROFILE%\.claude\BCQuality (pinned til stable-branchen)
|
||||
# Autentificering haandteres af Git Credential Manager - ingen raw-URLs,
|
||||
# ingen GitHub API, ingen CDN-cache. Foerste koersel udloeser evt. et
|
||||
# GCM-login i browseren; det ER onboarding-autentificeringen.
|
||||
#
|
||||
# Mirrors three layers into %USERPROFILE%\.claude\bcquality-knowledge:
|
||||
# custom/ - Curabis org-specific rules (ALWAYS read in full each session)
|
||||
# community/ - BC community patterns (loaded on relevance via INDEX.md)
|
||||
# microsoft/ - platform guardrails (loaded on relevance via INDEX.md)
|
||||
# ...plus INDEX.md (domain + keywords per fil) og opdaterer versionsmarkoeren.
|
||||
#
|
||||
# The upstream file list is discovered dynamically from the GitHub tree API, so
|
||||
# new/removed upstream files propagate automatically - nothing is hardcoded.
|
||||
# After downloading, an INDEX.md is generated (one line per file, with domain +
|
||||
# keywords from each file's frontmatter) so an agent can scan and pull only the
|
||||
# files relevant to a task instead of loading all ~100 every session.
|
||||
#
|
||||
# The mirror is per developer machine (~/.claude/bcquality-knowledge/), shared
|
||||
# by every CURABIS repo on it. It is NEVER committed to a project repository -
|
||||
# see BCQuality rule bcquality-knowledge-must-mirror-to-machine-not-repo.
|
||||
# One sync per machine covers every repo. Run periodically:
|
||||
# Mirroren committes ALDRIG til et projekt-repo - se BCQuality-reglen
|
||||
# bcquality-knowledge-must-mirror-to-machine-not-repo. Koer periodisk:
|
||||
# powershell -ExecutionPolicy Bypass -File "$env:USERPROFILE\.claude\sync-bcquality-knowledge.ps1"
|
||||
|
||||
$ErrorActionPreference = 'Stop'
|
||||
|
||||
$repo = 'Curabis/BCQuality'
|
||||
$branch = 'stable'
|
||||
$repoUrl = 'https://github.com/Curabis/BCQuality.git'
|
||||
$clone = Join-Path $env:USERPROFILE '.claude\BCQuality'
|
||||
$dest = Join-Path $env:USERPROFILE '.claude\bcquality-knowledge'
|
||||
$marker = Join-Path $env:USERPROFILE '.claude\.bcquality-version'
|
||||
$staging = "$dest.tmp"
|
||||
$rawBase = "https://raw.githubusercontent.com/$repo/$branch"
|
||||
$treeUrl = "https://api.github.com/repos/$repo/git/trees/$branch" + '?recursive=1'
|
||||
|
||||
# Upstream path prefix -> local layer folder
|
||||
# --- 1. Kanal-klon: opret eller opdater (pinned til stable) ---
|
||||
if (-not (Test-Path (Join-Path $clone '.git'))) {
|
||||
Write-Host "Kanal-klon mangler - kloner stable fra $repoUrl ..."
|
||||
git clone --branch stable --single-branch $repoUrl $clone
|
||||
if ($LASTEXITCODE -ne 0) { throw "git clone fejlede - er du autentificeret (GCM), og har du adgang til repoet?" }
|
||||
} else {
|
||||
git -C $clone fetch origin stable --quiet
|
||||
if ($LASTEXITCODE -ne 0) { throw "git fetch fejlede - tjek netvaerk/adgang." }
|
||||
git -C $clone checkout -B stable origin/stable --quiet
|
||||
}
|
||||
$sha = (git -C $clone rev-parse HEAD).Trim()
|
||||
Write-Host "Kanal-klon paa stable @ $($sha.Substring(0,7))"
|
||||
|
||||
# --- 2. Byg mirror fra klonens filer (ingen netvaerk herfra) ---
|
||||
$layerMap = [ordered]@{
|
||||
'custom/knowledge/' = 'custom'
|
||||
'community/knowledge/' = 'community'
|
||||
'microsoft/knowledge/' = 'microsoft'
|
||||
'custom\knowledge' = 'custom'
|
||||
'community\knowledge' = 'community'
|
||||
'microsoft\knowledge' = 'microsoft'
|
||||
}
|
||||
|
||||
function Get-Frontmatter {
|
||||
|
|
@ -47,50 +58,25 @@ function Get-Frontmatter {
|
|||
return $fm
|
||||
}
|
||||
|
||||
Write-Host "Fetching file tree from $repo@$branch ..."
|
||||
$headers = @{ 'User-Agent' = 'wareco-bcquality-sync'; 'Accept' = 'application/vnd.github+json' }
|
||||
$tree = (Invoke-RestMethod -Uri $treeUrl -Headers $headers).tree
|
||||
|
||||
# Build the download worklist from the tree
|
||||
$files = @()
|
||||
foreach ($node in $tree) {
|
||||
if ($node.type -ne 'blob') { continue }
|
||||
if ($node.path -notlike '*.md') { continue }
|
||||
foreach ($prefix in $layerMap.Keys) {
|
||||
if ($node.path.StartsWith($prefix)) {
|
||||
$relative = $node.path.Substring($prefix.Length) # e.g. performance/avoid-commit-inside-loops.md
|
||||
$files += [pscustomobject]@{
|
||||
Url = "$rawBase/$($node.path)"
|
||||
Layer = $layerMap[$prefix]
|
||||
Relative = $relative
|
||||
LocalPath = Join-Path $staging (Join-Path $layerMap[$prefix] $relative)
|
||||
}
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ($files.Count -eq 0) { throw 'No knowledge files found in upstream tree - aborting.' }
|
||||
|
||||
# Download into a staging folder so a mid-run failure never wipes the live copy
|
||||
if (Test-Path $staging) { Remove-Item -Recurse -Force $staging }
|
||||
New-Item -ItemType Directory -Force $staging | Out-Null
|
||||
|
||||
Write-Host "Downloading $($files.Count) knowledge files ..."
|
||||
$rc = 0
|
||||
foreach ($f in $files) {
|
||||
New-Item -ItemType Directory -Force (Split-Path $f.LocalPath) | Out-Null
|
||||
try {
|
||||
Invoke-WebRequest -Uri $f.Url -OutFile $f.LocalPath -UseBasicParsing -ErrorAction Stop
|
||||
Write-Host "OK $($f.Layer)/$($f.Relative)"
|
||||
} catch {
|
||||
Write-Error "FAIL $($f.Layer)/$($f.Relative)"
|
||||
$rc = 1
|
||||
$files = @()
|
||||
foreach ($prefix in $layerMap.Keys) {
|
||||
$srcDir = Join-Path $clone $prefix
|
||||
if (-not (Test-Path $srcDir)) { continue }
|
||||
$layer = $layerMap[$prefix]
|
||||
Get-ChildItem $srcDir -Recurse -Filter *.md | ForEach-Object {
|
||||
$relative = $_.FullName.Substring($srcDir.Length + 1)
|
||||
$localPath = Join-Path $staging (Join-Path $layer $relative)
|
||||
New-Item -ItemType Directory -Force (Split-Path $localPath) | Out-Null
|
||||
Copy-Item $_.FullName $localPath
|
||||
$files += [pscustomobject]@{ Layer = $layer; Relative = $relative; LocalPath = $localPath }
|
||||
}
|
||||
}
|
||||
if ($files.Count -eq 0) { throw 'Ingen knowledge-filer fundet i kanal-klonen - afbryder.' }
|
||||
|
||||
# Generate INDEX.md (relevance index for all layers)
|
||||
Write-Host "Generating INDEX.md ..."
|
||||
# --- 3. INDEX.md (relevans-indeks for alle lag) ---
|
||||
$idx = [System.Collections.Generic.List[string]]::new()
|
||||
$idx.Add('# BCQuality Knowledge Index')
|
||||
$idx.Add('')
|
||||
|
|
@ -100,7 +86,6 @@ $idx.Add('Layers: `custom` is ALWAYS read in full each session. For `community`
|
|||
$idx.Add('`microsoft`, scan this index and read only the files whose domain/keywords')
|
||||
$idx.Add('match the task at hand.')
|
||||
$idx.Add('')
|
||||
|
||||
foreach ($layer in @('custom', 'community', 'microsoft')) {
|
||||
$layerFiles = $files | Where-Object { $_.Layer -eq $layer } | Sort-Object Relative
|
||||
if (-not $layerFiles) { continue }
|
||||
|
|
@ -111,18 +96,18 @@ foreach ($layer in @('custom', 'community', 'microsoft')) {
|
|||
$fm = Get-Frontmatter $f.LocalPath
|
||||
$domain = if ($fm.ContainsKey('domain')) { $fm['domain'] } else { '' }
|
||||
$keywords = if ($fm.ContainsKey('keywords')) { $fm['keywords'].Trim('[', ']') } else { '' }
|
||||
$rel = $f.Relative -replace '\.md$', ''
|
||||
$rel = ($f.Relative -replace '\.md$', '') -replace '\\', '/'
|
||||
$idx.Add("- ``$layer/$rel`` - domain: $domain; keywords: $keywords")
|
||||
}
|
||||
$idx.Add('')
|
||||
}
|
||||
Set-Content -Path (Join-Path $staging 'INDEX.md') -Value $idx -Encoding utf8
|
||||
|
||||
# Swap staging into place
|
||||
# --- 4. Swap + markoer ---
|
||||
if (Test-Path $dest) { Remove-Item -Recurse -Force $dest }
|
||||
Rename-Item -Path $staging -NewName (Split-Path $dest -Leaf)
|
||||
Set-Content -Path $marker -Value $sha -Encoding ascii
|
||||
|
||||
Write-Host ''
|
||||
Write-Host "Done. $($files.Count) files across $($layerMap.Count) layers."
|
||||
Write-Host "Done. $($files.Count) filer, 3 lag, stable @ $($sha.Substring(0,7))."
|
||||
Write-Host "Machine-local mirror updated: $dest"
|
||||
exit $rc
|
||||
|
|
|
|||
|
|
@ -56,14 +56,11 @@ Loop: **reproduce -> root-cause -> minimal-fix recommendation.**
|
|||
|
||||
Layer 1 - Microsoft BCQuality: https://github.com/microsoft/BCQuality
|
||||
|
||||
Layer 2 - CURABIS custom knowledge (fetch before citing a finding):
|
||||
- https://raw.githubusercontent.com/Curabis/BCQuality/stable/custom/knowledge/architecture/pages-must-not-contain-business-logic.md
|
||||
- https://raw.githubusercontent.com/Curabis/BCQuality/stable/custom/knowledge/architecture/namespace-must-be-verified-from-source.md
|
||||
- https://raw.githubusercontent.com/Curabis/BCQuality/stable/custom/knowledge/architecture/al-identifiers-must-be-english.md
|
||||
- https://raw.githubusercontent.com/Curabis/BCQuality/stable/custom/knowledge/architecture/clarify-before-building.md
|
||||
- https://raw.githubusercontent.com/Curabis/BCQuality/stable/custom/knowledge/testing/test-setup-must-use-library-codeunit.md
|
||||
- https://raw.githubusercontent.com/Curabis/BCQuality/stable/custom/knowledge/testing/test-data-must-be-random-and-complete.md
|
||||
- https://raw.githubusercontent.com/Curabis/BCQuality/stable/custom/knowledge/testing/tests-must-adapt-to-existing-code.md
|
||||
Layer 2 - CURABIS custom knowledge: read from the machine-local mirror —
|
||||
`%USERPROFILE%\.claude\bcquality-knowledge\custom\` (always complete; never a
|
||||
hardcoded file list — the rulebook grows). Fallback without a mirror: the
|
||||
channel clone at `%USERPROFILE%\.claude\BCQuality\custom\knowledge\`. The
|
||||
repo is PRIVATE — raw URLs do not exist.
|
||||
|
||||
If a source is unreachable, **degrade gracefully**: fall back to the triage protocol
|
||||
below plus the CURABIS-ARCH rules in `bcquality.agent.md`, note that BCQuality was
|
||||
|
|
|
|||
|
|
@ -54,10 +54,13 @@ Resolve the current rule set at review time, in this order:
|
|||
`~/.claude/bcquality-knowledge/custom/` (Windows:
|
||||
`%USERPROFILE%\.claude\bcquality-knowledge\custom\`). The mirror is synced
|
||||
from the `stable` release channel and is always the complete custom layer.
|
||||
2. **Fallback (no mirror — Copilot, fresh machine, CI):** list the tree via
|
||||
`https://api.github.com/repos/Curabis/BCQuality/git/trees/stable?recursive=1`
|
||||
filtered to `custom/knowledge/**/*.md`, and fetch each file from
|
||||
`https://raw.githubusercontent.com/Curabis/BCQuality/stable/<path>`.
|
||||
2. **Fallback (no mirror):** read directly from the machine's channel clone —
|
||||
`%USERPROFILE%\.claude\BCQuality\custom\knowledge\**\*.md` (freshen with
|
||||
`git -C "$env:USERPROFILE\.claude\BCQuality" pull` if stale). The repo is
|
||||
PRIVATE: tree-API/raw-URL fallbacks no longer exist. Consumers without
|
||||
filesystem access outside the workspace (e.g. Copilot) rely on the
|
||||
repo-committed agent files alone — deep custom-layer lookups happen in
|
||||
Claude Code sessions.
|
||||
|
||||
Relevance filtering: `custom/` rules are always active in CURABIS repos — read
|
||||
them all; use each file's frontmatter `domain`/`keywords` only to prioritize,
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue