fleet/orbit/pkg/packaging/macos_notarize.go

90 lines
2.0 KiB
Go

package packaging
import (
"context"
"errors"
"fmt"
"os"
"sync"
"github.com/fatih/color"
"github.com/mitchellh/gon/notarize"
"github.com/mitchellh/gon/staple"
"github.com/rs/zerolog/log"
)
func notarizePkg(pkgPath string) error {
username, ok := os.LookupEnv("AC_USERNAME")
if !ok {
return errors.New("AC_USERNAME must be set in environment")
}
password, ok := os.LookupEnv("AC_PASSWORD")
if !ok {
return errors.New("AC_PASSWORD must be set in environment")
}
info, err := notarize.Notarize(
context.Background(),
&notarize.Options{
File: pkgPath,
BundleId: "com.fleetdm.orbit",
Username: username,
Password: password,
Status: &statusHuman{
Lock: &sync.Mutex{},
},
},
)
if err != nil {
return fmt.Errorf("notarize: %w", err)
}
log.Info().Str("logs", info.LogFileURL).Msg("notarization completed")
if err := staple.Staple(context.Background(), &staple.Options{File: pkgPath}); err != nil {
return fmt.Errorf("staple notarization: %w", err)
}
return nil
}
// This status plugin copied from
// https://github.com/mitchellh/gon/blob/v0.2.3/cmd/gon/status_human.go since it
// is not exposed from the gon library.
// statusHuman implements notarize.Status and outputs information to
// the CLI for human consumption.
type statusHuman struct {
Prefix string
Lock *sync.Mutex
lastStatus string
}
func (s *statusHuman) Submitting() {
s.Lock.Lock()
defer s.Lock.Unlock()
color.New().Fprintf(os.Stdout, " %sSubmitting file for notarization...\n", s.Prefix)
}
func (s *statusHuman) Submitted(uuid string) {
s.Lock.Lock()
defer s.Lock.Unlock()
color.New().Fprintf(os.Stdout, " %sSubmitted. Request UUID: %s\n", s.Prefix, uuid)
color.New().Fprintf(
os.Stdout, " %sWaiting for results from Apple. This can take minutes to hours.\n", s.Prefix)
}
func (s *statusHuman) Status(info notarize.Info) {
s.Lock.Lock()
defer s.Lock.Unlock()
if info.Status != s.lastStatus {
s.lastStatus = info.Status
color.New().Fprintf(os.Stdout, " %sStatus: %s\n", s.Prefix, info.Status)
}
}