Commit bd9fe39
authored
feat: make indexing and compile concurrency configurable (#174)
* feat(indexer): expose pageindex_max_concurrency to cap indexing concurrency
PageIndex fans out one indexing LLM call per structure node; on a large
document that can open a socket per node and exhaust the process
file-descriptor limit ("[Errno 24] Too many open files"). This wires an
OpenKB config knob through to PageIndex's IndexConfig.max_concurrency cap.
- New `pageindex_max_concurrency` KB config key (default None = let PageIndex
apply its own default).
- indexer forwards it via `_build_index_config` only when set AND the installed
PageIndex's IndexConfig declares the field, so OpenKB keeps working against a
pinned PageIndex that predates it (IndexConfig forbids unknown kwargs).
* feat(config): make compile concurrency configurable (closes #173)
Concept/entity generation ran at a hardcoded concurrency of 5
(DEFAULT_COMPILE_CONCURRENCY) with no way to lower it when the LLM provider
rate-limits. Add a `compile_concurrency` config key (default 5) and thread it
through every add / recompile / cloud-import compile call via a shared
`_compile_concurrency` resolver (null / non-positive → the compiler default).
Pairs with `pageindex_max_concurrency` (indexing side) from this PR — both
concurrency knobs are now KB-configurable.
* fix(config): address xhigh code-review findings on the concurrency knobs
- resolve_compile_concurrency moves to config.py (matching resolve_timeout's
convention) and now rejects bool (bool is an int subclass, so
`compile_concurrency: true` previously silently became concurrency=1) and
logs a warning on any malformed value, same as the other resolvers.
- _build_index_config now warns when pageindex_max_concurrency is configured
but the installed PageIndex doesn't support the field yet, instead of
silently dropping it with no signal to the user.
- Replaced the tautological test_forwards_max_concurrency_when_supported
(which branched on the same runtime condition as the code under test, so it
never exercised the forwarding assertion under CI's pinned PageIndex) with
fake IndexConfig doubles that make both branches deterministic regardless
of the installed pageindex version.
- Added a cross-check test pinning DEFAULT_CONFIG["compile_concurrency"]
against the compiler's own DEFAULT_COMPILE_CONCURRENCY so the two literals
can't silently drift apart.
- Added an end-to-end test proving index_long_document's own loaded config
(not just a hand-built dict) reaches PageIndexClient's IndexConfig.
- Hoisted the compile-concurrency resolution out of `recompile --all`'s
per-document loop (was recomputed every iteration despite being
loop-invariant).
- Documented both new config.yaml keys in config.yaml.example and
examples/configuration/README.md (kept in sync).
* refactor(config): unify pageindex_max_concurrency + compile_concurrency into `concurrency`
PageIndex indexing and OpenKB's own concept/entity compilation never run
concurrently with each other for the same document (they're sequential
phases of one add), and both knobs exist for the exact same reason — the
user hit a provider rate limit or an fd ceiling. Splitting them by internal
subsystem leaked OpenKB's architecture into the config surface for no
practical benefit, since a user tuning one for a rate limit would set the
other to the same value anyway.
- Single `concurrency` config key (default null = each stage keeps its own
built-in default).
- config.resolve_concurrency(config) -> int | None: validates (rejects bool
and non-positive values with a warning), returns None on unset/invalid —
no default substitution inside; callers decide what None means for them.
- cli.py's compile call sites: `resolve_concurrency(config) or
DEFAULT_COMPILE_CONCURRENCY`.
- indexer.py's _build_index_config now routes through resolve_concurrency
(openkb validates before forwarding to PageIndex, rather than relying
solely on PageIndex's own future validator) instead of raw config.get.
- This also removes the prior dual-literal-default drift risk entirely:
there's no second numeric default to keep in sync, since an unset
`concurrency` simply forwards nothing to PageIndex and lets the compiler
use its own DEFAULT_COMPILE_CONCURRENCY.
- Updated config.yaml.example and examples/configuration/README.md (kept in
sync) to the single key.
* build(deps): bump pageindex to 0.3.0.dev2 (ships IndexConfig.max_concurrency)
0.3.0.dev2 is the first published release that declares
IndexConfig.max_concurrency, so `concurrency` in config.yaml now takes
effect for the indexing stage in a normal `pip install` / `uv sync`, not
just against a local editable checkout. Vetted: downloaded the wheel and
confirmed its sha256 matches PyPI (b0cb1f6e…) and that IndexConfig declares
`max_concurrency: int | None` with a positivity field_validator. uv.lock
regenerated via `uv lock --upgrade-package pageindex`.
The runtime `"max_concurrency" in IndexConfig.model_fields` guard in
indexer._build_index_config is now always-true under the pinned dependency,
but is kept as graceful degradation for mismatched local installs.
* refactor(config): keep concurrency out of DEFAULT_CONFIG (align with other optional knobs)
Every other optional tuning knob (timeout, extra_headers, litellm,
entity_types, parallel_tool_calls) is resolved via its resolver's .get()
and lives only in config.yaml.example, not DEFAULT_CONFIG — which holds just
the core keys openkb init writes (model, language, pageindex_threshold).
concurrency was the lone exception; resolve_concurrency already reads it via
.get(), so the DEFAULT_CONFIG entry was redundant. Remove it for consistency.
* build(deps): bump pageindex 0.3.0.dev2 -> 0.3.0.dev3
Vetted: identical Requires-Dist/Requires-Python to dev2; IndexConfig,
PageIndexClient, and IndexConfig.max_concurrency (used by #174) all still
present; wheel/sdist hashes verified against PyPI. uv.lock regenerated via
`uv lock` (change scoped to the pageindex entry). Also aligns the stale
dev1 reference in the config README.
* feat(cli): add --version flag
The CLI group had no way to report its version (`openkb version` / `openkb -v`
both fail). Add `@click.version_option(package_name="openkb")` so `openkb
--version` prints "openkb <version>", read from installed package metadata
(tracks the hatch-vcs-derived version, no hardcoded string).1 parent 6774c59 commit bd9fe39
11 files changed
Lines changed: 306 additions & 17 deletions
File tree
- examples/configuration
- openkb
- tests
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
2 | 2 | | |
3 | 3 | | |
4 | 4 | | |
| 5 | + | |
| 6 | + | |
| 7 | + | |
| 8 | + | |
| 9 | + | |
| 10 | + | |
5 | 11 | | |
6 | 12 | | |
7 | 13 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
12 | 12 | | |
13 | 13 | | |
14 | 14 | | |
15 | | - | |
| 15 | + | |
16 | 16 | | |
17 | 17 | | |
18 | 18 | | |
| |||
70 | 70 | | |
71 | 71 | | |
72 | 72 | | |
| 73 | + | |
| 74 | + | |
| 75 | + | |
| 76 | + | |
| 77 | + | |
| 78 | + | |
73 | 79 | | |
74 | 80 | | |
75 | 81 | | |
| |||
105 | 111 | | |
106 | 112 | | |
107 | 113 | | |
| 114 | + | |
108 | 115 | | |
109 | 116 | | |
110 | 117 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
47 | 47 | | |
48 | 48 | | |
49 | 49 | | |
50 | | - | |
| 50 | + | |
51 | 51 | | |
52 | 52 | | |
53 | 53 | | |
54 | 54 | | |
55 | 55 | | |
56 | 56 | | |
| 57 | + | |
57 | 58 | | |
58 | 59 | | |
59 | 60 | | |
| |||
561 | 562 | | |
562 | 563 | | |
563 | 564 | | |
| 565 | + | |
564 | 566 | | |
565 | 567 | | |
566 | 568 | | |
| |||
569 | 571 | | |
570 | 572 | | |
571 | 573 | | |
572 | | - | |
| 574 | + | |
| 575 | + | |
| 576 | + | |
| 577 | + | |
| 578 | + | |
| 579 | + | |
| 580 | + | |
573 | 581 | | |
574 | 582 | | |
575 | 583 | | |
| |||
690 | 698 | | |
691 | 699 | | |
692 | 700 | | |
| 701 | + | |
693 | 702 | | |
694 | 703 | | |
695 | 704 | | |
| |||
748 | 757 | | |
749 | 758 | | |
750 | 759 | | |
| 760 | + | |
751 | 761 | | |
752 | 762 | | |
753 | 763 | | |
| |||
1642 | 1652 | | |
1643 | 1653 | | |
1644 | 1654 | | |
| 1655 | + | |
1645 | 1656 | | |
1646 | 1657 | | |
1647 | 1658 | | |
| |||
1677 | 1688 | | |
1678 | 1689 | | |
1679 | 1690 | | |
1680 | | - | |
| 1691 | + | |
| 1692 | + | |
| 1693 | + | |
| 1694 | + | |
| 1695 | + | |
| 1696 | + | |
| 1697 | + | |
| 1698 | + | |
| 1699 | + | |
| 1700 | + | |
1681 | 1701 | | |
1682 | 1702 | | |
1683 | 1703 | | |
| |||
1697 | 1717 | | |
1698 | 1718 | | |
1699 | 1719 | | |
1700 | | - | |
| 1720 | + | |
| 1721 | + | |
| 1722 | + | |
| 1723 | + | |
| 1724 | + | |
| 1725 | + | |
| 1726 | + | |
| 1727 | + | |
| 1728 | + | |
1701 | 1729 | | |
1702 | 1730 | | |
1703 | 1731 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
200 | 200 | | |
201 | 201 | | |
202 | 202 | | |
| 203 | + | |
| 204 | + | |
| 205 | + | |
| 206 | + | |
| 207 | + | |
| 208 | + | |
| 209 | + | |
| 210 | + | |
| 211 | + | |
| 212 | + | |
| 213 | + | |
| 214 | + | |
| 215 | + | |
| 216 | + | |
| 217 | + | |
| 218 | + | |
| 219 | + | |
| 220 | + | |
| 221 | + | |
| 222 | + | |
| 223 | + | |
| 224 | + | |
| 225 | + | |
| 226 | + | |
203 | 227 | | |
204 | 228 | | |
205 | 229 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
11 | 11 | | |
12 | 12 | | |
13 | 13 | | |
14 | | - | |
| 14 | + | |
15 | 15 | | |
16 | 16 | | |
17 | 17 | | |
| |||
153 | 153 | | |
154 | 154 | | |
155 | 155 | | |
| 156 | + | |
| 157 | + | |
| 158 | + | |
| 159 | + | |
| 160 | + | |
| 161 | + | |
| 162 | + | |
| 163 | + | |
| 164 | + | |
| 165 | + | |
| 166 | + | |
| 167 | + | |
| 168 | + | |
| 169 | + | |
| 170 | + | |
| 171 | + | |
| 172 | + | |
| 173 | + | |
| 174 | + | |
| 175 | + | |
| 176 | + | |
| 177 | + | |
| 178 | + | |
| 179 | + | |
| 180 | + | |
| 181 | + | |
| 182 | + | |
156 | 183 | | |
157 | 184 | | |
158 | 185 | | |
| |||
166 | 193 | | |
167 | 194 | | |
168 | 195 | | |
169 | | - | |
170 | | - | |
171 | | - | |
172 | | - | |
173 | | - | |
| 196 | + | |
174 | 197 | | |
175 | 198 | | |
176 | 199 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
32 | 32 | | |
33 | 33 | | |
34 | 34 | | |
35 | | - | |
| 35 | + | |
36 | 36 | | |
37 | 37 | | |
38 | 38 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
97 | 97 | | |
98 | 98 | | |
99 | 99 | | |
| 100 | + | |
| 101 | + | |
| 102 | + | |
| 103 | + | |
| 104 | + | |
| 105 | + | |
| 106 | + | |
| 107 | + | |
| 108 | + | |
| 109 | + | |
| 110 | + | |
| 111 | + | |
| 112 | + | |
| 113 | + | |
| 114 | + | |
| 115 | + | |
| 116 | + | |
| 117 | + | |
| 118 | + | |
| 119 | + | |
| 120 | + | |
| 121 | + | |
| 122 | + | |
100 | 123 | | |
101 | 124 | | |
102 | 125 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
9 | 9 | | |
10 | 10 | | |
11 | 11 | | |
| 12 | + | |
| 13 | + | |
| 14 | + | |
| 15 | + | |
| 16 | + | |
| 17 | + | |
| 18 | + | |
| 19 | + | |
| 20 | + | |
| 21 | + | |
| 22 | + | |
12 | 23 | | |
13 | 24 | | |
14 | 25 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
6 | 6 | | |
7 | 7 | | |
8 | 8 | | |
| 9 | + | |
9 | 10 | | |
10 | 11 | | |
11 | 12 | | |
| |||
135 | 136 | | |
136 | 137 | | |
137 | 138 | | |
| 139 | + | |
| 140 | + | |
| 141 | + | |
| 142 | + | |
| 143 | + | |
| 144 | + | |
| 145 | + | |
| 146 | + | |
| 147 | + | |
| 148 | + | |
| 149 | + | |
| 150 | + | |
| 151 | + | |
| 152 | + | |
| 153 | + | |
| 154 | + | |
| 155 | + | |
| 156 | + | |
| 157 | + | |
| 158 | + | |
| 159 | + | |
| 160 | + | |
| 161 | + | |
| 162 | + | |
| 163 | + | |
| 164 | + | |
| 165 | + | |
| 166 | + | |
| 167 | + | |
| 168 | + | |
| 169 | + | |
| 170 | + | |
| 171 | + | |
| 172 | + | |
| 173 | + | |
| 174 | + | |
| 175 | + | |
| 176 | + | |
| 177 | + | |
| 178 | + | |
| 179 | + | |
| 180 | + | |
| 181 | + | |
| 182 | + | |
| 183 | + | |
| 184 | + | |
| 185 | + | |
| 186 | + | |
| 187 | + | |
| 188 | + | |
| 189 | + | |
138 | 190 | | |
139 | 191 | | |
140 | 192 | | |
| |||
0 commit comments