@techextensor/tab-sdk 0.0.58 → 0.0.60

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.
@@ -1,6 +1,6 @@
1
1
  import * as i0 from '@angular/core';
2
2
  import { inject, Injectable } from '@angular/core';
3
- import { NotificationService, ConfirmationService, NotificationType, AuthService, TabFormioService, TemplateHelper, TabBlueprintService, AppHelper, MediaUploadHelper, ApiService, API, TabReleaseService, TranslationService, TabCrudService, TabGetService, LocalStorageService, SessionStorageService, StorageConstants, TabWorkflowService, MetadataHelper } from '@techextensor/tab-core-utility';
3
+ import { NotificationService, ConfirmationService, NotificationType, AuthService, TabFormioService, TemplateHelper, TabBlueprintService, AppHelper, MediaUploadHelper, ApiService, API, TabReleaseService, TranslationService, TabCrudService, TabGetService, LocalStorageService, SessionStorageService, StorageConstants, TabWorkflowService, SignalRService, NotificationInboxService, MetadataHelper } from '@techextensor/tab-core-utility';
4
4
  import { firstValueFrom } from 'rxjs';
5
5
 
6
6
  var ScreenDisplayMode;
@@ -2829,6 +2829,189 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.16", ngImpo
2829
2829
  }]
2830
2830
  }] });
2831
2831
 
