fix(extensions): report loader-visible metadata and refresh API version docs#922
Merged
Merged
Conversation
…on docs Closes #918. Addresses #919, with a correction to that issue's premise. ExtensionMeta derived an extension's identity, version, description and permissions solely from a package-level @ExtensionDescriptor. That annotation is optional: four of the seven shipped extensions carry none, so the metadata degraded to the implementation class's simple name with an empty version and an empty permission set, and the three that do carry one stated version = "1.0" while their artifacts are 3.0.0. ExtensionMeta now prefers the JAR manifest - the same source io.btrace.extension.impl.ExtensionMetadata parses when the runtime loads and permission-checks an extension - and consults the annotation only to fill gaps. This is a correctness fix to a public API, not to observable behaviour. The inspection CLI already read the manifest directly for the version and permissions it prints, and uses ExtensionMeta only as an additional permission contributor, so its output is unchanged; verified by inspecting packaged extensions with and without the change and diffing the result. ExtensionMeta's name, version, description and minBTraceVersion accessors currently have no callers at all, which is why the wrong values were never noticed. The permission-list parser is promoted to PermissionSet.parse so the manifest path, the legacy properties path and inspection share one definition instead of restating it. @ExtensionDescriptor keeps its role. The Gradle plugin reads its permissions member and fails the build when the manifest does not cover what the annotation requires, which is a genuine assertion worth keeping; its remaining members are not propagated anywhere. name() and version() gain defaults so extensions can omit what the build does not use, and the three package descriptors drop the version they were misstating. Docs: the extension development guide and the extension tutorial now say which member does work and which do not, and the six remaining BTrace-API-Version examples showing 2.3+ are updated to 3.0+ to match what the plugin emits. Verified: btrace-core, btrace-client, btrace-agent, the three affected extensions and the Gradle plugin test suites, spotlessCheck, and `ext inspect` run against packaged btrace-statsd and btrace-contracts archives. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
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.
What does this change do?
Makes
ExtensionMetareport the metadata the extension loader actually uses, removes a duplicated permission parser, and documents which parts of@ExtensionDescriptordo work.Please read the severity note before reviewing — this is public-API hygiene and documentation, not a user-facing defect. #919 as originally filed overstated the impact and has been corrected.
The metadata fix
ExtensionMetaderived identity, version, description and permissions solely from a package-level@ExtensionDescriptor. That annotation is optional — four of the seven shipped extensions carry none, so metadata degraded to the implementation class's simple name with an empty version and an empty permission set, while the three that carry one stateversion = "1.0"for artifacts that are3.0.0.It now prefers the JAR manifest — the same source
io.btrace.extension.impl.ExtensionMetadataparses when the runtime loads and permission-checks an extension — and consults the annotation only to fill gaps.Severity: no observable behaviour changes
ExtensionInspectoralready read the manifest directly for the version and permissions it prints (readVersionFromJar,readPermissionsFromManifestOrPropson both JARs) and usesExtensionMetaonly as an additional permission contributor.ExtensionReportnever printsExtensionMeta's name or version.Verified rather than assumed: packaged
btrace-statsd(has a descriptor stating1.0) andbtrace-contracts(has none) were inspected with and without this change — output is byte-identical in both cases (Version: 3.0.0-SNAPSHOT,Required: [NETWORK]/[THREADS]).ExtensionMeta.getName(),getVersion(),getDescription()andgetMinBTraceVersion()have no callers in the codebase, which is why the wrong values were never noticed. The fix matters for external callers of this public API and for anyone who wires these accessors up in future.Shared permission parsing
The permission-list parser existed twice, in different packages. It is promoted to
PermissionSet.parse(String); the manifest path, the legacy properties path and inspection now share one definition.@ExtensionDescriptorkeeps its real jobThe Gradle plugin reads its
permissionsmember and fails the build when the manifest does not cover what the annotation requires (BTraceExtensionPlugin.groovy: "Manifest permissions missing annotated requirements"). That is a genuine assertion and is untouched. Its remaining members are propagated nowhere, soname()andversion()gain defaults and the three package descriptors drop the version they were misstating.There was never a three-way conflict over authority: the manifest is authoritative, the annotation is a build-time permission assertion, and the third "format" was dead metadata.
Docs
BTraceExtensionDevelopmentGuide.mdandtutorials/06-write-your-own-extension.mdnow state which annotation member does work and which do not. The six remainingBTrace-API-Version: 2.3+examples acrossExtensionManifestFormat.mdandExtensionStorageDesign.mdare updated to3.0+, matching what the plugin emits (#918).Related issue
Closes #918
Addresses #919
Scope and compatibility
Compatibility or migration notes:
@ExtensionDescriptor.name()andversion()gain defaults, which is source- and binary-compatible; existing extensions that set them continue to compile.ExtensionMeta.from(Class)is retained and unchanged in signature, delegating to the newfrom(Class, Attributes)overload. No CLI, probe, protocol or packaging change.Testing
Plus
ext inspectrun against packagedbtrace-statsdandbtrace-contractsarchives, before and after, to confirm the output is unchanged.New tests:
ExtensionMetaTest(manifest precedence, id-as-name fallback, permissions for extensions with no package descriptor, blank-value handling, overload equivalence) andPermissionSetParseTest(separators, blank and null input, unknown names skipped rather than failing the list).Notes for reviewers
ext inspectreportsServices: org.slf4j.spi.SLF4JServiceProvider,javax.annotation.processing.Processorfor both extensions, which looks like unrelatedMETA-INF/servicesentries leaking into the report. Worth a separate issue if that is not intended.🤖 Generated with Claude Code
This change is