2024-04-10 04:49:36 +02:00
// Katenary CLI, main package.
//
// This package is not intended to be imported. It contains the
// main function that build the command line with `cobra` package.
2022-03-31 14:12:20 +02:00
package main
2022-02-14 17:00:32 +01:00
import (
"fmt"
2025-06-04 14:29:13 +02:00
"log"
2023-12-06 15:24:02 +01:00
"os"
"strings"
2022-02-14 17:00:32 +01:00
2025-08-19 23:58:51 +02:00
"katenary.io/internal/generator"
"katenary.io/internal/generator/katenaryfile"
"katenary.io/internal/generator/labels"
"katenary.io/internal/utils"
2025-08-03 15:54:58 +02:00
2023-12-06 15:24:02 +01:00
"github.com/compose-spec/compose-go/cli"
2022-03-31 14:12:20 +02:00
"github.com/spf13/cobra"
2022-02-14 17:15:11 +01:00
)
2022-02-14 17:00:32 +01:00
2023-12-06 15:24:02 +01:00
const longHelp = ` Katenary is a tool to convert compose files to Helm Charts .
2022-02-14 17:00:32 +01:00
2023-12-06 15:24:02 +01:00
Each [ command ] and subcommand has got an "help" and "--help" flag to show more information .
2022-03-31 14:12:20 +02:00
`
2022-02-14 17:00:32 +01:00
2022-03-31 14:12:20 +02:00
func main ( ) {
2024-04-24 20:55:27 +02:00
rootCmd := buildRootCmd ( )
2025-06-04 14:29:13 +02:00
if err := rootCmd . Execute ( ) ; err != nil {
log . Fatal ( err )
}
2024-04-24 20:55:27 +02:00
}
func buildRootCmd ( ) * cobra . Command {
2022-03-31 14:12:20 +02:00
rootCmd := & cobra . Command {
Use : "katenary" ,
Long : longHelp ,
Short : "Katenary is a tool to convert docker-compose files to Helm Charts" ,
2022-02-14 17:00:32 +01:00
}
2023-12-06 15:24:02 +01:00
rootCmd . Example = ` katenary convert -c docker-compose.yml -o ./charts `
2022-02-14 17:00:32 +01:00
2024-11-26 16:47:37 +01:00
rootCmd . Version = generator . GetVersion ( )
2023-12-06 15:24:02 +01:00
rootCmd . CompletionOptions . DisableDescriptions = false
rootCmd . CompletionOptions . DisableNoDescFlag = false
rootCmd . AddCommand (
generateCompletionCommand ( rootCmd . Name ( ) ) ,
generateVersionCommand ( ) ,
generateConvertCommand ( ) ,
generateHashComposefilesCommand ( ) ,
generateLabelHelpCommand ( ) ,
2024-11-18 17:12:12 +01:00
generateSchemaCommand ( ) ,
2023-12-06 15:24:02 +01:00
)
2024-04-24 20:55:27 +02:00
return rootCmd
2023-12-06 15:24:02 +01:00
}
const completionHelp = ` To load completions :
Bash :
# Add this line in your ~ / . bashrc or ~ / . bash_profile file
$ source < ( % [ 1 ] s completion bash )
# Or , you can load completions for each users session . Execute once :
# Linux :
$ % [ 1 ] s completion bash > / etc / bash_completion . d / % [ 1 ] s
# macOS :
$ % [ 1 ] s completion bash > $ ( brew -- prefix ) / etc / bash_completion . d / % [ 1 ] s
Zsh :
# If shell completion is not already enabled in your environment ,
# you will need to enable it . You can execute the following once :
$ echo "autoload -U compinit; compinit" >> ~ / . zshrc
# To load completions for each session , execute once :
$ % [ 1 ] s completion zsh > "${fpath[1]}/_%[1]s"
# You will need to start a new shell for this setup to take effect .
fish :
$ % [ 1 ] s completion fish | source
# To load completions for each session , execute once :
$ % [ 1 ] s completion fish > ~ / . config / fish / completions / % [ 1 ] s . fish
PowerShell :
PS > % [ 1 ] s completion powershell | Out - String | Invoke - Expression
# To load completions for every new session , run :
PS > % [ 1 ] s completion powershell > % [ 1 ] s . ps1
# and source this file from your PowerShell profile .
`
func generateCompletionCommand ( name string ) * cobra . Command {
bashV1 := false
cmd := & cobra . Command {
Use : "completion" ,
DisableFlagsInUseLine : true ,
ValidArgs : [ ] string { "bash" , "zsh" , "fish" , "powershell" } ,
Args : cobra . MatchAll ( cobra . ExactArgs ( 1 ) , cobra . OnlyValidArgs ) ,
Short : "Generates completion scripts" ,
Long : fmt . Sprintf ( completionHelp , name ) ,
2025-06-04 14:29:13 +02:00
RunE : func ( cmd * cobra . Command , args [ ] string ) error {
2023-12-06 15:24:02 +01:00
if len ( args ) == 0 {
2025-06-04 14:29:13 +02:00
return cmd . Help ( )
2023-12-06 15:24:02 +01:00
}
switch args [ 0 ] {
case "bash" :
// get the bash version
if cmd . Flags ( ) . Changed ( "bash-v1" ) {
2025-06-04 14:29:13 +02:00
return cmd . Root ( ) . GenBashCompletion ( os . Stdout )
2023-12-06 15:24:02 +01:00
}
2025-06-04 14:29:13 +02:00
return cmd . Root ( ) . GenBashCompletionV2 ( os . Stdout , true )
2023-12-06 15:24:02 +01:00
case "zsh" :
2025-06-04 14:29:13 +02:00
return cmd . Root ( ) . GenZshCompletion ( os . Stdout )
2023-12-06 15:24:02 +01:00
case "fish" :
2025-06-04 14:29:13 +02:00
return cmd . Root ( ) . GenFishCompletion ( os . Stdout , true )
2023-12-06 15:24:02 +01:00
case "powershell" :
2025-06-04 14:29:13 +02:00
return cmd . Root ( ) . GenPowerShellCompletion ( os . Stdout )
2023-12-06 15:24:02 +01:00
}
2025-06-04 14:29:13 +02:00
return fmt . Errorf ( "unknown completion type: %s" , args [ 0 ] )
2023-12-06 15:24:02 +01:00
} ,
2022-02-14 17:00:32 +01:00
}
2023-12-06 15:24:02 +01:00
// add a flag to force bash completion v1
cmd . Flags ( ) . Bool ( "bash-v1" , bashV1 , "Force bash completion v1" )
return cmd
}
func generateConvertCommand ( ) * cobra . Command {
force := false
outputDir := "./chart"
dockerComposeFile := make ( [ ] string , 0 )
profiles := make ( [ ] string , 0 )
helmdepUpdate := false
var appVersion * string
givenAppVersion := ""
chartVersion := "0.1.0"
2024-10-17 17:08:42 +02:00
icon := ""
envFiles := [ ] string { }
2023-12-06 15:24:02 +01:00
2022-03-31 14:12:20 +02:00
convertCmd := & cobra . Command {
Use : "convert" ,
2023-12-06 15:24:02 +01:00
Short : "Converts a docker-compose file to a Helm Chart" ,
2024-12-03 14:37:13 +01:00
RunE : func ( cmd * cobra . Command , args [ ] string ) error {
2025-07-06 10:53:18 +02:00
if len ( strings . TrimSpace ( givenAppVersion ) ) > 0 {
2023-12-06 15:24:02 +01:00
appVersion = & givenAppVersion
2022-02-14 17:00:32 +01:00
}
2024-12-03 14:37:13 +01:00
return generator . Convert ( generator . ConvertOptions {
2023-12-06 15:24:02 +01:00
Force : force ,
OutputDir : outputDir ,
Profiles : profiles ,
HelmUpdate : helmdepUpdate ,
AppVersion : appVersion ,
ChartVersion : chartVersion ,
2024-10-17 17:08:42 +02:00
Icon : icon ,
EnvFiles : envFiles ,
2023-12-06 15:24:02 +01:00
} , dockerComposeFile ... )
2022-03-31 14:12:20 +02:00
} ,
}
2023-12-06 15:24:02 +01:00
2024-10-17 17:08:42 +02:00
convertCmd . Flags ( ) . BoolVarP (
& force ,
"force" ,
"f" ,
force ,
"Force the overwrite of the chart directory" ,
)
convertCmd . Flags ( ) . BoolVarP (
& helmdepUpdate ,
"helm-update" ,
"u" ,
helmdepUpdate ,
"Update helm dependencies if helm is installed" ,
)
convertCmd . Flags ( ) . StringSliceVarP (
& profiles ,
"profile" ,
"p" ,
profiles ,
"Specify the profiles to use" ,
)
convertCmd . Flags ( ) . StringVarP (
& outputDir ,
"output-dir" ,
"o" ,
outputDir ,
"Specify the output directory" ,
)
convertCmd . Flags ( ) . StringSliceVarP (
& dockerComposeFile ,
"compose-file" ,
"c" ,
cli . DefaultFileNames ,
"Specify an alternate compose files - can be specified multiple times or use coma to separate them.\n" +
"Note that overides files are also used whatever the files you specify here.\nThe overides files are:\n" +
strings . Join ( cli . DefaultOverrideFileNames , ", \n" ) +
"\n" ,
)
convertCmd . Flags ( ) . StringVarP (
& givenAppVersion ,
"app-version" ,
"a" ,
"" ,
"Specify the app version (in Chart.yaml)" ,
)
convertCmd . Flags ( ) . StringVarP (
& chartVersion ,
"chart-version" ,
"v" ,
chartVersion ,
"Specify the chart version (in Chart.yaml)" ,
)
convertCmd . Flags ( ) . StringVarP (
& icon ,
"icon" ,
"i" ,
"" ,
"Specify the icon (in Chart.yaml), use a valid URL, Helm does not support local files at this time." ,
)
convertCmd . Flags ( ) . StringSliceVarP (
& envFiles ,
"env-file" ,
"e" ,
envFiles ,
"Specify the env file to use additonnaly to the .env file. Can be specified multiple times." ,
)
2023-12-06 15:24:02 +01:00
return convertCmd
}
func generateVersionCommand ( ) * cobra . Command {
return & cobra . Command {
Use : "version" ,
Short : "Print the version number of Katenary" ,
Run : func ( cmd * cobra . Command , args [ ] string ) {
2024-11-26 17:45:42 +01:00
fmt . Println ( generator . GetVersion ( ) )
2022-03-31 14:12:20 +02:00
} ,
2022-02-14 17:00:32 +01:00
}
2023-12-06 15:24:02 +01:00
}
2022-02-14 17:00:32 +01:00
2023-12-06 15:24:02 +01:00
func generateLabelHelpCommand ( ) * cobra . Command {
markdown := false
all := false
cmd := & cobra . Command {
Use : "help-labels [label]" ,
Short : "Print the labels help for all or a specific label" ,
Long : ` Print the labels help for all or a specific label
If no label is specified , the help for all labels is printed .
If a label is specified , the help for this label is printed .
2024-11-18 17:12:12 +01:00
The name of the label must be specified without the prefix ` + labels.Prefix() + ` .
2023-12-06 15:24:02 +01:00
e . g .
kanetary help - labels
katenary help - labels ingress
katenary help - labels map - env
` ,
2024-11-18 17:12:12 +01:00
ValidArgs : labels . GetLabelNames ( ) ,
2023-12-06 15:24:02 +01:00
Run : func ( cmd * cobra . Command , args [ ] string ) {
if len ( args ) > 0 {
2024-11-18 17:12:12 +01:00
fmt . Println ( labels . GetLabelHelpFor ( args [ 0 ] , markdown ) )
2022-03-31 14:12:20 +02:00
return
}
2023-12-06 15:24:02 +01:00
if all {
// show the help for all labels
2024-11-18 17:12:12 +01:00
l := len ( labels . GetLabelNames ( ) )
for i , label := range labels . GetLabelNames ( ) {
fmt . Println ( labels . GetLabelHelpFor ( label , markdown ) )
2023-12-06 15:24:02 +01:00
if ! markdown && i < l - 1 {
fmt . Println ( strings . Repeat ( "-" , 80 ) )
}
}
2022-03-31 14:12:20 +02:00
return
}
2024-11-18 17:12:12 +01:00
fmt . Println ( labels . GetLabelHelp ( markdown ) )
2022-03-31 14:12:20 +02:00
} ,
2022-02-14 17:00:32 +01:00
}
2023-12-06 15:24:02 +01:00
cmd . Flags ( ) . BoolVarP ( & markdown , "markdown" , "m" , markdown , "Use the markdown format" )
cmd . Flags ( ) . BoolVarP ( & all , "all" , "a" , all , "Print the full help for all labels" )
2022-03-31 14:12:20 +02:00
2023-12-06 15:24:02 +01:00
return cmd
}
func generateHashComposefilesCommand ( ) * cobra . Command {
cmd := & cobra . Command {
Use : "hash-composefiles [composefile]" ,
Short : "Print the hash of the composefiles" ,
Long : ` Print the hash of the composefiles
If no composefile is specified , the hash of all composefiles is printed . ` ,
Run : func ( cmd * cobra . Command , args [ ] string ) {
if len ( args ) > 0 {
if hash , err := utils . HashComposefiles ( args ) ; err != nil {
fmt . Println ( err )
} else {
fmt . Println ( hash )
}
return
}
} ,
2022-02-14 17:00:32 +01:00
}
2023-12-06 15:24:02 +01:00
return cmd
2022-02-14 17:00:32 +01:00
}
2024-11-18 17:12:12 +01:00
func generateSchemaCommand ( ) * cobra . Command {
cmd := & cobra . Command {
Use : "schema" ,
Short : "Print the schema of the katenary file" ,
Long : "Generate a schama for katenary.yaml file that can be used to validate the file or to use with yaml LSP to complete and check your configuration." ,
Run : func ( cmd * cobra . Command , args [ ] string ) {
fmt . Println ( katenaryfile . GenerateSchema ( ) )
} ,
}
return cmd
}