volcano.sh/volcano@v1.9.0/pkg/cli/job/run.go (about) 1 /* 2 Copyright 2018 The Volcano Authors. 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 job 18 19 import ( 20 "context" 21 "fmt" 22 "os" 23 "strings" 24 25 "github.com/spf13/cobra" 26 27 v1 "k8s.io/api/core/v1" 28 metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" 29 "sigs.k8s.io/yaml" 30 31 vcbatch "volcano.sh/apis/pkg/apis/batch/v1alpha1" 32 "volcano.sh/apis/pkg/client/clientset/versioned" 33 "volcano.sh/volcano/pkg/cli/util" 34 ) 35 36 type runFlags struct { 37 commonFlags 38 39 Name string 40 Namespace string 41 Image string 42 43 MinAvailable int 44 Replicas int 45 Requests string 46 Limits string 47 SchedulerName string 48 FileName string 49 } 50 51 var launchJobFlags = &runFlags{} 52 53 // InitRunFlags init the run flags. 54 func InitRunFlags(cmd *cobra.Command) { 55 initFlags(cmd, &launchJobFlags.commonFlags) 56 57 cmd.Flags().StringVarP(&launchJobFlags.Image, "image", "i", "busybox", "the container image of job") 58 cmd.Flags().StringVarP(&launchJobFlags.Namespace, "namespace", "n", "default", "the namespace of job") 59 cmd.Flags().StringVarP(&launchJobFlags.Name, "name", "N", "", "the name of job") 60 cmd.Flags().IntVarP(&launchJobFlags.MinAvailable, "min", "m", 1, "the minimal available tasks of job") 61 cmd.Flags().IntVarP(&launchJobFlags.Replicas, "replicas", "r", 1, "the total tasks of job") 62 cmd.Flags().StringVarP(&launchJobFlags.Requests, "requests", "R", "cpu=1000m,memory=100Mi", "the resource request of the task") 63 cmd.Flags().StringVarP(&launchJobFlags.Limits, "limits", "L", "cpu=1000m,memory=100Mi", "the resource limit of the task") 64 cmd.Flags().StringVarP(&launchJobFlags.SchedulerName, "scheduler", "S", "volcano", "the scheduler for this job") 65 cmd.Flags().StringVarP(&launchJobFlags.FileName, "filename", "f", "", "the yaml file of job") 66 } 67 68 var jobName = "job.volcano.sh" 69 70 // RunJob creates the job. 71 func RunJob() error { 72 config, err := util.BuildConfig(launchJobFlags.Master, launchJobFlags.Kubeconfig) 73 if err != nil { 74 return err 75 } 76 77 if launchJobFlags.Name == "" && launchJobFlags.FileName == "" { 78 err = fmt.Errorf("job name cannot be left blank") 79 return err 80 } 81 82 req, err := populateResourceListV1(launchJobFlags.Requests) 83 if err != nil { 84 return err 85 } 86 87 limit, err := populateResourceListV1(launchJobFlags.Limits) 88 if err != nil { 89 return err 90 } 91 92 job, err := readFile(launchJobFlags.FileName) 93 if err != nil { 94 return err 95 } 96 97 if job == nil { 98 job = constructLaunchJobFlagsJob(launchJobFlags, req, limit) 99 } 100 101 jobClient := versioned.NewForConfigOrDie(config) 102 newJob, err := jobClient.BatchV1alpha1().Jobs(launchJobFlags.Namespace).Create(context.TODO(), job, metav1.CreateOptions{}) 103 if err != nil { 104 return err 105 } 106 107 if newJob.Spec.Queue == "" { 108 newJob.Spec.Queue = "default" 109 } 110 111 fmt.Printf("run job %v successfully\n", newJob.Name) 112 113 return nil 114 } 115 116 func readFile(filename string) (*vcbatch.Job, error) { 117 if filename == "" { 118 return nil, nil 119 } 120 121 if !strings.Contains(filename, ".yaml") && !strings.Contains(filename, ".yml") { 122 return nil, fmt.Errorf("only support yaml file") 123 } 124 125 file, err := os.ReadFile(filename) 126 if err != nil { 127 return nil, fmt.Errorf("failed to read file, err: %v", err) 128 } 129 130 var job vcbatch.Job 131 if err := yaml.Unmarshal(file, &job); err != nil { 132 return nil, fmt.Errorf("failed to unmarshal file, err: %v", err) 133 } 134 135 return &job, nil 136 } 137 138 func constructLaunchJobFlagsJob(launchJobFlags *runFlags, req, limit v1.ResourceList) *vcbatch.Job { 139 return &vcbatch.Job{ 140 ObjectMeta: metav1.ObjectMeta{ 141 Name: launchJobFlags.Name, 142 Namespace: launchJobFlags.Namespace, 143 }, 144 Spec: vcbatch.JobSpec{ 145 MinAvailable: int32(launchJobFlags.MinAvailable), 146 SchedulerName: launchJobFlags.SchedulerName, 147 Tasks: []vcbatch.TaskSpec{ 148 { 149 Replicas: int32(launchJobFlags.Replicas), 150 151 Template: v1.PodTemplateSpec{ 152 ObjectMeta: metav1.ObjectMeta{ 153 Name: launchJobFlags.Name, 154 Labels: map[string]string{jobName: launchJobFlags.Name}, 155 }, 156 Spec: v1.PodSpec{ 157 RestartPolicy: v1.RestartPolicyNever, 158 Containers: []v1.Container{ 159 { 160 Image: launchJobFlags.Image, 161 Name: launchJobFlags.Name, 162 ImagePullPolicy: v1.PullIfNotPresent, 163 Resources: v1.ResourceRequirements{ 164 Limits: limit, 165 Requests: req, 166 }, 167 }, 168 }, 169 }, 170 }, 171 }, 172 }, 173 }, 174 } 175 }