diff --git a/Makefile b/Makefile index 63a8c38..90398ba 100644 --- a/Makefile +++ b/Makefile @@ -56,6 +56,10 @@ KIND_CLUSTER_NAME ?= kind E2E_KIND_VERSION ?= kindest/node:v1.31.0 K8S_VERSION = $(E2E_KIND_VERSION:kindest/node:v%=%) +GIT_TAG ?= $(shell git describe --tags --dirty --always) +VERSION_PKG = sigs.k8s.io/kjob/pkg/version +LD_FLAGS += -X '$(VERSION_PKG).GitVersion=$(GIT_TAG)' + ##@ General # The help target prints out all targets with their descriptions organized diff --git a/docs/commands/kjobctl.md b/docs/commands/kjobctl.md index a449321..ae92aac 100644 --- a/docs/commands/kjobctl.md +++ b/docs/commands/kjobctl.md @@ -204,4 +204,5 @@ ML/AI/Batch Jobs Made Easy * [kjobctl describe](kjobctl_describe/_index.md) - Show details of a specific resource or group of resources. * [kjobctl list](kjobctl_list/_index.md) - Display resources * [kjobctl printcrds](kjobctl_printcrds/_index.md) - Print the kjobctl CRDs +* [kjobctl version](kjobctl_version/_index.md) - Prints the client version diff --git a/docs/commands/kjobctl_version/_index.md b/docs/commands/kjobctl_version/_index.md new file mode 100644 index 0000000..37efdd1 --- /dev/null +++ b/docs/commands/kjobctl_version/_index.md @@ -0,0 +1,227 @@ + + +# kjobctl version + + +## Synopsis + + +Prints the client version + +``` +kjobctl version +``` + + +## Examples + +``` + # Prints the client version + kjobctl version +``` + + +## Options + + + + + + + + + + + + + + + + +
-h, --help
+

help for version

+
+ + + +## Options inherited from parent commands + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
--as string
+

Username to impersonate for the operation. User could be a regular user or a service account in a namespace.

+
--as-group strings
+

Group to impersonate for the operation, this flag can be repeated to specify multiple groups.

+
--as-uid string
+

UID to impersonate for the operation.

+
--cache-dir string     Default: "$HOME/.kube/cache"
+

Default cache directory

+
--certificate-authority string
+

Path to a cert file for the certificate authority

+
--client-certificate string
+

Path to a client certificate file for TLS

+
--client-key string
+

Path to a client key file for TLS

+
--cluster string
+

The name of the kubeconfig cluster to use

+
--context string
+

The name of the kubeconfig context to use

+
--disable-compression
+

If true, opt-out of response compression for all requests to the server

+
--insecure-skip-tls-verify
+

If true, the server's certificate will not be checked for validity. This will make your HTTPS connections insecure

+
--kubeconfig string
+

Path to the kubeconfig file to use for CLI requests.

+
-n, --namespace string
+

If present, the namespace scope for this CLI request

+
--request-timeout string     Default: "0"
+

The length of time to wait before giving up on a single server request. Non-zero values should contain a corresponding time unit (e.g. 1s, 2m, 3h). A value of zero means don't timeout requests.

+
-s, --server string
+

The address and port of the Kubernetes API server

+
--tls-server-name string
+

Server name to use for server certificate validation. If it is not provided, the hostname used to contact the server is used

+
--token string
+

Bearer token for authentication to the API server

+
--user string
+

The name of the kubeconfig user to use

