Repository: ecadlabs/taquito (ts)

Issue:
[Integration Test] Fix ballot operation test to have a dynamic wait
`integration-tests/sandbox-ballot-operation.spec.ts` have regressed due to sandboxes now having different block times each protocol. Fix the test so that we can unskip it.

The test relies on block timing as well as waiting the proper amount of time until the voting period changes. Adjust the test to dynamically so that it checks wait times of each protocol and formulate a method to wait correctly.

Pull request description:
Repair the broken ballot operation test flextesa
CLOSE #2403

rewrite the test so that it correctly finds exploration phase and posts the ballot.

Patch:
diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml
index af026475e..f5d4081a7 100644
--- a/.github/workflows/main.yml
+++ b/.github/workflows/main.yml
@@ -113,7 +113,15 @@ jobs:
           --protocol-kind ${{ matrix.protocol }}
     - run: npm ci
     - run: npm run build
-    - run: npm -w integration-tests run test:originate-known-contracts && npm -w integration-tests run test:${{ matrix.testnet }}-secret-key -- --testPathIgnorePatterns ledger-signer-failing-tests.spec.ts ledger-signer.spec.ts contract-estimation-tests.spec.ts rpc-get-protocol-constants.spec.ts
+    - run: npm -w integration-tests run test:${{ matrix.testnet }}-secret-key sandbox-ballot-operation.spec.ts
+      env:
+        RUN_${{ matrix.testnet_uppercase }}_WITH_SECRET_KEY: true
+        SECRET_KEY: edsk3QoqBuvdamxouPhin7swCvkQNgq4jP5KZPbwWNnwdZpSpJiEbq
+        TEZOS_RPC_${{ matrix.testnet_uppercase }}: http://localhost:20000
+        POLLING_INTERVAL_MILLISECONDS: 100
+        RPC_CACHE_MILLISECONDS: 0
+        TEZOS_BAKER: tz1VSUr8wwNhLAzempoch5d6hLRiTh8Cjcjb
+    - run: npm -w integration-tests run test:originate-known-contracts && npm -w integration-tests run test:${{ matrix.testnet }}-secret-key -- --testPathIgnorePatterns ledger-signer-failing-tests.spec.ts ledger-signer.spec.ts contract-estimation-tests.spec.ts rpc-get-protocol-constants.spec.ts sandbox-ballot-operation.spec.ts
       env:
         RUN_${{ matrix.testnet_uppercase }}_WITH_SECRET_KEY: true
         SECRET_KEY: edsk3S8mG2sSBmSRbikAcZVLCz4SrCq4DjmsQRic6MGktqNFijfrS2
diff --git a/packages/taquito-rpc/src/types.ts b/packages/taquito-rpc/src/types.ts
index 8d4bd7c1a..82f101ea8 100644
--- a/packages/taquito-rpc/src/types.ts
+++ b/packages/taquito-rpc/src/types.ts
@@ -1291,15 +1291,7 @@ export interface BallotsResponse {
   pass: BigNumber;
 }
 
-export type PeriodKindResponse =
-  | 'proposal'
-  | 'testing_vote'
-  | 'testing'
-  | 'promotion_vote'
-  | 'exploration'
-  | 'cooldown'
-  | 'promotion'
-  | 'adoption';
+export type PeriodKindResponse = 'proposal' | 'exploration' | 'cooldown' | 'promotion' | 'adoption';
 
 export type CurrentProposalResponse = string | null;
 


Test patch:
diff --git a/integration-tests/sandbox-ballot-operation.spec.ts b/integration-tests/sandbox-ballot-operation.spec.ts
index d67205c6f..104dae737 100644
--- a/integration-tests/sandbox-ballot-operation.spec.ts
+++ b/integration-tests/sandbox-ballot-operation.spec.ts
@@ -1,48 +1,81 @@
+import { VotingPeriodBlockResult } from '@taquito/rpc';
+import { InMemorySigner } from '@taquito/signer';
+import { TezosToolkit } from '@taquito/taquito';
 import { CONFIGS, sleep } from './config';
 
