Skip to content

Commit

Permalink
Support for std.thisFile, fixes google#91.
Browse files Browse the repository at this point in the history
Sadly it means that std in no longer the same object in each file.
  • Loading branch information
sbarzowski authored and sparkprime committed Oct 3, 2017
1 parent 82f213a commit 774715b
Show file tree
Hide file tree
Showing 6 changed files with 32 additions and 10 deletions.
2 changes: 1 addition & 1 deletion imports.go
Original file line number Diff line number Diff line change
Expand Up @@ -86,7 +86,7 @@ func codeToPV(e *evaluator, filename string, code string) potentialValue {
// The same thinking applies to external variables.
return makeErrorThunk(err)
}
return makeThunk(e.i.initialEnv, node)
return makeThunk(makeInitialEnv(filename, e.i.baseStd), node)
}

func (cache *ImportCache) ImportCode(codeDir, importedPath string, e *evaluator) (value, error) {
Expand Down
36 changes: 27 additions & 9 deletions interpreter.go
Original file line number Diff line number Diff line change
Expand Up @@ -203,7 +203,9 @@ type interpreter struct {

// The clean environment in which we execute imports, extVars as well
// as the main program. It contains std.
initialEnv environment
//initialEnv environment

baseStd valueObject

// Keeps imports
importCache *ImportCache
Expand Down Expand Up @@ -709,7 +711,7 @@ func (i *interpreter) EvalInCleanEnv(fromWhere *TraceElement, env *environment,
return val, err
}

func buildStdObject(i *interpreter) (value, error) {
func buildStdObject(i *interpreter) (valueObject, error) {
objVal, err := evaluateStd(i)
if err != nil {
return nil, err
Expand Down Expand Up @@ -761,6 +763,14 @@ func prepareExtVars(i *interpreter, ext vmExtMap) map[ast.Identifier]potentialVa
return result
}

func buildObject(hide ast.ObjectFieldHide, fields map[string]value) valueObject {
fieldMap := valueSimpleObjectFieldMap{}
for name, v := range fields {
fieldMap[name] = valueSimpleObjectField{hide, &readyValue{v}}
}
return makeValueSimpleObject(bindingFrame{}, fieldMap, nil)
}

func buildInterpreter(ext vmExtMap, maxStack int, importer Importer) (*interpreter, error) {
i := interpreter{
stack: makeCallStack(maxStack),
Expand All @@ -772,18 +782,25 @@ func buildInterpreter(ext vmExtMap, maxStack int, importer Importer) (*interpret
return nil, err
}

i.initialEnv = makeEnvironment(
bindingFrame{
"std": &readyValue{stdObj},
},
makeUnboundSelfBinding(),
)
i.baseStd = stdObj

i.extVars = prepareExtVars(&i, ext)

return &i, nil
}

func makeInitialEnv(filename string, baseStd valueObject) environment {
fileSpecific := buildObject(ast.ObjectFieldHidden, map[string]value{
"thisFile": makeValueString(filename),
})
return makeEnvironment(
bindingFrame{
"std": &readyValue{makeValueExtendedObject(baseStd, fileSpecific)},
},
makeUnboundSelfBinding(),
)
}

func evaluate(node ast.Node, ext vmExtMap, maxStack int, importer Importer) (string, error) {
i, err := buildInterpreter(ext, maxStack, importer)
if err != nil {
Expand All @@ -793,7 +810,8 @@ func evaluate(node ast.Node, ext vmExtMap, maxStack int, importer Importer) (str
evalTrace := &TraceElement{
loc: &evalLoc,
}
result, err := i.EvalInCleanEnv(evalTrace, &i.initialEnv, node)
env := makeInitialEnv(node.Loc().FileName, i.baseStd)
result, err := i.EvalInCleanEnv(evalTrace, &env, node)
if err != nil {
return "", err
}
Expand Down
1 change: 1 addition & 0 deletions testdata/std.thisFile.golden
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
"testdata/std.thisFile"
1 change: 1 addition & 0 deletions testdata/std.thisFile.jsonnet
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
std.thisFile
1 change: 1 addition & 0 deletions testdata/std.thisFile2.golden
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
"testdata/std.thisFile.jsonnet"
1 change: 1 addition & 0 deletions testdata/std.thisFile2.jsonnet
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
import "std.thisFile.jsonnet"

0 comments on commit 774715b

Please sign in to comment.