Hey peers!
I have a simple function that writes maps (string -> string).
stateful entrypoint set_map(new_map : map(string, string)) : bool =
only_owner()
filter_put(set_map_at_index, Map.to_list(new_map), [])
true
Every set_map call returns a transaction Id.
The question:
Is that somehow possible to retrieve a transaction id of the latest set_map call for a specific Map key?
E.g.
- first we call
set_map
with { "key1": "value1"}
and as a result it returns a transaction id (let’s call it txid_1
)
- then we call
set_map
with { "key1": "value1_altered"}
and as a result it returns a transaction id (let’s call it txid_2
)
- we want to have a function which accepts
"key1"
string as an argument and returns us txid_2
from the latest set_map
call.
Hello @markin.io
@botanicalcarebot.chain or @hanssv.chain, can you please help here?
Thank you,
Albena
1 Like
If I am reading your code correctly set_map
will return a boolean (and it will always be true
) not sure what transaction id you are referring to?
I’m sorry I can’t figure out what you are trying to do, where does txid_1
come from?
Hello, Hans.
The transaction ids I’m referring to (txid_1, txid_2, txid_n) are being returned by the JavaScript SDK after the successful invocations of the set_map
function.
const map = {
"key1": "value_1",
"key2": "value_2
}
contractInstance.call("set_map", [map]).then(contractResult => {
const transactionId = contractResult.hash
})
Let’s say, that we would like to show this transaction ID to a user of our system, but due to some limitations we can store transaction ids within our database only for a limited period of time.
Hence the necessity for the retrieving a transaction ID by the map key.
I’m not very familiar with the JS SDK, but if you want to store the hash of the contract result on-chain I guess you have to make another call to (another) contract - the caveat is that the result of the contract call can’t be available in the call itself (chicken and egg problem).
It sounds like a somewhat strange use case, but nothing stops you from having another contract (or another map in the same contract) where you can write down {"key1" : transactionId }
…
I’m sorry for not being clear. We haven’t considered storing the hash of the contract result on-chain.
The transaction is there already after the set_map
call, so if we know hash, we can check the transaction via æternity Explorer, and that’s the actual business logic - we want to provide a link to the transaction for the end-user.
The problem here is that transaction ids are being wiped out from our database within a week, hence we we can’t display the transaction URL to a user after this period.
But we still know the keys of the map which has been written using the set_map
method.
So, having this in mind is that somehow possible to say via smart contract:
Aeternity, please give me the hash of the latest transaction that has been created by set_map
function, and the map key was “key1”
?
This was the bit that mainly confused me, why you remember some things but not others…
In a smart contract context, I don’t think the transaction hash is available while running the transaction, so you would have to do it after the fact, like I suggested by keeping a second map in a contract that connects map-key and transaction hash. Extending the runtime environment of the (FATE) VM with the current transaction hash could be done, it would make your task easier.
In a node context, it isn’t part of the basic node (and will never be) It sounds very much like some sort of chain indexing functionality… I don’t think the middleware/aeternal has this yet, but perhaps something like this is feasible as an add-on?!
2 Likes
I guess @markin.io is talking about functionality similar to what etherscan offers for contract call transactions, but in sort-of reverse order (?)
Example:
(off-chain implementation): Currently you can implement it by having as script which connects to a middleware instance -> and looks for all of the transactions (contractCalls) for your particular contract address. Then lookup the event log (you need to properly emit on-chain events via Chain.event
in your sophia contract) -> decode (via the js-sdk), filter the results -> get your answer.
1 Like
Hey Milen. Nice to hear from you.
As I understand, this solution assumes fetching of the whole transaction history for a specific contract. Is that correct?
I’m asking because I’m concerned about the possible peformance impact of this method since we are expecting a huge amount of transactions to happen.
Hey,
As @hanssv.chain already mentioned such indexing is not yet implemented, so the solution I proposed is just a workaround you can DIY for your use-case (not sure how performant it will be).
If you want you can as well extend the middleware functionality as well.
1 Like
Thank you very much for the assistance. We are going to use this solution.