mirror of
				https://github.com/Instadapp/aave-protocol-v2.git
				synced 2024-07-29 21:47:30 +00:00 
			
		
		
		
	
		
			
				
	
	
		
			313 lines
		
	
	
		
			9.3 KiB
		
	
	
	
		
			TypeScript
		
	
	
	
	
	
			
		
		
	
	
			313 lines
		
	
	
		
			9.3 KiB
		
	
	
	
		
			TypeScript
		
	
	
	
	
	
| import { MAX_UINT_AMOUNT, ZERO_ADDRESS } from '../../helpers/constants';
 | |
| import { BUIDLEREVM_CHAINID } from '../../helpers/buidler-constants';
 | |
| import { buildPermitParams, getSignatureFromTypedData } from '../../helpers/contracts-helpers';
 | |
| import { expect } from 'chai';
 | |
| import { ethers } from 'ethers';
 | |
| import { makeSuite, TestEnv } from './helpers/make-suite';
 | |
| import { DRE } from '../../helpers/misc-utils';
 | |
| import { waitForTx } from '../../helpers/misc-utils';
 | |
| import { _TypedDataEncoder } from 'ethers/lib/utils';
 | |
| 
 | |
| const { parseEther } = ethers.utils;
 | |
| 
 | |
| makeSuite('AToken: Permit', (testEnv: TestEnv) => {
 | |
|   it('Checks the domain separator', async () => {
 | |
|     const { aDai } = testEnv;
 | |
|     const separator = await aDai.DOMAIN_SEPARATOR();
 | |
| 
 | |
|     const domain = {
 | |
|       name: await aDai.name(),
 | |
|       version: '1',
 | |
|       chainId: DRE.network.config.chainId,
 | |
|       verifyingContract: aDai.address,
 | |
|     };
 | |
|     const domainSeparator = _TypedDataEncoder.hashDomain(domain);
 | |
| 
 | |
|     expect(separator).to.be.equal(domainSeparator, 'Invalid domain separator');
 | |
|   });
 | |
| 
 | |
|   it('Get aDAI for tests', async () => {
 | |
|     const { dai, pool, deployer } = testEnv;
 | |
| 
 | |
|     await dai.mint(parseEther('20000'));
 | |
|     await dai.approve(pool.address, parseEther('20000'));
 | |
| 
 | |
|     await pool.deposit(dai.address, parseEther('20000'), deployer.address, 0);
 | |
|   });
 | |
| 
 | |
|   it('Reverts submitting a permit with 0 expiration', async () => {
 | |
|     const { aDai, deployer, users } = testEnv;
 | |
|     const owner = deployer;
 | |
|     const spender = users[1];
 | |
| 
 | |
|     const tokenName = await aDai.name();
 | |
| 
 | |
|     const chainId = DRE.network.config.chainId || BUIDLEREVM_CHAINID;
 | |
|     const expiration = 0;
 | |
|     const nonce = (await aDai._nonces(owner.address)).toNumber();
 | |
|     const permitAmount = ethers.utils.parseEther('2').toString();
 | |
|     const msgParams = buildPermitParams(
 | |
|       chainId,
 | |
|       aDai.address,
 | |
|       '1',
 | |
|       tokenName,
 | |
|       owner.address,
 | |
|       spender.address,
 | |
|       nonce,
 | |
|       permitAmount,
 | |
|       expiration.toFixed()
 | |
|     );
 | |
| 
 | |
|     const ownerPrivateKey = require('../../test-wallets.js').accounts[0].secretKey;
 | |
|     if (!ownerPrivateKey) {
 | |
|       throw new Error('INVALID_OWNER_PK');
 | |
|     }
 | |
| 
 | |
|     expect((await aDai.allowance(owner.address, spender.address)).toString()).to.be.equal(
 | |
|       '0',
 | |
|       'INVALID_ALLOWANCE_BEFORE_PERMIT'
 | |
|     );
 | |
| 
 | |
|     const { v, r, s } = getSignatureFromTypedData(ownerPrivateKey, msgParams);
 | |
| 
 | |
|     await expect(
 | |
|       aDai
 | |
|         .connect(spender.signer)
 | |
|         .permit(owner.address, spender.address, permitAmount, expiration, v, r, s)
 | |
|     ).to.be.revertedWith('INVALID_EXPIRATION');
 | |
| 
 | |
|     expect((await aDai.allowance(owner.address, spender.address)).toString()).to.be.equal(
 | |
|       '0',
 | |
|       'INVALID_ALLOWANCE_AFTER_PERMIT'
 | |
|     );
 | |
|   });
 | |
| 
 | |
|   it('Submits a permit with maximum expiration length', async () => {
 | |
|     const { aDai, deployer, users } = testEnv;
 | |
|     const owner = deployer;
 | |
|     const spender = users[1];
 | |
| 
 | |
|     const chainId = DRE.network.config.chainId || BUIDLEREVM_CHAINID;
 | |
|     const deadline = MAX_UINT_AMOUNT;
 | |
|     const nonce = (await aDai._nonces(owner.address)).toNumber();
 | |
|     const permitAmount = parseEther('2').toString();
 | |
|     const msgParams = buildPermitParams(
 | |
|       chainId,
 | |
|       aDai.address,
 | |
|       '1',
 | |
|       await aDai.name(),
 | |
|       owner.address,
 | |
|       spender.address,
 | |
|       nonce,
 | |
|       deadline,
 | |
|       permitAmount
 | |
|     );
 | |
| 
 | |
|     const ownerPrivateKey = require('../../test-wallets.js').accounts[0].secretKey;
 | |
|     if (!ownerPrivateKey) {
 | |
|       throw new Error('INVALID_OWNER_PK');
 | |
|     }
 | |
| 
 | |
|     expect((await aDai.allowance(owner.address, spender.address)).toString()).to.be.equal(
 | |
|       '0',
 | |
|       'INVALID_ALLOWANCE_BEFORE_PERMIT'
 | |
|     );
 | |
| 
 | |
|     const { v, r, s } = getSignatureFromTypedData(ownerPrivateKey, msgParams);
 | |
| 
 | |
|     await waitForTx(
 | |
|       await aDai
 | |
|         .connect(spender.signer)
 | |
|         .permit(owner.address, spender.address, permitAmount, deadline, v, r, s)
 | |
|     );
 | |
| 
 | |
|     expect((await aDai._nonces(owner.address)).toNumber()).to.be.equal(1);
 | |
|   });
 | |
| 
 | |
|   it('Cancels the previous permit', async () => {
 | |
|     const { aDai, deployer, users } = testEnv;
 | |
|     const owner = deployer;
 | |
|     const spender = users[1];
 | |
| 
 | |
|     const chainId = DRE.network.config.chainId || BUIDLEREVM_CHAINID;
 | |
|     const deadline = MAX_UINT_AMOUNT;
 | |
|     const nonce = (await aDai._nonces(owner.address)).toNumber();
 | |
|     const permitAmount = '0';
 | |
|     const msgParams = buildPermitParams(
 | |
|       chainId,
 | |
|       aDai.address,
 | |
|       '1',
 | |
|       await aDai.name(),
 | |
|       owner.address,
 | |
|       spender.address,
 | |
|       nonce,
 | |
|       deadline,
 | |
|       permitAmount
 | |
|     );
 | |
| 
 | |
|     const ownerPrivateKey = require('../../test-wallets.js').accounts[0].secretKey;
 | |
|     if (!ownerPrivateKey) {
 | |
|       throw new Error('INVALID_OWNER_PK');
 | |
|     }
 | |
| 
 | |
|     const { v, r, s } = getSignatureFromTypedData(ownerPrivateKey, msgParams);
 | |
| 
 | |
|     expect((await aDai.allowance(owner.address, spender.address)).toString()).to.be.equal(
 | |
|       ethers.utils.parseEther('2'),
 | |
|       'INVALID_ALLOWANCE_BEFORE_PERMIT'
 | |
|     );
 | |
| 
 | |
|     await waitForTx(
 | |
|       await aDai
 | |
|         .connect(spender.signer)
 | |
|         .permit(owner.address, spender.address, permitAmount, deadline, v, r, s)
 | |
|     );
 | |
|     expect((await aDai.allowance(owner.address, spender.address)).toString()).to.be.equal(
 | |
|       permitAmount,
 | |
|       'INVALID_ALLOWANCE_AFTER_PERMIT'
 | |
|     );
 | |
| 
 | |
|     expect((await aDai._nonces(owner.address)).toNumber()).to.be.equal(2);
 | |
|   });
 | |
| 
 | |
|   it('Tries to submit a permit with invalid nonce', async () => {
 | |
|     const { aDai, deployer, users } = testEnv;
 | |
|     const owner = deployer;
 | |
|     const spender = users[1];
 | |
| 
 | |
|     const chainId = DRE.network.config.chainId || BUIDLEREVM_CHAINID;
 | |
|     const deadline = MAX_UINT_AMOUNT;
 | |
|     const nonce = 1000;
 | |
|     const permitAmount = '0';
 | |
|     const msgParams = buildPermitParams(
 | |
|       chainId,
 | |
|       aDai.address,
 | |
|       '1',
 | |
|       await aDai.name(),
 | |
|       owner.address,
 | |
|       spender.address,
 | |
|       nonce,
 | |
|       deadline,
 | |
|       permitAmount
 | |
|     );
 | |
| 
 | |
|     const ownerPrivateKey = require('../../test-wallets.js').accounts[0].secretKey;
 | |
|     if (!ownerPrivateKey) {
 | |
|       throw new Error('INVALID_OWNER_PK');
 | |
|     }
 | |
| 
 | |
|     const { v, r, s } = getSignatureFromTypedData(ownerPrivateKey, msgParams);
 | |
| 
 | |
|     await expect(
 | |
|       aDai
 | |
|         .connect(spender.signer)
 | |
|         .permit(owner.address, spender.address, permitAmount, deadline, v, r, s)
 | |
|     ).to.be.revertedWith('INVALID_SIGNATURE');
 | |
|   });
 | |
| 
 | |
|   it('Tries to submit a permit with invalid expiration (previous to the current block)', async () => {
 | |
|     const { aDai, deployer, users } = testEnv;
 | |
|     const owner = deployer;
 | |
|     const spender = users[1];
 | |
| 
 | |
|     const chainId = DRE.network.config.chainId || BUIDLEREVM_CHAINID;
 | |
|     const expiration = '1';
 | |
|     const nonce = (await aDai._nonces(owner.address)).toNumber();
 | |
|     const permitAmount = '0';
 | |
|     const msgParams = buildPermitParams(
 | |
|       chainId,
 | |
|       aDai.address,
 | |
|       '1',
 | |
|       await aDai.name(),
 | |
|       owner.address,
 | |
|       spender.address,
 | |
|       nonce,
 | |
|       expiration,
 | |
|       permitAmount
 | |
|     );
 | |
| 
 | |
|     const ownerPrivateKey = require('../../test-wallets.js').accounts[0].secretKey;
 | |
|     if (!ownerPrivateKey) {
 | |
|       throw new Error('INVALID_OWNER_PK');
 | |
|     }
 | |
| 
 | |
|     const { v, r, s } = getSignatureFromTypedData(ownerPrivateKey, msgParams);
 | |
| 
 | |
|     await expect(
 | |
|       aDai
 | |
|         .connect(spender.signer)
 | |
|         .permit(owner.address, spender.address, expiration, permitAmount, v, r, s)
 | |
|     ).to.be.revertedWith('INVALID_EXPIRATION');
 | |
|   });
 | |
| 
 | |
|   it('Tries to submit a permit with invalid signature', async () => {
 | |
|     const { aDai, deployer, users } = testEnv;
 | |
|     const owner = deployer;
 | |
|     const spender = users[1];
 | |
| 
 | |
|     const chainId = DRE.network.config.chainId || BUIDLEREVM_CHAINID;
 | |
|     const deadline = MAX_UINT_AMOUNT;
 | |
|     const nonce = (await aDai._nonces(owner.address)).toNumber();
 | |
|     const permitAmount = '0';
 | |
|     const msgParams = buildPermitParams(
 | |
|       chainId,
 | |
|       aDai.address,
 | |
|       '1',
 | |
|       await aDai.name(),
 | |
|       owner.address,
 | |
|       spender.address,
 | |
|       nonce,
 | |
|       deadline,
 | |
|       permitAmount
 | |
|     );
 | |
| 
 | |
|     const ownerPrivateKey = require('../../test-wallets.js').accounts[0].secretKey;
 | |
|     if (!ownerPrivateKey) {
 | |
|       throw new Error('INVALID_OWNER_PK');
 | |
|     }
 | |
| 
 | |
|     const { v, r, s } = getSignatureFromTypedData(ownerPrivateKey, msgParams);
 | |
| 
 | |
|     await expect(
 | |
|       aDai
 | |
|         .connect(spender.signer)
 | |
|         .permit(owner.address, ZERO_ADDRESS, permitAmount, deadline, v, r, s)
 | |
|     ).to.be.revertedWith('INVALID_SIGNATURE');
 | |
|   });
 | |
| 
 | |
|   it('Tries to submit a permit with invalid owner', async () => {
 | |
|     const { aDai, deployer, users } = testEnv;
 | |
|     const owner = deployer;
 | |
|     const spender = users[1];
 | |
| 
 | |
|     const chainId = DRE.network.config.chainId || BUIDLEREVM_CHAINID;
 | |
|     const expiration = MAX_UINT_AMOUNT;
 | |
|     const nonce = (await aDai._nonces(owner.address)).toNumber();
 | |
|     const permitAmount = '0';
 | |
|     const msgParams = buildPermitParams(
 | |
|       chainId,
 | |
|       aDai.address,
 | |
|       '1',
 | |
|       await aDai.name(),
 | |
|       owner.address,
 | |
|       spender.address,
 | |
|       nonce,
 | |
|       expiration,
 | |
|       permitAmount
 | |
|     );
 | |
| 
 | |
|     const ownerPrivateKey = require('../../test-wallets.js').accounts[0].secretKey;
 | |
|     if (!ownerPrivateKey) {
 | |
|       throw new Error('INVALID_OWNER_PK');
 | |
|     }
 | |
| 
 | |
|     const { v, r, s } = getSignatureFromTypedData(ownerPrivateKey, msgParams);
 | |
| 
 | |
|     await expect(
 | |
|       aDai
 | |
|         .connect(spender.signer)
 | |
|         .permit(ZERO_ADDRESS, spender.address, expiration, permitAmount, v, r, s)
 | |
|     ).to.be.revertedWith('INVALID_OWNER');
 | |
|   });
 | |
| });
 | 
