Skip to content

Commit 1f3c4f3

Browse files
committed
[package outputs] generate selected output in flake
1 parent 62f5cb2 commit 1f3c4f3

File tree

5 files changed

+62
-3
lines changed

5 files changed

+62
-3
lines changed

internal/devpkg/narinfo_cache.go

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,10 @@ func (p *Package) IsInBinaryCache() (bool, error) {
2727
if p.PatchGlibc {
2828
return false, nil
2929
}
30+
// Packages with non-default outputs are not used to be taken from the binary cache.
31+
if len(p.Outputs) > 0 {
32+
return false, nil
33+
}
3034
if eligible, err := p.isEligibleForBinaryCache(); err != nil {
3135
return false, err
3236
} else if !eligible {

internal/devpkg/package.go

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -78,6 +78,10 @@ type Package struct {
7878
// example: github:nixos/nixpkgs/5233fd2ba76a3accb5aaa999c00509a11fd0793c#hello
7979
Raw string
8080

81+
// Outputs is a list of outputs to build from the package's derivation.
82+
// If empty, the default output is used.
83+
Outputs []string
84+
8185
// PatchGlibc applies a function to the package's derivation that
8286
// patches any ELF binaries to use the latest version of nixpkgs#glibc.
8387
PatchGlibc bool
@@ -113,6 +117,7 @@ func PackagesFromConfig(config *devconfig.Config, l lock.Locker) []*Package {
113117
pkg := newPackage(cfgPkg.VersionedName(), cfgPkg.IsEnabledOnPlatform(), l)
114118
pkg.DisablePlugin = cfgPkg.DisablePlugin
115119
pkg.PatchGlibc = cfgPkg.PatchGlibc && nix.SystemIsLinux()
120+
pkg.Outputs = cfgPkg.Outputs
116121
result = append(result, pkg)
117122
}
118123
return result
@@ -126,6 +131,7 @@ func PackageFromStringWithOptions(raw string, locker lock.Locker, opts devopt.Ad
126131
pkg := PackageFromStringWithDefaults(raw, locker)
127132
pkg.DisablePlugin = opts.DisablePlugin
128133
pkg.PatchGlibc = opts.PatchGlibc
134+
pkg.Outputs = opts.Outputs
129135
return pkg
130136
}
131137

internal/shellgen/flake_input.go

Lines changed: 40 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -50,9 +50,48 @@ func (f *flakeInput) PkgImportName() string {
5050
return f.Name + "-pkgs"
5151
}
5252

53+
type SymlinkJoin struct {
54+
Name string
55+
Paths []string
56+
}
57+
58+
// BuildInputsForSymlinkJoin returns a list of SymlinkJoin objects that can be used
59+
// as the buildInput. Used for packages that have non-default outputs that needs to
60+
// be combined into a single buildInput.
61+
func (f *flakeInput) BuildInputsForSymlinkJoin() ([]*SymlinkJoin, error) {
62+
joins := []*SymlinkJoin{}
63+
for _, pkg := range f.Packages {
64+
// skip packages that have no non-default outputs
65+
if len(pkg.Outputs) == 0 {
66+
continue
67+
}
68+
69+
attributePath, err := pkg.FullPackageAttributePath()
70+
if err != nil {
71+
return nil, err
72+
}
73+
joins = append(joins, &SymlinkJoin{
74+
Name: pkg.String() + "-combined",
75+
Paths: lo.Map(pkg.Outputs, func(output string, _ int) string {
76+
// TODO: handle !f.IsNixpkgs() case
77+
parts := strings.Split(attributePath, ".")
78+
return f.PkgImportName() + "." + strings.Join(parts[2:], ".") + "." + output
79+
}),
80+
})
81+
}
82+
return joins, nil
83+
}
84+
5385
func (f *flakeInput) BuildInputs() ([]string, error) {
5486
var err error
55-
attributePaths := lo.Map(f.Packages, func(pkg *devpkg.Package, _ int) string {
87+
88+
// Filter out packages that have non-default outputs
89+
// These are handled in BuildInputsForSymlinkJoin
90+
packages := lo.Filter(f.Packages, func(pkg *devpkg.Package, _ int) bool {
91+
return len(pkg.Outputs) == 0
92+
})
93+
94+
attributePaths := lo.Map(packages, func(pkg *devpkg.Package, _ int) string {
5695
attributePath, attributePathErr := pkg.FullPackageAttributePath()
5796
if attributePathErr != nil {
5897
err = attributePathErr

internal/shellgen/generate.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,7 @@ var tmplFS embed.FS
3030
// devbox.PrintEnv, which is the core function from which devbox shell/run/direnv
3131
// functionality is derived.
3232
func GenerateForPrintEnv(ctx context.Context, devbox devboxer) error {
33-
defer trace.StartRegion(ctx, "generateShellFiles").End()
33+
defer trace.StartRegion(ctx, "generateForPrintEnv").End()
3434

3535
plan, err := newFlakePlan(ctx, devbox)
3636
if err != nil {

internal/shellgen/tmpl/flake_remove_nixpkgs.nix.tmpl

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,17 @@
4646
})
4747
{{- end }}
4848
{{- end }}
49-
{{- range .FlakeInputs }}
49+
{{- range $_, $flakeInput := .FlakeInputs }}
50+
{{- range .BuildInputsForSymlinkJoin }}
51+
(pkgs.symlinkJoin {
52+
name = "{{.Name}}";
53+
paths = [
54+
{{- range .Paths }}
55+
{{.}}
56+
{{- end }}
57+
];
58+
})
59+
{{- end }}
5060
{{- range .BuildInputs }}
5161
{{.}}
5262
{{- end }}

0 commit comments

Comments
 (0)