-
Notifications
You must be signed in to change notification settings - Fork 9
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Handle anonymous environments when injecting it to the context #250
Conversation
} | ||
|
||
func newCopier() copier { | ||
return copier{memo: map[*Value]*Value{}} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I can merge this to reuse the copier between eval/val and this
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think it's fine to have two implementations for now: using the generic copier feels a bit risky to me given the sensitivity of the *value
graph to proper memoized copies.
FWIW, the *Value
s don't have the same restrictions, so we could also simplify this by removing the memoization.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
one change re: not mutating execcontexts, but generally looks good.
environment.go
Outdated
func (ec *ExecContext) Values(envName string) map[string]Value { | ||
context := ec.values | ||
context["currentEnvironment"] = NewValue(map[string]Value{ | ||
"name": NewValue(envName), | ||
}) | ||
|
||
if ec.rootEvironment == AnonymousEnvironmentName || ec.rootEvironment == "" { | ||
ec.rootEvironment = envName | ||
} | ||
|
||
context["rootEnvironment"] = NewValue(map[string]Value{ | ||
"name": NewValue(ec.rootEvironment), | ||
}) | ||
|
||
return context | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'd prefer not to mutate the values here. I'd prefer that we instead copy the context for each envName
and set the values in Copy
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
environment.go
Outdated
return context | ||
} | ||
|
||
var ErrForbiddenContextkey = errors.New("forbidden context key") |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nit: we generally use "reserved" for keys that the user is not allowed to set
var ErrForbiddenContextkey = errors.New("forbidden context key") | |
var ErrReservedContextkey = errors.New("reserved context key") |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
} | ||
|
||
func newCopier() copier { | ||
return copier{memo: map[*Value]*Value{}} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think it's fine to have two implementations for now: using the generic copier feels a bit risky to me given the sensitivity of the *value
graph to proper memoized copies.
FWIW, the *Value
s don't have the same restrictions, so we could also simplify this by removing the memoization.
environment.go
Outdated
func (ec *ExecContext) Copy() *ExecContext { | ||
return &ExecContext{ | ||
values: ec.values, | ||
rootEvironment: ec.rootEvironment, | ||
} | ||
} | ||
|
||
func (ec *ExecContext) Values(envName string) map[string]Value { | ||
context := copyContext(ec.values) | ||
context["currentEnvironment"] = NewValue(map[string]Value{ | ||
"name": NewValue(envName), | ||
}) | ||
|
||
if ec.rootEvironment == AnonymousEnvironmentName || ec.rootEvironment == "" { | ||
ec.rootEvironment = envName | ||
} | ||
|
||
context["rootEnvironment"] = NewValue(map[string]Value{ | ||
"name": NewValue(ec.rootEvironment), | ||
}) | ||
|
||
return context | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
sorry, I think I wasn't clear here. this is what I was suggesting:
func (ec *ExecContext) Copy() *ExecContext { | |
return &ExecContext{ | |
values: ec.values, | |
rootEvironment: ec.rootEvironment, | |
} | |
} | |
func (ec *ExecContext) Values(envName string) map[string]Value { | |
context := copyContext(ec.values) | |
context["currentEnvironment"] = NewValue(map[string]Value{ | |
"name": NewValue(envName), | |
}) | |
if ec.rootEvironment == AnonymousEnvironmentName || ec.rootEvironment == "" { | |
ec.rootEvironment = envName | |
} | |
context["rootEnvironment"] = NewValue(map[string]Value{ | |
"name": NewValue(ec.rootEvironment), | |
}) | |
return context | |
} | |
func (ec *ExecContext) Copy(envName string) *ExecContext { | |
values := copyContext(ec.values) | |
values["currentEnvironment"] = NewValue(map[string]Value{ | |
"name": NewValue(envName), | |
}) | |
root := ec.rootEnvironment | |
if ec.rootEvironment == AnonymousEnvironmentName || ec.rootEvironment == "" { | |
root = envName | |
} | |
values["rootEnvironment"] = NewValue(map[string]Value{ | |
"name": NewValue(root), | |
}) | |
return &ExecContext{ | |
values: values, | |
rootEvironment: root, | |
} | |
} | |
func (ec *ExecContext) Values() map[string]Value { | |
return ec.values | |
} |
With this approach the contents of a context are never mutated once the context is created.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ah I misunderstood. I thought the concern was mutating the value we have in memory, not the place were we mutate. Done
environment.go
Outdated
if ec.rootEvironment == AnonymousEnvironmentName || ec.rootEvironment == "" { | ||
ec.rootEvironment = envName | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this is still mutating ec
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
yes that is needed to propagate the root environment down the line
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
context.environment
intorootEnvironment
andcurrentEnvironment
(potentially justenvironment
)rootEnvironment
will evaluate to the rootest non anonymous environment for the imported environments (wont propagate to the root)Having these 3 envs:
In the case the
root
env is anonymous, it resolves:In the case the
root
env is a named environment, it resolves: