Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(316)

Side by Side Diff: deploytool/cmd/luci_deploy/layout.go

Issue 2963503003: [errors] Greatly simplify common/errors package. (Closed)
Patch Set: fix nits Created 3 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « deploytool/cmd/luci_deploy/kubernetes.go ('k') | deploytool/cmd/luci_deploy/manage.go » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2016 The LUCI Authors. All rights reserved. 1 // Copyright 2016 The LUCI Authors. All rights reserved.
2 // Use of this source code is governed under the Apache License, Version 2.0 2 // Use of this source code is governed under the Apache License, Version 2.0
3 // that can be found in the LICENSE file. 3 // that can be found in the LICENSE file.
4 4
5 package main 5 package main
6 6
7 import ( 7 import (
8 "io/ioutil" 8 "io/ioutil"
9 "os" 9 "os"
10 "path/filepath" 10 "path/filepath"
(...skipping 24 matching lines...) Expand all
35 } 35 }
36 36
37 // pathTo resolves a path, p, specified in a directory with source-root-relative 37 // pathTo resolves a path, p, specified in a directory with source-root-relative
38 // path relpath. 38 // path relpath.
39 // 39 //
40 // - If the path begins with "/", it is taken relative to the source root. 40 // - If the path begins with "/", it is taken relative to the source root.
41 // - If the path does not begin with "/", it is taken relative to "relpath" 41 // - If the path does not begin with "/", it is taken relative to "relpath"
42 // within the source root (e.g., "relpath" is prepended to it). 42 // within the source root (e.g., "relpath" is prepended to it).
43 func (s *layoutSource) pathTo(p, relpath string) string { 43 func (s *layoutSource) pathTo(p, relpath string) string {
44 if s.Relpath == "" { 44 if s.Relpath == "" {
45 » » panic(errors.Reason("source %(source)q is not checked out").D("s ource", s).Err()) 45 » » panic(errors.Reason("source %q is not checked out", s).Err())
46 } 46 }
47 47
48 // If this is absolute, take it relative to source root. 48 // If this is absolute, take it relative to source root.
49 if strings.HasPrefix(p, "/") { 49 if strings.HasPrefix(p, "/") {
50 relpath = "" 50 relpath = ""
51 } 51 }
52 52
53 // Convert "p" to a source-relative absolute path. 53 // Convert "p" to a source-relative absolute path.
54 p = strings.Trim(p, "/") 54 p = strings.Trim(p, "/")
55 if relpath != "" { 55 if relpath != "" {
(...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after
120 // cloudProject is the deployment cloud project, if one is specified. 120 // cloudProject is the deployment cloud project, if one is specified.
121 cloudProject *layoutDeploymentCloudProject 121 cloudProject *layoutDeploymentCloudProject
122 } 122 }
123 123
124 func (d *layoutDeployment) String() string { return string(d.title) } 124 func (d *layoutDeployment) String() string { return string(d.title) }
125 125
126 // substituteParams applies parameter substitution to the supplied string in a 126 // substituteParams applies parameter substitution to the supplied string in a
127 // left-to-right manner. 127 // left-to-right manner.
128 func (d *layoutDeployment) substituteParams(vp *string) error { 128 func (d *layoutDeployment) substituteParams(vp *string) error {
129 if err := substitute(vp, d.Parameter); err != nil { 129 if err := substitute(vp, d.Parameter); err != nil {
130 » » return errors.Annotate(err).Err() 130 » » return errors.Annotate(err, "").Err()
131 } 131 }
132 return nil 132 return nil
133 } 133 }
134 134
135 type layoutDeploymentComponent struct { 135 type layoutDeploymentComponent struct {
136 deploy.Component 136 deploy.Component
137 137
138 // reldir is the source-relative directory that relative paths in this 138 // reldir is the source-relative directory that relative paths in this
139 // component will reference. This will be the parent directory of the 139 // component will reference. This will be the parent directory of the
140 // component's configuration file. 140 // component's configuration file.
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after
172 } 172 }
173 173
174 func (comp *layoutDeploymentComponent) pathTo(relpath string) string { 174 func (comp *layoutDeploymentComponent) pathTo(relpath string) string {
175 return comp.source().pathTo(relpath, comp.reldir) 175 return comp.source().pathTo(relpath, comp.reldir)
176 } 176 }
177 177
178 func (comp *layoutDeploymentComponent) buildPath(bp *deploy.BuildPath) (string, error) { 178 func (comp *layoutDeploymentComponent) buildPath(bp *deploy.BuildPath) (string, error) {
179 if path, ok := comp.buildPathMap[bp]; ok { 179 if path, ok := comp.buildPathMap[bp]; ok {
180 return path, nil 180 return path, nil
181 } 181 }
182 » return "", errors.Reason("no build path resolved for: %(bp)+v").D("bp", bp, "%+v").Err() 182 » return "", errors.Reason("no build path resolved for: %+v", bp).Err()
183 } 183 }
184 184
185 func (comp *layoutDeploymentComponent) loadSourceComponent(reg componentRegistra r) error { 185 func (comp *layoutDeploymentComponent) loadSourceComponent(reg componentRegistra r) error {
186 if err := unmarshalTextProtobuf(comp.source().pathTo(comp.comp.Path, "") , &comp.Component); err != nil { 186 if err := unmarshalTextProtobuf(comp.source().pathTo(comp.comp.Path, "") , &comp.Component); err != nil {
187 » » return errors.Annotate(err).Reason("failed to load source compon ent %(component)q").D("component", comp).Err() 187 » » return errors.Annotate(err, "failed to load source component %q" , comp).Err()
188 } 188 }
189 189
190 // Referenced build paths. 190 // Referenced build paths.
191 for i, p := range comp.BuildPath { 191 for i, p := range comp.BuildPath {
192 var msg deploy.Component_Build 192 var msg deploy.Component_Build
193 if err := unmarshalTextProtobuf(comp.pathTo(p), &msg); err != ni l { 193 if err := unmarshalTextProtobuf(comp.pathTo(p), &msg); err != ni l {
194 » » » return errors.Annotate(err).Reason("failed to load compo nent Build #%(index)d from [%(path)s]"). 194 » » » return errors.Annotate(err, "failed to load component Bu ild #%d from [%s]", i, p).Err()
195 » » » » D("index", i).D("path", p).Err()
196 } 195 }
197 comp.Build = append(comp.Build, &msg) 196 comp.Build = append(comp.Build, &msg)
198 } 197 }
199 198
200 // Load any referenced data and normalize it for internal usage. 199 // Load any referenced data and normalize it for internal usage.
201 dep := comp.dep 200 dep := comp.dep
202 switch t := comp.GetComponent().(type) { 201 switch t := comp.GetComponent().(type) {
203 case *deploy.Component_AppengineModule: 202 case *deploy.Component_AppengineModule:
204 // Normalize AppEngine module: 203 // Normalize AppEngine module:
205 // - Modules explicitly named "default" will have their ModuleNa me changed 204 // - Modules explicitly named "default" will have their ModuleNa me changed
206 // to the empty string. 205 // to the empty string.
207 // - All referenced path parameters will be loaded and appended onto their 206 // - All referenced path parameters will be loaded and appended onto their
208 // non-path members. 207 // non-path members.
209 if dep.cloudProject == nil { 208 if dep.cloudProject == nil {
210 » » » return errors.Reason("AppEngine module %(comp)q requires a cloud project"). 209 » » » return errors.Reason("AppEngine module %q requires a clo ud project", comp).Err()
211 » » » » D("comp", comp).Err()
212 } 210 }
213 211
214 aem := t.AppengineModule 212 aem := t.AppengineModule
215 if aem.ModuleName == "default" { 213 if aem.ModuleName == "default" {
216 aem.ModuleName = "" 214 aem.ModuleName = ""
217 } 215 }
218 216
219 module := layoutDeploymentGAEModule{ 217 module := layoutDeploymentGAEModule{
220 AppEngineModule: aem, 218 AppEngineModule: aem,
221 comp: comp, 219 comp: comp,
222 } 220 }
223 221
224 // Referenced handler paths. 222 // Referenced handler paths.
225 for i, p := range aem.HandlerPath { 223 for i, p := range aem.HandlerPath {
226 var msg deploy.AppEngineModule_HandlerSet 224 var msg deploy.AppEngineModule_HandlerSet
227 if err := unmarshalTextProtobuf(comp.pathTo(p), &msg); e rr != nil { 225 if err := unmarshalTextProtobuf(comp.pathTo(p), &msg); e rr != nil {
228 » » » » return errors.Annotate(err).Reason("failed to lo ad HandlerSet #%(index)d for %(component)q"). 226 » » » » return errors.Annotate(err, "failed to load Hand lerSet #%d for %q", i, comp).Err()
229 » » » » » D("index", i).D("component", comp).Err()
230 } 227 }
231 module.Handlers.Handler = append(module.Handlers.Handler , msg.Handler...) 228 module.Handlers.Handler = append(module.Handlers.Handler , msg.Handler...)
232 } 229 }
233 230
234 // If the module specifies a direct "index.yaml" path, load inde x entries 231 // If the module specifies a direct "index.yaml" path, load inde x entries
235 // from there and translate them to resources. 232 // from there and translate them to resources.
236 if p := module.IndexYamlPath; p != "" { 233 if p := module.IndexYamlPath; p != "" {
237 path := module.comp.pathTo(p) 234 path := module.comp.pathTo(p)
238 res, err := loadIndexYAMLResource(path) 235 res, err := loadIndexYAMLResource(path)
239 if err != nil { 236 if err != nil {
240 » » » » return errors.Annotate(err).Reason("failed to lo ad 'index.yaml' from [%(path)s]"). 237 » » » » return errors.Annotate(err, "failed to load 'ind ex.yaml' from [%s]", path).Err()
241 » » » » » D("path", path).Err()
242 } 238 }
243 dep.cloudProject.appendResources(res, &module) 239 dep.cloudProject.appendResources(res, &module)
244 } 240 }
245 241
246 // Append GAE Resources. 242 // Append GAE Resources.
247 if r := module.Resources; r != nil { 243 if r := module.Resources; r != nil {
248 dep.cloudProject.appendResources(r, &module) 244 dep.cloudProject.appendResources(r, &module)
249 } 245 }
250 246
251 for i, p := range module.ResourcePath { 247 for i, p := range module.ResourcePath {
252 if err := comp.dep.substituteParams(&p); err != nil { 248 if err := comp.dep.substituteParams(&p); err != nil {
253 » » » » return errors.Annotate(err).Reason("failed to su bstitute parameters for resource path"). 249 » » » » return errors.Annotate(err, "failed to substitut e parameters for resource path").
254 » » » » » D("path", p).Err() 250 » » » » » InternalReason("path(%s)", p).Err()
255 } 251 }
256 252
257 var res deploy.AppEngineResources 253 var res deploy.AppEngineResources
258 if err := unmarshalTextProtobuf(comp.pathTo(p), &res); e rr != nil { 254 if err := unmarshalTextProtobuf(comp.pathTo(p), &res); e rr != nil {
259 » » » » return errors.Annotate(err).Reason("failed to lo ad Resources #%(index)d for %(component)"). 255 » » » » return errors.Annotate(err, "failed to load Reso urces #%d for %q", i, comp).
260 » » » » » D("index", i).D("path", p).D("component" , comp).Err() 256 » » » » » InternalReason("path(%s)", p).Err()
261 } 257 }
262 dep.cloudProject.appendResources(&res, &module) 258 dep.cloudProject.appendResources(&res, &module)
263 } 259 }
264 260
265 // Add this module to our cloud project's AppEngine modules list . 261 // Add this module to our cloud project's AppEngine modules list .
266 dep.cloudProject.appEngineModules = append(dep.cloudProject.appE ngineModules, &module) 262 dep.cloudProject.appEngineModules = append(dep.cloudProject.appE ngineModules, &module)
267 if reg != nil { 263 if reg != nil {
268 reg.addGAEModule(&module) 264 reg.addGAEModule(&module)
269 } 265 }
270 266
271 case *deploy.Component_GkePod: 267 case *deploy.Component_GkePod:
272 if len(comp.gkePods) == 0 { 268 if len(comp.gkePods) == 0 {
273 » » » return errors.Reason("GKE Container %(comp)q is not boun d to a GKE cluster"). 269 » » » return errors.Reason("GKE Container %q is not bound to a GKE cluster", comp).Err()
274 » » » » D("comp", comp.String()).Err()
275 } 270 }
276 271
277 comp.gkePod = &layoutDeploymentGKEPod{ 272 comp.gkePod = &layoutDeploymentGKEPod{
278 ContainerEnginePod: t.GkePod, 273 ContainerEnginePod: t.GkePod,
279 comp: comp, 274 comp: comp,
280 } 275 }
281 276
282 // None of the labels may use our "deploytool" prefix. 277 // None of the labels may use our "deploytool" prefix.
283 var invalidLabels []string 278 var invalidLabels []string
284 for k := range comp.gkePod.KubePod.Labels { 279 for k := range comp.gkePod.KubePod.Labels {
285 if isKubeDeployToolKey(k) { 280 if isKubeDeployToolKey(k) {
286 invalidLabels = append(invalidLabels, k) 281 invalidLabels = append(invalidLabels, k)
287 } 282 }
288 } 283 }
289 if len(invalidLabels) > 0 { 284 if len(invalidLabels) > 0 {
290 sort.Strings(invalidLabels) 285 sort.Strings(invalidLabels)
291 return errors.Reason("user-supplied labels may not use d eploytool prefix"). 286 return errors.Reason("user-supplied labels may not use d eploytool prefix").
292 » » » » D("labels", invalidLabels).Err() 287 » » » » InternalReason("labels(%v)", invalidLabels).Err( )
293 } 288 }
294 289
295 for _, bp := range comp.gkePods { 290 for _, bp := range comp.gkePods {
296 bp.pod = comp.gkePod 291 bp.pod = comp.gkePod
297 if reg != nil { 292 if reg != nil {
298 reg.addGKEPod(bp) 293 reg.addGKEPod(bp)
299 } 294 }
300 } 295 }
301 } 296 }
302 297
303 return nil 298 return nil
304 } 299 }
305 300
306 // expandPaths iterates through the Component-defined directory fields and 301 // expandPaths iterates through the Component-defined directory fields and
307 // expands their paths into actual filesystem paths. 302 // expands their paths into actual filesystem paths.
308 // 303 //
309 // This must be performed after the build instructions have been executed so 304 // This must be performed after the build instructions have been executed so
310 // that the "build_dir" map will be available if needed by a Component. 305 // that the "build_dir" map will be available if needed by a Component.
311 func (comp *layoutDeploymentComponent) expandPaths() error { 306 func (comp *layoutDeploymentComponent) expandPaths() error {
312 resolveBuildPath := func(bp *deploy.BuildPath) error { 307 resolveBuildPath := func(bp *deploy.BuildPath) error {
313 if _, ok := comp.buildPathMap[bp]; ok { 308 if _, ok := comp.buildPathMap[bp]; ok {
314 // Already resolved. 309 // Already resolved.
315 return nil 310 return nil
316 } 311 }
317 312
318 var resolved string 313 var resolved string
319 if bp.DirKey != "" { 314 if bp.DirKey != "" {
320 dir, ok := comp.buildDirs[bp.DirKey] 315 dir, ok := comp.buildDirs[bp.DirKey]
321 if !ok { 316 if !ok {
322 » » » » return errors.Reason("Invalid `dir_key` value: % (dirKey)q").D("dirKey", bp.DirKey).Err() 317 » » » » return errors.Reason("Invalid `dir_key` value: % q", bp.DirKey).Err()
323 } 318 }
324 resolved = deployToNative(dir, bp.Path) 319 resolved = deployToNative(dir, bp.Path)
325 } else { 320 } else {
326 resolved = comp.pathTo(bp.Path) 321 resolved = comp.pathTo(bp.Path)
327 } 322 }
328 323
329 if comp.buildPathMap == nil { 324 if comp.buildPathMap == nil {
330 comp.buildPathMap = make(map[*deploy.BuildPath]string) 325 comp.buildPathMap = make(map[*deploy.BuildPath]string)
331 } 326 }
332 comp.buildPathMap[bp] = resolved 327 comp.buildPathMap[bp] = resolved
333 return nil 328 return nil
334 } 329 }
335 330
336 switch t := comp.Component.Component.(type) { 331 switch t := comp.Component.Component.(type) {
337 case *deploy.Component_AppengineModule: 332 case *deploy.Component_AppengineModule:
338 aem := t.AppengineModule 333 aem := t.AppengineModule
339 if aem.Handlers != nil { 334 if aem.Handlers != nil {
340 for _, handler := range aem.Handlers.Handler { 335 for _, handler := range aem.Handlers.Handler {
341 switch c := handler.Content.(type) { 336 switch c := handler.Content.(type) {
342 case *deploy.AppEngineModule_Handler_StaticFiles _: 337 case *deploy.AppEngineModule_Handler_StaticFiles _:
343 sf := c.StaticFiles 338 sf := c.StaticFiles
344 switch bd := sf.BaseDir.(type) { 339 switch bd := sf.BaseDir.(type) {
345 case *deploy.AppEngineModule_Handler_Sta ticFiles_Path: 340 case *deploy.AppEngineModule_Handler_Sta ticFiles_Path:
346 // Normalize our static files di rectory to a BuildPath rooted at our 341 // Normalize our static files di rectory to a BuildPath rooted at our
347 // source. 342 // source.
348 sf.BaseDir = &deploy.AppEngineMo dule_Handler_StaticFiles_Build{ 343 sf.BaseDir = &deploy.AppEngineMo dule_Handler_StaticFiles_Build{
349 Build: &deploy.BuildPath {Path: bd.Path}, 344 Build: &deploy.BuildPath {Path: bd.Path},
350 } 345 }
351 if err := resolveBuildPath(sf.Ge tBuild()); err != nil { 346 if err := resolveBuildPath(sf.Ge tBuild()); err != nil {
352 » » » » » » » return errors.Annotate(e rr).Err() 347 » » » » » » » return errors.Annotate(e rr, "").Err()
353 } 348 }
354 349
355 case *deploy.AppEngineModule_Handler_Sta ticFiles_Build: 350 case *deploy.AppEngineModule_Handler_Sta ticFiles_Build:
356 if err := resolveBuildPath(bd.Bu ild); err != nil { 351 if err := resolveBuildPath(bd.Bu ild); err != nil {
357 » » » » » » » return errors.Annotate(e rr).Err() 352 » » » » » » » return errors.Annotate(e rr, "").Err()
358 } 353 }
359 354
360 default: 355 default:
361 » » » » » » return errors.Reason("unknown `b ase_dir` type %(type)T").D("type", bd).Err() 356 » » » » » » return errors.Reason("unknown `b ase_dir` type %T", bd).Err()
362 } 357 }
363 358
364 case *deploy.AppEngineModule_Handler_StaticDir: 359 case *deploy.AppEngineModule_Handler_StaticDir:
365 // Normalize our static directory (sourc e-relative) to a BuildPath 360 // Normalize our static directory (sourc e-relative) to a BuildPath
366 // rooted at our source. 361 // rooted at our source.
367 handler.Content = &deploy.AppEngineModul e_Handler_StaticBuildDir{ 362 handler.Content = &deploy.AppEngineModul e_Handler_StaticBuildDir{
368 StaticBuildDir: &deploy.BuildPat h{Path: c.StaticDir}, 363 StaticBuildDir: &deploy.BuildPat h{Path: c.StaticDir},
369 } 364 }
370 if err := resolveBuildPath(handler.GetSt aticBuildDir()); err != nil { 365 if err := resolveBuildPath(handler.GetSt aticBuildDir()); err != nil {
371 » » » » » » return errors.Annotate(err).Err( ) 366 » » » » » » return errors.Annotate(err, ""). Err()
372 } 367 }
373 368
374 case *deploy.AppEngineModule_Handler_StaticBuild Dir: 369 case *deploy.AppEngineModule_Handler_StaticBuild Dir:
375 if err := resolveBuildPath(c.StaticBuild Dir); err != nil { 370 if err := resolveBuildPath(c.StaticBuild Dir); err != nil {
376 » » » » » » return errors.Annotate(err).Err( ) 371 » » » » » » return errors.Annotate(err, ""). Err()
377 } 372 }
378 } 373 }
379 } 374 }
380 } 375 }
381 376
382 case *deploy.Component_GkePod: 377 case *deploy.Component_GkePod:
383 for _, container := range t.GkePod.KubePod.Container { 378 for _, container := range t.GkePod.KubePod.Container {
384 switch df := container.Dockerfile.(type) { 379 switch df := container.Dockerfile.(type) {
385 case *deploy.KubernetesPod_Container_Path: 380 case *deploy.KubernetesPod_Container_Path:
386 // Convert to BuildPath. 381 // Convert to BuildPath.
387 container.Dockerfile = &deploy.KubernetesPod_Con tainer_Build{ 382 container.Dockerfile = &deploy.KubernetesPod_Con tainer_Build{
388 Build: &deploy.BuildPath{Path: df.Path}, 383 Build: &deploy.BuildPath{Path: df.Path},
389 } 384 }
390 if err := resolveBuildPath(container.GetBuild()) ; err != nil { 385 if err := resolveBuildPath(container.GetBuild()) ; err != nil {
391 » » » » » return errors.Annotate(err).Err() 386 » » » » » return errors.Annotate(err, "").Err()
392 } 387 }
393 388
394 case *deploy.KubernetesPod_Container_Build: 389 case *deploy.KubernetesPod_Container_Build:
395 if err := resolveBuildPath(df.Build); err != nil { 390 if err := resolveBuildPath(df.Build); err != nil {
396 » » » » » return errors.Annotate(err).Err() 391 » » » » » return errors.Annotate(err, "").Err()
397 } 392 }
398 393
399 default: 394 default:
400 » » » » return errors.Reason("unknown `dockerfile` type %(type)T").D("type", df).Err() 395 » » » » return errors.Reason("unknown `dockerfile` type %T", df).Err()
401 } 396 }
402 } 397 }
403 } 398 }
404 399
405 return nil 400 return nil
406 } 401 }
407 402
408 // layoutDeploymentCloudProject tracks a cloud project element, as well as 403 // layoutDeploymentCloudProject tracks a cloud project element, as well as
409 // any cloud project configurations referenced by this Deployment's Components. 404 // any cloud project configurations referenced by this Deployment's Components.
410 type layoutDeploymentCloudProject struct { 405 type layoutDeploymentCloudProject struct {
(...skipping 111 matching lines...) Expand 10 before | Expand all | Expand 10 after
522 cloudProjects map[string]*layoutDeploymentCloudProject 517 cloudProjects map[string]*layoutDeploymentCloudProject
523 } 518 }
524 519
525 // workingFilesystem creates a new managed filesystem at our working directory 520 // workingFilesystem creates a new managed filesystem at our working directory
526 // root. 521 // root.
527 // 522 //
528 // This adds layout-defined components to the filesystem. 523 // This adds layout-defined components to the filesystem.
529 func (l *deployLayout) workingFilesystem() (*managedfs.Filesystem, error) { 524 func (l *deployLayout) workingFilesystem() (*managedfs.Filesystem, error) {
530 fs, err := managedfs.New(l.WorkingPath) 525 fs, err := managedfs.New(l.WorkingPath)
531 if err != nil { 526 if err != nil {
532 » » return nil, errors.Annotate(err).Err() 527 » » return nil, errors.Annotate(err, "").Err()
533 } 528 }
534 return fs, nil 529 return fs, nil
535 } 530 }
536 531
537 func (l *deployLayout) workingPathTo(relpath string) string { 532 func (l *deployLayout) workingPathTo(relpath string) string {
538 return filepath.Join(l.WorkingPath, relpath) 533 return filepath.Join(l.WorkingPath, relpath)
539 } 534 }
540 535
541 func (l *deployLayout) getDeploymentComponent(v string) (*layoutDeployment, *lay outDeploymentComponent, error) { 536 func (l *deployLayout) getDeploymentComponent(v string) (*layoutDeployment, *lay outDeploymentComponent, error) {
542 deployment, component := splitComponentPath(v) 537 deployment, component := splitComponentPath(v)
543 538
544 dep := l.deployments[deployment] 539 dep := l.deployments[deployment]
545 if dep == nil { 540 if dep == nil {
546 » » return nil, nil, errors.Reason("unknown Deployment %(dep)q"). 541 » » return nil, nil, errors.Reason("unknown Deployment %q", deployme nt).
547 » » » D("value", v).D("dep", deployment).Err() 542 » » » InternalReason("value(%s)", v).Err()
548 } 543 }
549 544
550 // If a component was specified, only add that component. 545 // If a component was specified, only add that component.
551 if component != "" { 546 if component != "" {
552 comp := dep.components[component] 547 comp := dep.components[component]
553 if comp == nil { 548 if comp == nil {
554 » » » return nil, nil, errors.Reason("unknown Deployment Compo nent %(value)q"). 549 » » » return nil, nil, errors.Reason("unknown Deployment Compo nent %q", v).
555 » » » » D("value", v).D("dep", deployment).D("comp", com ponent).Err() 550 » » » » InternalReason("dep(%s)/comp(%s)", deployment, c omponent).Err()
556 } 551 }
557 return dep, comp, nil 552 return dep, comp, nil
558 } 553 }
559 return dep, nil, nil 554 return dep, nil, nil
560 } 555 }
561 556
562 func (l *deployLayout) matchDeploymentComponent(m string, cb func(*layoutDeploym ent, *layoutDeploymentComponent)) error { 557 func (l *deployLayout) matchDeploymentComponent(m string, cb func(*layoutDeploym ent, *layoutDeploymentComponent)) error {
563 for _, depName := range l.deploymentNames { 558 for _, depName := range l.deploymentNames {
564 dep := l.deployments[depName] 559 dep := l.deployments[depName]
565 560
566 matched, err := filepath.Match(m, dep.String()) 561 matched, err := filepath.Match(m, dep.String())
567 if err != nil { 562 if err != nil {
568 » » » return errors.Annotate(err).Reason("failed to match %(pa ttern)q").D("pattern", m).Err() 563 » » » return errors.Annotate(err, "failed to match %q", m).Err ()
569 } 564 }
570 if matched { 565 if matched {
571 // Matches entire deployment. 566 // Matches entire deployment.
572 cb(dep, nil) 567 cb(dep, nil)
573 continue 568 continue
574 } 569 }
575 570
576 // Try each of the deployment's components. 571 // Try each of the deployment's components.
577 for _, compName := range dep.componentNames { 572 for _, compName := range dep.componentNames {
578 comp := dep.components[compName] 573 comp := dep.components[compName]
579 574
580 matched, err := filepath.Match(m, comp.String()) 575 matched, err := filepath.Match(m, comp.String())
581 if err != nil { 576 if err != nil {
582 » » » » return errors.Annotate(err).Reason("failed to ma tch %(pattern)q").D("pattern", m).Err() 577 » » » » return errors.Annotate(err, "failed to match %q" , m).Err()
583 } 578 }
584 if matched { 579 if matched {
585 cb(dep, comp) 580 cb(dep, comp)
586 } 581 }
587 } 582 }
588 } 583 }
589 584
590 return nil 585 return nil
591 } 586 }
592 587
593 func (l *deployLayout) load(c context.Context, path string) error { 588 func (l *deployLayout) load(c context.Context, path string) error {
594 if path == "" { 589 if path == "" {
595 wd, err := os.Getwd() 590 wd, err := os.Getwd()
596 if err != nil { 591 if err != nil {
597 return err 592 return err
598 } 593 }
599 path, err = findLayout(defaultLayoutFilename, wd) 594 path, err = findLayout(defaultLayoutFilename, wd)
600 if err != nil { 595 if err != nil {
601 return err 596 return err
602 } 597 }
603 } 598 }
604 599
605 if err := unmarshalTextProtobuf(path, &l.Layout); err != nil { 600 if err := unmarshalTextProtobuf(path, &l.Layout); err != nil {
606 return err 601 return err
607 } 602 }
608 603
609 // Load the user config, if available. 604 // Load the user config, if available.
610 if err := loadUserConfig(c, &l.user); err != nil { 605 if err := loadUserConfig(c, &l.user); err != nil {
611 » » return errors.Annotate(err).Reason("failed to load user config") .Err() 606 » » return errors.Annotate(err, "failed to load user config").Err()
612 } 607 }
613 if len(l.user.SourceOverride) > 0 { 608 if len(l.user.SourceOverride) > 0 {
614 l.userSourceOverrides = make(map[string]*deploy.Source, len(l.us er.SourceOverride)) 609 l.userSourceOverrides = make(map[string]*deploy.Source, len(l.us er.SourceOverride))
615 for k, v := range l.user.SourceOverride { 610 for k, v := range l.user.SourceOverride {
616 l.userSourceOverrides[k] = v 611 l.userSourceOverrides[k] = v
617 } 612 }
618 } 613 }
619 614
620 // Populate with defaults. 615 // Populate with defaults.
621 l.basePath = filepath.Dir(path) 616 l.basePath = filepath.Dir(path)
(...skipping 10 matching lines...) Expand all
632 if l.WorkingPath == "" { 627 if l.WorkingPath == "" {
633 l.WorkingPath = filepath.Join(l.basePath, ".working") 628 l.WorkingPath = filepath.Join(l.basePath, ".working")
634 } else { 629 } else {
635 if !filepath.IsAbs(l.WorkingPath) { 630 if !filepath.IsAbs(l.WorkingPath) {
636 l.WorkingPath = filepath.Join(l.basePath, l.WorkingPath) 631 l.WorkingPath = filepath.Join(l.basePath, l.WorkingPath)
637 } 632 }
638 } 633 }
639 634
640 absWorkingPath, err := filepath.Abs(l.WorkingPath) 635 absWorkingPath, err := filepath.Abs(l.WorkingPath)
641 if err != nil { 636 if err != nil {
642 » » return errors.Annotate(err).Reason("failed to resolve absolute p ath for %(path)q"). 637 » » return errors.Annotate(err, "failed to resolve absolute path for %q", l.WorkingPath).Err()
643 » » » D("path", l.WorkingPath).Err()
644 } 638 }
645 l.WorkingPath = absWorkingPath 639 l.WorkingPath = absWorkingPath
646 return nil 640 return nil
647 } 641 }
648 642
649 func (l *deployLayout) initFrozenCheckout(c context.Context) (*deploy.FrozenLayo ut, error) { 643 func (l *deployLayout) initFrozenCheckout(c context.Context) (*deploy.FrozenLayo ut, error) {
650 fis, err := ioutil.ReadDir(l.SourcesPath) 644 fis, err := ioutil.ReadDir(l.SourcesPath)
651 if err != nil { 645 if err != nil {
652 » » return nil, errors.Annotate(err).Reason("failed to read director y").Err() 646 » » return nil, errors.Annotate(err, "failed to read directory").Err ()
653 } 647 }
654 648
655 // Build internal and frozen layout in parallel. 649 // Build internal and frozen layout in parallel.
656 var frozen deploy.FrozenLayout 650 var frozen deploy.FrozenLayout
657 frozen.SourceGroup = make(map[string]*deploy.FrozenLayout_SourceGroup, l en(fis)) 651 frozen.SourceGroup = make(map[string]*deploy.FrozenLayout_SourceGroup, l en(fis))
658 652
659 for _, fi := range fis { 653 for _, fi := range fis {
660 name := title(fi.Name()) 654 name := title(fi.Name())
661 path := filepath.Join(l.SourcesPath, string(name)) 655 path := filepath.Join(l.SourcesPath, string(name))
662 656
(...skipping 27 matching lines...) Expand all
690 sg := deploy.FrozenLayout_SourceGroup{ 684 sg := deploy.FrozenLayout_SourceGroup{
691 Source: make(map[string]*deploy.FrozenLayout_Source, len (srcInfos)), 685 Source: make(map[string]*deploy.FrozenLayout_Source, len (srcInfos)),
692 } 686 }
693 687
694 var srcBase deploy.Source 688 var srcBase deploy.Source
695 err = unmarshalTextProtobufDir(path, srcInfos, &srcBase, func(na me string) error { 689 err = unmarshalTextProtobufDir(path, srcInfos, &srcBase, func(na me string) error {
696 cpy := srcBase 690 cpy := srcBase
697 691
698 t, err := titleFromConfigPath(name) 692 t, err := titleFromConfigPath(name)
699 if err != nil { 693 if err != nil {
700 » » » » return errors.Annotate(err).Reason("invalid sour ce title").Err() 694 » » » » return errors.Annotate(err, "invalid source titl e").Err()
701 } 695 }
702 696
703 src := deploy.FrozenLayout_Source{ 697 src := deploy.FrozenLayout_Source{
704 Source: &cpy, 698 Source: &cpy,
705 } 699 }
706 sg.Source[string(t)] = &src 700 sg.Source[string(t)] = &src
707 return nil 701 return nil
708 }) 702 })
709 if err != nil { 703 if err != nil {
710 » » » return nil, errors.Annotate(err).Reason("failed to load source group %(name)q from [%(path)s]"). 704 » » » return nil, errors.Annotate(err, "failed to load source group %q from [%s]", name, path).Err()
711 » » » » D("name", name).D("path", path).Err()
712 } 705 }
713 706
714 frozen.SourceGroup[string(name)] = &sg 707 frozen.SourceGroup[string(name)] = &sg
715 } 708 }
716 709
717 return &frozen, nil 710 return &frozen, nil
718 } 711 }
719 712
720 func (l *deployLayout) loadFrozenLayout(c context.Context) error { 713 func (l *deployLayout) loadFrozenLayout(c context.Context) error {
721 // Load the frozen configuration file from disk. 714 // Load the frozen configuration file from disk.
722 frozen, err := checkoutFrozen(l) 715 frozen, err := checkoutFrozen(l)
723 if err != nil { 716 if err != nil {
724 » » return errors.Annotate(err).Reason("failed to load frozen checko ut").Err() 717 » » return errors.Annotate(err, "failed to load frozen checkout").Er r()
725 } 718 }
726 719
727 // Load our source groups and sources. 720 // Load our source groups and sources.
728 l.sourceGroups = make(map[title]*layoutSourceGroup, len(frozen.SourceGro up)) 721 l.sourceGroups = make(map[title]*layoutSourceGroup, len(frozen.SourceGro up))
729 for sgName, fsg := range frozen.SourceGroup { 722 for sgName, fsg := range frozen.SourceGroup {
730 sg := layoutSourceGroup{ 723 sg := layoutSourceGroup{
731 FrozenLayout_SourceGroup: fsg, 724 FrozenLayout_SourceGroup: fsg,
732 layout: l, 725 layout: l,
733 title: title(sgName), 726 title: title(sgName),
734 sources: make(map[title]*layoutSource, len(fsg.Source)), 727 sources: make(map[title]*layoutSource, len(fsg.Source)),
735 } 728 }
736 729
737 for srcName, fs := range fsg.Source { 730 for srcName, fs := range fsg.Source {
738 src := layoutSource{ 731 src := layoutSource{
739 FrozenLayout_Source: fs, 732 FrozenLayout_Source: fs,
740 sg: &sg, 733 sg: &sg,
741 title: title(srcName), 734 title: title(srcName),
742 } 735 }
743 sg.sources[src.title] = &src 736 sg.sources[src.title] = &src
744 } 737 }
745 738
746 l.sourceGroups[sg.title] = &sg 739 l.sourceGroups[sg.title] = &sg
747 } 740 }
748 741
749 // Build our internally-connected structures from the frozen layout. 742 // Build our internally-connected structures from the frozen layout.
750 if err := l.loadApps(c); err != nil { 743 if err := l.loadApps(c); err != nil {
751 » » return errors.Annotate(err).Reason("failed to load applications from [%(path)s]"). 744 » » return errors.Annotate(err, "failed to load applications from [% s]", l.ApplicationsPath).Err()
752 » » » D("path", l.ApplicationsPath).Err()
753 } 745 }
754 if err := l.loadDeployments(c); err != nil { 746 if err := l.loadDeployments(c); err != nil {
755 » » return errors.Annotate(err).Reason("failed to load deployments f rom [%(path)s]"). 747 » » return errors.Annotate(err, "failed to load deployments from [%s ]", l.DeploymentsPath).Err()
756 » » » D("path", l.DeploymentsPath).Err()
757 } 748 }
758 return nil 749 return nil
759 } 750 }
760 751
761 func (l *deployLayout) loadApps(c context.Context) error { 752 func (l *deployLayout) loadApps(c context.Context) error {
762 fis, err := ioutil.ReadDir(l.ApplicationsPath) 753 fis, err := ioutil.ReadDir(l.ApplicationsPath)
763 if err != nil { 754 if err != nil {
764 » » return errors.Annotate(err).Reason("failed to read directory").E rr() 755 » » return errors.Annotate(err, "failed to read directory").Err()
765 } 756 }
766 apps := make(map[title]*deploy.Application, len(fis)) 757 apps := make(map[title]*deploy.Application, len(fis))
767 var appBase deploy.Application 758 var appBase deploy.Application
768 err = unmarshalTextProtobufDir(l.ApplicationsPath, fis, &appBase, func(n ame string) error { 759 err = unmarshalTextProtobufDir(l.ApplicationsPath, fis, &appBase, func(n ame string) error {
769 cpy := appBase 760 cpy := appBase
770 761
771 t, err := titleFromConfigPath(name) 762 t, err := titleFromConfigPath(name)
772 if err != nil { 763 if err != nil {
773 » » » return errors.Annotate(err).Reason("invalid application title").Err() 764 » » » return errors.Annotate(err, "invalid application title") .Err()
774 } 765 }
775 766
776 apps[t] = &cpy 767 apps[t] = &cpy
777 return nil 768 return nil
778 }) 769 })
779 if err != nil { 770 if err != nil {
780 return err 771 return err
781 } 772 }
782 773
783 l.apps = make(map[title]*layoutApp, len(apps)) 774 l.apps = make(map[title]*layoutApp, len(apps))
784 for t, app := range apps { 775 for t, app := range apps {
785 proj := layoutApp{ 776 proj := layoutApp{
786 Application: app, 777 Application: app,
787 title: t, 778 title: t,
788 components: make(map[title]*layoutAppComponent, len(app .Component)), 779 components: make(map[title]*layoutAppComponent, len(app .Component)),
789 } 780 }
790 781
791 // Initialize components. These can't actually be populated unti l we have 782 // Initialize components. These can't actually be populated unti l we have
792 // loaded our sources. 783 // loaded our sources.
793 for _, comp := range proj.Component { 784 for _, comp := range proj.Component {
794 compT := title(comp.Name) 785 compT := title(comp.Name)
795 if err := compT.validate(); err != nil { 786 if err := compT.validate(); err != nil {
796 » » » » return errors.Annotate(err).Reason("application %(app)q component %(component)q is not a valid component title"). 787 » » » » return errors.Annotate(err, "application %q comp onent %q is not a valid component title", t, comp.Name).Err()
797 » » » » » D("app", t).D("component", comp.Name).Er r()
798 } 788 }
799 proj.components[compT] = &layoutAppComponent{ 789 proj.components[compT] = &layoutAppComponent{
800 Application_Component: comp, 790 Application_Component: comp,
801 proj: &proj, 791 proj: &proj,
802 title: compT, 792 title: compT,
803 } 793 }
804 } 794 }
805 795
806 l.apps[t] = &proj 796 l.apps[t] = &proj
807 } 797 }
808 return nil 798 return nil
809 } 799 }
810 800
811 func (l *deployLayout) loadDeployments(c context.Context) error { 801 func (l *deployLayout) loadDeployments(c context.Context) error {
812 fis, err := ioutil.ReadDir(l.DeploymentsPath) 802 fis, err := ioutil.ReadDir(l.DeploymentsPath)
813 if err != nil { 803 if err != nil {
814 » » return errors.Annotate(err).Reason("failed to read directory").E rr() 804 » » return errors.Annotate(err, "failed to read directory").Err()
815 } 805 }
816 deployments := make(map[title]*deploy.Deployment, len(fis)) 806 deployments := make(map[title]*deploy.Deployment, len(fis))
817 var deploymentBase deploy.Deployment 807 var deploymentBase deploy.Deployment
818 err = unmarshalTextProtobufDir(l.DeploymentsPath, fis, &deploymentBase, func(name string) error { 808 err = unmarshalTextProtobufDir(l.DeploymentsPath, fis, &deploymentBase, func(name string) error {
819 cpy := deploymentBase 809 cpy := deploymentBase
820 810
821 t, err := titleFromConfigPath(name) 811 t, err := titleFromConfigPath(name)
822 if err != nil { 812 if err != nil {
823 » » » return errors.Annotate(err).Reason("invalid deployment t itle").Err() 813 » » » return errors.Annotate(err, "invalid deployment title"). Err()
824 } 814 }
825 815
826 deployments[t] = &cpy 816 deployments[t] = &cpy
827 return nil 817 return nil
828 }) 818 })
829 if err != nil { 819 if err != nil {
830 return err 820 return err
831 } 821 }
832 822
833 l.deployments = make(map[title]*layoutDeployment, len(deployments)) 823 l.deployments = make(map[title]*layoutDeployment, len(deployments))
834 for t, d := range deployments { 824 for t, d := range deployments {
835 dep, err := l.loadDeployment(t, d) 825 dep, err := l.loadDeployment(t, d)
836 if err != nil { 826 if err != nil {
837 » » » return errors.Annotate(err).Reason("failed to load deplo yment (%(deployment)q)"). 827 » » » return errors.Annotate(err, "failed to load deployment ( %q)", t).Err()
838 » » » » D("deployment", t).Err()
839 } 828 }
840 l.deployments[t] = dep 829 l.deployments[t] = dep
841 l.deploymentNames = append(l.deploymentNames, dep.title) 830 l.deploymentNames = append(l.deploymentNames, dep.title)
842 } 831 }
843 832
844 return nil 833 return nil
845 } 834 }
846 835
847 func (l *deployLayout) loadDeployment(t title, d *deploy.Deployment) (*layoutDep loyment, error) { 836 func (l *deployLayout) loadDeployment(t title, d *deploy.Deployment) (*layoutDep loyment, error) {
848 dep := layoutDeployment{ 837 dep := layoutDeployment{
849 Deployment: d, 838 Deployment: d,
850 l: l, 839 l: l,
851 title: t, 840 title: t,
852 sg: l.sourceGroups[title(d.SourceGroup)], 841 sg: l.sourceGroups[title(d.SourceGroup)],
853 } 842 }
854 if dep.sg == nil { 843 if dep.sg == nil {
855 » » return nil, errors.Reason("unknown source group %(sourceGroup)q" ). 844 » » return nil, errors.Reason("unknown source group %q", d.SourceGro up).Err()
856 » » » D("sourceGroup", d.SourceGroup).Err()
857 } 845 }
858 846
859 // Resolve our application. 847 // Resolve our application.
860 dep.app = l.apps[title(dep.Application)] 848 dep.app = l.apps[title(dep.Application)]
861 if dep.app == nil { 849 if dep.app == nil {
862 » » return nil, errors.Reason("unknown application %(app)q").D("app" , dep.Application).Err() 850 » » return nil, errors.Reason("unknown application %q", dep.Applicat ion).Err()
863 } 851 }
864 852
865 // Initialize our Components. Their protobufs cannot not be loaded until 853 // Initialize our Components. Their protobufs cannot not be loaded until
866 // we have a checkout. 854 // we have a checkout.
867 dep.components = make(map[title]*layoutDeploymentComponent, len(dep.app. components)) 855 dep.components = make(map[title]*layoutDeploymentComponent, len(dep.app. components))
868 for compTitle, projComp := range dep.app.components { 856 for compTitle, projComp := range dep.app.components {
869 comp := layoutDeploymentComponent{ 857 comp := layoutDeploymentComponent{
870 reldir: deployDirname(projComp.Path), 858 reldir: deployDirname(projComp.Path),
871 dep: &dep, 859 dep: &dep,
872 comp: projComp, 860 comp: projComp,
873 sources: []*layoutSource{dep.sg.sources[title(projComp.S ource)]}, 861 sources: []*layoutSource{dep.sg.sources[title(projComp.S ource)]},
874 } 862 }
875 if comp.sources[0] == nil { 863 if comp.sources[0] == nil {
876 » » » return nil, errors.Reason("application references non-ex istent source %(source)q"). 864 » » » return nil, errors.Reason("application references non-ex istent source %q", projComp.Source).Err()
877 » » » » D("source", projComp.Source).Err()
878 } 865 }
879 for _, os := range projComp.OtherSource { 866 for _, os := range projComp.OtherSource {
880 src := dep.sg.sources[title(os)] 867 src := dep.sg.sources[title(os)]
881 if src == nil { 868 if src == nil {
882 » » » » return nil, errors.Reason("application reference s non-existent other source %(source)q"). 869 » » » » return nil, errors.Reason("application reference s non-existent other source %q", os).Err()
883 » » » » » D("source", os).Err()
884 } 870 }
885 comp.sources = append(comp.sources, src) 871 comp.sources = append(comp.sources, src)
886 } 872 }
887 873
888 dep.components[compTitle] = &comp 874 dep.components[compTitle] = &comp
889 dep.componentNames = append(dep.componentNames, compTitle) 875 dep.componentNames = append(dep.componentNames, compTitle)
890 } 876 }
891 877
892 // Build a map of cloud project names. 878 // Build a map of cloud project names.
893 if dep.CloudProject != nil { 879 if dep.CloudProject != nil {
894 cp := layoutDeploymentCloudProject{ 880 cp := layoutDeploymentCloudProject{
895 Deployment_CloudProject: dep.CloudProject, 881 Deployment_CloudProject: dep.CloudProject,
896 dep: &dep, 882 dep: &dep,
897 } 883 }
898 if l.cloudProjects == nil { 884 if l.cloudProjects == nil {
899 l.cloudProjects = make(map[string]*layoutDeploymentCloud Project) 885 l.cloudProjects = make(map[string]*layoutDeploymentCloud Project)
900 } 886 }
901 if cur, ok := l.cloudProjects[cp.Name]; ok { 887 if cur, ok := l.cloudProjects[cp.Name]; ok {
902 » » » return nil, errors.Reason("cloud project %(name)q define d by both %(curDep)q and %(thisDep)q"). 888 » » » return nil, errors.Reason("cloud project %q defined by b oth %q and %q", cp.Name, cur.dep.title, dep.title).Err()
903 » » » » D("name", cp.Name).D("curDep", cur.dep.title).D( "thisDep", dep.title).Err()
904 } 889 }
905 l.cloudProjects[cp.Name] = &cp 890 l.cloudProjects[cp.Name] = &cp
906 891
907 if len(dep.CloudProject.GkeCluster) > 0 { 892 if len(dep.CloudProject.GkeCluster) > 0 {
908 cp.gkeClusters = make(map[string]*layoutDeploymentGKEClu ster, len(dep.CloudProject.GkeCluster)) 893 cp.gkeClusters = make(map[string]*layoutDeploymentGKEClu ster, len(dep.CloudProject.GkeCluster))
909 for _, gke := range dep.CloudProject.GkeCluster { 894 for _, gke := range dep.CloudProject.GkeCluster {
910 gkeCluster := layoutDeploymentGKECluster{ 895 gkeCluster := layoutDeploymentGKECluster{
911 Deployment_CloudProject_GKECluster: gke, 896 Deployment_CloudProject_GKECluster: gke,
912 cloudProject: &cp, 897 cloudProject: &cp,
913 } 898 }
914 899
915 // Bind Components to their GKE cluster. 900 // Bind Components to their GKE cluster.
916 for _, b := range gke.Pod { 901 for _, b := range gke.Pod {
917 comp := dep.components[title(b.Name)] 902 comp := dep.components[title(b.Name)]
918 switch { 903 switch {
919 case comp == nil: 904 case comp == nil:
920 » » » » » » return nil, errors.Reason("unkno wn component %(comp)q for cluster %(name)q"). 905 » » » » » » return nil, errors.Reason("unkno wn component %q for cluster %q", b.Name, gke.Name).Err()
921 » » » » » » » D("comp", b.Name).D("nam e", gke.Name).Err()
922 906
923 case b.Replicas <= 0: 907 case b.Replicas <= 0:
924 » » » » » » return nil, errors.Reason("GKE c omponent %(comp)q must have at least 1 replica"). 908 » » » » » » return nil, errors.Reason("GKE c omponent %q must have at least 1 replica", b.Name).Err()
925 » » » » » » » D("comp", b.Name).Err()
926 } 909 }
927 910
928 bp := &layoutDeploymentGKEPodBinding{ 911 bp := &layoutDeploymentGKEPodBinding{
929 Deployment_CloudProject_GKEClust er_PodBinding: b, 912 Deployment_CloudProject_GKEClust er_PodBinding: b,
930 cluster: &gkeCluster, 913 cluster: &gkeCluster,
931 } 914 }
932 comp.gkePods = append(comp.gkePods, bp) 915 comp.gkePods = append(comp.gkePods, bp)
933 gkeCluster.pods = append(gkeCluster.pods , bp) 916 gkeCluster.pods = append(gkeCluster.pods , bp)
934 } 917 }
935 918
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after
968 switch st, err := os.Stat(path); { 951 switch st, err := os.Stat(path); {
969 case err == nil: 952 case err == nil:
970 if !st.IsDir() { 953 if !st.IsDir() {
971 return path, nil 954 return path, nil
972 } 955 }
973 956
974 case isNotExist(err): 957 case isNotExist(err):
975 break 958 break
976 959
977 default: 960 default:
978 » » » return "", errors.Annotate(err).Reason("failed to state %(path)q"). 961 » » » return "", errors.Annotate(err, "failed to state %q", pa th).Err()
979 » » » » D("path", path).Err()
980 } 962 }
981 963
982 // Walk up one directory. 964 // Walk up one directory.
983 oldDir := dir 965 oldDir := dir
984 dir, _ = filepath.Split(dir) 966 dir, _ = filepath.Split(dir)
985 if oldDir == dir { 967 if oldDir == dir {
986 » » » return "", errors.Reason("could not find %(filename)q st arting from %(dir)q"). 968 » » » return "", errors.Reason("could not find %q starting fro m %q", filename, dir).Err()
987 » » » » D("filename", filename).D("dir", dir).Err()
988 } 969 }
989 } 970 }
990 } 971 }
991 972
992 type componentRegistrar interface { 973 type componentRegistrar interface {
993 addGAEModule(*layoutDeploymentGAEModule) 974 addGAEModule(*layoutDeploymentGAEModule)
994 addGKEPod(*layoutDeploymentGKEPodBinding) 975 addGKEPod(*layoutDeploymentGKEPodBinding)
995 } 976 }
OLDNEW
« no previous file with comments | « deploytool/cmd/luci_deploy/kubernetes.go ('k') | deploytool/cmd/luci_deploy/manage.go » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698