2.3GetEntryScriptHash 在智能合约的调用中,有直接调用者就有间接调用者(跨合约调用)。GetEntryScriptHash,它会返回入口(最初)调用者的脚本哈希。我们准备两个智能合约,合约A与合约B,假定合约A来调用合约B的功能函数。 合约B的代码如下: fromontology.interop.System.ExecutionEngineimportGetExecutingScriptHash,GetCallingScriptHash,GetEntryScriptHash fromontology.interop.System.RuntimeimportCheckWitness,GetTime,Notify,Serialize,Deserialize defMain(operation,args): ifoperation=="invokeB": returninvokeB() ifoperation=="avoidToBeInvokedByContract": returnavoidToBeInvokedByContract() returnFalse definvokeB(): #theresultofGetCallingScriptHashandGetEntryScriptHashissame #iftheyareinvokedbythesamecontract callerHash=GetCallingScriptHash() entryHash=GetEntryScriptHash() Notify([callerHash,entryHash]) return[callerHash,entryHash] defavoidToBeInvokedByContract(): #thepurposeistopreventhackfromothercontract callerHash=GetCallingScriptHash() entryHash=GetEntryScriptHash() ifcallerHash!=entryHash: Notify(["Youarenotallowedtoinvokethismethodthroughcontract"]) returnFalse else: Notify(["Youcanimplementwhatyouneedtodohere!"]) returnTrue 合约A的代码如下,该合约调用合约B。 fromontology.interop.System.AppimportRegisterAppCall fromontology.interop.System.ExecutionEngineimportGetExecutingScriptHash,GetCallingScriptHash,GetEntryScriptHash fromontology.interop.System.RuntimeimportCheckWitness,GetTime,Notify,Serialize,Deserialize ContractB=RegisterAppCall("0f44f18d37515a917364362ec256c2110a7b1377","operation","args") defMain(operation,args): ifoperation=="invokeA": opt=args[0] returninvokeA(opt) ifoperation=="checkHash": returncheckHash() returnFalse definvokeA(opt): callerHash=GetCallingScriptHash() entryHash=GetEntryScriptHash() Notify(["111_invokeA",callerHash,entryHash]) returnContractB(opt,[]) defcheckHash(): Notify(["111_checkHash"]) callerHash=GetCallingScriptHash() entryHash=GetEntryScriptHash() Notify([callerHash,entryHash]) returnTrue 如图,首先运行checkHash函数,我们发现在同一个合约的同一个函数中,调用GetCallingScriptHash与GetEntryScriptHashAPI返回值相同,都是"a37ca1f1a3421d36b504769a96c06024a07b2bfa"。这是因为他们既是直接调用者,也是最初调用者(没有跨合约调用),所以两个API返回值相同。但如果跨合约调用呢? |