lang: core, funcs: Port some functions to CallableFunc API
Some modern features of our function engine and language might require this new API, so port what we can and figure out the rest later.
This commit is contained in:
@@ -61,8 +61,9 @@ type ReadFileFunc struct {
|
||||
data *interfaces.FuncData
|
||||
last types.Value // last value received to use for diff
|
||||
|
||||
filename *string // the active filename
|
||||
result *string // last calculated output
|
||||
args []types.Value
|
||||
filename *string // the active filename
|
||||
result types.Value // last calculated output
|
||||
}
|
||||
|
||||
// String returns a simple name for this function. This is needed so this struct
|
||||
@@ -129,7 +130,13 @@ func (obj *ReadFileFunc) Stream(ctx context.Context) error {
|
||||
}
|
||||
obj.last = input // store for next
|
||||
|
||||
filename := input.Struct()[readFileArgNameFilename].Str()
|
||||
args, err := interfaces.StructToCallableArgs(input) // []types.Value, error)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
obj.args = args
|
||||
|
||||
filename := args[0].Str()
|
||||
// TODO: add validation for absolute path?
|
||||
// TODO: add check for empty string
|
||||
if obj.filename != nil && *obj.filename == filename {
|
||||
@@ -137,48 +144,61 @@ func (obj *ReadFileFunc) Stream(ctx context.Context) error {
|
||||
}
|
||||
obj.filename = &filename
|
||||
|
||||
p := strings.TrimSuffix(obj.data.Base, "/")
|
||||
if p == obj.data.Base { // didn't trim, so we fail
|
||||
// programming error
|
||||
return fmt.Errorf("no trailing slash on Base, got: `%s`", p)
|
||||
}
|
||||
path := p
|
||||
|
||||
if !strings.HasPrefix(*obj.filename, "/") {
|
||||
return fmt.Errorf("filename was not absolute, got: `%s`", *obj.filename)
|
||||
//path += "/" // be forgiving ?
|
||||
}
|
||||
path += *obj.filename
|
||||
|
||||
fs, err := obj.init.World.Fs(obj.data.FsURI) // open the remote file system
|
||||
result, err := obj.Call(ctx, obj.args)
|
||||
if err != nil {
|
||||
return errwrap.Wrapf(err, "can't load code from file system `%s`", obj.data.FsURI)
|
||||
}
|
||||
// this is relative to the module dir the func is in!
|
||||
content, err := fs.ReadFile(path) // open the remote file system
|
||||
// We could use it directly, but it feels like less correct.
|
||||
//content, err := obj.data.Fs.ReadFile(path) // open the remote file system
|
||||
if err != nil {
|
||||
return errwrap.Wrapf(err, "can't read file `%s` (%s)", *obj.filename, path)
|
||||
return err
|
||||
}
|
||||
|
||||
result := string(content) // convert to string
|
||||
|
||||
if obj.result != nil && *obj.result == result {
|
||||
// if the result is still the same, skip sending an update...
|
||||
if obj.result != nil && result.Cmp(obj.result) == nil {
|
||||
continue // result didn't change
|
||||
}
|
||||
obj.result = &result // store new result
|
||||
obj.result = result // store new result
|
||||
|
||||
case <-ctx.Done():
|
||||
return nil
|
||||
}
|
||||
|
||||
select {
|
||||
case obj.init.Output <- &types.StrValue{
|
||||
V: *obj.result,
|
||||
}:
|
||||
case obj.init.Output <- obj.result: // send
|
||||
// pass
|
||||
case <-ctx.Done():
|
||||
return nil
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Call this function with the input args and return the value if it is possible
|
||||
// to do so at this time.
|
||||
func (obj *ReadFileFunc) Call(ctx context.Context, args []types.Value) (types.Value, error) {
|
||||
filename := args[0].Str()
|
||||
|
||||
p := strings.TrimSuffix(obj.data.Base, "/")
|
||||
if p == obj.data.Base { // didn't trim, so we fail
|
||||
// programming error
|
||||
return nil, fmt.Errorf("no trailing slash on Base, got: `%s`", p)
|
||||
}
|
||||
path := p
|
||||
|
||||
if !strings.HasPrefix(filename, "/") {
|
||||
return nil, fmt.Errorf("filename was not absolute, got: `%s`", filename)
|
||||
//path += "/" // be forgiving ?
|
||||
}
|
||||
path += filename
|
||||
|
||||
fs, err := obj.init.World.Fs(obj.data.FsURI) // open the remote file system
|
||||
if err != nil {
|
||||
return nil, errwrap.Wrapf(err, "can't load code from file system `%s`", obj.data.FsURI)
|
||||
}
|
||||
// this is relative to the module dir the func is in!
|
||||
content, err := fs.ReadFile(path) // open the remote file system
|
||||
// We could use it directly, but it feels like less correct.
|
||||
//content, err := obj.data.Fs.ReadFile(path) // open the remote file system
|
||||
if err != nil {
|
||||
return nil, errwrap.Wrapf(err, "can't read file `%s` (%s)", filename, path)
|
||||
}
|
||||
|
||||
return &types.StrValue{
|
||||
V: string(content), // convert to string
|
||||
}, nil
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user