ETH-Pantheon / Aion

A system for Scheduling transactions with arbitrary bytecode on the Ethereum Network
https://www.aion.ethpantheon.com
MIT License
26 stars 13 forks source link

Having trouble getting schedule call to work. #7

Closed kblacker closed 5 years ago

kblacker commented 5 years ago

The code is written to ping a recurring request/call to my oracle contract every 10 minutes. This should return the current price of Ethereum as well as +1 to the myData counter. I am unable to get the "schedulemyfunction" function to work. I was able to successfully compile and deploy the code and when I input my Oracle contract address and job ID for the "myfucntion" function everything works fine, I get the current price and my counter increases by +1. 1 LINK is also paid to the oracle contract for fulfilling the request. But when I click to initiate the "schedulemyfunction" in remix It allows me to confirm the transaction through metamask and the transaction comes back successful on etherescan but nothing happens. I wait 10-15 min and I still see no schedule call. What am I doing wrong?

I am using this on ropsten testnet.

recurring.txt

ETH-Pantheon commented 5 years ago

Hello Kblacker

Your code looks OK. Can you please to share the address of the contract that schedules the transactions? Like this, we can check these requests on the servers and determine if these were executed or not and why.

The possible reason for the schedule to not to be executed is that the amount of gas is insufficient to execute myFunction logic (on your code). Note, that in Aion you can pass more gas than needed to avoid these situations and Aion estimate the used gas onchain and return the remaining to the original requester.

kblacker commented 5 years ago

Oracle Contract address: 0x74e9d81d4d4183ebd77e601fe03fce070204e399

Below are links to the etherscan reports:

When I call "myfunction" directly in remix: https://ropsten.etherscan.io/tx/0xbd10afea6f80c364ab538eaa8a2f43b249d2010dddba1805c295cbf61caa4d52

When I call "schedulemyfunction" in remix: https://ropsten.etherscan.io/tx/0xbc58a4e1e194ca106c841c6f492418dfb6c53992984bd31e8e9c2ef40e592d69

recurring1

When I go to depoly "MyContract" in remix and leave the "Value" text box at the top right empty I get a "gas estimation failed" error. If I deploy this contact with at least .005 ETH as the "Value" the contract gets confirmed through metamask and deploys just fine. Is this normal? Also where do I specify the amount of gas to send to Aion?

ETH-Pantheon commented 5 years ago

Your contract, according to the transactions is 0x8F8Bcd0b0BbEfA30d72E4b783CA7f651C7E01E4F, but you reported 0x74e9d81d4d4183ebd77e601fe03fce070204e399 so I am assuming that there is some confusion.

Etherscan show that Aion has been calling back your contract, see here the last call from Aion to your contract (https://ropsten.etherscan.io/tx/0x554654ebf569d36f4a6aeb5068ae67d1de2dd9c0bcb1efbf4bc1ca209e3d2de1) you can see it was successful and generated an event (Executed), with AionID 4982

However, after checking your code Aion is not calling myFunction, instead it will call the fallback function of the contract, because the data variable is not calculated correctly. In short, you should do as follows:

function myfucntion(address _oracle, string _jobId) public onlyOwner {
        Chainlink.Request memory req = buildChainlinkRequest(stringToBytes32(_jobId), this, this.fulfillEthereumPrice.selector);
        req.add("get", "https://min-api.cryptocompare.com/data/price?fsym=ETH&tsyms=USD");
        req.add("path", "USD");
        req.addInt("times", 100);
        sendChainlinkRequestTo(_oracle, req, ORACLE_PAYMENT);
        myData = myData+1;

        aion = Aion(0xFcFB45679539667f7ed55FA59A15c8Cad73d9a4E);
        bytes memory data = abi.encodeWithSelector(bytes4(keccak256('myfucntion(address,string)')),_oracle,_jobId);
        uint256 gaslimit = 500000;
        uint callCost = gaslimit*1e9 + aion.serviceFee();
        aion.ScheduleCall.value(callCost)( block.timestamp + 10 minutes, address(this), 0, gaslimit, 1e9, data, true);
    }

you can remove then schedulemyfunction from the code, now myFunction do the chainlink part and the schedule part.

Notice I made the gaslimit = 500000, you should change this to ensure that is enough for the chainlink request, I am guessing 500000 should be enough

About your other questions:

The example contract that you are using, request a call automatically when you deploy it (see the constructor), therefore the contract should have ether to pay for the gas and fee of the scheduled transaction, that is why you get an error is you do not send ether when you are deploying.

The function to schedule is: function ScheduleCall(uint256 blocknumber, address to, uint256 value, uint256 gaslimit, uint256 gasprice, bytes data, bool schedType) public payable returns (uint,address); You can see the description of each variable in the main page of the repository (here in Github) In your code, this function is called with a gaslimit amount of 200000, you can increase this number if needed.

Let us know.

Note: for testing, you can change the interval from 10 minutes to something smaller so that you don't have to wait that much. However, the faster that is can be is 12 blocks which is the minimum number of confirmations required by Aion.

kblacker commented 5 years ago

Unfortunately that did not work either. I implemented the code you provided which is posted below and it compiled without error. I deployed the new contract with .005ETH. I funded the contract with 10 LINK just to test. Once again the function operates correctly for the first call but no calls are scheduled after (I.e. every 5 minutes). I have included the ropten etherscan report for this transaction as well.

Code: recurring2.txt

"MyContract" Contract address: 0xc3cc976400f045f87e2a4d483c99c18a3782d926

Oracle contract address: 0x74e9d81d4d4183ebd77e601fe03fce070204e399

Etherscan: https://ropsten.etherscan.io/tx/0x3400960e7ddb72088f5e9f08d695a383ce62662c9a6cb7da75fc09034eab5868

ETH-Pantheon commented 5 years ago

Hi Kblacker

The internal transactions in your contract show that Aion called back but the transactions failed. The myfunction method has a modifier onlyOwner. When Aion tries to call myfunction the result of the modifier is false (because Aion is not the Owner) and the transaction fails. So just remove OnlyOwner (if you don't want anyone else to call your function, you can check that the caller is Aion)

I deployed this (including the chainlink contracts) removing the onlyOwner modifier in myfunctionand is running perfectly (address 0x5ae937ee7147b7f8aa13d5d1727542ae5785cfe9), Aion is calling this contract every 5 minutes: see the contract internal transactions here: https://ropsten.etherscan.io/address/0x5ae937ee7147b7f8aa13d5d1727542ae5785cfe9#internaltx

Let me know if you have more questions

kblacker commented 5 years ago

You were exactly right, I completely overlooked that. I removed it as well, deployed the contract and the code is working perfectly. Thank you so much for your help!