Deprecation of using Divulged Contracts

The minimal example is something like the following

module Main where

import Daml.Script

template T
  with
    p : Party
  where
    signatory p

template Fetcher
  with
    sig : Party
    obs : Party
  where
    signatory sig
    observer obs
    nonconsuming choice Fetch : T
      with
        cid : ContractId T
      controller obs
      do fetch cid

test = script do
  p1 <- allocateParty "p1"
  p2 <- allocateParty "p2"
  cid <- submit p1 $ createCmd (T p1)
  fetcher <- submit p1 $ createCmd (Fetcher p1 p2)
  divulger <- submit p2 $ createCmd (Fetcher p2 p1)
  submitMustFail p2 $ exerciseCmd fetcher (Fetch cid)
  submit p1 $ exerciseCmd divulger (Fetch cid)
  submit p2 $ exerciseCmd fetcher (Fetch cid)
  pure ()

Let’s walk through this:

  1. There is a contract cid where p1 is the only stakeholder.
  2. There is a contract fetcher which is signed by p1 and has p2 as an observer. That contract allows p2 to fetch a contract with p1’s authorization.
  3. However, if you try that, you’ll get an error saying that the contract is not visible to the submitter.
  4. Now, we create a divulger contract which is the same as fetcher but with the roles switched.
  5. p1 can execute the Fetch here since they are a stakeholder on cid. Because p2 is a signatory on the contract they see the exercise so they also see the fetch meaning the contract is divulged to them. So far, everything works as it should and none of this is deprecated.
  6. Currently, step 5 permanently changes things such that step 3 will now succeed because p2 has seen the contract once in step 5. This is the part that is deprecated.

This might all sound a bit confusing so let me try to provide an explanation of what works rather than what doesn’t:
For a transaction to not rely on divulgence of previous transactions, all contracts fetched, exercised, … in the current transaction must have one or more stakeholders in the union of actAs and readAs parties of the sumission.

3 Likes