2832
+ /**
2833
+ * SDK facade over the core SignalR service.
2834
+ *
2835
+ * Exposes only the surface that app/extension code needs:
2836
+ * - lifecycle (connect / disconnect)
2837
+ * - per-component subscription (register / unregister) for live CRUD push
2838
+ *
2839
+ * Async correlation-id tracking (`waitForOperation`) is intentionally NOT exposed —
2840
+ * that's an internal concern of the core CRUD services in tab-core-utility.
2841
+ *
2842
+ * @example
2843
+ * ```ts
2844
+ * // In a route resolver (route waits until the first connection attempt settles)
2845
+ * await TabSdk.signalR.connect();
2846
+ *
2847
+ * // In a component
2848
+ * ngOnInit() {
2849
+ * TabSdk.signalR.register(this.componentId, this.appObjectId, n => this.handle(n));
2850
+ * }
2851
+ * ngOnDestroy() {
2852
+ * TabSdk.signalR.unregister(this.componentId, this.appObjectId);
2853
+ * }
2854
+ *
2855
+ * // In auth signOut
2856
+ * await TabSdk.signalR.disconnect();
2857
+ * ```
2858
+ */
2859
+ class SignalRSdkService {
2860
+ signalR = inject(SignalRService);
2861
+ /**
2862
+ * Establish a connection to the SignalR hub.
2863
+ *
2864
+ * Awaitable — resolves when the first connection attempt settles (success or
2865
+ * failure). Idempotent: repeated calls are de-duplicated; if already
2866
+ * CONNECTED, resolves immediately. Any stale (non-Connected) connection is
2867
+ * torn down before rebuild.
2868
+ *
2869
+ * Use in route resolvers to gate navigation until the hub is ready.
2870
+ */
2871
+ async connect() {
2872
+ await this.signalR.connect();
2873
+ }
2874
+ /**
2875
+ * Tear down the connection (call from auth signOut / cross-tab logout).
2876
+ *
2877
+ * Stops the hub, clears component registrations, and errors any in-flight
2878
+ * waitForOperation observers so CRUD UIs resolve immediately instead of
2879
+ * stranding until the 120s timeout.
2880
+ */
2881
+ async disconnect() {
2882
+ await this.signalR.disconnect();
2883
+ }
2884
+ /**
2885
+ * Subscribe a component to real-time CRUD notifications for an AppObject.
2886
+ * Refcounted — the first registrant for an `appObjectId` joins the hub group;
2887
+ * the last `unregister` leaves it.
2888
+ */
2889
+ register(componentId, appObjectId, callback) {
2890
+ this.signalR.register(componentId, appObjectId, callback);
2891
+ }
2892
+ /**
2893
+ * Unsubscribe a component (call from `ngOnDestroy`).
2894
+ */
2895
+ unregister(componentId, appObjectId) {
2896
+ this.signalR.unregister(componentId, appObjectId);
2897
+ }
2898
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.16", ngImport: i0, type: SignalRSdkService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
2899
+ static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "19.2.16", ngImport: i0, type: SignalRSdkService, providedIn: 'root' });
2900
+ }
2901
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.16", ngImport: i0, type: SignalRSdkService, decorators: [{
2902
+ type: Injectable,
2903
+ args: [{ providedIn: 'root' }]
2904
+ }] });
2905
+
2906
+ /**
2907
+ * SDK facade over the core notification inbox service.
2908
+ *
2909
+ * The app passes the auth identifiers at connect time — the core services don't
2910
+ * read them from storage. This facade is the single place that knows how to
2911
+ * compose the BE's `workspaceKey` from the four IDs.
2912
+ *
2913
+ * Exposes only the surface that app/extension code needs:
2914
+ * - lifecycle (connect / disconnect)
2915
+ * - inbox actions (loadMore, markAsRead, markAllAsRead, clearOne, clearAll)
2916
+ * - state streams for UI (latestNotifications$, unreadCount$, etc.)
2917
+ *
2918
+ * @example
2919
+ * ```ts
2920
+ * // In a route resolver
2921
+ * await TabSdk.notification.connect({
2922
+ * userId: TabSdk.store.userId,
2923
+ * appId: TabSdk.store.appId,
2924
+ * tenantId: TabSdk.store.tenantId,
2925
+ * environmentId: TabSdk.store.environmentId,
2926
+ * });
2927
+ *
2928
+ * // In header for the badge
2929
+ * TabSdk.notification.unreadCount$.subscribe(count => this.badge = count);
2930
+ *
2931
+ * // In notification list
2932
+ * TabSdk.notification.loadMore(1);
2933
+ * TabSdk.notification.markAsRead(id);
2934
+ *
2935
+ * // In auth signOut
2936
+ * await TabSdk.notification.disconnect();
2937
+ * ```
2938
+ */
2939
+ class NotificationSdkService {
2940
+ inbox = inject(NotificationInboxService);
2941
+ // ----------- lifecycle -----------
2942
+ /**
2943
+ * Connect to the notification WebSocket. Awaitable, idempotent.
2944
+ *
2945
+ * The app supplies the auth identifiers — the core services stay pure
2946
+ * (no storage / auth coupling). This facade composes the BE's workspaceKey
2947
+ * from the four IDs and passes everything down.
2948
+ */
2949
+ async connect(params) {
2950
+ const workspaceKey = `${params.tenantId}.${params.appId}.${params.environmentId}`;
2951
+ await this.inbox.connect({
2952
+ userId: params.userId,
2953
+ appId: params.appId,
2954
+ tenantId: params.tenantId,
2955
+ workspaceKey,
2956
+ });
2957
+ }
2958
+ /**
2959
+ * Tear down the connection (call from auth signOut / cross-tab logout).
2960
+ */
2961
+ async disconnect() {
2962
+ await this.inbox.disconnect();
2963
+ }
2964
+ // ----------- actions -----------
2965
+ /** Fetch a page of notifications from the inbox. */
2966
+ loadMore(pageNumber, pageSize) {
2967
+ this.inbox.loadMore(pageNumber, pageSize);
2968
+ }
2969
+ /** Re-request unread count (header badge auto-refreshes via the stream). */
2970
+ requestUnreadCount() {
2971
+ this.inbox.requestUnreadCount();
2972
+ }
2973
+ /** Mark a single notification as read. */
2974
+ markAsRead(notificationId) {
2975
+ this.inbox.markAsRead(notificationId);
2976
+ }
2977
+ /** Mark all notifications as read. */
2978
+ markAllAsRead() {
2979
+ this.inbox.markAllAsRead();
2980
+ }
2981
+ /** Clear a single notification from the inbox. */
2982
+ clearOne(notificationId) {
2983
+ this.inbox.clearOne(notificationId);
2984
+ }
2985
+ /** Clear all notifications from the inbox. */
2986
+ clearAll() {
2987
+ this.inbox.clearAll();
2988
+ }
2989
+ // ----------- streams -----------
2990
+ /**
2991
+ * Emits notifications as they arrive.
2992
+ * - Inbox page fetch → emits an array.
2993
+ * - Live push → emits a single notification (component should prepend it).
2994
+ * Component logic should branch on Array.isArray(value).
2995
+ */
2996
+ latestNotifications$ = this.inbox.getLatestNotifications();
2997
+ /** Current unread count. Header subscribes for the badge. */
2998
+ unreadCount$ = this.inbox.getUnreadCount();
2999
+ /** Emits notificationId when a notification is marked read; null when all are. */
3000
+ markAsReadEvents$ = this.inbox.getMarkAsReadEvents();
3001
+ /** Emits cleared notification IDs; null when all are cleared. */
3002
+ clearEvents$ = this.inbox.getClearEvents();
3003
+ /** Loading state — true while a page fetch is in flight. */
3004
+ loading$ = this.inbox.getLoadingState();
3005
+ /** Total pages (page-based pagination per BE). */
3006
+ totalPages$ = this.inbox.getTotalPages();
3007
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.16", ngImport: i0, type: NotificationSdkService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
3008
+ static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "19.2.16", ngImport: i0, type: NotificationSdkService, providedIn: 'root' });
3009
+ }
3010
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.16", ngImport: i0, type: NotificationSdkService, decorators: [{
3011
+ type: Injectable,
3012
+ args: [{ providedIn: 'root' }]
3013
+ }] });
3014
+
2832
3015
  class TabSdk {
2833
3016
  static app;
2834
3017
  static auth;
@@ -2847,6 +3030,8 @@ class TabSdk {
2847
3030
  static workflow;
2848
3031
  static util;
2849
3032
  static state;
3033
+ static signalR;
3034
+ static notification;
2850
3035
  /**
2851
3036
  * Initialize the SDK with necessary services
2852
3037
  */
@@ -2869,6 +3054,8 @@ class TabSdk {
2869
3054
  this.http = injector.get(HttpService);
2870
3055
  this.store = injector.get(StoreService);
2871
3056
  this.workflow = injector.get(WorkflowService);
3057
+ this.signalR = injector.get(SignalRSdkService);
3058
+ this.notification = injector.get(NotificationSdkService);
2872
3059
  // Extract StateService from context before passing to util
2873
3060
  const { StateService: stateService, ...utilContext } = context || {};
2874
3061
  // Initialize util service with context (excluding StateService)
@@ -2895,6 +3082,8 @@ class TabSdk {
2895
3082
  Object.freeze(this.store);
2896
3083
  Object.freeze(this.util);
2897
3084
  Object.freeze(this.state);
3085
+ Object.freeze(this.signalR);
3086
+ Object.freeze(this.notification);
2898
3087
  }
2899
3088
  static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.16", ngImport: i0, type: TabSdk, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
2900
3089
  static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "19.2.16", ngImport: i0, type: TabSdk, providedIn: 'root' });