The easiest way to get something you can copy is probably to run daml build
in a terminal and copy it from there. Alternatively, click on View -> Problems
via the top menu and that should show you the full error as well.
I also suggest to share the code snippet via a github gist if possible, that way we can sort out the indentation issues fast.
In View â Problems, this is the only error message displayed.
What Iâd like to see is the line number which should be displayed there and the line numbers of the original code snippet (or as mentioned above, ideally the full code snippet) so we can see which part of the code is causing the error.
I see one syntax problem in these blocks:
"DV1" ->
let
data1 = RD
with
a = devSecCon.abc
b = dvSecCon.def
return (data1)
Here the value return (data1)
is inside the let block
. That doesnât work. Every element in a let
block must have the form var = expr
.
The thing on the right hand side of the ->
must itself be an expression. There are two possibilities:
Using let..in...
"DV1" ->
let
data1 = RD
with
a = devSecCon.abc
b = dvSecCon.def
in return (data1)
or using do
"DV1" -> do
let
data1 = RD
with
a = devSecCon.abc
b = dvSecCon.def
return (data1)
@Pris17 as a general pointer, a lot of the topics discussed here are covered in the introductory documentation to Daml: An introduction to Daml â Daml SDK 1.14.0 documentation
I can highly recommend working your way through that.
Both of above possibilities doesnât work. I still have indentation issues. After going with 2nd option from your reply, I am now getting below error on the closing bracket of forA loop.
parse error (possibly incorrect indentation or mismatched brackets)parser
I even tried removing do and indenting return. return is not inside let now. Still I face below error
parse error on input âreturnâparser
I can only echo what @cocreature said above: Without complete, reproducible code-samples, it is very difficult to diagnose and help.
I can see two other issues in that latest code snippet. First, the value produced by forA
will be a list, so you will not be able to bind it to a pair ((DVData1, DVData2) <- ...
). Second, Daml requires that identifiers that start with an uppercase letter be types, while identifiers that start with a lowercase letter be values. Hence, Daml will interpret DVData1
as a type and it is not valid to have a type in that position. You can correct that one by just changing to dvData1
instead.
You have not explained what it is you are actually trying to do, which makes helping you a lot more difficult. From what I can gather so far, the code youâre trying to write will:
- Take a list of parties and a specific identifier
- For each party, try to find a contract with that identifier as (part of) its key
- Return the data from the contract
I donât know why you want to do that, and there are a few caveats Iâll go into afterwards, but here is a self-contained sample code that does something like that:
module Main where
import Daml.Script
template ContractA
with
sig: Party
id: Text
arg1: Text
arg2: Int
where
signatory sig
key (sig, id) : (Party, Text)
maintainer key._1
data Result = Result with a: Text, b: Int
deriving (Eq, Show)
template ContractB
with
sig: Party
payload: [Result]
where
signatory sig
template DoStuff
with
sig: Party
where
signatory sig
preconsuming choice CreateContractB : ContractId ContractB
with parties: [Party]
id: Text
controller sig
do
-- Note: results is a list
results <- forA parties (\party -> do
(cid, payload) <- fetchByKey @ContractA (party, id)
case partyToText party of
"Alice" -> do
let data1 = Result
with
a = payload.arg1
b = payload.arg2
return data1
"Bob" -> do
let data2 = Result
with
a = payload.arg1
b = payload.arg2
return data2
_ -> error "No valid party")
create ContractB with payload = results, ..
setup : Script ()
setup = script do
alice <- allocatePartyWithHint "Alice" (PartyIdHint "Alice")
bob <- allocatePartyWithHint "Bob" (PartyIdHint "Bob")
carol <- allocatePartyWithHint "Carol" (PartyIdHint "Carol")
-- Fails because no ContractA contract exists yet
submitMustFail alice do
createAndExerciseCmd (DoStuff alice) CreateContractB with parties = [alice, bob], id = "id"
submit alice do
createCmd ContractA with sig = alice, id = "id", arg1 = "some text", arg2 = 42
-- succeeds because there is one contract for Alice and Alice can see it
submit alice do
createAndExerciseCmd (DoStuff alice) CreateContractB with parties = [alice], id = "id"
-- fails because there is no contract for Bob, so the `fetchByKey` command fails
submitMustFail alice do
createAndExerciseCmd (DoStuff alice) CreateContractB with parties = [alice, bob], id = "id"
return ()
This is all syntactically correct, and vaguely looks like your code. However, there are a number of issues with this design:
- The
CreateContractB
choice will fail as soon as you cannot fetch a contract in the given list of parties, either because you cannot see it (see Daml privacy rules and specifically rules for fetching a contract by key). - The choice will also fail as soon as the list passed in as a parameter contains anything else than
alice
orbob
, because of the explicitcase
on party name (and the expliciterror
rather than just ignoring non-matching names). It will also fail on most other ledgers than sandbox, because in general party names are not strictly equal to the given hint. - Youâd be much better off filtering the list of parties before sending it to the choice.
- This code is, ultimately, doing the same thing for both
"Bob"
and"Alice"
cases, so it could be rewritten without a case at all.
Without knowing what you are trying to achieve, itâs hard to tell you where to go from here, but hopefully this will help a bit.
TC.daml (1.2 KB)
I have attached the code here. There is parse error on line number 38.
@bernhard @Gary_Verhaegen Can you please quickly take a look at the code snippet and help me resolve the issue. Thanks
You didnât follow either of my suggestions. The blocks after ->
contain neither do
nor in
.
There are a couple of other indentation issues. The closing bracket in line 46 needs to be indented more, and the create in line 48, too. Then you have a missing semicolon in line 48.
TC.daml (1.3 KB)
Attached is updated file. Neither of both the above mentioned works. Using let âŚin as well as doâŚThey give errors on line number 47. Attached code has do inside the case. Still it throws error on line 47.
Error is:
parse error (possibly incorrect indentation or mismatched brackets)parser
Here is the module free of syntax errors:
module TC where
data SRData = SRData
with
a: Text
b: Text
deriving (Eq, Show)
template MRCreate
with
partyA : Party
id : Text
where
signatory partyA
controller partyA can
nonconsuming TestMR : ContractId MR
with
otherparties : [Party]
do
mcID <- lookupByKey @MR (partyA, id)
case (mcID) of
Some mcId -> return mcId
None -> do
[dv1data, dv2data] <- forA otherparties (\dv -> do
(cID, dvCon) <- fetchByKey @ContractB (dv, id)
case partyToText dv of
"DV1" -> do
let srdata1 = SRData
with a = dvCon.abc
b = dvCon.def
return (srdata1)
"DV2" -> do
let srdata2 = SRData
with a = dvCon.abc
b = dvCon.def
return (srdata2)
_ -> error "No valid DV")
return [dv1data, dv2data]
create MR with sRData1= dv1data; sRData2= dv2data; ..
template MR
with
partyA: Party
sRData1: SRData
sRData2 : SRData
where
signatory partyA
key (partyA, sRData1.a): (Party, Text)
maintainer key._1
It is still failing on the absence of a definition for ContractB
, though.
As a side note, your code uses tabs instead of spaces. I highly recommend against doing that in indentation sensitive languages like python or Daml. It makes it super easy to end up with situations that look like they are indented properly but are not.