github.com/danielqsj/helm@v2.0.0-alpha.4.0.20160908204436-976e0ba5199b+incompatible/cmd/helm/init.go (about) 1 /* 2 Copyright 2016 The Kubernetes Authors All rights reserved. 3 4 Licensed under the Apache License, Version 2.0 (the "License"); 5 you may not use this file except in compliance with the License. 6 You may obtain a copy of the License at 7 8 http://www.apache.org/licenses/LICENSE-2.0 9 10 Unless required by applicable law or agreed to in writing, software 11 distributed under the License is distributed on an "AS IS" BASIS, 12 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 See the License for the specific language governing permissions and 14 limitations under the License. 15 */ 16 17 package main 18 19 import ( 20 "errors" 21 "fmt" 22 "io" 23 "os" 24 "strings" 25 26 "github.com/spf13/cobra" 27 28 "k8s.io/helm/cmd/helm/installer" 29 ) 30 31 const initDesc = ` 32 This command installs Tiller (the helm server side component) onto your 33 Kubernetes Cluster and sets up local configuration in $HELM_HOME (default: ~/.helm/) 34 ` 35 36 var ( 37 defaultRepository = "kubernetes-charts" 38 defaultRepositoryURL = "http://storage.googleapis.com/kubernetes-charts" 39 ) 40 41 type initCmd struct { 42 image string 43 clientOnly bool 44 out io.Writer 45 } 46 47 func newInitCmd(out io.Writer) *cobra.Command { 48 i := &initCmd{ 49 out: out, 50 } 51 cmd := &cobra.Command{ 52 Use: "init", 53 Short: "initialize Helm on both client and server", 54 Long: initDesc, 55 RunE: func(cmd *cobra.Command, args []string) error { 56 if len(args) != 0 { 57 return errors.New("This command does not accept arguments") 58 } 59 return i.run() 60 }, 61 } 62 cmd.Flags().StringVarP(&i.image, "tiller-image", "i", "", "override tiller image") 63 cmd.Flags().BoolVarP(&i.clientOnly, "client-only", "c", false, "If set does not install tiller") 64 return cmd 65 } 66 67 // runInit initializes local config and installs tiller to Kubernetes Cluster 68 func (i *initCmd) run() error { 69 if err := ensureHome(); err != nil { 70 return err 71 } 72 73 if !i.clientOnly { 74 if err := installer.Install(tillerNamespace, i.image, flagDebug); err != nil { 75 if !strings.Contains(err.Error(), `"tiller-deploy" already exists`) { 76 return fmt.Errorf("error installing: %s", err) 77 } 78 fmt.Fprintln(i.out, "Warning: Tiller is already installed in the cluster. (Use --client-only to suppress this message.)") 79 } else { 80 fmt.Fprintln(i.out, "\nTiller (the helm server side component) has been installed into your Kubernetes Cluster.") 81 } 82 } else { 83 fmt.Fprintln(i.out, "Not installing tiller due to 'client-only' flag having been set") 84 } 85 fmt.Fprintln(i.out, "Happy Helming!") 86 return nil 87 } 88 89 func requireHome() error { 90 dirs := []string{homePath(), repositoryDirectory(), cacheDirectory(), localRepoDirectory()} 91 for _, d := range dirs { 92 if fi, err := os.Stat(d); err != nil { 93 return fmt.Errorf("directory %q is not configured", d) 94 } else if !fi.IsDir() { 95 return fmt.Errorf("expected %q to be a directory", d) 96 } 97 } 98 return nil 99 } 100 101 // ensureHome checks to see if $HELM_HOME exists 102 // 103 // If $HELM_HOME does not exist, this function will create it. 104 func ensureHome() error { 105 configDirectories := []string{homePath(), repositoryDirectory(), cacheDirectory(), localRepoDirectory()} 106 107 for _, p := range configDirectories { 108 if fi, err := os.Stat(p); err != nil { 109 fmt.Printf("Creating %s \n", p) 110 if err := os.MkdirAll(p, 0755); err != nil { 111 return fmt.Errorf("Could not create %s: %s", p, err) 112 } 113 } else if !fi.IsDir() { 114 return fmt.Errorf("%s must be a directory", p) 115 } 116 } 117 118 repoFile := repositoriesFile() 119 if fi, err := os.Stat(repoFile); err != nil { 120 fmt.Printf("Creating %s \n", repoFile) 121 if _, err := os.Create(repoFile); err != nil { 122 return err 123 } 124 if err := addRepository(defaultRepository, defaultRepositoryURL); err != nil { 125 return err 126 } 127 } else if fi.IsDir() { 128 return fmt.Errorf("%s must be a file, not a directory", repoFile) 129 } 130 131 localRepoIndexFile := localRepoDirectory(localRepoIndexFilePath) 132 if fi, err := os.Stat(localRepoIndexFile); err != nil { 133 fmt.Printf("Creating %s \n", localRepoIndexFile) 134 _, err := os.Create(localRepoIndexFile) 135 if err != nil { 136 return err 137 } 138 139 //TODO: take this out and replace with helm update functionality 140 os.Symlink(localRepoIndexFile, cacheDirectory("local-index.yaml")) 141 } else if fi.IsDir() { 142 return fmt.Errorf("%s must be a file, not a directory", localRepoIndexFile) 143 } 144 145 fmt.Printf("$HELM_HOME has been configured at %s.\n", helmHome) 146 return nil 147 }