From a9826c9d856f5b762828f78686d2525413c39647 Mon Sep 17 00:00:00 2001 From: shankar Date: Tue, 16 Dec 2025 01:26:19 +0000 Subject: [PATCH 1/9] feat: e2e fails update the comment with PR run instead of creating a new one Signed-off-by: shankar --- .github/workflows/reusable-test.yaml | 54 +++++++++++++++++++++------- 1 file changed, 41 insertions(+), 13 deletions(-) diff --git a/.github/workflows/reusable-test.yaml b/.github/workflows/reusable-test.yaml index 7b2e16a3f..586f88895 100644 --- a/.github/workflows/reusable-test.yaml +++ b/.github/workflows/reusable-test.yaml @@ -225,26 +225,54 @@ jobs: script: | const runUrl = `https://github.com/${context.repo.owner}/${context.repo.repo}/actions/runs/${context.runId}`; const prNumber = context.payload.pull_request?.number; + const header = "## ๐Ÿšจ E2E Tests Failed"; + const runEntry = `- [Action Run](${runUrl})`; if (prNumber) { - const comment = "## ๐Ÿšจ E2E Tests Failed\n\n" + - "The E2E tests failed during CI. These tests validate real blockchain interactions and may fail due to:\n" + - "- Network connectivity issues\n" + - "- RPC rate limiting\n" + - "- External service downtime\n" + - "**Action Run:** " + runUrl + "\n\n" + - "This is **non-blocking** and does not prevent merging. Check the action logs above for detailed failure information."; - try { - await github.rest.issues.createComment({ - issue_number: prNumber, + const { data: comments } = await github.rest.issues.listComments({ owner: context.repo.owner, repo: context.repo.repo, - body: comment + issue_number: prNumber, }); + + const botComment = comments.find(comment => + comment.user.type === 'Bot' && + comment.body.includes(header) + ); + + if (botComment) { + let newBody = botComment.body; + if (!newBody.includes("**Failed Runs:**")) { + newBody += "\n\n**Failed Runs:**"; + } + newBody += "\n" + runEntry; + + await github.rest.issues.updateComment({ + owner: context.repo.owner, + repo: context.repo.repo, + comment_id: botComment.id, + body: newBody + }); + } else { + const comment = header + "\n\n" + + "The E2E tests failed during CI. These tests validate real blockchain interactions and may fail due to:\n" + + "- Network connectivity issues\n" + + "- RPC rate limiting\n" + + "- External service downtime\n\n" + + "**Failed Runs:**\n" + + runEntry + "\n\n" + + "This is **non-blocking** and does not prevent merging. Check the action logs above for detailed failure information."; + + await github.rest.issues.createComment({ + issue_number: prNumber, + owner: context.repo.owner, + repo: context.repo.repo, + body: comment + }); + } } catch (error) { - // Silently fail if we don't have permission to comment (e.g., on forks) - console.log('Could not post comment to PR:', error.message); + console.log('Error managing PR comments:', error.message); } } From 76a4934e897554b946eb448e8fc3443824b7b375 Mon Sep 17 00:00:00 2001 From: shankar Date: Wed, 17 Dec 2025 02:17:49 +0000 Subject: [PATCH 2/9] fix: test pathing Signed-off-by: shankar --- packages/devtools-move/jest/e2e/initiaOFT.test.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/devtools-move/jest/e2e/initiaOFT.test.ts b/packages/devtools-move/jest/e2e/initiaOFT.test.ts index 0e329be3a..651b57009 100644 --- a/packages/devtools-move/jest/e2e/initiaOFT.test.ts +++ b/packages/devtools-move/jest/e2e/initiaOFT.test.ts @@ -46,7 +46,7 @@ describe('InitiaOFT View Methods', () => { restClient = getConnection('initia', 'testnet') as RESTClient // Initialize with local config - using path relative to workspace root - const configPath = '../test.layerzero.config.ts' + const configPath = './jest/test.layerzero.config.ts' const context = await initializeTaskContext(configPath) oft = context.oft as InitiaOFT // Use the real REST client From 0892d5ca9041c7cf653c55d194aaeb97cdd33246 Mon Sep 17 00:00:00 2001 From: shankar Date: Wed, 17 Dec 2025 02:21:54 +0000 Subject: [PATCH 3/9] chore: accumulate error logs instead of replacing Signed-off-by: shankar --- .github/workflows/reusable-test.yaml | 48 ++++++++++++++++++---------- 1 file changed, 32 insertions(+), 16 deletions(-) diff --git a/.github/workflows/reusable-test.yaml b/.github/workflows/reusable-test.yaml index 586f88895..3d45157ae 100644 --- a/.github/workflows/reusable-test.yaml +++ b/.github/workflows/reusable-test.yaml @@ -172,6 +172,10 @@ jobs: echo "::notice:: - Gas price fluctuations" echo "::notice::E2E test failures do NOT block the main CI pipeline" + - name: Log Run Information + run: | + echo "::notice:: E2E Test Run #${{ github.run_number }} (Run ID: ${{ github.run_id }})" + # There is a small bug in docker compose that will cause 401 if we don't pull the base image manually # # See more here https://github.com/docker/compose-cli/issues/1545 @@ -217,16 +221,22 @@ jobs: with: path: ./logs - # Post comment on E2E test failure - - name: Comment on E2E failure - if: steps.test-e2e.outcome == 'failure' + # Post comment on E2E test completion (success or failure) + - name: Comment on E2E results + if: always() && steps.test-e2e.outcome != 'skipped' && steps.test-e2e.outcome != 'cancelled' uses: actions/github-script@v7 with: script: | + const outcome = '${{ steps.test-e2e.outcome }}'; + const emoji = outcome === 'success' ? 'โœ…' : 'โŒ'; + const status = outcome === 'success' ? 'Passed' : 'Failed'; + const timestamp = new Date().toISOString(); + const runNumber = context.runNumber; const runUrl = `https://github.com/${context.repo.owner}/${context.repo.repo}/actions/runs/${context.runId}`; const prNumber = context.payload.pull_request?.number; - const header = "## ๐Ÿšจ E2E Tests Failed"; - const runEntry = `- [Action Run](${runUrl})`; + const header = "## ๐Ÿงช E2E Test Status"; + + const newEntry = `- ${emoji} [Run #${runNumber}](${runUrl}) - ${status} - ${timestamp}`; if (prNumber) { try { @@ -242,11 +252,20 @@ jobs: ); if (botComment) { - let newBody = botComment.body; - if (!newBody.includes("**Failed Runs:**")) { - newBody += "\n\n**Failed Runs:**"; + // Extract existing entries + const bodyLines = botComment.body.split('\n'); + const runsStartIndex = bodyLines.findIndex(line => line.trim() === '**Test Runs:**'); + + let newBody; + if (runsStartIndex !== -1) { + // Prepend new entry to existing runs (newest first) + const beforeRuns = bodyLines.slice(0, runsStartIndex + 1).join('\n'); + const existingRuns = bodyLines.slice(runsStartIndex + 1).join('\n'); + newBody = beforeRuns + '\n' + newEntry + '\n' + existingRuns; + } else { + // Shouldn't happen, but handle gracefully + newBody = botComment.body + '\n\n**Test Runs:**\n' + newEntry; } - newBody += "\n" + runEntry; await github.rest.issues.updateComment({ owner: context.repo.owner, @@ -255,14 +274,11 @@ jobs: body: newBody }); } else { + // Create new comment const comment = header + "\n\n" + - "The E2E tests failed during CI. These tests validate real blockchain interactions and may fail due to:\n" + - "- Network connectivity issues\n" + - "- RPC rate limiting\n" + - "- External service downtime\n\n" + - "**Failed Runs:**\n" + - runEntry + "\n\n" + - "This is **non-blocking** and does not prevent merging. Check the action logs above for detailed failure information."; + "E2E tests are non-blocking and validate real blockchain interactions. Failures may occur due to network issues, RPC rate limits, or external service downtime.\n\n" + + "**Test Runs:**\n" + + newEntry; await github.rest.issues.createComment({ issue_number: prNumber, From 312ffcd6442ba5b954522252aee7c79c7f00c112 Mon Sep 17 00:00:00 2001 From: shankar Date: Wed, 17 Dec 2025 02:36:25 +0000 Subject: [PATCH 4/9] chore: display UTC time instead of raw Date() ISO Signed-off-by: shankar --- .github/workflows/reusable-test.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/reusable-test.yaml b/.github/workflows/reusable-test.yaml index 3d45157ae..2eb2db895 100644 --- a/.github/workflows/reusable-test.yaml +++ b/.github/workflows/reusable-test.yaml @@ -230,7 +230,7 @@ jobs: const outcome = '${{ steps.test-e2e.outcome }}'; const emoji = outcome === 'success' ? 'โœ…' : 'โŒ'; const status = outcome === 'success' ? 'Passed' : 'Failed'; - const timestamp = new Date().toISOString(); + const timestamp = new Date().toISOString().replace('T', ' ').substring(0, 16) + ' (UTC)'; const runNumber = context.runNumber; const runUrl = `https://github.com/${context.repo.owner}/${context.repo.repo}/actions/runs/${context.runId}`; const prNumber = context.payload.pull_request?.number; From 77bfc7e3bb8f3b387e42d5da8961621b5f8fa662 Mon Sep 17 00:00:00 2001 From: shankar Date: Wed, 17 Dec 2025 02:43:54 +0000 Subject: [PATCH 5/9] chore: update message Signed-off-by: shankar --- .github/workflows/reusable-test.yaml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/.github/workflows/reusable-test.yaml b/.github/workflows/reusable-test.yaml index 2eb2db895..c500f4a7c 100644 --- a/.github/workflows/reusable-test.yaml +++ b/.github/workflows/reusable-test.yaml @@ -254,7 +254,7 @@ jobs: if (botComment) { // Extract existing entries const bodyLines = botComment.body.split('\n'); - const runsStartIndex = bodyLines.findIndex(line => line.trim() === '**Test Runs:**'); + const runsStartIndex = bodyLines.findIndex(line => line.trim() === '**Test Runs (Newest First):**'); let newBody; if (runsStartIndex !== -1) { @@ -264,7 +264,7 @@ jobs: newBody = beforeRuns + '\n' + newEntry + '\n' + existingRuns; } else { // Shouldn't happen, but handle gracefully - newBody = botComment.body + '\n\n**Test Runs:**\n' + newEntry; + newBody = botComment.body + '\n\n**Test Runs (Newest First):**\n' + newEntry; } await github.rest.issues.updateComment({ @@ -277,7 +277,7 @@ jobs: // Create new comment const comment = header + "\n\n" + "E2E tests are non-blocking and validate real blockchain interactions. Failures may occur due to network issues, RPC rate limits, or external service downtime.\n\n" + - "**Test Runs:**\n" + + "**Test Runs (Newest First):**\n" + newEntry; await github.rest.issues.createComment({ From 704aeeda3bc397c6075b6c2ed1b6cffb8f30ec4c Mon Sep 17 00:00:00 2001 From: shankar Date: Wed, 17 Dec 2025 02:44:20 +0000 Subject: [PATCH 6/9] fail test on purpose to check e2e printing Signed-off-by: shankar --- packages/devtools-move/jest/e2e/initiaOFT.test.ts | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/packages/devtools-move/jest/e2e/initiaOFT.test.ts b/packages/devtools-move/jest/e2e/initiaOFT.test.ts index 651b57009..333a06a1b 100644 --- a/packages/devtools-move/jest/e2e/initiaOFT.test.ts +++ b/packages/devtools-move/jest/e2e/initiaOFT.test.ts @@ -122,9 +122,15 @@ describe('InitiaOFT View Methods', () => { describe('getEnforcedOptions', () => { test('should return enforced options as string', async () => { - console.log('~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~') const result = await oft.getEnforcedOptions(EndpointId.BSC_V2_TESTNET, 1) expect(typeof result).toBe('string') }) }) + + // TODO: Remove this test after verifying CI reporting + describe('Intentional Failure', () => { + test('should fail to verify CI error reporting', () => { + expect(true).toBe(false) + }) + }) }) From 05c5db7c67cbdc59c3cab8252aee07b50e1f6066 Mon Sep 17 00:00:00 2001 From: shankar Date: Wed, 17 Dec 2025 02:50:23 +0000 Subject: [PATCH 7/9] chore: revert failed test Signed-off-by: shankar --- packages/devtools-move/jest/e2e/initiaOFT.test.ts | 7 ------- 1 file changed, 7 deletions(-) diff --git a/packages/devtools-move/jest/e2e/initiaOFT.test.ts b/packages/devtools-move/jest/e2e/initiaOFT.test.ts index 333a06a1b..1af180d5f 100644 --- a/packages/devtools-move/jest/e2e/initiaOFT.test.ts +++ b/packages/devtools-move/jest/e2e/initiaOFT.test.ts @@ -126,11 +126,4 @@ describe('InitiaOFT View Methods', () => { expect(typeof result).toBe('string') }) }) - - // TODO: Remove this test after verifying CI reporting - describe('Intentional Failure', () => { - test('should fail to verify CI error reporting', () => { - expect(true).toBe(false) - }) - }) }) From 8426815b02a319494b71de5e176c40a831457421 Mon Sep 17 00:00:00 2001 From: shankar Date: Wed, 17 Dec 2025 02:50:47 +0000 Subject: [PATCH 8/9] pnpm changeset Signed-off-by: shankar --- .changeset/good-ears-refuse.md | 5 +++++ 1 file changed, 5 insertions(+) create mode 100644 .changeset/good-ears-refuse.md diff --git a/.changeset/good-ears-refuse.md b/.changeset/good-ears-refuse.md new file mode 100644 index 000000000..55f6cff13 --- /dev/null +++ b/.changeset/good-ears-refuse.md @@ -0,0 +1,5 @@ +--- +"@layerzerolabs/devtools-move": patch +--- + +fix e2e test From aa8d41a3ea2933c5803a033f5b61678391f10d6c Mon Sep 17 00:00:00 2001 From: shankar Date: Wed, 17 Dec 2025 03:40:05 +0000 Subject: [PATCH 9/9] remove echo to not pollute github annotations Signed-off-by: shankar --- .github/workflows/reusable-test.yaml | 14 -------------- 1 file changed, 14 deletions(-) diff --git a/.github/workflows/reusable-test.yaml b/.github/workflows/reusable-test.yaml index c500f4a7c..27a54e4a3 100644 --- a/.github/workflows/reusable-test.yaml +++ b/.github/workflows/reusable-test.yaml @@ -162,20 +162,6 @@ jobs: - name: Setup build cache uses: ./.github/workflows/actions/setup-build-cache - - name: E2E Test Notice - run: | - echo "::notice::๐Ÿงช E2E tests are non-blocking and run against live networks" - echo "::notice::These tests validate real blockchain interactions but may fail due to:" - echo "::notice:: - Network connectivity issues" - echo "::notice:: - RPC rate limiting" - echo "::notice:: - External service downtime" - echo "::notice:: - Gas price fluctuations" - echo "::notice::E2E test failures do NOT block the main CI pipeline" - - - name: Log Run Information - run: | - echo "::notice:: E2E Test Run #${{ github.run_number }} (Run ID: ${{ github.run_id }})" - # There is a small bug in docker compose that will cause 401 if we don't pull the base image manually # # See more here https://github.com/docker/compose-cli/issues/1545