Skip to content

Expose declared runtime and toolchain constraints in ParseResult #104

Description

@andrew

On v0.12.2 and current main, the runtime a package declares it needs is dropped by every parser that reads one. Using Go 1.27.1:

r, _ := manifests.Parse("package.json", []byte(`{"name":"app","version":"1.0.0","engines":{"node":">=20"},"packageManager":"pnpm@9.1.0","dependencies":{"lodash":"^4.17.21"}}`))
fmt.Printf("%+v\n", r)
// &{Ecosystem:npm Kind:manifest Name:app Version:1.0.0 Licenses:[] LicenseFile: Digest: Dependencies:[{Name:lodash ...}] Declarations:[{Name:lodash ...}] Sources:[]}

The same holds for go and toolchain in go.mod, requires-python in pyproject.toml, and rust-version and edition in Cargo.toml. Parsing succeeds in each case and the constraint has nowhere to go.

ParseResult keeps identity, licences, scripts and sources, so a caller can tell what a package is and what it runs on install, but not whether it can run on the interpreter in hand. The packageJSON struct has no field for engines, and the Cargo manifest struct has none for rust-version. Recovering these means parsing the same file a second time.

Please add an additive field for declared constraints, along the lines of:

type Requirement struct {
    Kind       string // runtime, toolchain, package-manager
    Name       string // node, python, go, rust, pnpm
    Constraint string // verbatim, as written in the manifest
}

Initial coverage could be package.json engines and packageManager, go.mod go and toolchain, pyproject.toml requires-python with setup.cfg python_requires, Cargo.toml rust-version and edition, and *.gemspec required_ruby_version.

Values should stay verbatim, matching the rule already documented for Licenses, with no normalisation, range parsing or validation, and absent distinguished from explicitly empty. Ecosystems that express the same constraint as an ordinary dependency, such as a Composer require entry for php, should keep their current behaviour rather than being moved into this field.

The asdf parser's .tool-versions output is a different thing and should stay as it is: those pins say which toolchain a working copy selects, not which one a package declares it needs.

Public Parse tests should cover the new field across those ecosystems while retaining existing identity, dependency, licence and script results.

Related to #101, which adds descriptive fields to the same struct.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions