19 changed files with 425 additions and 115 deletions
@ -0,0 +1,116 @@ |
|||
import { CapacitorConfig } from '@capacitor/cli'; |
|||
|
|||
const config: CapacitorConfig = { |
|||
appId: 'app.timesafari', |
|||
appName: 'TimeSafari', |
|||
webDir: 'dist', |
|||
server: { |
|||
cleartext: true |
|||
}, |
|||
plugins: { |
|||
App: { |
|||
appUrlOpen: { |
|||
handlers: [ |
|||
{ |
|||
url: 'timesafari://*', |
|||
autoVerify: true |
|||
} |
|||
] |
|||
} |
|||
}, |
|||
SplashScreen: { |
|||
launchShowDuration: 3000, |
|||
launchAutoHide: true, |
|||
backgroundColor: '#ffffff', |
|||
androidSplashResourceName: 'splash', |
|||
androidScaleType: 'CENTER_CROP', |
|||
showSpinner: false, |
|||
androidSpinnerStyle: 'large', |
|||
iosSpinnerStyle: 'small', |
|||
spinnerColor: '#999999', |
|||
splashFullScreen: true, |
|||
splashImmersive: true |
|||
}, |
|||
CapSQLite: { |
|||
iosDatabaseLocation: 'Library/CapacitorDatabase', |
|||
iosIsEncryption: false, |
|||
iosBiometric: { |
|||
biometricAuth: false, |
|||
biometricTitle: 'Biometric login for TimeSafari' |
|||
}, |
|||
androidIsEncryption: false, |
|||
androidBiometric: { |
|||
biometricAuth: false, |
|||
biometricTitle: 'Biometric login for TimeSafari' |
|||
}, |
|||
electronIsEncryption: false |
|||
} |
|||
}, |
|||
ios: { |
|||
contentInset: 'never', |
|||
allowsLinkPreview: true, |
|||
scrollEnabled: true, |
|||
limitsNavigationsToAppBoundDomains: true, |
|||
backgroundColor: '#ffffff', |
|||
allowNavigation: [ |
|||
'*.timesafari.app', |
|||
'*.jsdelivr.net', |
|||
'api.endorser.ch' |
|||
] |
|||
}, |
|||
android: { |
|||
allowMixedContent: true, |
|||
captureInput: true, |
|||
webContentsDebuggingEnabled: false, |
|||
allowNavigation: [ |
|||
'*.timesafari.app', |
|||
'*.jsdelivr.net', |
|||
'api.endorser.ch', |
|||
'10.0.2.2:3000' |
|||
] |
|||
}, |
|||
electron: { |
|||
deepLinking: { |
|||
schemes: ['timesafari'] |
|||
}, |
|||
buildOptions: { |
|||
appId: 'app.timesafari', |
|||
productName: 'TimeSafari', |
|||
directories: { |
|||
output: 'dist-electron-packages' |
|||
}, |
|||
files: [ |
|||
'dist/**/*', |
|||
'electron/**/*' |
|||
], |
|||
mac: { |
|||
category: 'public.app-category.productivity', |
|||
target: [ |
|||
{ |
|||
target: 'dmg', |
|||
arch: ['x64', 'arm64'] |
|||
} |
|||
] |
|||
}, |
|||
win: { |
|||
target: [ |
|||
{ |
|||
target: 'nsis', |
|||
arch: ['x64'] |
|||
} |
|||
] |
|||
}, |
|||
linux: { |
|||
target: [ |
|||
{ |
|||
target: 'AppImage', |
|||
arch: ['x64'] |
|||
} |
|||
], |
|||
category: 'Utility' |
|||
} |
|||
} |
|||
} |
|||
}; |
|||
|
|||
export default config; |
@ -0,0 +1,63 @@ |
|||
import { test, expect } from '@playwright/test'; |
|||
import { importUserFromAccount, getTestUserData } from './testUtils'; |
|||
import { NOTIFY_DUPLICATE_ACCOUNT_IMPORT } from '../src/constants/notifications'; |
|||
|
|||
/** |
|||
* Test duplicate account import functionality |
|||
* |
|||
* This test verifies that: |
|||
* 1. A user can successfully import an account the first time |
|||
* 2. Attempting to import the same account again shows a warning message |
|||
* 3. The duplicate import is prevented |
|||
*/ |
|||
test.describe('Duplicate Account Import', () => { |
|||
test('should prevent importing the same account twice', async ({ page }) => { |
|||
const userData = getTestUserData("00"); |
|||
|
|||
// First import - should succeed
|
|||
await page.goto("./start"); |
|||
await page.getByText("You have a seed").click(); |
|||
await page.getByPlaceholder("Seed Phrase").fill(userData.seedPhrase); |
|||
await page.getByRole("button", { name: "Import" }).click(); |
|||
|
|||
// Verify first import was successful
|
|||
await expect(page.getByRole("code")).toContainText(userData.did); |
|||
|
|||
// Navigate back to start page for second import attempt
|
|||
await page.goto("./start"); |
|||
await page.getByText("You have a seed").click(); |
|||
await page.getByPlaceholder("Seed Phrase").fill(userData.seedPhrase); |
|||
await page.getByRole("button", { name: "Import" }).click(); |
|||
|
|||
// Verify duplicate import shows warning message
|
|||
// The warning can appear either from the pre-check or from the saveNewIdentity error handling
|
|||
await expect(page.getByText(NOTIFY_DUPLICATE_ACCOUNT_IMPORT.message)).toBeVisible(); |
|||
|
|||
// Verify we're still on the import page (not redirected to account)
|
|||
await expect(page.getByPlaceholder("Seed Phrase")).toBeVisible(); |
|||
}); |
|||
|
|||
test('should allow importing different accounts', async ({ page }) => { |
|||
const userZeroData = getTestUserData("00"); |
|||
const userOneData = getTestUserData("01"); |
|||
|
|||
// Import first user
|
|||
await page.goto("./start"); |
|||
await page.getByText("You have a seed").click(); |
|||
await page.getByPlaceholder("Seed Phrase").fill(userZeroData.seedPhrase); |
|||
await page.getByRole("button", { name: "Import" }).click(); |
|||
|
|||
// Verify first import was successful
|
|||
await expect(page.getByRole("code")).toContainText(userZeroData.did); |
|||
|
|||
// Navigate back to start page for second user import
|
|||
await page.goto("./start"); |
|||
await page.getByText("You have a seed").click(); |
|||
await page.getByPlaceholder("Seed Phrase").fill(userOneData.seedPhrase); |
|||
await page.getByRole("button", { name: "Import" }).click(); |
|||
|
|||
// Verify second import was successful (should not show duplicate warning)
|
|||
await expect(page.getByRole("code")).toContainText(userOneData.did); |
|||
await expect(page.getByText(NOTIFY_DUPLICATE_ACCOUNT_IMPORT.message)).not.toBeVisible(); |
|||
}); |
|||
}); |
Loading…
Reference in new issue