The first tagged run failed inside the publish step within a second, which is the shape of an auth rejection rather than a build problem. The step now prefers a repository NPM_TOKEN secret when one exists, prints the effective registry and a masked token, and runs npm whoami so a re-run names the cause instead of just failing.
The registry owner is the scope the package must publish under, so the name moves from @local/ to @dsh-plugin/ in all three places that must agree: package.json, cordis.patch.yml, and the client module id. `private` goes away because npm refuses to publish such a package, and publishConfig pins the registry to this organization's npm endpoint.
The tag workflow publishes whatever version the pushed v* tag names, using the built-in Gitea job token, and refuses a tag that disagrees with package.json.