15370: Re-enable docker tests.
[arvados.git] / cmd / arvados-package / fpm.go
1 // Copyright (C) The Arvados Authors. All rights reserved.
2 //
3 // SPDX-License-Identifier: AGPL-3.0
4
5 package main
6
7 import (
8         "bytes"
9         "context"
10         "fmt"
11         "io"
12         "os"
13         "os/exec"
14         "path/filepath"
15
16         "git.arvados.org/arvados.git/lib/install"
17 )
18
19 func fpm(ctx context.Context, opts opts, stdin io.Reader, stdout, stderr io.Writer) error {
20         var chownUid, chownGid int
21         if opts.PackageChown != "" {
22                 _, err := fmt.Sscanf(opts.PackageChown, "%d:%d", &chownUid, &chownGid)
23                 if err != nil {
24                         return fmt.Errorf("invalid value %q for PackageChown: %w", opts.PackageChown, err)
25                 }
26         }
27
28         exitcode := install.Command.RunCommand("arvados-server install", []string{
29                 "-type", "package",
30                 "-package-version", opts.PackageVersion,
31                 "-source", opts.SourceDir,
32         }, stdin, stdout, stderr)
33         if exitcode != 0 {
34                 return fmt.Errorf("arvados-server install failed: exit code %d", exitcode)
35         }
36
37         cmd := exec.Command("/var/lib/arvados/bin/gem", "install", "--user", "--no-document", "fpm")
38         cmd.Stdout = stdout
39         cmd.Stderr = stderr
40         err := cmd.Run()
41         if err != nil {
42                 return fmt.Errorf("gem install fpm: %w", err)
43         }
44
45         cmd = exec.Command("/var/lib/arvados/bin/gem", "env", "gempath")
46         cmd.Stderr = stderr
47         buf, err := cmd.Output() // /root/.gem/ruby/2.7.0:...
48         if err != nil || len(buf) == 0 {
49                 return fmt.Errorf("gem env gempath: %w", err)
50         }
51         gempath := string(bytes.TrimRight(bytes.Split(buf, []byte{':'})[0], "\n"))
52
53         if _, err := os.Stat(gempath + "/gems/fpm-1.11.0/lib/fpm/package/deb.rb"); err == nil {
54                 // Workaround for fpm bug https://github.com/jordansissel/fpm/issues/1739
55                 cmd = exec.Command("sed", "-i", `/require "digest"/a require "zlib"`, gempath+"/gems/fpm-1.11.0/lib/fpm/package/deb.rb")
56                 cmd.Stdout = stdout
57                 cmd.Stderr = stderr
58                 err = cmd.Run()
59                 if err != nil {
60                         return fmt.Errorf("monkeypatch fpm: %w", err)
61                 }
62         }
63
64         // Remove unneeded files. This is much faster than "fpm
65         // --exclude X" because fpm copies everything into a staging
66         // area before looking at the --exclude args.
67         cmd = exec.Command("bash", "-c", "cd /var/www/.gem/ruby && rm -rf */cache */bundler/gems/*/.git */bundler/gems/arvados-*/[^s]* */bundler/gems/arvados-*/s[^d]* */bundler/gems/arvados-*/sdk/[^cr]* */gems/passenger-*/src/cxx* ruby/*/gems/*/ext /var/lib/arvados/go /var/lib/arvados/arvados-workbench2 /var/lib/arvados/node-*")
68         cmd.Stdout = stdout
69         cmd.Stderr = stderr
70         err = cmd.Run()
71         if err != nil {
72                 return fmt.Errorf("%v: %w", cmd.Args, err)
73         }
74
75         format := "deb" // TODO: rpm
76         pkgfile := filepath.Join(opts.PackageDir, "arvados-server-easy_"+opts.PackageVersion+"_amd64."+format)
77
78         cmd = exec.Command(gempath+"/bin/fpm",
79                 "--package", pkgfile,
80                 "--name", "arvados-server-easy",
81                 "--version", opts.PackageVersion,
82                 "--url", "https://arvados.org",
83                 "--maintainer", opts.Maintainer,
84                 "--vendor", opts.Vendor,
85                 "--license", "GNU Affero General Public License, version 3.0",
86                 "--description", "platform for managing, processing, and sharing genomic and other large scientific and biomedical data",
87                 "--input-type", "dir",
88                 "--output-type", format)
89         deps, err := install.ProductionDependencies()
90         if err != nil {
91                 return err
92         }
93         for _, pkg := range deps {
94                 cmd.Args = append(cmd.Args, "--depends", pkg)
95         }
96         cmd.Args = append(cmd.Args,
97                 "--verbose",
98                 "--deb-use-file-permissions",
99                 "--rpm-use-file-permissions",
100                 "/etc/systemd/system/multi-user.target.wants/arvados.service",
101                 "/lib/systemd/system/arvados.service",
102                 "/usr/bin/arvados-client",
103                 "/usr/bin/arvados-server",
104                 "/var/lib/arvados",
105                 "/var/www/.gem",
106                 "/var/www/.passenger",
107                 "/var/www/.bundle",
108         )
109         fmt.Fprintf(stderr, "... %s\n", cmd.Args)
110         cmd.Dir = opts.PackageDir
111         cmd.Stdout = stdout
112         cmd.Stderr = stderr
113         err = cmd.Run()
114         if err != nil {
115                 return fmt.Errorf("fpm: %w", err)
116         }
117
118         if opts.PackageChown != "" {
119                 err = os.Chown(pkgfile, chownUid, chownGid)
120                 if err != nil {
121                         return fmt.Errorf("chown %s: %w", pkgfile, err)
122                 }
123         }
124
125         cmd = exec.Command("ls", "-l", pkgfile)
126         cmd.Stdout = stdout
127         cmd.Stderr = stderr
128         _ = cmd.Run()
129
130         return nil
131 }