typing: add types to command handlers - #6932
Conversation
|
Thank you for the PR! The changelog has not been updated, so here is a friendly reminder to check if you need to add an entry. |
There was a problem hiding this comment.
Pull request overview
grug see PR try make CLI command handler shape same everywhere: (Library, optparse.Values, list[str]). grug also see small runtime fixes found by typing, like ipfs -> play wiring, plus small API tighten in db sort.
Changes:
- add shared typed command-handler signature across core commands + many plugins
- widen
beets.dbcore.sort.Sort.sortinput fromlisttoIterableto match real call flow - adjust a few plugins/core helpers where typing show runtime mismatch (ipfs/play, update exclude fields, etc.)
Reviewed changes
Copilot reviewed 53 out of 53 changed files in this pull request and generated 4 comments.
Show a summary per file
| File | Description |
|---|---|
| test/plugins/test_ipfs.py | add regression test for ipfs playback wiring |
| beetsplug/zero.py | type command handler params |
| beetsplug/web/init.py | type command handler params; add ignore for wsgi_app assign |
| beetsplug/unimported.py | type command handler params |
| beetsplug/titlecase.py | type command handler params |
| beetsplug/thumbnails.py | type command handler params + lib type import |
| beetsplug/subsonicplaylist.py | type command handler params |
| beetsplug/spotify.py | type command handler params; tighten _match_library_tracks keywords type |
| beetsplug/scrub.py | type command handler params |
| beetsplug/play.py | type _play_command params; add selection annotation |
| beetsplug/parentwork.py | type command handler params |
| beetsplug/mpdstats.py | type command handler params |
| beetsplug/missing.py | type command handler params |
| beetsplug/metasync/init.py | type command handler params |
| beetsplug/mbsync.py | type command handler params |
| beetsplug/mbsubmit.py | type command handler params |
| beetsplug/mbcollection.py | type update_collection handler params |
| beetsplug/lyrics.py | type command handler params |
| beetsplug/listenbrainz.py | type command handler params |
| beetsplug/limit.py | type command handler params; annotate iterable selection |
| beetsplug/lastimport.py | type command handler params |
| beetsplug/keyfinder.py | type command handler params |
| beetsplug/ipfs.py | type handlers; change ipfs_play to call play plugin command |
| beetsplug/info.py | type command handler params; clarify summary annotation |
| beetsplug/ftintitle.py | type command handler params |
| beetsplug/freedesktop.py | type command handler params |
| beetsplug/fish.py | type command handler params |
| beetsplug/fetchart.py | type command handler params |
| beetsplug/export.py | type command handler params |
| beetsplug/edit.py | type command handler params |
| beetsplug/duplicates.py | type command handler params; annotate items selection |
| beetsplug/deezer.py | type command handler params |
| beetsplug/chroma.py | type command handler params; rename loop var to avoid confusion |
| beetsplug/bpsync.py | type command handler params |
| beetsplug/bpm.py | type command handler params |
| beetsplug/bpd/init.py | type command handler params; adjust control_port config get |
| beetsplug/bareasc.py | type command handler params |
| beetsplug/badfiles.py | type command handler params |
| beetsplug/autobpm.py | type command handler params |
| beetsplug/aura.py | type command handler params |
| beetsplug/acousticbrainz.py | type command handler params |
| beetsplug/absubmit.py | type command handler params |
| beets/ui/commands/write.py | type command handler params |
| beets/ui/commands/update.py | type command handler params; safer exclude fields + old item lookup + bytes path print |
| beets/ui/commands/stats.py | type command handler params |
| beets/ui/commands/remove.py | type command handler params |
| beets/ui/commands/move.py | type command handler params |
| beets/ui/commands/modify.py | type command handler params |
| beets/ui/commands/list.py | type command handler params |
| beets/ui/commands/help.py | type command handler params |
| beets/ui/commands/fields.py | type command handler params |
| beets/ui/commands/config.py | type command handler params |
| beets/dbcore/sort.py | accept Iterable for sort inputs; update sort method type shapes |
💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.
Codecov Report❌ Patch coverage is
Additional details and impacted files@@ Coverage Diff @@
## master #6932 +/- ##
==========================================
+ Coverage 75.84% 76.29% +0.44%
==========================================
Files 164 164
Lines 21295 21529 +234
Branches 3333 3332 -1
==========================================
+ Hits 16151 16425 +274
+ Misses 4360 4315 -45
- Partials 784 789 +5
🚀 New features to boost your workflow:
|
9a2d57d to
5ed97bd
Compare
37266f8 to
6a9182c
Compare
5ed97bd to
74d1233
Compare
6a9182c to
c495306
Compare
74d1233 to
7f8f933
Compare
There was a problem hiding this comment.
Pull request overview
Copilot reviewed 55 out of 55 changed files in this pull request and generated 1 comment.
Suppressed comments (2)
beets/dbcore/sort.py:26
- grug read PR text say
beets.dbcore.sortacceptIterablenow. but code change useSequence, still reject many iterables (like iterators / generator / Results) for typing. if goal is accept any iterable, need swapSequence->Iterable(and update overrides in this file same way so signatures match).
def sort(self, items: Sequence[AnyModel]) -> Sequence[AnyModel]:
"""Sort the given sequence of model objects."""
return sorted(items)
test/plugins/test_ipfs.py:99
- grug see test call
ipfs_play(self.lib, None, [])but new typing sayopts: optparse.Values. if mypy check tests, this fail. pass real optparse.Values (can grab from beetsplug.ipfs module) so test match command interface.
7f8f933 to
ba078ad
Compare
8afa61f to
ed37e83
Compare
There was a problem hiding this comment.
Pull request overview
Copilot reviewed 65 out of 65 changed files in this pull request and generated no new comments.
Suppressed comments (1)
beets/ui/init.py:475
- grug see add_album_option now set default=False. this break config mirror trick. many plugin do
self.config.set_args(opts)and havealbumin config (ex duplicates plugin). if user setduplicates: album: yesand runbeet duplicateswith no-a, opts.album False will override config back to False, so config no work (docs say config options mirror CLI). better keep album default None so set_args can skip when user not pass flag, and call sites can usebool(opts.album)when they need strict bool.
album = optparse.Option(
*flags,
action="store_true",
default=False,
help="match albums instead of tracks",
)
11bee48 to
2191fd8
Compare
2191fd8 to
0ebd95c
Compare
| """ | ||
|
|
||
| func: Callable[[library.Library, optparse.Values, list[str]], Any] | ||
| func: Callable[[library.Library, Any, list[str]], Any] |
There was a problem hiding this comment.
optparse.Values was more concise. I guess this is needed now since we use protocols for typing?
There was a problem hiding this comment.
Why was Protocol chosen instead of using optparse.Values as a base class?
There was a problem hiding this comment.
optparse always constructs a plain Values, not instances of our command-specific subclasses. A Protocol lets each handler declare the fields it consumes without incorrectly claiming that the runtime object is an instance of a custom Values subclass.
We also don't need to import optparse this way :)
0ebd95c to
e7b3692
Compare
e7b3692 to
40538b7
Compare
First part of #6924.
Summary
Library, options, andlist[str]interface.Protocoltypes where handlers depend on particular flags, while retainingoptparse.Valuesfor handlers that do not need a narrower shape. This makes the CLI boundary easier for type checkers to follow without coupling handlers to a concrete options container.beets.dbcore.sortfromlisttoSequenceand tighten several item/album collection annotations to match the data actually passed between APIs.beetsplug.ipfsinvokesPlayPlugin._play_commandwith the expected options shape and closes remote libraries after use.beetsplug.bpdreadscontrol_portthrough the config API that matches its actual value type.beets.ui.commands.updatehandles excluded fields, missing prior items, optional flags, and byte paths safely.Tests
Most changes are annotations and interface clarification. The behavioral changes are limited to the mismatches listed above.