// Lint applies linting to a given ytt template
Lint applies linting to a given ytt template
// Lint applies linting to a given ytt template
func (l *Linter) Lint(data, filename string) []LinterError {
	docSet, err := yamlmeta.NewDocumentSetFromBytes([]byte(data), yamlmeta.DocSetOpts{AssociatedName: filename})
	if err != nil {
		msg := err.Error()
		match := lineErrRegexp.FindStringSubmatch(msg)
		line, err := strconv.Atoi(match[1])
		if err != nil {
			panic(err)
		}
		msg = match[2]
		return []LinterError{{
			Msg: msg,
			Pos: fmt.Sprintf("%s:%d", filename, line),
		}}
	}
	injectIfHandling(docSet)
	injectStringTemplateHandling(docSet)
	compiledTemplate, err := yamltemplate.NewTemplate(filename, yamltemplate.TemplateOpts{
		IgnoreUnknownComments: true,
	}).Compile(docSet)
	if err != nil {
		fmt.Printf("NewTemplate: %s\n", err.Error())
		os.Exit(1)
	}
	loader := myTemplateLoader{compiledTemplate: compiledTemplate, name: filename}
	loader.TemplateLoader = workspace.NewTemplateLoader(&yamlmeta.Document{}, core.NewPlainUI(false), workspace.TemplateLoaderOpts{
		IgnoreUnknownComments: true,
	}, nil)
	var rootLib *workspace.Library
	loader.api, rootLib = newAPIandLib(filename, compiledTemplate.TplReplaceNode, loader)
	thread := &starlark.Thread{Name: "test", Load: loader.Load}
	thread.SetLocal("ytt.curr_library_key", rootLib)
	thread.SetLocal("ytt.root_library_key", rootLib)
	_, newVal, err := compiledTemplate.Eval(thread, loader)
	if err != nil {
		multiErr, ok := err.(template.CompiledTemplateMultiError)
		if ok {
			return mapMultierrorToLinterror(multiErr, filename)
		}
		fmt.Printf("Eval: %s\n", err.Error())
		os.Exit(1)
	}
	errors := make([]LinterError, 0)
	for _, doc := range newVal.(*yamlmeta.DocumentSet).Items {
		gvk, item := extractKind(doc)
		var err error
		var schema *v1.JSONSchemaProps
		if gvk.kind != "" {
			schema, err = loadK8SSchema(gvk)
			if err != nil {
				errors = append(errors,
					appendLocationIfKnownf(item, "Error loading schema for kind %s: %v\n", gvk.kind, err.Error()))
				continue
			}
		} else if isConcoursePipeline(doc) {
			schema, err = loadConcourseSchema()
			if err != nil {
				panic(err)
			}
		} else {
			continue
		}
		subSchema := convert(doc.Value)
		if subSchema.Description == "" && doc.Position.IsKnown() {
			doc.Position.SetFile(filename)
			subSchema.Description = doc.Position.AsString()
		}
		subErrors := l.isSubset(schema.Definitions, subSchema, schema, "")
		errors = append(errors, subErrors...)
	}
	return errors
}
func ( l * Linter ) Lint ( data , filename string ) [ ] LinterError { docSet , err := yamlmeta . NewDocumentSetFromBytes ( [ ] byte ( data ) , yamlmeta . DocSetOpts { AssociatedName : filename } ) if err != nil { msg := err . Error ( ) match := lineErrRegexp . FindStringSubmatch ( msg ) line , err := strconv . Atoi ( match [ 1 ] ) if err != nil { panic ( err ) } msg = match [ 2 ] return [ ] LinterError { { Msg : msg , Pos : fmt . Sprintf ( " " , filename , line ) , } } } injectIfHandling ( docSet ) injectStringTemplateHandling ( docSet ) compiledTemplate , err := yamltemplate . NewTemplate ( filename , yamltemplate . TemplateOpts { IgnoreUnknownComments : true , } ) . Compile ( docSet ) if err != nil { fmt . Printf ( " \n " , err . Error ( ) ) os . Exit ( 1 ) } loader := myTemplateLoader { compiledTemplate : compiledTemplate , name : filename } loader . TemplateLoader = workspace . NewTemplateLoader ( & yamlmeta . Document { } , core . NewPlainUI ( false ) , workspace . TemplateLoaderOpts { IgnoreUnknownComments : true , } , nil ) var rootLib * workspace . Library loader . api , rootLib = newAPIandLib ( filename , compiledTemplate . TplReplaceNode , loader ) thread := & starlark . Thread { Name : " " , Load : loader . Load } thread . SetLocal ( " " , rootLib ) thread . SetLocal ( " " , rootLib ) _ , newVal , err := compiledTemplate . Eval ( thread , loader ) if err != nil { multiErr , ok := err . ( template . CompiledTemplateMultiError ) if ok { return mapMultierrorToLinterror ( multiErr , filename ) } fmt . Printf ( " \n " , err . Error ( ) ) os . Exit ( 1 ) } errors := make ( [ ] LinterError , 0 ) for _ , doc := range newVal . ( * yamlmeta . DocumentSet ) . Items { gvk , item := extractKind ( doc ) var err error var schema * v1 . JSONSchemaProps if gvk . kind != " " { schema , err = loadK8SSchema ( gvk ) if err != nil { errors = append ( errors , appendLocationIfKnownf ( item , " \n " , gvk . kind , err . Error ( ) ) ) continue } } else if isConcoursePipeline ( doc ) { schema , err = loadConcourseSchema ( ) if err != nil { panic ( err ) } } else { continue } subSchema := convert ( doc . Value ) if subSchema . Description == " " && doc . Position . IsKnown ( ) { doc . Position . SetFile ( filename ) subSchema . Description = doc . Position . AsString ( ) } subErrors := l . isSubset ( schema . Definitions , subSchema , schema , " " ) errors = append ( errors , subErrors ... ) } return errors }
Lint applies linting to a given ytt template
Lint applies linting to a given ytt template
//fmt.Printf("### ast:\n") //docSet.Print(os.Stdout) //docSet.Print(os.Stdout) //fmt.Printf("### template:\n%s\n", compiledTemplate.DebugCodeAsString()) //fmt.Printf("### result ast:\n") //newVal.(*yamlmeta.DocumentSet).Print(os.Stdout) //combinedDocBytes, err := newVal.(*yamlmeta.DocumentSet).AsBytesWithPrinter(nil) //if err != nil { //	fmt.Printf(err.Error()) //	os.Exit(1) //} //fmt.Printf("### result\n") //fmt.Printf("%s\n", combinedDocBytes) //schemaBytes, err := newVal.(*yamlmeta.DocumentSet).AsBytesWithPrinter( //	func(w io.Writer) yamlmeta.DocumentPrinter { return &schemaPrinter{buf: w} }) //if err != nil { //	fmt.Printf(err.Error()) //	os.Exit(1) //} //fmt.Printf("### schema\n") //fmt.Printf("%s\n", schemaBytes) // TODO: print warning if not a trivial document