diff --git a/SOURCE_PROVENANCE.json b/SOURCE_PROVENANCE.json
index 34c0b73..76ec204 100644
--- a/SOURCE_PROVENANCE.json
+++ b/SOURCE_PROVENANCE.json
@@ -2,15 +2,55 @@
"schemaVersion": 1,
"surface": "docs",
"targetRepository": "PidgeonHealth/docs",
- "upstreamSha": "6d6564cf95819363f4ff13b434ca8cdaf228cb97",
+ "upstreamSha": "a7e19d716f3d62a41039f88ac5f98bee8ad63b89",
"sourceRef": "origin/main",
- "manifestSha256": "40f7b66a131b5b6765bcfaac35cabaa47d69cac0e04f444cc9a96849b0437b5c",
+ "manifestSha256": "96297d8522315f67330356ec075b83743ac3cd9e483a004bb69c8fdbd680e35e",
"projectorPath": "scripts/public-release/project.mjs",
- "projectorSha256": "f45498479728274e9a1e844bd83ca25a05c35b17c487e0544ffbfd2e10c942b8",
+ "projectorSha256": "d442193e68e021f966ead189854a9c695e525fc631044866cce7fea9f659e4a0",
"compositionManifestPath": null,
"compositionManifestSha256": null,
"secretScanner": "pidgeon-public-projection-v1",
"files": [
+ {
+ "path": ".github/CODEOWNERS",
+ "sha256": "85aff23b0ee0ee1f8202c392acb9190abfa60cdff2f83884f2d3fdd0d48afece",
+ "size": 84,
+ "mode": "100644",
+ "source": "config/public-ci-templates/per-target/docs/CODEOWNERS",
+ "license": "Pidgeon-Public-Documentation"
+ },
+ {
+ "path": ".github/dependabot.yml",
+ "sha256": "f9a5b5be714d882b9559d81a085e64d512443f574d48f18a5239e324a1cd202e",
+ "size": 522,
+ "mode": "100644",
+ "source": "config/public-ci-templates/per-target/docs/dependabot.yml",
+ "license": "Pidgeon-Public-Documentation"
+ },
+ {
+ "path": ".github/workflows/ci.yml",
+ "sha256": "78698e13e1e2d5b0e62a3b0459e9f390b12433948dd89b131329d3e190b7853a",
+ "size": 1068,
+ "mode": "100644",
+ "source": "config/public-ci-templates/per-target/docs/ci.yml",
+ "license": "Pidgeon-Public-Documentation"
+ },
+ {
+ "path": ".github/workflows/clean-build-smoke.yml",
+ "sha256": "8d5ef70711ab1f293b415c24f027938bffa9afa2dd87d168a0565c83d6a38bd6",
+ "size": 993,
+ "mode": "100644",
+ "source": "config/public-ci-templates/per-target/docs/clean-build-smoke.yml",
+ "license": "Pidgeon-Public-Documentation"
+ },
+ {
+ "path": ".github/workflows/release.yml",
+ "sha256": "025812b2fa66acd47fb0300bfc35e394d0a4abe7aa46e350a9af37195d2ffd17",
+ "size": 2449,
+ "mode": "100644",
+ "source": "config/public-ci-templates/per-target/docs/release.yml",
+ "license": "Pidgeon-Public-Documentation"
+ },
{
"path": "CONTRIBUTING.md",
"sha256": "1d0b18e31952f4896f892fe001ed68cffbc5a2eb9395fe114c3fedee08b2b5bc",
@@ -59,186 +99,210 @@
"source": "config/public-projections/scaffold/shared/SECURITY.md",
"license": "Pidgeon-Public-Documentation"
},
- {
- "path": "api-reference/admin.mdx",
- "sha256": "eb8ca3d96398a536e9e927e33fb26abdec76c6f6347ceefbd106cf4486e2ef2d",
- "size": 2936,
- "mode": "100644",
- "source": "pidgeon-docs/api-reference/admin.mdx",
- "license": "Pidgeon-Public-Documentation"
- },
{
"path": "api-reference/ai-triage.mdx",
- "sha256": "259190765c6762955b7df5e9fd2f1b312cecbf0285132417918972ccd6d37fe9",
- "size": 1527,
+ "sha256": "d04eff92e6645cf119c66a6b65d87310e77cb1131bc609029acd065759f49891",
+ "size": 1797,
"mode": "100644",
"source": "pidgeon-docs/api-reference/ai-triage.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "api-reference/analytics.mdx",
- "sha256": "f74144415a2417a7bf4d213fc714270ef8ecd35d148639e606dc4c7ca29dccb7",
- "size": 2902,
+ "sha256": "e79fd99cc85110c80a2a6748ec479a4021764c8cfb156e8e6fb84e5a7e080280",
+ "size": 3266,
"mode": "100644",
"source": "pidgeon-docs/api-reference/analytics.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "api-reference/diff.mdx",
- "sha256": "c9a599445fe065ca881a0d3dc6144e4ccabc124998b9335c3072c5b032d16f39",
- "size": 1474,
+ "sha256": "7153b4bdee3e0e64355aaf1ef028c14d3ab16caec6c731f24d8da0e30337e7dd",
+ "size": 1624,
"mode": "100644",
"source": "pidgeon-docs/api-reference/diff.mdx",
"license": "Pidgeon-Public-Documentation"
},
- {
- "path": "api-reference/enterprise.mdx",
- "sha256": "1950f9f16aa5da85d3e9ab167771771725b42a76aff217364d5ed11bd0c7312c",
- "size": 3112,
- "mode": "100644",
- "source": "pidgeon-docs/api-reference/enterprise.mdx",
- "license": "Pidgeon-Public-Documentation"
- },
{
"path": "api-reference/flock.mdx",
- "sha256": "383e4e42669445c331901363ddd942062974ac05009ecf6b8de9c64af45b1635",
- "size": 3210,
+ "sha256": "40572b68b4b55190637652ef602aa7d52a569e910478d2f227bb675bc281ac14",
+ "size": 4057,
"mode": "100644",
"source": "pidgeon-docs/api-reference/flock.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "api-reference/generate.mdx",
- "sha256": "7a205229e830408ef11521079b266499010d5ed1da5bfc81e7bb98c7ef5fcdd3",
- "size": 1282,
+ "sha256": "678080f34509dddecb8eab136ba8049a04b57cb50162d6fe51b5319b92b2d7fd",
+ "size": 1372,
"mode": "100644",
"source": "pidgeon-docs/api-reference/generate.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "api-reference/introduction.mdx",
- "sha256": "c23b0b5c20d08dad0ea5efa8cdb0beef54e158e0d0d71d5f28584be0387728ff",
- "size": 3455,
+ "sha256": "bd4972f1e86f1fd0b580dc4ded2d8f137cfe305ea9c6a230792b0faabece44b6",
+ "size": 3176,
"mode": "100644",
"source": "pidgeon-docs/api-reference/introduction.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "api-reference/loft-alerts.mdx",
- "sha256": "b02c1dd6fe1414bedca87fe288103be3bce663a0a68a17db79a052cbe2bbe464",
- "size": 1087,
+ "sha256": "3f3ad5df81bb3dc4f51c626e075669cddc60b98c80466245f41a155b96bbafbf",
+ "size": 1523,
"mode": "100644",
"source": "pidgeon-docs/api-reference/loft-alerts.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "api-reference/loft-interfaces.mdx",
- "sha256": "138b7db2663e685e10df9f89f23d6f9dcef025e6cab40c03b50930849dc9e9c0",
- "size": 2129,
+ "sha256": "cd10362dd037e8fd5c7c6d0730d75761710bfc1f6c6077fd4ce6fabfc9783934",
+ "size": 2592,
"mode": "100644",
"source": "pidgeon-docs/api-reference/loft-interfaces.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "api-reference/loft-status.mdx",
- "sha256": "40aeaf1cc98c104dbdf2708fd71678b32a64d6f76acbf8e83484c785d4d20a2e",
- "size": 647,
+ "sha256": "36844aaea7f567f94e65b4bf79b14f04d05603e0f93da0469c3dfdc7503e894e",
+ "size": 999,
"mode": "100644",
"source": "pidgeon-docs/api-reference/loft-status.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "api-reference/signalr.mdx",
- "sha256": "0a265c7d78342d05e39eeb2351b5545940f2756e041767fa5d38e1e289b134b2",
- "size": 2602,
+ "sha256": "198df74cc9ea830384b6c478a5b480c65d6389c338a0f6089359b41a75e3b883",
+ "size": 2839,
"mode": "100644",
"source": "pidgeon-docs/api-reference/signalr.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "api-reference/traces.mdx",
- "sha256": "0ff121fe88676e5c494a6c04c9c631927871208cec9c8eaff1cedfd8cc6f5727",
- "size": 2382,
+ "sha256": "6385af5349415ebfefbf99fe6d58e1bb6cb6d35fd5bd034a6d4c421bdd6bd638",
+ "size": 2784,
"mode": "100644",
"source": "pidgeon-docs/api-reference/traces.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "api-reference/validate.mdx",
- "sha256": "10d753678a8b908b520506d1ef6caf90ad55058893e10b6bbd9cd54bc561f99b",
- "size": 1652,
+ "sha256": "ebff55393c5cad8853d8f92c9e41cebbec3c5d629fa14ef6eb83f0d26ebe7224",
+ "size": 1742,
"mode": "100644",
"source": "pidgeon-docs/api-reference/validate.mdx",
"license": "Pidgeon-Public-Documentation"
},
+ {
+ "path": "cli/ai-commands.mdx",
+ "sha256": "c88f3d6f3e6e3a18bf1c4d125599d9ce391768ee8e858867219a3e5607a7c551",
+ "size": 5365,
+ "mode": "100644",
+ "source": "pidgeon-docs/cli/ai-commands.mdx",
+ "license": "Pidgeon-Public-Documentation"
+ },
{
"path": "cli/config-commands.mdx",
- "sha256": "596434fa917b5b5c67599d82e9ec59ffdcf8d6e6115605cfa3332a09140c4da8",
- "size": 2182,
+ "sha256": "bc4e2fd7d08658d2865bd9fb5d3a7edea42972dbff236d1b4f24357e889f0a68",
+ "size": 2416,
"mode": "100644",
"source": "pidgeon-docs/cli/config-commands.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "cli/conform-commands.mdx",
- "sha256": "8c4aa821f091001c8e106fccb42758b4c64aca7a70bf7ddaeb954946108de271",
- "size": 3833,
+ "sha256": "4d0642e4e9dc993365391b22feeaa6142f1185ee15c3de6b7b4d71140089f568",
+ "size": 5836,
"mode": "100644",
"source": "pidgeon-docs/cli/conform-commands.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "cli/data-commands.mdx",
- "sha256": "ea4adc14c9f195ae51cf7544d95c9e3e32b30433bbef2ce3a63326198f515680",
- "size": 1959,
+ "sha256": "3cf2520064faf1d9d175f3d15707c54437be3ca22d08335e635934129973e73a",
+ "size": 4245,
"mode": "100644",
"source": "pidgeon-docs/cli/data-commands.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "cli/flock-commands.mdx",
- "sha256": "0dbf8f73a4a79e1f382b6200ee684167348fab9773dc49c84c69fcd8d7e8eb09",
- "size": 2586,
+ "sha256": "b61bae0b6891705f99af9f3d161f5a1ca6b6728becea18a92610628f693eef19",
+ "size": 4587,
"mode": "100644",
"source": "pidgeon-docs/cli/flock-commands.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "cli/global-options.mdx",
- "sha256": "c70b2b98d87c48a829008642a56a26b6bb4218d47febebf8ddfba4907e8e98b7",
- "size": 1908,
+ "sha256": "db6887ef283cde53b9bb969eb86db121fe6d447fa94f51ab8f210374346483fa",
+ "size": 1905,
"mode": "100644",
"source": "pidgeon-docs/cli/global-options.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "cli/loft-commands.mdx",
- "sha256": "a163dda3d0bcf2e802e8ae512671477deed5536fa9b9586019d9652dc0360471",
- "size": 1980,
+ "sha256": "ea73c87377c66178fcfa1ddfcc98f63b0545b32e02197c153ca4e5c772f4d4be",
+ "size": 3401,
"mode": "100644",
"source": "pidgeon-docs/cli/loft-commands.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "cli/migrate-commands.mdx",
- "sha256": "df00e4c61f4b54d2fd20ec49c589232740fb27110bd97a329388db620c247fd8",
- "size": 4040,
+ "sha256": "9f68db07dc32454e54945d49c25720a167e9cbebabc066726d0180e70ed883ac",
+ "size": 4114,
"mode": "100644",
"source": "pidgeon-docs/cli/migrate-commands.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "cli/post-commands.mdx",
- "sha256": "fd9c8c58c637283f549567b889dde9a84dc03ba0d0a4ed88f50634ccde2f6d61",
- "size": 5141,
+ "sha256": "43541914604eccdcae85926385d7820e5a47da1f6ab7a14448349728e2e6b9ac",
+ "size": 6459,
"mode": "100644",
"source": "pidgeon-docs/cli/post-commands.mdx",
"license": "Pidgeon-Public-Documentation"
},
+ {
+ "path": "conform/cms-0057-f.mdx",
+ "sha256": "4f636692ff10e5bdd840bfe792cfa19d6558162c09c15f553fd3d431c687eff1",
+ "size": 2802,
+ "mode": "100644",
+ "source": "pidgeon-docs/conform/cms-0057-f.mdx",
+ "license": "Pidgeon-Public-Documentation"
+ },
+ {
+ "path": "conform/evidence-and-ci.mdx",
+ "sha256": "ca1572797720653cf75329ce3d32eefd5fe7fd0b4724e280e27f2b47e0f48fa2",
+ "size": 3324,
+ "mode": "100644",
+ "source": "pidgeon-docs/conform/evidence-and-ci.mdx",
+ "license": "Pidgeon-Public-Documentation"
+ },
+ {
+ "path": "conform/overview.mdx",
+ "sha256": "af06eb8ff4a13fa9e4f078c1b3490e84150acbdb37b8cebb63bc74f4e391eff0",
+ "size": 3572,
+ "mode": "100644",
+ "source": "pidgeon-docs/conform/overview.mdx",
+ "license": "Pidgeon-Public-Documentation"
+ },
+ {
+ "path": "conform/running-conformance.mdx",
+ "sha256": "a4a391609a408cda1baee29237d0a15a3d4f8025fb3a823bce94f126792f63e3",
+ "size": 2886,
+ "mode": "100644",
+ "source": "pidgeon-docs/conform/running-conformance.mdx",
+ "license": "Pidgeon-Public-Documentation"
+ },
{
"path": "docs.json",
- "sha256": "de68861c2ab24e688b309ccac4aed3c41a7025dea09c3ec08fe876229146b32f",
- "size": 6004,
+ "sha256": "bb9c197b922fb31d204dcbdd34af75b4325f80a1c2c4ae1784d243a3b81b0b72",
+ "size": 6670,
"mode": "100644",
"source": "pidgeon-docs/docs.json",
"license": "Pidgeon-Public-Documentation"
@@ -253,44 +317,52 @@
},
{
"path": "flock/output-formats.mdx",
- "sha256": "dc0b17fd155e62c091f826ec98a0502af70935639003b2b4a2530bd1166e4559",
- "size": 2279,
+ "sha256": "8db6f09ad03907c94a5363fb2ac3c111261fd64a42628f5291688132c4ff04ee",
+ "size": 2669,
"mode": "100644",
"source": "pidgeon-docs/flock/output-formats.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "flock/overview.mdx",
- "sha256": "9797dd84c4c16a89100259efaadf644d838a935d61cc0ad28417f112ef55c330",
- "size": 1767,
+ "sha256": "d73707953d827ed341eaf19c4f5aa0ca5e393a7d70d138cf8a61448c36b59c5f",
+ "size": 3707,
"mode": "100644",
"source": "pidgeon-docs/flock/overview.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "flock/population-generation.mdx",
- "sha256": "cc0c4e20500efb09e25f6e6cbda06f7d6e3949dd828c433a63a1f10725695632",
- "size": 1668,
+ "sha256": "38eabf1d2e3a2503544138b32a4df6484ba83d430e2ed0b833514faca5db3355",
+ "size": 2601,
"mode": "100644",
"source": "pidgeon-docs/flock/population-generation.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "flock/schema-intelligence.mdx",
- "sha256": "047b3bc23da073368601223e35b28cc04c2b08aa04461ae2772450a782049373",
- "size": 1355,
+ "sha256": "8297d5a2217e6a418160233bef5e219be2a2f16051614c2125d8441642e07df4",
+ "size": 2151,
"mode": "100644",
"source": "pidgeon-docs/flock/schema-intelligence.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "getting-started/account.mdx",
- "sha256": "bae24147256fc56dd965daa8b7760f6e142edc5a80daa967d39dc85aa05f647a",
- "size": 3627,
+ "sha256": "235b29e94402c2033dc6b6318526ec86b41166f4e27fc0eb330114bd24682af6",
+ "size": 3064,
"mode": "100644",
"source": "pidgeon-docs/getting-started/account.mdx",
"license": "Pidgeon-Public-Documentation"
},
+ {
+ "path": "getting-started/conform.mdx",
+ "sha256": "a38706a045606f7cf359b57f1754d92f046c0deca25d71253f83ea7b3ebcd495",
+ "size": 2823,
+ "mode": "100644",
+ "source": "pidgeon-docs/getting-started/conform.mdx",
+ "license": "Pidgeon-Public-Documentation"
+ },
{
"path": "getting-started/flock.mdx",
"sha256": "79ae15fbfb40b79ebdde71db6f4fb61ae3342619c05a16ab8238060b3c322c79",
@@ -299,50 +371,58 @@
"source": "pidgeon-docs/getting-started/flock.mdx",
"license": "Pidgeon-Public-Documentation"
},
+ {
+ "path": "getting-started/install-linux.mdx",
+ "sha256": "e84c705caf714680ce9a22009f27c003ecad9a7b8c5114e59169c53c7482618f",
+ "size": 3062,
+ "mode": "100644",
+ "source": "pidgeon-docs/getting-started/install-linux.mdx",
+ "license": "Pidgeon-Public-Documentation"
+ },
{
"path": "getting-started/install-macos.mdx",
- "sha256": "67e555f4163ce77e56d9a2ec2b5ee50648239dd7e700f0f4b10bc439d2a6a546",
- "size": 2736,
+ "sha256": "87a6c68c442b428889b410ba2282f4ad0ae91d894316a21686c00ad87df6af15",
+ "size": 2993,
"mode": "100644",
"source": "pidgeon-docs/getting-started/install-macos.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "getting-started/install-windows.mdx",
- "sha256": "e57c20a9ec583201507ab3632ab65a7de2fe008534cd81c211e3da123e2dcb6e",
- "size": 4638,
+ "sha256": "b7d8a92f61a6cb536fe5ebe06da89626ca40d5c97aea0b622a589db258c3312b",
+ "size": 4795,
"mode": "100644",
"source": "pidgeon-docs/getting-started/install-windows.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "getting-started/introduction.mdx",
- "sha256": "9f2605ab71324fad1434fc9b7ec29568a3102581acce7320875ad54adb14e86f",
- "size": 4662,
+ "sha256": "ca173efde85704a7f356803d116da90176917b77c4609c6616803dc53e818919",
+ "size": 5235,
"mode": "100644",
"source": "pidgeon-docs/getting-started/introduction.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "getting-started/launcher.mdx",
- "sha256": "1c3b4879e100687060525f93a4db55b129fdf174ad15fefabf94f1f1b6eb049b",
- "size": 3002,
+ "sha256": "b131f4399b6c9bcc47fcdac2d2f2a7878df83d953ab15bd8c57d947178ba10b1",
+ "size": 2978,
"mode": "100644",
"source": "pidgeon-docs/getting-started/launcher.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "getting-started/loft.mdx",
- "sha256": "25157ec00514f783fc2f636e047601e60af13c31698ddc6ab0c21f269368b32d",
- "size": 3524,
+ "sha256": "3624e64a28a0510a39c8380ac7130369cf9fb6412910c89de55eb0adac3b507d",
+ "size": 3519,
"mode": "100644",
"source": "pidgeon-docs/getting-started/loft.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "getting-started/migrate.mdx",
- "sha256": "f4e2f1929f435d5101a30f8f9663bb0ebeaeed907e773dc08d0b42068597b237",
- "size": 2909,
+ "sha256": "3cf83deebe85f081daa92a643106978340985f0178a2724eb0458ef7b03e2d10",
+ "size": 3043,
"mode": "100644",
"source": "pidgeon-docs/getting-started/migrate.mdx",
"license": "Pidgeon-Public-Documentation"
@@ -357,60 +437,92 @@
},
{
"path": "getting-started/quickstart-cli.mdx",
- "sha256": "ee6e75a9a11fc2b25dbf7b146fc2cf464a597b3da8c42c90f80587fae7621146",
- "size": 3884,
+ "sha256": "a0be02e2228af6ea6a919b68ab39e7a1ed7759f5221700261be9e09c8f8ae75f",
+ "size": 4307,
"mode": "100644",
"source": "pidgeon-docs/getting-started/quickstart-cli.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "getting-started/quickstart-desktop.mdx",
- "sha256": "b3c64ecca11a1fb2f4dc2e9560f1073236e861910409376fa56857683bf19b34",
- "size": 2761,
+ "sha256": "a0ef6e2ba544b68e3dc910e30155f4cd6e6a77fb799b92ebfba44be50f720c7f",
+ "size": 3247,
"mode": "100644",
"source": "pidgeon-docs/getting-started/quickstart-desktop.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "guides/build-test-scenarios.mdx",
- "sha256": "4a0f7ae5cffd74c3c19a59b96ed85a23f41d389e25a4bd2ae0c7b7c840db50cd",
- "size": 3473,
+ "sha256": "d630bf753180835bcc688b6a88345654004b0123dcce255f9768f36221adbbcb",
+ "size": 3461,
"mode": "100644",
"source": "pidgeon-docs/guides/build-test-scenarios.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "guides/de-identify-real-messages.mdx",
- "sha256": "a05ab9205d58bac803d11a544ba48575c40f811ddd1c9a52b9beb8d3d0e14880",
- "size": 3743,
+ "sha256": "dfa2678c12ee201c747babc8798b7d9780ce4709b30e472157b63fb10108b6be",
+ "size": 3750,
"mode": "100644",
"source": "pidgeon-docs/guides/de-identify-real-messages.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "guides/generate-realistic-test-data.mdx",
- "sha256": "2c52393f7dd6968676d30d17795877c0a46c07b3fedd72837d940e7fac7202c5",
- "size": 3383,
+ "sha256": "9a0790b2183b0cd624c27d12c3116623f19f5ee70c8c2cfc56cbff7852de44f3",
+ "size": 3374,
"mode": "100644",
"source": "pidgeon-docs/guides/generate-realistic-test-data.mdx",
"license": "Pidgeon-Public-Documentation"
},
+ {
+ "path": "guides/healthcare-interface-test-data-field-guide.mdx",
+ "sha256": "b1f710379fd4c767c5a5be9ab13e7919e77563e37af10bec8233edbdb1965cbd",
+ "size": 3301,
+ "mode": "100644",
+ "source": "pidgeon-docs/guides/healthcare-interface-test-data-field-guide.mdx",
+ "license": "Pidgeon-Public-Documentation"
+ },
+ {
+ "path": "guides/local-first-human-agent-workflow.mdx",
+ "sha256": "90c97da640b0fd42555df090db3152a4f14d98a2a1afdd166ef8237c6b6af67a",
+ "size": 2867,
+ "mode": "100644",
+ "source": "pidgeon-docs/guides/local-first-human-agent-workflow.mdx",
+ "license": "Pidgeon-Public-Documentation"
+ },
{
"path": "guides/monitor-mirth-with-loft.mdx",
- "sha256": "53003b9a10fcae411aa0b7a928dfbc5f6b0ceb1fa8515ccbd62c0e2a7b97c8bc",
- "size": 3784,
+ "sha256": "d3e99a0c3b60d2a0692b0f38f7fcc98808c7482c688fa3ae932534eccd4c6bb6",
+ "size": 3854,
"mode": "100644",
"source": "pidgeon-docs/guides/monitor-mirth-with-loft.mdx",
"license": "Pidgeon-Public-Documentation"
},
+ {
+ "path": "guides/public-packages-quickstart.mdx",
+ "sha256": "c49e212521408b02d468c13bfe85496dfa2597b846b86f98919a0eaaa1d25892",
+ "size": 3232,
+ "mode": "100644",
+ "source": "pidgeon-docs/guides/public-packages-quickstart.mdx",
+ "license": "Pidgeon-Public-Documentation"
+ },
{
"path": "guides/seed-database-with-flock.mdx",
- "sha256": "6f8b1236e30903ec26e8f0e696fc543b89bba4b324524865142c529c98821107",
- "size": 3887,
+ "sha256": "f245e2aacb7e0ea7291f7f60834d5517c15be6b83b1f8ba70677124cc7e4d8c7",
+ "size": 4507,
"mode": "100644",
"source": "pidgeon-docs/guides/seed-database-with-flock.mdx",
"license": "Pidgeon-Public-Documentation"
},
+ {
+ "path": "images/brand/icons/conform.png",
+ "sha256": "b49b0efc59e15d29dcce1e944e07d2c303758c42ca33214d7d2051dfc687ae24",
+ "size": 7565,
+ "mode": "100644",
+ "source": "pidgeon-docs/images/brand/icons/conform.png",
+ "license": "Pidgeon-Public-Documentation"
+ },
{
"path": "images/brand/icons/flock.png",
"sha256": "501565fccaad503595129b39f6b0c228ed521759b768e7f084df33220e728d83",
@@ -421,8 +533,8 @@
},
{
"path": "images/brand/icons/loft.png",
- "sha256": "b28d0398438e52cd78e854008bec91b0c9c81687e7bf3277f3f00d7c089949e7",
- "size": 6872,
+ "sha256": "6f0dec8d97abd12532c8df1c01d8c8c5b0e1de281cbec4cb3aa74dac14e8bdc8",
+ "size": 7864,
"mode": "100644",
"source": "pidgeon-docs/images/brand/icons/loft.png",
"license": "Pidgeon-Public-Documentation"
@@ -451,6 +563,14 @@
"source": "pidgeon-docs/images/brand/icons/post.png",
"license": "Pidgeon-Public-Documentation"
},
+ {
+ "path": "images/brand/wordmarks/conform.png",
+ "sha256": "9e5ccfd2c8bec7e23d2a3cd261eefb825d7d0ef93ce7bdc23f485135a5b00347",
+ "size": 47693,
+ "mode": "100644",
+ "source": "pidgeon-docs/images/brand/wordmarks/conform.png",
+ "license": "Pidgeon-Public-Documentation"
+ },
{
"path": "images/brand/wordmarks/flock.png",
"sha256": "b1447ded08db93a3449f74aa6a72f46fd61d8be646646cd41aa84e45fb18ba27",
@@ -461,8 +581,8 @@
},
{
"path": "images/brand/wordmarks/loft.png",
- "sha256": "8c29289ee712656bbf2a0cbc0675964289326b79ce22ed39da57e9b9ea16526b",
- "size": 11227,
+ "sha256": "9cf3d005ea7dd55f2bcfcb235141dbb4805f227b84dfcc09b8c88672d4ef21e6",
+ "size": 16788,
"mode": "100644",
"source": "pidgeon-docs/images/brand/wordmarks/loft.png",
"license": "Pidgeon-Public-Documentation"
@@ -493,32 +613,32 @@
},
{
"path": "index.mdx",
- "sha256": "d79c9751b5fe3d7c4e826ff15b82b944d890cb52dc6799a1e224fcac71ff05d1",
- "size": 2156,
+ "sha256": "756e6c14dbb550f694596f09d9460f86c3124643bb1dc1e270efca2d7d40da5d",
+ "size": 2591,
"mode": "100644",
"source": "pidgeon-docs/index.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "loft/alerting.mdx",
- "sha256": "618bd9683c04b2ea184dd12986052b11d1ff9642a4e3aad5ca8d31a9368df331",
- "size": 2107,
+ "sha256": "75f522891e63855ece680cd58189e235a0da5f956e6b9f96df9208b9e0f5f912",
+ "size": 2596,
"mode": "100644",
"source": "pidgeon-docs/loft/alerting.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "loft/interface-monitoring.mdx",
- "sha256": "38d0bd0dde41c89869ed0801c982b80e081c67408a7087a70298b04768f3b02f",
- "size": 1602,
+ "sha256": "82fb0870f0f214af30412faec44ed4578a55753522cd1a3249b89466c32f03cf",
+ "size": 2183,
"mode": "100644",
"source": "pidgeon-docs/loft/interface-monitoring.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "loft/overview.mdx",
- "sha256": "4383bc469dc526a8c9ea318de0e637702a82f9f90d4d412095354704d67f585a",
- "size": 1791,
+ "sha256": "871a7227b3e42d77813b55ad968f896e1e73be703baf1a0bb35fe85aff9d519d",
+ "size": 2110,
"mode": "100644",
"source": "pidgeon-docs/loft/overview.mdx",
"license": "Pidgeon-Public-Documentation"
@@ -533,72 +653,104 @@
},
{
"path": "mcp/overview.mdx",
- "sha256": "53506bd93254492f5de891f36b82bd3c77f9fb33765ba725e90dcea37e8189ce",
- "size": 5875,
+ "sha256": "5605bd163b44e0c89d93b9258dadcd7e612d4b99b4b4846e2bedb3b34d3b8819",
+ "size": 6037,
"mode": "100644",
"source": "pidgeon-docs/mcp/overview.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "mcp/tools.mdx",
- "sha256": "fa84e5db95960272ee17e7e202f6f72f436d2446d93705f2e484a4ed0287cbe1",
- "size": 4449,
+ "sha256": "0f43ded8fcbd485bf80a38607dbd4435788ef19e3fb552f3ff21e7efe83387a9",
+ "size": 4430,
"mode": "100644",
"source": "pidgeon-docs/mcp/tools.mdx",
"license": "Pidgeon-Public-Documentation"
},
+ {
+ "path": "migrate/bulk-data.mdx",
+ "sha256": "a10ba7b6ee570da72a0723509dc685954a27ca23e85208830f97fa5e4fe55f6e",
+ "size": 2136,
+ "mode": "100644",
+ "source": "pidgeon-docs/migrate/bulk-data.mdx",
+ "license": "Pidgeon-Public-Documentation"
+ },
+ {
+ "path": "migrate/mapping.mdx",
+ "sha256": "1184bda1f25754501938f0d1c30c728ffb0b234b713f0ae14a8515846c76ac06",
+ "size": 1656,
+ "mode": "100644",
+ "source": "pidgeon-docs/migrate/mapping.mdx",
+ "license": "Pidgeon-Public-Documentation"
+ },
+ {
+ "path": "migrate/overview.mdx",
+ "sha256": "57299219c373ad1fb9433536c048efc5fe3a02233a4cf85d657c38657fb47558",
+ "size": 2407,
+ "mode": "100644",
+ "source": "pidgeon-docs/migrate/overview.mdx",
+ "license": "Pidgeon-Public-Documentation"
+ },
{
"path": "post/ai-triage.mdx",
- "sha256": "4bdb6f3fd8703efa50ee7d29d40418f765bd15146ce3cd3265257304f87f9935",
- "size": 1797,
+ "sha256": "202d081724c1608854d2e0aa5f5ec4de2d4222f4eb03cd1f4f9d356fb29a156e",
+ "size": 2318,
"mode": "100644",
"source": "pidgeon-docs/post/ai-triage.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "post/datasets.mdx",
- "sha256": "32ad047d63361fadd3599e0d1c4361040d12677dcb5166399c8dd5dcef3447d0",
- "size": 1623,
+ "sha256": "6b5c489061ea708626ea5cddff2b2d388a2c5baa5bec19b8e7259c488eb2a7c8",
+ "size": 1952,
"mode": "100644",
"source": "pidgeon-docs/post/datasets.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "post/de-identification.mdx",
- "sha256": "cbdf04dfa30bcca1d550bc71735ccb739dac6669302b848cee5052e9c5ad663e",
- "size": 3642,
+ "sha256": "0c3ac8b281ea0d3aa9957aab1b8f01c9d3c05ae9b2fbdd8e683acdb014c4e941",
+ "size": 3613,
"mode": "100644",
"source": "pidgeon-docs/post/de-identification.mdx",
"license": "Pidgeon-Public-Documentation"
},
+ {
+ "path": "post/diff.mdx",
+ "sha256": "37d847fc359ddc6af87a41df455fb751645197028781f38647a5bc48631f3250",
+ "size": 3012,
+ "mode": "100644",
+ "source": "pidgeon-docs/post/diff.mdx",
+ "license": "Pidgeon-Public-Documentation"
+ },
{
"path": "post/message-generation.mdx",
- "sha256": "51d0ce490dac819b5825c57b69f955187fa5a7563d3f1c44f0777490223a6d92",
- "size": 7837,
+ "sha256": "3fc927c34d30afcf77661970b2b318118c8a5757325865584d6b555fea3bb6eb",
+ "size": 8095,
"mode": "100644",
"source": "pidgeon-docs/post/message-generation.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "post/validation.mdx",
- "sha256": "54faf41c3d3927a1b8c75989c80a3609563562900f9080f3e7524b68846c28cb",
- "size": 3929,
+ "sha256": "32bf0c0faa9f05b9ae817c81463136e4d592460f3a2956d43a14f9d912fca361",
+ "size": 3914,
"mode": "100644",
"source": "pidgeon-docs/post/validation.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "post/vendor-profiles.mdx",
- "sha256": "f60b2cdfe93c1e87d1dbaca33a56c07b9f35269a18a8687f8fd1083dffdec269",
- "size": 1824,
+ "sha256": "ac5fa89f0ba5ff5cbc8390f590f73267eb6935ef1f7f478878d1b1e7c7034d0b",
+ "size": 1821,
"mode": "100644",
"source": "pidgeon-docs/post/vendor-profiles.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "post/workflow-wizard.mdx",
- "sha256": "281ba2e608af0fa6c017f27f1f3a6b6086b02570ee9289490ee19f28669611d2",
- "size": 1597,
+ "sha256": "03f47982e04fe640cf1074ac3a9cdbed53658bebaf6c7d6b4af26c64b935c385",
+ "size": 1656,
"mode": "100644",
"source": "pidgeon-docs/post/workflow-wizard.mdx",
"license": "Pidgeon-Public-Documentation"
@@ -621,24 +773,24 @@
},
{
"path": "support/faq.mdx",
- "sha256": "742ef45f4598d8f1bb1751350c7cf61e3892854b0b7292d730737e2bc705fb8c",
- "size": 4202,
+ "sha256": "69523466b716663ea3237a59d6278f07cfad9dfe166951401f957212a3b056fe",
+ "size": 4406,
"mode": "100644",
"source": "pidgeon-docs/support/faq.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "support/known-issues.mdx",
- "sha256": "6480991e9787f4baebba1b6ebaab752ea9793612e1c78cd2b95aed55e907b7b7",
- "size": 1769,
+ "sha256": "d6cdc893b6dbb40a1b037972ddc15e2f7e3380cfd34d534433a93528e50acc5d",
+ "size": 1859,
"mode": "100644",
"source": "pidgeon-docs/support/known-issues.mdx",
"license": "Pidgeon-Public-Documentation"
},
{
"path": "support/troubleshooting.mdx",
- "sha256": "cc752eb2831a018d0c2a3ec160ca9fd306690a32c54c31c7989415b1697fe343",
- "size": 6273,
+ "sha256": "c7ad19d4c154956c6fb4a90a4d496e8624de48306c8b16cc8cdb29fd44876f34",
+ "size": 6808,
"mode": "100644",
"source": "pidgeon-docs/support/troubleshooting.mdx",
"license": "Pidgeon-Public-Documentation"
diff --git a/api-reference/admin.mdx b/api-reference/admin.mdx
deleted file mode 100644
index ef47190..0000000
--- a/api-reference/admin.mdx
+++ /dev/null
@@ -1,121 +0,0 @@
----
-title: Admin API
-description: RBAC role management, workspace operations, and SLA definitions — requires LoftAdmin authorization.
----
-
-All admin endpoints require the `LoftAdmin` authorization policy. Include a JWT or API key with admin privileges.
-
-## RBAC Management
-
-### GET /api/loft/admin/roles
-
-List organization role assignments.
-
-```bash curl
-curl -H "Authorization: Bearer YOUR_JWT" \
- http://localhost:5100/api/loft/admin/roles
-```
-
-### POST /api/loft/admin/roles
-
-Assign a role to a user.
-
-```bash curl
-curl -X POST http://localhost:5100/api/loft/admin/roles \
- -H "Authorization: Bearer YOUR_JWT" \
- -H "Content-Type: application/json" \
- -d '{"userId": "user-uuid", "role": "LoftOperator"}'
-```
-
-### DELETE /api/loft/admin/roles/{userId}
-
-Revoke a user's role.
-
-```bash curl
-curl -X DELETE -H "Authorization: Bearer YOUR_JWT" \
- http://localhost:5100/api/loft/admin/roles/user-uuid
-```
-
----
-
-## Workspace Management
-
-### GET /api/loft/admin/workspaces
-
-List workspaces.
-
-```bash curl
-curl -H "Authorization: Bearer YOUR_JWT" \
- http://localhost:5100/api/loft/admin/workspaces
-```
-
-### POST /api/loft/admin/workspaces
-
-Create a workspace.
-
-```bash curl
-curl -X POST http://localhost:5100/api/loft/admin/workspaces \
- -H "Authorization: Bearer YOUR_JWT" \
- -H "Content-Type: application/json" \
- -d '{"name": "East Region", "description": "East region interfaces"}'
-```
-
-### POST /api/loft/admin/workspaces/{id}/members
-
-Add a member to a workspace.
-
-```bash curl
-curl -X POST http://localhost:5100/api/loft/admin/workspaces/ws-001/members \
- -H "Authorization: Bearer YOUR_JWT" \
- -H "Content-Type: application/json" \
- -d '{"userId": "user-uuid", "role": "LoftViewer"}'
-```
-
-### POST /api/loft/admin/workspaces/{id}/interfaces
-
-Add an interface to a workspace.
-
-```bash curl
-curl -X POST http://localhost:5100/api/loft/admin/workspaces/ws-001/interfaces \
- -H "Authorization: Bearer YOUR_JWT" \
- -H "Content-Type: application/json" \
- -d '{"interfaceId": "intf-001"}'
-```
-
----
-
-## SLA Management
-
-### GET /api/loft/admin/sla/{interfaceId}
-
-Get SLA definition for an interface.
-
-```bash curl
-curl -H "Authorization: Bearer YOUR_JWT" \
- http://localhost:5100/api/loft/admin/sla/intf-001
-```
-
-### POST /api/loft/admin/sla
-
-Create an SLA definition.
-
-```bash curl
-curl -X POST http://localhost:5100/api/loft/admin/sla \
- -H "Authorization: Bearer YOUR_JWT" \
- -H "Content-Type: application/json" \
- -d '{"interfaceId": "intf-001", "uptimeTarget": 99.9, "maxResponseMs": 500, "alertThresholdPercent": 5}'
-```
-
-### GET /api/loft/admin/sla/{interfaceId}/report
-
-Get SLA compliance report.
-
-| Query Param | Type | Description |
-|-------------|------|-------------|
-| `from` | ISO 8601 | Report start |
-| `to` | ISO 8601 | Report end |
-
-```bash curl
-curl -H "Authorization: Bearer YOUR_JWT" \
- "http://localhost:5100/api/loft/admin/sla/intf-001/report?from=2026-02-01&to=2026-02-22"
-```
diff --git a/api-reference/ai-triage.mdx b/api-reference/ai-triage.mdx
index 5dae446..5aa4033 100644
--- a/api-reference/ai-triage.mdx
+++ b/api-reference/ai-triage.mdx
@@ -3,7 +3,7 @@ title: AI Triage
description: AI-powered failure analysis, pattern detection, and vendor upgrade checking via the Bridge API.
---
-Four endpoints for AI-assisted analysis of message failures. All **public** — no authentication required.
+Four endpoints for AI-assisted analysis of message failures. AI Triage is a **Post Pro feature**. These Bridge routes are unauthenticated because the Bridge is a single-user loopback sidecar: it listens only on `localhost` for the signed-in user, so there is no network surface to authenticate against. The feature entitlement is enforced in the app, not on the loopback route.
## POST /api/loft/triage
diff --git a/api-reference/analytics.mdx b/api-reference/analytics.mdx
index fbf2d68..be128c2 100644
--- a/api-reference/analytics.mdx
+++ b/api-reference/analytics.mdx
@@ -3,7 +3,9 @@ title: Analytics
description: Time-series queries, dashboards, reports, and CSV exports for Loft interface analytics.
---
-Seven endpoints for analytics and reporting. All **public**.
+Seven endpoints for analytics and reporting.
+
+Loft is a Pro product. These routes are served by the Loft desktop app's local Bridge on loopback (`localhost:5100`) for the signed-in user, which resolves the Professional tier locally, so a local call needs no API key. This is not a hosted API and is not reachable from another machine. A request below the Professional tier returns `402`, never a hard `403`.
## GET /api/loft/analytics/timeseries
@@ -11,7 +13,7 @@ Query time-series data for an interface.
| Query Param | Type | Default | Description |
|-------------|------|---------|-------------|
-| `interfaceId` | string | — | Filter to specific interface |
+| `interfaceId` | string | all | Filter to a specific interface |
| `since` | ISO 8601 | 24h ago | Start time |
| `until` | ISO 8601 | Now | End time |
| `granularity` | string | `"oneHour"` | `oneMinute`, `oneHour`, `oneDay` |
@@ -41,7 +43,7 @@ curl "http://localhost:5100/api/loft/analytics/topn?metric=messagesFailed&n=5"
## POST /api/loft/analytics/query
-Custom filter query with advanced criteria.
+Custom filter query with additional criteria.
```bash curl
curl -X POST http://localhost:5100/api/loft/analytics/query \
@@ -91,7 +93,7 @@ Export analytics data as CSV.
| Query Param | Type | Default | Description |
|-------------|------|---------|-------------|
-| `interfaceId` | string | — | Interface to export |
+| `interfaceId` | string | all | Interface to export |
| `since` | ISO 8601 | 24h ago | Start time |
| `until` | ISO 8601 | Now | End time |
| `granularity` | string | `"oneHour"` | Data resolution |
diff --git a/api-reference/diff.mdx b/api-reference/diff.mdx
index cd2ab8e..a483699 100644
--- a/api-reference/diff.mdx
+++ b/api-reference/diff.mdx
@@ -5,7 +5,7 @@ description: Compare two healthcare messages field-by-field via the Bridge API.
## POST /api/diff
-Compare two messages and return field-level differences. **Public** — no authentication required.
+Compare two messages and return field-level differences. Diff is a **Post Pro feature**. The Bridge route is unauthenticated because the Bridge is a single-user loopback sidecar; the Pro entitlement is enforced in the app, not on the loopback route.
### Request Body
diff --git a/api-reference/enterprise.mdx b/api-reference/enterprise.mdx
deleted file mode 100644
index a9d5545..0000000
--- a/api-reference/enterprise.mdx
+++ /dev/null
@@ -1,148 +0,0 @@
----
-title: Enterprise API
-description: Observability, SSO configuration, audit logs, feature flags, and health check endpoints.
----
-
-## Observability
-
-Requires `LoftAdmin` authorization.
-
-### GET /api/admin/observability/sla/{orgId}
-
-Get organization-level SLA overview.
-
-```bash curl
-curl -H "Authorization: Bearer YOUR_JWT" \
- "http://localhost:5100/api/admin/observability/sla/org-uuid?from=2026-02-01&to=2026-02-22"
-```
-
-### GET /api/admin/observability/sla/{orgId}/violations
-
-Get SLA violations for an organization.
-
-```bash curl
-curl -H "Authorization: Bearer YOUR_JWT" \
- "http://localhost:5100/api/admin/observability/sla/org-uuid/violations?from=2026-02-01"
-```
-
-### GET /api/admin/observability/metrics/cost
-
-Get infrastructure cost metrics.
-
-```bash curl
-curl -H "Authorization: Bearer YOUR_JWT" \
- http://localhost:5100/api/admin/observability/metrics/cost
-```
-
----
-
-## SSO Configuration
-
-Requires `LoftAdmin` authorization.
-
-### GET /api/loft/sso/providers
-
-List configured SSO providers.
-
-```bash curl
-curl -H "Authorization: Bearer YOUR_JWT" \
- http://localhost:5100/api/loft/sso/providers
-```
-
-### POST /api/loft/sso/configure
-
-Configure an SSO provider.
-
-```bash curl
-curl -X POST http://localhost:5100/api/loft/sso/configure \
- -H "Authorization: Bearer YOUR_JWT" \
- -H "Content-Type: application/json" \
- -d '{
- "providerType": "oidc",
- "displayName": "Corporate SSO",
- "clientId": "your-client-id",
- "clientSecret": "your-client-secret",
- "issuerUrl": "https://login.corp.com",
- "jitProvisioning": true
- }'
-```
-
-### DELETE /api/loft/sso/providers/{providerType}
-
-Remove an SSO provider.
-
-```bash curl
-curl -X DELETE -H "Authorization: Bearer YOUR_JWT" \
- http://localhost:5100/api/loft/sso/providers/oidc
-```
-
----
-
-## Audit Logs
-
-Requires `LoftAdmin` authorization.
-
-### GET /api/loft/audit/
-
-Query audit logs.
-
-| Query Param | Type | Description |
-|-------------|------|-------------|
-| `action` | string | Filter by action type |
-| `resourceType` | string | Filter by resource |
-| `from` | ISO 8601 | Start time |
-| `to` | ISO 8601 | End time |
-| `limit` | int | Max results |
-| `offset` | int | Pagination offset |
-
-```bash curl
-curl -H "Authorization: Bearer YOUR_JWT" \
- "http://localhost:5100/api/loft/audit/?action=role.assign&limit=50"
-```
-
-### GET /api/loft/audit/export
-
-Export audit logs as CSV or JSON.
-
-```bash curl
-curl -H "Authorization: Bearer YOUR_JWT" \
- "http://localhost:5100/api/loft/audit/export?format=csv&from=2026-02-01" \
- -o audit.csv
-```
-
----
-
-## Feature Flags
-
-### GET /api/features
-
-Get feature flags. **Public** — returns org-specific flags if authenticated, global flags otherwise.
-
-```bash curl
-curl http://localhost:5100/api/features
-```
-
----
-
-## Health Check
-
-### GET /api/health
-
-Health check endpoint. **Public**.
-
-```bash curl
-curl http://localhost:5100/api/health
-```
-
-```json
-{
- "status": "healthy",
- "timestamp": "2026-02-22T14:30:00Z",
- "version": "1.0.0",
- "uptimeSeconds": 86400,
- "checks": {
- "database": "healthy",
- "cache": "healthy"
- }
-}
-```
diff --git a/api-reference/flock.mdx b/api-reference/flock.mdx
index 74505f4..82f5f6a 100644
--- a/api-reference/flock.mdx
+++ b/api-reference/flock.mdx
@@ -1,9 +1,9 @@
---
title: Flock API
-description: Synthetic population generation endpoints — connect to databases, learn patterns, generate populations, and seed data.
+description: "Synthetic population generation endpoints on the local Flock Bridge: connect to a database, learn distributions, generate a population, and seed data."
---
-Twelve endpoints for synthetic population generation. All **public**.
+These endpoints are served by the Flock Bridge sidecar on `localhost:5102`. The Bridge listens only on loopback for the signed-in user, so the routes are unauthenticated locally. Flock itself is a Pro feature and requires a Pidgeon account.
## POST /api/flock/connect
@@ -11,7 +11,7 @@ Connect to a database and analyze its schema.
| Field | Type | Description |
|-------|------|-------------|
-| `provider` | string | `postgres`, `mysql`, `sqlserver` |
+| `provider` | string | `postgres`, `sqlserver`, `mysql` |
| `connectionString` | string | Database connection string |
```bash curl
@@ -30,12 +30,16 @@ curl http://localhost:5102/api/flock/schema
## POST /api/flock/learn
-Learn statistical patterns from existing sample data.
+Learn statistical distributions from existing rows.
+
+| Field | Type | Default | Description |
+|-------|------|---------|-------------|
+| `sampleSize` | int | `500` | Rows to sample per table |
```bash curl
curl -X POST http://localhost:5102/api/flock/learn \
-H "Content-Type: application/json" \
- -d '{"tables": ["patients", "encounters"], "sampleSize": 500}'
+ -d '{"sampleSize": 500}'
```
## GET /api/flock/profiles
@@ -60,15 +64,16 @@ Start a generation job. Returns a job ID for polling.
| Field | Type | Default | Description |
|-------|------|---------|-------------|
-| `count` | int | `100` | Number of patients |
-| `format` | string | `"sql"` | `sql`, `csv`, `hl7`, `fhir` |
-| `geographicFocus` | string | `"us"` | Geographic distribution |
+| `count` | int | `1000` | Number of patients |
+| `format` | string | `"sql"` | `sql`, `csv`, `hl7`, `fhir`, `pas-bundle` |
+| `geographicFocus` | string | null | Geographic focus (for example a state abbreviation) |
| `seed` | int | null | Reproducible seed |
+| `profile` | string | null | Learned data profile name |
```bash curl
curl -X POST http://localhost:5102/api/flock/generate \
-H "Content-Type: application/json" \
- -d '{"count": 1000, "format": "sql", "geographicFocus": "us"}'
+ -d '{"count": 1000, "format": "sql", "geographicFocus": "TX"}'
```
## GET /api/flock/generate/{id}
@@ -89,22 +94,27 @@ curl http://localhost:5102/api/flock/generate/job-123/analytics
## POST /api/flock/seed
-Seed the connected database with generated data.
+Seed the connected database with the generated population.
+
+| Field | Type | Default | Description |
+|-------|------|---------|-------------|
+| `connectionString` | string | required | Target database connection |
+| `provider` | string | `postgres` | Database provider |
```bash curl
curl -X POST http://localhost:5102/api/flock/seed \
-H "Content-Type: application/json" \
- -d '{"jobId": "job-123"}'
+ -d '{"connectionString": "Host=localhost;Database=ehr;...", "provider": "postgres"}'
```
## POST /api/flock/seed/dry-run
-Preview SQL without executing.
+Preview the seed plan without executing.
```bash curl
curl -X POST http://localhost:5102/api/flock/seed/dry-run \
-H "Content-Type: application/json" \
- -d '{"jobId": "job-123"}'
+ -d '{"connectionString": "Host=localhost;Database=ehr;...", "provider": "postgres"}'
```
## DELETE /api/flock/seed/cleanup
@@ -114,7 +124,7 @@ Remove all synthetic data from the database.
| Query Param | Type | Description |
|-------------|------|-------------|
| `connectionString` | string | Database connection |
-| `provider` | string | Database type |
+| `provider` | string | Database provider |
```bash curl
curl -X DELETE "http://localhost:5102/api/flock/seed/cleanup?connectionString=Host%3Dlocalhost%3BDatabase%3Dehr&provider=postgres"
@@ -122,7 +132,7 @@ curl -X DELETE "http://localhost:5102/api/flock/seed/cleanup?connectionString=Ho
## GET /api/flock/compliance/{id}
-Get a compliance report for a generation job.
+Get the no-PHI attestation for a generation job. It confirms the population is synthetic-only and reports whether any PHI was detected.
```bash curl
curl http://localhost:5102/api/flock/compliance/job-123
diff --git a/api-reference/generate.mdx b/api-reference/generate.mdx
index e83f2d6..7f163be 100644
--- a/api-reference/generate.mdx
+++ b/api-reference/generate.mdx
@@ -5,7 +5,7 @@ description: Generate synthetic healthcare messages via the Bridge API.
## POST /api/generate
-Generate synthetic healthcare messages. **Public** — no authentication required.
+Generate synthetic healthcare messages. This is a free-tier route. The Post Bridge listens only on `localhost` for the signed-in user, so no network authentication applies.
### Request Body
diff --git a/api-reference/introduction.mdx b/api-reference/introduction.mdx
index f6e5f90..4b09321 100644
--- a/api-reference/introduction.mdx
+++ b/api-reference/introduction.mdx
@@ -1,9 +1,9 @@
---
title: API Reference
-description: The Pidgeon Bridge API — a local sidecar each desktop app runs, not a hosted cloud API. Authentication, response format, and endpoint overview.
+description: The Pidgeon Bridge API, a local sidecar each desktop app runs, not a hosted cloud API. Authentication, response format, and endpoint overview.
---
-Each desktop app (Post, Flock, Loft, Migrate) starts a local **Bridge** — an ASP.NET Core sidecar — on a fixed port while it's running. The desktop apps themselves use this same API. There is no public hosted API today: every request in this reference is local to the machine running the app, on a loopback port reachable only while that app is open.
+Each Pidgeon desktop app (Post, Flock, Loft, Migrate, Conform) starts a local **Bridge**, an ASP.NET Core sidecar, on a fixed loopback port while the app runs. The desktop apps use this same API. There is no public hosted API today: every request in this reference is local to the machine running the app, on a loopback port reachable only while that app is open.
**Base URL**: `http://localhost:`, where the port depends on which app's Bridge you're calling:
@@ -12,55 +12,45 @@ Each desktop app (Post, Flock, Loft, Migrate) starts a local **Bridge** — an A
| Loft | `5100` |
| Post | `5101` |
| Flock | `5102` |
+| Migrate | `5103` |
+| Conform | `5104` |
-The endpoints below (Loft interfaces/alerts/status/analytics/traces, Flock, Admin, Enterprise) are Loft- and Flock-scoped and default to their Bridge's port in the examples that follow; substitute the port for the app you're integrating with.
+This reference documents the Post, Flock, and Loft routes. Migrate and Conform run Bridges too, but their routes aren't documented here yet; drive them from the [Migrate CLI](/cli/migrate-commands) and [Conform CLI](/cli/conform-commands). The Pidgeon launcher has no Bridge of its own.
-This reference documents the local Bridge HTTP contract for automation and integration against a running desktop app. It has not been exhaustively cross-checked against every current Bridge route — if an example here 404s, prefer the CLI equivalent and treat the mismatch as a docs bug.
+This reference documents the local Bridge HTTP contract for automation against a running desktop app. It has not been exhaustively cross-checked against every current Bridge route. If an example here 404s, prefer the CLI equivalent and treat the mismatch as a docs bug.
## Authentication
-Two authentication schemes are supported. Include one on protected endpoints:
+The Bridge listens only on loopback, for the user signed into the app on that machine. Most routes need no token. Where a route is protected, include the app session's credential:
+The free-versus-Pro boundary is enforced by the app and your Pidgeon account entitlements, not by an internet-facing permission model. A feature like AI Triage is a Post Pro feature even though its loopback route carries no separate auth.
+
## Response Format
-## Authorization Policies
-
-| Policy | Requirement |
-|--------|-------------|
-| Public | No authentication required |
-| Authenticated | Valid JWT or API Key |
-| OrgMember | Authenticated + `org_id` claim |
-| LoftViewer | OrgMember + Viewer role |
-| LoftOperator | OrgMember + Operator role |
-| LoftEditor | OrgMember + Editor role |
-| LoftAdmin | OrgMember + Admin role |
-
## Usage limits
-Because the Bridge runs locally, there's no network-abuse rate limit to enforce — usage limits instead follow your account's plan and entitlements (for example, Flock's population size caps in the desktop app's **Population** panel). Where a response includes rate-limit headers, they reflect the entitlement-based cap for that endpoint, not a fixed per-tier number documented here.
-
-## Endpoint Groups
-
-| Group | Auth | Description |
-|-------|------|-------------|
-| [Generate](/api-reference/generate) | Public | Synthetic message generation |
-| [Validate](/api-reference/validate) | Public | Message validation |
-| [Diff](/api-reference/diff) | Public | Message comparison |
-| [AI Triage](/api-reference/ai-triage) | Public | AI-powered failure analysis |
-| [Loft Interfaces](/api-reference/loft-interfaces) | Public | Interface CRUD + metrics |
-| [Loft Alerts](/api-reference/loft-alerts) | Public | Alert management |
-| [Loft Status](/api-reference/loft-status) | Public | Status and reports |
-| [Analytics](/api-reference/analytics) | Public | Time-series and dashboards |
-| [Traces](/api-reference/traces) | Public | Patient tracing and gaps |
-| [Flock](/api-reference/flock) | Public | Population generation |
-| [Admin](/api-reference/admin) | LoftAdmin | RBAC, workspaces, SLA |
-| [Enterprise](/api-reference/enterprise) | LoftAdmin | SSO, audit, observability |
-| [SignalR](/api-reference/signalr) | JWT/API Key | Live updates |
-
-## Content Type
+Because the Bridge runs locally, there's no network-abuse rate limit to enforce. Usage limits follow your account's plan and entitlements, for example Flock's population caps in the desktop app's **Population** panel. Where a response includes rate-limit headers, they reflect the entitlement-based cap for that endpoint.
+
+## Endpoint groups
+
+| Group | Description |
+|-------|-------------|
+| [Generate](/api-reference/generate) | Synthetic message generation |
+| [Validate](/api-reference/validate) | Message validation |
+| [Diff](/api-reference/diff) | Message comparison |
+| [AI Triage](/api-reference/ai-triage) | AI-powered failure analysis (Post Pro) |
+| [Loft Interfaces](/api-reference/loft-interfaces) | Interface CRUD and metrics |
+| [Loft Alerts](/api-reference/loft-alerts) | Alert management |
+| [Loft Status](/api-reference/loft-status) | Status and reports |
+| [Analytics](/api-reference/analytics) | Time-series and dashboards |
+| [Traces](/api-reference/traces) | Patient tracing and gaps |
+| [Flock](/api-reference/flock) | Population generation |
+| [SignalR](/api-reference/signalr) | Live updates |
+
+## Content type
All request and response bodies use JSON. Set `Content-Type: application/json` on all requests with a body.
diff --git a/api-reference/loft-alerts.mdx b/api-reference/loft-alerts.mdx
index ce1c5a1..8a991bf 100644
--- a/api-reference/loft-alerts.mdx
+++ b/api-reference/loft-alerts.mdx
@@ -3,9 +3,11 @@ title: Loft Alerts
description: Query and acknowledge monitoring alerts via the Bridge API.
---
+Loft is a Pro product. These routes are served by the Loft desktop app's local Bridge on loopback (`localhost:5100`) for the signed-in user, which resolves the Professional tier locally, so a local call needs no API key. This is not a hosted API and is not reachable from another machine. A request below the Professional tier returns `402`, never a hard `403`.
+
## GET /api/loft/alerts
-List alerts with optional filters. **Public**.
+List alerts with optional filters.
| Query Param | Type | Default | Description |
|-------------|------|---------|-------------|
@@ -23,7 +25,7 @@ curl "http://localhost:5100/api/loft/alerts?severity=critical&sinceHours=6"
"success": true,
"data": [
{
- "id": "alert-5012",
+ "id": "7d9c1e46-3b0a-4c2e-9f1a-2b6d5e4f8a10",
"interfaceId": "intf-001",
"interfaceName": "ER Interface",
"severity": "critical",
@@ -41,8 +43,8 @@ curl "http://localhost:5100/api/loft/alerts?severity=critical&sinceHours=6"
## POST /api/loft/alerts/{id}/acknowledge
-Acknowledge an alert. **Public**.
+Acknowledge an alert. The `{id}` is the alert's GUID.
```bash curl
-curl -X POST http://localhost:5100/api/loft/alerts/alert-5012/acknowledge
+curl -X POST http://localhost:5100/api/loft/alerts/7d9c1e46-3b0a-4c2e-9f1a-2b6d5e4f8a10/acknowledge
```
diff --git a/api-reference/loft-interfaces.mdx b/api-reference/loft-interfaces.mdx
index 979570c..97dab11 100644
--- a/api-reference/loft-interfaces.mdx
+++ b/api-reference/loft-interfaces.mdx
@@ -3,7 +3,9 @@ title: Loft Interfaces
description: CRUD operations and metrics for monitored healthcare integration interfaces.
---
-Manage monitored interfaces. All endpoints are **public**.
+Manage monitored interfaces.
+
+Loft is a Pro product. These routes are served by the Loft desktop app's local Bridge on loopback (`localhost:5100`) for the signed-in user, which resolves the Professional tier locally, so a local call needs no API key. This is not a hosted API and is not reachable from another machine. A request below the Professional tier returns `402`, never a hard `403`.
## GET /api/loft/interfaces
@@ -21,7 +23,7 @@ Create a new interface.
|-------|------|---------|-------------|
| `name` | string | Required | Display name |
| `directoryPath` | string | Required | Filesystem path to watch |
-| `profileName` | string | — | Vendor profile for validation |
+| `profileName` | string | none | Vendor profile for validation |
| `filePattern` | string | `"*.hl7"` | Glob pattern for message files |
```bash curl
@@ -80,4 +82,4 @@ Get interface metrics.
curl "http://localhost:5100/api/loft/interfaces/intf-001/metrics?sinceHours=12"
```
-Response includes `messagesTotal`, `messagesSuccessful`, `messagesFailed`, `successRate`, `averageLatencyMs`, `p99LatencyMs`.
+Response includes `totalMessagesProcessed`, `totalErrors`, `totalSuccesses`, `errorRate`, `lastMessageAt`, `startedAt`, `uptimeSeconds`, and an `hourlyBreakdown` array (each bucket has `hour`, `messagesProcessed`, `errors`, and `successes`).
diff --git a/api-reference/loft-status.mdx b/api-reference/loft-status.mdx
index 9c4b253..f4abc82 100644
--- a/api-reference/loft-status.mdx
+++ b/api-reference/loft-status.mdx
@@ -3,9 +3,11 @@ title: Loft Status & Reports
description: Get overall Loft monitoring status and generate reports via the Bridge API.
---
+Loft is a Pro product. These routes are served by the Loft desktop app's local Bridge on loopback (`localhost:5100`) for the signed-in user, which resolves the Professional tier locally, so a local call needs no API key. This is not a hosted API and is not reachable from another machine. A request below the Professional tier returns `402`, never a hard `403`.
+
## GET /api/loft/status
-Get overall monitoring status across all interfaces. **Public**.
+Get overall monitoring status across all interfaces.
```bash curl
curl http://localhost:5100/api/loft/status
@@ -13,7 +15,7 @@ curl http://localhost:5100/api/loft/status
## GET /api/loft/report
-Generate a monitoring report. **Public**.
+Generate a monitoring report.
| Query Param | Type | Default | Description |
|-------------|------|---------|-------------|
diff --git a/api-reference/signalr.mdx b/api-reference/signalr.mdx
index bd0d75d..c5c6e31 100644
--- a/api-reference/signalr.mdx
+++ b/api-reference/signalr.mdx
@@ -7,7 +7,9 @@ Loft pushes live updates over a SignalR hub for dashboard integration. The hub d
**Hub URL**: `ws://localhost:5100/hubs/loft` (the Loft desktop app's local Bridge; no hosted hub exists)
-Authentication via JWT Bearer token or API Key.
+Loft is a Pro product. The hub is served by the Loft desktop app's local Bridge on loopback for the signed-in user. It is not a hosted hub and is not reachable from another machine.
+
+The connection authenticates as the signed-in user with a JWT Bearer token or API key.
## Client → Server Methods
@@ -15,8 +17,8 @@ Authentication via JWT Bearer token or API Key.
|--------|-----------|-------------|
| `SubscribeToInterface` | `interfaceId: string` | Subscribe to updates for a specific interface |
| `UnsubscribeFromInterface` | `interfaceId: string` | Unsubscribe from interface updates |
-| `SubscribeToAll` | — | Subscribe to all interface updates |
-| `UnsubscribeFromAll` | — | Unsubscribe from all updates |
+| `SubscribeToAll` | none | Subscribe to all interface updates |
+| `UnsubscribeFromAll` | none | Unsubscribe from all updates |
## Server → Client Events
diff --git a/api-reference/traces.mdx b/api-reference/traces.mdx
index 33553b7..196ae32 100644
--- a/api-reference/traces.mdx
+++ b/api-reference/traces.mdx
@@ -3,7 +3,9 @@ title: Traces & Gaps
description: Trace patient journeys across interfaces, detect message gaps, and measure interface latency.
---
-Five endpoints for message tracing and gap detection. All **public**.
+Five endpoints for message tracing and gap detection.
+
+Loft is a Pro product. These routes are served by the Loft desktop app's local Bridge on loopback (`localhost:5100`) for the signed-in user, which resolves the Professional tier locally, so a local call needs no API key. This is not a hosted API and is not reachable from another machine. A request below the Professional tier returns `402`, never a hard `403`.
## GET /api/loft/traces
@@ -30,9 +32,9 @@ curl "http://localhost:5100/api/loft/traces?patient_id=MRN12345&since=2026-02-01
"patientId": "MRN12345",
"totalSpanMs": 14400000,
"events": [
- {"interface": "ER ADT", "messageType": "ADT^A01", "timestamp": "2026-02-20T08:30:00Z", "status": "valid"},
- {"interface": "Lab", "messageType": "ORU^R01", "timestamp": "2026-02-20T09:15:00Z", "status": "valid"},
- {"interface": "ER ADT", "messageType": "ADT^A03", "timestamp": "2026-02-20T12:30:00Z", "status": "valid"}
+ {"interfaceName": "ER ADT", "messageType": "ADT^A01", "timestamp": "2026-02-20T08:30:00Z", "validationStatus": "valid"},
+ {"interfaceName": "Lab", "messageType": "ORU^R01", "timestamp": "2026-02-20T09:15:00Z", "validationStatus": "valid"},
+ {"interfaceName": "ER ADT", "messageType": "ADT^A03", "timestamp": "2026-02-20T12:30:00Z", "validationStatus": "valid"}
],
"gaps": []
},
diff --git a/api-reference/validate.mdx b/api-reference/validate.mdx
index 8a8972f..7aaf4b7 100644
--- a/api-reference/validate.mdx
+++ b/api-reference/validate.mdx
@@ -5,7 +5,7 @@ description: Validate healthcare messages against standard specifications via th
## POST /api/validate
-Validate a healthcare message. **Public** — no authentication required.
+Validate a healthcare message. This is a free-tier route. The Post Bridge listens only on `localhost` for the signed-in user, so no network authentication applies.
### Request Body
diff --git a/cli/ai-commands.mdx b/cli/ai-commands.mdx
new file mode 100644
index 0000000..06c5cce
--- /dev/null
+++ b/cli/ai-commands.mdx
@@ -0,0 +1,109 @@
+---
+title: AI Commands
+description: Manage on-device AI models, configure a BYOK provider, set the PHI-egress policy, and run message operations like triage, explain, and fix.
+---
+
+`pidgeon ai` is a Post Pro feature and is hardware dependent. It ships with the Post desktop app and the licensed CLI, not the free `dotnet tool install` build. Every AI operation runs on-device by default; nothing leaves the machine without an explicit opt-in.
+
+The `ai` family manages the on-device model, configures an optional cloud provider (BYOK), sets the egress policy that governs where inference is allowed to run, and runs message operations (triage a failure, explain a message, apply field-level fixes).
+
+## Model management
+
+On-device inference needs a local model. Set one up in one step:
+
+```bash
+# Pick the model that fits this machine, download it if needed, and make it active
+pidgeon ai setup
+```
+
+Or manage models directly:
+
+```bash
+pidgeon ai list --available # Downloadable model catalog
+pidgeon ai list --installed # Models installed locally
+pidgeon ai download qwen3-4b # Download and install a model
+pidgeon ai download qwen3-4b --background # Large downloads run in the background
+pidgeon ai info qwen3-4b # Model details (size, RAM, capabilities)
+pidgeon ai remove qwen3-4b # Remove a locally installed model
+```
+
+### On-device models
+
+Two bundled models are validated today:
+
+| Model | Fit |
+|-------|-----|
+| `qwen3-4b` | The default on-device model on a typical laptop (16 GB RAM recommended). |
+| `smollm2-1.7b` | The small-RAM fallback for 8 GB machines. |
+
+Run `pidgeon ai list --available` for the full downloadable catalog on your machine.
+
+Gemma 4 support (`gemma4-e4b`, `gemma4-12b`) is being validated and may appear in the catalog. Confirm availability with `pidgeon ai list --available` before relying on it.
+
+## Provider configuration (BYOK)
+
+Point the AI operations at a cloud provider instead of the on-device model. Bring your own key, so cost control stays with you.
+
+```bash
+pidgeon ai configure --provider openai --model gpt-4o --api-key sk-...
+pidgeon ai status # Show the configured provider and connection health
+pidgeon ai test-connection # Send a synthetic canary request (provider billing may apply)
+pidgeon ai remove-credential # Delete a provider credential from this device
+```
+
+Supported providers: `openai`, `anthropic`, `openrouter`, `ollama`, `azure`, `gemini`, or any OpenAI-compatible endpoint (`openai-compatible`). For an OpenAI-compatible server, pass `--endpoint` and `--model`; many in-tenant servers are keyless. Use `--locus in-network` for a server you run yourself and `--locus cloud` for a compatibility-API SaaS. The locus is declared, never inferred from the address.
+
+## Message operations
+
+Each verb takes a message file (HL7, FHIR JSON, or NCPDP XML):
+
+| Command | What it does |
+|---------|--------------|
+| `pidgeon ai triage ` | Analyze validation failures and suggest fixes. Accepts `--mode` and `--vendor`. |
+| `pidgeon ai explain ` | Explain a message in plain English. |
+| `pidgeon ai fix ` | Recommend field-level fixes and apply the approved changes. |
+| `pidgeon ai enrich ` | Fill sparse optional fields with realistic values. |
+| `pidgeon ai suggest ` | Suggest a realistic value for a single field. |
+| `pidgeon ai modify ` | Modify a message with an AI-assisted instruction. |
+| `pidgeon ai template ` | Apply a predefined modification template. |
+
+```bash
+# Triage a message that fails validation
+pidgeon ai triage broken.hl7
+
+# Explain what a message contains
+pidgeon ai explain admit.hl7
+```
+
+## PHI-egress policy
+
+`pidgeon ai egress` views or sets where inference is allowed to run. The default keeps all content on-device; nothing goes off-device without an explicit opt-in.
+
+```bash
+pidgeon ai egress # Show the current policy
+pidgeon ai egress --mode workstation-ollama # Use a local Ollama runtime
+pidgeon ai egress --require-on-device true # Refuse any off-device inference
+pidgeon ai egress --mode byok-cloud --baa-opt-in true # Allow real content to a cloud provider under a BAA
+```
+
+| Flag | Values | Meaning |
+|------|--------|---------|
+| `--mode` | `bundled-on-device` (default), `workstation-ollama`, `customer-controlled`, `byok-cloud` | Where inference runs. |
+| `--baa-opt-in` | `true` / `false` | Permit real content to a `byok-cloud` provider. |
+| `--require-on-device` | `true` / `false` | Refuse any off-device inference regardless of the synthetic attestation. |
+| `--max-locus` | `on-device`, `in-network`, `cloud` | The highest locus any provider may occupy before content is refused. |
+
+Every call that resolves to a non-local provider is audit-logged with the provider, deployment mode, and content length.
+
+## Health and policy
+
+```bash
+pidgeon ai health # Runtime daemon, active provider, capability verdict, egress ceiling, last error
+pidgeon ai settings # Effective AI settings and their authority
+pidgeon ai policy # The managed org policy that locks AI settings
+```
+
+## Next steps
+
+- [AI Triage in Post](/post/ai-triage): the same on-device analysis in the desktop panel
+- [Message Generation](/post/message-generation): the `model` and `api` generation modes
diff --git a/cli/config-commands.mdx b/cli/config-commands.mdx
index 3ea0aa2..51b5a60 100644
--- a/cli/config-commands.mdx
+++ b/cli/config-commands.mdx
@@ -3,6 +3,8 @@ title: Config Commands
description: Analyze real messages to detect vendor patterns, manage named profiles, and compare configurations.
---
+Vendor-profile management (`pidgeon config`) ships with the Post desktop app and the licensed CLI, not the free `dotnet tool install` build. If you installed only the free CLI, these commands are delivered through Post.
+
## pidgeon config analyze
Analyze sample messages to detect vendor-specific patterns and save as a named profile.
diff --git a/cli/conform-commands.mdx b/cli/conform-commands.mdx
index 2c422c2..07795fe 100644
--- a/cli/conform-commands.mdx
+++ b/cli/conform-commands.mdx
@@ -3,7 +3,7 @@ title: Conform Commands
description: Probe a live FHIR endpoint against a published Implementation Guide from CI, with a non-zero exit code and an HTML scorecard.
---
-Conform is the FHIR conformance module of Post. `pidgeon conform` probes a live FHIR endpoint against a published Implementation Guide (US Core, Da Vinci PAS 2.1) and returns pass/fail with a non-zero CI exit code plus a self-contained HTML scorecard. It's the CI gate for CMS-0057-F.
+Conform is Pidgeon's FHIR conformance product. `pidgeon conform` probes a live FHIR endpoint against a published Implementation Guide (US Core, Da Vinci PAS 2.1) and returns pass/fail with a non-zero CI exit code plus a self-contained HTML scorecard. It's the CI gate for CMS-0057-F. For the concepts behind these flags, see the [Conform section](/conform/overview).
```bash
pidgeon conform --endpoint [options]
@@ -17,16 +17,25 @@ pidgeon conform --endpoint [options]
| `--endpoint-set` | string | — | Name of an installed conform-endpoint set (`pidgeon recipe list`) to walk every endpoint in |
| `--resource` | string | — | Resource path `ResourceType/id` (e.g. `Patient/example`). Required unless `--walk` |
| `--profile` | string | — | IG profile short name (e.g. `us-core-patient`) or canonical URL. Required unless `--walk` |
-| `--auth` | string | — | Authorization header value (`Bearer eyJ…`). Leave unset for unauthenticated endpoints |
+| `--auth` | string | — | Authorization header value (`Bearer eyJ…`). Leave unset for unauthenticated endpoints. Mutually exclusive with `--auth-smart-backend` |
+| `--auth-smart-backend` | flag | off | Authenticate via SMART Backend Services: discover the token endpoint, sign an RS384 client assertion, exchange it for an access token |
+| `--client-id` | string | — | Registered backend-services client id. Requires `--auth-smart-backend` |
+| `--key-file` | string | — | PEM-encoded RSA private key that signs the client assertion. Requires `--auth-smart-backend` |
+| `--scope` | string | `system/*.read` | OAuth scopes for the `client_credentials` grant |
+| `--token-endpoint` | string | — | Explicit OAuth token endpoint; skips `.well-known/smart-configuration` discovery |
| `--walk` | flag | off | Probe every resource × profile pair declared in the endpoint's CapabilityStatement |
| `--ci` | flag | off | CI mode: must-support warnings flip the exit to non-zero; a walk validating zero resources exits `2` |
| `--require-full-coverage` | flag | off | Exit `2` unless every declared resource type was actually probed (walk only) |
| `--probe-operations` | flag | off | Also POST a synthetic PAS request Bundle to `Claim/$submit` and grade the response |
| `--check-terminology` | flag | off | Validate coded fields against a live FHIR terminology service; an unresolved code flips the exit to `1` |
+| `--terminology-endpoint` | string | `http://127.0.0.1:8080/fhir` | Cross-vocab terminology service for `--check-terminology` (ICD-10-CM / LOINC / RxNorm) |
+| `--snomed-endpoint` | string | `http://127.0.0.1:8181/fhir` | SNOMED CT terminology service; `http://snomed.info/sct` codes route here |
| `--only-resources` | string | — | Comma-separated resource types to walk (e.g. `Patient,Encounter`). Walk only |
| `--ig` | string | — | Filter walk probes to profiles from this IG base URL. Walk only |
-| `--output-file` | string | stdout | Write the report to a file (pair with `--output html`) |
-| `--badge` | string | — | Write a shields.io-style pass/fail SVG status badge to this path |
+| `--readiness-pack` | string | — | Grade the walk against a compiled readiness pack and write an evidence envelope. Supported: `us-core-3.1.1` (requires the `fhir-us-core-3.1.1` package). Walk only |
+| `--evidence-out` | string | `conform-evidence.json` | Path for the readiness evidence envelope JSON. Requires `--readiness-pack` |
+| `--output-file` | string | stdout | Write the report to a file instead of stdout (particularly useful for the HTML scorecard) |
+| `--badge` | string | — | Write dated pass/fail badge artifacts (SVG + shields.io endpoint JSON) whose verdict mirrors the exit code |
## Examples
@@ -43,6 +52,14 @@ pidgeon conform --endpoint https://api.payer.example/fhir --walk --ig http://hl7
# Authenticated endpoint
pidgeon conform --endpoint https://api.payer.example/fhir --walk --auth "Bearer eyJ..."
+
+# SMART Backend Services (system-to-system) auth
+pidgeon conform --endpoint https://api.payer.example/fhir --walk \
+ --auth-smart-backend --client-id my-client --key-file ./key.pem
+
+# Grade against the US Core 3.1.1 readiness pack and write an evidence envelope
+pidgeon conform --endpoint https://api.payer.example/fhir --walk \
+ --readiness-pack us-core-3.1.1 --evidence-out conform-evidence.json
```
## Exit codes
@@ -63,5 +80,7 @@ pidgeon conform --endpoint "$FHIR_URL" --walk --ci || exit 1
## Learn more
-- [Get started with Post](/getting-started/post) — the Conformance panel in the desktop app
-- [CLI Quickstart](/getting-started/quickstart-cli) — conform in a CI pipeline
+- [Conform overview](/conform/overview): the concepts behind these flags
+- [CMS-0057-F](/conform/cms-0057-f): required vs recommended IGs
+- [Evidence and CI](/conform/evidence-and-ci): exit codes, scorecards, readiness packs
+- [Get started with Post](/getting-started/post): the Conformance panel in the desktop app
diff --git a/cli/data-commands.mdx b/cli/data-commands.mdx
index f37bdfa..747dae0 100644
--- a/cli/data-commands.mdx
+++ b/cli/data-commands.mdx
@@ -1,11 +1,11 @@
---
title: Data Commands
-description: Manage healthcare reference datasets — install, import, and update LOINC, SNOMED, ICD-10, NDC, and more.
+description: Manage terminology datasets and FHIR Implementation Guide packages. Install, import, and update LOINC, SNOMED, ICD-10, NDC, US Core, Da Vinci, and more.
---
-Pidgeon uses reference datasets for realistic code generation during message creation. These commands manage your local dataset installations.
+`pidgeon data` is a free CLI command. It manages two kinds of local package: **terminology datasets** (the code systems that make generated messages pass downstream validation) and **FHIR Implementation Guide packages** (the profiles that `pidgeon conform` and FHIR validation grade against). Run `pidgeon data list` for the live catalog on your machine.
-## Available Datasets
+## Terminology datasets
| Dataset | Codes | Size | Free | Pro |
|---------|-------|------|------|-----|
@@ -17,41 +17,81 @@ Pidgeon uses reference datasets for realistic code generation during message cre
| CVX | 288 entries | 1 MB | Full | Full |
| RxNorm | Large | 1.7 GB | — | Full |
| HCPCS | Full set | 5 MB | — | Full |
-| CPT | — | — | — | Add-on ($30/user/yr) |
+| CPT | Procedure codes | — | — | Licensed add-on |
+
+Eight terminology datasets ship; CPT is a separate licensed add-on gated by AMA royalty terms. This table is the CLI companion to [Datasets & Data Packages](/post/datasets).
+
+## FHIR Implementation Guide packages
+
+`pidgeon data` is also the IG package manager. Install a guide, and FHIR validation and `pidgeon conform` grade against its profiles.
+
+| Package | IG | Version |
+|---------|-----|---------|
+| `fhir-r4-core` | FHIR R4 base | 4.0.1 |
+| `fhir-us-core-3.1.1` | US Core | 3.1.1 |
+| `fhir-us-core-6.0` | US Core | 6.1.0 |
+| `fhir-davinci-pas-2.1` | Da Vinci Prior Auth Support | 2.1.0 |
+| `fhir-davinci-crd-2.1` | Da Vinci Coverage Requirements Discovery | 2.1.0 |
+| `fhir-davinci-dtr-2.0` | Da Vinci Documentation Templates and Rules | 2.0.0 |
+
+```bash
+pidgeon data install fhir-us-core-3.1.1
+pidgeon data install fhir-davinci-pas-2.1
+```
+
+## License-gated standards packages
+
+Some standards material is member-only and closed by default. It installs only with an explicit `--accept-license`:
+
+```bash
+# NCPDP SCRIPT (member-only XSDs; NCPDP membership required)
+pidgeon data install ncpdp-script --accept-license
+
+# X12 5010 guides
+pidgeon data install x12-5010 --accept-license
+```
+
+Until the `ncpdp-script` package is installed, NCPDP generation and validation report a license-required state rather than running. See [Message Generation](/post/message-generation#ncpdp-script-2017071).
## pidgeon data list
-List all available and installed datasets.
+List every available and installed package: terminology datasets, FHIR IGs, and license-gated standards.
```bash
pidgeon data list
```
```text
-Dataset Status Version Size
-─────────────────────────────────────────────
-LOINC Installed 2.81 25 MB
-SNOMED CT US Available Sep 2025 1.5 GB
-ICD-10-CM Installed 2026 15 MB
-ICD-9-CM Installed v32 8 MB
-NDC Installed Current 30 MB
-CVX Installed Current 1 MB
-RxNorm Available Feb 2026 1.7 GB
-HCPCS Available Jan 2026 5 MB
+Name DataType Status Version
+────────────────────────────────────────────────────────────
+loinc lab-tests installed 2.81
+snomed snomed-concepts available Sep 2025
+icd10 diagnoses installed 2026
+ndc medications installed Current
+fhir-r4-core fhir-ig installed 4.0.1
+fhir-us-core-3.1.1 fhir-ig available 3.1.1
+fhir-davinci-pas-2.1 fhir-ig installed 2.1.0
+ncpdp-script ncpdp-schemas available (license)
```
## pidgeon data install
-Download and install a dataset.
+Download and install a package (terminology dataset, FHIR IG, or a license-gated standards package).
```bash
-pidgeon data install
+pidgeon data install [--accept-license] [--all]
```
+| Flag | Description |
+|------|-------------|
+| `--accept-license` | Accept required license terms (for example UMLS, NCPDP membership). Required for member-only packages. |
+| `--all` | Install every available package. |
+
```bash
pidgeon data install loinc
-pidgeon data install snomed
pidgeon data install rxnorm
+pidgeon data install fhir-us-core-3.1.1
+pidgeon data install ncpdp-script --accept-license
```
## pidgeon data import
diff --git a/cli/flock-commands.mdx b/cli/flock-commands.mdx
index dc4eb01..664656f 100644
--- a/cli/flock-commands.mdx
+++ b/cli/flock-commands.mdx
@@ -1,44 +1,62 @@
---
title: Flock Commands
-description: CLI commands for Flock synthetic population generation — connect to databases, learn patterns, generate populations, and seed data.
+description: "CLI commands for Flock synthetic population generation: connect to a database, learn distributions, generate a population, and seed the data."
---
+`flock` is a Pro command delivered through the Flock desktop app, not the free community CLI. If you installed only `dotnet tool install --global Pidgeon.CLI`, the `flock` subcommand is not present. It requires a Pidgeon account sign-in.
+
## pidgeon flock connect
-Connect to a database and analyze its schema.
+Connect to a database and introspect its schema.
```bash
-pidgeon flock connect --provider --connection-string
+pidgeon flock connect --provider --connection
```
-| Flag | Type | Description |
-|------|------|-------------|
-| `--provider ` | string | Database type: `postgres`, `mysql`, `sqlserver` |
-| `--connection-string ` | string | Database connection string |
+| Flag | Type | Default | Description |
+|------|------|---------|-------------|
+| `--provider ` | string | `postgres` | Database provider: `postgres`, `sqlserver`, `mysql` |
+| `--connection ` | string | required | Database connection string |
```bash
pidgeon flock connect \
--provider postgres \
- --connection-string "Host=localhost;Port=5432;Database=ehr;Username=dev;Password=${DB_PASSWORD}"
+ --connection "Host=localhost;Port=5432;Database=ehr;Username=dev;Password=${DB_PASSWORD}"
```
+MariaDB connects through the `mysql` provider; `postgresql` and `mssql` are accepted as aliases.
+
+---
+
+## pidgeon flock schema
+
+View and classify the introspected schema.
+
+```bash
+pidgeon flock schema [--classify] [--visualize]
+```
+
+| Flag | Type | Default | Description |
+|------|------|---------|-------------|
+| `--classify` | flag | `false` | Classify tables by healthcare domain |
+| `--visualize` | flag | `false` | Emit the schema as a Mermaid ER diagram |
+
---
## pidgeon flock learn
-Learn statistical patterns from existing sample data.
+Learn statistical distributions from existing rows.
```bash
-pidgeon flock learn [options]
+pidgeon flock learn [--sample ]
```
| Flag | Type | Default | Description |
|------|------|---------|-------------|
-| `--tables ` | string | All tables | Comma-separated list of tables to analyze |
-| `--sample-size ` | int | `100` | Number of rows to sample per table |
+| `--sample ` | int | `500` | Number of rows to sample per table |
```bash
-pidgeon flock learn --tables patients,encounters,diagnoses --sample-size 500
+pidgeon flock learn --sample 500
```
---
@@ -53,17 +71,20 @@ pidgeon flock generate [options]
| Flag | Type | Default | Description |
|------|------|---------|-------------|
-| `--count ` | int | `100` | Number of patients to generate |
-| `--format ` | string | `sql` | Output format: `sql`, `csv`, `hl7`, `fhir` |
-| `--geographic-focus ` | string | `us` | Geographic distribution |
-| `--seed ` | int | Random | Reproducible seed |
-| `--output ` | string | stdout | Output file or directory |
+| `--count`, `-c ` | int | `100` | Number of patients to generate |
+| `--format`, `-f ` | string | `sql` | Output format: `sql`, `csv`, `hl7`, `fhir`, `pas-bundle` |
+| `--schema ` | string | optional | Path to a SQL DDL or JSON schema |
+| `--state ` | string | optional | State abbreviation for geographic focus (for example `TX`, `CA`) |
+| `--seed ` | int | random | Seed for reproducible output |
+| `--profile ` | string | optional | Use a learned data profile |
+| `--output`, `-o ` | string | stdout | Output directory for generated files |
+| `--from-config ` | string | optional | Run a saved population config (supersedes `--count` / `--format` / `--state` / `--seed` / `--profile`) |
```bash
# Generate 1000 patients as SQL
pidgeon flock generate --count 1000 --format sql --output ./seed-data/
-# Generate as FHIR bundles
+# Generate as FHIR Bundles
pidgeon flock generate --count 500 --format fhir --output ./fhir-data/
# Reproducible output
@@ -74,33 +95,53 @@ pidgeon flock generate --count 1000 --format csv --seed 42
## pidgeon flock seed
-Seed a connected database with generated data.
+Seed a target database with generated data.
```bash
-pidgeon flock seed [options]
+pidgeon flock seed --target --connection [options]
```
-| Flag | Type | Description |
-|------|------|-------------|
-| `--dry-run` | flag | Preview SQL without executing |
-| `--cleanup` | flag | Remove previously seeded synthetic data |
+| Flag | Type | Default | Description |
+|------|------|---------|-------------|
+| `--target ` | string | `postgres` | Database provider: `postgres`, `sqlserver`, `mysql` |
+| `--connection ` | string | required | Target database connection string |
+| `--dry-run` | flag | `false` | Generate SQL without executing |
+| `--from ` | string | optional | Seed records written by `flock generate -o` instead of the in-process job |
```bash
# Preview what would be inserted
-pidgeon flock seed --dry-run
+pidgeon flock seed --target postgres --connection "Host=localhost;Database=ehr;..." --dry-run
+
+# Seed from a directory that generate wrote
+pidgeon flock seed --target postgres --connection "Host=localhost;Database=ehr;..." --from ./seed-data/
+```
+
+---
+
+## pidgeon flock cleanup
+
+Remove synthetic data from a target database.
-# Seed the database
-pidgeon flock seed
+```bash
+pidgeon flock cleanup --provider --connection
+```
-# Clean up synthetic data
-pidgeon flock seed --cleanup
+| Flag | Type | Default | Description |
+|------|------|---------|-------------|
+| `--connection ` | string | required | Target database connection string |
+| `--provider ` | string | `postgres` | Database provider |
+
+```bash
+pidgeon flock cleanup --provider postgres --connection "Host=localhost;Database=ehr;..."
```
+Cleanup removes every record tagged as synthetic. This cannot be undone.
+
---
## pidgeon flock status
-Check the status of a running generation job.
+Show the installed Flock data packages.
```bash
pidgeon flock status
diff --git a/cli/global-options.mdx b/cli/global-options.mdx
index 64295b4..2c28a80 100644
--- a/cli/global-options.mdx
+++ b/cli/global-options.mdx
@@ -31,7 +31,7 @@ When `--standard` is omitted, Pidgeon auto-detects the standard from the message
| Format | When to Use |
|--------|-------------|
-| `auto` | Default — picks the best format for the standard |
+| `auto` | Default; picks the best format for the standard |
| `hl7` | Raw HL7 pipe-delimited format |
| `json` | Pretty-printed JSON (FHIR resources, structured output) |
| `ndjson` | Newline-delimited JSON for bulk/streaming |
diff --git a/cli/loft-commands.mdx b/cli/loft-commands.mdx
index 8441f79..8b5f6db 100644
--- a/cli/loft-commands.mdx
+++ b/cli/loft-commands.mdx
@@ -1,35 +1,40 @@
---
title: Loft Commands
-description: CLI commands for Loft interface monitoring — watch directories, check status, view alerts, and generate reports.
+description: "CLI commands for Loft interface monitoring: watch directories, check status, view alerts, and generate reports."
---
+Loft is a Pro product delivered with the Loft desktop app. The `pidgeon loft` commands and the local Bridge on `localhost:5100` ship with that app. The free `dotnet tool install --global Pidgeon.CLI` build does not include `loft`.
+
## pidgeon loft watch
-Start monitoring a directory for incoming healthcare messages.
+Watch a directory for incoming `.hl7` files and validate each one as it lands.
```bash
-pidgeon loft watch --directory [options]
+pidgeon loft watch --path [options]
```
| Flag | Type | Default | Description |
|------|------|---------|-------------|
-| `--directory ` | string | Required | Directory to watch for messages |
-| `--profile ` | string | — | Vendor profile for validation |
-| `--file-pattern ` | string | `*.hl7` | File pattern to match |
+| `--path ` | string | Required | Directory to watch for `.hl7` files |
+| `--profile ` | string | none | Vendor profile for validation |
+| `--mode ` | string | `compatibility` | Validation mode: `strict` or `compatibility` |
+| `--alert ` | string | `console` | Alert provider: `console`, `file:`, or `webhook:`. Repeatable. |
```bash
-# Watch a Mirth output directory
-pidgeon loft watch --directory /var/mirth/outbound/er --profile epic_er
+# Watch a Mirth output directory against a vendor profile
+pidgeon loft watch --path /var/mirth/outbound/er --profile epic_er
-# Watch with custom file pattern
-pidgeon loft watch --directory /var/loft/lab --file-pattern "*.txt"
+# Watch in strict mode and post failures to a webhook
+pidgeon loft watch --path /var/loft/lab --mode strict --alert webhook:https://hooks.example.org/loft
```
+The `watch` command validates `.hl7` files only, and its `--alert` flag covers the console, file, and webhook providers inline. To watch a custom file pattern, or to route to Slack, Microsoft Teams, email, or PagerDuty, create a persistent interface through the desktop app or its local Bridge. See [Interface Monitoring](/loft/interface-monitoring) and [Alerting](/loft/alerting).
+
---
## pidgeon loft status
-Show current monitoring status across all watched interfaces.
+Show current monitoring metrics across all watched interfaces.
```bash
pidgeon loft status
@@ -39,7 +44,7 @@ pidgeon loft status
## pidgeon loft alerts
-List recent alerts from monitored interfaces.
+List recent alerts from the Loft metrics store.
```bash
pidgeon loft alerts [options]
@@ -47,22 +52,24 @@ pidgeon loft alerts [options]
| Flag | Type | Default | Description |
|------|------|---------|-------------|
-| `--severity ` | string | All | Filter: `critical`, `warning`, `info` |
-| `--since ` | string | `24h` | Time window (e.g., `1h`, `12h`, `7d`) |
+| `--since ` | string | `1h` | Time window (e.g. `1h`, `12h`, `7d`) |
+| `--severity ` | string | All | Filter: `critical`, `warning`, `info`, `error` |
+| `--format ` | string | `table` | Output format: `table` or `json` |
+| `-o, --output ` | string | stdout | File path for the JSON export |
```bash
-# View critical alerts from the last 6 hours
+# Critical alerts from the last 6 hours
pidgeon loft alerts --severity critical --since 6h
-# View all recent alerts
-pidgeon loft alerts --since 1h
+# All recent alerts as JSON
+pidgeon loft alerts --since 1h --format json
```
---
## pidgeon loft report
-Generate a monitoring report.
+Generate a summary report of Loft monitoring activity.
```bash
pidgeon loft report [options]
@@ -70,13 +77,17 @@ pidgeon loft report [options]
| Flag | Type | Default | Description |
|------|------|---------|-------------|
-| `--format ` | string | `text` | Report format: `text`, `html`, `json` |
| `--since ` | string | `24h` | Time range for the report |
+| `--format ` | string | `text` | `text`, `json`, `pdf`, `excel`, or `html` |
+
+Text and JSON print to stdout. For a PDF, Excel, or HTML file, use `pidgeon loft report generate`, which writes to a path with `-o`:
```bash
# Text report for the last 24 hours
pidgeon loft report
-# HTML report for the last week
-pidgeon loft report --format html --since 7d --output report.html
+# HTML report file for the last week
+pidgeon loft report generate --format html --since 7d --output report.html
```
+
+`report generate` also takes `--template` (`interface-health`, `partner-scorecard`, or `sla-compliance`). The `report schedule`, `report list`, `report run`, and `report history` subcommands manage recurring reports.
diff --git a/cli/migrate-commands.mdx b/cli/migrate-commands.mdx
index 3e9893f..cbb200a 100644
--- a/cli/migrate-commands.mdx
+++ b/cli/migrate-commands.mdx
@@ -3,13 +3,13 @@ title: Migrate Commands
description: Export healthcare data to FHIR R4 Bulk Data NDJSON, with de-identification, reconciliation, and resume.
---
-Migrate moves healthcare data between systems via FHIR R4 Bulk Data Access (NDJSON per the HL7 IG). v1 ships the `run` export workflow reading from Centricity / athenaPractice 23.0 `FHIR_*` views.
+Migrate moves healthcare data between systems via FHIR R4 Bulk Data Access (NDJSON per the HL7 IG). v1 ships the `run` export workflow reading from Centricity / athenaPractice 23.0 `FHIR_*` views. For the concepts behind these commands, see the [Migrate section](/migrate/overview).
-Migrate requires a Pidgeon account sign-in. It is built for migration projects, not synthetic test data — for populations, see [Flock](/cli/flock-commands).
+Migrate requires a Pidgeon account sign-in. It is built for migration projects, not synthetic test data. For populations, see [Flock](/cli/flock-commands).
## pidgeon migrate run
-Export from a source EHR to FHIR R4 Bulk Data NDJSON — one file per resource type plus a `manifest.json` conforming to the HL7 FHIR Bulk Data Access IG.
+Export from a source EHR to FHIR R4 Bulk Data NDJSON, one file per resource type plus a `manifest.json` conforming to the HL7 FHIR Bulk Data Access IG.
```bash
pidgeon migrate run --source --output [options]
@@ -43,7 +43,7 @@ pidgeon migrate run --source "Host=localhost;Database=centricity;..." --output .
## pidgeon migrate analyst
-Deterministic migration analysis: assess a source, review the mapping and loss catalog, convert a bounded sample, cluster exceptions, analyze reconciliation, and assemble cutover-readiness evidence. Read/derive-only — results are local evidence artifacts.
+Deterministic migration analysis: assess a source, review the mapping and loss catalog, convert a bounded sample, cluster exceptions, analyze reconciliation, and assemble cutover-readiness evidence. Read/derive-only; results are local evidence artifacts.
```bash
pidgeon migrate analyst [options]
@@ -67,4 +67,4 @@ pidgeon migrate to-xds --bundle [options]
## Desktop app
-The Migrate desktop app runs the same `run` workflow with a preflight checklist, a live migration log, and reconciliation — see [Get started with Migrate](/getting-started/migrate).
+The Migrate desktop app runs the same `run` workflow with a preflight checklist, a live migration log, and reconciliation. See [Get started with Migrate](/getting-started/migrate).
diff --git a/cli/post-commands.mdx b/cli/post-commands.mdx
index caa97e7..03aaee1 100644
--- a/cli/post-commands.mdx
+++ b/cli/post-commands.mdx
@@ -1,8 +1,10 @@
---
title: Post Commands
-description: CLI commands for message generation, validation, de-identification, diff, and workflow management with Pidgeon Post.
+description: CLI commands for message generation, validation, de-identification, diff, and workflow management with Post.
---
+`generate`, `validate`, and `deident` are in the free CLI (`dotnet tool install --global Pidgeon.CLI`). `diff` and `workflow` ship with the Post desktop app and the licensed CLI, not the free `dotnet tool` build. Each Pro command below says so.
+
## pidgeon generate
Generate synthetic healthcare messages.
@@ -19,12 +21,12 @@ The standard is auto-detected from the message type: `ADT^A01` → HL7, `Patient
| `--count, -c ` | int | `1` | Number of messages to generate |
| `--seed, -s ` | int | Random | Reproducible seed value |
| `--vendor, -v ` | string | — | Vendor profile for realistic patterns |
-| `--mode, -m ` | string | `procedural` | Generation mode: `procedural`, `local-ai`, `api-ai` |
+| `--mode, -m ` | string | `procedural` | Generation mode: `procedural`, `model` (on-device AI), `api` (cloud AI) |
| `--hl7-version` | string | `2.3` | HL7 version: `2.3`, `2.3.1`, `2.4`, `2.5`, `2.5.1`, `2.6`, `2.7`, `2.8` |
| `--output, -o ` | string | stdout | Output file or directory |
| `--format, -f ` | string | `auto` | Output format: `auto`, `hl7`, `json`, `ndjson` |
-Generation modes `local-ai` and `api-ai` are Pro features requiring a Pidgeon account with Post Pro entitlement, or BYOK configuration.
+Generation modes `model` (on-device) and `api` (cloud, BYOK) are Pro features requiring a Pidgeon account with Post Pro entitlement. The AI modes ship with the desktop app and the licensed CLI, not the free `dotnet tool` build.
```bash
# Generate 10 HL7 admission messages
@@ -58,9 +60,11 @@ Files can be passed as positional arguments (with wildcard support) or via `--fi
| `` | positional | — | Files to validate (supports wildcards) |
| `--file, -f ` | string | — | Single file to validate |
| `--folder ` | string | — | Directory to validate |
-| `--mode ` | string | `strict` | `strict` or `compatibility` |
+| `--mode, -m ` | string | `strict` | `strict` or `compatibility` |
+| `--standard, -s ` | string | auto-detect | Force a standard: `hl7`, `fhir`, `ncpdp` |
| `--ig ` | string | — | FHIR implementation guide |
-| `--profile ` | string | — | Vendor profile for validation |
+| `--profile, -p ` | string | — | Vendor profile for validation |
+| `--report ` | string | — | Write an HTML report, or JSON when the path ends in `.json` |
```bash
# Strict validation
@@ -108,9 +112,9 @@ pidgeon deident --in ./real --out ./safe --date-shift 90d --salt "project-x"
## pidgeon diff
-Pro feature — requires a Pidgeon account with Post Pro entitlement.
+Pro feature. Requires a Pidgeon account with Post Pro entitlement, and ships with the Post desktop app and the licensed CLI, not the free `dotnet tool` build.
-Compare messages or directories with field-level analysis.
+Compare messages or directories with field-level analysis. Field-aware for HL7, JSON-tree for FHIR.
```bash
pidgeon diff [options]
@@ -124,23 +128,30 @@ Paths can be passed as positional arguments or via `--left`/`--right`.
| ` ` | positional | — | Files or directories to compare |
| `--left, -l ` | string | — | Left file or directory |
| `--right, -r ` | string | — | Right file or directory |
-| `--report, -o ` | string | — | Generate HTML report |
-| `--ai, -a` | flag | auto | Enable AI analysis |
-| `--no-ai` | flag | — | Force algorithmic only |
+| `--report, -o ` | string | — | Write an HTML or JSON diff report |
+| `--ignore, -i ` | string | — | Comma-list of fields/segments to skip (for example `MSH-7,PID-3`) |
+| `--severity, -s ` | string | `hint` | Minimum severity to report: `hint`, `warn`, `error` |
+| `--ai, -a` | flag | off | Turn on AI hints (coming in a future release) |
+| `--no-ai` | flag | — | Force algorithmic-only analysis |
```bash
# Compare two messages
pidgeon diff env-a/admit.hl7 env-b/admit.hl7
+# Ignore volatile header fields
+pidgeon diff env-a/admit.hl7 env-b/admit.hl7 --ignore MSH-7,MSH-10
+
# Generate HTML diff report
pidgeon diff ./dev ./staging --report diff-report.html
```
+AI-assisted diff hints are not yet available. The `--ai` flag is reserved for a future release; today diff runs constraint-aware field analysis without a model.
+
---
## pidgeon workflow
-Pro feature — requires a Pidgeon account with Post Pro entitlement.
+Pro feature. Requires a Pidgeon account with Post Pro entitlement, and ships with the Post desktop app and the licensed CLI, not the free `dotnet tool` build.
Create and run multi-step clinical test scenarios.
diff --git a/conform/cms-0057-f.mdx b/conform/cms-0057-f.mdx
new file mode 100644
index 0000000..604f9b7
--- /dev/null
+++ b/conform/cms-0057-f.mdx
@@ -0,0 +1,61 @@
+---
+title: CMS-0057-F
+description: What the CMS Interoperability and Prior Authorization final rule requires, the FHIR baseline it names, and what Conform checks today.
+---
+
+CMS-0057-F, the CMS Interoperability and Prior Authorization final rule (2024), requires impacted payers to operate a set of FHIR APIs. Impacted payers are Medicare Advantage organizations, state Medicaid and CHIP agencies, and QHP issuers on the federally-facilitated exchanges. The API compliance dates are generally January 1, 2027.
+
+## What the rule requires
+
+The rule requires four payer FHIR APIs:
+
+- **Patient Access API**
+- **Provider Access API**
+- **Payer-to-Payer API**
+- **Prior Authorization API**
+
+The required standards baseline is FHIR R4.0.1, US Core 3.1.1, SMART App Launch 1.0, and Bulk Data 1.0 (45 CFR 170.215, as adopted).
+
+## Required vs recommended
+
+Not everything in the Da Vinci ecosystem is mandated, and keeping that straight decides what you test against.
+
+| Standard | Status under CMS-0057-F |
+|---|---|
+| FHIR R4.0.1 | **Required** baseline |
+| US Core 3.1.1 | **Required** baseline |
+| SMART App Launch 1.0 | **Required** baseline |
+| Bulk Data 1.0 | **Required** baseline |
+| Da Vinci PAS 2.1 | **Recommended** (CMS standards/IG FAQ) |
+| Da Vinci CRD 2.1 | **Recommended** |
+| Da Vinci DTR 2.0 | **Recommended** |
+| US Core 6.1 | Ecosystem target, a permitted updated version |
+
+## What Conform covers today
+
+Conform ships the Implementation Guides that matter for this rule:
+
+| IG | Package | Role |
+|---|---|---|
+| US Core 3.1.1 | `fhir-us-core-3.1.1` | CMS-0057-F required baseline |
+| US Core 6.0 | `fhir-us-core-6.0` | Ecosystem target (USCDI v3) |
+| Da Vinci PAS 2.1 | `fhir-davinci-pas-2.1` | Prior authorization |
+| Da Vinci CRD 2.1 | `fhir-davinci-crd-2.1` | Coverage requirements discovery |
+| Da Vinci DTR 2.0 | `fhir-davinci-dtr-2.0` | Documentation templates and rules |
+
+Install an IG package with `pidgeon data install `, then point Conform at your endpoint. The US Core 3.1.1 readiness pack grades a walk against the required baseline and writes an evidence envelope. See [Evidence and CI](/conform/evidence-and-ci).
+
+## What Conform does not do
+
+Conform tests conformance to these Implementation Guides. It does not:
+
+- certify CMS-0057-F compliance, or assert that an endpoint is "compliant";
+- exercise SMART App Launch or OIDC end-user authorization flows (it authenticates with a static bearer token or SMART Backend Services);
+- run the complete Bulk Data kick-off, poll, and download lifecycle.
+
+The evidence it produces states what was tested and what was not. Treat it as conformance evidence you present, not a verdict on the regulation as a whole.
+
+## Next
+
+- [Running conformance](/conform/running-conformance)
+- [Evidence and CI](/conform/evidence-and-ci)
diff --git a/conform/evidence-and-ci.mdx b/conform/evidence-and-ci.mdx
new file mode 100644
index 0000000..43c7255
--- /dev/null
+++ b/conform/evidence-and-ci.mdx
@@ -0,0 +1,69 @@
+---
+title: Evidence and CI
+description: Conform's exit codes, HTML scorecard, readiness packs and evidence envelopes, and a CI gate you can drop into a pipeline.
+---
+
+Conform is built to run in CI and leave evidence behind. The exit code gates a pipeline; the scorecard and evidence envelope are the artifacts you keep.
+
+## Exit codes
+
+Conform extends the CLI's `0`/`1` convention with a coverage code, so a gate can tell "failed" apart from "tested nothing":
+
+| Code | Meaning |
+|------|---------|
+| `0` | The report passed |
+| `1` | The report failed; or, under `--ci`, passed with a must-support or stub-profile warning; or an endpoint/IG load error; or a failed `--probe-operations` or `--check-terminology` probe |
+| `2` | No coverage: under `--ci`, a walk validated zero resources. `--require-full-coverage` widens this to "any declared type was skipped." A real failure (`1`) always outranks the coverage gate |
+
+`--ci` is the flag that makes warnings count. Must-support warnings (rule ids prefixed `MUSTSUPPORT-`) and stub-profile warnings flip a passing report to a non-zero exit, so a subtle gap fails the build instead of sliding through.
+
+## A CI gate
+
+```bash
+pidgeon conform --endpoint "$FHIR_URL" --walk --ci || exit 1
+```
+
+In GitHub Actions:
+
+```yaml
+- name: FHIR conformance
+ run: |
+ pidgeon data install fhir-us-core-3.1.1
+ pidgeon conform --endpoint "${{ secrets.FHIR_URL }}" --walk --ci \
+ --output-file scorecard.html
+- uses: actions/upload-artifact@v4
+ with:
+ name: conform-scorecard
+ path: scorecard.html
+```
+
+## Scorecard and badge
+
+- `--output-file scorecard.html` writes a self-contained HTML scorecard you can attach to a ticket or hand to a stakeholder.
+- `--badge conform-badge.svg` writes a dated pass/fail badge (an SVG plus a shields.io endpoint JSON) whose verdict mirrors the exit code.
+
+## Readiness packs and evidence envelopes
+
+A readiness pack grades a walk against a compiled requirement set and writes a machine-readable evidence envelope with honest not-tested states:
+
+```bash
+pidgeon conform --endpoint https://api.payer.example/fhir --walk \
+ --readiness-pack us-core-3.1.1 \
+ --evidence-out conform-evidence.json
+```
+
+`us-core-3.1.1` is the CMS-0057-F required baseline pack and needs the `fhir-us-core-3.1.1` package installed. The envelope records each cited assertion as passed, failed, or not tested, so the gaps are explicit rather than implied.
+
+## Operation and terminology probes
+
+- `--probe-operations` POSTs a synthetic PAS request Bundle to `Claim/$submit` and grades the response against the PAS response Bundle profile. A failed probe flips the exit to `1`.
+- `--check-terminology` validates coded fields against a live terminology service (see [Running conformance](/conform/running-conformance)).
+
+## Rule IDs you'll see
+
+Conform reports findings with stable rule ids: `FHIR-PROFILE` (a structural profile violation), `MUSTSUPPORT-` (a must-support element absent from the sampled instance), `CONFORM_STUB_PROFILE` (validated against an embedded subset because the IG package wasn't installed), and `PROFILE_NOT_FOUND`. Under `--ci`, the must-support and stub-profile findings are the ones that flip the exit code.
+
+## Next
+
+- [Conform CLI reference](/cli/conform-commands)
+- [Running conformance](/conform/running-conformance)
diff --git a/conform/overview.mdx b/conform/overview.mdx
new file mode 100644
index 0000000..a28f268
--- /dev/null
+++ b/conform/overview.mdx
@@ -0,0 +1,56 @@
+---
+title: Conform overview
+description: Prove a FHIR implementation satisfies the Implementation Guides a program requires, explain the gaps, and keep the evidence. The CI gate you don't have to build.
+---
+
+
+

+

+
+
+Conform checks a live FHIR endpoint against the published Implementation Guides a program requires, tells you which elements pass and which fall short, and writes the result as evidence you can attach to a ticket, a CI run, or a contract. It produces conformance evidence against named IG versions. It is not a compliance certification.
+
+The wedge is CMS-0057-F. Impacted payers must operate FHIR APIs with compliance dates generally January 1, 2027, and each of those APIs has to conform to specific IG versions. Conform is the check you run against a live endpoint to see where you stand. See [CMS-0057-F](/conform/cms-0057-f) for what the rule actually requires.
+
+## Where Conform runs
+
+
+
+ `pidgeon conform` walks an endpoint from your terminal or a CI pipeline and returns a non-zero exit code on failure. No account, no hosted deployment.
+
+
+ The Conformance panel in Post wires an endpoint, runs the walk, and reads results per rule. Same engine, point-and-click.
+
+
+
+
+Conform is becoming Pidgeon's fifth product. The standalone Conform desktop app is in beta and not yet available to download. Today you run conformance from the CLI and the Conformance panel in Post, which keeps a quick endpoint check and hands the deeper evidence work to Conform.
+
+
+## What it checks
+
+- **Structural conformance** to a profile: cardinality, datatypes, fixed and pattern values, bindings, slicing, and a measured FHIRPath subset.
+- **Must-support elements**, reported honestly. One sampled instance is evidence of presence, never proof of full must-support capability.
+- **The PAS `$submit` operation**, with `--probe-operations`, graded against the PAS response Bundle profile.
+- **Coded fields** against a live terminology service, with `--check-terminology`.
+
+Every run can emit a self-contained HTML scorecard, a JSON report for machines, and a dated pass/fail badge. See [Evidence and CI](/conform/evidence-and-ci).
+
+## Evidence, not certification
+
+Conform reports conformance against the IG versions you name. It does not certify CMS-0057-F compliance and never labels an endpoint "compliant." That line is deliberate: the evidence is yours to present, and it stays honest about what was and wasn't tested.
+
+## Where Conform sits in the suite
+
+Pidgeon is five products on one engine:
+
+> Flock models it. Post exercises it. Conform proves it. Migrate moves it. Loft protects it.
+
+Conform is the "proves it" step. Once Post has built and exercised an exchange, Conform demonstrates that the FHIR side satisfies its contract.
+
+## Next
+
+- [CMS-0057-F](/conform/cms-0057-f): what the rule requires, and what Conform covers today
+- [Running conformance](/conform/running-conformance): endpoints, profiles, walks, and auth
+- [Evidence and CI](/conform/evidence-and-ci): exit codes, scorecards, readiness packs
+- [Conform CLI reference](/cli/conform-commands)
diff --git a/conform/running-conformance.mdx b/conform/running-conformance.mdx
new file mode 100644
index 0000000..8ee0234
--- /dev/null
+++ b/conform/running-conformance.mdx
@@ -0,0 +1,76 @@
+---
+title: Running conformance
+description: Point Conform at a FHIR endpoint, walk it against its CapabilityStatement, and authenticate with a bearer token or SMART Backend Services.
+---
+
+`pidgeon conform` probes a live FHIR endpoint against a published Implementation Guide. Install the IG you're testing against, then either target a single resource or walk the whole endpoint.
+
+## Install the IG you're testing against
+
+Conform grades against the IG packages you have installed:
+
+```bash
+pidgeon data install fhir-us-core-3.1.1
+```
+
+Other packages: `fhir-us-core-6.0`, `fhir-davinci-pas-2.1`, `fhir-davinci-crd-2.1`, `fhir-davinci-dtr-2.0`. See [CMS-0057-F](/conform/cms-0057-f) for which IG maps to which requirement.
+
+## One resource against one profile
+
+```bash
+pidgeon conform --endpoint https://api.payer.example/fhir \
+ --resource Patient/123 --profile us-core-patient
+```
+
+`--profile` takes an IG short name (`us-core-patient`) or a canonical URL. `--resource` is `ResourceType/id`.
+
+## Walk the whole endpoint
+
+`--walk` reads the endpoint's CapabilityStatement and probes every resource × profile pair it declares:
+
+```bash
+pidgeon conform --endpoint https://api.payer.example/fhir --walk
+```
+
+Narrow the walk with `--only-resources Patient,Encounter`, or scope it to one IG with `--ig http://hl7.org/fhir/us/core/`.
+
+## Authenticate
+
+Most real endpoints need a token. Conform supports two paths.
+
+**Static bearer token:**
+```bash
+pidgeon conform --endpoint https://api.payer.example/fhir --walk \
+ --auth "Bearer eyJhbGciOi..."
+```
+
+**SMART Backend Services** (system-to-system). Conform discovers the token endpoint from `.well-known/smart-configuration`, signs an RS384 client assertion with your private key, and exchanges it for an access token:
+```bash
+pidgeon conform --endpoint https://api.payer.example/fhir --walk \
+ --auth-smart-backend \
+ --client-id my-backend-client \
+ --key-file ./backend-private-key.pem \
+ --scope "system/*.read"
+```
+
+Pass `--token-endpoint` to skip discovery. `--auth` and `--auth-smart-backend` are mutually exclusive.
+
+## Check coded fields against terminology
+
+`--check-terminology` validates every coded field in the fetched resources against a live FHIR terminology service. A code that doesn't resolve flips the exit code to `1`:
+
+```bash
+pidgeon conform --endpoint https://api.payer.example/fhir --walk \
+ --check-terminology \
+ --terminology-endpoint http://127.0.0.1:8080/fhir \
+ --snomed-endpoint http://127.0.0.1:8181/fhir
+```
+
+## From the Post app
+
+The Conformance panel in Post runs the same walk. Wire the endpoint, pick the IG, run it, and read the pass/fail per rule with streaming results. See [Get started with Post](/getting-started/post).
+
+## Next
+
+- [Evidence and CI](/conform/evidence-and-ci): exit codes, scorecards, readiness packs, and badges
+- [Conform CLI reference](/cli/conform-commands): every flag
diff --git a/docs.json b/docs.json
index 87674d2..d3c64f8 100644
--- a/docs.json
+++ b/docs.json
@@ -38,7 +38,8 @@
"icon": "download",
"pages": [
"getting-started/install-windows",
- "getting-started/install-macos"
+ "getting-started/install-macos",
+ "getting-started/install-linux"
]
},
{
@@ -47,6 +48,7 @@
"pages": [
"getting-started/launcher",
"getting-started/post",
+ "getting-started/conform",
"getting-started/flock",
"getting-started/loft",
"getting-started/migrate"
@@ -58,6 +60,7 @@
"pages": [
"post/message-generation",
"post/validation",
+ "post/diff",
"post/de-identification",
"post/vendor-profiles",
"post/workflow-wizard",
@@ -65,6 +68,16 @@
"post/datasets"
]
},
+ {
+ "group": "Conform (Conformance)",
+ "icon": "circle-check",
+ "pages": [
+ "conform/overview",
+ "conform/cms-0057-f",
+ "conform/running-conformance",
+ "conform/evidence-and-ci"
+ ]
+ },
{
"group": "Flock (Population Engine)",
"icon": "users",
@@ -84,10 +97,22 @@
"loft/alerting"
]
},
+ {
+ "group": "Migrate (Bulk Data Migration)",
+ "icon": "arrow-right-arrow-left",
+ "pages": [
+ "migrate/overview",
+ "migrate/bulk-data",
+ "migrate/mapping"
+ ]
+ },
{
"group": "Guides & Tutorials",
"icon": "book-open",
"pages": [
+ "guides/public-packages-quickstart",
+ "guides/healthcare-interface-test-data-field-guide",
+ "guides/local-first-human-agent-workflow",
"guides/generate-realistic-test-data",
"guides/de-identify-real-messages",
"guides/build-test-scenarios",
@@ -122,7 +147,8 @@
"pages": [
"api-reference/generate",
"api-reference/validate",
- "api-reference/diff"
+ "api-reference/diff",
+ "api-reference/ai-triage"
]
},
{
@@ -132,7 +158,6 @@
"api-reference/loft-interfaces",
"api-reference/loft-alerts",
"api-reference/loft-status",
- "api-reference/ai-triage",
"api-reference/analytics",
"api-reference/traces"
]
@@ -144,14 +169,6 @@
"api-reference/flock"
]
},
- {
- "group": "Admin & Enterprise",
- "icon": "shield-check",
- "pages": [
- "api-reference/admin",
- "api-reference/enterprise"
- ]
- },
{
"group": "Live Updates",
"icon": "bolt",
@@ -174,6 +191,7 @@
"cli/flock-commands",
"cli/loft-commands",
"cli/migrate-commands",
+ "cli/ai-commands",
"cli/data-commands",
"cli/config-commands"
]
diff --git a/flock/output-formats.mdx b/flock/output-formats.mdx
index 54dd802..0d8bae7 100644
--- a/flock/output-formats.mdx
+++ b/flock/output-formats.mdx
@@ -49,22 +49,27 @@ Transaction bundles for FHIR server seeding.
pidgeon flock generate --count 200 --format fhir --output ./fhir-data/
```
-Generates FHIR Transaction Bundles with proper reference integrity across the same 24 spec-validated resource types Post generates, including Patient, Encounter, Condition, Observation, MedicationRequest, Procedure, DiagnosticReport, AllergyIntolerance, Immunization, Organization, Practitioner, Location, and Coverage.
+Generates FHIR Transaction Bundles with proper reference integrity across the same 137 spec-validated resource types Post generates, including Patient, Encounter, Condition, Observation, MedicationRequest, Procedure, DiagnosticReport, AllergyIntolerance, Immunization, Organization, Practitioner, Location, and Coverage.
-## Seeding and Cleanup
+## Seeding and cleanup
+
+Seed a target database directly, or point `seed` at a directory that `generate -o` wrote:
```bash
-# Seed the connected database
-pidgeon flock seed
+# Preview the SQL without executing
+pidgeon flock seed --target postgres --connection "Host=localhost;Database=ehr;..." --dry-run
+
+# Seed the target database from generated records
+pidgeon flock seed --target postgres --connection "Host=localhost;Database=ehr;..." --from ./seed-data/
+```
-# Preview SQL without executing
-pidgeon flock seed --dry-run
+Cleanup is its own command. It removes the records Flock tagged as synthetic:
-# Remove all synthetic data
-pidgeon flock seed --cleanup
+```bash
+pidgeon flock cleanup --provider postgres --connection "Host=localhost;Database=ehr;..."
```
-Cleanup removes all records tagged as synthetic. This cannot be undone.
+Cleanup removes every record tagged as synthetic. This cannot be undone.
## Generation Analytics
diff --git a/flock/overview.mdx b/flock/overview.mdx
index 7a9e568..f3f099b 100644
--- a/flock/overview.mdx
+++ b/flock/overview.mdx
@@ -1,43 +1,57 @@
---
title: Flock Overview
-description: Seed test databases that look like production in minutes — not months. Zero PHI, instant compliance approval.
+description: Seed a test database that looks like production without copying a single real record. No PHI, no production-snapshot sign-off to wait on.
---
-Connect to your database, and Flock generates populations that match your schema — with realistic demographics, comorbidity correlations, and temporal coherence built in. Output as SQL INSERT (FK-ordered), CSV, HL7 streams, or FHIR Bundles.
+An empty test database doesn't catch real bugs. A database full of copied production data is a compliance problem and a security review you have to sit through. Flock is the third option: point it at your schema and it generates a synthetic population that fits your tables, keeps every foreign key valid, and contains no PHI because no real record ever entered the pipeline.
-## Key Features
+## One loop: schema in, seeded database out
-- **Schema-aware** — Connects to your database, analyzes the schema, and generates data that fits your table structures
-- **Epidemiologically grounded** — Age, gender, race, and geographic distributions match real US Census data
-- **Comorbidity correlation** — Diabetes correlates with hypertension, obesity with sleep apnea
-- **Temporal coherence** — Admissions before discharges, lab orders before results
-- **Family linkage** — Realistic household structures and family relationships
-- **Multiple outputs** — SQL INSERT (FK-ordered), CSV, HL7 streams, FHIR Bundles
-
-## Use Cases
-
-- QA and integration testing with realistic volumes
-- Development environment seeding
-- Demo environments for sales and training
-- Load testing with production-scale datasets
-- Training new staff on EHR systems
-
-## Workflow
+Flock reads your database schema, a live connection or a SQL DDL file, and maps the foreign keys into a dependency graph. It generates records in that dependency order so every reference resolves. You get the population as FK-ordered SQL INSERTs, CSV, HL7 v2 message streams, or FHIR transaction Bundles, and you can seed a connected database directly.
```bash
# 1. Connect to your database
-pidgeon flock connect --provider postgres --connection-string "Host=localhost;Database=ehr;..."
+pidgeon flock connect --provider postgres --connection "Host=localhost;Database=ehr;..."
-# 2. Optionally learn from existing data
-pidgeon flock learn --tables patients,encounters --sample-size 500
+# 2. Optionally learn distributions from existing rows
+pidgeon flock learn --sample 500
-# 3. Generate synthetic population
-pidgeon flock generate --count 1000 --format sql
+# 3. Generate a synthetic population
+pidgeon flock generate --count 1000 --format sql --output ./seed-data/
-# 4. Seed the database
-pidgeon flock seed
+# 4. Seed the target database
+pidgeon flock seed --target postgres --connection "Host=localhost;Database=ehr;..." --from ./seed-data/
```
-## Pricing
+## Why the data looks real
+
+The generated cohort isn't uniform noise. Demographics track US Census age, sex, race, and geographic distributions, and clinical content is grounded in a 108-condition comorbidity matrix built from public epidemiology (CDC WONDER, NHANES, CDC surveillance). Diabetes pulls in hypertension, obesity pulls in sleep apnea, and temporal order holds across the record: admissions precede discharges, lab orders precede results, medication start dates precede end dates. That grounding is why a QA run against Flock data surfaces the failures a hand-built handful of test patients never will. It is a credibility proof-point, not the headline. The headline is schema-aware, FK-safe, no-PHI data in your target format.
+
+## When something fails
+
+| What you see | What it means | Next action |
+|---|---|---|
+| `connect` returns a provider error | The provider value or connection string didn't resolve | Use `postgres`, `sqlserver`, or `mysql`, and confirm the connection string. See [Schema Intelligence](/flock/schema-intelligence). |
+| A foreign key fails on seed | The target schema drifted from what Flock introspected | Re-run `connect` against the current schema, then regenerate. |
+| Generation stops at a record cap | You hit your plan's generation limit | Reduce `--count`, or check your plan in the account portal. |
+
+## Getting Flock
+
+Flock is a paid product and requires a Pidgeon account sign-in. Post's free CLI (message generation and validation) does not include Flock; the `flock` command is delivered through the Flock desktop app and the Pro CLI. See [Get started with Flock](/getting-started/flock).
+
+## Next steps
-Flock is $49/mo self-serve, plus metered API usage at scale. It requires a Pidgeon account sign-in — Post's free CLI does not unlock Flock.
+
+
+ How Flock classifies tables and maps foreign keys.
+
+
+ Demographics, correlated conditions, and temporal coherence.
+
+
+ SQL, CSV, HL7 v2, and FHIR Bundles.
+
+
+ From an empty schema to a seeded population.
+
+
diff --git a/flock/population-generation.mdx b/flock/population-generation.mdx
index 178b912..1035833 100644
--- a/flock/population-generation.mdx
+++ b/flock/population-generation.mdx
@@ -1,50 +1,44 @@
---
title: Population Generation
-description: Generate patient populations that look like your real data — age distributions, comorbidity correlations, temporal coherence — without a single real patient.
+description: "Generate a patient population that behaves like your real data: census demographics, correlated conditions, and temporal order, with no real patient in the pipeline."
---
-Demographics from US Census, condition correlations from CDC WONDER and NHANES, temporal ordering enforced across all clinical events.
+Flock generates a cohort, not a pile of independent rows. Demographics come from US Census distributions, condition correlations from a 108-condition comorbidity matrix grounded in public epidemiology (CDC WONDER, NHANES, CDC surveillance), and temporal order is enforced across every clinical event. The result reads like a population a real facility would see, which is what makes it useful for testing.
## Demographics
-Population demographics are drawn from US Census data:
-- **Age distribution** — Matches census age brackets for the selected geographic region
-- **Gender ratio** — Reflects actual population ratios
-- **Race/ethnicity** — Census-derived distributions
-- **Geographic distribution** — ZIP code and county-level population data
+Age, sex, race, and geography are drawn from US Census distributions for the selected region. Set the geographic focus with a state abbreviation:
-## Comorbidity Correlation
+```bash
+pidgeon flock generate --count 1000 --format sql --state TX
+```
-Conditions are correlated realistically:
-- Diabetes → Hypertension (70% co-occurrence)
-- Obesity → Sleep apnea, Type 2 diabetes
-- Smoking → COPD, lung cancer
-- Age → Increased chronic conditions
+Age brackets, sex ratios, and the race and ethnicity mix track the census figures for that region rather than a flat random spread.
-## Temporal Coherence
+## Correlated conditions
-All temporal relationships are maintained:
-- Admission timestamps precede discharge timestamps
-- Lab orders precede lab results
-- Medication start dates precede end dates
-- Patient age is consistent with date of birth
+Conditions co-occur the way they do in real patients. The comorbidity matrix carries conditional probabilities between condition pairs, so a generated patient with type 2 diabetes is likely to also carry hypertension, obesity brings sleep apnea and fatty liver disease along with it, and a COPD patient trends toward nicotine dependence and, less often, lung cancer. This is the credibility layer, not the headline: the point of Flock is schema-aware, FK-safe, no-PHI data, and the epidemiological grounding is what keeps that data from looking synthetic.
-## Family Linkage
+## Temporal coherence
-Realistic household structures:
-- Spouse relationships with shared addresses
-- Parent-child relationships with age-appropriate gaps
-- Emergency contact cross-references
+Every generated timeline holds together. Admission timestamps precede discharge timestamps, lab orders precede their results, medication start dates precede end dates, and a patient's age stays consistent with their date of birth. A downstream system that validates ordering sees data it can actually process.
-## CLI Usage
+## Family linkage
-```bash
-# Generate 1000 patients
-pidgeon flock generate --count 1000 --format sql --geographic-focus us
+Households are modeled, not scattered. Spouses share addresses, parent and child records carry age-appropriate gaps, and emergency-contact fields reference other generated people rather than dangling.
+
+## Reproducible runs
+
+Pass a seed to get the identical population every time, which makes a generated dataset something you can commit to a test fixture:
-# Reproducible generation
+```bash
pidgeon flock generate --count 500 --format csv --seed 42
+```
+
+## FHIR output
-# Generate as FHIR bundles
+```bash
pidgeon flock generate --count 200 --format fhir --output ./fhir-data/
```
+
+Generates FHIR transaction Bundles across the 137 spec-validated resource types Post generates, with references resolved inside each Bundle.
diff --git a/flock/schema-intelligence.mdx b/flock/schema-intelligence.mdx
index f9caea2..7ae57e6 100644
--- a/flock/schema-intelligence.mdx
+++ b/flock/schema-intelligence.mdx
@@ -1,40 +1,49 @@
---
title: Schema Intelligence
-description: Point Flock at your database and it figures out the schema — table relationships, healthcare classifications, and column semantics — automatically.
+description: "Point Flock at your database and it maps the schema for you: table relationships, healthcare classifications, and column semantics."
---
-Classifies tables as patient, encounter, clinical, financial, or reference — then maps foreign keys and infers column semantics like MRN fields, coded values, and date columns.
+Flock reads your schema before it generates anything. It classifies each table as patient, encounter, clinical, financial, or reference, maps the foreign keys into a dependency graph, and infers what each column holds: MRN fields, coded values, date columns, free text. That graph is what keeps every generated row FK-safe.
-## Supported Databases
+## Supported databases
-| Database | Provider String |
-|----------|----------------|
+Flock introspects three database engines. Schema inference, sample extraction, and seeding are implemented for each.
+
+| Database | `--provider` value |
+|----------|--------------------|
| PostgreSQL | `postgres` |
| SQL Server | `sqlserver` |
+| MySQL | `mysql` |
+
+MariaDB connects through the `mysql` provider. `postgresql` and `mssql` are accepted as aliases for `postgres` and `sqlserver`.
## Connect
```bash
pidgeon flock connect \
--provider postgres \
- --connection-string "Host=localhost;Port=5432;Database=ehr;Username=dev;Password=${DB_PASSWORD}"
+ --connection "Host=localhost;Port=5432;Database=ehr;Username=dev;Password=${DB_PASSWORD}"
```
-## What Flock Detects
+## What Flock reads
+
+Connecting runs a full introspection pass against the database catalog:
+
+- **Table classification.** Each table is tagged patient, encounter, clinical, financial, or reference from its columns and naming.
+- **Relationship mapping.** Foreign keys become a dependency order, so an insert never precedes the row it references.
+- **Column semantics.** Flock identifies MRN fields, date columns, coded values, and free text from types and constraints.
+- **Healthcare patterns.** Common EHR naming conventions are recognized so the classification holds on real vendor schemas.
-- **Table classification** — Patient, encounter, clinical, financial, or reference tables
-- **Relationship mapping** — Foreign key detection and dependency ordering
-- **Column type inference** — Identifies MRN fields, date columns, coded values, free text
-- **Healthcare patterns** — Recognizes common EHR table naming conventions
+Run `pidgeon flock schema --classify` to print the classification, or `pidgeon flock schema --visualize` to emit the schema as a Mermaid ER diagram.
## API
```bash
-# Connect and analyze
+# Connect and introspect
curl -X POST http://localhost:5102/api/flock/connect \
-H "Content-Type: application/json" \
-d '{"provider": "postgres", "connectionString": "Host=localhost;Database=ehr;..."}'
-# Retrieve analyzed schema
+# Retrieve the classified schema
curl http://localhost:5102/api/flock/schema
```
diff --git a/getting-started/account.mdx b/getting-started/account.mdx
index a234200..e985810 100644
--- a/getting-started/account.mdx
+++ b/getting-started/account.mdx
@@ -12,7 +12,7 @@ Your Pidgeon account lives at [account.pidgeon.health](https://account.pidgeon.h
Open [account.pidgeon.health](https://account.pidgeon.health). Four ways in:
- **Email and password**
- - **Magic link** — enter your email, click the link it sends, no password
+ - **Magic link**: enter your email, click the link it sends, no password
- **Google**
- **Microsoft**
@@ -22,15 +22,13 @@ Your Pidgeon account lives at [account.pidgeon.health](https://account.pidgeon.h
The account view shows the plan you're on and the entitlements it carries per product, so you know what each app includes when you sign in there.
- {/* BETA-GATE(Stage 4): subscribe + live entitlement state ride on the Stripe live smoke. Until that gate clears, describe the plan view as read-only and do not claim self-serve purchase. */}
Self-serve subscription and billing management arrive with the paid beta. Until then the plan view is read-only; to change a plan, email [support@pidgeon.health](mailto:support@pidgeon.health).
- The downloads catalog is public — you can reach it signed out. It lists each app, its current version, and a SHA-256 checksum per file.
+ The downloads catalog is public; you can reach it signed out. It lists each app, its current version, and a SHA-256 checksum per file.
- {/* BETA-GATE(Stage 2): catalog populates when signed artifacts + checksums publish to downloads.pidgeon.health. The honest empty state below is the current verified behavior. */}
- Before the first signed artifacts publish, the catalog shows an honest **"No artifacts published yet"** empty state rather than dead links. Once builds land, download the installer for each app you want and follow [Install on Windows](/getting-started/install-windows) or [Install on macOS](/getting-started/install-macos).
+ Before the first signed artifacts publish, the catalog shows an honest **"No artifacts published yet"** empty state rather than dead links. Once builds land, download the installer for each app you want and follow [Install on Windows](/getting-started/install-windows) or [Install on macOS](/getting-started/install-macos). On Linux, install the [CLI](/getting-started/install-linux) instead.
@@ -42,12 +40,11 @@ Your Pidgeon account lives at [account.pidgeon.health](https://account.pidgeon.h
| The downloads catalog reads **"No artifacts published yet"** | No signed build has published to the catalog yet | This is expected during the beta ramp; check back, or watch [Known issues](/support/known-issues) for the publish status. |
| An account page shows a bounded error with a **Retry** | The account service couldn't be reached | Retry once you're back online; your session and plan data are unaffected. |
-{/* BETA-GATE(Stage 4 / app-nucleus + commerce): entitlement-linked downloads, a devices/versions surface, and an in-portal support-contact affordance are not live yet. Document them only when those slices ship; do not claim them here. */}
Entitlement-linked downloads and a devices-and-versions view are planned beta work and are not in the portal yet.
## Next steps
- [Get started with Pidgeon (the launcher)](/getting-started/launcher)
-- [Get started with Post](/getting-started/post) — no account needed
-- [Troubleshooting](/support/troubleshooting) — what each app shows when something's off
+- [Get started with Post](/getting-started/post): no account needed
+- [Troubleshooting](/support/troubleshooting): what each app shows when something's off
- [FAQ](/support/faq)
diff --git a/getting-started/conform.mdx b/getting-started/conform.mdx
new file mode 100644
index 0000000..29acffe
--- /dev/null
+++ b/getting-started/conform.mdx
@@ -0,0 +1,60 @@
+---
+title: Get started with Conform
+description: Run FHIR conformance evidence today from the CLI or the Conformance panel in Post. The standalone Conform app is in beta.
+---
+
+Conform proves a FHIR implementation satisfies the Implementation Guides a program requires and leaves you the evidence. It is Pidgeon's fifth product, focused on the CMS-0057-F readiness wedge.
+
+
+The standalone Conform desktop app is in beta and not yet available to download. You can run the full conformance capability today from the CLI (`pidgeon conform`) and the Conformance panel in Post.
+
+
+## Run it today
+
+
+
+ Walk an endpoint in one command, with a non-zero exit code for CI.
+
+
+ Wire an endpoint in the Conformance panel and read results per rule.
+
+
+
+## One loop: install, walk, keep the evidence
+
+
+
+ ```bash
+ pidgeon data install fhir-us-core-3.1.1
+ ```
+ US Core 3.1.1 is the CMS-0057-F required baseline. See [CMS-0057-F](/conform/cms-0057-f) for the full IG map.
+
+
+ ```bash
+ pidgeon conform --endpoint https://api.payer.example/fhir --walk --ci
+ ```
+ `--walk` probes every resource × profile pair the endpoint's CapabilityStatement declares; `--ci` makes must-support warnings fail the run.
+
+
+ ```bash
+ pidgeon conform --endpoint https://api.payer.example/fhir --walk \
+ --readiness-pack us-core-3.1.1 --evidence-out conform-evidence.json \
+ --output-file scorecard.html
+ ```
+ You get a machine-readable evidence envelope and a self-contained HTML scorecard.
+
+
+
+## When something fails
+
+| What you see | What it means | Next action |
+|---|---|---|
+| Exit code `2` | The walk validated zero resources. Nothing was declared in the CapabilityStatement, or every declared type returned an empty search | Confirm the endpoint's CapabilityStatement and that the resources exist. A run that tested nothing is not evidence. |
+| `MUSTSUPPORT-` findings under `--ci` | A must-support element was absent from the sampled instance | These flip the exit code by design. Populate the element, or record it as a known gap in the evidence envelope. |
+| `CONFORM_STUB_PROFILE` warning | A resource validated against an embedded subset because the IG package wasn't installed | Install the owning IG package with `pidgeon data install ` and re-run. |
+
+## Next
+
+- [Conform overview](/conform/overview)
+- [Running conformance](/conform/running-conformance)
+- [Evidence and CI](/conform/evidence-and-ci)
diff --git a/getting-started/install-linux.mdx b/getting-started/install-linux.mdx
new file mode 100644
index 0000000..57cf259
--- /dev/null
+++ b/getting-started/install-linux.mdx
@@ -0,0 +1,70 @@
+---
+title: Install on Linux
+description: Install the Pidgeon CLI on Linux with the published .NET tool. Linux is a CLI target; there are no Linux desktop apps.
+---
+
+On Linux, Pidgeon is the CLI. The desktop apps (Post, Flock, Loft, Migrate, and the Pidgeon launcher) run on macOS and Windows only. The CLI gives you the free generation, validation, and de-identification loop from a terminal, and it drops straight into CI.
+
+Current CLI beta release: `0.1.0-beta.2`.
+
+## What the free CLI includes
+
+The community CLI ships 12 commands: `generate`, `validate`, `deident`, `data`, `artifacts`, `lookup`, `find`, `path`, `run`, `session`, `completions`, and `capabilities`. That covers synthetic message generation, spec validation, on-device de-identification, standards lookup, and data-package management.
+
+`conform`, `flock`, `loft`, `migrate`, `ai`, `diff`, and `config` are delivered through the desktop apps, which are macOS and Windows only. If you install the CLI with `dotnet tool` on Linux and run `pidgeon conform`, it won't be there. Run conformance from the CLI that ships with the desktop apps, or from the Conformance panel in Post.
+
+## Requirements
+
+- A 64-bit Linux distribution (x64 or arm64)
+- For the `dotnet tool` install: the [.NET 8 runtime or SDK](https://dotnet.microsoft.com/download/dotnet/8.0)
+- AI features are not part of the free CLI, so no extra RAM is required
+
+## Install with the .NET tool
+
+Cross-platform, kept current through NuGet. Needs the .NET 8 runtime on the machine.
+
+
+
+ ```bash
+ dotnet tool install --global Pidgeon.CLI --version 0.1.0-beta.2
+ ```
+
+
+
+ Global .NET tools install to `~/.dotnet/tools`. If `pidgeon` isn't found after install, add that directory to your shell profile:
+
+ ```bash
+ echo 'export PATH="$PATH:$HOME/.dotnet/tools"' >> ~/.bashrc
+ source ~/.bashrc
+ ```
+
+
+
+ ```bash
+ pidgeon --version
+ ```
+
+ If `pidgeon` runs but reports that it can't find a runtime, set `DOTNET_ROOT` to your dotnet install path. See [Troubleshooting](/support/troubleshooting) for the exact fix.
+
+
+
+
+The `0.1.0-beta.2` GitHub release includes a signed Windows ZIP, but it does not
+include a Linux archive. Use the published .NET tool on Linux until a Linux
+self-contained artifact appears in a later release.
+
+
+
+The CLI runs the engine in-process. There is no Bridge sidecar and no local port on Linux. The loopback Bridge ports (Loft `5100`, Post `5101`, Flock `5102`, Migrate `5103`, Conform `5104`) belong to the macOS and Windows desktop apps.
+
+
+## Next steps
+
+
+
+ Generate and validate your first message, then wire the exit codes into CI.
+
+
+ See the full command surface and global options.
+
+
diff --git a/getting-started/install-macos.mdx b/getting-started/install-macos.mdx
index a71726a..d80d260 100644
--- a/getting-started/install-macos.mdx
+++ b/getting-started/install-macos.mdx
@@ -3,8 +3,6 @@ title: Install on macOS
description: Download the signed, notarized macOS apps from the downloads catalog, verify checksums, and launch.
---
-{/* BETA-GATE(Stage 2): downloads.pidgeon.health catalog goes live with artifacts + checksums. */}
-
Pidgeon ships five macOS desktop apps: **Post**, **Flock**, **Loft**, **Migrate**, and the **Pidgeon** launcher. Each is a separate download. Install only what you need.
Current beta release: `0.2.0-beta.1`.
@@ -19,6 +17,8 @@ Current beta release: `0.2.0-beta.1`.
Get the apps from the downloads catalog at [downloads.pidgeon.health](https://downloads.pidgeon.health). The catalog lists every app, its current version, and a SHA-256 checksum per file.
+
+ Early in the beta ramp, before signed builds have published, the catalog shows a "No artifacts published yet" state rather than dead links. Check [Known issues](/support/known-issues) for publish status.
@@ -34,7 +34,7 @@ Current beta release: `0.2.0-beta.1`.
- The macOS apps are signed with an Apple Developer ID certificate (**Pattern Engine LLC**) and notarized by Apple, so Gatekeeper opens them normally — you won't see the "cannot be opened because Apple cannot verify it" block. On the very first launch macOS may show a one-time "downloaded from the internet" confirmation; click **Open**.
+ The macOS apps are signed with an Apple Developer ID certificate (**Pattern Engine LLC**) and notarized by Apple, so Gatekeeper opens them normally. You won't see the "cannot be opened because Apple cannot verify it" block. On the very first launch macOS may show a one-time "downloaded from the internet" confirmation; click **Open**.
To confirm the signature and notarization yourself:
@@ -45,7 +45,7 @@ Current beta release: `0.2.0-beta.1`.
- Each app starts its local Bridge sidecar (the engine process) on a loopback port: Loft on `localhost:5100`, Post on `localhost:5101`, Flock on `localhost:5102`. The Bridge binds to loopback only; nothing listens on your network.
+ Each app starts its local Bridge sidecar (the engine process) on a loopback port: Loft on `localhost:5100`, Post on `localhost:5101`, Flock on `localhost:5102`, and Migrate on `localhost:5103`. Conform's Bridge uses `localhost:5104`; the standalone Conform app is in beta, so today conformance runs inside Post. The Bridge binds to loopback only; nothing listens on your network.
Post works without an account. Flock, Loft, Migrate, and the launcher ask you to sign in with your Pidgeon account.
diff --git a/getting-started/install-windows.mdx b/getting-started/install-windows.mdx
index d1ce8da..79a027f 100644
--- a/getting-started/install-windows.mdx
+++ b/getting-started/install-windows.mdx
@@ -3,8 +3,6 @@ title: Install on Windows
description: Download the signed installers from the downloads catalog, verify the publisher and checksum, and know what to expect from SmartScreen.
---
-{/* BETA-GATE(Stage 2): downloads.pidgeon.health catalog goes live with signed artifacts + checksums. Resolve this placeholder by confirming the catalog URL and artifact names at beta publish. */}
-
Pidgeon ships five Windows desktop apps: **Post**, **Flock**, **Loft**, **Migrate**, and the **Pidgeon** launcher. Each is a separate installer. Install only what you need; the launcher can detect and open the others later.
Current beta release: `0.2.0-beta.1`.
@@ -21,7 +19,7 @@ Current beta release: `0.2.0-beta.1`.
Get installers from the downloads catalog at [downloads.pidgeon.health](https://downloads.pidgeon.health). The catalog lists every app, its current version, and a SHA-256 checksum per file.
- Download the `.exe` installer for each app you want.
+ Download the `.exe` installer for each app you want. Early in the beta ramp, before signed builds have published, the catalog shows a "No artifacts published yet" state rather than dead links. Check [Known issues](/support/known-issues) for publish status.
@@ -39,7 +37,7 @@ Current beta release: `0.2.0-beta.1`.
- Each app starts its local Bridge sidecar (the engine process) on a loopback port: Loft on `localhost:5100`, Post on `localhost:5101`, Flock on `localhost:5102`. The Bridge binds to loopback only; nothing listens on your network.
+ Each app starts its local Bridge sidecar (the engine process) on a loopback port: Loft on `localhost:5100`, Post on `localhost:5101`, Flock on `localhost:5102`, and Migrate on `localhost:5103`. Conform's Bridge uses `localhost:5104`; the standalone Conform app is in beta, so today conformance runs inside Post. The Bridge binds to loopback only; nothing listens on your network.
Post works without an account. Flock, Loft, Migrate, and the launcher ask you to sign in with your Pidgeon account.
diff --git a/getting-started/introduction.mdx b/getting-started/introduction.mdx
index 7c5e2d5..c879f31 100644
--- a/getting-started/introduction.mdx
+++ b/getting-started/introduction.mdx
@@ -1,59 +1,69 @@
---
title: Introduction
-description: Pidgeon Health replaces manual test data creation, production data copying, and blind interface monitoring with a single platform — zero PHI, zero setup.
+description: Pidgeon Health replaces manual test data creation, production data copying, and blind interface monitoring with one engine and five products. Zero PHI on the synthetic path.
---
-If you work with HL7, FHIR, or NCPDP, you've probably spent hours creating test messages by hand, copied production data you shouldn't have, or discovered an interface was down because a nurse called. Pidgeon replaces all of that.
+If you work with HL7, FHIR, or NCPDP, you've probably spent hours building test messages by hand, copied production data you shouldn't have, or found out an interface was down because a nurse called. Pidgeon replaces all of that.
-## Four Products, One Engine
+## Five products, one engine
- **Testing & Validation** — Generate HL7 v2.3–v2.8, FHIR R4, and NCPDP SCRIPT messages in seconds, validate against the published spec or real vendor patterns, de-identify on-device. Includes **Conform**, the FHIR implementation-guide conformance checker.
+ **Testing and validation.** Generate HL7 v2.3–v2.8, FHIR R4, and NCPDP SCRIPT messages in seconds, validate against the published spec or real vendor patterns, and de-identify on-device.
- *Free generation and validation, no account required. Pro unlocks the Workflow Wizard, Diff, AI Triage, and full datasets.*
+ *Free generation and validation, no account required. Pro adds the Workflow Wizard, Diff, AI Triage, and full datasets.*
+
+
+ **FHIR conformance.** Prove a live FHIR endpoint satisfies the Implementation Guides a program requires, from CI, with a non-zero exit code and an evidence scorecard. The wedge is CMS-0057-F.
+
+ *Conformance evidence against named IG versions, never a compliance certification.*
- **Synthetic Population Engine** — Seed test databases with schema-aware, FK-safe patient populations. Compliance signs off in minutes because there's no PHI to review.
+ **Synthetic population engine.** Seed test databases with schema-aware, FK-safe patient populations. There's no PHI to review, so compliance signs off in minutes.
*Output as SQL, CSV, HL7 streams, or FHIR Bundles.*
- **Interface Observability** — Loft watches your configured sources, flags suspect interface messages for human review, and alerts your team. Every catch lands in a review queue with a suggested fix.
+ **Interface observability.** Loft watches your configured sources, flags suspect interface messages for human review, and alerts your team. Every catch lands in a review queue with a suggested fix.
*Built for teams running Mirth, Rhapsody, and similar engines.*
- **FHIR Bulk Data Migration** — Move healthcare data between systems via FHIR R4 Bulk Data Access (NDJSON per the HL7 IG), with preflight checks, de-identification, reconciliation, and resume.
+ **FHIR Bulk Data migration.** Move healthcare data between systems via FHIR R4 Bulk Data Access (NDJSON per the HL7 IG), with preflight checks, de-identification, reconciliation, and resume.
*Built for migration projects, not synthetic test data.*
-Post, Flock, Loft, and Migrate are desktop apps, opened directly or through **Pidgeon** — the launcher app that shows every product's install and entitlement status in one grid. See [Get started with Pidgeon (the launcher)](/getting-started/launcher).
+The five products are desktop apps, opened directly or through **Pidgeon**, the launcher that shows every product's install and entitlement status in one grid. See [Get started with Pidgeon (the launcher)](/getting-started/launcher).
+
+
+Conform is Pidgeon's newest product. Its conformance capability ships today in the CLI (`pidgeon conform`) and the Conformance panel in Post. The standalone Conform desktop app is in beta and not yet available to download.
+
+
+## How the products connect
-## How the Products Connect
+The products share one engine, so you configure it once and use it everywhere:
-All four products share a core engine — configure it once, use it everywhere:
+> Flock models it. Post exercises it. Conform proves it. Migrate moves it. Loft protects it.
-- **Shared parsing and validation** — The same HL7/FHIR/NCPDP parsers power Post's validation, Flock's output, Loft's message analysis, and Migrate's conversion
-- **Shared de-identification** — On-device PHI removal available across every product
-- **Shared vendor profiles** — Learn your vendor's patterns once, apply them across generation, validation, and monitoring
-- **Cross-product workflows** — Generate a population with Flock, test the messages with Post, monitor the feed with Loft
+- **Shared parsing and validation.** The same HL7/FHIR/NCPDP parsers power Post's validation, Conform's profile checks, Flock's output, Loft's message analysis, and Migrate's conversion.
+- **Shared de-identification.** On-device PHI removal, available across every product.
+- **Shared vendor profiles.** Learn your vendor's patterns once, apply them across generation, validation, and monitoring.
-Each product has its own buyer and budget — this is a shared engine with a retention story, not a purchasing pipeline you walk end to end.
+Each product has its own buyer and budget. This is a shared engine with a retention story, not a pipeline one customer walks end to end.
-## Who Is Pidgeon For?
+## Who is Pidgeon for?
Stop hand-crafting test messages. Generate realistic data on demand, validate against your vendor's actual patterns, and go into go-lives prepared.
- Carry your testing toolkit from client to client. Vendor profiles are portable across engagements — no more starting from scratch at every new site.
+ Carry your testing toolkit from client to client. Vendor profiles are portable across engagements, so you're not starting from scratch at every new site.
- Eliminate PHI from test environments without a 4-month approval process. Monitor interface health from a single dashboard instead of waiting for incident reports.
+ Keep PHI out of test environments without a four-month approval process. Watch interface health from one place instead of waiting for incident reports.
Seed test databases that look like production in minutes. New developers are productive on day one instead of spending their first week building test data.
@@ -62,8 +72,8 @@ Each product has its own buyer and budget — this is a shared engine with a ret
## Free CLI, desktop apps for everyone else
-- **CLI** — Always free. Install the `Pidgeon.CLI` tool with `dotnet tool install --global Pidgeon.CLI --version 0.1.0-beta.1` and you're generating messages in under a minute.
-- **Desktop apps** — Post, Flock, Loft, and Migrate for the majority who'd rather point and click. Post's core loop (generate, validate, conform) works with no account; Post Pro starts at $29/mo, and Flock, Loft, and Migrate require a Pidgeon account sign-in.
+- **CLI.** Always free. Install the `Pidgeon.CLI` tool with `dotnet tool install --global Pidgeon.CLI --version 0.1.0-beta.2`. The free CLI carries the core commands (generate, validate, de-identify, and more); the product-specific commands ship with their desktop apps.
+- **Desktop apps.** Post, Flock, Loft, and Migrate for the majority who'd rather point and click. Post's core loop (generate, validate, run a conformance check) works with no account; Post Pro starts at $29/mo, and Flock, Loft, and Migrate require a Pidgeon account sign-in.
diff --git a/getting-started/launcher.mdx b/getting-started/launcher.mdx
index 3fd4647..c8143d2 100644
--- a/getting-started/launcher.mdx
+++ b/getting-started/launcher.mdx
@@ -3,7 +3,7 @@ title: Get started with Pidgeon (the launcher)
description: One sign-in, one place to see which Pidgeon apps are installed, what version they're on, and what your account includes.
---
-Pidgeon is the launcher app: one sign-in and a single grid showing all four products (Post, Flock, Loft, Migrate), whether each is installed, what your account entitles you to, and a button to open each one. You don't need it to use any individual app, but it's the fastest way to see everything at once.
+Pidgeon is the launcher app: one sign-in and a single grid of your Pidgeon products, whether each is installed, what your account entitles you to, and a button to open each one. The grid covers Post, Flock, Loft, and Migrate today; Conform joins it as its desktop app comes out of beta. You don't need the launcher to use any individual app, but it's the fastest way to see everything at once.
## Before you start
@@ -31,7 +31,6 @@ Pidgeon is the launcher app: one sign-in and a single grid showing all four prod
The status bar shows the launcher version. Product cards show installed versions.
- {/* BETA-GATE(Stage 2 / Launcher S1): update-check copy below goes live with the updater channel; keep it conditional until updater keys + channel config ship. */}
When the beta update channel is live, the launcher surfaces an update prompt on a product card when a newer version exists.
@@ -48,6 +47,7 @@ Pidgeon is the launcher app: one sign-in and a single grid showing all four prod
- [Your Pidgeon account](/getting-started/account)
- [Get started with Post](/getting-started/post)
+- [Get started with Conform](/getting-started/conform)
- [Get started with Flock](/getting-started/flock)
- [Get started with Loft](/getting-started/loft)
- [Get started with Migrate](/getting-started/migrate)
diff --git a/getting-started/loft.mdx b/getting-started/loft.mdx
index 8178580..8df266a 100644
--- a/getting-started/loft.mdx
+++ b/getting-started/loft.mdx
@@ -21,7 +21,7 @@ Loft is a desktop app and requires a Pidgeon account sign-in. Watched sources ar
CLI equivalent:
```bash
- pidgeon loft watch --directory /var/mirth/outbound/er --profile epic_er
+ pidgeon loft watch --path /var/mirth/outbound/er --profile epic_er
```
diff --git a/getting-started/migrate.mdx b/getting-started/migrate.mdx
index 80e1d15..49d8ac9 100644
--- a/getting-started/migrate.mdx
+++ b/getting-started/migrate.mdx
@@ -46,5 +46,7 @@ Migrate requires a Pidgeon account sign-in.
## Next steps
+- [Migrate in depth](/migrate/overview): the export, mapping, and analysis workflows
+- [Migrate CLI reference](/cli/migrate-commands)
- [CLI quickstart](/getting-started/quickstart-cli)
- Sidebar entries marked **Soon** (Export Wizard, Mappings, History) are not active in this beta; the Dashboard runs the full loop above.
diff --git a/getting-started/quickstart-cli.mdx b/getting-started/quickstart-cli.mdx
index 4ae8ceb..f8adeb8 100644
--- a/getting-started/quickstart-cli.mdx
+++ b/getting-started/quickstart-cli.mdx
@@ -1,18 +1,23 @@
---
title: CLI Quickstart
-description: Install the CLI, generate and validate your first HL7 message, run a FHIR conformance check, and wire the exit codes into CI. Free, no account required.
+description: Install the free CLI, generate and validate your first HL7 message, and wire the exit codes into CI. No account required.
---
-The CLI is one binary that exposes generate, validate, conform, and de-identify from a terminal. It follows the Unix convention (`0` success, non-zero failure), so every command below drops into a CI pipeline as-is.
+The CLI is one binary that generates, validates, and de-identifies test messages from a terminal. It follows the Unix convention (`0` success, non-zero failure), so every command below drops into a CI pipeline as-is.
+
+
+The free CLI (the community NuGet build) ships 12 commands: `generate`, `validate`, `deident`, `data`, `artifacts`, `lookup`, `find`, `path`, `run`, `session`, `completions`, and `capabilities`. `conform`, `flock`, `loft`, `migrate`, `ai`, `diff`, and `config` are delivered through the desktop apps. If you run only `dotnet tool install` and then type `pidgeon conform`, it won't be there; run those from the CLI bundled with the desktop apps, or from the matching app panel.
+
## Prerequisites
-- [.NET 8 SDK](https://dotnet.microsoft.com/download/dotnet/8.0) or later
+- [.NET 8 runtime or SDK](https://dotnet.microsoft.com/download/dotnet/8.0) for the `dotnet tool` install below
+- The public NuGet package is the cross-platform beta install path. The current GitHub release also includes a signed Windows ZIP.
```bash
- dotnet tool install --global Pidgeon.CLI --version 0.1.0-beta.1
+ dotnet tool install --global Pidgeon.CLI --version 0.1.0-beta.2
```
Verify the installation:
@@ -64,16 +69,6 @@ The CLI is one binary that exposes generate, validate, conform, and de-identify
Each issue includes expected/actual values, a fix suggestion, and a `pidgeon lookup` tip that opens the built-in standards reference. `--mode strict` checks against the published spec; `--mode compatibility` tolerates common real-world deviations.
-
- Probe a live FHIR endpoint against a published Implementation Guide and get a pass/fail with an HTML scorecard:
-
- ```bash
- pidgeon conform --endpoint https://api.example.org/fhir --ig davinci-pas-2.1 --ci
- ```
-
- Current IG scope includes US Core and Da Vinci PAS 2.1. With `--ci`, must-support warnings also produce a non-zero exit so your pipeline gate catches them; without `--ci` they stay warnings.
-
-
If you have real messages to work with, de-identify them first:
@@ -95,14 +90,18 @@ The CLI is one binary that exposes generate, validate, conform, and de-identify
+## Running a conformance check
+
+`pidgeon conform` probes a live FHIR endpoint against a published Implementation Guide (US Core and Da Vinci PAS 2.1 today) and returns a pass/fail with a non-zero CI exit code. It's delivered through the desktop apps, not the free `dotnet tool` package, so run it from the CLI bundled with an app or from Post's Conformance panel. See [Get started with Conform](/getting-started/conform).
+
## Exit codes
-The CLI emits exactly two exit codes, suitable for CI gates and shell scripting:
+The free CLI emits exactly two exit codes, suitable for CI gates and shell scripting:
| Code | Meaning | Examples |
|---|---|---|
-| `0` | Success | Message generated; validation passed; conform report passed (without must-support warnings under `--ci`) |
-| `1` | Failure | Validation issues found in strict mode; conform report failed, or passed with must-support warnings under `--ci`; missing required argument; unknown command; endpoint/IG load error |
+| `0` | Success | Message generated; validation passed |
+| `1` | Failure | Validation issues found in strict mode; missing required argument; unknown command |
A minimal CI gate:
diff --git a/getting-started/quickstart-desktop.mdx b/getting-started/quickstart-desktop.mdx
index 65c094a..476b3a6 100644
--- a/getting-started/quickstart-desktop.mdx
+++ b/getting-started/quickstart-desktop.mdx
@@ -1,9 +1,9 @@
---
title: Desktop Quickstart
-description: Install Pidgeon, generate an HL7 message in Post, validate it, and see the Pro features that unlock with an account.
+description: Install Pidgeon, generate an HL7 message in Post, validate it, and see what a Pro account adds.
---
-The desktop apps are the point-and-click path through the same engine the CLI uses. This walkthrough uses **Post** — the free front door — then points at the Pro features and the other three products.
+The desktop apps are the point-and-click path through the same engine the CLI uses. This walkthrough uses **Post**, the free front door, then points at the Pro features and the rest of the suite: Flock, Loft, Migrate, and Conform.
## Before you start
@@ -20,17 +20,19 @@ The desktop apps are the point-and-click path through the same engine the CLI us
- Open the **Conformance** panel (under **Inspect**) to probe a live FHIR endpoint against a published Implementation Guide — this is Conform, the module of Post covering US Core and Da Vinci PAS 2.1 today.
+ Open the **Conformance** panel (under **Inspect**) to probe a live FHIR endpoint against a published Implementation Guide (US Core and Da Vinci PAS 2.1 today). This is Conform, Pidgeon's fifth product. Its conformance capability runs inside Post now; the standalone Conform app is in beta and not yet downloadable.
- Signing in with a Pro entitlement unlocks:
+ Signing in with a Pro entitlement adds:
- - **Workflow Wizard** — build multi-step scenarios (admit → labs → discharge) visually
- - **Diff** — compare two messages or directories with field-level highlighting
- - **AI Triage** — plain-English explanations of validation failures (on-device or BYOK)
- - **Reports** — export HTML validation and conformance reports for stakeholders
- - Full reference datasets (LOINC, SNOMED CT, NDC, RxNorm, HCPCS)
+ - **Workflow Wizard**: build multi-step scenarios (admit, labs, discharge) visually
+ - **Diff**: compare two messages or directories with field-level highlighting
+ - **AI Triage**: plain-English explanations of validation failures, on-device or BYOK
+ - **Reports**: export HTML validation and conformance reports for stakeholders
+ - Expanded reference datasets (LOINC, SNOMED CT, NDC, RxNorm, HCPCS)
+
+ AI Triage is a Post Pro feature. The local Bridge route it uses is unauthenticated because the Bridge only listens on loopback for the signed-in user.
@@ -44,8 +46,10 @@ pidgeon validate --folder ./messages --mode strict
pidgeon conform --endpoint https://api.example.org/fhir --ig davinci-pas-2.1 --ci
```
+The `conform` command ships with the CLI bundled inside the desktop apps, not the free `dotnet tool` package. See the [CLI quickstart](/getting-started/quickstart-cli) for what the free CLI includes.
+
## Next steps
-- [Your Pidgeon account](/getting-started/account) — see your plan and entitlements
-- [Get started with Flock](/getting-started/flock), [Loft](/getting-started/loft), or [Migrate](/getting-started/migrate)
+- [Your Pidgeon account](/getting-started/account): see your plan and entitlements
+- Get started with [Flock](/getting-started/flock), [Loft](/getting-started/loft), [Migrate](/getting-started/migrate), or [Conform](/getting-started/conform)
- [Build test scenarios with the Workflow Wizard](/guides/build-test-scenarios)
diff --git a/guides/build-test-scenarios.mdx b/guides/build-test-scenarios.mdx
index b00514f..4071690 100644
--- a/guides/build-test-scenarios.mdx
+++ b/guides/build-test-scenarios.mdx
@@ -5,7 +5,7 @@ description: Define admit-to-discharge test sequences once and run them repeated
The Workflow Wizard is a Pro feature, available in the Post desktop app and the CLI with a Post Pro entitlement.
-Testing a single ADT message doesn't prove your interface works. Real go-lives need admit → lab order → result → discharge sequences — and you need to run them repeatedly as you iterate. Define the scenario once in YAML, run it as many times as you need.
+Testing a single ADT message doesn't prove your interface works. Real go-lives need admit → lab order → result → discharge sequences, and you need to run them repeatedly as you iterate. Define the scenario once in YAML, run it as many times as you need.
## Interactive wizard
@@ -60,7 +60,7 @@ Execute a scenario file and save the generated messages:
pidgeon workflow run ed-visit.yaml --output ./test-results
```
-This generates each message in sequence with the specified delays and saves them to the output directory. Timestamps are coherent across all messages — the lab order timestamp is after admission, results after the order, and so on.
+This generates each message in sequence with the specified delays and saves them to the output directory. Timestamps are coherent across all messages: the lab order timestamp is after admission, results after the order, and so on.
## Validation checkpoints
@@ -113,4 +113,4 @@ The Post desktop app's Workflow Wizard provides a visual builder where you can:
- [Generate test data](/guides/generate-realistic-test-data) for individual message types
- [Monitor your interfaces](/guides/monitor-mirth-with-loft) with Loft while running scenarios
-- [Compare environments](/post/validation) using diff to verify test results
+- [Compare environments](/post/diff) using diff to verify test results
diff --git a/guides/de-identify-real-messages.mdx b/guides/de-identify-real-messages.mdx
index c847ce5..2b7c8f4 100644
--- a/guides/de-identify-real-messages.mdx
+++ b/guides/de-identify-real-messages.mdx
@@ -1,6 +1,6 @@
---
title: De-identify Real Messages
-description: Replace manual MRN scrubbing with a single command. On-device processing — no PHI ever leaves your machine.
+description: Replace manual MRN scrubbing with a single command. On-device processing, so no PHI ever leaves your machine.
---
@@ -9,7 +9,7 @@ De-identification assists with HIPAA compliance but does not guarantee it. Alway
## Prerequisites
-- Pidgeon CLI installed (`dotnet tool install --global Pidgeon.CLI --version 0.1.0-beta.1`)
+- Pidgeon CLI installed (`dotnet tool install --global Pidgeon.CLI --version 0.1.0-beta.2`)
- A directory of real HL7 messages to de-identify
## Basic de-identification
@@ -92,7 +92,7 @@ pidgeon deident --in ./inbox --out ./clean --date-shift 30d --keep-ids
```
- The de-identified messages retain the same structure, segment ordering, and field patterns as the originals — ideal for integration testing.
+ The de-identified messages retain the same structure, segment ordering, and field patterns as the originals, which is what integration testing needs.
diff --git a/guides/generate-realistic-test-data.mdx b/guides/generate-realistic-test-data.mdx
index ddf4978..571ce57 100644
--- a/guides/generate-realistic-test-data.mdx
+++ b/guides/generate-realistic-test-data.mdx
@@ -1,11 +1,11 @@
---
title: Generate Realistic Test Data
-description: Go from zero to a full test dataset in under 5 minutes — HL7, FHIR, and NCPDP messages that match your vendor's real patterns.
+description: Go from zero to a full test dataset in under 5 minutes. HL7, FHIR, and NCPDP messages that match your vendor's real patterns.
---
## Prerequisites
-- Pidgeon CLI installed (`dotnet tool install --global Pidgeon.CLI --version 0.1.0-beta.1`)
+- Pidgeon CLI installed (`dotnet tool install --global Pidgeon.CLI --version 0.1.0-beta.2`)
- Optionally: a vendor profile from real sample messages
## Generate your first messages
@@ -18,7 +18,7 @@ pidgeon generate ADT^A01 --count 5
This produces 5 synthetic ADT^A01 messages with realistic patient demographics, encounter data, and properly structured segments (MSH, EVN, PID, PV1).
-Use `--seed 42` for reproducible output — the same seed always generates the same messages.
+Use `--seed 42` for reproducible output. The same seed always generates the same messages.
## Multi-standard generation
@@ -42,7 +42,7 @@ pidgeon generate RxFill --count 3
```
-HL7 v2 and FHIR R4 generation are free. NCPDP SCRIPT is closed by default — install the member-supplied standards package first (`pidgeon data install ncpdp-script --accept-license`, NCPDP membership required).
+HL7 v2 and FHIR R4 generation are free. NCPDP SCRIPT is closed by default. Install the member-supplied standards package first (`pidgeon data install ncpdp-script --accept-license`, NCPDP membership required).
## Use vendor profiles for realistic patterns
diff --git a/guides/healthcare-interface-test-data-field-guide.mdx b/guides/healthcare-interface-test-data-field-guide.mdx
new file mode 100644
index 0000000..698e2e1
--- /dev/null
+++ b/guides/healthcare-interface-test-data-field-guide.mdx
@@ -0,0 +1,86 @@
+---
+title: Healthcare interface test-data field guide
+description: Build synthetic positive and negative controls that expose the interface behavior tidy demo data can hide.
+---
+
+A clean sample message proves very little about the cases an integration team
+will have to explain. A useful test-data set combines repeatable synthetic
+inputs, expected outcomes, and evidence that another person can inspect.
+
+
+Use synthetic examples for this workflow. Validation findings support technical
+review; they are not a compliance determination and do not replace the team's
+own acceptance criteria.
+
+
+## Start with a test question
+
+Write one observable question before generating data:
+
+- Does the receiver distinguish an absent value from an empty value?
+- What happens when a repeating field appears more than once?
+- Does the route preserve an identifier without silently changing its format?
+- Can the team reproduce the same failure from the same input?
+
+Avoid starting with “make realistic data.” Realism without an expected result
+produces volume, not evidence.
+
+## Build a small control set
+
+For each question, keep at least three synthetic cases:
+
+| Control | Purpose | Expected evidence |
+| --- | --- | --- |
+| Positive | A supported ordinary case | Accepted result and preserved values |
+| Boundary | The nearest valid edge case | Accepted or flagged according to the documented rule |
+| Negative | One deliberate violation | A specific, reviewable failure rather than a generic rejection |
+
+Give every case a stable identifier and record the generator version and seed.
+Change one meaningful condition at a time so the result remains explainable.
+
+## Generate repeatable examples
+
+The community CLI can generate deterministic synthetic messages:
+
+```bash
+pidgeon generate hl7 "ADT^A01" --seed 42 --output positive.hl7
+pidgeon validate positive.hl7
+```
+
+Use a different committed fixture for each controlled variation. Do not edit a
+large message in ten places and then ask the team to infer which change caused
+the result.
+
+## Use the right product boundary
+
+- **Post** is the message and interface testing surface. Use it to create,
+ validate, compare, and review focused interchange cases.
+- **Flock** is the schema-aware population-seeding surface. Use it when the
+ test requires a coherent synthetic population shaped from schema inputs.
+
+The public CLI supports the community workflow. Product availability and
+commercial capabilities are separate from the public package release.
+
+## Keep an evidence packet
+
+For a result another engineer may need to reproduce, keep:
+
+1. the synthetic input or generator recipe;
+2. the exact package or application version;
+3. the seed and options;
+4. the expected result;
+5. the observed result;
+6. the relevant validation output; and
+7. the human review decision.
+
+That packet makes a failure discussable without turning a screenshot or an
+agent summary into the source of truth.
+
+## Review before reuse
+
+Re-run the controls when a mapping, validator, package, implementation guide,
+or receiver changes. Preserve the prior result rather than overwriting it, and
+record which change caused the new baseline.
+
+For the local review boundary, continue with the
+[human-and-agent workflow map](/guides/local-first-human-agent-workflow).
diff --git a/guides/local-first-human-agent-workflow.mdx b/guides/local-first-human-agent-workflow.mdx
new file mode 100644
index 0000000..874fa12
--- /dev/null
+++ b/guides/local-first-human-agent-workflow.mdx
@@ -0,0 +1,64 @@
+---
+title: Local-first human and agent workflow
+description: Divide healthcare interoperability work so an agent can help with inspectable evidence while the human keeps scope and accountability.
+---
+
+An agent is most useful in healthcare interoperability when it can inspect a
+bounded task and produce evidence the operator can review. It is least useful
+when a plausible answer quietly replaces the source material or the human
+decision.
+
+## Divide the work deliberately
+
+| Stage | Human responsibility | Agent-assisted work |
+| --- | --- | --- |
+| Frame | Define the question, allowed data, environment, and acceptance rule | Turn the question into a proposed checklist or command plan |
+| Prepare | Select synthetic fixtures or approved local inputs | Generate repeatable synthetic cases and enumerate controlled variations |
+| Execute | Approve the operation and its scope | Run local generation, validation, comparison, or reference commands |
+| Inspect | Review source input, findings, and exceptions | Organize results and point to the evidence behind each finding |
+| Decide | Accept, reject, escalate, or revise | Record the decision context without making the decision itself |
+
+## Keep the evidence local
+
+Pidgeon's local workflows can run with no cloud message-content egress. Keep
+message content and detailed technical evidence on the controlled machine, and
+pass only the minimum bounded context to an agent or external service that the
+team has approved.
+
+
+“Local-first” describes the workflow boundary, not a universal promise that no
+Pidgeon surface ever uses a network. Account, update, licensing, and explicitly
+enabled provider features have their own documented boundaries.
+
+
+## Make every finding inspectable
+
+An agent-supported finding should carry:
+
+- the input or stable fixture identifier;
+- the exact tool and version;
+- the command or operation;
+- the relevant rule or comparison;
+- the observed output;
+- uncertainty or missing context; and
+- the human disposition.
+
+If the evidence cannot be inspected, the result is a suggestion, not a
+technical conclusion.
+
+## Use the community interfaces
+
+The public `pidgeon` CLI provides a scriptable local interface. The governed
+`@pidgeonhealth/pidgeon-mcp` adapter exposes community capabilities to a
+compatible MCP client while keeping the underlying operation in the local CLI
+or an explicitly selected desktop Bridge.
+
+Start with the [public packages quickstart](/guides/public-packages-quickstart)
+and use synthetic data for the first controlled run.
+
+## Preserve the human gate
+
+Do not treat these tools as clinical decision support, an autonomous
+remediation system, or a substitute for implementation ownership. The agent
+can accelerate preparation, execution, and explanation. The accountable human
+still defines the boundary and signs off on what happens next.
diff --git a/guides/monitor-mirth-with-loft.mdx b/guides/monitor-mirth-with-loft.mdx
index 85fb6a2..4c8d07d 100644
--- a/guides/monitor-mirth-with-loft.mdx
+++ b/guides/monitor-mirth-with-loft.mdx
@@ -5,9 +5,9 @@ description: Stop finding out about interface failures from clinical staff. Poin
## Prerequisites
-- Pidgeon CLI installed (`dotnet tool install --global Pidgeon.CLI --version 0.1.0-beta.1`)
-- Access to Mirth Connect's file writer output directories
-- A vendor profile for your message patterns (optional but recommended)
+- The Loft desktop app installed and signed in. Loft is a Pro product; it provides the `pidgeon loft` commands and the local Bridge on `localhost:5100`. The free `dotnet tool install --global Pidgeon.CLI` build does not include `loft`.
+- Access to Mirth Connect's file writer output directories.
+- A vendor profile for your message patterns (optional but recommended). `pidgeon config analyze` is in the free CLI.
## Step 1: Identify Mirth output directories
@@ -36,19 +36,17 @@ Watch a single interface:
```bash
pidgeon loft watch \
- --directory /var/mirth/outbound/er-adt/ \
- --profile mirth_er_adt \
- --file-pattern "*.hl7"
+ --path /var/mirth/outbound/er-adt/ \
+ --profile mirth_er_adt
```
-Loft monitors the directory, validates each new message as it arrives, and alerts on failures.
+Loft monitors the directory, validates each new `.hl7` file as it arrives, and alerts on failures.
## Step 4: Create interfaces via the Bridge API
-For production setups, create interfaces through the Loft desktop app's local Bridge sidecar so they persist and appear in the **Sources** panel. The Bridge runs on `localhost:5100` while the Loft app is open — there is no hosted API; every call below is local to the machine running Loft:
+For production setups, create interfaces through the Loft desktop app's local Bridge sidecar so they persist and appear in the **Sources** panel. The Bridge runs on `localhost:5100` while the Loft app is open. There is no hosted API; every call below is local to the machine running Loft:
```bash
-# Create ER ADT interface
curl -X POST http://localhost:5100/api/loft/interfaces \
-H "Content-Type: application/json" \
-d '{
@@ -57,31 +55,13 @@ curl -X POST http://localhost:5100/api/loft/interfaces \
"profileName": "mirth_er_adt",
"filePattern": "*.hl7"
}'
-
-# Create Lab Results interface
-curl -X POST http://localhost:5100/api/loft/interfaces \
- -H "Content-Type: application/json" \
- -d '{
- "name": "Mirth Lab Results",
- "directoryPath": "/var/mirth/outbound/lab-results/",
- "profileName": "mirth_lab",
- "filePattern": "*.hl7"
- }'
```
-## Step 5: Configure alerting
-
-Set up alerts in the Loft desktop app or via the Bridge API. Loft supports:
+Repeat for each interface (lab results, pharmacy), changing `name`, `directoryPath`, and `profileName`. The [Interface Monitoring](/loft/interface-monitoring) page has the full field reference.
-| Channel | Supported |
-|---------|-----------|
-| Local log | Yes |
-| Webhook | Yes |
-| Email | Yes |
-| Slack | Yes |
-| PagerDuty | Yes |
+## Step 5: Configure alerting
-Alert payloads are redacted before they go out to any notification channel.
+Set up alerts in the Loft desktop app or via the Bridge API. Loft has six channels: local log, webhook, Slack, Microsoft Teams, email, and PagerDuty. Payloads to off-device channels are scrubbed of message content before they leave the machine. See [Alerting](/loft/alerting) for the full channel model and routing options.
## Step 6: Monitor metrics
diff --git a/guides/public-packages-quickstart.mdx b/guides/public-packages-quickstart.mdx
new file mode 100644
index 0000000..56e22f9
--- /dev/null
+++ b/guides/public-packages-quickstart.mdx
@@ -0,0 +1,89 @@
+---
+title: Public packages quickstart
+description: Install the Pidgeon public beta packages and run a small local healthcare-data workflow.
+---
+
+Pidgeon's public beta gives engineers three ways into the same local-first
+workflow: the .NET engine packages, the `pidgeon` command-line tool, and a thin
+Model Context Protocol adapter. Start with the CLI unless you are embedding
+the engine into an application or connecting an MCP client.
+
+
+These are beta packages. Pin the exact versions below, review the known limits,
+and test the workflow before relying on it in a controlled environment. The
+desktop products are distributed separately from these community packages.
+
+
+## Choose an entry point
+
+| Need | Package | Current beta |
+| --- | --- | --- |
+| Use Pidgeon from a terminal or CI job | `Pidgeon.CLI` | `0.1.0-beta.2` |
+| Embed the engine in a .NET application | `Pidgeon.Core` | `0.1.0-beta.1` |
+| Add the provenance-cleared offline baseline data | `Pidgeon.Data.Baseline` | `0.1.0-beta.1` |
+| Connect an MCP client to the community CLI | `@pidgeonhealth/pidgeon-mcp` | `0.1.0-beta.1` |
+
+## Run the CLI locally
+
+Install the .NET tool:
+
+```bash
+dotnet tool install --global Pidgeon.CLI --version 0.1.0-beta.2
+pidgeon --version
+```
+
+Generate a deterministic synthetic HL7 v2 message, validate it, and preserve
+the output for review:
+
+```bash
+pidgeon generate hl7 "ADT^A01" --seed 42 --output sample.hl7
+pidgeon validate sample.hl7
+```
+
+The seed makes the generated example repeatable. The validation result is
+evidence about that input and the supported rules, not a certification or a
+guarantee about a production interface.
+
+## Embed Core and Baseline
+
+Add both packages when an application needs the public engine and its admitted
+offline resource set:
+
+```bash
+dotnet add package Pidgeon.Core --version 0.1.0-beta.1
+dotnet add package Pidgeon.Data.Baseline --version 0.1.0-beta.1
+```
+
+Register the baseline package explicitly with `AddPidgeonBaselineData()` in
+your dependency-injection composition. Core does not silently reach into the
+legacy data tree, and an absent required data package degrades with a typed
+result rather than pretending the resource exists.
+
+## Connect an MCP client
+
+Use the governed adapter package:
+
+```bash
+npx -y @pidgeonhealth/pidgeon-mcp@0.1.0-beta.1
+```
+
+
+Do not substitute `@pidgeonhealth/mcp`. That name is a contained legacy
+package and is not part of the governed public beta release train.
+
+
+The adapter shells out to the local CLI in CLI mode. It does not turn the MCP
+client into an autonomous healthcare operator: the human remains responsible
+for scope, review, and use of the resulting evidence.
+
+## Verify before expanding
+
+1. Pin the package versions in source control.
+2. Run a synthetic example without patient data.
+3. Review the generated output and validation result.
+4. Record the command, version, seed, and result when repeatability matters.
+5. Report a reproducible issue through the relevant
+ [Pidgeon Health repository](https://github.com/PidgeonHealth).
+
+Next, read the [test-data field guide](/guides/healthcare-interface-test-data-field-guide)
+or the [human-and-agent workflow map](/guides/local-first-human-agent-workflow).
diff --git a/guides/seed-database-with-flock.mdx b/guides/seed-database-with-flock.mdx
index ec17cf6..afd6c4b 100644
--- a/guides/seed-database-with-flock.mdx
+++ b/guides/seed-database-with-flock.mdx
@@ -1,14 +1,14 @@
---
title: Seed a Database with Flock
-description: Go from empty test database to production-realistic patient population in minutes — zero PHI, instant compliance approval.
+description: Go from an empty test database to a production-realistic patient population in minutes, with no PHI and no production snapshot to get signed off.
---
An empty test database doesn't catch real bugs. A database full of copied production data is a compliance violation. Flock gives you the third option: realistic synthetic populations seeded directly into your schema.
## Prerequisites
-- Pidgeon CLI installed (`dotnet tool install --global Pidgeon.CLI --version 0.1.0-beta.1`)
-- A database with an existing schema (PostgreSQL, MySQL, or SQL Server)
+- Pidgeon CLI installed (`dotnet tool install --global Pidgeon.CLI --version 0.1.0-beta.2`), plus the Flock desktop app or Pro CLI (the `flock` command is not in the free community build)
+- A database with an existing schema (PostgreSQL, SQL Server, or MySQL)
- Database credentials with read/write access
## Step 1: Connect to your database
@@ -16,7 +16,7 @@ An empty test database doesn't catch real bugs. A database full of copied produc
```bash
pidgeon flock connect \
--provider postgres \
- --connection-string "Host=localhost;Port=5432;Database=ehr_dev;Username=dev;Password=${DB_PASSWORD}"
+ --connection "Host=localhost;Port=5432;Database=ehr_dev;Username=dev;Password=${DB_PASSWORD}"
```
Flock analyzes the schema and reports:
@@ -26,41 +26,46 @@ Flock analyzes the schema and reports:
## Step 2: Learn patterns from existing data (optional)
-If your database already has sample data, Flock can learn the statistical distribution patterns:
+If your database already has sample data, Flock can learn its statistical distributions:
```bash
-pidgeon flock learn --tables patients,encounters,diagnoses --sample-size 500
+pidgeon flock learn --sample 500
```
This creates a profile that captures:
-- Column value distributions (age ranges, gender ratios)
+- Column value distributions (age ranges, sex ratios)
- Referential patterns (which diagnosis codes appear together)
- Temporal patterns (encounter durations, admission-to-discharge intervals)
## Step 3: Generate a synthetic population
-Generate 1,000 patients with related records:
+Generate 1,000 patients with related records, writing them to a directory the seed step can read:
```bash
pidgeon flock generate \
--count 1000 \
--format sql \
- --geographic-focus us \
- --seed 42
+ --state TX \
+ --seed 42 \
+ --output ./seed-data/
```
Flock generates:
-- **Demographics**: Age, gender, race, and geography distributions matching US Census data
-- **Comorbidities**: Realistic disease correlations (diabetes with hypertension, obesity with sleep apnea)
-- **Temporal coherence**: Admissions before discharges, lab orders before results
-- **Family linkage**: Realistic household structures and family relationships
+- **Demographics**: age, sex, race, and geography distributions matching US Census data
+- **Correlated conditions**: realistic disease correlations (diabetes with hypertension, obesity with sleep apnea)
+- **Temporal coherence**: admissions before discharges, lab orders before results
+- **Family linkage**: household structures and family relationships
## Step 4: Preview with dry-run
Before writing anything, preview the generated SQL:
```bash
-pidgeon flock seed --dry-run
+pidgeon flock seed \
+ --target postgres \
+ --connection "Host=localhost;Port=5432;Database=ehr_dev;Username=dev;Password=${DB_PASSWORD}" \
+ --from ./seed-data/ \
+ --dry-run
```
This outputs the SQL INSERT statements in foreign-key order without executing them. Review to confirm the data looks correct.
@@ -68,29 +73,25 @@ This outputs the SQL INSERT statements in foreign-key order without executing th
## Step 5: Seed the database
```bash
-pidgeon flock seed
+pidgeon flock seed \
+ --target postgres \
+ --connection "Host=localhost;Port=5432;Database=ehr_dev;Username=dev;Password=${DB_PASSWORD}" \
+ --from ./seed-data/
```
-Flock inserts records in FK-dependency order so referential integrity is maintained. All synthetic records are tagged for easy identification and cleanup.
+Flock inserts records in FK-dependency order so referential integrity holds, and reports the rows inserted per table. All synthetic records are tagged for later identification and cleanup.
## Step 6: Verify the results
-Check that data was seeded correctly:
+The seed command prints an FK-safe insert summary (rows per table, in dependency order). To confirm independently, count the tagged rows in your database:
```bash
-# Check job analytics
-pidgeon flock status
-```
-
-Or via the API:
-
-```bash
-curl http://localhost:5102/api/flock/generate/{jobId}/analytics
+psql "$DATABASE_URL" -c "SELECT count(*) FROM patients;"
```
## Alternative output formats
-Flock can generate data in multiple formats beyond SQL:
+Flock can generate data in formats beyond SQL:
```bash SQL INSERT
@@ -115,16 +116,18 @@ pidgeon flock generate --count 1000 --format fhir --output ./seed-data/
Remove all Flock-generated records when you're done:
```bash
-pidgeon flock seed --cleanup
+pidgeon flock cleanup \
+ --provider postgres \
+ --connection "Host=localhost;Port=5432;Database=ehr_dev;Username=dev;Password=${DB_PASSWORD}"
```
Or via the API:
```bash
-curl -X DELETE "http://localhost:5102/api/flock/seed/cleanup?connectionString=Host%3Dlocalhost%3B..."
+curl -X DELETE "http://localhost:5102/api/flock/seed/cleanup?connectionString=Host%3Dlocalhost%3BDatabase%3Dehr_dev&provider=postgres"
```
-Cleanup removes all records tagged as synthetic. This cannot be undone.
+Cleanup removes every record tagged as synthetic. This cannot be undone.
## Next steps
diff --git a/images/brand/icons/conform.png b/images/brand/icons/conform.png
new file mode 100644
index 0000000..2dfe224
Binary files /dev/null and b/images/brand/icons/conform.png differ
diff --git a/images/brand/icons/loft.png b/images/brand/icons/loft.png
index 07a9dc2..f562faa 100644
Binary files a/images/brand/icons/loft.png and b/images/brand/icons/loft.png differ
diff --git a/images/brand/wordmarks/conform.png b/images/brand/wordmarks/conform.png
new file mode 100644
index 0000000..4ae16d6
Binary files /dev/null and b/images/brand/wordmarks/conform.png differ
diff --git a/images/brand/wordmarks/loft.png b/images/brand/wordmarks/loft.png
index 955ea36..7386899 100644
Binary files a/images/brand/wordmarks/loft.png and b/images/brand/wordmarks/loft.png differ
diff --git a/index.mdx b/index.mdx
index f07d37b..3f57ece 100644
--- a/index.mdx
+++ b/index.mdx
@@ -1,22 +1,25 @@
---
title: Pidgeon Health Documentation
-description: Generate realistic test messages in seconds, validate against real vendor patterns, and stop copying production data into test environments.
+description: Generate realistic test messages, prove FHIR conformance, seed databases, migrate data, and monitor live interfaces. Fully synthetic, zero PHI on the synthetic path.
---
-Stop copying production data into test environments. Generate realistic HL7, FHIR, and NCPDP messages in seconds — fully synthetic, zero PHI, zero compliance risk.
+Stop copying production data into test environments. One engine, five products: generate realistic HL7, FHIR, and NCPDP messages, prove your FHIR endpoints conform, seed test databases, move data between systems, and watch live interfaces. The synthetic path carries no PHI, so there's nothing to mask and no security review to clear.
- **Testing Tool** — Generate HL7 v2.3–v2.8, FHIR R4, and NCPDP SCRIPT messages, validate, de-identify, and check FHIR conformance with Conform. Free CLI + free generation/validation in the desktop app; Pro unlocks the rest.
+ **Testing tool.** Generate HL7 v2.3–v2.8, FHIR R4, and NCPDP SCRIPT messages, validate against the published spec, and de-identify on-device. Free CLI and free generation/validation in the desktop app; Pro adds the rest.
+
+
+ **FHIR conformance.** Prove a live FHIR endpoint satisfies the Implementation Guides CMS-0057-F requires, from CI, with a non-zero exit code and an evidence scorecard. Conformance evidence, not certification.
- **Population Engine** — Seed test databases with clinically realistic patient populations. Epidemiologically grounded. Compliance signs off in minutes, not months.
+ **Population engine.** Seed test databases with schema-aware, FK-safe patient populations. No PHI to review, so compliance signs off in minutes.
- **Observability** — Know when your interfaces break before clinical staff calls you. Loft watches configured sources, alerts your team, and queues suspect messages for human review.
+ **Observability.** Know when an interface breaks before clinical staff calls. Loft watches configured sources, alerts your team, and queues suspect messages for human review.
-
- **Bulk Data Migration** — Move production data between systems via FHIR R4 Bulk Data Access, with preflight checks, de-identification, and reconciliation.
+
+ **Bulk data migration.** Move production data between systems via FHIR R4 Bulk Data Access, with preflight checks, de-identification, and reconciliation.
@@ -27,7 +30,7 @@ Stop copying production data into test environments. Generate realistic HL7, FHI
First message in under a minute. Always free.
- Point-and-click generation, validation, and conformance checks in Post.
+ Point-and-click generation, validation, and conformance checks.
Integrate with the local Bridge sidecar each desktop app runs.
diff --git a/loft/alerting.mdx b/loft/alerting.mdx
index b944f56..2c3135a 100644
--- a/loft/alerting.mdx
+++ b/loft/alerting.mdx
@@ -1,30 +1,32 @@
---
title: Alerting
-description: Get notified through PagerDuty, email, or webhook the moment an interface starts failing — not hours later.
+description: Get notified through PagerDuty, email, Slack, or a webhook the moment an interface starts failing, not hours later.
---
-Five channels, three severity levels, deduplication, and escalation routing. Configurable per interface.
+Six channels, three severity levels, deduplication, and escalation routing. Configurable per interface.
-## Alert Channels
+## Alert channels
-| Channel | Supported |
-|---------|:-----:|
-| Local log | Yes |
-| Webhook (Slack, Teams, etc.) | Yes |
-| Email (SMTP) | Yes |
-| PagerDuty | Yes |
+| Channel | Delivery | Egress |
+|---------|----------|--------|
+| Local log | Console, or a log file on the machine | Stays on device |
+| Webhook | HTTP POST to any endpoint that accepts JSON | Off-device |
+| Slack | Formatted message to a Slack incoming webhook | Off-device |
+| Microsoft Teams | Formatted card to a Teams incoming webhook | Off-device |
+| Email | SMTP (or SendGrid) to a recipient list | Off-device |
+| PagerDuty | Events API v2 with a routing key | Off-device |
-Alert payloads are redacted before they go out to any channel — message content never leaves your network.
+Payloads sent to an off-device channel are scrubbed of message content before they leave the machine. Local log channels keep the full detail. Message content never leaves your network.
-Use the webhook channel to integrate with Slack, Microsoft Teams, or any service that accepts incoming webhooks.
+Slack and Teams are their own channels: each formats the alert for that service. Use the generic Webhook channel for anything else that accepts an incoming webhook.
-## Advanced Alert Features
+## Routing and deduplication
-- **Deduplication** — Suppresses repeat alerts for the same issue within a configurable window
-- **Escalation** — Routes alerts based on severity to different channels or on-call groups
-- **Detailed payloads** — Each alert includes file path, severity, error/warning counts, message type, sending application, and full error list
+- **Deduplication**: suppresses repeat alerts for the same issue within a configurable window.
+- **Escalation**: routes alerts by severity to different channels or on-call groups.
+- **Payload contents**: each alert carries the file path, severity, error and warning counts, message type, sending application, and the failing rules with their locations.
-## Severity Levels
+## Severity levels
| Level | Description |
|-------|-------------|
@@ -32,7 +34,7 @@ Alert payloads are redacted before they go out to any channel — message conten
| `warning` | Elevated error rate or anomalous throughput |
| `info` | Informational events (interface started, config changed) |
-## Alert Lifecycle
+## Alert lifecycle
Alerts follow a lifecycle: **triggered** → **acknowledged** → **resolved**.
@@ -47,7 +49,7 @@ pidgeon loft alerts --severity critical
curl -X POST http://localhost:5100/api/loft/alerts/{id}/acknowledge
```
-## Example Alert
+## Example alert
```text
CRITICAL: Validation failure rate exceeded threshold
diff --git a/loft/interface-monitoring.mdx b/loft/interface-monitoring.mdx
index 553a2fc..2325b88 100644
--- a/loft/interface-monitoring.mdx
+++ b/loft/interface-monitoring.mdx
@@ -1,15 +1,17 @@
---
title: Interface Monitoring
-description: Point Loft at your Mirth output directories and know immediately when something breaks — before the help desk does.
+description: Point Loft at your Mirth output directories and know when something breaks before the help desk does.
---
One command to start watching. Every new message file picked up from a watched source is parsed and validated against your vendor profile, with metrics tracked per interface.
-## Creating Interfaces
+## Creating interfaces
+
+The CLI `pidgeon loft watch` runs an ad-hoc watch and validates `.hl7` files as they land. To create a persistent interface that survives restarts and appears in the desktop app's **Sources** panel, POST to the local Bridge. This is the canonical create example; the [Loft Interfaces API reference](/api-reference/loft-interfaces) documents every field.
```bash CLI
-pidgeon loft watch --directory /var/mirth/outbound/er --profile epic_er --file-pattern "*.hl7"
+pidgeon loft watch --path /var/mirth/outbound/er --profile epic_er
```
```bash API
@@ -24,20 +26,25 @@ curl -X POST http://localhost:5100/api/loft/interfaces \
```
-## Interface Metrics
+## Interface metrics
Each interface tracks:
-- **Messages total** — Total messages processed
-- **Success rate** — Percentage passing validation
-- **Error rate** — Messages with validation failures
-- **Throughput** — Messages per minute/hour
-- **Latency** — Average and p99 processing time
+
+| Metric | What it measures |
+|--------|------------------|
+| Total messages processed | Messages parsed from the source |
+| Total successes | Messages that passed validation |
+| Total errors | Messages that failed validation |
+| Error rate | Failed messages as a fraction of the total |
+| Hourly breakdown | Per-hour processed, errors, and successes |
```bash
curl "http://localhost:5100/api/loft/interfaces/{id}/metrics?sinceHours=24"
```
-## Managing Interfaces
+The response also carries `lastMessageAt`, `startedAt`, and `uptimeSeconds`. See the [Loft Interfaces API reference](/api-reference/loft-interfaces) for the full shape.
+
+## Managing interfaces
```bash
# List all interfaces
@@ -52,7 +59,7 @@ curl -X PUT http://localhost:5100/api/loft/interfaces/{id} \
curl -X DELETE http://localhost:5100/api/loft/interfaces/{id}
```
-## Status Overview
+## Status overview
```bash
# CLI
diff --git a/loft/overview.mdx b/loft/overview.mdx
index 07f2002..258a01a 100644
--- a/loft/overview.mdx
+++ b/loft/overview.mdx
@@ -3,29 +3,30 @@ title: Loft Overview
description: Know when your interfaces break before clinical staff calls you. Loft watches configured sources and flags content-level failures for human review.
---
+
+

+

+
+
Loft watches the messages flowing through your interfaces and catches what engine dashboards miss: a silently malformed med order, a misrouted lab result. Every catch lands in a review queue with a suggested fix. A human approves or rejects every remediation; Loft never changes a message on its own.
## What Loft does
-1. **Configure sources**: point Loft at your integration engine's output directories or pickup folders
-2. **Validate on pickup**: every new message picked up from a watched source is parsed and validated against your vendor profile
-3. **Alert on failures**: configurable alerting via local log, webhook, email, Slack, or PagerDuty
-4. **Track trends**: dashboards show throughput, error rates, and anomalies over time
-5. **Review and remediate**: flagged messages land in a review queue with a suggested fix for a human to accept or reject
-6. **Export evidence**: build an audit trail of catches, reviews, and outcomes
+1. **Configure sources**: point Loft at your integration engine's output directories or pickup folders.
+2. **Validate on pickup**: every new message picked up from a watched source is parsed and validated against your vendor profile.
+3. **Alert on failures**: six channels (local log, webhook, Slack, Microsoft Teams, email, PagerDuty). See [Alerting](/loft/alerting).
+4. **Track trends**: dashboards show throughput, error rates, and anomalies over time.
+5. **Review and remediate**: flagged messages land in a review queue with a suggested fix for a human to accept or reject.
+6. **Export evidence**: build an audit trail of catches, reviews, and outcomes.
-Message content stays on your network. Loft processes watched sources locally; alert payloads are redacted before they leave the machine.
+Message content stays on your network. Loft processes watched sources locally, and payloads to off-device alert channels are scrubbed of message content before they leave the machine.
-## Getting Started
+## Getting started
-```bash
-# CLI quick start
-pidgeon loft watch --directory /var/mirth/outbound/er --profile epic_er
+Watch a directory from the CLI:
-# Or create interfaces via API
-curl -X POST http://localhost:5100/api/loft/interfaces \
- -H "Content-Type: application/json" \
- -d '{"name": "ER Interface", "directoryPath": "/var/loft/er", "profileName": "epic_er"}'
+```bash
+pidgeon loft watch --path /var/mirth/outbound/er --profile epic_er
```
-See [Get started with Loft](/getting-started/loft) for the desktop app walkthrough, or [Monitor Mirth with Loft](/guides/monitor-mirth-with-loft) for a step-by-step Mirth setup.
+To create a persistent interface through the Loft desktop app's local Bridge, see [Interface Monitoring](/loft/interface-monitoring) for the full request. Then read [Get started with Loft](/getting-started/loft) for the desktop app walkthrough, or [Monitor Mirth with Loft](/guides/monitor-mirth-with-loft) for a step-by-step Mirth setup.
diff --git a/mcp/overview.mdx b/mcp/overview.mdx
index 6202659..1a6ba06 100644
--- a/mcp/overview.mdx
+++ b/mcp/overview.mdx
@@ -5,7 +5,7 @@ description: Drive Pidgeon's HL7 / FHIR / NCPDP engine from Claude, Cursor, VS C
The public Pidgeon MCP adapter (`@pidgeonhealth/pidgeon-mcp`) exposes the community capabilities of the Pidgeon CLI over the [Model Context Protocol](https://modelcontextprotocol.io). In CLI mode it launches the local `pidgeon` command; in Bridge mode it connects to a running desktop Bridge and registers only the capabilities that Bridge advertises.
-The MCP transport is the delivery mechanism, not the entitlement. The free/paid line is enforced at Bridge authentication + a validated subscription — not at the transport. A free agent loop is never broken by a hard error; it degrades gracefully.
+The MCP transport is the delivery mechanism, not the entitlement. The free/paid line is enforced at Bridge authentication plus a validated subscription, not at the transport. A free agent loop is never broken by a hard error; it degrades gracefully.
## The one rule
@@ -18,7 +18,7 @@ The server is an npm package that shells out to the Pidgeon CLI (CLI mode) or ta
```bash
- dotnet tool install --global Pidgeon.CLI --version 0.1.0-beta.1
+ dotnet tool install --global Pidgeon.CLI --version 0.1.0-beta.2
```
@@ -40,20 +40,25 @@ The server is an npm package that shells out to the Pidgeon CLI (CLI mode) or ta
+
+Use `@pidgeonhealth/pidgeon-mcp`. The older `@pidgeonhealth/mcp` package is a
+contained legacy package and is not part of the governed public beta train.
+
+
## Two transport modes
The `PIDGEON_MODE` environment variable selects the transport, and the transport determines which tools register.
| Mode | Value | What it talks to | Which tools register |
|------|-------|------------------|----------------------|
-| **CLI** | `PIDGEON_MODE=cli` | Spawns the `pidgeon` CLI locally | Exactly the checked-in **community** tool set — the tools the free CLI can service end to end. No account, no Bridge. |
-| **Bridge** | `PIDGEON_MODE=bridge` | HTTP to a running desktop app's local Bridge | Exactly the roster the Bridge **advertises** for your resolved tier — free tools plus any Pro tools your subscription entitles. |
+| **CLI** | `PIDGEON_MODE=cli` | Spawns the `pidgeon` CLI locally | Exactly the checked-in **community** tool set: the tools the free CLI can service from start to finish. No account, no Bridge. |
+| **Bridge** | `PIDGEON_MODE=bridge` | HTTP to a running desktop app's local Bridge | Exactly the roster the Bridge **advertises** for your resolved tier: free tools plus any Pro tools your subscription entitles. |
-In Bridge mode, the server registers only what the Bridge advertises for your tier. If it can't reach an advertisement (older build, Bridge unreachable), it fails closed to the community set — it never materializes a Pro tool from a client-side label. See the [tool catalog](/mcp/tools) for the exact split.
+In Bridge mode, the server registers only what the Bridge advertises for your tier. If it can't reach an advertisement (older build, Bridge unreachable), it fails closed to the community set and never materializes a Pro tool from a client-side label. See the [tool catalog](/mcp/tools) for the exact split.
## On-device AI
-AI-assisted tools (for example `refine_hl7_segment`) default to a **bundled on-device model** — no API key, and no message content leaves the machine. Set it up once:
+AI-assisted tools (for example `refine_hl7_segment`) default to a **bundled on-device model**: no API key, and no message content leaves the machine. Set it up once:
```bash
pidgeon ai download qwen3-4b
@@ -74,7 +79,7 @@ BYOK (a cloud provider) is optional and never required. The free `explain_error`
## Guided prompts
-The server ships six guided prompts that chain tools into a complete workflow. Each is honest about where the free line falls — a free agent gets the full diagnosis and never a hard stop.
+The server ships six guided prompts that chain tools into a complete workflow. Each is honest about where the free line falls: a free agent gets the full diagnosis and never a hard stop.
| Prompt | Chains | Free through |
|--------|--------|--------------|
@@ -85,7 +90,7 @@ The server ships six guided prompts that chain tools into a complete workflow. E
| `reproduce_and_fix` | explain → validate → explain_error → refine → diff → send | Free through triage |
| `seed_validate_monitor` | generate_population → run_workflow → validate → loft_status | Free through validation |
-In CLI mode, the three fully free workflows (`debug_hl7_error`, `go_live_prep`, `onboard_vendor_interface`) register out of the box — every tool they chain is in the community catalog. The other three chain Pro tools and appear in Bridge mode, advertised for your tier.
+In CLI mode, the three fully free workflows (`debug_hl7_error`, `go_live_prep`, `onboard_vendor_interface`) register out of the box; every tool they chain is in the community catalog. The other three chain Pro tools and appear in Bridge mode, advertised for your tier.
## Reference resources
@@ -102,5 +107,5 @@ Six read-only resources give an agent its bearings before it acts:
## Next steps
-- [MCP tool catalog](/mcp/tools) — the exact free, community, and Pro tool split
-- [CLI Reference](/cli/global-options) — the same operations from a terminal
+- [MCP tool catalog](/mcp/tools): the exact free, community, and Pro tool split
+- [CLI Reference](/cli/global-options): the same operations from a terminal
diff --git a/mcp/tools.mdx b/mcp/tools.mdx
index d16f996..d27db08 100644
--- a/mcp/tools.mdx
+++ b/mcp/tools.mdx
@@ -1,13 +1,13 @@
---
title: MCP Tool Catalog
-description: The exact free, community, and Pro tool split the Pidgeon MCP server exposes — matching the checked-in community catalog and the Bridge-advertised roster.
+description: The exact free, community, and Pro tool split the Pidgeon MCP server exposes, matching the checked-in community catalog and the Bridge-advertised roster.
---
The server ships **22 tools**: 13 free and 9 Pro. Which ones register depends on the [transport mode](/mcp/overview#two-transport-modes). This page is the human-readable companion to the generated `MANIFEST.md` and the checked-in community catalog; the live, machine-readable roster for your session is always `pidgeon://version`.
## Community tools (CLI mode)
-With `PIDGEON_MODE=cli` — no account, no Bridge — the server registers **exactly these eleven** tools: the ones the free CLI's command catalog can service end to end. Nothing else appears; a Pro tool never materializes from a client-side label.
+With `PIDGEON_MODE=cli` (no account, no Bridge) the server registers **exactly these eleven** tools: the ones the free CLI's command catalog can service from start to finish. Nothing else appears; a Pro tool never materializes from a client-side label.
| Tool | What it does |
|------|--------------|
@@ -21,13 +21,13 @@ With `PIDGEON_MODE=cli` — no account, no Bridge — the server registers **exa
| `manage_data_packages` | List and install reference data packages. |
| `search_artifacts` | Search local starter recipes, installed recipes, and data packages. |
| `pidgeon_status` | Local environment and capability diagnostics. |
-| `describe_tool` | Return the full contract for any tool by name — free and uncapped, and it describes Pro tools without unlocking them. |
+| `describe_tool` | Return the full contract for any tool by name. Free and uncapped, and it describes Pro tools without granting access to them. |
-`generate_message` in CLI mode is single-patient and volume-capped, with graceful degradation as you approach the cap — never a hard failure that breaks an agent loop.
+`generate_message` in CLI mode is single-patient and volume-capped, with graceful degradation as you approach the cap, never a hard failure that breaks an agent loop.
## Free tools added in Bridge mode
-With `PIDGEON_MODE=bridge` and a running desktop app, the Bridge advertises the full free tier — the eleven community tools plus these two (their substrate runs in the Bridge, so the CLI alone can't service them):
+With `PIDGEON_MODE=bridge` and a running desktop app, the Bridge advertises the full free tier: the eleven community tools plus these two (their substrate runs in the Bridge, so the CLI alone can't service them):
| Tool | What it does |
|------|--------------|
@@ -38,7 +38,7 @@ With `PIDGEON_MODE=bridge` and a running desktop app, the Bridge advertises the
## Pro tools
-These nine are server-advertised only after authentication, for a resolved subscription tier. They require a [Pidgeon account](/getting-started/account) with an active subscription — the **Agentic Seat** ($49/mo per developer or agent seat), or usage-metered credits.
+These nine are server-advertised only after authentication, for a resolved subscription tier. They require a [Pidgeon account](/getting-started/account) with an active subscription: the **Agentic Seat** (per developer or agent seat) or usage-metered credits.
| Tool | What it does |
|------|--------------|
@@ -54,9 +54,9 @@ These nine are server-advertised only after authentication, for a resolved subsc
## How the split is enforced
-The community set is a checked-in, fail-closed allowlist — registration by reflection or filesystem discovery is forbidden for the public composition. In Bridge mode the server registers exactly what the Bridge advertises for your tier; when a tier changes, the advertisement refreshes and newly entitled tools unlock. There is no way to surface a tool the active composition doesn't include.
+The community set is a checked-in, fail-closed allowlist; registration by reflection or filesystem discovery is forbidden for the public composition. In Bridge mode the server registers exactly what the Bridge advertises for your tier; when a tier changes, the advertisement refreshes and newly entitled tools appear. There is no way to surface a tool the active composition doesn't include.
## Next steps
-- [MCP Server overview](/mcp/overview) — install, transport modes, prompts, and resources
-- [Your Pidgeon account](/getting-started/account) — plan and entitlements
+- [MCP Server overview](/mcp/overview): install, transport modes, prompts, and resources
+- [Your Pidgeon account](/getting-started/account): plan and entitlements
diff --git a/migrate/bulk-data.mdx b/migrate/bulk-data.mdx
new file mode 100644
index 0000000..b7cdccb
--- /dev/null
+++ b/migrate/bulk-data.mdx
@@ -0,0 +1,48 @@
+---
+title: Bulk Data export
+description: Export a source EHR to FHIR R4 Bulk Data NDJSON with de-identification, reconciliation, dry-run, and resume.
+---
+
+`migrate run` exports from a source EHR to FHIR R4 Bulk Data NDJSON: one file per resource type plus a `manifest.json` conforming to the HL7 FHIR Bulk Data Access IG.
+
+```bash
+pidgeon migrate run --source --output [options]
+```
+
+v1 reads from Centricity / athenaPractice 23.0 `FHIR_*` views over a Postgres or SQL Server database, auto-detected by shape. The default resource set is Patient, Encounter, Observation, Condition, MedicationRequest, and Procedure; narrow or widen it with `--resources`.
+
+## De-identify on the way out
+
+Add `--deidentify` and Migrate runs every emitted resource through on-device de-identification before it's written. Cross-resource references stay coherent, so a de-identified Encounter still points at the right de-identified Patient.
+
+```bash
+pidgeon migrate run --source "Host=localhost;Database=centricity;..." --output ./export \
+ --deidentify --deident-date-shift +30d
+```
+
+`--deident-salt` fixes the hashing salt so references stay consistent across runs; `--deident-date-shift` shifts every date by a uniform offset.
+
+## Reconcile
+
+Every run reconciles resource counts per type: what the source held versus what was exported, so you can prove nothing was dropped. In the desktop app this is the reconciliation view; from the CLI it's part of the run output and the manifest.
+
+## Dry run first
+
+`--dry-run` reads, transforms, and reconciles without writing NDJSON. The manifest is still emitted, so you can validate the mapping and the counts before a real export.
+
+```bash
+pidgeon migrate run --source "..." --output ./export --dry-run
+```
+
+## Resume an interrupted run
+
+If a run is interrupted, Migrate writes a `.checkpoint.json` in the output directory. Re-run with `--resume` to continue from the checkpoint instead of starting over.
+
+```bash
+pidgeon migrate run --source "..." --output ./export --resume
+```
+
+## Next
+
+- [Mapping and analysis](/migrate/mapping)
+- [Migrate CLI reference](/cli/migrate-commands)
diff --git a/migrate/mapping.mdx b/migrate/mapping.mdx
new file mode 100644
index 0000000..35152ec
--- /dev/null
+++ b/migrate/mapping.mdx
@@ -0,0 +1,39 @@
+---
+title: Mapping and analysis
+description: Control per-field mapping with YAML, assess a migration with the analyst workflow, and submit a C-CDA to an IHE XDS.b registry.
+---
+
+## Mapping YAML
+
+`migrate run` ships sane defaults, and you can override per-field retain, redact, and date-shift policy with a mapping YAML:
+
+```bash
+pidgeon migrate run --source "..." --output ./export --mapping ./my-mapping.yml
+```
+
+The mapping controls how each source field is carried, redacted, or date-shifted, per customer. `--source-adapter` selects the source EHR adapter (default `centricity`).
+
+## Analyst: assess before you cut over
+
+`migrate analyst` is a deterministic, read-only analysis workflow. It assesses a source, reviews the mapping and loss catalog, converts a bounded sample (1–25 rows, so a run is fast and reproducible), clusters exceptions, analyzes reconciliation, and assembles cutover-readiness evidence. Results are local evidence artifacts; nothing is written back to the source.
+
+```bash
+pidgeon migrate analyst [options]
+```
+
+Use it to answer "what will this migration lose, and where" before you commit to a cutover.
+
+## to-xds: FHIR bundle to IHE XDS.b
+
+`migrate to-xds` reads a FHIR R4 bundle, generates a C-CDA, and submits it to an IHE XDS.b registry via ITI-41 Provide and Register:
+
+```bash
+pidgeon migrate to-xds --bundle ./bundle.json
+```
+
+With `--verify`, on by default, it confirms the round-trip by ITI-18 FindDocuments and ITI-43 Retrieve, and asserts the retrieved document is byte-identical to what it submitted.
+
+## Next
+
+- [Bulk Data export](/migrate/bulk-data)
+- [Migrate CLI reference](/cli/migrate-commands)
diff --git a/migrate/overview.mdx b/migrate/overview.mdx
new file mode 100644
index 0000000..e90ccea
--- /dev/null
+++ b/migrate/overview.mdx
@@ -0,0 +1,38 @@
+---
+title: Migrate overview
+description: Move production healthcare data between systems via FHIR R4 Bulk Data Access, with preflight checks, de-identification, reconciliation, and resume.
+---
+
+Migrate moves production healthcare data between systems via FHIR R4 Bulk Data Access. It exports from a source EHR to NDJSON per the HL7 Bulk Data Access IG, de-identifies on the way out when you ask it to, and reconciles resource counts so you can prove nothing was dropped. It is built for migration projects, not synthetic test data. If you need test populations, that's [Flock](/flock/overview).
+
+
+Migrate requires a Pidgeon account sign-in. v1 ships the `run` export workflow reading from Centricity / athenaPractice 23.0 `FHIR_*` views.
+
+
+## What Migrate does
+
+
+
+ `migrate run` reads a source EHR and writes one NDJSON file per resource type plus a `manifest.json` conforming to the HL7 FHIR Bulk Data Access IG.
+
+
+ `migrate analyst` assesses a source, reviews the mapping and loss catalog, converts a bounded sample, clusters exceptions, and assembles cutover-readiness evidence.
+
+
+
+Migrate also converts a FHIR bundle to a C-CDA and submits it to an IHE XDS.b registry with `migrate to-xds`. See [Mapping and analysis](/migrate/mapping).
+
+## Not a synthetic data tool
+
+Flock generates synthetic populations for QA. Migrate moves real production data for a migration. Different job, different data, different product. The two share the engine's parsers and de-identification, not a workflow.
+
+## Local Bridge
+
+Like the other desktop apps, Migrate runs its engine in a local Bridge sidecar on `localhost:5103`, reachable only on loopback while the app is open. Its Bridge routes aren't documented in the [API reference](/api-reference/introduction) yet, so drive Migrate from the [CLI](/cli/migrate-commands) or the [desktop app](/getting-started/migrate).
+
+## Next
+
+- [Bulk Data export](/migrate/bulk-data): the `run` workflow in depth
+- [Mapping and analysis](/migrate/mapping): mapping YAML, `analyst`, and `to-xds`
+- [Migrate CLI reference](/cli/migrate-commands)
+- [Get started with Migrate](/getting-started/migrate): the desktop app loop
diff --git a/post/ai-triage.mdx b/post/ai-triage.mdx
index b24d1ff..0100249 100644
--- a/post/ai-triage.mdx
+++ b/post/ai-triage.mdx
@@ -3,13 +3,13 @@ title: AI Triage
description: Stop deciphering cryptic validation errors. Get plain-English root cause analysis and fix suggestions, on-device by default.
---
-Pro feature — requires a Pidgeon account with Post Pro entitlement.
+Pro feature. Requires a Pidgeon account with Post Pro entitlement. AI Triage ships with the Post desktop app and the licensed CLI, not the free `dotnet tool install` build.
-Pass validation failures through an on-device model for root cause analysis — including vendor-specific context like "this is a common Epic-to-downstream mapping issue." On-device is the default posture: $0 marginal cost, and no message content leaves your machine unless you explicitly opt into a cloud provider.
+Pass validation failures through an on-device model for root cause analysis, including vendor-specific context like "this is a common Epic-to-downstream mapping issue." On-device is the default posture: $0 marginal cost, and no message content leaves your machine unless you explicitly opt into a cloud provider.
## Setup
-AI Triage runs on-device out of the box; no configuration is required. To opt into a cloud provider instead (BYOK — your keys, your cost control), set the egress policy and your provider key:
+AI Triage runs on-device out of the box; no configuration is required. To opt into a cloud provider instead (BYOK, your keys, your cost control), set the egress policy and your provider key:
```bash
pidgeon ai egress --mode byok-cloud --baa-opt-in true
@@ -18,14 +18,18 @@ export PIDGEON_OPENAI_KEY="sk-..."
export PIDGEON_ANTHROPIC_KEY="sk-ant-..."
```
-`pidgeon ai egress` (no arguments) shows the current PHI-egress policy. Every call that resolves to a non-local provider is audit-logged. See [CLI Reference](/cli/post-commands) for the full set of AI modes.
+`pidgeon ai egress` (no arguments) shows the current PHI-egress policy. Every call that resolves to a non-local provider is audit-logged. See [AI Commands](/cli/ai-commands) for the full set of AI modes and providers.
## Usage
+Triage a message that fails validation:
+
```bash
-pidgeon validate --file broken.hl7 --ai-triage
+pidgeon ai triage broken.hl7
```
+You can also open a validated message in the Post desktop app and run triage from the AI Triage panel. Both drive the same on-device analysis.
+
## Example Output
```text
@@ -44,4 +48,4 @@ Similar issues found: 23 messages in the last 24 hours
## API
-The AI Triage API is available at `POST /api/loft/triage`. See the [API Reference](/api-reference/ai-triage) for details.
+The Post Bridge exposes AI Triage at `POST /api/loft/triage` on `localhost:5101`. That route is unauthenticated because the Bridge is a single-user loopback sidecar: it only listens on `localhost` for the signed-in user, and the AI Triage feature itself stays gated behind Post Pro. See the [API Reference](/api-reference/ai-triage) for the request and response shape.
diff --git a/post/datasets.mdx b/post/datasets.mdx
index bfb8b6a..a68e5b9 100644
--- a/post/datasets.mdx
+++ b/post/datasets.mdx
@@ -1,9 +1,9 @@
---
title: Datasets & Data Packages
-description: Generated messages use real ICD-10 codes, real LOINC identifiers, and real NDC numbers — not placeholder values that fail downstream validation.
+description: Generated messages use real ICD-10 codes, real LOINC identifiers, and real NDC numbers, not placeholder values that fail downstream validation.
---
-Eight datasets ship with Pidgeon, from ICD-10 diagnosis codes to NDC drug products. Free tier includes basic subsets; Pro unlocks full datasets plus RxNorm, HCPCS, and CPT.
+Eight terminology datasets ship with Pidgeon, from ICD-10 diagnosis codes to NDC drug products. The free tier includes basic subsets; Pro includes the full datasets plus RxNorm and HCPCS. CPT is a separate licensed add-on (a ninth dataset), gated by AMA royalty terms.
## Available Datasets
@@ -17,10 +17,12 @@ Eight datasets ship with Pidgeon, from ICD-10 diagnosis codes to NDC drug produc
| CVX | 288 vaccine codes | Full | Full |
| RxNorm | Drug terminology | — | Full |
| HCPCS | Procedure/service codes | — | Full |
-| CPT | Procedure codes | — | Add-on ($30/user/yr) |
+| CPT | Procedure codes | — | Licensed add-on |
The CPT dataset requires a separate license add-on due to AMA royalty requirements.
+`pidgeon data` also manages FHIR Implementation Guide packages (US Core, Da Vinci PAS/CRD/DTR) and the license-gated NCPDP SCRIPT package. See [Data Commands](/cli/data-commands) for the full package catalog and install flags.
+
## Managing Datasets
```bash
diff --git a/post/de-identification.mdx b/post/de-identification.mdx
index 1ef70e7..f56fb6e 100644
--- a/post/de-identification.mdx
+++ b/post/de-identification.mdx
@@ -1,9 +1,9 @@
---
title: De-identification
-description: Stop manually scrubbing MRNs and patient names from production messages. De-identify on-device — no PHI ever leaves your machine.
+description: Stop manually scrubbing MRNs and patient names from production messages. De-identify on-device, so no PHI ever leaves your machine.
---
-Four methods — from simple Safe Harbor removal to full synthetic replacement — covering 80+ PHI fields across 10 HL7 segment types. Everything runs locally.
+Four methods, from Safe Harbor removal to full synthetic replacement, covering 80+ PHI fields across 10 HL7 segment types. Everything runs locally.
This tool assists with de-identification but does not guarantee HIPAA Safe Harbor compliance on its own. Always review output and consult your compliance team.
@@ -14,7 +14,7 @@ Four methods — from simple Safe Harbor removal to full synthetic replacement
Removes all 18 HIPAA Safe Harbor identifiers. The simplest and most conservative approach.
- Removes identifiers **and** replaces them with realistic synthetic values. The result looks like a real message — useful for testing downstream systems that reject empty fields.
+ Removes identifiers **and** replaces them with synthetic values. The result looks like a real message, which helps when testing downstream systems that reject empty fields.
Statistical approach using k-anonymity and l-diversity analysis. Configurable risk thresholds let you balance data utility against re-identification risk. Produces equivalence class analysis and risk scoring reports.
@@ -62,9 +62,9 @@ pidgeon deident --in ./real --out ./safe --date-shift 30d --keep-ids
Post can assess re-identification risk for your de-identified output:
-- **k-anonymity scoring** — Measures whether individuals can be singled out
-- **l-diversity analysis** — Checks sensitive attribute diversity within equivalence classes
-- **Compliance reporting** — HTML and JSON reports suitable for audit documentation
+- **k-anonymity scoring**: measures whether individuals can be singled out
+- **l-diversity analysis**: checks sensitive attribute diversity within equivalence classes
+- **Compliance reporting**: HTML and JSON reports suitable for audit documentation
## Consistency Across Batches
diff --git a/post/diff.mdx b/post/diff.mdx
new file mode 100644
index 0000000..a26b394
--- /dev/null
+++ b/post/diff.mdx
@@ -0,0 +1,59 @@
+---
+title: Diff
+description: Compare two messages or two directories field by field. Field-aware for HL7, JSON-tree for FHIR, with an HTML report you can attach to a ticket.
+---
+
+Pro feature. Requires a Pidgeon account with Post Pro entitlement. Diff ships with the Post desktop app and the licensed CLI, not the free `dotnet tool install` build.
+
+When a message works in one environment and fails in another, the question is always the same: what actually changed? Diff answers it at the field level. Point it at two messages, or two directories, and it reports every field that differs, not a line-by-line text diff that buries the one field that matters.
+
+## What it compares
+
+- **HL7 v2**: field-aware. Differences are reported by segment and field position (`PID.5.1`, `PV1.44`), not raw character offsets, so a re-ordered optional field or a changed subcomponent surfaces as one clear entry.
+- **FHIR R4**: JSON-tree. Differences are reported by resource path.
+- **Directories**: compare a baseline folder against a candidate folder to diff a whole environment at once.
+
+## Usage
+
+```bash
+# Compare two messages
+pidgeon diff env-a/admit.hl7 env-b/admit.hl7
+
+# Compare two environments and write an HTML report
+pidgeon diff ./dev ./staging --report diff-report.html
+```
+
+## Ignore volatile fields
+
+Message control IDs and timestamps change on every send. Skip them so the diff shows only meaningful changes:
+
+```bash
+pidgeon diff env-a/admit.hl7 env-b/admit.hl7 --ignore MSH-7,MSH-10
+```
+
+`--ignore` takes a comma-list of segments or fields. Wildcards work too (`OBX-*` ignores every OBX field).
+
+## Severity and mode
+
+| Flag | Values | Description |
+|------|--------|-------------|
+| `--severity, -s` | `hint` (default), `warn`, `error` | Minimum severity to report. |
+| `--report, -o ` | HTML or JSON | Write a self-contained report; the format follows the file extension. |
+| `--basic, -b` | flag | Plain diff, without constraint validation or demographic analysis. |
+
+By default Diff runs constraint-aware analysis: it understands which fields carry coded values and flags a change that would break downstream validation, not just any change.
+
+## HTML report
+
+The `--report` output is a self-contained HTML file: the field-level change table plus triage hints, ready to attach to a ticket or hand to a stakeholder. No server, no external assets.
+
+AI-assisted diff hints are not yet available. The `--ai` flag is reserved for a future release; today Diff runs its constraint-aware field analysis without a model.
+
+## From the CLI or the app
+
+Diff is a pane in the Post desktop app and a command in the CLI. Both drive the same engine. See [Post Commands](/cli/post-commands#pidgeon-diff) for the full flag reference and the [Bridge API](/api-reference/diff) for the programmatic route.
+
+## Next steps
+
+- [Validation](/post/validation): catch spec and vendor deviations before diffing
+- [Vendor Profiles](/post/vendor-profiles): compare against your vendor's real patterns
diff --git a/post/message-generation.mdx b/post/message-generation.mdx
index e9c22ab..8489d63 100644
--- a/post/message-generation.mdx
+++ b/post/message-generation.mdx
@@ -1,9 +1,9 @@
---
title: Message Generation
-description: Generate realistic HL7, FHIR, and NCPDP test messages in seconds — no manual creation, no production data copying, no compliance risk.
+description: Generate HL7, FHIR, and NCPDP test messages in seconds. No manual creation, no production data copying, no compliance risk.
---
-Every code uses real reference datasets — ICD-10, LOINC, NDC, SNOMED CT, CVX, RxNorm, HCPCS — so generated messages pass downstream validation the same way production data would.
+Every code comes from a real reference dataset (ICD-10, LOINC, NDC, SNOMED CT, CVX, RxNorm, HCPCS), so generated messages pass downstream validation the same way production data would.
## Supported Standards
@@ -21,7 +21,7 @@ pidgeon generate Bundle
```
```bash NCPDP SCRIPT
-# NCPDP is license-gated — see below
+# NCPDP is license-gated (see below)
pidgeon generate NewRx
pidgeon generate RxFill
pidgeon generate CancelRx
@@ -32,46 +32,46 @@ pidgeon generate CancelRx
## HL7 v2 Coverage
-Post's HL7 v2 parsing and generation is structurally broad, but the number that matters is what's proven end-to-end: generate → validate → round-trip against the published spec. That verified set is **279 HL7 message-type × version combinations** — 38 message types, each across some or all of HL7 v2.3 through v2.8 — from the engine's own runtime capability matrix, not a hand-maintained table:
+Post's HL7 v2 parsing and generation is structurally broad. The number that matters is what's proven from generation through validation and round-trip against the published spec: **279 HL7 message-type × version combinations** across 38 message types, each covering some or all of HL7 v2.3 through v2.8. It comes from the engine's own runtime capability matrix, not a hand-maintained table:
```bash
pidgeon --output-format json capabilities --standard hl7
```
-
+
`ADT^A01` Admission, `ADT^A02` Transfer, `ADT^A03` Discharge, `ADT^A04` Registration, `ADT^A05` Pre-admit, `ADT^A08` Update patient info, `ADT^A11` Cancel admit, `ADT^A12` Cancel transfer, `ADT^A13` Cancel discharge
`ORM^O01` General order, `ORU^R01` Observation result, `OML^O21` Lab order (multi-order), `RSP^K11`/`K21`/`K22` Query responses, `QBP^Q11`/`Q21`/`Q22` Query by parameter
-
+
`RDE^O11` Pharmacy/treatment encoded order, `RDE^O25` Pharmacy/treatment refill authorization, `RGV^O15` Pharmacy/treatment give, `RAS^O17` Pharmacy/treatment administration
-
+
`SIU^S12` New appointment, `SIU^S13` Request rescheduling, `SIU^S14` Modification notification, `SIU^S15` Cancellation notification, `SIU^S17` Deletion notification
-
+
`MDM^T02` Original with content, `MDM^T04`/`T06`/`T08`/`T10` document addenda, status changes, and replacements
-
+
`BAR^P01` Add patient account, `BAR^P02` Purge patient account, `BAR^P05` Update account, `DFT^P03` Post detail financial transaction
-
+
`VXU^V04` Unsolicited vaccination update
-
+
`ACK` general acknowledgment
Shell-safe syntax is supported: `ADT-A01`, `ADT_A01`, and `ADT.A01` all work as alternatives to `ADT^A01`.
-This list is the current spec-validated set, not a ceiling — Post's parser handles a broader range of HL7 v2 structurally. Run `pidgeon capabilities` for the live matrix rather than trusting this page to stay current.
+These 38 message types are the current spec-validated set, not a ceiling. Post's parser handles a broader range of HL7 v2 structurally. Run `pidgeon capabilities` for the live matrix rather than trusting this page to stay current.
## FHIR R4 Resources
-**24 resource types** at spec-validated level, spanning clinical, administrative, and financial domains:
+**137 resource types** at spec-validated level, spanning clinical, administrative, and financial domains. Common types by domain:
@@ -97,13 +97,15 @@ pidgeon --output-format json capabilities --standard hl7
+The accordion lists common resource types. The full spec-validated set is 137; run `pidgeon capabilities --standard fhir` for the live matrix.
+
```bash
pidgeon --output-format json capabilities --standard fhir
```
## NCPDP SCRIPT 2017071
-NCPDP SCRIPT generation is **closed by default** and license-gated. NCPDP's SCRIPT XSDs are member-only, so the standards material is not shipped: confirm your NCPDP membership, then run `pidgeon data install ncpdp-script --accept-license` to enable generation. Until the package is installed, NCPDP is reported as license-required.
+NCPDP SCRIPT generation is **closed by default** and license-gated. NCPDP's SCRIPT XSDs are member-only, so the standards material is not shipped: confirm your NCPDP membership, then run `pidgeon data install ncpdp-script --accept-license` to install the package. Until it is installed, NCPDP is reported as license-required rather than emitting a message.
Once enabled, the SCRIPT transaction set spans the prescription workflow with XML serialization and structural validation:
@@ -122,7 +124,7 @@ Once enabled, the SCRIPT transaction set spans the prescription workflow with XM
-Run `pidgeon --output-format json capabilities --standard ncpdp` for the exact enabled set on your machine — it reports the license-required state until the `ncpdp-script` package is installed.
+Run `pidgeon --output-format json capabilities --standard ncpdp` for the exact enabled set on your machine. It reports the license-required state until the `ncpdp-script` package is installed.
## Generation Modes
@@ -135,19 +137,19 @@ Once enabled, the SCRIPT transaction set spans the prescription workflow with XM
```
-
- Uses a local AI model for enhanced clinical narratives and realistic note text.
+
+ Uses a local AI model for clinical narratives and free-text note content. On-device by default, so no message content leaves the machine.
```bash
- pidgeon generate ORU^R01 --mode local-ai
+ pidgeon generate ORU^R01 --mode model
```
-
- Cloud AI provider for highest quality clinical narratives. Requires BYOK configuration.
+
+ Routes narrative generation to a configured cloud provider (BYOK). Off-device inference requires an explicit opt-in.
```bash
- pidgeon generate MDM^T02 --mode api-ai
+ pidgeon generate MDM^T02 --mode api
```
diff --git a/post/validation.mdx b/post/validation.mdx
index b506b99..3a421a4 100644
--- a/post/validation.mdx
+++ b/post/validation.mdx
@@ -3,7 +3,7 @@ title: Validation
description: Catch message errors before they reach production. Validate HL7 v2.3–v2.8, FHIR R4, and NCPDP SCRIPT against specs or your vendor's real-world patterns.
---
-Two modes — **strict** for spec compliance, **compatibility** for real-world vendor tolerance — across three standards and eight HL7 versions.
+Two modes across three standards and eight HL7 versions: **strict** for spec compliance, **compatibility** for real-world vendor tolerance.
@@ -19,10 +19,10 @@ Two modes — **strict** for spec compliance, **compatibility** for real-world v
| Standard | Versions | What's Validated |
|----------|----------|-----------------|
| HL7 v2 | **v2.3, v2.3.1, v2.4, v2.5, v2.5.1, v2.6, v2.7, v2.8** | Segment structure, required fields, data types, code sets, segment ordering |
-| FHIR R4 | R4 | Required elements, cardinality, terminology bindings, 24 resource types, profile constraints |
+| FHIR R4 | R4 | Required elements, cardinality, terminology bindings, 137 resource types, profile constraints |
| NCPDP SCRIPT | 2017071 | Transaction structure, NPI Luhn check, DEA format validation, required fields |
-HL7 v2 and FHIR R4 validation are free. NCPDP SCRIPT validation depends on the member-only SCRIPT standards package — install it with `pidgeon data install ncpdp-script --accept-license` (NCPDP membership required) before validating NCPDP messages.
+HL7 v2 and FHIR R4 validation are free. NCPDP SCRIPT validation depends on the member-only SCRIPT standards package. Install it with `pidgeon data install ncpdp-script --accept-license` (NCPDP membership required) before validating NCPDP messages.
## Usage
@@ -77,7 +77,7 @@ Each validation issue includes the expected value, actual value, a fix suggestio
pidgeon validate --file message.hl7 --mode strict --output json
```
-Returns the full `ValidationResult` as JSON — including `isValid`, all issues with diagnostic fields (`expectedValue`, `actualValue`, `suggestion`), and summary statistics (`fieldsValidated`, `conformanceScore`, `validationTime`). Exit code 0 on pass, 1 on fail.
+Returns the full `ValidationResult` as JSON, including `isValid`, all issues with diagnostic fields (`expectedValue`, `actualValue`, `suggestion`), and summary statistics (`fieldsValidated`, `conformanceScore`, `validationTime`). Exit code 0 on pass, 1 on fail.
## Vendor Profile Validation
@@ -87,4 +87,4 @@ Validate against your vendor's actual patterns instead of just the spec:
pidgeon validate --file test.hl7 --profile epic_er
```
-Compatibility mode with a vendor profile catches the issues that matter in your specific environment — not just spec violations, but deviations from how your vendor actually sends messages. See [Vendor Profiles](/post/vendor-profiles).
+Compatibility mode with a vendor profile catches the issues that matter in your specific environment: not just spec violations, but deviations from how your vendor actually sends messages. See [Vendor Profiles](/post/vendor-profiles).
diff --git a/post/vendor-profiles.mdx b/post/vendor-profiles.mdx
index 906e646..ca21ee4 100644
--- a/post/vendor-profiles.mdx
+++ b/post/vendor-profiles.mdx
@@ -37,9 +37,9 @@ Point Post at a sample directory, and it extracts field population rates, segmen
## Built-in Vendor Baselines
-Post includes baseline profiles for Epic, Cerner (Oracle Health), AllScripts, and Meditech.
+Post includes baseline profiles for Epic, Cerner (Oracle Health), Allscripts, and Meditech.
-Built-in profiles provide a starting point. For best results, create custom profiles from your actual message samples — every installation is different.
+Built-in profiles provide a starting point. For best results, create custom profiles from your actual message samples. Every installation is different.
## Profile Management
diff --git a/post/workflow-wizard.mdx b/post/workflow-wizard.mdx
index 8856485..fbfa311 100644
--- a/post/workflow-wizard.mdx
+++ b/post/workflow-wizard.mdx
@@ -3,9 +3,9 @@ title: Workflow Wizard
description: Define admit-to-discharge or order-to-result test scenarios in YAML and run them repeatedly. No more rebuilding test sequences by hand.
---
-Pro feature — requires a Pidgeon account with Post Pro entitlement, in the desktop app or the CLI.
+Pro feature. Requires a Pidgeon account with Post Pro entitlement. It ships with the Post desktop app and the licensed CLI, not the free `dotnet tool install` build.
-Define multi-step clinical scenarios in YAML — admission, orders, results, discharge — with relative timing between steps. Patient data stays consistent across every message in the sequence.
+Define multi-step clinical scenarios in YAML (admission, orders, results, discharge) with relative timing between steps. Patient data stays consistent across every message in the sequence.
## Interactive Mode
diff --git a/support/faq.mdx b/support/faq.mdx
index 97989b3..7dca230 100644
--- a/support/faq.mdx
+++ b/support/faq.mdx
@@ -51,11 +51,11 @@ description: Accounts, data handling, supported standards, SmartScreen, the Brid
- The Bridge is the local engine sidecar each desktop app starts: Loft on `localhost:5100`, Post on `localhost:5101`, Flock on `localhost:5102`. It binds to loopback only. When an app reports the Bridge as offline, open Settings → Connection in that app and retry.
+ The Bridge is the local engine sidecar each desktop app starts: Loft on `localhost:5100`, Post on `localhost:5101`, Flock on `localhost:5102`, Migrate on `localhost:5103`, and Conform on `localhost:5104`. The Bridge binds to loopback only. When an app reports the Bridge as offline, open Settings → Connection in that app and retry.
- The CLI exposes generate, validate, conform, and de-identify from a terminal with Unix exit codes (`0` success, `1` failure). Start with the [CLI quickstart](/getting-started/quickstart-cli).
+ The free CLI exposes generate, validate, and de-identify from a terminal with Unix exit codes (`0` success, `1` failure). App-delivered commands (`conform`, `flock`, `loft`, `migrate`, `ai`, `diff`, `config`) ship with the CLI bundled inside the desktop apps. Start with the [CLI quickstart](/getting-started/quickstart-cli).
diff --git a/support/known-issues.mdx b/support/known-issues.mdx
index f319476..5d68126 100644
--- a/support/known-issues.mdx
+++ b/support/known-issues.mdx
@@ -3,16 +3,14 @@ title: Known issues
description: Current limitations in the Pidgeon beta, each with a workaround or a status.
---
-Current beta release: `0.2.0-beta.1`. This page tracks known limitations in the beta. If you hit something that isn't listed, email [support@pidgeon.health](mailto:support@pidgeon.health).
-
-{/* Beta limitation entries land here as app-nucleus QA and release rehearsal surface them. Keep one row per issue: Surface / Issue / Workaround / Status. */}
+Current beta release: `0.2.0-beta.1` (desktop apps); CLI `0.1.0-beta.2`. This page tracks known limitations in the beta. If you hit something that isn't listed, email [support@pidgeon.health](mailto:support@pidgeon.health).
## Install and delivery
| Surface | Issue | Workaround | Status |
|---|---|---|---|
| Windows | SmartScreen may warn on early downloads even though installers are signed by Pattern Engine LLC | Verify the signature (Properties → Digital Signatures), then More info → Run anyway. Details: [Install on Windows](/getting-started/install-windows) | Expected to fade as publisher reputation accrues |
-| All apps | Automatic update checks are not yet enabled in beta builds | Watch the downloads catalog for new versions and install over the existing app | Update channel is planned beta work |
+| All apps | Automatic update checks are not yet available in beta builds | Watch the downloads catalog for new versions and install over the existing app | Update channel is planned beta work |
## Apps
@@ -20,6 +18,7 @@ Current beta release: `0.2.0-beta.1`. This page tracks known limitations in the
|---|---|---|---|
| Loft | Desktop app only; opening the UI in a browser tab shows a desktop-only notice | Use the installed desktop app | By design for the beta |
| Migrate | Sidebar entries marked "Soon" (Export Wizard, Mappings, History) are not active | The Dashboard runs the full preflight, export, reconcile, and resume loop | Planned |
+| Conform | Standalone Conform app is in beta and not yet a separate download | Run conformance from Post's Conformance panel, or from the CLI bundled with the desktop apps | Standalone app is planned beta work |
## Reporting
diff --git a/support/troubleshooting.mdx b/support/troubleshooting.mdx
index 9b4cb09..e16457a 100644
--- a/support/troubleshooting.mdx
+++ b/support/troubleshooting.mdx
@@ -1,23 +1,26 @@
---
title: Troubleshooting
-description: What each app shows when the Bridge is offline, input is invalid, or credentials are missing — and the next action for every case.
+description: What each app shows when the Bridge is offline, input is invalid, or credentials are missing, plus the next action for every case.
---
-Every Pidgeon app fails the same way on purpose: the window chrome and navigation stay on screen, the error is bounded and names what happened, and there's a clear next action — usually a **Retry**. You should never see a blank wall. This page lists, per surface, what a failure actually looks like and what to do.
+Every Pidgeon app fails the same way on purpose: the window chrome and navigation stay on screen, the error is bounded and names what happened, and there's a clear next action, usually a **Retry**. You should never see a blank wall. This page lists, per surface, what a failure actually looks like and what to do.
## First thing to check: the Bridge
-Each desktop app starts a local engine sidecar — the **Bridge** — on a loopback port. Most "the app won't do anything" reports are a Bridge that isn't running yet or has stopped.
+Each desktop app starts a local engine sidecar (the **Bridge**) on a loopback port. Most "the app won't do anything" reports are a Bridge that isn't running yet or has stopped.
| App | Bridge port | How the app reaches it |
|---|---|---|
| Loft | `localhost:5100` | HTTP health poll |
| Post | `localhost:5101` | HTTP API |
| Flock | `localhost:5102` | HTTP health poll |
-| Migrate | (Tauri-invoke) | desktop bridge call, not an HTTP port |
-| Pidgeon launcher | — | no Bridge of its own; probes each product directly |
+| Conform | `localhost:5104` | HTTP API (standalone app in beta; conformance runs in Post today) |
+| Migrate | `localhost:5103` | HTTP API |
+| Pidgeon launcher | none | no Bridge of its own; probes each product directly |
-When an app reports the Bridge offline, the fix is the same: make sure the app finished starting, then use the in-app **Retry** (or **Settings → Connection**). The Bridge binds to loopback only — nothing listens on your network.
+When an app reports the Bridge offline, the fix is the same: make sure the app finished starting, then use the in-app **Retry** (or **Settings → Connection**). The Bridge binds to loopback only; nothing listens on your network.
+
+Conformance runs inside Post today, on Post's `5101` Bridge, so conformance failures surface under [Post](#post) below. The standalone Conform app on `5104` is in beta and not yet downloadable.
## Post
@@ -46,7 +49,7 @@ When an app reports the Bridge offline, the fix is the same: make sure the app f
| What you see | What it means | Next action |
|---|---|---|
| A banner **"Bridge API unreachable"** and a second **"Tauri bridge unavailable"**, both with **Retry**; a red **"Bridge offline"** footer pill | Migrate's desktop bridge call isn't resolving | Retry once the app has fully started. |
-| The **"Start export wizard"** button is **disabled** | The wizard is gated until the Bridge is available (it does not crash) | Restore the Bridge connection; the button enables when the app can reach it. |
+| The **"Start export wizard"** button is **disabled** | The wizard is gated until the Bridge is available (it does not crash) | Restore the Bridge connection; the button becomes active when the app can reach it. |
| **"No migrations yet"** empty state | No migration has been run on this machine | Expected on a fresh install; run the Dashboard preflight to begin. |
## Pidgeon launcher
@@ -59,7 +62,7 @@ When an app reports the Bridge offline, the fix is the same: make sure the app f
## CLI
-The CLI follows Unix conventions: exit `0` on success, exit `1` on failure — so it slots straight into CI gates.
+The CLI follows Unix conventions: exit `0` on success, exit `1` on failure, so it slots straight into CI gates.
| What you see | What it means | Next action |
|---|---|---|
@@ -68,7 +71,7 @@ The CLI follows Unix conventions: exit `0` on success, exit `1` on failure — s
| Strict-mode validation exits `1` | The message has conformance issues | Read the reported issues; exit `1` is the intended CI signal, not a tool crash. |
-On macOS, if the installed tool can't find a runtime, set `DOTNET_ROOT` to your dotnet install path (for example `/usr/local/share/dotnet`) before running `pidgeon`.
+On macOS or Linux, if the `dotnet tool` install can't find a runtime, set `DOTNET_ROOT` to your dotnet install path before running `pidgeon`. For example `/usr/local/share/dotnet` on macOS, or `/usr/share/dotnet` (or `$HOME/.dotnet` for a manual install) on Linux, depending on how you installed .NET. The current public beta uses the .NET tool as its cross-platform install path; the separate signed ZIP in `0.1.0-beta.2` is a Windows artifact.
## Account portal
@@ -80,4 +83,4 @@ On macOS, if the installed tool can't find a runtime, set `DOTNET_ROOT` to your
## Still stuck?
-Email [support@pidgeon.health](mailto:support@pidgeon.health) with the app name, version (status bar), your OS, whether the Bridge status pill showed online or offline, and what you expected versus what happened. Check [Known issues](/support/known-issues) first — your problem may already have a workaround.
+Email [support@pidgeon.health](mailto:support@pidgeon.health) with the app name, version (status bar), your OS, whether the Bridge status pill showed online or offline, and what you expected versus what happened. Check [Known issues](/support/known-issues) first; your problem may already have a workaround.