Skip to content

Conversation

@RossComputerGuy
Copy link
Member

@RossComputerGuy RossComputerGuy commented Feb 10, 2026

Motivation

Adds a subset of meta into the provenance when the provenance experimental feature is used. So far, just record identifiers, license, and licenses. We may want to expand this further but for now, this will allow us to judge how it affects the narinfo size.

Context

Summary by CodeRabbit

  • New Features

    • Provenance now includes explicit derivation metadata (including license and position) and nests provenance entries.
  • Behavior

    • Provenance-aware builds set language version to 7 and conditionally inject derivation meta to preserve older compatibility.
    • Provenance display now shows “← with derivation metadata” and prints derivation meta (licenses, identifiers).
  • Tests

    • Functional tests updated to expect meta-enriched provenance.
  • Documentation

    • Provenance docs updated to describe the new "Meta" provenance item.

@coderabbitai
Copy link

coderabbitai bot commented Feb 10, 2026

Note

Reviews paused

It looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the reviews.auto_review.auto_pause_after_reviewed_commits setting.

Use the following commands to manage reviews:

  • @coderabbitai resume to resume automatic reviews.
  • @coderabbitai review to trigger a single review.

Use the checkboxes below for quick actions:

  • ▶️ Resume reviews
  • 🔍 Trigger review
📝 Walkthrough

Walkthrough

Adds a DerivationProvenance type, wires derivation meta JSON into provenance chains during derivation construction, registers/serializes the new provenance type, updates provenance-show rendering to display derivation metadata and licenses, exposes headers/sources in libexpr build, and updates tests/configs to expect meta-wrapped provenance.

Changes

Cohort / File(s) Summary
Build config
src/libexpr/include/nix/expr/meson.build, src/libexpr/meson.build
Expose provenance.hh in public headers and add provenance.cc to libexpr sources.
Provenance types & serialization
src/libexpr/include/nix/expr/provenance.hh, src/libexpr/provenance.cc
Add DerivationProvenance (stores next and meta), implement to_json() and register "derivation" provenance deserializer/constructor.
Derivation integration (primops)
src/libexpr/primops.cc, src/libexpr/include/nix/expr/eval.hh
Convert __meta to JSON, prune identifier/license fields, wrap existing provenance with DerivationProvenance(meta), pass provenance into writeDerivation, and adjust language version gating; add __meta, identifiers, license, licenses symbols.
Provenance display & docs
src/nix/provenance.cc, src/nix/provenance-show.md
Display derivation metadata and licenses during provenance traversal ("← with derivation metadata"), render CPE/license info, and document the new provenance meta item.
Tests / configs
tests/functional/config.nix.in, tests/functional/flakes/provenance.sh, tests/functional/simple.nix
Conditionally inject __meta based on langVersion, update expected provenance JSON to include nested meta blocks and license metadata, and add license metadata to test fixtures.

Sequence Diagram

sequenceDiagram
    participant EvalState as EvalState
    participant PrimOps as PrimOps
    participant JSON as JSONSerializer
    participant Provenance as Provenance

    EvalState->>PrimOps: derivationStrict(state, args, state.provenance)
    PrimOps->>PrimOps: detect meta in args / langVersion check
    PrimOps->>JSON: printValueAsJSON(meta)
    JSON-->>PrimOps: json_meta
    PrimOps->>PrimOps: prune identifiers/licenses from json_meta
    PrimOps->>Provenance: create DerivationProvenance(next=state.provenance, meta=json_meta)
    Provenance-->>PrimOps: wrapped provenance
    PrimOps->>PrimOps: call writeDerivation(..., provenance=wrapped)
    PrimOps->>Provenance: provenance->to_json() for storage/display
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~45 minutes

Possibly related PRs

Suggested labels

flake-regression-test

Suggested reviewers

  • cole-h
  • edolstra

Poem

🐰 I found a meta nibble, wrapped it neat,
A license tucked where next-pointers meet,
The derivation hops with JSON bright,
Lang seven listens to the rabbit's bite,
Now provenance remembers every treat.

