Spiegel von
https://github.com/dani-garcia/vaultwarden.git
synchronisiert 2025-03-12 16:47:03 +01:00
Improve tests
Dieser Commit ist enthalten in:
Ursprung
7649ce8a3c
Commit
edef0ca80d
14 geänderte Dateien mit 393 neuen und 247 gelöschten Zeilen
|
@ -89,7 +89,7 @@ services:
|
|||
Maildev:
|
||||
profiles: ["vaultwarden", "maildev"]
|
||||
container_name: maildev
|
||||
image: timshel/maildev
|
||||
image: timshel/maildev:3.0.4
|
||||
ports:
|
||||
- ${SMTP_PORT}:1025
|
||||
- 1080:1080
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
import { type Browser, type TestInfo } from '@playwright/test';
|
||||
import { expect, type Browser, type TestInfo } from '@playwright/test';
|
||||
import { EventEmitter } from "events";
|
||||
import { type Mail, MailServer } from 'maildev';
|
||||
import { execSync } from 'node:child_process';
|
||||
|
@ -32,19 +32,6 @@ export function loadEnv(){
|
|||
}
|
||||
}
|
||||
|
||||
export function closeMails(mailServer: MailServer, mailIterators: AsyncIterator<Mail>[]) {
|
||||
if( mailServer ) {
|
||||
mailServer.close();
|
||||
}
|
||||
if( mailIterators ) {
|
||||
for (const mails of mailIterators) {
|
||||
if(mails){
|
||||
mails.return();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
export async function waitFor(url: String, browser: Browser) {
|
||||
var ready = false;
|
||||
var context;
|
||||
|
@ -217,3 +204,9 @@ export async function restartVaultwarden(page: Page, testInfo: TestInfo, env, re
|
|||
stopVaultwarden();
|
||||
return startVaultwarden(page.context().browser(), testInfo, env, resetDB);
|
||||
}
|
||||
|
||||
export async function checkNotification(page: Page, hasText: string) {
|
||||
await expect(page.locator('bit-toast').filter({ hasText })).toBeVisible();
|
||||
await page.locator('bit-toast').filter({ hasText }).getByRole('button').click();
|
||||
await expect(page.locator('bit-toast').filter({ hasText })).toHaveCount(0);
|
||||
}
|
||||
|
|
282
playwright/package-lock.json
generiert
282
playwright/package-lock.json
generiert
|
@ -17,7 +17,130 @@
|
|||
"@playwright/test": "^1.49.1",
|
||||
"dotenv": "^16.4.7",
|
||||
"dotenv-expand": "^11.0.7",
|
||||
"maildev": "github:timshel/maildev#3.0.2"
|
||||
"maildev": "github:timshel/maildev#3.0.4"
|
||||
}
|
||||
},
|
||||
"node_modules/@asamuzakjp/css-color": {
|
||||
"version": "2.8.3",
|
||||
"resolved": "https://registry.npmjs.org/@asamuzakjp/css-color/-/css-color-2.8.3.tgz",
|
||||
"integrity": "sha512-GIc76d9UI1hCvOATjZPyHFmE5qhRccp3/zGfMPapK3jBi+yocEzp6BBB0UnfRYP9NP4FANqUZYb0hnfs3TM3hw==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"@csstools/css-calc": "^2.1.1",
|
||||
"@csstools/css-color-parser": "^3.0.7",
|
||||
"@csstools/css-parser-algorithms": "^3.0.4",
|
||||
"@csstools/css-tokenizer": "^3.0.3",
|
||||
"lru-cache": "^10.4.3"
|
||||
}
|
||||
},
|
||||
"node_modules/@csstools/color-helpers": {
|
||||
"version": "5.0.1",
|
||||
"resolved": "https://registry.npmjs.org/@csstools/color-helpers/-/color-helpers-5.0.1.tgz",
|
||||
"integrity": "sha512-MKtmkA0BX87PKaO1NFRTFH+UnkgnmySQOvNxJubsadusqPEC2aJ9MOQiMceZJJ6oitUl/i0L6u0M1IrmAOmgBA==",
|
||||
"dev": true,
|
||||
"funding": [
|
||||
{
|
||||
"type": "github",
|
||||
"url": "https://github.com/sponsors/csstools"
|
||||
},
|
||||
{
|
||||
"type": "opencollective",
|
||||
"url": "https://opencollective.com/csstools"
|
||||
}
|
||||
],
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
},
|
||||
"node_modules/@csstools/css-calc": {
|
||||
"version": "2.1.1",
|
||||
"resolved": "https://registry.npmjs.org/@csstools/css-calc/-/css-calc-2.1.1.tgz",
|
||||
"integrity": "sha512-rL7kaUnTkL9K+Cvo2pnCieqNpTKgQzy5f+N+5Iuko9HAoasP+xgprVh7KN/MaJVvVL1l0EzQq2MoqBHKSrDrag==",
|
||||
"dev": true,
|
||||
"funding": [
|
||||
{
|
||||
"type": "github",
|
||||
"url": "https://github.com/sponsors/csstools"
|
||||
},
|
||||
{
|
||||
"type": "opencollective",
|
||||
"url": "https://opencollective.com/csstools"
|
||||
}
|
||||
],
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"@csstools/css-parser-algorithms": "^3.0.4",
|
||||
"@csstools/css-tokenizer": "^3.0.3"
|
||||
}
|
||||
},
|
||||
"node_modules/@csstools/css-color-parser": {
|
||||
"version": "3.0.7",
|
||||
"resolved": "https://registry.npmjs.org/@csstools/css-color-parser/-/css-color-parser-3.0.7.tgz",
|
||||
"integrity": "sha512-nkMp2mTICw32uE5NN+EsJ4f5N+IGFeCFu4bGpiKgb2Pq/7J/MpyLBeQ5ry4KKtRFZaYs6sTmcMYrSRIyj5DFKA==",
|
||||
"dev": true,
|
||||
"funding": [
|
||||
{
|
||||
"type": "github",
|
||||
"url": "https://github.com/sponsors/csstools"
|
||||
},
|
||||
{
|
||||
"type": "opencollective",
|
||||
"url": "https://opencollective.com/csstools"
|
||||
}
|
||||
],
|
||||
"dependencies": {
|
||||
"@csstools/color-helpers": "^5.0.1",
|
||||
"@csstools/css-calc": "^2.1.1"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"@csstools/css-parser-algorithms": "^3.0.4",
|
||||
"@csstools/css-tokenizer": "^3.0.3"
|
||||
}
|
||||
},
|
||||
"node_modules/@csstools/css-parser-algorithms": {
|
||||
"version": "3.0.4",
|
||||
"resolved": "https://registry.npmjs.org/@csstools/css-parser-algorithms/-/css-parser-algorithms-3.0.4.tgz",
|
||||
"integrity": "sha512-Up7rBoV77rv29d3uKHUIVubz1BTcgyUK72IvCQAbfbMv584xHcGKCKbWh7i8hPrRJ7qU4Y8IO3IY9m+iTB7P3A==",
|
||||
"dev": true,
|
||||
"funding": [
|
||||
{
|
||||
"type": "github",
|
||||
"url": "https://github.com/sponsors/csstools"
|
||||
},
|
||||
{
|
||||
"type": "opencollective",
|
||||
"url": "https://opencollective.com/csstools"
|
||||
}
|
||||
],
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"@csstools/css-tokenizer": "^3.0.3"
|
||||
}
|
||||
},
|
||||
"node_modules/@csstools/css-tokenizer": {
|
||||
"version": "3.0.3",
|
||||
"resolved": "https://registry.npmjs.org/@csstools/css-tokenizer/-/css-tokenizer-3.0.3.tgz",
|
||||
"integrity": "sha512-UJnjoFsmxfKUdNYdWgOB0mWUypuLvAfQPH1+pyvRJs6euowbFkFC6P13w1l8mJyi3vxYMxc9kld5jZEGRQs6bw==",
|
||||
"dev": true,
|
||||
"funding": [
|
||||
{
|
||||
"type": "github",
|
||||
"url": "https://github.com/sponsors/csstools"
|
||||
},
|
||||
{
|
||||
"type": "opencollective",
|
||||
"url": "https://opencollective.com/csstools"
|
||||
}
|
||||
],
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
},
|
||||
"node_modules/@noble/hashes": {
|
||||
|
@ -32,12 +155,12 @@
|
|||
}
|
||||
},
|
||||
"node_modules/@playwright/test": {
|
||||
"version": "1.49.1",
|
||||
"resolved": "https://registry.npmjs.org/@playwright/test/-/test-1.49.1.tgz",
|
||||
"integrity": "sha512-Ky+BVzPz8pL6PQxHqNRW1k3mIyv933LML7HktS8uik0bUXNCdPhoS/kLihiO1tMf/egaJb4IutXd7UywvXEW+g==",
|
||||
"version": "1.50.1",
|
||||
"resolved": "https://registry.npmjs.org/@playwright/test/-/test-1.50.1.tgz",
|
||||
"integrity": "sha512-Jii3aBg+CEDpgnuDxEp/h7BimHcUTDlpEtce89xEumlJ5ef2hqepZ+PWp1DDpYC/VO9fmWVI1IlEaoI5fK9FXQ==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"playwright": "1.49.1"
|
||||
"playwright": "1.50.1"
|
||||
},
|
||||
"bin": {
|
||||
"playwright": "cli.js"
|
||||
|
@ -65,12 +188,6 @@
|
|||
"integrity": "sha512-9BCxFwvbGg/RsZK9tjXd8s4UcwR0MWeFQ1XEKIQVVvAGJyINdrqKMcTRyLoK8Rse1GjzLV9cwjWV1olXRWEXVA==",
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/@types/cookie": {
|
||||
"version": "0.4.1",
|
||||
"resolved": "https://registry.npmjs.org/@types/cookie/-/cookie-0.4.1.tgz",
|
||||
"integrity": "sha512-XW/Aa8APYr6jSVVA1y/DEIZX0/GMKLEVekNG727R8cs56ahETkRAy/3DR7+fJyh7oUgGwNQaRfXCun0+KbWY7Q==",
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/@types/cors": {
|
||||
"version": "2.8.17",
|
||||
"resolved": "https://registry.npmjs.org/@types/cors/-/cors-2.8.17.tgz",
|
||||
|
@ -91,9 +208,9 @@
|
|||
}
|
||||
},
|
||||
"node_modules/@types/node": {
|
||||
"version": "22.10.5",
|
||||
"resolved": "https://registry.npmjs.org/@types/node/-/node-22.10.5.tgz",
|
||||
"integrity": "sha512-F8Q+SeGimwOo86fiovQh8qiXfFEh2/ocYv7tU5pJ3EXMSSxk1Joj5wefpFK2fHTf/N6HKGSxIDBT9f3gCxXPkQ==",
|
||||
"version": "22.13.1",
|
||||
"resolved": "https://registry.npmjs.org/@types/node/-/node-22.13.1.tgz",
|
||||
"integrity": "sha512-jK8uzQlrvXqEU91UxiK5J7pKHyzgnI1Qnl0QDHIgVGuolJhRb9EEl28Cj9b3rGR8B2lhFCtvIm5os8lFnO/1Ew==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"undici-types": "~6.20.0"
|
||||
|
@ -295,9 +412,9 @@
|
|||
}
|
||||
},
|
||||
"node_modules/compression": {
|
||||
"version": "1.7.5",
|
||||
"resolved": "https://registry.npmjs.org/compression/-/compression-1.7.5.tgz",
|
||||
"integrity": "sha512-bQJ0YRck5ak3LgtnpKkiabX5pNF7tMUh1BSy2ZBOTh0Dim0BUu6aPPwByIns6/A5Prh8PufSPerMDUklpzes2Q==",
|
||||
"version": "1.8.0",
|
||||
"resolved": "https://registry.npmjs.org/compression/-/compression-1.8.0.tgz",
|
||||
"integrity": "sha512-k6WLKfunuqCYD3t6AsuPGvQWaKwuLLh2/xHNcX4qE+vIfDNXpSqnrhwA7O53R7WVQUnt8dVAIW+YHr7xTgOgGA==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"bytes": "3.1.2",
|
||||
|
@ -362,17 +479,24 @@
|
|||
}
|
||||
},
|
||||
"node_modules/cssstyle": {
|
||||
"version": "4.1.0",
|
||||
"resolved": "https://registry.npmjs.org/cssstyle/-/cssstyle-4.1.0.tgz",
|
||||
"integrity": "sha512-h66W1URKpBS5YMI/V8PyXvTMFT8SupJ1IzoIV8IeBC/ji8WVmrO8dGlTi+2dh6whmdk6BiKJLD/ZBkhWbcg6nA==",
|
||||
"version": "4.2.1",
|
||||
"resolved": "https://registry.npmjs.org/cssstyle/-/cssstyle-4.2.1.tgz",
|
||||
"integrity": "sha512-9+vem03dMXG7gDmZ62uqmRiMRNtinIZ9ZyuF6BdxzfOD+FdN5hretzynkn0ReS2DO2GSw76RWHs0UmJPI2zUjw==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"rrweb-cssom": "^0.7.1"
|
||||
"@asamuzakjp/css-color": "^2.8.2",
|
||||
"rrweb-cssom": "^0.8.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
}
|
||||
},
|
||||
"node_modules/cssstyle/node_modules/rrweb-cssom": {
|
||||
"version": "0.8.0",
|
||||
"resolved": "https://registry.npmjs.org/rrweb-cssom/-/rrweb-cssom-0.8.0.tgz",
|
||||
"integrity": "sha512-guoltQEx+9aMf2gDZ0s62EcV8lsXR+0w8915TC3ITdn2YueuNjdAYh/levpU9nFaoChh9RUS5ZdQMrKfVEN9tw==",
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/data-urls": {
|
||||
"version": "5.0.0",
|
||||
"resolved": "https://registry.npmjs.org/data-urls/-/data-urls-5.0.0.tgz",
|
||||
|
@ -396,9 +520,9 @@
|
|||
}
|
||||
},
|
||||
"node_modules/decimal.js": {
|
||||
"version": "10.4.3",
|
||||
"resolved": "https://registry.npmjs.org/decimal.js/-/decimal.js-10.4.3.tgz",
|
||||
"integrity": "sha512-VBBaLc1MgL5XpzgIP7ny5Z6Nx3UrRkIViUkPUdtl9aya5amy3De1gsUUSB1g3+3sExYNjCAsAznmukyxCb1GRA==",
|
||||
"version": "10.5.0",
|
||||
"resolved": "https://registry.npmjs.org/decimal.js/-/decimal.js-10.5.0.tgz",
|
||||
"integrity": "sha512-8vDa8Qxvr/+d94hSh5P3IJwI5t8/c0KsMp+g8bNw9cY2icONa5aPfvKeieW1WlG0WQYwwhJ7mjui2xtiePQSXw==",
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/deepmerge": {
|
||||
|
@ -488,9 +612,9 @@
|
|||
}
|
||||
},
|
||||
"node_modules/dompurify": {
|
||||
"version": "3.2.3",
|
||||
"resolved": "https://registry.npmjs.org/dompurify/-/dompurify-3.2.3.tgz",
|
||||
"integrity": "sha512-U1U5Hzc2MO0oW3DF+G9qYN0aT7atAou4AgI0XjWz061nyBPbdxkfdhfy5uMgGn6+oLFCfn44ZGbdDqCzVmlOWA==",
|
||||
"version": "3.2.4",
|
||||
"resolved": "https://registry.npmjs.org/dompurify/-/dompurify-3.2.4.tgz",
|
||||
"integrity": "sha512-ysFSFEDVduQpyhzAob/kkuJjf5zWkZD8/A9ywSp1byueyuCfHamrCBa14/Oc2iiB0e51B+NpxSl5gmzn+Ms/mg==",
|
||||
"dev": true,
|
||||
"optionalDependencies": {
|
||||
"@types/trusted-types": "^2.0.7"
|
||||
|
@ -576,12 +700,11 @@
|
|||
}
|
||||
},
|
||||
"node_modules/engine.io": {
|
||||
"version": "6.6.2",
|
||||
"resolved": "https://registry.npmjs.org/engine.io/-/engine.io-6.6.2.tgz",
|
||||
"integrity": "sha512-gmNvsYi9C8iErnZdVcJnvCpSKbWTt1E8+JZo8b+daLninywUWi5NQ5STSHZ9rFjFO7imNcvb8Pc5pe/wMR5xEw==",
|
||||
"version": "6.6.4",
|
||||
"resolved": "https://registry.npmjs.org/engine.io/-/engine.io-6.6.4.tgz",
|
||||
"integrity": "sha512-ZCkIjSYNDyGn0R6ewHDtXgns/Zre/NT6Agvq1/WobF7JXgFff4SeDroKiCO3fNJreU9YG429Sc81o4w5ok/W5g==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"@types/cookie": "^0.4.1",
|
||||
"@types/cors": "^2.8.12",
|
||||
"@types/node": ">=10.0.0",
|
||||
"accepts": "~1.3.4",
|
||||
|
@ -689,9 +812,9 @@
|
|||
}
|
||||
},
|
||||
"node_modules/es-object-atoms": {
|
||||
"version": "1.0.0",
|
||||
"resolved": "https://registry.npmjs.org/es-object-atoms/-/es-object-atoms-1.0.0.tgz",
|
||||
"integrity": "sha512-MZ4iQ6JwHOBQjahnjwaC1ZtIBH+2ohjamzAO3oaHcXYup7qxjF2fixyH+Q71voWHeOkI2q/TnJao/KfXYIZWbw==",
|
||||
"version": "1.1.1",
|
||||
"resolved": "https://registry.npmjs.org/es-object-atoms/-/es-object-atoms-1.1.1.tgz",
|
||||
"integrity": "sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"es-errors": "^1.3.0"
|
||||
|
@ -1185,17 +1308,15 @@
|
|||
}
|
||||
},
|
||||
"node_modules/long": {
|
||||
"version": "5.2.3",
|
||||
"resolved": "https://registry.npmjs.org/long/-/long-5.2.3.tgz",
|
||||
"integrity": "sha512-lcHwpNoggQTObv5apGNCTdJrO69eHOZMi4BNC+rTLER8iHAqGrUVeLh/irVIM7zTw2bOXA8T6uNPeujwOLg/2Q=="
|
||||
"version": "5.3.0",
|
||||
"resolved": "https://registry.npmjs.org/long/-/long-5.3.0.tgz",
|
||||
"integrity": "sha512-5vvY5yF1zF/kXk+L94FRiTDa1Znom46UjPCH6/XbSvS8zBKMFBHTJk8KDMqJ+2J6QezQFi7k1k8v21ClJYHPaw=="
|
||||
},
|
||||
"node_modules/lru-cache": {
|
||||
"version": "7.18.3",
|
||||
"resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-7.18.3.tgz",
|
||||
"integrity": "sha512-jumlc0BIUrS3qJGgIkWZsyfAM7NCWiBcCDhnd+3NNM5KbBmLTgHVfWBcg6W+rLUsIpzpERPsvwUP7CckAQSOoA==",
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
}
|
||||
"version": "10.4.3",
|
||||
"resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-10.4.3.tgz",
|
||||
"integrity": "sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ==",
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/lru.min": {
|
||||
"version": "1.1.1",
|
||||
|
@ -1212,8 +1333,8 @@
|
|||
}
|
||||
},
|
||||
"node_modules/maildev": {
|
||||
"version": "3.0.2",
|
||||
"resolved": "git+ssh://git@github.com/timshel/maildev.git#b76b02f184a2b56115ccdf477e81d6532c763994",
|
||||
"version": "3.0.4",
|
||||
"resolved": "git+ssh://git@github.com/timshel/maildev.git#ac9aa31d50b1849a73248eaa679a5702e9d10f21",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
|
@ -1258,6 +1379,15 @@
|
|||
"tlds": "1.255.0"
|
||||
}
|
||||
},
|
||||
"node_modules/mailparser/node_modules/nodemailer": {
|
||||
"version": "6.9.16",
|
||||
"resolved": "https://registry.npmjs.org/nodemailer/-/nodemailer-6.9.16.tgz",
|
||||
"integrity": "sha512-psAuZdTIRN08HKVd/E8ObdV6NO7NTBY3KsC30F7M4H1OnmLCUNaS56FpYxyb26zWLSyYF9Ozch9KYHhHegsiOQ==",
|
||||
"dev": true,
|
||||
"engines": {
|
||||
"node": ">=6.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/mailsplit": {
|
||||
"version": "5.4.2",
|
||||
"resolved": "https://registry.npmjs.org/mailsplit/-/mailsplit-5.4.2.tgz",
|
||||
|
@ -1383,6 +1513,14 @@
|
|||
"node": ">=12.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/named-placeholders/node_modules/lru-cache": {
|
||||
"version": "7.18.3",
|
||||
"resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-7.18.3.tgz",
|
||||
"integrity": "sha512-jumlc0BIUrS3qJGgIkWZsyfAM7NCWiBcCDhnd+3NNM5KbBmLTgHVfWBcg6W+rLUsIpzpERPsvwUP7CckAQSOoA==",
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
}
|
||||
},
|
||||
"node_modules/negotiator": {
|
||||
"version": "0.6.4",
|
||||
"resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.4.tgz",
|
||||
|
@ -1393,9 +1531,9 @@
|
|||
}
|
||||
},
|
||||
"node_modules/nodemailer": {
|
||||
"version": "6.9.16",
|
||||
"resolved": "https://registry.npmjs.org/nodemailer/-/nodemailer-6.9.16.tgz",
|
||||
"integrity": "sha512-psAuZdTIRN08HKVd/E8ObdV6NO7NTBY3KsC30F7M4H1OnmLCUNaS56FpYxyb26zWLSyYF9Ozch9KYHhHegsiOQ==",
|
||||
"version": "6.10.0",
|
||||
"resolved": "https://registry.npmjs.org/nodemailer/-/nodemailer-6.10.0.tgz",
|
||||
"integrity": "sha512-SQ3wZCExjeSatLE/HBaXS5vqUOQk6GtBdIIKxiFdmm01mOQZX/POJkO3SUX1wDiYcwUOJwT23scFSC9fY2H8IA==",
|
||||
"dev": true,
|
||||
"engines": {
|
||||
"node": ">=6.0.0"
|
||||
|
@ -1417,9 +1555,9 @@
|
|||
}
|
||||
},
|
||||
"node_modules/object-inspect": {
|
||||
"version": "1.13.3",
|
||||
"resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.3.tgz",
|
||||
"integrity": "sha512-kDCGIbxkDSXE3euJZZXzc6to7fCrKHNI/hSRQnRuQ+BWjFNzZwiFF8fj/6o2t2G9/jTj8PSIYTfCLelLZEeRpA==",
|
||||
"version": "1.13.4",
|
||||
"resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.4.tgz",
|
||||
"integrity": "sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew==",
|
||||
"dev": true,
|
||||
"engines": {
|
||||
"node": ">= 0.4"
|
||||
|
@ -1510,13 +1648,13 @@
|
|||
}
|
||||
},
|
||||
"node_modules/pg": {
|
||||
"version": "8.13.1",
|
||||
"resolved": "https://registry.npmjs.org/pg/-/pg-8.13.1.tgz",
|
||||
"integrity": "sha512-OUir1A0rPNZlX//c7ksiu7crsGZTKSOXJPgtNiHGIlC9H0lO+NC6ZDYksSgBYY/thSWhnSRBv8w1lieNNGATNQ==",
|
||||
"version": "8.13.2",
|
||||
"resolved": "https://registry.npmjs.org/pg/-/pg-8.13.2.tgz",
|
||||
"integrity": "sha512-L5QkPvTjVWWHbLaFjCkOSplpb2uCiRYbg0IJ2okCy5ClYfWlSgDDnvdR6dyw3EWAH2AfS4j8E61QFI7gLfTtlw==",
|
||||
"dependencies": {
|
||||
"pg-connection-string": "^2.7.0",
|
||||
"pg-pool": "^3.7.0",
|
||||
"pg-protocol": "^1.7.0",
|
||||
"pg-pool": "^3.7.1",
|
||||
"pg-protocol": "^1.7.1",
|
||||
"pg-types": "^2.1.0",
|
||||
"pgpass": "1.x"
|
||||
},
|
||||
|
@ -1555,17 +1693,17 @@
|
|||
}
|
||||
},
|
||||
"node_modules/pg-pool": {
|
||||
"version": "3.7.0",
|
||||
"resolved": "https://registry.npmjs.org/pg-pool/-/pg-pool-3.7.0.tgz",
|
||||
"integrity": "sha512-ZOBQForurqh4zZWjrgSwwAtzJ7QiRX0ovFkZr2klsen3Nm0aoh33Ls0fzfv3imeH/nw/O27cjdz5kzYJfeGp/g==",
|
||||
"version": "3.7.1",
|
||||
"resolved": "https://registry.npmjs.org/pg-pool/-/pg-pool-3.7.1.tgz",
|
||||
"integrity": "sha512-xIOsFoh7Vdhojas6q3596mXFsR8nwBQBXX5JiV7p9buEVAGqYL4yFzclON5P9vFrpu1u7Zwl2oriyDa89n0wbw==",
|
||||
"peerDependencies": {
|
||||
"pg": ">=8.0"
|
||||
}
|
||||
},
|
||||
"node_modules/pg-protocol": {
|
||||
"version": "1.7.0",
|
||||
"resolved": "https://registry.npmjs.org/pg-protocol/-/pg-protocol-1.7.0.tgz",
|
||||
"integrity": "sha512-hTK/mE36i8fDDhgDFjy6xNOG+LCorxLG3WO17tku+ij6sVHXh1jQUJ8hYAnRhNla4QVD2H8er/FOjc/+EgC6yQ=="
|
||||
"version": "1.7.1",
|
||||
"resolved": "https://registry.npmjs.org/pg-protocol/-/pg-protocol-1.7.1.tgz",
|
||||
"integrity": "sha512-gjTHWGYWsEgy9MsY0Gp6ZJxV24IjDqdpTW7Eh0x+WfJLFsm/TJx1MzL6T0D88mBvkpxotCQ6TwW6N+Kko7lhgQ=="
|
||||
},
|
||||
"node_modules/pg-types": {
|
||||
"version": "2.2.0",
|
||||
|
@ -1591,12 +1729,12 @@
|
|||
}
|
||||
},
|
||||
"node_modules/playwright": {
|
||||
"version": "1.49.1",
|
||||
"resolved": "https://registry.npmjs.org/playwright/-/playwright-1.49.1.tgz",
|
||||
"integrity": "sha512-VYL8zLoNTBxVOrJBbDuRgDWa3i+mfQgDTrL8Ah9QXZ7ax4Dsj0MSq5bYgytRnDVVe+njoKnfsYkH3HzqVj5UZA==",
|
||||
"version": "1.50.1",
|
||||
"resolved": "https://registry.npmjs.org/playwright/-/playwright-1.50.1.tgz",
|
||||
"integrity": "sha512-G8rwsOQJ63XG6BbKj2w5rHeavFjy5zynBA9zsJMMtBoe/Uf757oG12NXz6e6OirF7RCrTVAKFXbLmn1RbL7Qaw==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"playwright-core": "1.49.1"
|
||||
"playwright-core": "1.50.1"
|
||||
},
|
||||
"bin": {
|
||||
"playwright": "cli.js"
|
||||
|
@ -1609,9 +1747,9 @@
|
|||
}
|
||||
},
|
||||
"node_modules/playwright-core": {
|
||||
"version": "1.49.1",
|
||||
"resolved": "https://registry.npmjs.org/playwright-core/-/playwright-core-1.49.1.tgz",
|
||||
"integrity": "sha512-BzmpVcs4kE2CH15rWfzpjzVGhWERJfmnXmniSyKeRZUs9Ws65m+RGIi7mjJK/euCegfn3i7jvqWeWyHe9y3Vgg==",
|
||||
"version": "1.50.1",
|
||||
"resolved": "https://registry.npmjs.org/playwright-core/-/playwright-core-1.50.1.tgz",
|
||||
"integrity": "sha512-ra9fsNWayuYumt+NiM069M6OkcRb1FZSK8bgi66AtpFoWkg2+y0bJSNmkFrWhMbEBbVKC/EruAHH3g0zmtwGmQ==",
|
||||
"dev": true,
|
||||
"bin": {
|
||||
"playwright-core": "cli.js"
|
||||
|
@ -2298,9 +2436,9 @@
|
|||
}
|
||||
},
|
||||
"node_modules/whatwg-url": {
|
||||
"version": "14.1.0",
|
||||
"resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-14.1.0.tgz",
|
||||
"integrity": "sha512-jlf/foYIKywAt3x/XWKZ/3rz8OSJPiWktjmk891alJUEjiVxKX9LEO92qH3hv4aJ0mN3MWPvGMCy8jQi95xK4w==",
|
||||
"version": "14.1.1",
|
||||
"resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-14.1.1.tgz",
|
||||
"integrity": "sha512-mDGf9diDad/giZ/Sm9Xi2YcyzaFpbdLpJPr+E9fSkyQ7KpQD4SdFcugkRQYzhmfI4KeV4Qpnn2sKPdo+kmsgRQ==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"tr46": "^5.0.0",
|
||||
|
|
|
@ -11,7 +11,7 @@
|
|||
"@playwright/test": "^1.49.1",
|
||||
"dotenv": "^16.4.7",
|
||||
"dotenv-expand": "^11.0.7",
|
||||
"maildev": "github:timshel/maildev#3.0.2"
|
||||
"maildev": "github:timshel/maildev#3.0.4"
|
||||
},
|
||||
"dependencies": {
|
||||
"mysql2": "^3.12.0",
|
||||
|
|
38
playwright/tests/collection.spec.ts
Normale Datei
38
playwright/tests/collection.spec.ts
Normale Datei
|
@ -0,0 +1,38 @@
|
|||
import { test, expect, type TestInfo } from '@playwright/test';
|
||||
|
||||
import * as utils from "../global-utils";
|
||||
import { createAccount, logUser } from './setups/user';
|
||||
|
||||
let users = utils.loadEnv();
|
||||
|
||||
test.beforeAll('Setup', async ({ browser }, testInfo: TestInfo) => {
|
||||
await utils.startVaultwarden(browser, testInfo);
|
||||
});
|
||||
|
||||
test.afterAll('Teardown', async ({}) => {
|
||||
utils.stopVaultwarden();
|
||||
});
|
||||
|
||||
test('Create', async ({ page }) => {
|
||||
await createAccount(test, page, users.user1);
|
||||
await logUser(test, page, users.user1);
|
||||
|
||||
await test.step('Create Org', async () => {
|
||||
await page.getByRole('link', { name: 'New organisation' }).click();
|
||||
await page.getByLabel('Organisation name (required)').fill('Test');
|
||||
await page.getByRole('button', { name: 'Submit' }).click();
|
||||
await page.locator('div').filter({ hasText: 'Members' }).nth(2).click();
|
||||
|
||||
await utils.checkNotification(page, 'Organisation created');
|
||||
});
|
||||
|
||||
await test.step('Create Collection', async () => {
|
||||
await page.getByRole('link', { name: 'Collections' }).click();
|
||||
await page.getByRole('button', { name: 'New' }).click();
|
||||
await page.getByRole('menuitem', { name: 'Collection' }).click();
|
||||
await page.getByLabel('Name (required)').fill('RandomCollec');
|
||||
await page.getByRole('button', { name: 'Save' }).click();
|
||||
await utils.checkNotification(page, 'Created collection RandomCollec');
|
||||
await expect(page.getByRole('button', { name: 'RandomCollec' })).toBeVisible();
|
||||
});
|
||||
});
|
|
@ -30,57 +30,24 @@ test.afterAll('Teardown', async ({}) => {
|
|||
});
|
||||
|
||||
test('Account creation', async ({ page }) => {
|
||||
const emails = mailserver.iterator(users.user1.email);
|
||||
|
||||
await createAccount(test, page, users.user1);
|
||||
|
||||
const { value: created } = await emails.next();
|
||||
expect(created.subject).toBe("Welcome");
|
||||
expect(created.from[0]?.address).toBe(process.env.VAULTWARDEN_SMTP_FROM);
|
||||
|
||||
// Back to the login page
|
||||
await expect(page).toHaveTitle('Vaultwarden Web');
|
||||
await expect(page.getByTestId("toast-message")).toHaveText(/Your new account has been created/);
|
||||
await page.getByRole('button', { name: 'Continue' }).click();
|
||||
|
||||
// Unlock page
|
||||
await page.getByLabel('Master password').fill(users.user1.password);
|
||||
await page.getByRole('button', { name: 'Log in with master password' }).click();
|
||||
|
||||
// We are now in the default vault page
|
||||
await expect(page).toHaveTitle(/Vaultwarden Web/);
|
||||
|
||||
const { value: logged } = await emails.next();
|
||||
expect(logged.subject).toBe("New Device Logged In From Firefox");
|
||||
expect(logged.to[0]?.address).toBe(process.env.TEST_USER_MAIL);
|
||||
expect(logged.from[0]?.address).toBe(process.env.VAULTWARDEN_SMTP_FROM);
|
||||
|
||||
emails.return();
|
||||
const mailBuffer = mailserver.buffer(users.user1.email);
|
||||
await createAccount(test, page, users.user1, mailBuffer);
|
||||
mailBuffer.close();
|
||||
});
|
||||
|
||||
test('Login', async ({ context, page }) => {
|
||||
const emails = mailserver.iterator(users.user1.email);
|
||||
const mailBuffer = mailserver.buffer(users.user1.email);
|
||||
|
||||
await logUser(test, page, users.user1);
|
||||
|
||||
await test.step('new device email', async () => {
|
||||
const { value: logged } = await emails.next();
|
||||
expect(logged.subject).toBe("New Device Logged In From Firefox");
|
||||
expect(logged.from[0]?.address).toBe(process.env.VAULTWARDEN_SMTP_FROM);
|
||||
});
|
||||
await logUser(test, page, users.user1, mailBuffer);
|
||||
|
||||
await test.step('verify email', async () => {
|
||||
await page.getByText('Verify your account\'s email').click();
|
||||
await expect(page.getByText('Verify your account\'s email')).toBeVisible();
|
||||
await page.getByRole('button', { name: 'Send email' }).click();
|
||||
|
||||
// Close the toast message
|
||||
await expect(page.getByTestId("toast-message")).toHaveText(/Check your email inbox/);
|
||||
await page.locator('#toast-container').getByRole('button').click();
|
||||
await expect(page.getByTestId("toast-message")).toHaveCount(0);
|
||||
await utils.checkNotification(page, 'Check your email inbox for a verification link');
|
||||
|
||||
const { value: verify } = await emails.next();
|
||||
expect(verify.subject).toBe("Verify Your Email");
|
||||
const verify = await mailBuffer.next((m) => m.subject === "Verify Your Email");
|
||||
expect(verify.from[0]?.address).toBe(process.env.VAULTWARDEN_SMTP_FROM);
|
||||
|
||||
const page2 = await context.newPage();
|
||||
|
@ -89,10 +56,10 @@ test('Login', async ({ context, page }) => {
|
|||
await page2.close();
|
||||
|
||||
await page.goto(link);
|
||||
await expect(page.getByTestId("toast-message")).toHaveText("Account email verified");
|
||||
await utils.checkNotification(page, 'Account email verified');
|
||||
});
|
||||
|
||||
emails.return();
|
||||
mailBuffer.close();
|
||||
});
|
||||
|
||||
test('Activaite 2fa', async ({ context, page }) => {
|
||||
|
@ -156,7 +123,7 @@ test('2fa', async ({ context, page }) => {
|
|||
await page.getByRole('button', { name: 'Continue' }).click();
|
||||
await page.getByRole('button', { name: 'Turn off' }).click();
|
||||
await page.getByRole('button', { name: 'Yes' }).click();
|
||||
await expect(page.getByTestId("toast-message")).toHaveText(/Two-step login provider turned off/);
|
||||
await utils.checkNotification(page, 'Two-step login provider turned off');
|
||||
});
|
||||
|
||||
emails.close();
|
||||
|
|
|
@ -89,6 +89,6 @@ test('Authenticator 2fa', async ({ context, page }) => {
|
|||
await page.getByRole('button', { name: 'Continue' }).click();
|
||||
await page.getByRole('button', { name: 'Turn off' }).click();
|
||||
await page.getByRole('button', { name: 'Yes' }).click();
|
||||
await expect(page.getByTestId("toast-message")).toHaveText(/Two-step login provider turned off/);
|
||||
await utils.checkNotification(page, 'Two-step login provider turned off');
|
||||
});
|
||||
});
|
||||
|
|
|
@ -1,83 +1,59 @@
|
|||
import { test, expect, type TestInfo } from '@playwright/test';
|
||||
import { MailDev } from 'maildev';
|
||||
|
||||
import * as utils from "../global-utils";
|
||||
import * as utils from '../global-utils';
|
||||
import * as orgs from './setups/orgs';
|
||||
import { createAccount, logUser } from './setups/user';
|
||||
|
||||
let users = utils.loadEnv();
|
||||
|
||||
let mailserver, user1Mails, user2Mails, user3Mails;
|
||||
let mailServer, mail1Buffer, mail2Buffer, mail3Buffer;
|
||||
|
||||
test.beforeAll('Setup', async ({ browser }, testInfo: TestInfo) => {
|
||||
mailserver = new MailDev({
|
||||
mailServer = new MailDev({
|
||||
port: process.env.MAILDEV_SMTP_PORT,
|
||||
web: { port: process.env.MAILDEV_HTTP_PORT },
|
||||
})
|
||||
|
||||
await mailserver.listen();
|
||||
await mailServer.listen();
|
||||
|
||||
await utils.startVaultwarden(browser, testInfo, {
|
||||
SMTP_HOST: process.env.MAILDEV_HOST,
|
||||
SMTP_FROM: process.env.VAULTWARDEN_SMTP_FROM,
|
||||
});
|
||||
|
||||
user1Mails = mailserver.iterator(users.user1.email);
|
||||
user2Mails = mailserver.iterator(users.user2.email);
|
||||
user3Mails = mailserver.iterator(users.user3.email);
|
||||
mail1Buffer = mailServer.buffer(users.user1.email);
|
||||
mail2Buffer = mailServer.buffer(users.user2.email);
|
||||
mail3Buffer = mailServer.buffer(users.user3.email);
|
||||
});
|
||||
|
||||
test.afterAll('Teardown', async ({}, testInfo: TestInfo) => {
|
||||
utils.stopVaultwarden(testInfo);
|
||||
utils.closeMails(mailserver, [user1Mails, user2Mails, user3Mails]);
|
||||
[mail1Buffer, mail2Buffer, mail3Buffer, mailServer].map((m) => m?.close());
|
||||
});
|
||||
|
||||
test('Create user3', async ({ page }) => {
|
||||
await createAccount(test, page, users.user3, user3Mails);
|
||||
await createAccount(test, page, users.user3, mail3Buffer);
|
||||
});
|
||||
|
||||
test('Invite users', async ({ page }) => {
|
||||
await createAccount(test, page, users.user1, user1Mails);
|
||||
await logUser(test, page, users.user1, user1Mails);
|
||||
await createAccount(test, page, users.user1, mail1Buffer);
|
||||
await logUser(test, page, users.user1, mail1Buffer);
|
||||
|
||||
await test.step('Create Org', async () => {
|
||||
await page.getByRole('link', { name: 'New organisation' }).click();
|
||||
await page.getByLabel('Organisation name (required)').fill('Test');
|
||||
await page.getByRole('button', { name: 'Submit' }).click();
|
||||
await page.locator('div').filter({ hasText: 'Members' }).nth(2).click();
|
||||
});
|
||||
|
||||
await test.step('Invite user2', async () => {
|
||||
await page.getByRole('button', { name: 'Invite member' }).click();
|
||||
await page.getByLabel('Email (required)').fill(users.user2.email);
|
||||
await page.getByRole('tab', { name: 'Collections' }).click();
|
||||
await page.getByLabel('Permission').selectOption('edit');
|
||||
await page.getByLabel('Select collections').click();
|
||||
await page.getByLabel('Options list').getByText('Default collection').click();
|
||||
await page.getByRole('button', { name: 'Save' }).click();
|
||||
await expect(page.getByTestId("toast-message")).toHaveText('User(s) invited');
|
||||
await page.locator('#toast-container').getByRole('button').click();
|
||||
});
|
||||
|
||||
await test.step('Invite user3', async () => {
|
||||
await page.getByRole('button', { name: 'Invite member' }).click();
|
||||
await page.getByLabel('Email (required)').fill(users.user3.email);
|
||||
await page.getByRole('tab', { name: 'Collections' }).click();
|
||||
await page.getByLabel('Permission').selectOption('edit');
|
||||
await page.getByLabel('Select collections').click();
|
||||
await page.getByLabel('Options list').getByText('Default collection').click();
|
||||
await page.getByRole('button', { name: 'Save' }).click();
|
||||
await expect(page.getByTestId("toast-message")).toHaveText('User(s) invited');
|
||||
await page.locator('#toast-container').getByRole('button').click();
|
||||
await orgs.create(test, page, 'Test');
|
||||
await orgs.members(test, page, 'Test');
|
||||
await orgs.invite(test, page, 'Test', users.user2.email);
|
||||
await orgs.invite(test, page, 'Test', users.user3.email, {
|
||||
navigate: false,
|
||||
});
|
||||
});
|
||||
|
||||
test('invited with new account', async ({ page }) => {
|
||||
const { value: invited } = await user2Mails.next();
|
||||
expect(invited.subject).toContain("Join Test")
|
||||
const invited = await mail2Buffer.next((mail) => mail.subject === 'Join Test');
|
||||
|
||||
await test.step('Create account', async () => {
|
||||
await page.setContent(invited.html);
|
||||
const link = await page.getByTestId("invite").getAttribute("href");
|
||||
const link = await page.getByTestId('invite').getAttribute('href');
|
||||
await page.goto(link);
|
||||
await expect(page).toHaveTitle(/Create account | Vaultwarden Web/);
|
||||
|
||||
|
@ -87,12 +63,7 @@ test('invited with new account', async ({ page }) => {
|
|||
await page.getByRole('button', { name: 'Create account' }).click();
|
||||
|
||||
// Back to the login page
|
||||
await expect(page).toHaveTitle('Vaultwarden Web');
|
||||
await expect(page.getByTestId("toast-message")).toHaveText(/Your new account has been created/);
|
||||
await page.locator('#toast-container').getByRole('button').click();
|
||||
|
||||
const { value: welcome } = await user2Mails.next();
|
||||
expect(welcome.subject).toContain("Welcome")
|
||||
await utils.checkNotification(page, 'Your new account has been created');
|
||||
});
|
||||
|
||||
await test.step('Login', async () => {
|
||||
|
@ -105,23 +76,21 @@ test('invited with new account', async ({ page }) => {
|
|||
|
||||
// We are now in the default vault page
|
||||
await expect(page).toHaveTitle(/Vaultwarden Web/);
|
||||
await expect(page.getByTestId("toast-title")).toHaveText("Invitation accepted");
|
||||
await page.locator('#toast-container').getByRole('button').click();
|
||||
|
||||
const { value: logged } = await user2Mails.next();
|
||||
expect(logged.subject).toContain("New Device Logged");
|
||||
await utils.checkNotification(page, 'Invitation accepted');
|
||||
});
|
||||
|
||||
const { value: accepted } = await user1Mails.next();
|
||||
expect(accepted.subject).toContain("Invitation to Test accepted")
|
||||
await test.step('Check mails', async () => {
|
||||
await expect(mail2Buffer.next((m) => m.subject === 'Welcome')).resolves.toBeDefined();
|
||||
await expect(mail2Buffer.next((m) => m.subject === 'New Device Logged In From Firefox')).resolves.toBeDefined();
|
||||
await expect(mail1Buffer.next((m) => m.subject.includes('Invitation to Test accepted'))).resolves.toBeDefined();
|
||||
});
|
||||
});
|
||||
|
||||
test('invited with existing account', async ({ page }) => {
|
||||
const { value: invited } = await user3Mails.next();
|
||||
expect(invited.subject).toContain("Join Test")
|
||||
const invited = await mail3Buffer.next((mail) => mail.subject === 'Join Test');
|
||||
|
||||
await page.setContent(invited.html);
|
||||
const link = await page.getByTestId("invite").getAttribute("href");
|
||||
const link = await page.getByTestId('invite').getAttribute('href');
|
||||
|
||||
await page.goto(link);
|
||||
|
||||
|
@ -135,36 +104,23 @@ test('invited with existing account', async ({ page }) => {
|
|||
|
||||
// We are now in the default vault page
|
||||
await expect(page).toHaveTitle(/Vaultwarden Web/);
|
||||
await expect(page.getByTestId("toast-title")).toHaveText("Invitation accepted");
|
||||
await page.locator('#toast-container').getByRole('button').click();
|
||||
await utils.checkNotification(page, 'Invitation accepted');
|
||||
|
||||
const { value: logged } = await user3Mails.next();
|
||||
expect(logged.subject).toContain("New Device Logged")
|
||||
|
||||
const { value: accepted } = await user1Mails.next();
|
||||
expect(accepted.subject).toContain("Invitation to Test accepted")
|
||||
await expect(mail3Buffer.next((m) => m.subject === 'New Device Logged In From Firefox')).resolves.toBeDefined();
|
||||
await expect(mail1Buffer.next((m) => m.subject.includes('Invitation to Test accepted'))).resolves.toBeDefined();
|
||||
});
|
||||
|
||||
test('Confirm invited user', async ({ page }) => {
|
||||
await logUser(test, page, users.user1, user1Mails);
|
||||
await page.getByLabel('Switch products').click();
|
||||
await page.getByRole('link', { name: ' Admin Console' }).click();
|
||||
await page.getByRole('link', { name: 'Members' }).click();
|
||||
await logUser(test, page, users.user1, mail1Buffer);
|
||||
|
||||
await test.step('Accept user2', async () => {
|
||||
await page.getByRole('row', { name: users.user2.name }).getByLabel('Options').click();
|
||||
await page.getByRole('menuitem', { name: 'Confirm' }).click();
|
||||
await page.getByRole('button', { name: 'Confirm' }).click();
|
||||
await expect(page.getByTestId("toast-message")).toHaveText(/confirmed/);
|
||||
await page.locator('#toast-container').getByRole('button').click();
|
||||
await orgs.members(test, page, 'Test');
|
||||
await orgs.confirm(test, page, 'Test', users.user2.name);
|
||||
|
||||
const { value: logged } = await user2Mails.next();
|
||||
expect(logged.subject).toContain("Invitation to Test confirmed");
|
||||
});
|
||||
await expect(mail2Buffer.next((m) => m.subject.includes('Invitation to Test confirmed'))).resolves.toBeDefined();
|
||||
});
|
||||
|
||||
test('Organization is visible', async ({ page }) => {
|
||||
await logUser(test, page, users.user2, user2Mails);
|
||||
await logUser(test, page, users.user2, mail2Buffer);
|
||||
await page.getByLabel('vault: Test').click();
|
||||
await expect(page.getByLabel('Filter: Default collection')).toBeVisible();
|
||||
});
|
||||
|
|
|
@ -37,8 +37,7 @@ test('Invite users', async ({ page }) => {
|
|||
await page.getByLabel('Select collections').click();
|
||||
await page.getByLabel('Options list').getByText('Default collection').click();
|
||||
await page.getByRole('button', { name: 'Save' }).click();
|
||||
await expect(page.getByTestId("toast-message")).toHaveText('User(s) invited');
|
||||
await page.locator('#toast-container').getByRole('button').click();
|
||||
await utils.checkNotification(page, 'User(s) invited');
|
||||
await expect(page.getByRole('row', { name: users.user2.email })).toHaveText(/Invited/);
|
||||
});
|
||||
|
||||
|
@ -50,8 +49,7 @@ test('Invite users', async ({ page }) => {
|
|||
await page.getByLabel('Select collections').click();
|
||||
await page.getByLabel('Options list').getByText('Default collection').click();
|
||||
await page.getByRole('button', { name: 'Save' }).click();
|
||||
await expect(page.getByTestId("toast-message")).toHaveText('User(s) invited');
|
||||
await page.locator('#toast-container').getByRole('button').click();
|
||||
await utils.checkNotification(page, 'User(s) invited');
|
||||
await expect(page.getByRole('row', { name: users.user3.name })).toHaveText(/Needs confirmation/);
|
||||
});
|
||||
|
||||
|
@ -59,8 +57,7 @@ test('Invite users', async ({ page }) => {
|
|||
await page.getByRole('row', { name: users.user3.name }).getByLabel('Options').click();
|
||||
await page.getByRole('menuitem', { name: 'Confirm' }).click();
|
||||
await page.getByRole('button', { name: 'Confirm' }).click();
|
||||
await expect(page.getByTestId("toast-message")).toHaveText(/confirmed/);
|
||||
await page.locator('#toast-container').getByRole('button').click();
|
||||
await utils.checkNotification(page, 'confirmed');
|
||||
});
|
||||
});
|
||||
|
||||
|
@ -78,7 +75,7 @@ test('Confirm invited user', async ({ page }) => {
|
|||
await page.getByRole('row', { name: users.user2.name }).getByLabel('Options').click();
|
||||
await page.getByRole('menuitem', { name: 'Confirm' }).click();
|
||||
await page.getByRole('button', { name: 'Confirm' }).click();
|
||||
await expect(page.getByTestId("toast-message")).toHaveText(/confirmed/);
|
||||
await utils.checkNotification(page, 'confirmed');
|
||||
});
|
||||
});
|
||||
|
||||
|
|
62
playwright/tests/setups/orgs.ts
Normale Datei
62
playwright/tests/setups/orgs.ts
Normale Datei
|
@ -0,0 +1,62 @@
|
|||
import { expect, type Browser,Page } from '@playwright/test';
|
||||
|
||||
import * as utils from '../../global-utils';
|
||||
|
||||
export async function create(test, page: Page, name: string) {
|
||||
await test.step('Create Org', async () => {
|
||||
await page.locator('a').filter({ hasText: 'Password Manager' }).first().click();
|
||||
await expect(page.getByTitle('All vaults', { exact: true })).toBeVisible();
|
||||
await page.getByRole('link', { name: 'New organisation' }).click();
|
||||
await page.getByLabel('Organisation name (required)').fill(name);
|
||||
await page.getByRole('button', { name: 'Submit' }).click();
|
||||
|
||||
await utils.checkNotification(page, 'Organisation created');
|
||||
});
|
||||
}
|
||||
|
||||
export async function members(test, page: Page, name: string) {
|
||||
await test.step(`Navigate to ${name}`, async () => {
|
||||
await page.locator('a').filter({ hasText: 'Admin Console' }).first().click();
|
||||
await page.locator('org-switcher').getByLabel(/Toggle collapse/).click();
|
||||
await page.locator('org-switcher').getByRole('link', { name: `${name}` }).first().click();
|
||||
await expect(page.getByRole('heading', { name: `${name} collections` })).toBeVisible();
|
||||
await page.locator('div').filter({ hasText: 'Members' }).nth(2).click();
|
||||
await expect(page.getByRole('heading', { name: 'Members' })).toBeVisible();
|
||||
});
|
||||
}
|
||||
|
||||
export async function invite(test, page: Page, name: string, email: string) {
|
||||
await test.step(`Invite ${email}`, async () => {
|
||||
await expect(page.getByRole('heading', { name: 'Members' })).toBeVisible();
|
||||
await page.getByRole('button', { name: 'Invite member' }).click();
|
||||
await page.getByLabel('Email (required)').fill(email);
|
||||
await page.getByRole('tab', { name: 'Collections' }).click();
|
||||
await page.getByLabel('Permission').selectOption('edit');
|
||||
await page.getByLabel('Select collections').click();
|
||||
await page.getByLabel('Options list').getByText('Default collection').click();
|
||||
await page.getByRole('button', { name: 'Save' }).click();
|
||||
await utils.checkNotification(page, 'User(s) invited');
|
||||
});
|
||||
}
|
||||
|
||||
export async function confirm(test, page: Page, name: string, user_name: string) {
|
||||
await test.step(`Confirm ${user_name}`, async () => {
|
||||
await expect(page.getByRole('heading', { name: 'Members' })).toBeVisible();
|
||||
await page.getByRole('row', { name: user_name }).getByLabel('Options').click();
|
||||
await page.getByRole('menuitem', { name: 'Confirm' }).click();
|
||||
await expect(page.getByRole('heading', { name: 'Confirm user' })).toBeVisible();
|
||||
await page.getByRole('button', { name: 'Confirm' }).click();
|
||||
await utils.checkNotification(page, 'confirmed');
|
||||
});
|
||||
}
|
||||
|
||||
export async function revoke(test, page: Page, name: string, user_name: string) {
|
||||
await test.step(`Revoke ${user_name}`, async () => {
|
||||
await expect(page.getByRole('heading', { name: 'Members' })).toBeVisible();
|
||||
await page.getByRole('row', { name: user_name }).getByLabel('Options').click();
|
||||
await page.getByRole('menuitem', { name: 'Revoke access' }).click();
|
||||
await expect(page.getByRole('heading', { name: 'Revoke access' })).toBeVisible();
|
||||
await page.getByRole('button', { name: 'Revoke access' }).click();
|
||||
await utils.checkNotification(page, 'Revoked organisation access');
|
||||
});
|
||||
}
|
|
@ -1,6 +1,8 @@
|
|||
import { expect, type Page, Test } from '@playwright/test';
|
||||
import { type MailBuffer, MailServer } from 'maildev';
|
||||
|
||||
import * as utils from '../../global-utils';
|
||||
|
||||
/**
|
||||
* If a MailBuffer is passed it will be used and consume the expected emails
|
||||
*/
|
||||
|
@ -44,8 +46,8 @@ export async function logNewUser(
|
|||
|
||||
if( mailBuffer ){
|
||||
await test.step('Check emails', async () => {
|
||||
await expect(mailBuffer.next((m) => m.subject === "Welcome")).resolves.toBeDefined();
|
||||
await expect(mailBuffer.next((m) => m.subject.includes("New Device Logged"))).resolves.toBeDefined();
|
||||
await expect(mailBuffer.next((m) => m.subject === "Master Password Has Been Changed")).resolves.toBeDefined();
|
||||
});
|
||||
}
|
||||
});
|
||||
|
|
|
@ -1,6 +1,9 @@
|
|||
import { expect, type Browser,Page } from '@playwright/test';
|
||||
import { type MailBuffer } from 'maildev';
|
||||
|
||||
export async function createAccount(test, page: Page, user: { email: string, name: string, password: string }, emails) {
|
||||
import * as utils from '../../global-utils';
|
||||
|
||||
export async function createAccount(test, page: Page, user: { email: string, name: string, password: string }, mailBuffer?: MailBuffer) {
|
||||
await test.step('Create user', async () => {
|
||||
// Landing page
|
||||
await page.goto('/');
|
||||
|
@ -16,16 +19,15 @@ export async function createAccount(test, page: Page, user: { email: string, nam
|
|||
|
||||
// Back to the login page
|
||||
await expect(page).toHaveTitle('Vaultwarden Web');
|
||||
await expect(page.getByTestId("toast-message")).toHaveText(/Your new account has been created/);
|
||||
await utils.checkNotification(page, 'Your new account has been created');
|
||||
|
||||
if( emails ){
|
||||
const { value: welcome } = await emails.next();
|
||||
expect(welcome.subject).toContain("Welcome");
|
||||
if( mailBuffer ){
|
||||
await expect(mailBuffer.next((m) => m.subject === "Welcome")).resolves.toBeDefined();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
export async function logUser(test, page: Page, user: { email: string, password: string }, emails) {
|
||||
export async function logUser(test, page: Page, user: { email: string, password: string }, mailBuffer?: MailBuffer) {
|
||||
await test.step('Log user', async () => {
|
||||
// Landing page
|
||||
await page.goto('/');
|
||||
|
@ -39,9 +41,8 @@ export async function logUser(test, page: Page, user: { email: string, password:
|
|||
// We are now in the default vault page
|
||||
await expect(page).toHaveTitle(/Vaultwarden Web/);
|
||||
|
||||
if( emails ){
|
||||
const { value: logged } = await emails.next();
|
||||
expect(logged.subject).toContain("New Device Logged");
|
||||
if( mailBuffer ){
|
||||
await expect(mailBuffer.next((m) => m.subject === 'New Device Logged In From Firefox')).resolves.toBeDefined();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
|
|
@ -30,7 +30,7 @@ test.beforeAll('Setup', async ({ browser }, testInfo: TestInfo) => {
|
|||
|
||||
test.afterAll('Teardown', async ({}) => {
|
||||
utils.stopVaultwarden();
|
||||
[mailServer, mail1Buffer, mail2Buffer, mail3Buffer].map((m) => m?.close());
|
||||
[mail1Buffer, mail2Buffer, mail3Buffer, mailServer].map((m) => m?.close());
|
||||
});
|
||||
|
||||
test('Create user3', async ({ page }) => {
|
||||
|
@ -55,8 +55,7 @@ test('Invite users', async ({ page }) => {
|
|||
await page.getByLabel('Select collections').click();
|
||||
await page.getByLabel('Options list').getByText('Default collection').click();
|
||||
await page.getByRole('button', { name: 'Save' }).click();
|
||||
await expect(page.getByTestId("toast-message")).toHaveText('User(s) invited');
|
||||
await page.locator('#toast-container').getByRole('button').click();
|
||||
await utils.checkNotification(page, 'User(s) invited');
|
||||
});
|
||||
|
||||
await test.step('Invite user3', async () => {
|
||||
|
@ -67,12 +66,11 @@ test('Invite users', async ({ page }) => {
|
|||
await page.getByLabel('Select collections').click();
|
||||
await page.getByLabel('Options list').getByText('Default collection').click();
|
||||
await page.getByRole('button', { name: 'Save' }).click();
|
||||
await expect(page.getByTestId("toast-message")).toHaveText('User(s) invited');
|
||||
await page.locator('#toast-container').getByRole('button').click();
|
||||
await utils.checkNotification(page, 'User(s) invited');
|
||||
});
|
||||
});
|
||||
|
||||
test.fail('invited with new account', async ({ page }) => {
|
||||
test('invited with new account', async ({ page }) => {
|
||||
const link = await test.step('Extract email link', async () => {
|
||||
const invited = await mail2Buffer.next((m) => m.subject === "Join Test");
|
||||
await page.setContent(invited.html);
|
||||
|
@ -99,8 +97,7 @@ test.fail('invited with new account', async ({ page }) => {
|
|||
|
||||
await test.step('Default vault page', async () => {
|
||||
await expect(page).toHaveTitle(/Vaultwarden Web/);
|
||||
await expect(page.getByTestId("toast-title")).toHaveText("Invitation accepted");
|
||||
await page.locator('#toast-container').getByRole('button').click();
|
||||
// await utils.checkNotification(page, 'Invitation accepted');
|
||||
});
|
||||
|
||||
await test.step('Check mails', async () => {
|
||||
|
@ -135,8 +132,7 @@ test('invited with existing account', async ({ page }) => {
|
|||
|
||||
await test.step('Default vault page', async () => {
|
||||
await expect(page).toHaveTitle(/Vaultwarden Web/);
|
||||
await expect(page.getByTestId("toast-title")).toHaveText("Invitation accepted");
|
||||
await page.locator('#toast-container').getByRole('button').click();
|
||||
await utils.checkNotification(page, 'Invitation accepted');
|
||||
});
|
||||
|
||||
await test.step('Check mails', async () => {
|
||||
|
|
|
@ -39,8 +39,7 @@ test('Invite users', async ({ page }) => {
|
|||
await page.getByLabel('Select collections').click();
|
||||
await page.getByLabel('Options list').getByText('Default collection').click();
|
||||
await page.getByRole('button', { name: 'Save' }).click();
|
||||
await expect(page.getByTestId("toast-message")).toHaveText('User(s) invited');
|
||||
await page.locator('#toast-container').getByRole('button').click();
|
||||
await utils.checkNotification(page, 'User(s) invited');
|
||||
await expect(page.getByRole('row', { name: users.user2.email })).toHaveText(/Invited/);
|
||||
});
|
||||
|
||||
|
@ -52,8 +51,7 @@ test('Invite users', async ({ page }) => {
|
|||
await page.getByLabel('Select collections').click();
|
||||
await page.getByLabel('Options list').getByText('Default collection').click();
|
||||
await page.getByRole('button', { name: 'Save' }).click();
|
||||
await expect(page.getByTestId("toast-message")).toHaveText('User(s) invited');
|
||||
await page.locator('#toast-container').getByRole('button').click();
|
||||
await utils.checkNotification(page, 'User(s) invited');
|
||||
await expect(page.getByRole('row', { name: users.user3.name })).toHaveText(/Needs confirmation/);
|
||||
});
|
||||
|
||||
|
@ -61,8 +59,7 @@ test('Invite users', async ({ page }) => {
|
|||
await page.getByRole('row', { name: users.user3.name }).getByLabel('Options').click();
|
||||
await page.getByRole('menuitem', { name: 'Confirm' }).click();
|
||||
await page.getByRole('button', { name: 'Confirm' }).click();
|
||||
await expect(page.getByTestId("toast-message")).toHaveText(/confirmed/);
|
||||
await page.locator('#toast-container').getByRole('button').click();
|
||||
await utils.checkNotification(page, 'confirmed');
|
||||
});
|
||||
});
|
||||
|
||||
|
@ -82,8 +79,7 @@ test('Confirm invited user', async ({ page }) => {
|
|||
await page.getByRole('row', { name: users.user2.name }).getByLabel('Options').click();
|
||||
await page.getByRole('menuitem', { name: 'Confirm' }).click();
|
||||
await page.getByRole('button', { name: 'Confirm' }).click();
|
||||
await expect(page.getByTestId("toast-message")).toHaveText(/confirmed/);
|
||||
await page.locator('#toast-container').getByRole('button').click();
|
||||
await utils.checkNotification(page, 'confirmed');
|
||||
});
|
||||
});
|
||||
|
||||
|
|
Laden …
Tabelle hinzufügen
In neuem Issue referenzieren