Skip to content

Commit 0762751

Browse files
authored
Merge pull request #9 from kycheng/publish-pakcgae
Publish pakcgae for chartmuseum2oci
2 parents c2025f8 + 4817399 commit 0762751

File tree

5 files changed

+331
-2
lines changed

5 files changed

+331
-2
lines changed

.github/workflows/ci.yml

Lines changed: 116 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,116 @@
1+
name: CI
2+
3+
on:
4+
push:
5+
branches: [ main, master, develop ]
6+
pull_request:
7+
branches: [ main, master, develop ]
8+
9+
env:
10+
GO_VERSION: '1.20'
11+
12+
jobs:
13+
test:
14+
name: Test
15+
runs-on: ubuntu-latest
16+
17+
steps:
18+
- name: Checkout code
19+
uses: actions/checkout@v4
20+
21+
- name: Set up Go
22+
uses: actions/setup-go@v4
23+
with:
24+
go-version: ${{ env.GO_VERSION }}
25+
26+
- name: Cache Go modules
27+
uses: actions/cache@v3
28+
with:
29+
path: ~/go/pkg/mod
30+
key: ${{ runner.os }}-go-${{ hashFiles('**/go.sum') }}
31+
restore-keys: |
32+
${{ runner.os }}-go-
33+
34+
- name: Download dependencies
35+
run: |
36+
cd chartmuseum2oci
37+
go mod download
38+
39+
- name: Verify dependencies
40+
run: |
41+
cd chartmuseum2oci
42+
go mod verify
43+
44+
- name: Run tests
45+
run: |
46+
cd chartmuseum2oci
47+
go test -v ./...
48+
49+
- name: Run linter
50+
uses: golangci/golangci-lint-action@v3
51+
with:
52+
version: latest
53+
working-directory: chartmuseum2oci
54+
args: --timeout=5m
55+
56+
build:
57+
name: Build
58+
runs-on: ${{ matrix.os }}
59+
needs: test
60+
strategy:
61+
matrix:
62+
include:
63+
- os: ubuntu-latest
64+
goos: linux
65+
goarch: amd64
66+
artifact_name: chartmuseum2oci-linux-amd64
67+
- os: ubuntu-latest
68+
goos: linux
69+
goarch: arm64
70+
artifact_name: chartmuseum2oci-linux-arm64
71+
- os: macos-latest
72+
goos: darwin
73+
goarch: amd64
74+
artifact_name: chartmuseum2oci-darwin-amd64
75+
- os: macos-latest
76+
goos: darwin
77+
goarch: arm64
78+
artifact_name: chartmuseum2oci-darwin-arm64
79+
80+
steps:
81+
- name: Checkout code
82+
uses: actions/checkout@v4
83+
84+
- name: Set up Go
85+
uses: actions/setup-go@v4
86+
with:
87+
go-version: ${{ env.GO_VERSION }}
88+
89+
- name: Get commit hash
90+
id: commit
91+
run: echo "commit=$(git rev-parse --short HEAD)" >> $GITHUB_OUTPUT
92+
93+
- name: Get build date
94+
id: build_date
95+
run: echo "build_date=$(date -u +%Y-%m-%dT%H:%M:%SZ)" >> $GITHUB_OUTPUT
96+
97+
- name: Build binary
98+
run: |
99+
cd chartmuseum2oci
100+
CGO_ENABLED=0 GOOS=${{ matrix.goos }} GOARCH=${{ matrix.goarch }} go build \
101+
-ldflags="-X main.version=dev \
102+
-X main.commit=${{ steps.commit.outputs.commit }} \
103+
-X main.buildDate=${{ steps.build_date.outputs.build_date }}" \
104+
-o ${{ matrix.artifact_name }} \
105+
main.go
106+
107+
- name: Test binary
108+
run: |
109+
cd chartmuseum2oci
110+
./${{ matrix.artifact_name }} --version
111+
112+
- name: Upload artifacts
113+
uses: actions/upload-artifact@v3
114+
with:
115+
name: ${{ matrix.artifact_name }}
116+
path: chartmuseum2oci/${{ matrix.artifact_name }}