🚥 Pre-merge checks | ✅ 2 | ❌ 1
❌ Failed checks (1 warning)
Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (2 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title accurately reflects the main change: adding provenance recording of a subset of package meta (identifiers, license, licenses), which is demonstrated across new provenance struct, implementation, tests, and integration points.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch RossComputerGuy/simple-meta-provenance

No actionable comments were generated in the recent review. 🎉

🧹 Recent nitpick comments
src/libexpr/primops.cc (2)

1577-1599: Inner loop variable i shadows the outer loop variable i.

Line 1583's auto & i shadows the outer auto & i from Line 1510. While functionally correct (the inner loop doesn't need the outer i), this is a maintainability hazard — a future edit inside this block could silently reference the wrong iterator.

♻️ Rename inner loop variable to avoid shadowing
-                    for (auto & i : meta->lexicographicOrder(state.symbols)) {
-                        auto key = state.symbols[i->name];
-                        switch (i->name.getId()) {
+                    for (auto & metaAttr : meta->lexicographicOrder(state.symbols)) {
+                        auto key = state.symbols[metaAttr->name];
+                        switch (metaAttr->name.getId()) {
                         case EvalState::s.identifiers.getId():
                         case EvalState::s.license.getId():
                         case EvalState::s.licenses.getId():
-                            obj.emplace(key, printValueAsJSON(state, true, *i->value, pos, context));
+                            obj.emplace(key, printValueAsJSON(state, true, *metaAttr->value, pos, context));
                             break;
                         default:
                             continue;

5448-5455: Language version tied to an experimental feature flag is unconventional.

Making __langVersion depend on whether Xp::Provenance is enabled means the same Nix binary can report different language versions depending on configuration. This could confuse tooling that expects langVersion to be a stable property of a given Nix release.

Consider whether a separate mechanism (e.g., a provenance-specific builtin or attribute on builtins) would be a less surprising way for Nixpkgs to detect __meta support, reserving langVersion bumps for actual language-level changes that ship unconditionally.


Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
tests/functional/flakes/provenance.sh (1)

107-137: ⚠️ Potential issue | 🔴 Critical

Copied provenance is missing the meta layer — test will likely fail.

The first test (lines 19–61) asserts that build provenance now follows the chain build → meta → flake → subpath → tree. However, this "copied" provenance test still expects the old chain copied → build → flake → subpath → tree without the meta node. Since nix copy wraps the original provenance with a "copied" envelope, the inner structure should still contain the meta layer.

Suggested fix: insert the meta layer into the copied provenance expectation
 {
   "from": "file://$binaryCache",
   "next": {
     "drv": "$(basename "$drvPath")",
     "next": {
-      "flakeOutput": "packages.$system.default",
+      "meta": {
+        "license": [
+          {
+            "deprecated": true,
+            "free": true,
+            "fullName": "GNU Lesser General Public License v2.1",
+            "redistributable": true,
+            "shortName": "lgpl21",
+            "spdxId": "LGPL-2.1",
+            "url": "https://spdx.org/licenses/LGPL-2.1.html"
+          }
+        ]
+      },
       "next": {
-        "next": {
-          "attrs": {
-            "lastModified": $lastModified,
-            "ref": "refs/heads/master",
-            "rev": "$rev",
-            "revCount": 1,
-            "type": "git",
-            "url": "file://$flake1Dir"
+        "flakeOutput": "packages.$system.default",
+        "next": {
+          "next": {
+            "attrs": {
+              "lastModified": $lastModified,
+              "ref": "refs/heads/master",
+              "rev": "$rev",
+              "revCount": 1,
+              "type": "git",
+              "url": "file://$flake1Dir"
+            },
+            "type": "tree"
           },
-          "type": "tree"
+          "subpath": "/flake.nix",
+          "type": "subpath"
         },
-        "subpath": "/flake.nix",
-        "type": "subpath"
+        "type": "flake"
       },
-      "type": "flake"
+      "type": "meta"
     },
     "output": "out",
     "type": "build"
   },
   "type": "copied"
 }
🤖 Fix all issues with AI agents
In `@src/libexpr/primops.cc`:
- Around line 1577-1594: The new EvalState::s.meta.getId() branch
unconditionally requires experimentalFeatureSettings.require(Xp::Provenance) and
assumes printValueAsJSON returns an object, breaking existing derivations and
causing uncaught exceptions for non-object meta values; change the logic so you
only enforce Provenance and construct MetaProvenance when the feature is
enabled, otherwise fall through to the default handling (so old behavior
remains), and before iterating call printValueAsJSON and verify the returned
nlohmann::json is an object (e.g., is_object()); if it's not an object, either
forward to the default case or raise a clear Nix evaluation error instead of
calling it.key(), then only create MetaProvenance and assign provenance when the
JSON check passes (using symbols: EvalState::s.meta.getId(),
experimentalFeatureSettings.require, printValueAsJSON, MetaProvenance,
provenance).
🧹 Nitpick comments (1)
src/libexpr/primops.cc (1)

5443-5450: Bumping __langVersion based on an experimental feature conflates language version with feature flags.

__langVersion traditionally reflects language syntax/semantics evolution. Tying it to whether Xp::Provenance is enabled means the same Nix binary reports different language versions depending on runtime config, which may confuse downstream consumers that use langVersion for feature detection of non-provenance language features. Consider whether a separate builtins.provenance or builtins ? provenanceMeta check would be a cleaner detection mechanism for Nixpkgs.

Comment on lines 1577 to 1594
case EvalState::s.meta.getId():
experimentalFeatureSettings.require(Xp::Provenance);

{
auto meta = printValueAsJSON(state, true, *i->value, pos, context);

for (auto it = meta.begin(); it != meta.end();) {
if (it.key() == "identifiers" || it.key() == "license" || it.key() == "licenses") {
it++;
continue;
}

it = meta.erase(it);
}

provenance = std::make_shared<const MetaProvenance>(provenance, make_ref<nlohmann::json>(meta));
}
break;
Copy link

@coderabbitai coderabbitai bot Feb 10, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
# Check for EvalState::s.meta symbol definitions and usage patterns
echo "=== Searching for Symbol meta definitions in EvalState ==="
rg -n 'Symbol.*meta' --type cpp | head -20

echo ""
echo "=== Searching for s.meta usage patterns ==="
rg -n '\bs\.meta\b' --type cpp -C2 | head -50

echo ""
echo "=== Check derivation function for meta attribute handling ==="
rg -n 'meta.*getId\(\)|s\.meta' --type cpp -B3 -A3 | head -40

echo ""
echo "=== Look for pre-existing meta case in switch statements ==="
rg -n 'case.*meta\b|s\.meta.*case' --type cpp -C1 | head -30

echo ""
echo "=== Search for EvalState symbol initialization ==="
rg -n 'EvalState::s\.' src/libexpr/ --type cpp | grep -E '(Symbol|meta)' | head -20

Repository: DeterminateSystems/nix-src

Length of output: 6844


🏁 Script executed:

#!/bin/bash
# Check the derivation function context around line 1577
echo "=== Context around line 1577 in primops.cc ==="
sed -n '1500,1600p' src/libexpr/primops.cc | head -120

echo ""
echo "=== Find the function that contains this switch statement ==="
rg -n 'static.*void.*derivation|derivationInternal\|derivation_impl' src/libexpr/primops.cc -A5 | head -20

echo ""
echo "=== Check what happens with meta before line 1577 (before this new case) ==="
sed -n '1540,1577p' src/libexpr/primops.cc

Repository: DeterminateSystems/nix-src

Length of output: 7275


🏁 Script executed:

#!/bin/bash
# Get the complete switch statement and default case
echo "=== Complete switch statement from line 1558 onwards ==="
sed -n '1558,1750p' src/libexpr/primops.cc

echo ""
echo "=== Check the default case handling ==="
sed -n '1700,1750p' src/libexpr/primops.cc

Repository: DeterminateSystems/nix-src

Length of output: 11637


🏁 Script executed:

#!/bin/bash
# Check test configuration and meta usage in tests
echo "=== Check config.nix.in for meta handling ==="
if [ -f tests/lang/config.nix.in ]; then
  cat tests/lang/config.nix.in | head -50
fi

echo ""
echo "=== Search for test files with meta attributes ==="
rg -l 'meta\s*=' tests/lang/ --type nix | head -10

echo ""
echo "=== Check simple.nix mentioned in review ==="
if [ -f tests/lang/simple.nix ]; then
  head -40 tests/lang/simple.nix
fi

echo ""
echo "=== Check for Provenance feature guard conditions ==="
rg -n 'Xp::Provenance|require.*Provenance' src/libexpr/ --type cpp -B2 -A2 | head -30

Repository: DeterminateSystems/nix-src

Length of output: 1070


🏁 Script executed:

#!/bin/bash
# Check printValueAsJSON return type and JSON handling
echo "=== Search for printValueAsJSON function signature ==="
rg -n 'nlohmann::json.*printValueAsJSON' src/libexpr/ --type cpp -B2 -A5 | head -40

echo ""
echo "=== Check how printValueAsJSON handles different value types ==="
rg -n 'printValueAsJSON' src/libexpr/primops.cc -B2 -A10 | grep -A10 'case.*meta'

echo ""
echo "=== Verify if JSON is guaranteed to be object for meta ==="
rg -n 'printValueAsJSON.*meta' src/libexpr/ --type cpp -C5

echo ""
echo "=== Check if there's type checking before it.key() ==="
sed -n '1580,1595p' src/libexpr/primops.cc

Repository: DeterminateSystems/nix-src

Length of output: 1605


🏁 Script executed:

#!/bin/bash
# Check printValueAsJSON implementation for different value types
echo "=== Check printValueAsJSON implementation ==="
rg -n 'nlohmann::json printValueAsJSON' src/libexpr/value-to-json.cc -A30 | head -50

echo ""
echo "=== Check if JSON type is validated before iteration ==="
rg -n 'is_object\|is_array\|type\(\)' src/libexpr/value-to-json.cc | head -20

echo ""
echo "=== Look for any tests of meta as non-attrset ==="
rg -n 'meta.*string\|meta.*int\|meta.*list' . --type nix | head -10

echo ""
echo "=== Check nlohmann::json begin() behavior on non-objects ==="
python3 << 'EOF'
# Check nlohmann::json documentation/behavior
print("nlohmann::json iterator behavior:")
print("- For objects: iterator over key-value pairs")
print("- For non-objects (arrays, strings, numbers): begin() returns begin iterator")
print("- Calling .key() on non-object iterator is undefined behavior/exception")
print("")
print("The code at lines 1582-1590 does:")
print("  for (auto it = meta.begin(); it != meta.end();)")
print("      if (it.key() == ...)")
print("")
print("This assumes meta is always an object (JSON object type).")
print("If meta = 'foo' (string), printValueAsJSON returns JSON string,")
print("and calling it.key() would cause issues.")
EOF

Repository: DeterminateSystems/nix-src

Length of output: 790


Intercepting meta unconditionally breaks existing derivations and lacks type safety.

This new case EvalState::s.meta.getId(): in the derivation builder (line 1577) intercepts all derivation calls containing a meta attribute. Before this change, meta was silently passed through to the derivation environment (via the default case). Now it unconditionally requires experimentalFeatureSettings.require(Xp::Provenance), which means:

  1. Any derivation with a meta attribute will fail if the Provenance feature is not enabled. This is a breaking change for existing code, including any tests or external derivations that include meta.

  2. The code assumes meta is always a JSON object and iterates with it.key() without type checking. If a user passes a non-attrset meta (e.g., meta = "foo"; or meta = [1 2];), printValueAsJSON will return a non-object JSON, causing it.key() to throw an unhelpful exception rather than a clear Nix evaluation error.

🤖 Prompt for AI Agents
In `@src/libexpr/primops.cc` around lines 1577 - 1594, The new
EvalState::s.meta.getId() branch unconditionally requires
experimentalFeatureSettings.require(Xp::Provenance) and assumes printValueAsJSON
returns an object, breaking existing derivations and causing uncaught exceptions
for non-object meta values; change the logic so you only enforce Provenance and
construct MetaProvenance when the feature is enabled, otherwise fall through to
the default handling (so old behavior remains), and before iterating call
printValueAsJSON and verify the returned nlohmann::json is an object (e.g.,
is_object()); if it's not an object, either forward to the default case or raise
a clear Nix evaluation error instead of calling it.key(), then only create
MetaProvenance and assign provenance when the JSON check passes (using symbols:
EvalState::s.meta.getId(), experimentalFeatureSettings.require,
printValueAsJSON, MetaProvenance, provenance).

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

  1. meta should be able to be deserialized into a JSON object 99% of the time, if it doesn't then there's a problem
  2. meta has never been passed into a derivation due to structured attrs not being enabled by default
  3. The cool thing with this PR is it only affects how meta is passed into the derivation serialization, nix expressions still see the full meta.

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@RossComputerGuy Thank you for the clarifications! Those are important points that address my concerns:

  1. Not a breaking change: Your point about meta never being passed into derivations before (due to the structured attrs and config.nix removal logic) resolves my main concern about breaking existing code. If it wasn't serialized into derivations previously, then requiring the Provenance feature here is indeed a net-new behavior, not a breaking change.

  2. JSON object assumption: I understand that meta should be an attrset in practice. Given that this is new functionality gated behind an experimental feature, the assumption is reasonable for the target use case.

  3. Serialization-only impact: The fact that Nix expressions still see the full meta and only the internal derivation serialization is affected makes the scope much clearer.

Given this context, my initial characterization was too strong. That said, as a best practice for robustness, you might consider adding a type check before the iteration (e.g., if (!meta.is_object()) throw EvalError(...)) to provide a clearer error message in that 1% edge case where someone might pass a non-attrset meta. But this is a "nice-to-have" rather than critical, especially since it's behind an experimental feature flag.

Thank you for taking the time to explain the background!


🧠 Learnings used
Learnt from: edolstra
Repo: DeterminateSystems/nix-src PR: 321
File: src/libstore/build/derivation-building-goal.cc:443-447
Timestamp: 2026-01-23T12:00:50.308Z
Learning: In the Nix build system, for the `AlreadyValid` case in derivation building (when outputs already exist and are valid), provenance of the current derivation should NOT be returned because the existing outputs may have been built with different provenance than the current derivation, making it misleading to associate them.

@RossComputerGuy RossComputerGuy force-pushed the RossComputerGuy/simple-meta-provenance branch 3 times, most recently from e2a917c to ee14c7c Compare February 10, 2026 20:28
Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Fix all issues with AI agents
In `@src/libexpr/primops.cc`:
- Around line 1577-1594: The meta branch calls printValueAsJSON which appends
string contexts into the shared context but then breaks, so the meta JSON never
gets added to the derivation (drv) and its string contexts become phantom
inputs; after creating provenance (MetaProvenance) in the EvalState::s.meta
case, explicitly add the filtered meta JSON into the derivation the same way the
default handler does (e.g., push the meta into drv.structuredAttrs and/or set
the appropriate drv.env entries) or invoke the common handling path for
structured values so that meta itself is recorded in drv and its string contexts
are correctly tied to actual drv inputs; reference symbols: EvalState::s.meta,
printValueAsJSON, MetaProvenance, provenance, drv.structuredAttrs, drv.env, and
context when making this change.

In `@tests/functional/flakes/provenance.sh`:
- Around line 167-189: Update the stale comment that currently states "--impure
does not add provenance" to reflect the new behavior: --impure no longer adds
full build/flake provenance but still records a meta provenance node (look for
the assertion expecting a JSON with "type": "meta" and "next": null). Also
normalize the heredoc to match the rest of the file by changing the occurrence
of "<< EOF" to "<<EOF" so the test style is consistent. Ensure the updated
comment and the heredoc token are edited in the test block surrounding the
--impure check and the JSON assertion.
🧹 Nitpick comments (2)
src/nix/provenance.cc (1)

95-97: Consider displaying a summary of the metadata content.

The current output "← with metadata" is opaque — users have no indication of what metadata is attached. Other provenance types display key details (e.g., the derivation path for BuildProvenance, the URL for FlakeProvenance). You could show which metadata fields are present (e.g., "← with metadata (license, identifiers)") to make nix provenance show more informative.

That said, if the intent is to keep it minimal for now and iterate later, this is fine.

src/libexpr/primops.cc (1)

5443-5450: Coupling __langVersion to an experimental feature flag is unconventional — consider the stabilization path.

__langVersion is typically a monotonically increasing constant that reflects language-level changes available to all users. Tying it to Xp::Provenance means that the same Nix binary reports different language versions depending on configuration, which could confuse tools or caches that key on __langVersion.

When Provenance is stabilized (or if it's removed), this branching needs to be reconciled — either version 7 becomes the permanent value, or a different signaling mechanism is used. The current approach works as a short-term experiment, but consider documenting this caveat or using a different mechanism (e.g., a builtins.provenanceEnabled flag) if this persists beyond the experimental phase.

@github-actions
Copy link

github-actions bot commented Feb 10, 2026

@github-actions github-actions bot temporarily deployed to pull request February 10, 2026 20:34 Inactive
@github-actions github-actions bot temporarily deployed to pull request February 10, 2026 20:53 Inactive
* Provenance indicating that this store path was instantiated by the `derivation` builtin function. Its main purpose is
* to record `meta` fields.
*/
struct MetaProvenance : Provenance
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Let's call this DerivationProvenance. MetaProvenance is pretty vague.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done

experimentalFeatureSettings.require(Xp::ImpureDerivations);
}
break;
case EvalState::s.meta.getId():
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Let's rename this to __meta, similar to __structuredAttrs, to denote that it's a special attribute.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hmm, that seems to break things. __meta isn't being removed from the serialization so it ends up wanting __structuredAttrs.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok, the provenance is just not showing up.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I forgot to allocate the symbol.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done

}
break;
case EvalState::s.meta.getId():
experimentalFeatureSettings.require(Xp::Provenance);
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe this should just ignore the meta attribute if provenance is disabled.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done

experimentalFeatureSettings.require(Xp::Provenance);

{
auto meta = printValueAsJSON(state, true, *i->value, pos, context);
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's a bit inefficient to serialize attributes that we're not interested in, so for performance it's better to iterate over the meta attrset and only serialize the attrs that we care about.

We should measure what the performance impact is on something like nix flake show nixpkgs --legacy.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm not entirely sure how the evaluator works from the C++ API. I know from the C API though how to use it. Could use a bit of guidance on how to iterate through the attr set.

logger->cout("← from file " ANSI_BOLD "%s" ANSI_NORMAL, subpath->subpath.abs());
provenance = subpath->next;
} else if (auto meta = std::dynamic_pointer_cast<const MetaProvenance>(provenance)) {
logger->cout("← with metadata");
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This should print the meta attributes.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I assume pretty print it and not just shove the JSON to the logger.

Example:

/nix/store/j1zlwj1j8q3awm8jl9friy3xih7njzwf-aaa.drv
← with derivation metadata
  license: lgpl3Only

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

/nix/store/nvmynjjgaln144r8vy2y0m5km2fj8m3i-bash-interactive-5.3p9.drv
← with derivation metadata
    CPE: cpe:2.3:a:gnu:bash:5.3:9:*:*:*:*:*:*
    License: gpl3Plus
/nix/store/lfqpgrr022iyxrs952i7376i2nw4nnw1-llvm-21.1.8.drv
← with derivation metadata
    CPE: cpe:2.3:a:llvm:*:*:*:*:*:*:*:*:*
    Licenses:
        - ncsa
        - asl20
        - llvm-exception

Done

@RossComputerGuy RossComputerGuy force-pushed the RossComputerGuy/simple-meta-provenance branch from 02837c0 to bccd6a4 Compare February 11, 2026 20:58
@github-actions github-actions bot temporarily deployed to pull request February 11, 2026 21:05 Inactive
@github-actions github-actions bot temporarily deployed to pull request February 11, 2026 21:25 Inactive
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants