= [
name: "offer-details",
component: () => import("../views/OfferDetailsView.vue"),
},
+ {
+ path: "/onboard-meeting-list",
+ name: "onboard-meeting-list",
+ component: () => import("../views/OnboardMeetingListView.vue"),
+ },
+ {
+ path: "/onboard-meeting-members/:groupId",
+ name: "onboard-meeting-members",
+ component: () => import("../views/OnboardMeetingMembersView.vue"),
+ },
+ {
+ path: "/onboard-meeting-setup",
+ name: "onboard-meeting-setup",
+ component: () => import("../views/OnboardMeetingSetupView.vue"),
+ },
{
path: "/project/:id?",
name: "project",
diff --git a/src/views/ClaimReportCertificateView.vue b/src/views/ClaimReportCertificateView.vue
new file mode 100644
index 0000000..0cfd08c
--- /dev/null
+++ b/src/views/ClaimReportCertificateView.vue
@@ -0,0 +1,190 @@
+
+
+
+
+
+
+
diff --git a/src/views/ContactsView.vue b/src/views/ContactsView.vue
index 8d553e2..8e06f1a 100644
--- a/src/views/ContactsView.vue
+++ b/src/views/ContactsView.vue
@@ -23,27 +23,50 @@
-
-
-
-
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
{{
- shortDid(contact.did)
+ libsUtil.shortDid(contact.did)
}}
@@ -587,6 +610,18 @@ export default class ContactsView extends Vue {
);
}
+ private warning(message: string, title: string = "Error", timeout = 5000) {
+ this.$notify(
+ {
+ group: "alert",
+ type: "warning",
+ title: title,
+ text: message,
+ },
+ timeout,
+ );
+ }
+
private showOnboardingInfo() {
this.$notify(
{
@@ -1338,21 +1373,6 @@ export default class ContactsView extends Vue {
});
}
- private shortDid(did: string) {
- if (did.startsWith("did:peer:")) {
- return (
- did.substring(0, "did:peer:".length + 2) +
- "..." +
- did.substring("did:peer:".length + 18, "did:peer:".length + 25) +
- "..."
- );
- } else if (did.startsWith("did:ethr:")) {
- return did.substring(0, "did:ethr:".length + 9) + "...";
- } else {
- return did.substring(0, did.indexOf(":", 4) + 7) + "...";
- }
- }
-
private showCopySelectionsInfo() {
this.$notify(
{
@@ -1364,5 +1384,59 @@ export default class ContactsView extends Vue {
5000,
);
}
+
+ private async showOnboardMeetingDialog() {
+ try {
+ // First check if they're in a meeting
+ const headers = await getHeaders(this.activeDid);
+ const memberResponse = await this.axios.get(
+ this.apiServer + "/api/partner/groupOnboardMember",
+ { headers },
+ );
+
+ if (memberResponse.data.data) {
+ // They're in a meeting, check if they're the host
+ const hostResponse = await this.axios.get(
+ this.apiServer + "/api/partner/groupOnboard",
+ { headers },
+ );
+
+ if (hostResponse.data.data) {
+ // They're the host, take them to setup
+ (this.$router as Router).push({ name: "onboard-meeting-setup" });
+ } else {
+ // They're not the host, take them to list
+ (this.$router as Router).push({ name: "onboard-meeting-list" });
+ }
+ } else {
+ // They're not in a meeting, show the dialog
+ this.$notify(
+ {
+ group: "modal",
+ type: "confirm",
+ title: "Onboarding Meeting",
+ text: "Would you like to start a new meeting?",
+ onYes: async () => {
+ (this.$router as Router).push({ name: "onboard-meeting-setup" });
+ },
+ yesText: "Start New Meeting",
+ onNo: async () => {
+ (this.$router as Router).push({ name: "onboard-meeting-list" });
+ },
+ noText: "Join Existing Meeting",
+ },
+ -1,
+ );
+ }
+ } catch (error) {
+ logConsoleAndDb(
+ "Error checking meeting status:" + errorStringForLog(error),
+ );
+ this.danger(
+ "There was an error checking your meeting status.",
+ "Meeting Error",
+ );
+ }
+ }
}
diff --git a/src/views/HomeView.vue b/src/views/HomeView.vue
index ae2156f..2db6c18 100644
--- a/src/views/HomeView.vue
+++ b/src/views/HomeView.vue
@@ -366,6 +366,8 @@
+
+
diff --git a/src/views/NewEditProjectView.vue b/src/views/NewEditProjectView.vue
index 2f15508..610e073 100644
--- a/src/views/NewEditProjectView.vue
+++ b/src/views/NewEditProjectView.vue
@@ -204,7 +204,11 @@ import { AxiosError, AxiosRequestHeaders } from "axios";
import { DateTime } from "luxon";
import { hexToBytes } from "@noble/hashes/utils";
// these core imports could also be included as "import type ..."
-import { EventTemplate, UnsignedEvent, VerifiedEvent } from "nostr-tools/core";
+import {
+ EventTemplate,
+ UnsignedEvent,
+ VerifiedEvent,
+} from "nostr-tools/lib/types/core";
import {
accountFromExtendedKey,
extendedKeysFromSeedWords,
diff --git a/src/views/OnboardMeetingListView.vue b/src/views/OnboardMeetingListView.vue
new file mode 100644
index 0000000..480dc1c
--- /dev/null
+++ b/src/views/OnboardMeetingListView.vue
@@ -0,0 +1,343 @@
+
+
+
+
+
+
+
+ Onboarding Meetings
+
+
+
+
+
+
+
+
+
You are in this meeting.
+
+
+
{{ attendingMeeting.name }}
+
+
+
+
+
+
+
+
+
{{ meeting.name }}
+
+
+
+ No onboarding meetings available
+
+
+
+
+
+
+
Enter Meeting Password
+
+
+
+
+
+
+
+
+
+
+
diff --git a/src/views/OnboardMeetingMembersView.vue b/src/views/OnboardMeetingMembersView.vue
new file mode 100644
index 0000000..6618fc3
--- /dev/null
+++ b/src/views/OnboardMeetingMembersView.vue
@@ -0,0 +1,72 @@
+
+
+
+
+
+
+
+ Meeting Members
+
+
+
+
+
+ {{ errorMessage }}
+
+
+ For authorization, wait for your meeting organizer to approve you.
+
+
+
+
+
+
+
+
+
diff --git a/src/views/OnboardMeetingSetupView.vue b/src/views/OnboardMeetingSetupView.vue
new file mode 100644
index 0000000..a81c760
--- /dev/null
+++ b/src/views/OnboardMeetingSetupView.vue
@@ -0,0 +1,676 @@
+
+
+
+
+
+
+
+ Onboarding Meeting
+
+
+
+
+
+
+
Current Meeting
+
+
+
+
+
+
Name: {{ currentMeeting.name }}
+
+ Expires:
+ {{ formatExpirationTime(currentMeeting.expiresAt) }}
+
+
+
+
+ Share the password with the people you want to onboard.
+
+
+
+ Your copy of the password is not saved. Edit the meeting, or delete it
+ and create a new meeting.
+
+
+
+
+
+
+
+
Delete Meeting?
+
+ This action cannot be undone. Are you sure you want to delete this
+ meeting?
+
+
+
+
+
+
+
+
+
+
+
+ {{ isInCreateMode() ? "Create New Meeting" : "Edit Meeting" }}
+
+
+
+
+
+
+
+
+
Meeting Members
+
+
+ Open shortcut page for members
+
+
+
+
+
+
+
+
+
+
diff --git a/src/views/QuickActionBvcEndView.vue b/src/views/QuickActionBvcEndView.vue
index e147a9d..1fbc56e 100644
--- a/src/views/QuickActionBvcEndView.vue
+++ b/src/views/QuickActionBvcEndView.vue
@@ -22,7 +22,7 @@
Confirm
-
+
There are no claims yet today for you to confirm.
diff --git a/src/views/TestView.vue b/src/views/TestView.vue
index 4d25524..ceb8704 100644
--- a/src/views/TestView.vue
+++ b/src/views/TestView.vue
@@ -35,7 +35,7 @@
5000,
)
"
- class="font-bold uppercase bg-slate-900 text-white px-3 py-2 rounded-md mr-2"
+ class="font-bold capitalize bg-slate-900 text-white px-3 py-2 rounded-md mr-2"
>
Toast
@@ -52,7 +52,7 @@
5000,
)
"
- class="font-bold uppercase bg-slate-600 text-white px-3 py-2 rounded-md mr-2"
+ class="font-bold capitalize bg-slate-600 text-white px-3 py-2 rounded-md mr-2"
>
Info
@@ -69,7 +69,7 @@
5000,
)
"
- class="font-bold uppercase bg-emerald-600 text-white px-3 py-2 rounded-md mr-2"
+ class="font-bold capitalize bg-emerald-600 text-white px-3 py-2 rounded-md mr-2"
>
Success
@@ -86,7 +86,7 @@
5000,
)
"
- class="font-bold uppercase bg-amber-600 text-white px-3 py-2 rounded-md mr-2"
+ class="font-bold capitalize bg-amber-600 text-white px-3 py-2 rounded-md mr-2"
>
Warning
@@ -103,7 +103,7 @@
5000,
)
"
- class="font-bold uppercase bg-rose-600 text-white px-3 py-2 rounded-md mr-2"
+ class="font-bold capitalize bg-rose-600 text-white px-3 py-2 rounded-md mr-2"
>
Danger
@@ -118,7 +118,7 @@
-1,
)
"
- class="font-bold uppercase bg-slate-600 text-white px-3 py-2 rounded-md mr-2"
+ class="font-bold capitalize bg-slate-600 text-white px-3 py-2 rounded-md mr-2"
>
Notif ON
@@ -133,7 +133,7 @@
-1,
)
"
- class="font-bold uppercase bg-slate-600 text-white px-3 py-2 rounded-md mr-2"
+ class="font-bold capitalize bg-slate-600 text-white px-3 py-2 rounded-md mr-2"
>
Notif MUTE
@@ -148,7 +148,7 @@
-1,
)
"
- class="font-bold uppercase bg-slate-600 text-white px-3 py-2 rounded-md mr-2"
+ class="font-bold capitalize bg-slate-600 text-white px-3 py-2 rounded-md mr-2"
>
Notif OFF
@@ -184,7 +184,7 @@
Register Passkey
@@ -194,13 +194,13 @@
Create JWT
@@ -210,19 +210,19 @@
Verify New JWT
@@ -230,11 +230,25 @@
Verify New JWT -- requires creation first
+
+
+
Encryption & Decryption
+ See console for more output.
+
+
+ Result: {{ encryptionTestResult }}
+
+
@@ -248,6 +262,7 @@ import { Router } from "vue-router";
import QuickNav from "@/components/QuickNav.vue";
import { AppString, NotificationIface } from "@/constants/app";
import { db, retrieveSettingsForActiveAccount } from "@/db/index";
+import * as cryptoLib from "@/libs/crypto";
import * as vcLib from "@/libs/crypto/vc";
import {
PeerSetup,
@@ -279,6 +294,9 @@ const TEST_PAYLOAD = {
export default class Help extends Vue {
$notify!: (notification: NotificationIface, timeout?: number) => void;
+ // for encryption/decryption
+ encryptionTestResult?: boolean;
+
// for file import
fileName?: string;
@@ -289,6 +307,8 @@ export default class Help extends Vue {
peerSetup?: PeerSetup;
userName?: string;
+ cryptoLib = cryptoLib;
+
async mounted() {
const settings = await retrieveSettingsForActiveAccount();
this.activeDid = settings.activeDid || "";
@@ -363,6 +383,10 @@ export default class Help extends Vue {
this.credIdHex = account.passkeyCredIdHex;
}
+ public async testEncryptionDecryption() {
+ this.encryptionTestResult = await cryptoLib.testEncryptionDecryption();
+ }
+
public async createJwtSimplewebauthn() {
const account: AccountKeyInfo | undefined = await retrieveAccountMetadata(
this.activeDid || "",
diff --git a/test-playwright/00-noid-tests.spec.ts b/test-playwright/00-noid-tests.spec.ts
index df87db2..3631e87 100644
--- a/test-playwright/00-noid-tests.spec.ts
+++ b/test-playwright/00-noid-tests.spec.ts
@@ -84,8 +84,8 @@ test('Check setting name & sharing info', async ({ page }) => {
await expect(page.getByText('Set Your Name')).toBeVisible();
await page.getByRole('textbox').fill('Me Test User');
await page.locator('button:has-text("Save")').click();
- await expect(page.getByText('share another way')).toBeVisible();
- await page.getByRole('button', { name: /share another way/ }).click();
+ await expect(page.getByText('share some other way')).toBeVisible();
+ await page.getByRole('button', { name: /share some other way/ }).click();
await expect(page.getByRole('button', { name: 'copy to clipboard' })).toBeVisible();
await page.getByRole('button', { name: 'copy to clipboard' }).click();
await expect(page.getByText('contact info was copied')).toBeVisible();