diff --git a/pkg/assembler/backends/inmem/path_test.go b/pkg/assembler/backends/inmem/path_test.go index bbdf23bcf39..7acc5bfac52 100644 --- a/pkg/assembler/backends/inmem/path_test.go +++ b/pkg/assembler/backends/inmem/path_test.go @@ -335,9 +335,24 @@ func Test_Nodes(t *testing.T) { }}, }, { name: "hasSBOM", - inPkg: []*model.PkgInputSpec{testdata.P1}, + inPkg: []*model.PkgInputSpec{testdata.P1, testdata.P2}, + inArt: []*model.ArtifactInputSpec{testdata.A1}, + isDepCall: &isDepCall{ + P1: testdata.P1, + P2: testdata.P2, + MF: mAll, + ID: &model.IsDependencyInputSpec{}, + }, + isOcurCall: &isOcurCall{ + PkgSrc: model.PackageOrSourceInput{ + Package: testdata.P1, + }, + Artifact: testdata.A1, + Occurrence: &model.IsOccurrenceInputSpec{ + Justification: "test justification", + }, + }, hasSBOMCall: &hasSBOMCall{ - Sub: model.PackageOrArtifactInput{ Package: testdata.P1, }, @@ -346,10 +361,14 @@ func Test_Nodes(t *testing.T) { }, }, want: []model.Node{&model.HasSbom{ - Subject: testdata.P1out, - DownloadLocation: "location two", + Subject: testdata.P1out, + DownloadLocation: "location two", + IncludedSoftware: []model.PackageOrArtifact{model.Package{ID: "4"}, model.Package{ID: "5"}, model.Artifact{ID: "6"}}, + IncludedDependencies: []*model.IsDependency{{ID: "7"}}, + IncludedOccurrences: []*model.IsOccurrence{{ID: "8"}}, }}, }, { + name: "hasSLSA", inArt: []*model.ArtifactInputSpec{testdata.A1, testdata.A2}, inBld: []*model.BuilderInputSpec{testdata.B1, testdata.B2}, @@ -501,9 +520,12 @@ func Test_Nodes(t *testing.T) { t.Fatalf("Could not instantiate testing backend: %v", err) } var nodeID string + includes := model.HasSBOMIncludesInputSpec{} for _, p := range tt.inPkg { - if _, err := b.IngestPackage(ctx, *p); err != nil { + if pkg, err := b.IngestPackage(ctx, *p); err != nil { t.Fatalf("Could not ingest package: %v", err) + } else { + includes.Software = append(includes.Software, pkg.Namespaces[0].Names[0].Versions[0].ID) } } for _, s := range tt.inSrc { @@ -512,8 +534,10 @@ func Test_Nodes(t *testing.T) { } } for _, a := range tt.inArt { - if _, err := b.IngestArtifact(ctx, a); err != nil { + if art, err := b.IngestArtifact(ctx, a); err != nil { t.Fatalf("Could not ingest artifact: %v", err) + } else { + includes.Software = append(includes.Software, art.ID) } } for _, bld := range tt.inBld { @@ -538,6 +562,7 @@ func Test_Nodes(t *testing.T) { return } nodeID = ingestedPkg.Namespaces[0].Names[0].Versions[0].ID + includes.Software = append(includes.Software, nodeID) } if tt.artifactInput != nil { ingestedArt, err := b.IngestArtifact(ctx, tt.artifactInput) @@ -658,16 +683,6 @@ func Test_Nodes(t *testing.T) { } nodeID = found.ID } - if tt.hasSBOMCall != nil { - found, err := b.IngestHasSbom(ctx, tt.hasSBOMCall.Sub, *tt.hasSBOMCall.HS) - if (err != nil) != tt.wantErr { - t.Fatalf("did not get expected ingest error, want: %v, got: %v", tt.wantErr, err) - } - if err != nil { - return - } - nodeID = found.ID - } if tt.hasSlsaCall != nil { found, err := b.IngestSLSA(ctx, *tt.hasSlsaCall.Sub, tt.hasSlsaCall.BF, *tt.hasSlsaCall.BB, *tt.hasSlsaCall.SLSA) if (err != nil) != tt.wantErr { @@ -697,6 +712,7 @@ func Test_Nodes(t *testing.T) { return } nodeID = found.ID + includes.Dependencies = append(includes.Dependencies, nodeID) } if tt.isOcurCall != nil { found, err := b.IngestOccurrence(ctx, tt.isOcurCall.PkgSrc, *tt.isOcurCall.Artifact, *tt.isOcurCall.Occurrence) @@ -707,6 +723,18 @@ func Test_Nodes(t *testing.T) { return } nodeID = found.ID + includes.Occurrences = append(includes.Occurrences, nodeID) + } + if tt.hasSBOMCall != nil { + // After isDepCall and isOcurCall so they can set up includes. + found, err := b.IngestHasSbom(ctx, tt.hasSBOMCall.Sub, *tt.hasSBOMCall.HS, includes) + if (err != nil) != tt.wantErr { + t.Fatalf("did not get expected ingest error, want: %v, got: %v", tt.wantErr, err) + } + if err != nil { + return + } + nodeID = found.ID } if tt.pkgEqualCall != nil { found, err := b.IngestPkgEqual(ctx, *tt.pkgEqualCall.P1, *tt.pkgEqualCall.P2, *tt.pkgEqualCall.HE) diff --git a/pkg/assembler/clients/generated/operations.go b/pkg/assembler/clients/generated/operations.go index 7b3934cb9c1..e312c321172 100644 --- a/pkg/assembler/clients/generated/operations.go +++ b/pkg/assembler/clients/generated/operations.go @@ -5118,6 +5118,70 @@ func (v *AllPkgEqualPackagesPackage) __premarshalJSON() (*__premarshalAllPkgEqua return &retval, nil } +// AllPkgIDTree includes the GraphQL fields of PackageID requested by the fragment AllPkgIDTree. +// The GraphQL type's documentation follows. +// +// The ID of the package within the package trie +type AllPkgIDTree struct { + Id string `json:"id"` + Namespaces []AllPkgIDTreeNamespacesPackageNamespaceID `json:"namespaces"` +} + +// GetId returns AllPkgIDTree.Id, and is useful for accessing the field via an interface. +func (v *AllPkgIDTree) GetId() string { return v.Id } + +// GetNamespaces returns AllPkgIDTree.Namespaces, and is useful for accessing the field via an interface. +func (v *AllPkgIDTree) GetNamespaces() []AllPkgIDTreeNamespacesPackageNamespaceID { + return v.Namespaces +} + +// AllPkgIDTreeNamespacesPackageNamespaceID includes the requested fields of the GraphQL type PackageNamespaceID. +// The GraphQL type's documentation follows. +// +// The ID of the package namespace within the package trie +type AllPkgIDTreeNamespacesPackageNamespaceID struct { + Id string `json:"id"` + Names []AllPkgIDTreeNamespacesPackageNamespaceIDNamesPackageNameID `json:"names"` +} + +// GetId returns AllPkgIDTreeNamespacesPackageNamespaceID.Id, and is useful for accessing the field via an interface. +func (v *AllPkgIDTreeNamespacesPackageNamespaceID) GetId() string { return v.Id } + +// GetNames returns AllPkgIDTreeNamespacesPackageNamespaceID.Names, and is useful for accessing the field via an interface. +func (v *AllPkgIDTreeNamespacesPackageNamespaceID) GetNames() []AllPkgIDTreeNamespacesPackageNamespaceIDNamesPackageNameID { + return v.Names +} + +// AllPkgIDTreeNamespacesPackageNamespaceIDNamesPackageNameID includes the requested fields of the GraphQL type PackageNameID. +// The GraphQL type's documentation follows. +// +// The ID of the package name within the package trie +type AllPkgIDTreeNamespacesPackageNamespaceIDNamesPackageNameID struct { + Id string `json:"id"` + Versions []AllPkgIDTreeNamespacesPackageNamespaceIDNamesPackageNameIDVersionsPackageVersionID `json:"versions"` +} + +// GetId returns AllPkgIDTreeNamespacesPackageNamespaceIDNamesPackageNameID.Id, and is useful for accessing the field via an interface. +func (v *AllPkgIDTreeNamespacesPackageNamespaceIDNamesPackageNameID) GetId() string { return v.Id } + +// GetVersions returns AllPkgIDTreeNamespacesPackageNamespaceIDNamesPackageNameID.Versions, and is useful for accessing the field via an interface. +func (v *AllPkgIDTreeNamespacesPackageNamespaceIDNamesPackageNameID) GetVersions() []AllPkgIDTreeNamespacesPackageNamespaceIDNamesPackageNameIDVersionsPackageVersionID { + return v.Versions +} + +// AllPkgIDTreeNamespacesPackageNamespaceIDNamesPackageNameIDVersionsPackageVersionID includes the requested fields of the GraphQL type PackageVersionID. +// The GraphQL type's documentation follows. +// +// The ID of the package version within the package trie +type AllPkgIDTreeNamespacesPackageNamespaceIDNamesPackageNameIDVersionsPackageVersionID struct { + Id string `json:"id"` +} + +// GetId returns AllPkgIDTreeNamespacesPackageNamespaceIDNamesPackageNameIDVersionsPackageVersionID.Id, and is useful for accessing the field via an interface. +func (v *AllPkgIDTreeNamespacesPackageNamespaceIDNamesPackageNameIDVersionsPackageVersionID) GetId() string { + return v.Id +} + // AllPkgTree includes the GraphQL fields of Package requested by the fragment AllPkgTree. // The GraphQL type's documentation follows. // @@ -8029,113 +8093,6 @@ func (v *HashEqualInputSpec) GetOrigin() string { return v.Origin } // GetCollector returns HashEqualInputSpec.Collector, and is useful for accessing the field via an interface. func (v *HashEqualInputSpec) GetCollector() string { return v.Collector } -// IdPkgTree includes the GraphQL fields of Package requested by the fragment IdPkgTree. -// The GraphQL type's documentation follows. -// -// Package represents the root of the package trie/tree. -// -// We map package information to a trie, closely matching the pURL specification -// (https://github.com/package-url/purl-spec/blob/0dd92f26f8bb11956ffdf5e8acfcee71e8560407/README.rst), -// but deviating from it where GUAC heuristics allow for better representation of -// package information. Each path in the trie fully represents a package; we split -// the trie based on the pURL components. -// -// This node matches a pkg: partial pURL. The type field matches the -// pURL types but we might also use "guac" for the cases where the pURL -// representation is not complete or when we have custom rules. -// -// Since this node is at the root of the package trie, it is named Package, not -// PackageType. -type IdPkgTree struct { - Id string `json:"id"` - Namespaces []IdPkgTreeNamespacesPackageNamespace `json:"namespaces"` -} - -// GetId returns IdPkgTree.Id, and is useful for accessing the field via an interface. -func (v *IdPkgTree) GetId() string { return v.Id } - -// GetNamespaces returns IdPkgTree.Namespaces, and is useful for accessing the field via an interface. -func (v *IdPkgTree) GetNamespaces() []IdPkgTreeNamespacesPackageNamespace { return v.Namespaces } - -// IdPkgTreeNamespacesPackageNamespace includes the requested fields of the GraphQL type PackageNamespace. -// The GraphQL type's documentation follows. -// -// PackageNamespace is a namespace for packages. -// -// In the pURL representation, each PackageNamespace matches the -// pkg:// partial pURL. -// -// Namespaces are optional and type specific. Because they are optional, we use -// empty string to denote missing namespaces. -type IdPkgTreeNamespacesPackageNamespace struct { - Id string `json:"id"` - Names []IdPkgTreeNamespacesPackageNamespaceNamesPackageName `json:"names"` -} - -// GetId returns IdPkgTreeNamespacesPackageNamespace.Id, and is useful for accessing the field via an interface. -func (v *IdPkgTreeNamespacesPackageNamespace) GetId() string { return v.Id } - -// GetNames returns IdPkgTreeNamespacesPackageNamespace.Names, and is useful for accessing the field via an interface. -func (v *IdPkgTreeNamespacesPackageNamespace) GetNames() []IdPkgTreeNamespacesPackageNamespaceNamesPackageName { - return v.Names -} - -// IdPkgTreeNamespacesPackageNamespaceNamesPackageName includes the requested fields of the GraphQL type PackageName. -// The GraphQL type's documentation follows. -// -// PackageName is a name for packages. -// -// In the pURL representation, each PackageName matches the -// pkg:// pURL. -// -// Names are always mandatory. -// -// This is the first node in the trie that can be referred to by other parts of -// GUAC. -type IdPkgTreeNamespacesPackageNamespaceNamesPackageName struct { - Id string `json:"id"` - Versions []IdPkgTreeNamespacesPackageNamespaceNamesPackageNameVersionsPackageVersion `json:"versions"` -} - -// GetId returns IdPkgTreeNamespacesPackageNamespaceNamesPackageName.Id, and is useful for accessing the field via an interface. -func (v *IdPkgTreeNamespacesPackageNamespaceNamesPackageName) GetId() string { return v.Id } - -// GetVersions returns IdPkgTreeNamespacesPackageNamespaceNamesPackageName.Versions, and is useful for accessing the field via an interface. -func (v *IdPkgTreeNamespacesPackageNamespaceNamesPackageName) GetVersions() []IdPkgTreeNamespacesPackageNamespaceNamesPackageNameVersionsPackageVersion { - return v.Versions -} - -// IdPkgTreeNamespacesPackageNamespaceNamesPackageNameVersionsPackageVersion includes the requested fields of the GraphQL type PackageVersion. -// The GraphQL type's documentation follows. -// -// PackageVersion is a package version. -// -// In the pURL representation, each PackageName matches the -// pkg://@ pURL. -// -// Versions are optional and each Package type defines own rules for handling -// them. For this level of GUAC, these are just opaque strings. -// -// NOTE: The handling of versions might change before this schema becomes stable. -// -// This node can be referred to by other parts of GUAC. -// -// Subpath and qualifiers are optional. Lack of qualifiers is represented by an -// empty list and lack of subpath by empty string (to be consistent with -// optionality of namespace and version). Two nodes that have different qualifiers -// and/or subpath but the same version mean two different packages in the trie -// (they are different). Two nodes that have same version but qualifiers of one -// are a subset of the qualifier of the other also mean two different packages in -// the trie. -type IdPkgTreeNamespacesPackageNamespaceNamesPackageNameVersionsPackageVersion struct { - Id string `json:"id"` -} - -// GetId returns IdPkgTreeNamespacesPackageNamespaceNamesPackageNameVersionsPackageVersion.Id, and is useful for accessing the field via an interface. -func (v *IdPkgTreeNamespacesPackageNamespaceNamesPackageNameVersionsPackageVersion) GetId() string { - return v.Id -} - // IngestArtifactResponse is returned by IngestArtifact on success. type IngestArtifactResponse struct { // Ingests a new artifact and returns it. The returned ID can be empty string. @@ -8226,46 +8183,33 @@ type IngestLicensesResponse struct { // GetIngestLicenses returns IngestLicensesResponse.IngestLicenses, and is useful for accessing the field via an interface. func (v *IngestLicensesResponse) GetIngestLicenses() []string { return v.IngestLicenses } -// IngestPackageIngestPackage includes the requested fields of the GraphQL type Package. +// IngestPackageIngestPackagePackageID includes the requested fields of the GraphQL type PackageID. // The GraphQL type's documentation follows. // -// Package represents the root of the package trie/tree. -// -// We map package information to a trie, closely matching the pURL specification -// (https://github.com/package-url/purl-spec/blob/0dd92f26f8bb11956ffdf5e8acfcee71e8560407/README.rst), -// but deviating from it where GUAC heuristics allow for better representation of -// package information. Each path in the trie fully represents a package; we split -// the trie based on the pURL components. -// -// This node matches a pkg: partial pURL. The type field matches the -// pURL types but we might also use "guac" for the cases where the pURL -// representation is not complete or when we have custom rules. -// -// Since this node is at the root of the package trie, it is named Package, not -// PackageType. -type IngestPackageIngestPackage struct { - IdPkgTree `json:"-"` +// The ID of the package within the package trie +type IngestPackageIngestPackagePackageID struct { + AllPkgIDTree `json:"-"` } -// GetId returns IngestPackageIngestPackage.Id, and is useful for accessing the field via an interface. -func (v *IngestPackageIngestPackage) GetId() string { return v.IdPkgTree.Id } +// GetId returns IngestPackageIngestPackagePackageID.Id, and is useful for accessing the field via an interface. +func (v *IngestPackageIngestPackagePackageID) GetId() string { return v.AllPkgIDTree.Id } -// GetNamespaces returns IngestPackageIngestPackage.Namespaces, and is useful for accessing the field via an interface. -func (v *IngestPackageIngestPackage) GetNamespaces() []IdPkgTreeNamespacesPackageNamespace { - return v.IdPkgTree.Namespaces +// GetNamespaces returns IngestPackageIngestPackagePackageID.Namespaces, and is useful for accessing the field via an interface. +func (v *IngestPackageIngestPackagePackageID) GetNamespaces() []AllPkgIDTreeNamespacesPackageNamespaceID { + return v.AllPkgIDTree.Namespaces } -func (v *IngestPackageIngestPackage) UnmarshalJSON(b []byte) error { +func (v *IngestPackageIngestPackagePackageID) UnmarshalJSON(b []byte) error { if string(b) == "null" { return nil } var firstPass struct { - *IngestPackageIngestPackage + *IngestPackageIngestPackagePackageID graphql.NoUnmarshalJSON } - firstPass.IngestPackageIngestPackage = v + firstPass.IngestPackageIngestPackagePackageID = v err := json.Unmarshal(b, &firstPass) if err != nil { @@ -8273,20 +8217,20 @@ func (v *IngestPackageIngestPackage) UnmarshalJSON(b []byte) error { } err = json.Unmarshal( - b, &v.IdPkgTree) + b, &v.AllPkgIDTree) if err != nil { return err } return nil } -type __premarshalIngestPackageIngestPackage struct { +type __premarshalIngestPackageIngestPackagePackageID struct { Id string `json:"id"` - Namespaces []IdPkgTreeNamespacesPackageNamespace `json:"namespaces"` + Namespaces []AllPkgIDTreeNamespacesPackageNamespaceID `json:"namespaces"` } -func (v *IngestPackageIngestPackage) MarshalJSON() ([]byte, error) { +func (v *IngestPackageIngestPackagePackageID) MarshalJSON() ([]byte, error) { premarshaled, err := v.__premarshalJSON() if err != nil { return nil, err @@ -8294,63 +8238,52 @@ func (v *IngestPackageIngestPackage) MarshalJSON() ([]byte, error) { return json.Marshal(premarshaled) } -func (v *IngestPackageIngestPackage) __premarshalJSON() (*__premarshalIngestPackageIngestPackage, error) { - var retval __premarshalIngestPackageIngestPackage +func (v *IngestPackageIngestPackagePackageID) __premarshalJSON() (*__premarshalIngestPackageIngestPackagePackageID, error) { + var retval __premarshalIngestPackageIngestPackagePackageID - retval.Id = v.IdPkgTree.Id - retval.Namespaces = v.IdPkgTree.Namespaces + retval.Id = v.AllPkgIDTree.Id + retval.Namespaces = v.AllPkgIDTree.Namespaces return &retval, nil } // IngestPackageResponse is returned by IngestPackage on success. type IngestPackageResponse struct { // Ingests a new package and returns a corresponding package hierarchy containing only the IDs. The returned ID can be empty string. - IngestPackage IngestPackageIngestPackage `json:"ingestPackage"` + IngestPackage IngestPackageIngestPackagePackageID `json:"ingestPackage"` } // GetIngestPackage returns IngestPackageResponse.IngestPackage, and is useful for accessing the field via an interface. -func (v *IngestPackageResponse) GetIngestPackage() IngestPackageIngestPackage { return v.IngestPackage } +func (v *IngestPackageResponse) GetIngestPackage() IngestPackageIngestPackagePackageID { + return v.IngestPackage +} -// IngestPackagesIngestPackagesPackage includes the requested fields of the GraphQL type Package. +// IngestPackagesIngestPackagesPackageID includes the requested fields of the GraphQL type PackageID. // The GraphQL type's documentation follows. // -// Package represents the root of the package trie/tree. -// -// We map package information to a trie, closely matching the pURL specification -// (https://github.com/package-url/purl-spec/blob/0dd92f26f8bb11956ffdf5e8acfcee71e8560407/README.rst), -// but deviating from it where GUAC heuristics allow for better representation of -// package information. Each path in the trie fully represents a package; we split -// the trie based on the pURL components. -// -// This node matches a pkg: partial pURL. The type field matches the -// pURL types but we might also use "guac" for the cases where the pURL -// representation is not complete or when we have custom rules. -// -// Since this node is at the root of the package trie, it is named Package, not -// PackageType. -type IngestPackagesIngestPackagesPackage struct { - IdPkgTree `json:"-"` +// The ID of the package within the package trie +type IngestPackagesIngestPackagesPackageID struct { + AllPkgIDTree `json:"-"` } -// GetId returns IngestPackagesIngestPackagesPackage.Id, and is useful for accessing the field via an interface. -func (v *IngestPackagesIngestPackagesPackage) GetId() string { return v.IdPkgTree.Id } +// GetId returns IngestPackagesIngestPackagesPackageID.Id, and is useful for accessing the field via an interface. +func (v *IngestPackagesIngestPackagesPackageID) GetId() string { return v.AllPkgIDTree.Id } -// GetNamespaces returns IngestPackagesIngestPackagesPackage.Namespaces, and is useful for accessing the field via an interface. -func (v *IngestPackagesIngestPackagesPackage) GetNamespaces() []IdPkgTreeNamespacesPackageNamespace { - return v.IdPkgTree.Namespaces +// GetNamespaces returns IngestPackagesIngestPackagesPackageID.Namespaces, and is useful for accessing the field via an interface. +func (v *IngestPackagesIngestPackagesPackageID) GetNamespaces() []AllPkgIDTreeNamespacesPackageNamespaceID { + return v.AllPkgIDTree.Namespaces } -func (v *IngestPackagesIngestPackagesPackage) UnmarshalJSON(b []byte) error { +func (v *IngestPackagesIngestPackagesPackageID) UnmarshalJSON(b []byte) error { if string(b) == "null" { return nil } var firstPass struct { - *IngestPackagesIngestPackagesPackage + *IngestPackagesIngestPackagesPackageID graphql.NoUnmarshalJSON } - firstPass.IngestPackagesIngestPackagesPackage = v + firstPass.IngestPackagesIngestPackagesPackageID = v err := json.Unmarshal(b, &firstPass) if err != nil { @@ -8358,20 +8291,20 @@ func (v *IngestPackagesIngestPackagesPackage) UnmarshalJSON(b []byte) error { } err = json.Unmarshal( - b, &v.IdPkgTree) + b, &v.AllPkgIDTree) if err != nil { return err } return nil } -type __premarshalIngestPackagesIngestPackagesPackage struct { +type __premarshalIngestPackagesIngestPackagesPackageID struct { Id string `json:"id"` - Namespaces []IdPkgTreeNamespacesPackageNamespace `json:"namespaces"` + Namespaces []AllPkgIDTreeNamespacesPackageNamespaceID `json:"namespaces"` } -func (v *IngestPackagesIngestPackagesPackage) MarshalJSON() ([]byte, error) { +func (v *IngestPackagesIngestPackagesPackageID) MarshalJSON() ([]byte, error) { premarshaled, err := v.__premarshalJSON() if err != nil { return nil, err @@ -8379,22 +8312,22 @@ func (v *IngestPackagesIngestPackagesPackage) MarshalJSON() ([]byte, error) { return json.Marshal(premarshaled) } -func (v *IngestPackagesIngestPackagesPackage) __premarshalJSON() (*__premarshalIngestPackagesIngestPackagesPackage, error) { - var retval __premarshalIngestPackagesIngestPackagesPackage +func (v *IngestPackagesIngestPackagesPackageID) __premarshalJSON() (*__premarshalIngestPackagesIngestPackagesPackageID, error) { + var retval __premarshalIngestPackagesIngestPackagesPackageID - retval.Id = v.IdPkgTree.Id - retval.Namespaces = v.IdPkgTree.Namespaces + retval.Id = v.AllPkgIDTree.Id + retval.Namespaces = v.AllPkgIDTree.Namespaces return &retval, nil } // IngestPackagesResponse is returned by IngestPackages on success. type IngestPackagesResponse struct { // Bulk ingests packages and returns the list of corresponding package hierarchies containing only the IDs. The returned array of IDs can be empty strings. - IngestPackages []IngestPackagesIngestPackagesPackage `json:"ingestPackages"` + IngestPackages []IngestPackagesIngestPackagesPackageID `json:"ingestPackages"` } // GetIngestPackages returns IngestPackagesResponse.IngestPackages, and is useful for accessing the field via an interface. -func (v *IngestPackagesResponse) GetIngestPackages() []IngestPackagesIngestPackagesPackage { +func (v *IngestPackagesResponse) GetIngestPackages() []IngestPackagesIngestPackagesPackageID { return v.IngestPackages } @@ -25047,10 +24980,10 @@ func IngestLicenses( const IngestPackage_Operation = ` mutation IngestPackage ($pkg: PkgInputSpec!) { ingestPackage(pkg: $pkg) { - ... IdPkgTree + ... AllPkgIDTree } } -fragment IdPkgTree on Package { +fragment AllPkgIDTree on PackageID { id namespaces { id @@ -25094,10 +25027,10 @@ func IngestPackage( const IngestPackages_Operation = ` mutation IngestPackages ($pkgs: [PkgInputSpec!]!) { ingestPackages(pkgs: $pkgs) { - ... IdPkgTree + ... AllPkgIDTree } } -fragment IdPkgTree on Package { +fragment AllPkgIDTree on PackageID { id namespaces { id diff --git a/pkg/assembler/clients/helpers/assembler.go b/pkg/assembler/clients/helpers/assembler.go index 19bc973df38..155254b54d5 100644 --- a/pkg/assembler/clients/helpers/assembler.go +++ b/pkg/assembler/clients/helpers/assembler.go @@ -498,7 +498,7 @@ func validatePackageSourceOrArtifactInput(pkg *model.PkgInputSpec, src *model.So return nil } -func retrievePackageVersionID(pkg *model.IngestPackageIngestPackage) (*string, error) { +func retrievePackageVersionID(pkg *model.IngestPackageIngestPackagePackageID) (*string, error) { if pkg != nil && len(pkg.Namespaces) == 1 && len(pkg.Namespaces[0].Names) == 1 && len(pkg.Namespaces[0].Names[0].Versions) == 1 { return &pkg.Namespaces[0].Names[0].Versions[0].Id, nil } else { diff --git a/pkg/assembler/clients/helpers/bulk.go b/pkg/assembler/clients/helpers/bulk.go index ce28f910195..58429e06659 100644 --- a/pkg/assembler/clients/helpers/bulk.go +++ b/pkg/assembler/clients/helpers/bulk.go @@ -850,7 +850,7 @@ func ingestCertifyLegals(ctx context.Context, client graphql.Client, v []assembl return nil } -func retrievePackageVersionIDs(pkgs []model.IngestPackagesIngestPackagesPackage) ([]string, error) { +func retrievePackageVersionIDs(pkgs []model.IngestPackagesIngestPackagesPackageID) ([]string, error) { var results []string for _, pkg := range pkgs { if len(pkg.Namespaces) == 1 && len(pkg.Namespaces[0].Names) == 1 && len(pkg.Namespaces[0].Names[0].Versions) == 1 { diff --git a/pkg/assembler/clients/operations/package.graphql b/pkg/assembler/clients/operations/package.graphql index e33f490ad97..43771f29f04 100644 --- a/pkg/assembler/clients/operations/package.graphql +++ b/pkg/assembler/clients/operations/package.graphql @@ -19,7 +19,7 @@ mutation IngestPackage($pkg: PkgInputSpec!) { ingestPackage(pkg: $pkg) { - ...IdPkgTree + ...AllPkgIDTree } } @@ -27,7 +27,7 @@ mutation IngestPackage($pkg: PkgInputSpec!) { mutation IngestPackages($pkgs: [PkgInputSpec!]!) { ingestPackages(pkgs: $pkgs) { - ...IdPkgTree + ...AllPkgIDTree } } diff --git a/pkg/assembler/clients/operations/trees.graphql b/pkg/assembler/clients/operations/trees.graphql index 0cff4c33434..a9c29ce7cec 100644 --- a/pkg/assembler/clients/operations/trees.graphql +++ b/pkg/assembler/clients/operations/trees.graphql @@ -19,7 +19,7 @@ # TODO(mihaimaruseac): Clean this up: do we want All of these to be returned? -fragment IdPkgTree on Package { +fragment AllPkgIDTree on PackageID { id namespaces { id diff --git a/pkg/assembler/graphql/generated/artifact.generated.go b/pkg/assembler/graphql/generated/artifact.generated.go index 884bea0380d..8d3838fc2dc 100644 --- a/pkg/assembler/graphql/generated/artifact.generated.go +++ b/pkg/assembler/graphql/generated/artifact.generated.go @@ -53,8 +53,8 @@ type MutationResolver interface { IngestLicenses(ctx context.Context, licenses []*model.LicenseInputSpec) ([]string, error) IngestHasMetadata(ctx context.Context, subject model.PackageSourceOrArtifactInput, pkgMatchType model.MatchFlags, hasMetadata model.HasMetadataInputSpec) (string, error) IngestBulkHasMetadata(ctx context.Context, subjects model.PackageSourceOrArtifactInputs, pkgMatchType model.MatchFlags, hasMetadataList []*model.HasMetadataInputSpec) ([]string, error) - IngestPackage(ctx context.Context, pkg model.PkgInputSpec) (*model.Package, error) - IngestPackages(ctx context.Context, pkgs []*model.PkgInputSpec) ([]*model.Package, error) + IngestPackage(ctx context.Context, pkg model.PkgInputSpec) (*model.PackageID, error) + IngestPackages(ctx context.Context, pkgs []*model.PkgInputSpec) ([]*model.PackageID, error) IngestPkgEqual(ctx context.Context, pkg model.PkgInputSpec, otherPackage model.PkgInputSpec, pkgEqual model.PkgEqualInputSpec) (string, error) IngestPkgEquals(ctx context.Context, pkgs []*model.PkgInputSpec, otherPackages []*model.PkgInputSpec, pkgEquals []*model.PkgEqualInputSpec) ([]string, error) IngestSource(ctx context.Context, source model.SourceInputSpec) (string, error) @@ -3946,9 +3946,9 @@ func (ec *executionContext) _Mutation_ingestPackage(ctx context.Context, field g } return graphql.Null } - res := resTmp.(*model.Package) + res := resTmp.(*model.PackageID) fc.Result = res - return ec.marshalNPackage2ᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackage(ctx, field.Selections, res) + return ec.marshalNPackageID2ᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageID(ctx, field.Selections, res) } func (ec *executionContext) fieldContext_Mutation_ingestPackage(ctx context.Context, field graphql.CollectedField) (fc *graphql.FieldContext, err error) { @@ -3960,13 +3960,11 @@ func (ec *executionContext) fieldContext_Mutation_ingestPackage(ctx context.Cont Child: func(ctx context.Context, field graphql.CollectedField) (*graphql.FieldContext, error) { switch field.Name { case "id": - return ec.fieldContext_Package_id(ctx, field) - case "type": - return ec.fieldContext_Package_type(ctx, field) + return ec.fieldContext_PackageID_id(ctx, field) case "namespaces": - return ec.fieldContext_Package_namespaces(ctx, field) + return ec.fieldContext_PackageID_namespaces(ctx, field) } - return nil, fmt.Errorf("no field named %q was found under type Package", field.Name) + return nil, fmt.Errorf("no field named %q was found under type PackageID", field.Name) }, } defer func() { @@ -4009,9 +4007,9 @@ func (ec *executionContext) _Mutation_ingestPackages(ctx context.Context, field } return graphql.Null } - res := resTmp.([]*model.Package) + res := resTmp.([]*model.PackageID) fc.Result = res - return ec.marshalNPackage2ᚕᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageᚄ(ctx, field.Selections, res) + return ec.marshalNPackageID2ᚕᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageIDᚄ(ctx, field.Selections, res) } func (ec *executionContext) fieldContext_Mutation_ingestPackages(ctx context.Context, field graphql.CollectedField) (fc *graphql.FieldContext, err error) { @@ -4023,13 +4021,11 @@ func (ec *executionContext) fieldContext_Mutation_ingestPackages(ctx context.Con Child: func(ctx context.Context, field graphql.CollectedField) (*graphql.FieldContext, error) { switch field.Name { case "id": - return ec.fieldContext_Package_id(ctx, field) - case "type": - return ec.fieldContext_Package_type(ctx, field) + return ec.fieldContext_PackageID_id(ctx, field) case "namespaces": - return ec.fieldContext_Package_namespaces(ctx, field) + return ec.fieldContext_PackageID_namespaces(ctx, field) } - return nil, fmt.Errorf("no field named %q was found under type Package", field.Name) + return nil, fmt.Errorf("no field named %q was found under type PackageID", field.Name) }, } defer func() { diff --git a/pkg/assembler/graphql/generated/package.generated.go b/pkg/assembler/graphql/generated/package.generated.go index 03edd42b45d..6664407955c 100644 --- a/pkg/assembler/graphql/generated/package.generated.go +++ b/pkg/assembler/graphql/generated/package.generated.go @@ -169,6 +169,100 @@ func (ec *executionContext) fieldContext_Package_namespaces(ctx context.Context, return fc, nil } +func (ec *executionContext) _PackageID_id(ctx context.Context, field graphql.CollectedField, obj *model.PackageID) (ret graphql.Marshaler) { + fc, err := ec.fieldContext_PackageID_id(ctx, field) + if err != nil { + return graphql.Null + } + ctx = graphql.WithFieldContext(ctx, fc) + defer func() { + if r := recover(); r != nil { + ec.Error(ctx, ec.Recover(ctx, r)) + ret = graphql.Null + } + }() + resTmp, err := ec.ResolverMiddleware(ctx, func(rctx context.Context) (interface{}, error) { + ctx = rctx // use context from middleware stack in children + return obj.ID, nil + }) + if err != nil { + ec.Error(ctx, err) + return graphql.Null + } + if resTmp == nil { + if !graphql.HasFieldError(ctx, fc) { + ec.Errorf(ctx, "must not be null") + } + return graphql.Null + } + res := resTmp.(string) + fc.Result = res + return ec.marshalNID2string(ctx, field.Selections, res) +} + +func (ec *executionContext) fieldContext_PackageID_id(ctx context.Context, field graphql.CollectedField) (fc *graphql.FieldContext, err error) { + fc = &graphql.FieldContext{ + Object: "PackageID", + Field: field, + IsMethod: false, + IsResolver: false, + Child: func(ctx context.Context, field graphql.CollectedField) (*graphql.FieldContext, error) { + return nil, errors.New("field of type ID does not have child fields") + }, + } + return fc, nil +} + +func (ec *executionContext) _PackageID_namespaces(ctx context.Context, field graphql.CollectedField, obj *model.PackageID) (ret graphql.Marshaler) { + fc, err := ec.fieldContext_PackageID_namespaces(ctx, field) + if err != nil { + return graphql.Null + } + ctx = graphql.WithFieldContext(ctx, fc) + defer func() { + if r := recover(); r != nil { + ec.Error(ctx, ec.Recover(ctx, r)) + ret = graphql.Null + } + }() + resTmp, err := ec.ResolverMiddleware(ctx, func(rctx context.Context) (interface{}, error) { + ctx = rctx // use context from middleware stack in children + return obj.Namespaces, nil + }) + if err != nil { + ec.Error(ctx, err) + return graphql.Null + } + if resTmp == nil { + if !graphql.HasFieldError(ctx, fc) { + ec.Errorf(ctx, "must not be null") + } + return graphql.Null + } + res := resTmp.([]*model.PackageNamespaceID) + fc.Result = res + return ec.marshalNPackageNamespaceID2ᚕᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageNamespaceIDᚄ(ctx, field.Selections, res) +} + +func (ec *executionContext) fieldContext_PackageID_namespaces(ctx context.Context, field graphql.CollectedField) (fc *graphql.FieldContext, err error) { + fc = &graphql.FieldContext{ + Object: "PackageID", + Field: field, + IsMethod: false, + IsResolver: false, + Child: func(ctx context.Context, field graphql.CollectedField) (*graphql.FieldContext, error) { + switch field.Name { + case "id": + return ec.fieldContext_PackageNamespaceID_id(ctx, field) + case "names": + return ec.fieldContext_PackageNamespaceID_names(ctx, field) + } + return nil, fmt.Errorf("no field named %q was found under type PackageNamespaceID", field.Name) + }, + } + return fc, nil +} + func (ec *executionContext) _PackageName_id(ctx context.Context, field graphql.CollectedField, obj *model.PackageName) (ret graphql.Marshaler) { fc, err := ec.fieldContext_PackageName_id(ctx, field) if err != nil { @@ -311,6 +405,98 @@ func (ec *executionContext) fieldContext_PackageName_versions(ctx context.Contex return fc, nil } +func (ec *executionContext) _PackageNameID_id(ctx context.Context, field graphql.CollectedField, obj *model.PackageNameID) (ret graphql.Marshaler) { + fc, err := ec.fieldContext_PackageNameID_id(ctx, field) + if err != nil { + return graphql.Null + } + ctx = graphql.WithFieldContext(ctx, fc) + defer func() { + if r := recover(); r != nil { + ec.Error(ctx, ec.Recover(ctx, r)) + ret = graphql.Null + } + }() + resTmp, err := ec.ResolverMiddleware(ctx, func(rctx context.Context) (interface{}, error) { + ctx = rctx // use context from middleware stack in children + return obj.ID, nil + }) + if err != nil { + ec.Error(ctx, err) + return graphql.Null + } + if resTmp == nil { + if !graphql.HasFieldError(ctx, fc) { + ec.Errorf(ctx, "must not be null") + } + return graphql.Null + } + res := resTmp.(string) + fc.Result = res + return ec.marshalNID2string(ctx, field.Selections, res) +} + +func (ec *executionContext) fieldContext_PackageNameID_id(ctx context.Context, field graphql.CollectedField) (fc *graphql.FieldContext, err error) { + fc = &graphql.FieldContext{ + Object: "PackageNameID", + Field: field, + IsMethod: false, + IsResolver: false, + Child: func(ctx context.Context, field graphql.CollectedField) (*graphql.FieldContext, error) { + return nil, errors.New("field of type ID does not have child fields") + }, + } + return fc, nil +} + +func (ec *executionContext) _PackageNameID_versions(ctx context.Context, field graphql.CollectedField, obj *model.PackageNameID) (ret graphql.Marshaler) { + fc, err := ec.fieldContext_PackageNameID_versions(ctx, field) + if err != nil { + return graphql.Null + } + ctx = graphql.WithFieldContext(ctx, fc) + defer func() { + if r := recover(); r != nil { + ec.Error(ctx, ec.Recover(ctx, r)) + ret = graphql.Null + } + }() + resTmp, err := ec.ResolverMiddleware(ctx, func(rctx context.Context) (interface{}, error) { + ctx = rctx // use context from middleware stack in children + return obj.Versions, nil + }) + if err != nil { + ec.Error(ctx, err) + return graphql.Null + } + if resTmp == nil { + if !graphql.HasFieldError(ctx, fc) { + ec.Errorf(ctx, "must not be null") + } + return graphql.Null + } + res := resTmp.([]*model.PackageVersionID) + fc.Result = res + return ec.marshalNPackageVersionID2ᚕᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageVersionIDᚄ(ctx, field.Selections, res) +} + +func (ec *executionContext) fieldContext_PackageNameID_versions(ctx context.Context, field graphql.CollectedField) (fc *graphql.FieldContext, err error) { + fc = &graphql.FieldContext{ + Object: "PackageNameID", + Field: field, + IsMethod: false, + IsResolver: false, + Child: func(ctx context.Context, field graphql.CollectedField) (*graphql.FieldContext, error) { + switch field.Name { + case "id": + return ec.fieldContext_PackageVersionID_id(ctx, field) + } + return nil, fmt.Errorf("no field named %q was found under type PackageVersionID", field.Name) + }, + } + return fc, nil +} + func (ec *executionContext) _PackageNamespace_id(ctx context.Context, field graphql.CollectedField, obj *model.PackageNamespace) (ret graphql.Marshaler) { fc, err := ec.fieldContext_PackageNamespace_id(ctx, field) if err != nil { @@ -451,6 +637,100 @@ func (ec *executionContext) fieldContext_PackageNamespace_names(ctx context.Cont return fc, nil } +func (ec *executionContext) _PackageNamespaceID_id(ctx context.Context, field graphql.CollectedField, obj *model.PackageNamespaceID) (ret graphql.Marshaler) { + fc, err := ec.fieldContext_PackageNamespaceID_id(ctx, field) + if err != nil { + return graphql.Null + } + ctx = graphql.WithFieldContext(ctx, fc) + defer func() { + if r := recover(); r != nil { + ec.Error(ctx, ec.Recover(ctx, r)) + ret = graphql.Null + } + }() + resTmp, err := ec.ResolverMiddleware(ctx, func(rctx context.Context) (interface{}, error) { + ctx = rctx // use context from middleware stack in children + return obj.ID, nil + }) + if err != nil { + ec.Error(ctx, err) + return graphql.Null + } + if resTmp == nil { + if !graphql.HasFieldError(ctx, fc) { + ec.Errorf(ctx, "must not be null") + } + return graphql.Null + } + res := resTmp.(string) + fc.Result = res + return ec.marshalNID2string(ctx, field.Selections, res) +} + +func (ec *executionContext) fieldContext_PackageNamespaceID_id(ctx context.Context, field graphql.CollectedField) (fc *graphql.FieldContext, err error) { + fc = &graphql.FieldContext{ + Object: "PackageNamespaceID", + Field: field, + IsMethod: false, + IsResolver: false, + Child: func(ctx context.Context, field graphql.CollectedField) (*graphql.FieldContext, error) { + return nil, errors.New("field of type ID does not have child fields") + }, + } + return fc, nil +} + +func (ec *executionContext) _PackageNamespaceID_names(ctx context.Context, field graphql.CollectedField, obj *model.PackageNamespaceID) (ret graphql.Marshaler) { + fc, err := ec.fieldContext_PackageNamespaceID_names(ctx, field) + if err != nil { + return graphql.Null + } + ctx = graphql.WithFieldContext(ctx, fc) + defer func() { + if r := recover(); r != nil { + ec.Error(ctx, ec.Recover(ctx, r)) + ret = graphql.Null + } + }() + resTmp, err := ec.ResolverMiddleware(ctx, func(rctx context.Context) (interface{}, error) { + ctx = rctx // use context from middleware stack in children + return obj.Names, nil + }) + if err != nil { + ec.Error(ctx, err) + return graphql.Null + } + if resTmp == nil { + if !graphql.HasFieldError(ctx, fc) { + ec.Errorf(ctx, "must not be null") + } + return graphql.Null + } + res := resTmp.([]*model.PackageNameID) + fc.Result = res + return ec.marshalNPackageNameID2ᚕᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageNameIDᚄ(ctx, field.Selections, res) +} + +func (ec *executionContext) fieldContext_PackageNamespaceID_names(ctx context.Context, field graphql.CollectedField) (fc *graphql.FieldContext, err error) { + fc = &graphql.FieldContext{ + Object: "PackageNamespaceID", + Field: field, + IsMethod: false, + IsResolver: false, + Child: func(ctx context.Context, field graphql.CollectedField) (*graphql.FieldContext, error) { + switch field.Name { + case "id": + return ec.fieldContext_PackageNameID_id(ctx, field) + case "versions": + return ec.fieldContext_PackageNameID_versions(ctx, field) + } + return nil, fmt.Errorf("no field named %q was found under type PackageNameID", field.Name) + }, + } + return fc, nil +} + func (ec *executionContext) _PackageQualifier_key(ctx context.Context, field graphql.CollectedField, obj *model.PackageQualifier) (ret graphql.Marshaler) { fc, err := ec.fieldContext_PackageQualifier_key(ctx, field) if err != nil { @@ -721,19 +1001,63 @@ func (ec *executionContext) fieldContext_PackageVersion_subpath(ctx context.Cont return fc, nil } -// endregion **************************** field.gotpl ***************************** - -// region **************************** input.gotpl ***************************** - -func (ec *executionContext) unmarshalInputPackageQualifierInputSpec(ctx context.Context, obj interface{}) (model.PackageQualifierInputSpec, error) { - var it model.PackageQualifierInputSpec - asMap := map[string]interface{}{} - for k, v := range obj.(map[string]interface{}) { - asMap[k] = v +func (ec *executionContext) _PackageVersionID_id(ctx context.Context, field graphql.CollectedField, obj *model.PackageVersionID) (ret graphql.Marshaler) { + fc, err := ec.fieldContext_PackageVersionID_id(ctx, field) + if err != nil { + return graphql.Null } - - fieldsInOrder := [...]string{"key", "value"} - for _, k := range fieldsInOrder { + ctx = graphql.WithFieldContext(ctx, fc) + defer func() { + if r := recover(); r != nil { + ec.Error(ctx, ec.Recover(ctx, r)) + ret = graphql.Null + } + }() + resTmp, err := ec.ResolverMiddleware(ctx, func(rctx context.Context) (interface{}, error) { + ctx = rctx // use context from middleware stack in children + return obj.ID, nil + }) + if err != nil { + ec.Error(ctx, err) + return graphql.Null + } + if resTmp == nil { + if !graphql.HasFieldError(ctx, fc) { + ec.Errorf(ctx, "must not be null") + } + return graphql.Null + } + res := resTmp.(string) + fc.Result = res + return ec.marshalNID2string(ctx, field.Selections, res) +} + +func (ec *executionContext) fieldContext_PackageVersionID_id(ctx context.Context, field graphql.CollectedField) (fc *graphql.FieldContext, err error) { + fc = &graphql.FieldContext{ + Object: "PackageVersionID", + Field: field, + IsMethod: false, + IsResolver: false, + Child: func(ctx context.Context, field graphql.CollectedField) (*graphql.FieldContext, error) { + return nil, errors.New("field of type ID does not have child fields") + }, + } + return fc, nil +} + +// endregion **************************** field.gotpl ***************************** + +// region **************************** input.gotpl ***************************** + +func (ec *executionContext) unmarshalInputPackageQualifierInputSpec(ctx context.Context, obj interface{}) (model.PackageQualifierInputSpec, error) { + var it model.PackageQualifierInputSpec + asMap := map[string]interface{}{} + for k, v := range obj.(map[string]interface{}) { + asMap[k] = v + } + + fieldsInOrder := [...]string{"key", "value"} + for _, k := range fieldsInOrder { v, ok := asMap[k] if !ok { continue @@ -1044,6 +1368,50 @@ func (ec *executionContext) _Package(ctx context.Context, sel ast.SelectionSet, return out } +var packageIDImplementors = []string{"PackageID"} + +func (ec *executionContext) _PackageID(ctx context.Context, sel ast.SelectionSet, obj *model.PackageID) graphql.Marshaler { + fields := graphql.CollectFields(ec.OperationContext, sel, packageIDImplementors) + + out := graphql.NewFieldSet(fields) + deferred := make(map[string]*graphql.FieldSet) + for i, field := range fields { + switch field.Name { + case "__typename": + out.Values[i] = graphql.MarshalString("PackageID") + case "id": + out.Values[i] = ec._PackageID_id(ctx, field, obj) + if out.Values[i] == graphql.Null { + out.Invalids++ + } + case "namespaces": + out.Values[i] = ec._PackageID_namespaces(ctx, field, obj) + if out.Values[i] == graphql.Null { + out.Invalids++ + } + default: + panic("unknown field " + strconv.Quote(field.Name)) + } + } + out.Dispatch(ctx) + if out.Invalids > 0 { + return graphql.Null + } + + atomic.AddInt32(&ec.deferred, int32(len(deferred))) + + for label, dfs := range deferred { + ec.processDeferredGroup(graphql.DeferredGroup{ + Label: label, + Path: graphql.GetPath(ctx), + FieldSet: dfs, + Context: ctx, + }) + } + + return out +} + var packageNameImplementors = []string{"PackageName"} func (ec *executionContext) _PackageName(ctx context.Context, sel ast.SelectionSet, obj *model.PackageName) graphql.Marshaler { @@ -1093,6 +1461,50 @@ func (ec *executionContext) _PackageName(ctx context.Context, sel ast.SelectionS return out } +var packageNameIDImplementors = []string{"PackageNameID"} + +func (ec *executionContext) _PackageNameID(ctx context.Context, sel ast.SelectionSet, obj *model.PackageNameID) graphql.Marshaler { + fields := graphql.CollectFields(ec.OperationContext, sel, packageNameIDImplementors) + + out := graphql.NewFieldSet(fields) + deferred := make(map[string]*graphql.FieldSet) + for i, field := range fields { + switch field.Name { + case "__typename": + out.Values[i] = graphql.MarshalString("PackageNameID") + case "id": + out.Values[i] = ec._PackageNameID_id(ctx, field, obj) + if out.Values[i] == graphql.Null { + out.Invalids++ + } + case "versions": + out.Values[i] = ec._PackageNameID_versions(ctx, field, obj) + if out.Values[i] == graphql.Null { + out.Invalids++ + } + default: + panic("unknown field " + strconv.Quote(field.Name)) + } + } + out.Dispatch(ctx) + if out.Invalids > 0 { + return graphql.Null + } + + atomic.AddInt32(&ec.deferred, int32(len(deferred))) + + for label, dfs := range deferred { + ec.processDeferredGroup(graphql.DeferredGroup{ + Label: label, + Path: graphql.GetPath(ctx), + FieldSet: dfs, + Context: ctx, + }) + } + + return out +} + var packageNamespaceImplementors = []string{"PackageNamespace"} func (ec *executionContext) _PackageNamespace(ctx context.Context, sel ast.SelectionSet, obj *model.PackageNamespace) graphql.Marshaler { @@ -1142,6 +1554,50 @@ func (ec *executionContext) _PackageNamespace(ctx context.Context, sel ast.Selec return out } +var packageNamespaceIDImplementors = []string{"PackageNamespaceID"} + +func (ec *executionContext) _PackageNamespaceID(ctx context.Context, sel ast.SelectionSet, obj *model.PackageNamespaceID) graphql.Marshaler { + fields := graphql.CollectFields(ec.OperationContext, sel, packageNamespaceIDImplementors) + + out := graphql.NewFieldSet(fields) + deferred := make(map[string]*graphql.FieldSet) + for i, field := range fields { + switch field.Name { + case "__typename": + out.Values[i] = graphql.MarshalString("PackageNamespaceID") + case "id": + out.Values[i] = ec._PackageNamespaceID_id(ctx, field, obj) + if out.Values[i] == graphql.Null { + out.Invalids++ + } + case "names": + out.Values[i] = ec._PackageNamespaceID_names(ctx, field, obj) + if out.Values[i] == graphql.Null { + out.Invalids++ + } + default: + panic("unknown field " + strconv.Quote(field.Name)) + } + } + out.Dispatch(ctx) + if out.Invalids > 0 { + return graphql.Null + } + + atomic.AddInt32(&ec.deferred, int32(len(deferred))) + + for label, dfs := range deferred { + ec.processDeferredGroup(graphql.DeferredGroup{ + Label: label, + Path: graphql.GetPath(ctx), + FieldSet: dfs, + Context: ctx, + }) + } + + return out +} + var packageQualifierImplementors = []string{"PackageQualifier"} func (ec *executionContext) _PackageQualifier(ctx context.Context, sel ast.SelectionSet, obj *model.PackageQualifier) graphql.Marshaler { @@ -1240,14 +1696,49 @@ func (ec *executionContext) _PackageVersion(ctx context.Context, sel ast.Selecti return out } -// endregion **************************** object.gotpl **************************** +var packageVersionIDImplementors = []string{"PackageVersionID"} -// region ***************************** type.gotpl ***************************** +func (ec *executionContext) _PackageVersionID(ctx context.Context, sel ast.SelectionSet, obj *model.PackageVersionID) graphql.Marshaler { + fields := graphql.CollectFields(ec.OperationContext, sel, packageVersionIDImplementors) + + out := graphql.NewFieldSet(fields) + deferred := make(map[string]*graphql.FieldSet) + for i, field := range fields { + switch field.Name { + case "__typename": + out.Values[i] = graphql.MarshalString("PackageVersionID") + case "id": + out.Values[i] = ec._PackageVersionID_id(ctx, field, obj) + if out.Values[i] == graphql.Null { + out.Invalids++ + } + default: + panic("unknown field " + strconv.Quote(field.Name)) + } + } + out.Dispatch(ctx) + if out.Invalids > 0 { + return graphql.Null + } + + atomic.AddInt32(&ec.deferred, int32(len(deferred))) -func (ec *executionContext) marshalNPackage2githubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackage(ctx context.Context, sel ast.SelectionSet, v model.Package) graphql.Marshaler { - return ec._Package(ctx, sel, &v) + for label, dfs := range deferred { + ec.processDeferredGroup(graphql.DeferredGroup{ + Label: label, + Path: graphql.GetPath(ctx), + FieldSet: dfs, + Context: ctx, + }) + } + + return out } +// endregion **************************** object.gotpl **************************** + +// region ***************************** type.gotpl ***************************** + func (ec *executionContext) marshalNPackage2ᚕᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageᚄ(ctx context.Context, sel ast.SelectionSet, v []*model.Package) graphql.Marshaler { ret := make(graphql.Array, len(v)) var wg sync.WaitGroup @@ -1302,6 +1793,64 @@ func (ec *executionContext) marshalNPackage2ᚖgithubᚗcomᚋguacsecᚋguacᚋp return ec._Package(ctx, sel, v) } +func (ec *executionContext) marshalNPackageID2githubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageID(ctx context.Context, sel ast.SelectionSet, v model.PackageID) graphql.Marshaler { + return ec._PackageID(ctx, sel, &v) +} + +func (ec *executionContext) marshalNPackageID2ᚕᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageIDᚄ(ctx context.Context, sel ast.SelectionSet, v []*model.PackageID) graphql.Marshaler { + ret := make(graphql.Array, len(v)) + var wg sync.WaitGroup + isLen1 := len(v) == 1 + if !isLen1 { + wg.Add(len(v)) + } + for i := range v { + i := i + fc := &graphql.FieldContext{ + Index: &i, + Result: &v[i], + } + ctx := graphql.WithFieldContext(ctx, fc) + f := func(i int) { + defer func() { + if r := recover(); r != nil { + ec.Error(ctx, ec.Recover(ctx, r)) + ret = nil + } + }() + if !isLen1 { + defer wg.Done() + } + ret[i] = ec.marshalNPackageID2ᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageID(ctx, sel, v[i]) + } + if isLen1 { + f(i) + } else { + go f(i) + } + + } + wg.Wait() + + for _, e := range ret { + if e == graphql.Null { + return graphql.Null + } + } + + return ret +} + +func (ec *executionContext) marshalNPackageID2ᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageID(ctx context.Context, sel ast.SelectionSet, v *model.PackageID) graphql.Marshaler { + if v == nil { + if !graphql.HasFieldError(ctx, graphql.GetFieldContext(ctx)) { + ec.Errorf(ctx, "the requested element is null which the schema does not allow") + } + return graphql.Null + } + return ec._PackageID(ctx, sel, v) +} + func (ec *executionContext) marshalNPackageName2ᚕᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageNameᚄ(ctx context.Context, sel ast.SelectionSet, v []*model.PackageName) graphql.Marshaler { ret := make(graphql.Array, len(v)) var wg sync.WaitGroup @@ -1356,6 +1905,60 @@ func (ec *executionContext) marshalNPackageName2ᚖgithubᚗcomᚋguacsecᚋguac return ec._PackageName(ctx, sel, v) } +func (ec *executionContext) marshalNPackageNameID2ᚕᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageNameIDᚄ(ctx context.Context, sel ast.SelectionSet, v []*model.PackageNameID) graphql.Marshaler { + ret := make(graphql.Array, len(v)) + var wg sync.WaitGroup + isLen1 := len(v) == 1 + if !isLen1 { + wg.Add(len(v)) + } + for i := range v { + i := i + fc := &graphql.FieldContext{ + Index: &i, + Result: &v[i], + } + ctx := graphql.WithFieldContext(ctx, fc) + f := func(i int) { + defer func() { + if r := recover(); r != nil { + ec.Error(ctx, ec.Recover(ctx, r)) + ret = nil + } + }() + if !isLen1 { + defer wg.Done() + } + ret[i] = ec.marshalNPackageNameID2ᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageNameID(ctx, sel, v[i]) + } + if isLen1 { + f(i) + } else { + go f(i) + } + + } + wg.Wait() + + for _, e := range ret { + if e == graphql.Null { + return graphql.Null + } + } + + return ret +} + +func (ec *executionContext) marshalNPackageNameID2ᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageNameID(ctx context.Context, sel ast.SelectionSet, v *model.PackageNameID) graphql.Marshaler { + if v == nil { + if !graphql.HasFieldError(ctx, graphql.GetFieldContext(ctx)) { + ec.Errorf(ctx, "the requested element is null which the schema does not allow") + } + return graphql.Null + } + return ec._PackageNameID(ctx, sel, v) +} + func (ec *executionContext) marshalNPackageNamespace2ᚕᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageNamespaceᚄ(ctx context.Context, sel ast.SelectionSet, v []*model.PackageNamespace) graphql.Marshaler { ret := make(graphql.Array, len(v)) var wg sync.WaitGroup @@ -1410,6 +2013,60 @@ func (ec *executionContext) marshalNPackageNamespace2ᚖgithubᚗcomᚋguacsec return ec._PackageNamespace(ctx, sel, v) } +func (ec *executionContext) marshalNPackageNamespaceID2ᚕᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageNamespaceIDᚄ(ctx context.Context, sel ast.SelectionSet, v []*model.PackageNamespaceID) graphql.Marshaler { + ret := make(graphql.Array, len(v)) + var wg sync.WaitGroup + isLen1 := len(v) == 1 + if !isLen1 { + wg.Add(len(v)) + } + for i := range v { + i := i + fc := &graphql.FieldContext{ + Index: &i, + Result: &v[i], + } + ctx := graphql.WithFieldContext(ctx, fc) + f := func(i int) { + defer func() { + if r := recover(); r != nil { + ec.Error(ctx, ec.Recover(ctx, r)) + ret = nil + } + }() + if !isLen1 { + defer wg.Done() + } + ret[i] = ec.marshalNPackageNamespaceID2ᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageNamespaceID(ctx, sel, v[i]) + } + if isLen1 { + f(i) + } else { + go f(i) + } + + } + wg.Wait() + + for _, e := range ret { + if e == graphql.Null { + return graphql.Null + } + } + + return ret +} + +func (ec *executionContext) marshalNPackageNamespaceID2ᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageNamespaceID(ctx context.Context, sel ast.SelectionSet, v *model.PackageNamespaceID) graphql.Marshaler { + if v == nil { + if !graphql.HasFieldError(ctx, graphql.GetFieldContext(ctx)) { + ec.Errorf(ctx, "the requested element is null which the schema does not allow") + } + return graphql.Null + } + return ec._PackageNamespaceID(ctx, sel, v) +} + func (ec *executionContext) marshalNPackageQualifier2ᚕᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageQualifierᚄ(ctx context.Context, sel ast.SelectionSet, v []*model.PackageQualifier) graphql.Marshaler { ret := make(graphql.Array, len(v)) var wg sync.WaitGroup @@ -1528,6 +2185,60 @@ func (ec *executionContext) marshalNPackageVersion2ᚖgithubᚗcomᚋguacsecᚋg return ec._PackageVersion(ctx, sel, v) } +func (ec *executionContext) marshalNPackageVersionID2ᚕᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageVersionIDᚄ(ctx context.Context, sel ast.SelectionSet, v []*model.PackageVersionID) graphql.Marshaler { + ret := make(graphql.Array, len(v)) + var wg sync.WaitGroup + isLen1 := len(v) == 1 + if !isLen1 { + wg.Add(len(v)) + } + for i := range v { + i := i + fc := &graphql.FieldContext{ + Index: &i, + Result: &v[i], + } + ctx := graphql.WithFieldContext(ctx, fc) + f := func(i int) { + defer func() { + if r := recover(); r != nil { + ec.Error(ctx, ec.Recover(ctx, r)) + ret = nil + } + }() + if !isLen1 { + defer wg.Done() + } + ret[i] = ec.marshalNPackageVersionID2ᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageVersionID(ctx, sel, v[i]) + } + if isLen1 { + f(i) + } else { + go f(i) + } + + } + wg.Wait() + + for _, e := range ret { + if e == graphql.Null { + return graphql.Null + } + } + + return ret +} + +func (ec *executionContext) marshalNPackageVersionID2ᚖgithubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPackageVersionID(ctx context.Context, sel ast.SelectionSet, v *model.PackageVersionID) graphql.Marshaler { + if v == nil { + if !graphql.HasFieldError(ctx, graphql.GetFieldContext(ctx)) { + ec.Errorf(ctx, "the requested element is null which the schema does not allow") + } + return graphql.Null + } + return ec._PackageVersionID(ctx, sel, v) +} + func (ec *executionContext) unmarshalNPkgInputSpec2githubᚗcomᚋguacsecᚋguacᚋpkgᚋassemblerᚋgraphqlᚋmodelᚐPkgInputSpec(ctx context.Context, v interface{}) (model.PkgInputSpec, error) { res, err := ec.unmarshalInputPkgInputSpec(ctx, v) return res, graphql.ErrorOnPath(ctx, err) diff --git a/pkg/assembler/graphql/generated/root_.generated.go b/pkg/assembler/graphql/generated/root_.generated.go index ff426031332..30430a922ce 100644 --- a/pkg/assembler/graphql/generated/root_.generated.go +++ b/pkg/assembler/graphql/generated/root_.generated.go @@ -240,18 +240,33 @@ type ComplexityRoot struct { Type func(childComplexity int) int } + PackageID struct { + ID func(childComplexity int) int + Namespaces func(childComplexity int) int + } + PackageName struct { ID func(childComplexity int) int Name func(childComplexity int) int Versions func(childComplexity int) int } + PackageNameID struct { + ID func(childComplexity int) int + Versions func(childComplexity int) int + } + PackageNamespace struct { ID func(childComplexity int) int Names func(childComplexity int) int Namespace func(childComplexity int) int } + PackageNamespaceID struct { + ID func(childComplexity int) int + Names func(childComplexity int) int + } + PackageQualifier struct { Key func(childComplexity int) int Value func(childComplexity int) int @@ -264,6 +279,10 @@ type ComplexityRoot struct { Version func(childComplexity int) int } + PackageVersionID struct { + ID func(childComplexity int) int + } + PkgEqual struct { Collector func(childComplexity int) int ID func(childComplexity int) int @@ -1679,6 +1698,20 @@ func (e *executableSchema) Complexity(typeName, field string, childComplexity in return e.complexity.Package.Type(childComplexity), true + case "PackageID.id": + if e.complexity.PackageID.ID == nil { + break + } + + return e.complexity.PackageID.ID(childComplexity), true + + case "PackageID.namespaces": + if e.complexity.PackageID.Namespaces == nil { + break + } + + return e.complexity.PackageID.Namespaces(childComplexity), true + case "PackageName.id": if e.complexity.PackageName.ID == nil { break @@ -1700,6 +1733,20 @@ func (e *executableSchema) Complexity(typeName, field string, childComplexity in return e.complexity.PackageName.Versions(childComplexity), true + case "PackageNameID.id": + if e.complexity.PackageNameID.ID == nil { + break + } + + return e.complexity.PackageNameID.ID(childComplexity), true + + case "PackageNameID.versions": + if e.complexity.PackageNameID.Versions == nil { + break + } + + return e.complexity.PackageNameID.Versions(childComplexity), true + case "PackageNamespace.id": if e.complexity.PackageNamespace.ID == nil { break @@ -1721,6 +1768,20 @@ func (e *executableSchema) Complexity(typeName, field string, childComplexity in return e.complexity.PackageNamespace.Namespace(childComplexity), true + case "PackageNamespaceID.id": + if e.complexity.PackageNamespaceID.ID == nil { + break + } + + return e.complexity.PackageNamespaceID.ID(childComplexity), true + + case "PackageNamespaceID.names": + if e.complexity.PackageNamespaceID.Names == nil { + break + } + + return e.complexity.PackageNamespaceID.Names(childComplexity), true + case "PackageQualifier.key": if e.complexity.PackageQualifier.Key == nil { break @@ -1763,6 +1824,13 @@ func (e *executableSchema) Complexity(typeName, field string, childComplexity in return e.complexity.PackageVersion.Version(childComplexity), true + case "PackageVersionID.id": + if e.complexity.PackageVersionID.ID == nil { + break + } + + return e.complexity.PackageVersionID.ID(childComplexity), true + case "PkgEqual.collector": if e.complexity.PkgEqual.Collector == nil { break @@ -4699,9 +4767,41 @@ extend type Query { extend type Mutation { "Ingests a new package and returns a corresponding package hierarchy containing only the IDs. The returned ID can be empty string." - ingestPackage(pkg: PkgInputSpec!): Package! + ingestPackage(pkg: PkgInputSpec!): PackageID! "Bulk ingests packages and returns the list of corresponding package hierarchies containing only the IDs. The returned array of IDs can be empty strings." - ingestPackages(pkgs: [PkgInputSpec!]!): [Package!]! + ingestPackages(pkgs: [PkgInputSpec!]!): [PackageID!]! +} + +""" +The ID of the package within the package trie +""" +type PackageID { + id: ID! + namespaces: [PackageNamespaceID!]! +} + +""" +The ID of the package namespace within the package trie +""" +type PackageNamespaceID { + id: ID! + names: [PackageNameID!]! +} + +""" +The ID of the package name within the package trie +""" +type PackageNameID { + id: ID! + versions: [PackageVersionID!]! +} + + +""" +The ID of the package version within the package trie +""" +type PackageVersionID { + id: ID! } `, BuiltIn: false}, {Name: "../schema/path.graphql", Input: `# diff --git a/pkg/assembler/graphql/helpers/package.go b/pkg/assembler/graphql/helpers/package.go index 785ed2f7b02..3b71b68cb4d 100644 --- a/pkg/assembler/graphql/helpers/package.go +++ b/pkg/assembler/graphql/helpers/package.go @@ -20,16 +20,16 @@ import ( ) // Return a package structure containing only IDs -func GetPackageAsIds(packages []*model.Package) []*model.Package { - results := []*model.Package{} +func GetPackageAsIds(packages []*model.Package) []*model.PackageID { + results := []*model.PackageID{} for _, pkg := range packages { - result := &model.Package{ID: pkg.ID} + result := &model.PackageID{ID: pkg.ID} for _, namespace := range pkg.Namespaces { - resultNamespace := &model.PackageNamespace{ID: namespace.ID} + resultNamespace := &model.PackageNamespaceID{ID: namespace.ID} for _, name := range namespace.Names { - resultName := &model.PackageName{ID: name.ID} + resultName := &model.PackageNameID{ID: name.ID} for _, version := range name.Versions { - resultVersion := &model.PackageVersion{ID: version.ID} + resultVersion := &model.PackageVersionID{ID: version.ID} resultName.Versions = append(resultName.Versions, resultVersion) } resultNamespace.Names = append(resultNamespace.Names, resultName) diff --git a/pkg/assembler/graphql/model/nodes.go b/pkg/assembler/graphql/model/nodes.go index 5e6c2ff1f54..e34ad309ec8 100644 --- a/pkg/assembler/graphql/model/nodes.go +++ b/pkg/assembler/graphql/model/nodes.go @@ -764,6 +764,12 @@ func (Package) IsPackageOrSource() {} func (Package) IsNode() {} +// The ID of the package within the package trie +type PackageID struct { + ID string `json:"id"` + Namespaces []*PackageNamespaceID `json:"namespaces"` +} + // PackageName is a name for packages. // // In the pURL representation, each PackageName matches the @@ -779,6 +785,12 @@ type PackageName struct { Versions []*PackageVersion `json:"versions"` } +// The ID of the package name within the package trie +type PackageNameID struct { + ID string `json:"id"` + Versions []*PackageVersionID `json:"versions"` +} + // PackageNamespace is a namespace for packages. // // In the pURL representation, each PackageNamespace matches the @@ -792,6 +804,12 @@ type PackageNamespace struct { Names []*PackageName `json:"names"` } +// The ID of the package namespace within the package trie +type PackageNamespaceID struct { + ID string `json:"id"` + Names []*PackageNameID `json:"names"` +} + // PackageOrArtifactInput allows using PackageOrArtifact union as // input type to be used in mutations. // @@ -928,6 +946,11 @@ type PackageVersion struct { Subpath string `json:"subpath"` } +// The ID of the package version within the package trie +type PackageVersionID struct { + ID string `json:"id"` +} + // PkgEqual is an attestation that a set of packages are similar. type PkgEqual struct { ID string `json:"id"` diff --git a/pkg/assembler/graphql/resolvers/package.resolvers.go b/pkg/assembler/graphql/resolvers/package.resolvers.go index 0f7a237771b..57be0bffb7c 100644 --- a/pkg/assembler/graphql/resolvers/package.resolvers.go +++ b/pkg/assembler/graphql/resolvers/package.resolvers.go @@ -13,7 +13,7 @@ import ( ) // IngestPackage is the resolver for the ingestPackage field. -func (r *mutationResolver) IngestPackage(ctx context.Context, pkg model.PkgInputSpec) (*model.Package, error) { +func (r *mutationResolver) IngestPackage(ctx context.Context, pkg model.PkgInputSpec) (*model.PackageID, error) { // Return the id of the PackageVersion which has been ingested // TODO (knrc) - check why this was originally returning the ID for the Package, since that is not specific enough @@ -29,7 +29,7 @@ func (r *mutationResolver) IngestPackage(ctx context.Context, pkg model.PkgInput } // IngestPackages is the resolver for the ingestPackages field. -func (r *mutationResolver) IngestPackages(ctx context.Context, pkgs []*model.PkgInputSpec) ([]*model.Package, error) { +func (r *mutationResolver) IngestPackages(ctx context.Context, pkgs []*model.PkgInputSpec) ([]*model.PackageID, error) { ingestedPackages, err := r.Backend.IngestPackages(ctx, pkgs) if err == nil { results := helpers.GetPackageAsIds(ingestedPackages) diff --git a/pkg/assembler/graphql/schema/package.graphql b/pkg/assembler/graphql/schema/package.graphql index 54fcbf31c5c..12af0d0b097 100644 --- a/pkg/assembler/graphql/schema/package.graphql +++ b/pkg/assembler/graphql/schema/package.graphql @@ -182,7 +182,39 @@ extend type Query { extend type Mutation { "Ingests a new package and returns a corresponding package hierarchy containing only the IDs. The returned ID can be empty string." - ingestPackage(pkg: PkgInputSpec!): Package! + ingestPackage(pkg: PkgInputSpec!): PackageID! "Bulk ingests packages and returns the list of corresponding package hierarchies containing only the IDs. The returned array of IDs can be empty strings." - ingestPackages(pkgs: [PkgInputSpec!]!): [Package!]! + ingestPackages(pkgs: [PkgInputSpec!]!): [PackageID!]! +} + +""" +The ID of the package within the package trie +""" +type PackageID { + id: ID! + namespaces: [PackageNamespaceID!]! +} + +""" +The ID of the package namespace within the package trie +""" +type PackageNamespaceID { + id: ID! + names: [PackageNameID!]! +} + +""" +The ID of the package name within the package trie +""" +type PackageNameID { + id: ID! + versions: [PackageVersionID!]! +} + + +""" +The ID of the package version within the package trie +""" +type PackageVersionID { + id: ID! }