Skip to content

Commit 83f1df5

Browse files
authored
Frontend - Web Node Loading Screen Improvements (#874)
1 parent 6a95fba commit 83f1df5

File tree

6 files changed

+170
-138
lines changed

6 files changed

+170
-138
lines changed

frontend/src/app/app.module.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,7 @@ export class AppGlobalErrorhandler implements ErrorHandler {
4444
constructor(private errorHandlerService: GlobalErrorHandlerService) {}
4545

4646
handleError(error: any): void {
47+
console.log(123123123);
4748
Sentry.captureException(error);
4849
this.errorHandlerService.handleError(error);
4950
console.error(error);

frontend/src/app/core/services/web-node.service.ts

Lines changed: 25 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,18 @@
11
import { Inject, Injectable } from '@angular/core';
2-
import { BehaviorSubject, catchError, filter, from, fromEvent, map, merge, Observable, of, switchMap, tap } from 'rxjs';
2+
import {
3+
BehaviorSubject,
4+
catchError,
5+
EMPTY,
6+
filter,
7+
from,
8+
fromEvent,
9+
map,
10+
merge,
11+
Observable,
12+
of,
13+
switchMap,
14+
tap,
15+
} from 'rxjs';
316
import base from 'base-x';
417
import { any } from '@openmina/shared';
518
import { HttpClient } from '@angular/common/http';
@@ -55,16 +68,15 @@ export class WebNodeService {
5568
}
5669

5770
loadWasm$(): Observable<void> {
58-
this.loadWebnodeJs();
59-
sendSentryEvent('Loading WebNode JS');
71+
this.webNodeStartTime = Date.now();
72+
// this.loadWebnodeJs();
6073
return merge(
6174
of(any(window).webnode).pipe(filter(Boolean)),
6275
fromEvent(window, 'webNodeLoaded'),
6376
).pipe(
6477
switchMap(() => this.http.get<{ publicKey: string, privateKey: string }>('assets/webnode/web-node-secrets.json')),
6578
tap(data => {
6679
this.webNodeKeyPair = data;
67-
sendSentryEvent('WebNode JS Loaded. Loading WebNode Wasm');
6880
}),
6981
map(() => void 0),
7082
);
@@ -75,19 +87,16 @@ export class WebNodeService {
7587
.pipe(
7688
switchMap((wasm: any) => from(wasm.default('assets/webnode/pkg/openmina_node_web_bg.wasm')).pipe(map(() => wasm))),
7789
switchMap((wasm) => {
78-
sendSentryEvent('WebNode Wasm loaded. Starting WebNode');
7990
this.webnodeProgress$.next('Loaded');
8091
return from(wasm.run(this.webNodeKeyPair.privateKey));
8192
}),
8293
tap((webnode: any) => {
83-
sendSentryEvent('WebNode Started');
84-
this.webNodeStartTime = Date.now();
8594
(window as any)['webnode'] = webnode;
8695
this.webnode$.next(webnode);
8796
this.webnodeProgress$.next('Started');
8897
}),
8998
catchError((error) => {
90-
sendSentryEvent('WebNode failed to start');
99+
sendSentryEvent('WebNode failed to start: ' + error.message);
91100
console.error(error);
92101
return of(null);
93102
}),
@@ -115,18 +124,16 @@ export class WebNodeService {
115124
filter(Boolean),
116125
switchMap(handle => from(any(handle).state().peers())),
117126
tap((peers) => {
118-
if (!this.sentryEvents.sentNoPeersEvent && Date.now() - this.webNodeStartTime >= 5000 && peers.length === 0) {
119-
sendSentryEvent('WebNode has no peers after 5 seconds from startup.');
120-
this.sentryEvents.sentNoPeersEvent = true;
121-
}
122-
if (!this.sentryEvents.sentPeersEvent && peers.length > 0) {
123-
const seconds = (Date.now() - this.webNodeStartTime) / 1000;
124-
sendSentryEvent(`WebNode found its first peer after ${seconds}s`);
125-
this.sentryEvents.sentPeersEvent = true;
126-
}
127+
// if (!this.sentryEvents.sentNoPeersEvent && Date.now() - this.webNodeStartTime >= 5000 && peers.length === 0) {
128+
// sendSentryEvent('WebNode has no peers after 5 seconds from startup.');
129+
// this.sentryEvents.sentNoPeersEvent = true;
130+
// }
131+
// if (!this.sentryEvents.sentPeersEvent && peers.length > 0) {
132+
// this.sentryEvents.sentPeersEvent = true;
133+
// }
127134
if (!this.sentryEvents.firstPeerConnected && peers.some((p: any) => p.connection_status === DashboardPeerStatus.CONNECTED)) {
128135
const seconds = (Date.now() - this.webNodeStartTime) / 1000;
129-
sendSentryEvent(`WebNode connected to its first peer after ${seconds}s`);
136+
sendSentryEvent(`WebNode connected in ${seconds.toFixed(1)}s`);
130137
this.sentryEvents.firstPeerConnected = true;
131138
this.webnodeProgress$.next('Connected');
132139
}

frontend/src/app/features/webnode/web-node-demo-dashboard/web-node-demo-dashboard.component.html

Lines changed: 36 additions & 49 deletions
Original file line numberDiff line numberDiff line change
@@ -1,74 +1,61 @@
11
<div class="logo-header w-100 border-bottom fx-row-full-cent">
22
<img ngSrc="assets/images/logo/logo-text.svg" height="40" width="136"/>
33
</div>
4-
<div class="data-wrapper flex-column flex-around align-center">
5-
<div class="header flex-column align-center pl-10 pr-10 text-center mb-16">
6-
<div class="loading-webnode f-500">
7-
Produce blocks,
8-
<span>right in your browser</span>
9-
</div>
4+
<div class="data-wrapper flex-column w-100 overflow-auto align-center">
5+
<div class="loading-content h-100 flex-column flex-around align-center">
6+
<div class="header flex-column align-center pl-10 pr-10 text-center mb-16">
7+
<div class="loading-webnode f-500 mb-8">
8+
Produce blocks,
9+
<span>right in your browser</span>
10+
</div>
1011

11-
<div class="font-16 tertiary mt-16 font-16 f-300">
12-
@if (!loading[loading.length - 1].loaded) {
13-
@if (loading[0].status === WebNodeStepStatus.LOADING) {
14-
Downloading...
15-
} @else {
16-
~7 seconds left
17-
}
18-
} @else {
19-
Web Node is ready
20-
}
12+
<div class="font-16 tertiary f-300">{{ loadingMessage }}</div>
2113
</div>
22-
</div>
2314

24-
<div #progress class="progress w-100 fx-row-full-cent"></div>
15+
<div #progress class="progress w-100 fx-row-full-cent"></div>
2516

26-
<div class="mt-16 flex-column w-100 pl-10 pr-10">
27-
@for (item of loading; track $index) {
28-
<div class="fx-row-vert-cent h-xl font-16">
29-
@if (item.status === WebNodeStepStatus.LOADING) {
30-
<mina-loading-spinner [size]="20" [borderWidth]="2"></mina-loading-spinner>
31-
} @else {
32-
<span [ngClass]="item.status === WebNodeStepStatus.DONE ? 'success-primary' : 'tertiary'"
33-
class="circle-check mina-icon icon-200">check_circle</span>
34-
}
35-
<div [ngClass]="item.status === WebNodeStepStatus.PENDING ? 'tertiary' : 'primary'"
36-
class="ml-8 f-400">{{ item.name }}
37-
</div>
38-
@if (item.data) {
39-
@if (item.data.total) {
40-
<span class="tertiary ml-5">{{ item.data.downloaded }} of {{ item.data.total }} MB</span>
17+
<div class="mt-16 flex-column pl-10 pr-10">
18+
@for (item of loading; track $index) {
19+
<div class="fx-row-vert-cent h-xl font-16">
20+
@if (item.status === WebNodeStepStatus.LOADING) {
21+
<mina-loading-spinner [size]="20" [borderWidth]="2"></mina-loading-spinner>
4122
} @else {
42-
<span class="tertiary ml-5">{{ item.data.est }}</span>
23+
<span [ngClass]="item.status === WebNodeStepStatus.DONE ? 'success-primary' : 'tertiary'"
24+
class="circle-check mina-icon icon-200">check_circle</span>
4325
}
44-
}
45-
</div>
46-
}
26+
<div [ngClass]="item.status === WebNodeStepStatus.PENDING ? 'tertiary' : 'primary'"
27+
class="ml-8 f-400">{{ item.name }}
28+
</div>
29+
</div>
30+
}
31+
</div>
4732
</div>
4833

4934
@if (!loading[loading.length - 1].loaded && errors.length) {
50-
<div class="flex-column w-100 bg-surface p-12 mt-10 border-rad-6">
51-
<div class="font-16 flex-row flex-column-md flex-between align-center flex-start-md"
52-
[ngClass]="errors.length ? 'warn-primary' : 'aware-primary'">
53-
<div>It appears there are some errors.</div>
54-
</div>
55-
<div class="flex-column border-rad-8 warn-secondary monospace break-word">
56-
@for (error of errors; track $index) {
57-
<div class="lh-sm">{{ error }}</div>
58-
}
35+
<div class="flex-column w-100 pl-10 pr-10 mt-10">
36+
<div class="flex-column w-100 bg-surface p-12 border-rad-6">
37+
<div class="w-100 font-16 flex-row flex-column-md flex-between align-center flex-start-md"
38+
[ngClass]="errors.length ? 'warn-primary' : 'aware-primary'">
39+
<div>It appears there are some errors.</div>
40+
</div>
41+
<div class="flex-column border-rad-8 warn-secondary monospace break-word">
42+
@for (error of errors; track $index) {
43+
<div class="lh-sm">{{ error }}</div>
44+
}
45+
</div>
5946
</div>
6047
</div>
6148
}
6249
</div>
6350
<div class="footer border-top fx-row-vert-cent flex-between w-100 pl-10 pr-10">
64-
<div class="fx-row-vert-cent">
51+
<div class="fx-row-vert-cent mr-10">
6552
<span class="mina-icon icon-300 selected-primary mr-5">lightbulb</span>
6653
<div class="selected-primary f-big f-500">
6754
You can run the Web Node from your phone
6855
</div>
6956
</div>
70-
<button class="border-rad-8 fx-row-full-cent font-16 ml-10"
71-
[class.disabled]="!loading[loading.length - 1].loaded"
57+
<button class="border-rad-8 fx-row-full-cent font-16"
58+
[class.disabled]="!ready"
7259
(click)="goToDashboard()">
7360
<span>Continue</span>
7461
</button>

frontend/src/app/features/webnode/web-node-demo-dashboard/web-node-demo-dashboard.component.scss

Lines changed: 36 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -12,36 +12,42 @@ $white: #000000;
1212

1313
.logo-header {
1414
height: 56px;
15+
16+
img {
17+
opacity: 0.5;
18+
}
1519
}
1620

1721
.data-wrapper {
1822
height: calc(100% - 56px - 72px);
19-
max-width: 568px;
20-
padding: 10vw 0;
2123

22-
.header {
23-
.loading-webnode {
24-
font-size: 24px;
25-
line-height: 32px;
24+
.loading-content {
25+
max-width: 568px;
26+
27+
.header {
28+
.loading-webnode {
29+
font-size: 20px;
30+
line-height: 30px;
31+
}
2632
}
27-
}
2833

29-
mina-loading-spinner {
30-
margin: 0 2px;
31-
}
34+
mina-loading-spinner {
35+
margin: 0 2px;
36+
}
3237

33-
.mina-icon.circle-check {
34-
font-variation-settings: 'FILL' 1, 'wght' 300 !important;
35-
}
38+
.mina-icon.circle-check {
39+
font-variation-settings: 'FILL' 1, 'wght' 300 !important;
40+
}
3641

37-
.mina-icon.aware-primary {
38-
animation: fadeIn 1500ms ease-in-out infinite;
39-
}
42+
.mina-icon.aware-primary {
43+
animation: fadeIn 1500ms ease-in-out infinite;
44+
}
4045

41-
.progress {
42-
min-height: 380px;
43-
@media (max-width: 768px) {
44-
min-height: 36vh;
46+
.progress {
47+
min-height: 256px;
48+
@media (max-width: 768px) {
49+
min-height: 30vh;
50+
}
4551
}
4652
}
4753
}
@@ -54,6 +60,7 @@ $white: #000000;
5460
width: 158px;
5561
height: 48px !important;
5662
background-color: $cta-container;
63+
color: $base-background;
5764

5865
&.disabled {
5966
opacity: 0.25;
@@ -64,6 +71,15 @@ $white: #000000;
6471
background-color: $selected-primary;
6572
}
6673
}
74+
75+
@media (max-width: 768px) {
76+
> div {
77+
display: none;
78+
}
79+
button {
80+
width: 100%;
81+
}
82+
}
6783
}
6884

6985
@keyframes fadeIn {
@@ -82,9 +98,6 @@ $white: #000000;
8298
}
8399

84100
@media (max-width: 568px) {
85-
.font-16 {
86-
font-size: 14px;
87-
}
88101
.loading-webnode span {
89102
display: block;
90103
}

0 commit comments

Comments
 (0)