@chisquare-tech/origine-ngx-apps-services 0.2.0 → 0.2.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -281,6 +281,12 @@ const DAYS = [
281
281
  { id: 'sun', label: 'Sunday' }, { id: 'mon', label: 'Monday' }, { id: 'tue', label: 'Tuesday' }, { id: 'wed', label: 'Wednesday' },
282
282
  { id: 'thu', label: 'Thursday' }, { id: 'fri', label: 'Friday' }, { id: 'sat', label: 'Saturday' },
283
283
  ];
284
+ /** While the browser tab is hidden, the page's polls slow to once a minute (the cell is read for each). */
285
+ const HIDDEN_POLL_MS = 60_000;
286
+ /** The delay before the next poll: `visibleMs` while the page is seen, once a minute while it is hidden. */
287
+ function pollDelay(visibleMs) {
288
+ return typeof document !== 'undefined' && document.visibilityState === 'hidden' ? Math.max(visibleMs, HIDDEN_POLL_MS) : visibleMs;
289
+ }
284
290
 
285
291
  // /{org}/{project}/services (prototype "services_list"): the project's instances with their state,
286
292
  // what they are attached to, their backups and price, and the organization's quota line (SVC-01, 26).
@@ -959,7 +965,7 @@ class ServiceConsoleTab {
959
965
  <span class="o-r"></span>
960
966
  @if (d().canManage) {<label class="o-flex o-sm" style="gap:6px"><input type="checkbox" [ngModel]="write()" (ngModelChange)="write.set($event)" data-testid="svc-console-write" /> Allow writes</label>}
961
967
  @if (d().databases.length) {
962
- <select class="o-in o-sm" style="width:auto" aria-label="Database" [ngModel]="db()" (ngModelChange)="db.set($event)" data-testid="svc-console-db">
968
+ <select class="o-in o-sm" style="width:auto" aria-label="Database" [ngModel]="db() || d().databases[0]?.name" (ngModelChange)="db.set($event)" data-testid="svc-console-db">
963
969
  @for (x of d().databases; track x.name) {<option [value]="x.name">{{ x.name }}</option>}
964
970
  </select>
965
971
  }
@@ -1022,7 +1028,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.12", ngImpo
1022
1028
  <span class="o-r"></span>
1023
1029
  @if (d().canManage) {<label class="o-flex o-sm" style="gap:6px"><input type="checkbox" [ngModel]="write()" (ngModelChange)="write.set($event)" data-testid="svc-console-write" /> Allow writes</label>}
1024
1030
  @if (d().databases.length) {
1025
- <select class="o-in o-sm" style="width:auto" aria-label="Database" [ngModel]="db()" (ngModelChange)="db.set($event)" data-testid="svc-console-db">
1031
+ <select class="o-in o-sm" style="width:auto" aria-label="Database" [ngModel]="db() || d().databases[0]?.name" (ngModelChange)="db.set($event)" data-testid="svc-console-db">
1026
1032
  @for (x of d().databases; track x.name) {<option [value]="x.name">{{ x.name }}</option>}
1027
1033
  </select>
1028
1034
  }
@@ -1149,7 +1155,7 @@ class ServiceDumpsCard {
1149
1155
  this.go(this.api.deleteDump(this.projectKey(), this.d().id, x.id), () => this.done.emit('Dump deleted.'), 'The dump could not be deleted.');
1150
1156
  }
1151
1157
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.12", ngImport: i0, type: ServiceDumpsCard, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
1152
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.12", type: ServiceDumpsCard, isStandalone: true, selector: "o-svc-dumps", inputs: { d: { classPropertyName: "d", publicName: "d", isSignal: true, isRequired: true, transformFunction: null }, projectKey: { classPropertyName: "projectKey", publicName: "projectKey", isSignal: true, isRequired: true, transformFunction: null }, dumps: { classPropertyName: "dumps", publicName: "dumps", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { done: "done", failed: "failed" }, ngImport: i0, template: `
1158
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.12", type: ServiceDumpsCard, isStandalone: true, selector: "o-svc-dumps", inputs: { d: { classPropertyName: "d", publicName: "d", isSignal: true, isRequired: true, transformFunction: null }, projectKey: { classPropertyName: "projectKey", publicName: "projectKey", isSignal: true, isRequired: true, transformFunction: null }, dumps: { classPropertyName: "dumps", publicName: "dumps", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { done: "done", failed: "failed" }, host: { styleAttribute: "display:flex;flex-direction:column;gap:14px" }, ngImport: i0, template: `
1153
1159
  <div class="o-card o-cb o-col" style="gap:8px" data-testid="svc-fork-card">
1154
1160
  <b>Fork for staging</b>
1155
1161
  <span class="o-hint">Copy from the latest backup into a new instance. {{ d().name }} keeps running untouched.</span>
@@ -1200,6 +1206,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.12", ngImpo
1200
1206
  selector: 'o-svc-dumps',
1201
1207
  imports: [FormsModule],
1202
1208
  changeDetection: ChangeDetectionStrategy.OnPush,
1209
+ host: { style: 'display:flex;flex-direction:column;gap:14px' },
1203
1210
  template: `
1204
1211
  <div class="o-card o-cb o-col" style="gap:8px" data-testid="svc-fork-card">
1205
1212
  <b>Fork for staging</b>
@@ -1287,7 +1294,7 @@ class ServiceLogsTab {
1287
1294
  this.lines.set(l.lines ?? []);
1288
1295
  this.note.set(l.message ?? '');
1289
1296
  this.loaded.set(true);
1290
- this.timer = setTimeout(() => this.load(p, id, k), 10_000);
1297
+ this.timer = setTimeout(() => this.load(p, id, k), pollDelay(10_000));
1291
1298
  },
1292
1299
  error: (e) => {
1293
1300
  this.loaded.set(true);
@@ -1687,7 +1694,19 @@ class ServicePage {
1687
1694
  this.api.logs(this.key(), d, 'slow', 20).pipe(catchError(() => of(null))).subscribe((l) => this.slowLines.set(l?.lines ?? []));
1688
1695
  });
1689
1696
  });
1697
+ // Hidden, the polls slow to once a minute; seen again, the figures are read at once.
1698
+ const seen = () => {
1699
+ if (document.visibilityState !== 'visible' || !this.d())
1700
+ return;
1701
+ this.load();
1702
+ if (this.tab() !== 'overview' && this.tab() !== 'metrics')
1703
+ return;
1704
+ clearTimeout(this.metricsTimer);
1705
+ this.pollMetrics();
1706
+ };
1707
+ document.addEventListener('visibilitychange', seen);
1690
1708
  inject(DestroyRef).onDestroy(() => {
1709
+ document.removeEventListener('visibilitychange', seen);
1691
1710
  params.unsubscribe();
1692
1711
  query.unsubscribe();
1693
1712
  clearTimeout(this.loadTimer);
@@ -1727,8 +1746,8 @@ class ServicePage {
1727
1746
  if (d.window?.from && !this.pitr())
1728
1747
  this.pitr.set(toLocalInput(new Date().toISOString()));
1729
1748
  }
1730
- const settling = moving(d.state) || !!this.openRotation() || d.attachments.some((a) => a.state === 'pending') || (d.backups ?? []).some((b) => b.phase === 'running' || b.phase === 'pending');
1731
- this.loadTimer = setTimeout(() => this.load(), settling ? 4000 : 30_000);
1749
+ const settling = moving(d.state) || d.readyNodes < d.nodes || (d.dumps ?? []).some((x) => x.phase !== 'completed' && x.phase !== 'failed') || !!this.openRotation() || d.attachments.some((a) => a.state === 'pending') || (d.backups ?? []).some((b) => b.phase === 'running' || b.phase === 'pending');
1750
+ this.loadTimer = setTimeout(() => this.load(), pollDelay(settling ? 4000 : 30_000));
1732
1751
  },
1733
1752
  error: (e) => {
1734
1753
  this.error.set(e?.status === 404 ? 'No such service in this project.' : apiMessage(e, 'The service could not be loaded.'));
@@ -1742,9 +1761,9 @@ class ServicePage {
1742
1761
  this.api.metrics(this.key(), d.id).subscribe({
1743
1762
  next: (m) => {
1744
1763
  this.readings.update((rs) => [...rs, m].slice(-90));
1745
- this.metricsTimer = setTimeout(() => this.pollMetrics(), 10_000);
1764
+ this.metricsTimer = setTimeout(() => this.pollMetrics(), pollDelay(10_000));
1746
1765
  },
1747
- error: () => (this.metricsTimer = setTimeout(() => this.pollMetrics(), 30_000)),
1766
+ error: () => (this.metricsTimer = setTimeout(() => this.pollMetrics(), pollDelay(30_000))),
1748
1767
  });
1749
1768
  }
1750
1769
  setTab(t) {
@@ -2658,5 +2677,5 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.12", ngImpo
2658
2677
  * Generated bundle index. Do not edit.
2659
2678
  */
2660
2679
 
2661
- export { DAYS, ENGINE_COLOUR, LIFECYCLE, PRESETS, ServiceConsoleTab, ServiceDumpsCard, ServiceLogsTab, ServiceMetricsTab, ServicePage, ServicesApi, ServicesHost, ServicesListPage, ServicesNewPage, apiMessage, backupKind, backupsLine, bytes, fromLocalInput, hhmm, hhmmss, money, moving, num, pct, presetChip, ratio, shortDate, spark, sparkPath, stateChip, stateDot, toLocalInput, utcHour, when };
2680
+ export { DAYS, ENGINE_COLOUR, HIDDEN_POLL_MS, LIFECYCLE, PRESETS, ServiceConsoleTab, ServiceDumpsCard, ServiceLogsTab, ServiceMetricsTab, ServicePage, ServicesApi, ServicesHost, ServicesListPage, ServicesNewPage, apiMessage, backupKind, backupsLine, bytes, fromLocalInput, hhmm, hhmmss, money, moving, num, pct, pollDelay, presetChip, ratio, shortDate, spark, sparkPath, stateChip, stateDot, toLocalInput, utcHour, when };
2662
2681
  //# sourceMappingURL=chisquare-tech-origine-ngx-apps-services.mjs.map