forked from trent_larson/crowd-funder-for-time-pwa
add tests for new activity of offers-directly-to-user
This commit is contained in:
@@ -221,6 +221,7 @@
|
|||||||
<button
|
<button
|
||||||
class="text-sm bg-gradient-to-b from-blue-400 to-blue-700 shadow-[inset_0_-1px_0_0_rgba(0,0,0,0.5)] text-white px-2 py-1.5 rounded-md border border-blue-400"
|
class="text-sm bg-gradient-to-b from-blue-400 to-blue-700 shadow-[inset_0_-1px_0_0_rgba(0,0,0,0.5)] text-white px-2 py-1.5 rounded-md border border-blue-400"
|
||||||
@click="openOfferDialog(contact.did, contact.name)"
|
@click="openOfferDialog(contact.did, contact.name)"
|
||||||
|
data-testId="offerButton"
|
||||||
>
|
>
|
||||||
Offer
|
Offer
|
||||||
</button>
|
</button>
|
||||||
|
|||||||
@@ -206,7 +206,10 @@
|
|||||||
v-if="numNewOffersToUser"
|
v-if="numNewOffersToUser"
|
||||||
class="bg-gradient-to-b from-green-400 to-green-700 shadow-[inset_0_-1px_0_0_rgba(0,0,0,0.5)] px-4 py-4 rounded-md text-white"
|
class="bg-gradient-to-b from-green-400 to-green-700 shadow-[inset_0_-1px_0_0_rgba(0,0,0,0.5)] px-4 py-4 rounded-md text-white"
|
||||||
>
|
>
|
||||||
<span class="block text-center text-6xl">
|
<span
|
||||||
|
class="block text-center text-6xl"
|
||||||
|
data-testId="newDirectOffersActivityNumber"
|
||||||
|
>
|
||||||
{{ numNewOffersToUser }}
|
{{ numNewOffersToUser }}
|
||||||
</span>
|
</span>
|
||||||
<p>new offer{{ numNewOffersToUser === 1 ? "" : "s" }} to you</p>
|
<p>new offer{{ numNewOffersToUser === 1 ? "" : "s" }} to you</p>
|
||||||
|
|||||||
@@ -25,18 +25,25 @@
|
|||||||
:icon="showOffersDetails ? 'chevron-down' : 'chevron-right'"
|
:icon="showOffersDetails ? 'chevron-down' : 'chevron-right'"
|
||||||
class="cursor-pointer ml-4 text-lg"
|
class="cursor-pointer ml-4 text-lg"
|
||||||
@click="expandOffersToUserAndMarkRead()"
|
@click="expandOffersToUserAndMarkRead()"
|
||||||
|
data-testid="showOffersToUser"
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div v-if="showOffersDetails" class="ml-4">
|
<div v-if="showOffersDetails" class="ml-4">
|
||||||
<ul class="list-disc ml-4">
|
<ul class="list-disc ml-4">
|
||||||
<li v-for="offer in newOffersToUser" :key="offer.id" class="mt-4 relative group">
|
<li
|
||||||
|
v-for="offer in newOffersToUser"
|
||||||
|
:key="offer.id"
|
||||||
|
class="mt-4 relative group"
|
||||||
|
>
|
||||||
<span>{{
|
<span>{{
|
||||||
didInfo(offer.offeredByDid, activeDid, allMyDids, allContacts)
|
didInfo(offer.offeredByDid, activeDid, allMyDids, allContacts)
|
||||||
}}</span>
|
}}</span>
|
||||||
offers
|
offers
|
||||||
<span v-if="offer.objectDescription">{{ offer.objectDescription }}
|
<span v-if="offer.objectDescription">{{
|
||||||
</span>{{ offer.objectDescription && offer.amount ? ", and " : "" }}
|
offer.objectDescription
|
||||||
|
}}</span
|
||||||
|
>{{ offer.objectDescription && offer.amount ? ", and " : "" }}
|
||||||
<span v-if="offer.amount">{{
|
<span v-if="offer.amount">{{
|
||||||
displayAmount(offer.unit, offer.amount)
|
displayAmount(offer.unit, offer.amount)
|
||||||
}}</span>
|
}}</span>
|
||||||
@@ -67,7 +74,12 @@ import GiftedDialog from "@/components/GiftedDialog.vue";
|
|||||||
import QuickNav from "@/components/QuickNav.vue";
|
import QuickNav from "@/components/QuickNav.vue";
|
||||||
import EntityIcon from "@/components/EntityIcon.vue";
|
import EntityIcon from "@/components/EntityIcon.vue";
|
||||||
import { NotificationIface } from "@/constants/app";
|
import { NotificationIface } from "@/constants/app";
|
||||||
import { accountsDB, db, retrieveSettingsForActiveAccount, updateAccountSettings } from "@/db/index";
|
import {
|
||||||
|
accountsDB,
|
||||||
|
db,
|
||||||
|
retrieveSettingsForActiveAccount,
|
||||||
|
updateAccountSettings,
|
||||||
|
} from "@/db/index";
|
||||||
import { Contact } from "@/db/tables/contacts";
|
import { Contact } from "@/db/tables/contacts";
|
||||||
import {
|
import {
|
||||||
didInfo,
|
didInfo,
|
||||||
@@ -151,7 +163,9 @@ export default class NewActivityView extends Vue {
|
|||||||
}
|
}
|
||||||
|
|
||||||
async markOffersAsReadStartingWith(jwtId: string) {
|
async markOffersAsReadStartingWith(jwtId: string) {
|
||||||
const index = this.newOffersToUser.findIndex(offer => offer.jwtId === jwtId);
|
const index = this.newOffersToUser.findIndex(
|
||||||
|
(offer) => offer.jwtId === jwtId,
|
||||||
|
);
|
||||||
if (index !== -1 && index < this.newOffersToUser.length - 1) {
|
if (index !== -1 && index < this.newOffersToUser.length - 1) {
|
||||||
// Set to the next offer's jwtId
|
// Set to the next offer's jwtId
|
||||||
await updateAccountSettings(this.activeDid, {
|
await updateAccountSettings(this.activeDid, {
|
||||||
|
|||||||
79
test-playwright/60-new-activity.spec.ts
Normal file
79
test-playwright/60-new-activity.spec.ts
Normal file
@@ -0,0 +1,79 @@
|
|||||||
|
import { test, expect } from '@playwright/test';
|
||||||
|
import { importUser, generateNewEthrUser, switchToUser } from './testUtils';
|
||||||
|
|
||||||
|
test('New offers for another user', async ({ page }) => {
|
||||||
|
const user01Did = await generateNewEthrUser(page);
|
||||||
|
await page.goto('./');
|
||||||
|
expect(page.getByTestId('newDirectOffersActivityNumber')).toBeHidden();
|
||||||
|
|
||||||
|
await importUser(page, '00');
|
||||||
|
await page.goto('./contacts');
|
||||||
|
await page.getByPlaceholder('URL or DID, Name, Public Key').fill(user01Did + ', A Friend');
|
||||||
|
await page.locator('button > svg.fa-plus').click();
|
||||||
|
await expect(page.locator('div[role="alert"] span:has-text("Contact Added")')).toBeVisible();
|
||||||
|
await page.locator('div[role="alert"] button:has-text("No")').click(); // don't register
|
||||||
|
await page.locator('div[role="alert"] button > svg.fa-xmark').click(); // dismiss info alert
|
||||||
|
await expect(page.locator('div[role="alert"] button > svg.fa-xmark')).toBeHidden(); // ensure alert is gone
|
||||||
|
|
||||||
|
// show buttons to make offers directly to people
|
||||||
|
await page.getByRole('button').filter({ hasText: /Show Given Hours/i }).click();
|
||||||
|
|
||||||
|
// make an offer directly to user 1
|
||||||
|
// Generate a random string of 3 characters, skipping the "0." at the beginning
|
||||||
|
const randomString1 = Math.random().toString(36).substring(2, 5);
|
||||||
|
await page.getByTestId('offerButton').click();
|
||||||
|
await page.getByTestId('inputDescription').fill(`help of ${randomString1} from #000`);
|
||||||
|
await page.getByTestId('inputOfferAmount').fill('1');
|
||||||
|
await page.getByRole('button', { name: 'Sign & Send' }).click();
|
||||||
|
await expect(page.getByText('That offer was recorded.')).toBeVisible();
|
||||||
|
await page.locator('div[role="alert"] button > svg.fa-xmark').click(); // dismiss info alert
|
||||||
|
await expect(page.locator('div[role="alert"] button > svg.fa-xmark')).toBeHidden(); // ensure alert is gone
|
||||||
|
|
||||||
|
// make another offer to user 1
|
||||||
|
const randomString2 = Math.random().toString(36).substring(2, 5);
|
||||||
|
await page.getByTestId('offerButton').click();
|
||||||
|
await page.getByTestId('inputDescription').fill(`help of ${randomString2} from #000`);
|
||||||
|
await page.getByTestId('inputOfferAmount').fill('3');
|
||||||
|
await page.getByRole('button', { name: 'Sign & Send' }).click();
|
||||||
|
await expect(page.getByText('That offer was recorded.')).toBeVisible();
|
||||||
|
await page.locator('div[role="alert"] button > svg.fa-xmark').click(); // dismiss info alert
|
||||||
|
await expect(page.locator('div[role="alert"] button > svg.fa-xmark')).toBeHidden(); // ensure alert is gone
|
||||||
|
|
||||||
|
// as user 1, go to the home page and check that two offers are shown as new
|
||||||
|
await switchToUser(page, user01Did);
|
||||||
|
await page.goto('./');
|
||||||
|
await page.getByTestId('closeOnboardingAndFinish').click();
|
||||||
|
let offerNumElem = page.getByTestId('newDirectOffersActivityNumber');
|
||||||
|
await expect(offerNumElem).toHaveText('2');
|
||||||
|
await offerNumElem.click();
|
||||||
|
|
||||||
|
await expect(page.getByText('New Offers To You')).toBeVisible();
|
||||||
|
await page.getByTestId('showOffersToUser').click();
|
||||||
|
// note that they show in reverse chronologicalorder
|
||||||
|
await expect(page.getByText(`help of ${randomString2} from #000`)).toBeVisible();
|
||||||
|
await expect(page.getByText(`help of ${randomString1} from #000`)).toBeVisible();
|
||||||
|
|
||||||
|
// click on the latest offer to keep it as "unread"
|
||||||
|
await page.hover(`li:has-text("help of ${randomString2} from #000")`);
|
||||||
|
// await page.locator('li').filter({ hasText: `help of ${randomString2} from #000` }).click();
|
||||||
|
// await page.locator('div').filter({ hasText: /keep all above/ }).click();
|
||||||
|
// now find the "Click to keep all above as new offers" after that list item and click it
|
||||||
|
const liElem = page.locator('li').filter({ hasText: `help of ${randomString2} from #000` });
|
||||||
|
await liElem.hover();
|
||||||
|
const keepAboveAsNew = liElem.locator('div').filter({ hasText: /keep all above/ });
|
||||||
|
await keepAboveAsNew.click();
|
||||||
|
|
||||||
|
// now see that only one offer is shown as new
|
||||||
|
await page.goto('./');
|
||||||
|
offerNumElem = page.getByTestId('newDirectOffersActivityNumber');
|
||||||
|
await expect(offerNumElem).toHaveText('1');
|
||||||
|
await offerNumElem.click();
|
||||||
|
await expect(page.getByText('New Offer To You')).toBeVisible();
|
||||||
|
await page.getByTestId('showOffersToUser').click();
|
||||||
|
|
||||||
|
// now see that no offers are shown as new
|
||||||
|
await page.goto('./');
|
||||||
|
// wait until the list with ID listLatestActivity has at least one visible item
|
||||||
|
await page.locator('#listLatestActivity li').first().waitFor({ state: 'visible' });
|
||||||
|
await expect(page.getByTestId('newDirectOffersActivityNumber')).toBeHidden();
|
||||||
|
});
|
||||||
@@ -34,10 +34,12 @@ export async function importUser(page: Page, id?: string): Promise<string> {
|
|||||||
|
|
||||||
// This is to switch to someone already in the identity table. It doesn't include registration.
|
// This is to switch to someone already in the identity table. It doesn't include registration.
|
||||||
export async function switchToUser(page: Page, did: string): Promise<void> {
|
export async function switchToUser(page: Page, did: string): Promise<void> {
|
||||||
// await page.goto('./account');
|
// This is the direct approach but users have to tap on things so we'll do that instead.
|
||||||
// await page.getByRole('heading', { name: 'Advanced' }).click();
|
//await page.goto('./identity-switcher');
|
||||||
// await page.getByRole('link', { name: 'Switch Identifier' }).click();
|
|
||||||
await page.goto('./identity-switcher');
|
await page.goto('./account');
|
||||||
|
await page.getByRole('heading', { name: 'Advanced' }).click();
|
||||||
|
await page.getByRole('link', { name: 'Switch Identifier' }).click();
|
||||||
const didElem = await page.locator(`code:has-text("${did}")`);
|
const didElem = await page.locator(`code:has-text("${did}")`);
|
||||||
await didElem.isVisible();
|
await didElem.isVisible();
|
||||||
await didElem.click();
|
await didElem.click();
|
||||||
|
|||||||
Reference in New Issue
Block a user