Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
28 commits
Select commit Hold shift + click to select a range
195bc19
feat: max message length tests
Miki-Session Sep 30, 2025
984a177
feat: add more visual regression tests
Miki-Session Oct 7, 2025
0c14fd6
Merge branch 'feat/pre-pro-tests' into dev
Miki-Session Oct 8, 2025
03455dd
feat: add ssim.js
Miki-Session Oct 9, 2025
69c1c65
feat: use SSIM instead of pixel matching for screenshot comparison
Miki-Session Oct 9, 2025
daad111
fix: renamed android locators
Miki-Session Oct 9, 2025
140b6cb
feat: add retry loop to devnet check
Miki-Session Oct 9, 2025
fc548aa
fix: use correct baseline screenshots
Miki-Session Oct 9, 2025
1f7a32d
fix: also check devnet availability at workflow start
Miki-Session Oct 9, 2025
c5abac4
fix: threshold is parametrized
Miki-Session Oct 9, 2025
37e74b8
fix: dismiss kb for message bubble test
Miki-Session Oct 9, 2025
e0401af
feat: add settings page visual check
Miki-Session Oct 9, 2025
78ac0a6
fix: adjust sent indicator android
Miki-Session Oct 9, 2025
ab7947c
fix: 1.28.2 still has the old locators
Miki-Session Oct 10, 2025
8a10bb3
fix: refine screenshot threshold handling
Miki-Session Oct 10, 2025
e960d51
feat: UPM home screen test
Miki-Session Oct 15, 2025
6745af8
chore: add more allure suites and descriptions
Miki-Session Oct 16, 2025
a7597c4
feat: add blinded message request test
Miki-Session Oct 17, 2025
f52b8b4
fix: upm test compares trimmed values
Miki-Session Oct 20, 2025
ba8eaa7
feat: add optional tolerance to color matching
Miki-Session Oct 21, 2025
5b470de
chore: decrease settings tolerance from 97 to 96
Miki-Session Oct 21, 2025
3c86fc9
feat: add allure rollback workflow
Miki-Session Oct 24, 2025
aab5ae3
feat: add delete group test
Miki-Session Oct 31, 2025
a9a63e1
chore: add more allure suites and descriptions
Miki-Session Oct 31, 2025
9042775
fix: make delete group a 4 device test
Miki-Session Nov 3, 2025
528927e
feat: add network page fetch test
Miki-Session Nov 4, 2025
0b4149d
fix: add another self healing blacklist item
Miki-Session Nov 5, 2025
1a16a48
chore: add allure to network page tests
Miki-Session Nov 5, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
42 changes: 42 additions & 0 deletions .github/workflows/allure-rollback.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
name: Roll-back Allure Report

# This workflow removes (unpublishes) the last Allure report from gh-pages.
#
# When to use:
# - Did not intend to create a new report (e.g. accidentally published a debug run)
# - Incorrect inputs (wrong build, metadta, Appium branch, etc.)
# - Test is corrupted by any other reason, don't want to muddy the result history

on:
workflow_dispatch:

jobs:
cleanup:
runs-on: ubuntu-latest
steps:
- name: Checkout gh-pages branch
uses: actions/checkout@v4
with:
ref: gh-pages
lfs: true
fetch-depth: 0 # Need full history for other workflows that rely on file ages

- name: Configure git
run: |
git config user.name "github-actions[bot]"
git config user.email "github-actions[bot]@users.noreply.github.com"

- name: Reset, force push and prune
run: |
echo "Resetting gh-pages by 1 commit..."
git reset HEAD~1
git push --force-with-lease
git lfs prune --verify-remote || echo "LFS prune failed (non-fatal)"

- name: Summary
run: |
echo "Successfully removed last commit from gh-pages" >> $GITHUB_STEP_SUMMARY
echo "Pruned orphaned LFS objects" >> $GITHUB_STEP_SUMMARY
echo "" >> $GITHUB_STEP_SUMMARY
echo "Triggered by: ${{ github.actor }}" >> $GITHUB_STEP_SUMMARY
echo "Current HEAD: $(git rev-parse HEAD)" >> $GITHUB_STEP_SUMMARY
50 changes: 45 additions & 5 deletions .github/workflows/android-regression.yml
Original file line number Diff line number Diff line change
Expand Up @@ -95,18 +95,58 @@ jobs:
- name: Download APK & extract it
run: |
pwd

# Check if devnet is accessible before choosing APK
echo "Checking devnet accessibility for APK selection..."
DEVNET_ACCESSIBLE=false