+
+ + + +## See Also + +* [kjobctl](../kjobctl.md) - ML/AI/Batch Jobs Made Easy + diff --git a/pkg/cmd/cmd.go b/pkg/cmd/cmd.go index 3e65975..20f9b6e 100644 --- a/pkg/cmd/cmd.go +++ b/pkg/cmd/cmd.go @@ -31,6 +31,7 @@ import ( "sigs.k8s.io/kjob/pkg/cmd/list" crds "sigs.k8s.io/kjob/pkg/cmd/printcrds" "sigs.k8s.io/kjob/pkg/cmd/util" + "sigs.k8s.io/kjob/pkg/cmd/version" ) type KjobctlOptions struct { @@ -82,6 +83,7 @@ func NewKjobctlCmd(o KjobctlOptions) *cobra.Command { cmd.AddCommand(list.NewListCmd(clientGetter, o.IOStreams, o.Clock)) cmd.AddCommand(deletecmd.NewDeleteCmd(clientGetter, o.IOStreams)) cmd.AddCommand(crds.NewCmd()) + cmd.AddCommand(version.NewVersionCmd(o.IOStreams)) return cmd } diff --git a/pkg/cmd/version/version.go b/pkg/cmd/version/version.go new file mode 100644 index 0000000..3f59e16 --- /dev/null +++ b/pkg/cmd/version/version.go @@ -0,0 +1,69 @@ +/* +Copyright 2025 The Kubernetes Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +package version + +import ( + "fmt" + + "github.com/spf13/cobra" + "k8s.io/cli-runtime/pkg/genericiooptions" + "k8s.io/kubectl/pkg/util/templates" + + "sigs.k8s.io/kjob/pkg/version" +) + +var ( + versionExample = templates.Examples(` + # Prints the client version + kjobctl version + `) +) + +// VersionOptions is a struct to support version command +type VersionOptions struct { + genericiooptions.IOStreams +} + +// NewOptions returns initialized Options +func NewOptions(streams genericiooptions.IOStreams) *VersionOptions { + return &VersionOptions{ + IOStreams: streams, + } +} + +// NewVersionCmd returns a new cobra.Command for fetching version +func NewVersionCmd(streams genericiooptions.IOStreams) *cobra.Command { + o := NewOptions(streams) + + cmd := &cobra.Command{ + Use: "version", + Short: "Prints the client version", + Example: versionExample, + Args: cobra.NoArgs, + DisableFlagsInUseLine: true, + Run: func(_ *cobra.Command, _ []string) { + o.Run() + }, + } + + return cmd +} + +// Run executes version command +func (o *VersionOptions) Run() { + fmt.Fprintf(o.Out, "Client Version: %s\n", version.GitVersion) +} diff --git a/pkg/cmd/version/version_test.go b/pkg/cmd/version/version_test.go new file mode 100644 index 0000000..1113574 --- /dev/null +++ b/pkg/cmd/version/version_test.go @@ -0,0 +1,50 @@ +/* +Copyright 2025 The Kubernetes Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +package version + +import ( + "testing" + + "github.com/google/go-cmp/cmp" + "github.com/google/go-cmp/cmp/cmpopts" + "k8s.io/cli-runtime/pkg/genericiooptions" +) + +func TestVersionCmd(t *testing.T) { + streams, _, out, outErr := genericiooptions.NewTestIOStreams() + + cmd := NewVersionCmd(streams) + cmd.SetArgs([]string{}) + + var wantErr error + gotErr := cmd.Execute() + if diff := cmp.Diff(wantErr, gotErr, cmpopts.EquateErrors()); diff != "" { + t.Errorf("Unexpected error (-want/+got)\n%s", diff) + } + + wantOut := "Client Version: v0.0.0-main\n" + gotOut := out.String() + if diff := cmp.Diff(wantOut, gotOut); diff != "" { + t.Errorf("Unexpected output (-want/+got)\n%s", diff) + } + + var wantOutErr string + gotOutErr := outErr.String() + if diff := cmp.Diff(wantOutErr, gotOutErr); diff != "" { + t.Errorf("Unexpected output (-want/+got)\n%s", diff) + } +} diff --git a/pkg/version/version.go b/pkg/version/version.go new file mode 100644 index 0000000..613964d --- /dev/null +++ b/pkg/version/version.go @@ -0,0 +1,28 @@ +/* +Copyright 2025 The Kubernetes Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +package version + +// GitVersion version information. +// +// This is the fallback data used when version information from git is not +// provided via go ldflags. +// +// If you are looking at these fields in the git tree, they look +// strange. They are modified on the fly by the build process. +var ( + GitVersion = "v0.0.0-main" +)