scripts/release_version_test.go
Rama main · réplica de lectura del repositorio original.
package scripts
import (
"os"
"os/exec"
"path/filepath"
"strings"
"testing"
"github.com/stretchr/testify/require"
"github.com/usememos/memos/internal/version"
)
func TestDevelopmentVersion(t *testing.T) {
original := version.Version
t.Cleanup(func() { version.Version = original })
for _, tc := range []struct{ date, version string }{
{"2026-09-27T14:58:52Z", "26.09.27"},
{"2026-10-01T00:30:00+08:00", "26.09.30"},
{"2026-12-31T23:30:00-08:00", "27.01.1"},
} {
t.Run(tc.date, func(t *testing.T) {
repo := t.TempDir()
runGit := func(args ...string) {
t.Helper()
cmd := exec.Command("git", append([]string{"-C", repo, "-c", "user.name=Version Test", "-c", "user.email=test@example.com", "-c", "commit.gpgsign=false"}, args...)...)
cmd.Env = append(os.Environ(), "GIT_AUTHOR_DATE=2020-01-01T00:00:00Z", "GIT_COMMITTER_DATE="+tc.date)
out, err := cmd.CombinedOutput()
require.NoError(t, err, string(out))
}
check := func(repo string) {
t.Helper()
sha, err := exec.Command("git", "-C", repo, "rev-parse", "HEAD").Output()
require.NoError(t, err)
cmd := exec.Command("bash", "release_version.sh", "development-version", repo)
cmd.Env = append(os.Environ(), "TZ=Pacific/Honolulu")
out, err := cmd.CombinedOutput()
require.NoError(t, err, string(out))
want := tc.version + "-dev." + strings.TrimSpace(string(sha))[:7] + "\n"
require.Equal(t, want, string(out))
// The script and the binary must name the same development build.
version.Version = strings.TrimSpace(string(out))
require.NoError(t, version.Validate())
}
runGit("init", "-b", "main")
runGit("commit", "--allow-empty", "-m", "source")
runGit("tag", "26.10.1")
check(repo)
require.NoError(t, os.WriteFile(filepath.Join(repo, "uncommitted"), []byte("local change"), 0o600))
check(repo)
shallow := filepath.Join(t.TempDir(), "shallow")
out, err := exec.Command("git", "clone", "--depth=1", "file://"+repo, shallow).CombinedOutput()
require.NoError(t, err, string(out))
check(shallow)
})
}
t.Run("no Git metadata", func(t *testing.T) {
out, err := exec.Command("bash", "release_version.sh", "development-version", t.TempDir()).CombinedOutput()
require.Error(t, err, string(out))
})
}
func TestReleaseVersions(t *testing.T) {
for _, tc := range []struct {
tag, series, prerelease, images string
}{
{"26.09.0", "26.09", "false", "26.09.0\n26.09\nstable\n"},
{"26.09.1", "26.09", "false", "26.09.1\n26.09\nstable\n"},
{"26.09.10", "26.09", "false", "26.09.10\n26.09\nstable\n"},
{"26.10.1", "26.10", "false", "26.10.1\n26.10\nstable\n"},
{"27.01.0", "27.01", "false", "27.01.0\n27.01\nstable\n"},
{"26.09.0-rc.1", "26.09", "true", "26.09.0-rc.1\n"},
{"26.09.1-rc.2", "26.09", "true", "26.09.1-rc.2\n"},
} {
t.Run(tc.tag, func(t *testing.T) {
out, err := exec.Command("bash", "release_version.sh", "version", tc.tag).CombinedOutput()
require.NoError(t, err, string(out))
require.Equal(t, "tag="+tc.tag+"\nversion="+tc.tag+"\nseries="+tc.series+"\nis_prerelease="+tc.prerelease+"\n", string(out))
out, err = exec.Command("bash", "release_version.sh", "image-tags", tc.tag).CombinedOutput()
require.NoError(t, err, string(out))
require.Equal(t, tc.images, string(out))
})
}
for _, tag := range []string{
"v0.31.0", "v26.09.0", "v26.09.1", "v26.09.0-rc.1", "26.09", "26.09-rc.1", "26.9.0", "26.00.0", "26.13.0", "2026.09.0",
"26.09.01", "26.09.0-rc.0", "26.09.0-rc.01", "26.09.0beta", "26.09.1+build", "26.09.1-dev.abc1234",
} {
out, err := exec.Command("bash", "release_version.sh", "version", tag).CombinedOutput()
require.Error(t, err, tag)
require.Contains(t, string(out), "Unsupported release tag")
}
}
// The script and the binary must accept the same release tags, or a tag could
// build a binary that refuses to start. Development versions are binary-only.
func TestReleaseTagsMatchBinaryVersions(t *testing.T) {
original := version.Version
t.Cleanup(func() { version.Version = original })
for _, tag := range []string{
"26.09.0", "26.09.1", "26.09.10", "27.01.0", "26.09.0-rc.1", "26.09.1-rc.2",
"v26.09.0", "0.31.0", "26.09", "26.9.0", "26.00.0", "26.13.0", "2026.09.0", "26.09.01", "26.09-rc.1", "26.09.0-rc.0", "26.09.0-rc.01",
"26.09.1-dev.1", "26.09.1-dirty", "26.09.0beta", "26.09.1+build", "dev",
} {
scriptErr := exec.Command("bash", "release_version.sh", "version", tag).Run()
version.Version = tag
require.Equal(t, scriptErr == nil, version.Validate() == nil, tag)
}
version.Version = "26.09.1-dev.abc1234"
require.NoError(t, version.Validate())
require.Error(t, exec.Command("bash", "release_version.sh", "version", version.Version).Run())
}
func TestPreviousReleaseImage(t *testing.T) {
repo := t.TempDir()
runGit := func(args ...string) {
t.Helper()
cmd := exec.Command("git", append([]string{"-C", repo, "-c", "user.name=Release Test", "-c", "user.email=test@example.com", "-c", "commit.gpgsign=false"}, args...)...)
out, err := cmd.CombinedOutput()
require.NoError(t, err, string(out))
}
check := func(want string) {
t.Helper()
out, err := exec.Command("bash", "release_version.sh", "previous-tag", repo).CombinedOutput()
require.NoError(t, err, string(out))
require.Equal(t, want+"\n", string(out))
out, err = exec.Command("bash", "release_version.sh", "previous-image", repo).CombinedOutput()
require.NoError(t, err, string(out))
require.Equal(t, "neosmemo/memos:"+strings.TrimPrefix(want, "v")+"\n", string(out))
}
runGit("init", "-b", "main")
runGit("commit", "--allow-empty", "-m", "old")
runGit("tag", "v0.30.0")
runGit("commit", "--allow-empty", "-m", "baseline")
runGit("tag", "v0.31.0")
runGit("commit", "--allow-empty", "-m", "first calendar release")
runGit("tag", "26.09.0")
check("v0.31.0")
runGit("commit", "--allow-empty", "-m", "point release")
runGit("tag", "26.09.2")
check("26.09.0")
runGit("commit", "--allow-empty", "-m", "tenth point release")
runGit("tag", "26.09.10")
// Two-part tags are image aliases, never releases.
runGit("tag", "99.99")
runGit("commit", "--allow-empty", "-m", "release candidate")
runGit("tag", "26.10.0-rc.1")
check("26.09.10")
runGit("commit", "--allow-empty", "-m", "after release candidate")
check("26.09.10")
runGit("checkout", "--orphan", "unrelated")
runGit("commit", "--allow-empty", "-m", "unrelated release")
runGit("tag", "29.01.0")
runGit("checkout", "main")
check("26.09.10")
runGit("tag", "26.10.0")
runGit("commit", "--allow-empty", "-m", "next year")
runGit("tag", "27.01.0")
check("26.10.0")
// The floor excludes pre-baseline tags even if no supported release exists.
repo = t.TempDir()
runGit("init", "-b", "main")
runGit("commit", "--allow-empty", "-m", "old")
runGit("tag", "v0.30.0")
runGit("commit", "--allow-empty", "-m", "candidate")
for _, command := range []string{"previous-tag", "previous-image"} {
out, err := exec.Command("bash", "release_version.sh", command, repo).CombinedOutput()
require.Error(t, err, command)
require.Contains(t, string(out), "No supported previous release found")
}
}