Repository navigation
klavi-experts 0.2.0: ready for Experts 1.1 - #2
Merged
Merged
Conversation
added 3 commits
October 30, 2026 09:52
klavi.ai is another company's domain: reports sent to security@klavi.ai or conduct@klavi.ai would have gone to them. security@klv.ai is the contact security.txt already publishes. Docs only, no release.
pytest-asyncio 0.24+ warns when asyncio_default_fixture_loop_scope is unset, and filterwarnings = error turned that warning into an INTERNALERROR before a single test ran, on every Python version. Also moves the workflows to the Node 24 majors of checkout and setup-python. Also carries the version bump to 0.2.0.
Knowledge works. The 0.1 upload sent `file` and `collection_uid` (the
server reads `files` and `collection`: a 422), waited by polling a document
row that never says it is indexed, and searched a conversation-context route
with the wrong body (a 422). Measured against a 1.1 install, and the same at
1.0.49:
- upload() answers with the indexing job (UploadJob), on the non-deprecated
/documents/job-queue-upload.
- wait_for_processing(job) polls the job and returns an UploadStatus: truthy
when every file is searchable, with each file's document uid or error.
- search() is /similarity_search/ and returns SearchHit passages.
- list_documents filters by `collection` and maps doc_name/doc_type/summary.
- New: upload_status(), delete_document(), list_documents(skip, search).
1.1 behaviour:
- LicenseReadOnlyError (a LicenseError, read_only=True) for the 30-day
read-only window's `license_expired_readonly`.
- ExpertNotAvailableError for /chat's 403 expert_not_available, read from
its {"detail": {...}} body; send() settles the placeholder so it does not
type forever.
- guest_visible also requires no org-profile scope (Expert.scope_uids).
- Mesh: a `queued` event while a busy member's model has the request in
line; served_by, mesh_fallback, mesh_unavailable and model on the result.
- data_artifacts and generated_images on the result; split_uid and
start_ms/end_ms on source documents.
Fixes:
- A failed streamed request (a refused chat turn, an upload) crashed with
httpx.ResponseNotRead before reporting the server's error.
- A timeout or dropped connection mid-answer is a StreamError, not httpx's.
- The knowledge service's 401 "insufficient permissions" is a permission
error, not an auth error.
- cancel() returns whether the server stopped anything.
- stream_timeout is a client option (a mesh turn can wait in line).
The vendored spec is regenerated at 1.1.0, with the knowledge routes added.
Live suite (now with an upload, index, search, delete round trip) passes
against 1.1.0-rc.127.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Release PR for 0.2.0. Folds in #1 (security and conduct contacts at klv.ai), which is in this branch, so merging this marks it merged.
CI was failing
pytest -qdied with an INTERNALERROR on every Python version before a test ran: pytest-asyncio 0.24+ warns whenasyncio_default_fixture_loop_scopeis unset, andfilterwarnings = ["error"]made that fatal. Set explicitly. The workflows also move to the Node 24 majors of checkout and setup-python.The
livejob has never actually run: there is noEXPERTS_TEST_KEYsecret, so it skips and reports success.Knowledge never worked
Every call except
list_collectionswas against the wrong field or route, in 0.1 against 1.0.49 as much as against 1.1:uploadfile+collection_uid→ 422files+collectionon/documents/job-queue-upload; returns theUploadJobwait_for_processingUploadStatus(truthy when searchable; per-file uid or error)search/similarity_search/; returnsSearchHitpassageslist_documentscollection_uidignored; names/types emptycollection, anddoc_name/doc_type/summarymappedNew:
upload_status(),delete_document(),list_documents(skip=, search=).1.1 behaviour
LicenseReadOnlyError(subclass ofLicenseError,read_only=True) forlicense_expired_readonly. Before, it came through as a plain permission error./chatnow 403s an expert the caller may not use. Raised asExpertNotAvailableError(its{"detail": {...}}body used to read as "Request failed with status 403").send()settles the placeholder, so the conversation does not show it typing forever.Expert.scope_uids), matching what minting a session refuses.QueuedEventwhile a busy member's model has the request in line;served_by,mesh_fallback,mesh_unavailableandmodelon the result;stream_timeoutclient option.data_artifacts,generated_images;split_uid,start_ms,end_mson source documents.Fixes
httpx.ResponseNotReadinstead of raising the server's error. The unit tests' mocked responses were pre-read, so they never saw it.StreamError, not httpx's own error.cancel()returns whether the server stopped anything.Breaking (0.x minor)
upload()returnsUploadJob, notKnowledgeDocument.wait_for_processing()takes the job and returnsUploadStatus. Its truthiness keepsif wait_for_processing(...):working.search()returnsSearchHits.None of the three worked before.
Spec
spec/openapi.jsonis regenerated at 1.1.0. It adds the knowledge routes the SDK now calls and the 1.1 errors. The generator change is klv-ai/experts-knowledgesdk/openapi-1.1, and that file is byte-identical to this one.Tested
tests/test_knowledge.pyuses payloads copied from a 1.1 install.pytest tests/live: 10 passed against a Proxmox VM on 1.1.0-rc.127 (gateway rc.37, conversations rc.30, embedding rc.23). That includes a new upload → index → search → delete round trip.expert_not_available(the test key is an admin) and mesh events. Those are unit-tested from the services' code.After merge
Tag
v0.2.0on main to publish to PyPI (release.yml checks the tag against both version strings).