github.com/qri-io/qri@v0.10.1-0.20220104210721-c771715036cb/transform/startf/ds/bound.go (about)

     1  package ds
     2  
     3  import (
     4  	"fmt"
     5  
     6  	"github.com/qri-io/dataset"
     7  	"github.com/qri-io/starlib/dataframe"
     8  	"go.starlark.net/starlark"
     9  )
    10  
    11  // BoundDataset represents the datset a transform script is bound to
    12  type BoundDataset struct {
    13  	frozen       bool
    14  	commitCalled bool
    15  	latest       *dataset.Dataset
    16  	outconf      *dataframe.OutputConfig
    17  	onCommit     func(ds *Dataset) error
    18  	load         func(refstr string) (*Dataset, error)
    19  }
    20  
    21  // compile-time interface assertions
    22  var (
    23  	_ starlark.Value    = (*BoundDataset)(nil)
    24  	_ starlark.HasAttrs = (*BoundDataset)(nil)
    25  )
    26  
    27  // NewBoundDataset constructs a target dataset
    28  func NewBoundDataset(latest *dataset.Dataset, outconf *dataframe.OutputConfig, onCommit func(ds *Dataset) error) *BoundDataset {
    29  	return &BoundDataset{latest: latest, onCommit: onCommit, outconf: outconf}
    30  }
    31  
    32  // String returns the Dataset as a string
    33  func (b *BoundDataset) String() string { return b.stringify() }
    34  
    35  // Type returns a short string describing the value's type.
    36  func (BoundDataset) Type() string { return fmt.Sprintf("%s.BoundDataset", "dataset") }
    37  
    38  // Freeze renders Dataset immutable.
    39  func (b *BoundDataset) Freeze() { b.frozen = true }
    40  
    41  // Hash cannot be used with Dataset
    42  func (b *BoundDataset) Hash() (uint32, error) {
    43  	return 0, fmt.Errorf("unhashable: %s", b.Type())
    44  }
    45  
    46  // Truth converts the dataset into a bool
    47  func (b *BoundDataset) Truth() starlark.Bool { return true }
    48  
    49  // Attr gets a value for a string attribute
    50  func (b *BoundDataset) Attr(name string) (starlark.Value, error) {
    51  	return builtinAttr(b, name, boundDatasetMethods)
    52  }
    53  
    54  // AttrNames lists available attributes
    55  func (b *BoundDataset) AttrNames() []string {
    56  	return builtinAttrNames(boundDatasetMethods)
    57  }
    58  
    59  func (b *BoundDataset) stringify() string { return "<BoundDataset>" }
    60  
    61  // methods defined on the history object
    62  var boundDatasetMethods = map[string]*starlark.Builtin{
    63  	"latest": starlark.NewBuiltin("latest", head),
    64  	"commit": starlark.NewBuiltin("commit", commit),
    65  }
    66  
    67  func head(thread *starlark.Thread, builtin *starlark.Builtin, args starlark.Tuple, kwargs []starlark.Tuple) (starlark.Value, error) {
    68  	self := builtin.Receiver().(*BoundDataset)
    69  	return NewDataset(self.latest, self.outconf), nil
    70  }
    71  
    72  func commit(thread *starlark.Thread, builtin *starlark.Builtin, args starlark.Tuple, kwargs []starlark.Tuple) (starlark.Value, error) {
    73  	self := builtin.Receiver().(*BoundDataset)
    74  	if self.commitCalled {
    75  		return nil, fmt.Errorf("commit can only be called once in a transform script")
    76  	}
    77  	starDs := &Dataset{}
    78  	if err := starlark.UnpackArgs("commit", args, kwargs, "ds", starDs); err != nil {
    79  		return starlark.None, err
    80  	}
    81  	if self.onCommit != nil {
    82  		if err := self.onCommit(starDs); err != nil {
    83  			return starlark.None, err
    84  		}
    85  	}
    86  
    87  	self.commitCalled = true
    88  	return starlark.None, nil
    89  }