Copy handed-over documents into a chosen WebDAV folder, as a store in this package #5
Labels
No labels
bug
documentation
enhancement
performance
security
No milestone
No project
No assignees
1 participant
Notifications
Due date
No due date set.
Dependencies
No dependencies set
Reference
Postulo/postulo-dav#5
Loading…
Reference in a new issue
No description provided.
Delete branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
The list of DAV improvements asks for "the storage component (WebDAV), that for now is not implemented, but will be use for storing documents (on the user side)". This package registers one entry point today,
postulo.syncs(pyproject.toml:30-31). postulo/postulo#241 (item 2) proposed a separatepostulo-webdav-storerepository reusingpostulo_dav.dav; the list makes it a component of this plugin instead: a second entry point,postulo.stores, in this package, which takes up #241's item 2.The core has what a store needs:
StorePlugin.put(document, file, metadata, config, user)returns anExternalReforNone, per person, retried by the scheduler (src/postulo/documents/archiving.pyin the core), for what was handed over and never for a PDF exported on its own (postulo/postulo#236). A switch per document kind comes free.delete()andbrowse()are never called (src/postulo/plugins/base.py:781-793in the core).Reading: "storing documents" means keeping a copy of each in the person's WebDAV folder; the alternative is under Decisions.
What the plugin should do
postulo.stores, with its own name (saywebdav): plugin names are unique across the instance (find_any,src/postulo/plugins/registry.py:314-325in the core). Its own connection (a connection has one plugin and one kind): folder address, user name, password. The address is the folder's full URL, since RFC 6764 defines well-known URIs for CardDAV and CalDAV only; on Nextcloud,/remote.php/dav/files/<user>/<folder>/.validate()keeps the sync'shttps://rule.src/postulo_dav/dav.py), work shared with #6:get()returnsresponse.textandput()encodes astr(dav.py:223-242);MKCOL:create_collectionmakes only address books and calendars (dav.py:180-200);collections()drops (dav.py:162-167) andetags()skips (dav.py:216-218), at Depth 1 (RFC 4918 §9.1 lets a server refuse infinity).DocumentMetadata(kind_label,title,filename,company,role,sent_on,created_at), each part made safe for a path. Missing folders are made one level at a time:MKCOLanswers 409 while a parent is missing (RFC 4918 §9.3.1).PUTwithIf-None-Match: *, as for new cards (dav.py:232). On 412 the file there is read back: the same size and SHA-256 (metadata.checksum) is a retry after a lost reply and counts as sent; anything else gets a suffixed name.ConnectionUnusable, so the connection is switched off with the reason (and its password forgotten, unless kept) instead of failing for every document (postulo/postulo#243).oc:fileid, which is not documented to survive a move.DAV:quota-available-bytes(asked by name, RFC 4331 §3) and writes nothing, as postulo/postulo-dav#2 settled for the sync.src/postulo/documents/forms.py:26in the core) and renders are PDFs: one plainPUTis enough.New strings go through
uv run postulo-messages extract, fr-fr and pt-pt filled on the commit (the test gates them), the 23 EU catalogues before a tag (uv run pytest -m release). The names needed (StorePlugin,DocumentMetadata,ExternalRef,ConnectionUnusable) are on the surface at the pinned 1d6cdd7e0, so no repin;tests/test_surface.pygains them.Decisions
src/postulo/documents/stores.py), a core change not proposed here.<company>/<role>/<date> <filename>, dated bysent_on, elsecreated_at;<kind_label>/without an application) or flat with descriptive names. Recommended: by company by default, flat as a choice. Separate folders per kind already work as two connections.delete()andbrowse(); storing does not, so not filed.Needs from the core
Nothing. A folder picker instead of a typed address comes with #13.
Done when
MKCOLorPUT.From the list of DAV plugin improvements of 2026-09-30.