Co-authored-by: Claude <developers@lethean.io> Co-committed-by: Claude <developers@lethean.io>
149 lines
4.4 KiB
Go
149 lines
4.4 KiB
Go
package builders
|
|
|
|
import (
|
|
"os"
|
|
"path/filepath"
|
|
"testing"
|
|
|
|
"github.com/host-uk/core/pkg/build"
|
|
"github.com/host-uk/core/pkg/io"
|
|
"github.com/stretchr/testify/assert"
|
|
"github.com/stretchr/testify/require"
|
|
)
|
|
|
|
func TestCPPBuilder_Name_Good(t *testing.T) {
|
|
builder := NewCPPBuilder()
|
|
assert.Equal(t, "cpp", builder.Name())
|
|
}
|
|
|
|
func TestCPPBuilder_Detect_Good(t *testing.T) {
|
|
fs := io.Local
|
|
|
|
t.Run("detects C++ project with CMakeLists.txt", func(t *testing.T) {
|
|
dir := t.TempDir()
|
|
err := os.WriteFile(filepath.Join(dir, "CMakeLists.txt"), []byte("cmake_minimum_required(VERSION 3.16)"), 0644)
|
|
require.NoError(t, err)
|
|
|
|
builder := NewCPPBuilder()
|
|
detected, err := builder.Detect(fs, dir)
|
|
assert.NoError(t, err)
|
|
assert.True(t, detected)
|
|
})
|
|
|
|
t.Run("returns false for non-C++ project", func(t *testing.T) {
|
|
dir := t.TempDir()
|
|
err := os.WriteFile(filepath.Join(dir, "go.mod"), []byte("module test"), 0644)
|
|
require.NoError(t, err)
|
|
|
|
builder := NewCPPBuilder()
|
|
detected, err := builder.Detect(fs, dir)
|
|
assert.NoError(t, err)
|
|
assert.False(t, detected)
|
|
})
|
|
|
|
t.Run("returns false for empty directory", func(t *testing.T) {
|
|
dir := t.TempDir()
|
|
|
|
builder := NewCPPBuilder()
|
|
detected, err := builder.Detect(fs, dir)
|
|
assert.NoError(t, err)
|
|
assert.False(t, detected)
|
|
})
|
|
}
|
|
|
|
func TestCPPBuilder_Build_Bad(t *testing.T) {
|
|
t.Run("returns error for nil config", func(t *testing.T) {
|
|
builder := NewCPPBuilder()
|
|
artifacts, err := builder.Build(nil, nil, []build.Target{{OS: "linux", Arch: "amd64"}})
|
|
assert.Error(t, err)
|
|
assert.Nil(t, artifacts)
|
|
assert.Contains(t, err.Error(), "config is nil")
|
|
})
|
|
}
|
|
|
|
func TestCPPBuilder_TargetToProfile_Good(t *testing.T) {
|
|
builder := NewCPPBuilder()
|
|
|
|
tests := []struct {
|
|
os, arch string
|
|
expected string
|
|
}{
|
|
{"linux", "amd64", "gcc-linux-x86_64"},
|
|
{"linux", "x86_64", "gcc-linux-x86_64"},
|
|
{"linux", "arm64", "gcc-linux-armv8"},
|
|
{"darwin", "arm64", "apple-clang-armv8"},
|
|
{"darwin", "amd64", "apple-clang-x86_64"},
|
|
{"windows", "amd64", "msvc-194-x86_64"},
|
|
}
|
|
|
|
for _, tt := range tests {
|
|
t.Run(tt.os+"/"+tt.arch, func(t *testing.T) {
|
|
profile := builder.targetToProfile(build.Target{OS: tt.os, Arch: tt.arch})
|
|
assert.Equal(t, tt.expected, profile)
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestCPPBuilder_TargetToProfile_Bad(t *testing.T) {
|
|
builder := NewCPPBuilder()
|
|
|
|
t.Run("returns empty for unknown target", func(t *testing.T) {
|
|
profile := builder.targetToProfile(build.Target{OS: "plan9", Arch: "mips"})
|
|
assert.Empty(t, profile)
|
|
})
|
|
}
|
|
|
|
func TestCPPBuilder_FindArtifacts_Good(t *testing.T) {
|
|
fs := io.Local
|
|
|
|
t.Run("finds packages in build/packages", func(t *testing.T) {
|
|
dir := t.TempDir()
|
|
packagesDir := filepath.Join(dir, "build", "packages")
|
|
require.NoError(t, os.MkdirAll(packagesDir, 0755))
|
|
|
|
// Create mock package files
|
|
require.NoError(t, os.WriteFile(filepath.Join(packagesDir, "test-1.0-linux-x86_64.tar.xz"), []byte("pkg"), 0644))
|
|
require.NoError(t, os.WriteFile(filepath.Join(packagesDir, "test-1.0-linux-x86_64.tar.xz.sha256"), []byte("checksum"), 0644))
|
|
require.NoError(t, os.WriteFile(filepath.Join(packagesDir, "test-1.0-linux-x86_64.rpm"), []byte("rpm"), 0644))
|
|
|
|
builder := NewCPPBuilder()
|
|
target := build.Target{OS: "linux", Arch: "amd64"}
|
|
artifacts, err := builder.findArtifacts(fs, dir, target)
|
|
require.NoError(t, err)
|
|
|
|
// Should find tar.xz and rpm but not sha256
|
|
assert.Len(t, artifacts, 2)
|
|
for _, a := range artifacts {
|
|
assert.Equal(t, "linux", a.OS)
|
|
assert.Equal(t, "amd64", a.Arch)
|
|
assert.False(t, filepath.Ext(a.Path) == ".sha256")
|
|
}
|
|
})
|
|
|
|
t.Run("falls back to binaries in build/release/src", func(t *testing.T) {
|
|
dir := t.TempDir()
|
|
binDir := filepath.Join(dir, "build", "release", "src")
|
|
require.NoError(t, os.MkdirAll(binDir, 0755))
|
|
|
|
// Create mock binary (executable)
|
|
binPath := filepath.Join(binDir, "test-daemon")
|
|
require.NoError(t, os.WriteFile(binPath, []byte("binary"), 0755))
|
|
|
|
// Create a library (should be skipped)
|
|
require.NoError(t, os.WriteFile(filepath.Join(binDir, "libcrypto.a"), []byte("lib"), 0644))
|
|
|
|
builder := NewCPPBuilder()
|
|
target := build.Target{OS: "linux", Arch: "amd64"}
|
|
artifacts, err := builder.findArtifacts(fs, dir, target)
|
|
require.NoError(t, err)
|
|
|
|
// Should find the executable but not the library
|
|
assert.Len(t, artifacts, 1)
|
|
assert.Contains(t, artifacts[0].Path, "test-daemon")
|
|
})
|
|
}
|
|
|
|
func TestCPPBuilder_Interface_Good(t *testing.T) {
|
|
var _ build.Builder = (*CPPBuilder)(nil)
|
|
var _ build.Builder = NewCPPBuilder()
|
|
}
|