{"id":51026370,"url":"https://github.com/norandom/siyuan-knowledge-sync","last_synced_at":"2026-06-21T20:01:17.364Z","repository":{"id":363328574,"uuid":"1239822171","full_name":"norandom/siyuan-knowledge-sync","owner":"norandom","description":"Sync client for SiYuan wiki","archived":false,"fork":false,"pushed_at":"2026-06-08T11:37:09.000Z","size":416,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":0,"default_branch":"main","last_synced_at":"2026-06-08T13:23:57.577Z","etag":null,"topics":["git","information-systems","knowledge-base","markdown","ontology","siyuan","tags","wiki"],"latest_commit_sha":null,"homepage":"https://wiki.because-security.com/","language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/norandom.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2026-05-15T13:30:11.000Z","updated_at":"2026-06-08T11:40:02.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/norandom/siyuan-knowledge-sync","commit_stats":null,"previous_names":["norandom/siyuan-knowledge-sync"],"tags_count":5,"template":false,"template_full_name":null,"purl":"pkg:github/norandom/siyuan-knowledge-sync","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/norandom%2Fsiyuan-knowledge-sync","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/norandom%2Fsiyuan-knowledge-sync/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/norandom%2Fsiyuan-knowledge-sync/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/norandom%2Fsiyuan-knowledge-sync/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/norandom","download_url":"https://codeload.github.com/norandom/siyuan-knowledge-sync/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/norandom%2Fsiyuan-knowledge-sync/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":34623906,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-05-26T15:22:16.424Z","status":"online","status_checked_at":"2026-06-21T02:00:05.568Z","response_time":54,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["git","information-systems","knowledge-base","markdown","ontology","siyuan","tags","wiki"],"created_at":"2026-06-21T20:01:16.379Z","updated_at":"2026-06-21T20:01:17.346Z","avatar_url":"https://github.com/norandom.png","language":"Go","funding_links":[],"categories":[],"sub_categories":[],"readme":"# siyuan-knowledge-sync\n\nSync a folder of markdown notes to [SiYuan](https://b3log.org/siyuan/). Every note gets a `domain` and `intent` tag that controls where it lands in your SiYuan wiki. The tool reads your Git repo, figures out what changed, and pushes only the differences.\n\n## Concepts\n\n**Ontology.** In information science, an ontology is \"a formal, explicit specification of a shared conceptualization\" ([Gruber, 1993](https://doi.org/10.1006/ijhc.1995.1081)). In this tool, an ontology defines the set of allowed `domain` and `intent` values, the SiYuan folder each domain maps to, and an optional tag vocabulary. The defaults ship as examples; you can replace them entirely.\n\n**Tag.** A tag is a piece of metadata attached to a document that describes its content or role, independent of its location in a folder hierarchy. Here, tags live in YAML frontmatter (`domain:`, `intent:`, and optional free-form tags) and drive routing, search, and compliance checks.\n\n**Bimodal.** Bimodal means the ontology has two independent axes. Every note carries exactly one `domain` (what it is about) and one `intent` (what kind of document it is). For example, a note tagged `domain: security` / `intent: sop` is a security-related standard operating procedure. These two dimensions are orthogonal: you can combine any domain with any intent.\n\n## Quick start\n\n### 1. Install\n\nDownload the latest binary for your platform from GitHub releases:\n\n```bash\n# Linux (amd64)\ncurl -L -o siyuan-knowledge-sync https://github.com/norandom/siyuan-knowledge-sync/releases/latest/download/siyuan-knowledge-sync_latest_linux_amd64\nchmod +x siyuan-knowledge-sync\nsudo mv siyuan-knowledge-sync /usr/local/bin/\n\n# Linux (arm64)\ncurl -L -o siyuan-knowledge-sync https://github.com/norandom/siyuan-knowledge-sync/releases/latest/download/siyuan-knowledge-sync_latest_linux_arm64\nchmod +x siyuan-knowledge-sync\nsudo mv siyuan-knowledge-sync /usr/local/bin/\n\n# Linux (armv7, e.g. Raspberry Pi)\ncurl -L -o siyuan-knowledge-sync https://github.com/norandom/siyuan-knowledge-sync/releases/latest/download/siyuan-knowledge-sync_latest_linux_arm\nchmod +x siyuan-knowledge-sync\nsudo mv siyuan-knowledge-sync /usr/local/bin/\n\n# macOS (Apple silicon)\ncurl -L -o siyuan-knowledge-sync https://github.com/norandom/siyuan-knowledge-sync/releases/latest/download/siyuan-knowledge-sync_latest_darwin_arm64\nchmod +x siyuan-knowledge-sync\nsudo mv siyuan-knowledge-sync /usr/local/bin/\n\n# macOS (Intel)\ncurl -L -o siyuan-knowledge-sync https://github.com/norandom/siyuan-knowledge-sync/releases/latest/download/siyuan-knowledge-sync_latest_darwin_amd64\nchmod +x siyuan-knowledge-sync\nsudo mv siyuan-knowledge-sync /usr/local/bin/\n\n# Windows (PowerShell)\nInvoke-WebRequest -Uri \"https://github.com/norandom/siyuan-knowledge-sync/releases/latest/download/siyuan-knowledge-sync_latest_windows_amd64.exe\" -OutFile \"siyuan-knowledge-sync.exe\"\n```\n\nOr with Go:\n\n```bash\ngo install github.com/norandom/siyuan-knowledge-sync/cmd/siyuan-knowledge-sync@latest\n```\n\nOr build from source:\n\n```bash\ngit clone https://github.com/norandom/siyuan-knowledge-sync.git\ncd siyuan-knowledge-sync\ngo build -o siyuan-knowledge-sync ./cmd/siyuan-knowledge-sync\n```\n\n### 2. Configure\n\nCreate `.siyuan-sync.yaml` in your repo root (or anywhere — pass `-c path/to/config.yaml`):\n\n```yaml\nendpoint: http://localhost:6806\ntoken: your-siyuan-api-token\nrepo_path: /path/to/your/markdown/repo\nautofix: true\n```\n\n### 3. Tag your notes\n\nEvery markdown file needs a YAML frontmatter block with `domain` and `intent`:\n\n```yaml\n---\ndomain: security\nintent: sop\n---\n# How to rotate API keys\n\n1. Generate the new key...\n```\n\nThe values shown below are the built-in defaults. You can replace them entirely in your config (see [Configuration reference](#configuration-reference)). To see the active set, run `siyuan-knowledge-sync schema --json`.\n\n**Default domains** (the topic of the note):\n\n| domain | SiYuan folder |\n|---|---|\n| `devops` | Sysadmin \u0026 DevOps |\n| `forensics` | Digital Forensics |\n| `security` | Security |\n| `ai-ml` | AI \u0026 ML |\n| `software-dev` | Software Development |\n| `quant-finance` | Quant Finance |\n\n**Default intents** (the kind of document):\n\n| intent | Purpose |\n|---|---|\n| `config` | Configuration reference |\n| `sop` | Standard operating procedure |\n| `log` | Activity or incident log |\n| `decision` | Decision record |\n| `concept` | Conceptual explanation |\n\nYou can define your own domains and intents in the config file. For example, a team focused on product management might use `domain: product` / `intent: prd`, while a research group might use `domain: neuroscience` / `intent: hypothesis`.\n\n### 4. Sync\n\n```bash\nsiyuan-knowledge-sync sync\n```\n\nThe sync is incremental: only Git-tracked files that changed since the last run get uploaded. New notes land in the SiYuan folder matching their `domain`. Notes already at the right path are skipped; notes in the wrong folder get moved (git mv + commit).\n\n## Commands\n\n### `sync` — Upload changes to SiYuan\n\n```bash\nsiyuan-knowledge-sync sync              # incremental sync\nsiyuan-knowledge-sync sync --dry-run    # audit only, no changes\n```\n\n### `download` — Pull SiYuan content to local files\n\n```bash\nsiyuan-knowledge-sync download                     # skip conflicts\nsiyuan-knowledge-sync download --conflict overwrite # replace local files\nsiyuan-knowledge-sync download --conflict merge     # merge content\n```\n\n### `audit` — Check files for compliance issues\n\n```bash\nsiyuan-knowledge-sync audit             # report issues\nsiyuan-knowledge-sync audit --autofix   # fix what can be fixed\n```\n\nChecks for: missing domain/intent, invalid values, bad heading levels, missing block IDs, unknown tags, TOC problems.\n\n### `schema` — Show ontology configuration\n\n```bash\nsiyuan-knowledge-sync schema            # human-readable\nsiyuan-knowledge-sync schema --json     # JSON output\n```\n\n### `migrate` — Bulk moves when ontology changes\n\n```bash\nsiyuan-knowledge-sync migrate plan    # generate a plan\nsiyuan-knowledge-sync migrate apply plan.json   # execute it\n```\n\n## Configuration reference\n\nFull `.siyuan-sync.yaml`:\n\n```yaml\nendpoint: http://localhost:6806\ntoken: your-api-token\nrepo_path: /home/you/notes\nautofix: true\n\n# Optional: Cloudflare Access (Zero Trust)\ncf_access_client_id: your-cf-client-id\ncf_access_client_secret: your-cf-secret\n\n# Optional: override the default ontology\nontology:\n  # Replace the built-in domains with your own.\n  # Each entry needs an id (used in frontmatter) and a folder (SiYuan destination).\n  domains:\n    - id: product\n      folder: Product Management\n    - id: engineering\n      folder: Engineering\n    - id: research\n      folder: Research\n\n  # Replace the built-in intents.\n  # Each entry needs an id. Add a folder to route intents to their own index doc.\n  intents:\n    - id: prd\n    - id: rfc\n    - id: postmortem\n    - id: adr\n\n  # Optional: restrict allowed tags to this list.\n  # Omit to allow any tag. Set to [] to forbid free-form tags entirely.\n  tags:\n    - draft\n    - review\n    - archived\n```\n\nOmit `ontology:` to use the built-in defaults. Provide it to replace the defaults entirely. Run `siyuan-knowledge-sync schema --json` to verify your active configuration.\n\n## Repo layout\n\nThe tool walks every `.md` file tracked by Git. Where a file lives on disk does not matter for discovery -- Git tracking is the only prerequisite. What matters is the `domain` in its frontmatter.\n\n**Canonical layout.** Each domain maps to a folder name (see defaults above or your config). A file with `domain: security` belongs in the `Security/` folder. If it is already there (or in a subdirectory of it), nothing happens. If it is somewhere else, the tool moves it with `git mv` and commits the change.\n\n```\nnotes/\n├── Security/                     ← domain: security files live here\n│   ├── rotate-keys.md\n│   └── incident-response/\n│       └── playbook.md           ← subdirectories are fine\n├── Sysadmin \u0026 DevOps/            ← domain: devops\n│   └── deploy-staging.md\n├── Random Notes/                 ← will be routed on next sync\n│   └── old-security-note.md      ← domain: security → moves to Security/\n└── README.md                     ← not .md with frontmatter? ignored\n```\n\n**Root-level files.** A `.md` file at the repo root (no directory) syncs to a SiYuan notebook named `root`. This is rarely what you want -- use a domain folder instead.\n\n**Routing is flat.** When a file moves, only its basename is preserved. `Random Notes/old-security-note.md` becomes `Security/old-security-note.md`, not `Security/Random Notes/old-security-note.md`.\n\n**Assets.** Relative image/link references (e.g. `![](images/diagram.png)`) are scanned during routing. If a move would break a reference, the tool reports a warning but still moves the file. Place assets alongside their notes or use absolute paths.\n\n## License\n\nMIT\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fnorandom%2Fsiyuan-knowledge-sync","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fnorandom%2Fsiyuan-knowledge-sync","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fnorandom%2Fsiyuan-knowledge-sync/lists"}