.github/workflows/release.yml

Lines changed: 130 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,130 @@
1+
name: Release
2+
3+
on:
4+
push:
5+
tags:
6+
- 'v*'
7+
workflow_dispatch:
8+
inputs:
9+
version:
10+
description: 'Version to release (e.g., v1.0.0)'
11+
required: true
12+
type: string
13+
14+
env:
15+
GO_VERSION: '1.20'
16+
17+
jobs:
18+
build:
19+
name: Build
20+
runs-on: ${{ matrix.os }}
21+
strategy:
22+
matrix:
23+
include:
24+
- os: ubuntu-latest
25+
goos: linux
26+
goarch: amd64
27+
artifact_name: chartmuseum2oci-linux-amd64
28+
- os: ubuntu-latest
29+
goos: linux
30+
goarch: arm64
31+
artifact_name: chartmuseum2oci-linux-arm64
32+
- os: macos-latest
33+
goos: darwin
34+
goarch: amd64
35+
artifact_name: chartmuseum2oci-darwin-amd64
36+
- os: macos-latest
37+
goos: darwin
38+
goarch: arm64
39+
artifact_name: chartmuseum2oci-darwin-arm64
40+
41+
steps:
42+
- name: Checkout code
43+
uses: actions/checkout@v4
44+
with:
45+
fetch-depth: 0
46+
47+
- name: Set up Go
48+
uses: actions/setup-go@v4
49+
with:
50+
go-version: ${{ env.GO_VERSION }}
51+
52+
- name: Get version
53+
id: version
54+
run: |
55+
if [ "${{ github.event_name }}" = "workflow_dispatch" ]; then
56+
echo "version=${{ github.event.inputs.version }}" >> $GITHUB_OUTPUT
57+
else
58+
echo "version=${GITHUB_REF#refs/tags/}" >> $GITHUB_OUTPUT
59+
fi
60+
61+
- name: Get commit hash
62+
id: commit
63+
run: echo "commit=$(git rev-parse --short HEAD)" >> $GITHUB_OUTPUT
64+
65+
- name: Get build date
66+
id: build_date
67+
run: echo "build_date=$(date -u +%Y-%m-%dT%H:%M:%SZ)" >> $GITHUB_OUTPUT
68+
69+
- name: Build binary
70+
run: |
71+
cd chartmuseum2oci
72+
CGO_ENABLED=0 GOOS=${{ matrix.goos }} GOARCH=${{ matrix.goarch }} go build \
73+
-ldflags="-X main.version=${{ steps.version.outputs.version }} \
74+
-X main.commit=${{ steps.commit.outputs.commit }} \
75+
-X main.buildDate=${{ steps.build_date.outputs.build_date }}" \
76+
-o ${{ matrix.artifact_name }} \
77+
main.go
78+
79+
- name: Create checksum
80+
run: |
81+
cd chartmuseum2oci
82+
sha256sum ${{ matrix.artifact_name }} > ${{ matrix.artifact_name }}.sha256
83+
84+
- name: Upload artifacts
85+
uses: actions/upload-artifact@v3
86+
with:
87+
name: ${{ matrix.artifact_name }}
88+
path: |
89+
chartmuseum2oci/${{ matrix.artifact_name }}
90+
chartmuseum2oci/${{ matrix.artifact_name }}.sha256
91+
92+
release:
93+
name: Release
94+
needs: build
95+
runs-on: ubuntu-latest
96+
if: github.event_name == 'push' && startsWith(github.ref, 'refs/tags/')
97+
98+
steps:
99+
- name: Checkout code
100+
uses: actions/checkout@v4
101+
102+
- name: Get version
103+
id: version
104+
run: echo "version=${GITHUB_REF#refs/tags/}" >> $GITHUB_OUTPUT
105+
106+
- name: Download all artifacts
107+
uses: actions/download-artifact@v3
108+
109+
- name: Create release archive
110+
run: |
111+
mkdir -p release
112+
for artifact in chartmuseum2oci-*; do
113+
if [ -d "$artifact" ]; then
114+
cp "$artifact"/* release/
115+
fi
116+
done
117+
cd release
118+
tar -czf chartmuseum2oci-${{ steps.version.outputs.version }}-binaries.tar.gz chartmuseum2oci-*
119+
sha256sum chartmuseum2oci-${{ steps.version.outputs.version }}-binaries.tar.gz > chartmuseum2oci-${{ steps.version.outputs.version }}-binaries.tar.gz.sha256
120+
121+
- name: Create Release
122+
uses: softprops/action-gh-release@v1
123+
with:
124+
files: |
125+
release/chartmuseum2oci-*
126+
release/chartmuseum2oci-${{ steps.version.outputs.version }}-binaries.tar.gz
127+
release/chartmuseum2oci-${{ steps.version.outputs.version }}-binaries.tar.gz.sha256
128+
generate_release_notes: true
129+
env:
130+
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}

chartmuseum2oci/go.mod

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ go 1.20
55
require (
66
github.com/goharbor/go-client v0.26.2
77
github.com/pkg/errors v0.9.1
8+
github.com/rogpeppe/go-internal v1.3.0
89
github.com/schollz/progressbar/v3 v3.13.1
910
)
1011

chartmuseum2oci/go.sum

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -219,6 +219,7 @@ github.com/rivo/uniseg v0.2.0 h1:S1pD9weZBuJdFmowNwbpi7BJ8TNftyUImj/0WQi72jY=
219219
github.com/rivo/uniseg v0.2.0/go.mod h1:J6wj4VEh+S6ZtnVlnTBMWIodfgj8LQOQFoIToxlJtxc=
220220
github.com/rogpeppe/go-internal v1.1.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
221221
github.com/rogpeppe/go-internal v1.2.2/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
222+
github.com/rogpeppe/go-internal v1.3.0 h1:RR9dF3JtopPvtkroDZuVD7qquD0bnHlKSqaQhgwt8yk=
222223
github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
223224
github.com/schollz/progressbar/v3 v3.13.1 h1:o8rySDYiQ59Mwzy2FELeHY5ZARXZTVJC7iHD6PEFUiE=
224225
github.com/schollz/progressbar/v3 v3.13.1/go.mod h1:xvrbki8kfT1fzWzBT/UZd9L6GA+jdL7HAgq2RFnO6fQ=

chartmuseum2oci/main.go

Lines changed: 83 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ import (
1111
"net/url"
1212
"os"
1313
"os/exec"
14+
"strings"
1415
"time"
1516

1617
"github.com/goharbor/go-client/pkg/harbor"
@@ -19,6 +20,7 @@ import (
1920
"github.com/goharbor/go-client/pkg/sdk/v2.0/client"
2021
"github.com/goharbor/go-client/pkg/sdk/v2.0/client/project"
2122
"github.com/pkg/errors"
23+
"github.com/rogpeppe/go-internal/semver"
2224
"github.com/schollz/progressbar/v3"
2325
)
2426

@@ -39,6 +41,8 @@ const (
3941
helmBinaryPath = "helm"
4042
timeout = 5 * time.Second
4143
defaultPageSize = 10
44+
// Define minimum required version
45+
helmMinVersion = "v3.19.0"
4246
)
4347

4448
var (
@@ -52,8 +56,14 @@ var (
5256
destPath string //nolint:gochecknoglobals
5357
projectsToMigrate ProjectsToMigrateList //nolint:gochecknoglobals
5458

55-
insecure bool //nolint:gochecknoglobals
56-
plainHttp bool //nolint:gochecknoglobals
59+
insecure bool //nolint:gochecknoglobals
60+
plainHttp bool //nolint:gochecknoglobals
61+
showVersion bool //nolint:gochecknoglobals
62+
63+
// Version information set during build
64+
version = "dev"
65+
commit = "unknown"
66+
buildDate = "unknown"
5767
)
5868

5969
func init() { //nolint:gochecknoinits
@@ -70,8 +80,16 @@ func initFlags() {
7080
flag.Var(&projectsToMigrate, "project", "Name of the project(s) to migrate")
7181
flag.BoolVar(&insecure, "insecure", false, "Skip TLS verification for helm operations")
7282
flag.BoolVar(&plainHttp, "plain-http", false, "Use plain HTTP for helm operations")
83+
flag.BoolVar(&showVersion, "version", false, "Show version information")
7384
flag.Parse()
7485

86+
if showVersion {
87+
fmt.Printf("chartmuseum2oci version %s\n", version)
88+
fmt.Printf("commit: %s\n", commit)
89+
fmt.Printf("build date: %s\n", buildDate)
90+
os.Exit(0)
91+
}
92+
7593
if harborURL == "" {
7694
log.Fatal(errors.New("Missing required --url flag"))
7795
}
@@ -117,7 +135,70 @@ func initHarborHost() {
117135
harborHost = u.Host
118136
}
119137

138+
// checkHelmVersion checks if Helm version meets the minimum requirement
139+
140+
func checkHelmVersion() error {
141+
cmd := exec.Command(helmBinaryPath, "version", "--short") //nolint:gosec
142+
143+
var stdOut, stdErr bytes.Buffer
144+
cmd.Stdout = &stdOut
145+
cmd.Stderr = &stdErr
146+
147+
if err := cmd.Run(); err != nil {
148+
return errors.Wrapf(err, "fail to execute helm version command: %s", stdErr.String())
149+
}
150+
151+
versionOutput := strings.TrimSpace(stdOut.String())
152+
153+
// Extract version from output like "v3.19.0+gce43812"
154+
versionStr := extractVersionFromOutput(versionOutput)
155+
if versionStr == "" {
156+
return errors.Errorf("unable to extract version from Helm output: %s", versionOutput)
157+
}
158+
159+
// Validate version format using semver library
160+
if !semver.IsValid("v" + versionStr) {
161+
return errors.Errorf("invalid Helm version format: %s", versionStr)
162+
}
163+
164+
// Check if version meets minimum requirement
165+
if semver.Compare("v"+versionStr, minVersion) < 0 {
166+
return errors.Errorf("Helm version %s is too old, requires version >= %s", versionStr, minVersion)
167+
}
168+
169+
log.Printf("Helm version check passed: %s", versionStr)
170+
return nil
171+
}
172+
173+
// extractVersionFromOutput extracts version string from Helm version output
174+
func extractVersionFromOutput(output string) string {
175+
// Handle different Helm version output formats:
176+
// - "v3.19.0+gce43812" (with git commit)
177+
// - "v3.19.0" (without git commit)
178+
// - "3.19.0" (without 'v' prefix)
179+
180+
// Remove 'v' prefix if present
181+
version := strings.TrimPrefix(output, "v")
182+
183+
// Find the first '+' or end of string to get clean version
184+
if plusIndex := strings.Index(version, "+"); plusIndex != -1 {
185+
version = version[:plusIndex]
186+
}
187+
188+
// Validate that it looks like a semantic version
189+
parts := strings.Split(version, ".")
190+
if len(parts) != 3 {
191+
return ""
192+
}
193+
194+
return version
195+
}
196+
120197
func main() {
198+
if err := checkHelmVersion(); err != nil {
199+
log.Fatal(errors.Wrapf(err, "fail to check Helm version"))
200+
}
201+
121202
if err := helmLogin(); err != nil {
122203
log.Fatal(errors.Wrapf(err, "fail to login to Helm"))
123204
}

0 commit comments

Comments
 (0)