How can I use an interface' method from within a template choice

G-d willing

Hello,
I wrote a simple template that implements a simple interface. Here is the beginning of the code that works:

data MyView = MyView with
    party_1 : Party
    party_2 : Party
    amount : Decimal
    period : Decimal
  deriving (Eq, Show)

interface MyInterface where
  viewtype MyView

  getAmount : Decimal
  getPeriod : Decimal
  getTotalAmount : Decimal

template MyTemplate 
  with
    myView : MyView
  where
    signatory myView.party_1
    observer myView.party_2

    interface instance MyInterface for MyTemplate where
      view = myView
      getAmount = 100.0
      getPeriod = 12.0
      getTotalAmount = 1200.0

At this point, I want to do 2 things, which I can’t seem to figure out how to do:

  1. How can I make the getTotalAmount function instead returning a hardcoded value, to return a calculation of other functions, such as:
      getTotalAmount = getAmount * getPeriod

This one does not work, I am getting this error:

Couldn't match type ‘Numeric 10’ with ‘MyInterface -> Decimal’
        arising from a functional dependency between:
          constraint ‘DA.Internal.Desugar.HasMethod
                        MyInterface "getTotalAmount" (MyInterface -> Decimal)’
            arising from a use of ‘DA.Internal.Desugar.mkMethod’
          instance ‘DA.Internal.Desugar.HasMethod
                      MyInterface "getTotalAmount" Decimal’

At the same time, how do I use these functions inside a choice of the template. For example, I would like to have the following choice:

    nonconsuming choice CalcTotalAmount : Decimal 
      controller myView.party_1
        do
          return getTotalAmount 

I am getting the same error message when using the function inside that choice.

Thanks,

All interface methods define a function that takes an argument of type Interface (MyInterface in your example). So to use them either to define another method or within a choice you need to pass that argument.

In your example, that is just this, i.e,. the value of MyTemplate which you can convert to MyInterface using toInterface:

template MyTemplate 
  with
    myView : MyView
  where
    signatory myView.party_1
    observer myView.party_2

    interface instance MyInterface for MyTemplate where
      view = myView
      getAmount = 100.0
      getPeriod = 12.0
      getTotalAmount = getAmount (toInterface this) * getPeriod (toInterface this)

    nonconsuming choice CalcTotalAmount : Decimal 
      controller myView.party_1
        do
          return (getTotalAmount (toInterface this))
1 Like