Add codesign sign + verify

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
Leon Mika 2026-05-02 10:16:30 +10:00
parent eefce13a7c
commit 83904d8f8c
2 changed files with 88 additions and 0 deletions

41
internal/codesign/sign.go Normal file
View file

@ -0,0 +1,41 @@
package codesign
import (
"context"
"fmt"
"github.com/leonmika/wails-release/internal/runner"
)
// SignOpts configures a codesign invocation.
type SignOpts struct {
AppPath string
Identity string
KeychainPath string
}
// Sign runs `codesign` against a .app bundle, signing recursively with
// the hardened runtime and a secure timestamp.
func Sign(ctx context.Context, r runner.Runner, opts SignOpts) error {
args := []string{
"--deep", "--force", "--options", "runtime", "--timestamp",
"--sign", opts.Identity,
"--keychain", opts.KeychainPath,
opts.AppPath,
}
if _, err := r.Run(ctx, runner.Spec{Name: "codesign", Args: args}); err != nil {
return fmt.Errorf("codesign sign: %w", err)
}
return nil
}
// Verify runs `codesign --verify --deep --strict` against the bundle.
func Verify(ctx context.Context, r runner.Runner, appPath string) error {
if _, err := r.Run(ctx, runner.Spec{
Name: "codesign",
Args: []string{"--verify", "--deep", "--strict", appPath},
}); err != nil {
return fmt.Errorf("codesign verify: %w", err)
}
return nil
}

View file

@ -0,0 +1,47 @@
package codesign_test
import (
"context"
"reflect"
"testing"
"github.com/leonmika/wails-release/internal/codesign"
"github.com/leonmika/wails-release/internal/runner"
)
func TestSign_BuildsCorrectArgs(t *testing.T) {
f := &runner.Fake{}
f.On("codesign", nil).Return(nil, nil)
err := codesign.Sign(context.Background(), f, codesign.SignOpts{
AppPath: "/build/MyApp.app",
Identity: "Developer ID Application: Acme Inc (ABCD1234)",
KeychainPath: "/tmp/k",
})
if err != nil {
t.Fatalf("unexpected: %v", err)
}
want := []string{
"--deep", "--force", "--options", "runtime", "--timestamp",
"--sign", "Developer ID Application: Acme Inc (ABCD1234)",
"--keychain", "/tmp/k",
"/build/MyApp.app",
}
if !reflect.DeepEqual(f.Calls[0].Args, want) {
t.Fatalf("args got %v want %v", f.Calls[0].Args, want)
}
}
func TestVerify_BuildsCorrectArgs(t *testing.T) {
f := &runner.Fake{}
f.On("codesign", nil).Return(nil, nil)
err := codesign.Verify(context.Background(), f, "/build/MyApp.app")
if err != nil {
t.Fatalf("unexpected: %v", err)
}
want := []string{"--verify", "--deep", "--strict", "/build/MyApp.app"}
if !reflect.DeepEqual(f.Calls[0].Args, want) {
t.Fatalf("args got %v want %v", f.Calls[0].Args, want)
}
}