# Retry logic matching your TypeScript function
for attempt in 1 2 3; do
echo "Devnet check attempt $attempt/3..."
if curl -s --connect-timeout 5 --max-time 10 http://sesh-net.local:1280 >/dev/null 2>&1; then
echo "Devnet is accessible on attempt $attempt"
DEVNET_ACCESSIBLE=true
break
else
echo "Attempt $attempt failed"
if [ $attempt -lt 3 ]; then
echo "Waiting ${attempt}s before retry..."
sleep $attempt
fi
fi
done

if [ "$DEVNET_ACCESSIBLE" = "false" ]; then
echo "Devnet is not accessible after 3 attempts"
fi

# Download and extract APK
wget -q -O session-android.apk.tar.xz ${{ github.event.inputs.APK_URL }}
tar xf session-android.apk.tar.xz
mv session-android-*universal extracted

if ls extracted/*automaticQa.apk; then
mv extracted/*automaticQa.apk extracted/session-android.apk
echo "IS_AUTOMATIC_QA=true" >> $GITHUB_ENV
elif ls extracted/*qa.apk; then
# Choose APK based on devnet accessibility
if ls extracted/*automaticQa.apk 1>/dev/null 2>&1; then
if [ "$DEVNET_ACCESSIBLE" = "true" ]; then
echo "Using AQA build (devnet accessible)"
mv extracted/*automaticQa.apk extracted/session-android.apk
echo "IS_AUTOMATIC_QA=true" >> $GITHUB_ENV
else
echo "AQA build available but devnet not accessible - falling back to regular QA build"
if ls extracted/*qa.apk 1>/dev/null 2>&1; then
mv extracted/*qa.apk extracted/session-android.apk
echo "IS_AUTOMATIC_QA=false" >> $GITHUB_ENV
else
echo "No regular QA build found as fallback"
exit 1
fi
fi
elif ls extracted/*qa.apk 1>/dev/null 2>&1; then
echo "Using regular QA build"
mv extracted/*qa.apk extracted/session-android.apk
echo "IS_AUTOMATIC_QA=false" >> $GITHUB_ENV
else
echo "Error: No .qa APK found (only .qa builds are supported)"
echo "No suitable APK found"
exit 1
fi

Expand Down
1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,7 @@
"prettier": "^3.3.3",
"sharp": "^0.34.2",
"sinon": "^19.0.2",
"ssim.js": "^3.5.0",
"sync-request-curl": "^3.3.3",
"ts-node": "^10.9.1",
"typescript": "^5.6.3",
Expand Down
4 changes: 2 additions & 2 deletions run/screenshots/android/app_disguise.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions run/screenshots/android/conversation_alice.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions run/screenshots/android/conversation_bob.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
4 changes: 2 additions & 2 deletions run/screenshots/android/landingpage_new_account.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
4 changes: 2 additions & 2 deletions run/screenshots/android/landingpage_restore_account.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions run/screenshots/android/settings.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions run/screenshots/android/settings_appearance.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions run/screenshots/android/settings_conversations.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions run/screenshots/android/settings_notifications.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions run/screenshots/android/settings_privacy.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions run/screenshots/android/upm_home.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
4 changes: 2 additions & 2 deletions run/screenshots/ios/app_disguise.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions run/screenshots/ios/conversation_alice.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions run/screenshots/ios/conversation_bob.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
4 changes: 2 additions & 2 deletions run/screenshots/ios/landingpage_new_account.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
4 changes: 2 additions & 2 deletions run/screenshots/ios/landingpage_restore_account.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions run/screenshots/ios/settings.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions run/screenshots/ios/settings_appearance.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions run/screenshots/ios/settings_conversations.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions run/screenshots/ios/settings_notifications.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions run/screenshots/ios/settings_privacy.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
9 changes: 4 additions & 5 deletions run/test/specs/app_disguise_icons.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,11 +6,10 @@ import { USERNAME } from '../../types/testing';
import { AppearanceMenuItem, SelectAppIcon, UserSettings } from './locators/settings';
import { newUser } from './utils/create_account';
import { closeApp, openAppOnPlatformSingleDevice, SupportedPlatformsType } from './utils/open_app';
import { AppDisguisePageScreenshot } from './utils/screenshot_paths';
import { verifyElementScreenshot } from './utils/verify_screenshots';
import { verifyPageScreenshot } from './utils/verify_screenshots';

bothPlatformsIt({
title: 'App disguise icons',
title: 'Check app disguise icon layout',
risk: 'medium',
countOfDevicesNeeded: 1,
testCb: appDisguiseIcons,
Expand All @@ -31,9 +30,9 @@ async function appDisguiseIcons(platform: SupportedPlatformsType, testInfo: Test
await device.clickOnElementAll(new UserSettings(device));
await device.clickOnElementAll(new AppearanceMenuItem(device));
});
await test.step(TestSteps.VERIFY.ELEMENT_SCREENSHOT('app disguise icons'), async () => {
await test.step(TestSteps.VERIFY.SCREENSHOT('app disguise icons'), async () => {
await device.clickOnElementAll(new SelectAppIcon(device));
await verifyElementScreenshot(device, new AppDisguisePageScreenshot(device), testInfo);
await verifyPageScreenshot(device, platform, 'app_disguise', testInfo, 0.99);
});
await test.step(TestSteps.SETUP.CLOSE_APP, async () => {
await closeApp(device);
Expand Down
3 changes: 2 additions & 1 deletion run/test/specs/check_avatar_color.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,12 +10,13 @@ import { isSameColor } from './utils/check_colour';
import { closeApp, SupportedPlatformsType } from './utils/open_app';

bothPlatformsIt({
title: 'Avatar color',
title: 'Check placeholder avatar color',
risk: 'medium',
countOfDevicesNeeded: 2,
testCb: avatarColor,
allureSuites: {
parent: 'Visual Checks',
suite: 'Settings',
},
allureDescription: `Verifies that a user's placeholder avatar color appears the same to a contact`,
});
Expand Down
3 changes: 3 additions & 0 deletions run/test/specs/community_emoji_react.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,9 @@ bothPlatformsIt({
suite: 'Emoji reacts',
},
allureDescription: 'Verifies that an emoji reaction can be sent and is received in a community',
allureLinks: {
android: 'SES-4608',
},
});

async function sendEmojiReactionCommunity(platform: SupportedPlatformsType, testInfo: TestInfo) {
Expand Down
75 changes: 75 additions & 0 deletions run/test/specs/community_requests_off.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
import { expect, TestInfo } from '@playwright/test';
import { USERNAME } from '@session-foundation/qa-seeder';

import { testCommunityLink, testCommunityName } from '../../constants/community';
import { bothPlatformsIt } from '../../types/sessionIt';
import { newUser } from './utils/create_account';
import { joinCommunity } from './utils/join_community';
import { closeApp, openAppTwoDevices, SupportedPlatformsType } from './utils/open_app';

bothPlatformsIt({
title: 'Community message requests off',
risk: 'medium',
testCb: blindedMessageRequests,
countOfDevicesNeeded: 2,
allureDescription:
'Verifies that a message request cannot be sent when Community Message Requests are off.',
});

// TODO: tidy this up with neat locators
async function blindedMessageRequests(platform: SupportedPlatformsType, testInfo: TestInfo) {
const { device1, device2 } = await openAppTwoDevices(platform, testInfo);
await Promise.all([
newUser(device1, USERNAME.ALICE, { saveUserData: false }),
newUser(device2, USERNAME.BOB, { saveUserData: false }),
]);
await Promise.all(
[device1, device2].map(async device => {
await joinCommunity(device, testCommunityLink, testCommunityName);
})
);
const message = `I do not accept blinded message requests + ${platform} + ${Date.now()}`;
await device2.sendMessage(message);
// Click on profile picture (Android) or sender name (iOS)
await device1
.onAndroid()
.clickOnElementXPath(
`//android.view.ViewGroup[@resource-id='network.loki.messenger.qa:id/mainContainer'][.//android.widget.TextView[contains(@text,'${message}')]]//androidx.compose.ui.platform.ComposeView[@resource-id='network.loki.messenger.qa:id/profilePictureView']`
);
await device1
.onIOS()
.clickOnElementXPath(
`//XCUIElementTypeCell[.//XCUIElementTypeOther[@name='Message body' and contains(@label,'${message}')]]//XCUIElementTypeStaticText[contains(@value,'(15')]`
);

let attr;

if (platform === 'android') {
const el = await device1.waitForTextElementToBePresent({
strategy: 'id',
selector: 'account-id',
});
const elText = await device1.getTextFromElement(el);
expect(elText).toMatch(/^15/);
const messageButton = await device1.waitForTextElementToBePresent({
strategy: 'xpath',
selector: `//android.widget.TextView[@text="Message"]/parent::android.view.View`,
});
attr = await device1.getAttribute('enabled', messageButton.ELEMENT);
} else {
await device1.waitForTextElementToBePresent({
strategy: 'accessibility id',
selector: 'Blinded ID',
});
const messageButton = await device1.waitForTextElementToBePresent({
strategy: 'accessibility id',
selector: 'Message',
});
attr = await device1.getAttribute('enabled', messageButton.ELEMENT);
}
if (attr !== 'false') {
device1.log(`Message button attribute is 'enabled = ${attr}'`);
throw new Error(`Message button should be disabled but it is not`);
}
await closeApp(device1, device2);
}
Loading
Loading