-CONFIGS().forEach(async ({ lib, protocol, setup }) => {
-  const Tezos = lib;
+CONFIGS().forEach(async ({ lib, rpc, protocol, setup }) => {
+  const flextesanet = rpc === 'http://localhost:20000' ? test : test.skip;
+  let blocksPerVotingPeriod: number;
+  let blockTime: number;
+  let currentPeriod: VotingPeriodBlockResult;
 
-  describe(`Ballot operation test (${protocol})`, () => {
+  // Our ci flextesa script have 3 bakers Alice, Bob and Charlie (.github/workflows/main.yml)
+  const Alice = lib; // Alice's secret key is passed through the command to run test is configured by integration-tests/config.ts
+  const Bob = new TezosToolkit(rpc);
+  Bob.setSignerProvider(new InMemorySigner('edsk3RFfvaFaxbHx8BMtEW1rKQcPtDML3LXjNqMNLCzC3wLC1bWbAt'));
+  const Charlie = new TezosToolkit(rpc);
+  Charlie.setSignerProvider(new InMemorySigner('edsk3RgWvbKKA1atEUcaGwivge7QtckHkTL9nQJUXQKY5r8WKp4pF4'));
+
+  describe(`Test Proposal and Ballot operation in ${protocol.substring(0, 8)} with flextesa`, () => {
     beforeAll(async (done) => {
       await setup();
+      let constants = await Alice.rpc.getConstants();
+      blocksPerVotingPeriod = constants.blocks_per_cycle * constants.cycles_per_voting_period!;
+      blockTime = constants.minimal_block_delay!.toNumber();
+      done();
+    });
 
-      try {
-        const period = await Tezos.rpc.getCurrentPeriod();
-        await sleep((period.remaining + 5)  * 1000);
+    flextesanet('Should be able to inject proposal operation in proposal period', async (done) => {
 
-        const proposalsOp = await Tezos.contract.proposals({
+      // double check if it's proposal period so that we can inject proposal operation
+      currentPeriod = await Alice.rpc.getCurrentPeriod();
+      if (currentPeriod.voting_period.kind === 'proposal') {
+        const proposalsOp = await Alice.contract.proposals({
           proposals: ['ProtoALphaALphaALphaALphaALphaALphaALphaALphaDdp3zK']
         });
-
         await proposalsOp.confirmation();
-      } catch(e) {
-        console.log(e);
+
+        expect(proposalsOp.operationResults).toBeDefined();
+        expect(proposalsOp.operationResults?.kind).toEqual('proposals');
+        expect(proposalsOp.operationResults?.proposals).toEqual(['ProtoALphaALphaALphaALphaALphaALphaALphaALphaDdp3zK']);
+        expect(proposalsOp.includedInBlock).toBeDefined();
+        expect(proposalsOp.hash).toBeDefined();
+
+        // injecting 2 more proposals from baker Bob and Charlie to reach above quorum
+        const BobOp = await Bob.contract.proposals({
+          proposals: ['ProtoALphaALphaALphaALphaALphaALphaALphaALphaDdp3zK']
+        });
+        await BobOp.confirmation();
+        const CharlieOp = await Charlie.contract.proposals({
+          proposals: ['ProtoALphaALphaALphaALphaALphaALphaALphaALphaDdp3zK']
+        });
+        await CharlieOp.confirmation();
+        done();
       }
-      done();
     });
 
-    // TODO: Fix timing issues in regards to different block times in different sandboxes
-    it.skip('Submit a proposal and inject ballot vote', async (done) => {
-      const period = await Tezos.rpc.getCurrentPeriod();
+    flextesanet('Should be able to inject ballot operation in exploration period', async (done) => {
+      // if it's still proposal period make the test sleep to get into exploration period to inject ballot operation
+      currentPeriod = await Alice.rpc.getCurrentPeriod();
+      if (currentPeriod.voting_period.kind === 'proposal') {
+        await sleep(((currentPeriod.remaining + 1) * blockTime) * 1000)
+      };
+      currentPeriod = await Alice.rpc.getCurrentPeriod();
+      if (currentPeriod.voting_period.kind === 'exploration') {
+        const explorationBallotOp = await Alice.contract.ballot({
+          proposal: 'ProtoALphaALphaALphaALphaALphaALphaALphaALphaDdp3zK',
+          ballot: 'yay'
+        });
+        await explorationBallotOp.confirmation();
 
-      if (period.voting_period.kind === 'proposal') {
-        await sleep((period.remaining + 5) * 1000);
+        expect(explorationBallotOp.operationResults).toBeDefined();
+        expect(explorationBallotOp.operationResults?.kind).toEqual('ballot');
+        expect(explorationBallotOp.operationResults?.proposal).toEqual('ProtoALphaALphaALphaALphaALphaALphaALphaALphaDdp3zK');
+        expect(explorationBallotOp.operationResults?.ballot).toEqual('yay');
+        expect(explorationBallotOp.includedInBlock).toBeDefined();
+        expect(explorationBallotOp.hash).toBeDefined();
+        done();
       }
-      
-      const op = await Tezos.contract.ballot({
-        proposal: 'ProtoALphaALphaALphaALphaALphaALphaALphaALphaDdp3zK',
-        ballot: 'yay'
-      });
-      await op.confirmation();
-
-      expect(op.operationResults).toBeDefined();
-      expect(op.operationResults?.proposal).toEqual('ProtoALphaALphaALphaALphaALphaALphaALphaALphaDdp3zK');
-      expect(op.operationResults?.ballot).toEqual('yay');
-      expect(op.includedInBlock).toBeDefined();
-      expect(op.hash).toBeDefined();
-  
-      done();
     });
-  })
-})
\ No newline at end of file
+  });
+});
diff --git a/integration-tests/sandbox-drain-delegate-operation.spec.ts b/integration-tests/sandbox-drain-delegate-operation.spec.ts
index d21e0a45d..bbe51c5e2 100644
--- a/integration-tests/sandbox-drain-delegate-operation.spec.ts
+++ b/integration-tests/sandbox-drain-delegate-operation.spec.ts
@@ -1,17 +1,17 @@
-import { TezosToolkit, Protocols } from "@taquito/taquito";
+import { TezosToolkit } from "@taquito/taquito";
 import { CONFIGS, sleep } from "./config";
 
-CONFIGS().forEach(({ lib, rpc, setup, createAddress }) => {
+CONFIGS().forEach(({ lib, rpc, protocol, setup, createAddress }) => {
   const Tezos = lib;
-  const flextesanet =  rpc === 'http://localhost:20000' ? test : test.skip;
+  const flextesanet = rpc === 'http://localhost:20000' ? test : test.skip;
 
-  describe(`Test Drain Delegate using: ${rpc}`, () => {
+  describe(`Test Drain Delegate in ${protocol}`, () => {
     let Delegate: TezosToolkit;
     let delegatePkh: string;
     let Destination: TezosToolkit;
     let destinationPkh: string;
     beforeAll(async (done) => {
-      await setup(true);
+      await setup();
 
       try {
         Delegate = await createAddress();
@@ -35,7 +35,7 @@ CONFIGS().forEach(({ lib, rpc, setup, createAddress }) => {
         const constants = await Delegate.rpc.getConstants();
         await sleep(((constants.preserved_cycles + 2) * constants.blocks_per_cycle * (constants.minimal_block_delay!.toNumber())) * 1000);
 
-      } catch(e) {
+      } catch (e) {
         console.log(JSON.stringify(e));
       }
       done();