Skip to content

Commit

Permalink
Draft: automate exporting CV spec
Browse files Browse the repository at this point in the history
  • Loading branch information
bastjan committed Aug 5, 2024
1 parent 2e9cc92 commit 3cc08a5
Show file tree
Hide file tree
Showing 3 changed files with 160 additions and 0 deletions.
97 changes: 97 additions & 0 deletions tools/importcvspec/importcvspec.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,97 @@
package main

import (
"fmt"
"go/ast"
"go/build"
"go/importer"
"go/parser"
"go/token"
"go/types"
"log"

"golang.org/x/exp/maps"
)

func main() {
fset := token.NewFileSet()

pkg := parseWithTypes(fset)
fmt.Println("Package parsed and type checked", pkg.Name())

cvs := pkg.Scope().Lookup("ClusterVersionSpec")
if cvs == nil {
log.Fatal("ClusterVersionSpec not found")
}
fmt.Println("ClusterVersionSpec found")
fmt.Println(types.ObjectString(cvs, types.RelativeTo(pkg)))
str, ok := cvs.Type().Underlying().(*types.Struct)
if !ok {
log.Fatal("ClusterVersionSpec is not a struct")
}

toExport := extractNamed([]types.Object{cvs}, str)

fmt.Println("####################")

for _, obj := range toExport {
fmt.Println(types.ObjectString(obj, types.RelativeTo(pkg)))
}

fmt.Println("####################")

}

func extractNamed(toExport []types.Object, cvs types.Type) []types.Object {
switch t := cvs.(type) {
case *types.Named:
fmt.Println("Named type", t.Obj())
toExport = append(toExport, t.Obj())
toExport = extractNamed(toExport, t.Underlying())
case *types.Basic:
case *types.Pointer:
toExport = extractNamed(toExport, t.Elem())
case *types.Array:
toExport = extractNamed(toExport, t.Elem())
case *types.Slice:
toExport = extractNamed(toExport, t.Elem())
case *types.Map:
toExport = extractNamed(toExport, t.Key())
toExport = extractNamed(toExport, t.Elem())
case *types.Struct:
for i := 0; i < t.NumFields(); i++ {
field := t.Field(i)
fmt.Printf("%s (%T)\n", field.String(), field.Type())
toExport = extractNamed(toExport, field.Type())
}
default:
log.Fatalf("Type not yet supported %T", t)
}
return toExport
}

func parseWithTypes(fset *token.FileSet) *types.Package {
imp, err := build.Import("github.com/openshift/api/config/v1", "", build.FindOnly)
if err != nil {
log.Fatal(err)
}
fmt.Println("Import from: ", imp.Dir)
rawPkgs, err := parser.ParseDir(fset, imp.Dir, nil, parser.SkipObjectResolution)
if err != nil {
log.Fatal(err)
}
rawPkg := rawPkgs["v1"]
info := types.Info{
Types: make(map[ast.Expr]types.TypeAndValue),
Defs: make(map[*ast.Ident]types.Object),
Uses: make(map[*ast.Ident]types.Object),
}
conf := types.Config{
Importer: importer.ForCompiler(fset, "source", nil),
}
pkg, err := conf.Check(imp.Dir, fset, maps.Values(rawPkg.Files), &info)
if err != nil {
log.Fatal(err)
}
return pkg
}
48 changes: 48 additions & 0 deletions tools/impt/impt_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
package impt_test

import (
"fmt"
"go/ast"
"go/build"
"go/importer"
"go/parser"
"go/token"
"go/types"
"log"
"testing"

"golang.org/x/exp/maps"
)

func TestImport(t *testing.T) {
fset := token.NewFileSet()
pt := parseWithTypes(fset)
fmt.Println("Package parsed and type checked", pt.Name())
fmt.Println("Package path", pt)
}

func parseWithTypes(fset *token.FileSet) *types.Package {
imp, err := build.Import("github.com/appuio/openshift-upgrade-controller/tools/toimp", "", build.FindOnly)
if err != nil {
log.Fatal(err)
}
fmt.Println("Import from: ", imp.Dir)
rawPkgs, err := parser.ParseDir(fset, imp.Dir, nil, parser.SkipObjectResolution)
if err != nil {
log.Fatal(err)
}
rawPkg := rawPkgs["toimp"]
info := types.Info{
Types: make(map[ast.Expr]types.TypeAndValue),
Defs: make(map[*ast.Ident]types.Object),
Uses: make(map[*ast.Ident]types.Object),
}
conf := types.Config{
Importer: importer.ForCompiler(fset, "source", nil),
}
pkg, err := conf.Check(imp.Dir, fset, maps.Values(rawPkg.Files), &info)
if err != nil {
log.Fatal(err)
}
return pkg
}
15 changes: 15 additions & 0 deletions tools/toimp/toimp.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
package toimp

import configv1 "github.com/openshift/api/config/v1"

type ClusterID string

type LocalSpec struct {
ClusterID ClusterID `json:"clusterID"`
}

func Convert(ls LocalSpec) configv1.ClusterVersionSpec {
cvs := configv1.ClusterVersionSpec{}
cvs.ClusterID = configv1.ClusterID(ls.ClusterID)
return cvs
}

0 comments on commit 3cc08a5

Please sign in to comment.