@oxyhq/core 3.4.18 → 3.5.0

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.
@@ -100,6 +100,7 @@ export class HttpService {
100
100
  this.tokenRefreshPromise = null;
101
101
  this.tokenRefreshCooldownUntil = 0;
102
102
  this.authRefreshHandler = null;
103
+ this.accessTokenProvider = null;
103
104
  /**
104
105
  * Fan-out listeners notified on EVERY access-token change on this instance:
105
106
  * explicit `setTokens`, `clearTokens`, an AuthManager-owned refresh, and the
@@ -130,6 +131,24 @@ export class HttpService {
130
131
  this.deduplicator = new RequestDeduplicator();
131
132
  this.requestQueue = new RequestQueue(config.maxConcurrentRequests || 10, config.requestQueueSize || 100);
132
133
  }
134
+ syncAccessTokenFromProvider() {
135
+ if (!this.accessTokenProvider) {
136
+ return this.tokenStore.getAccessToken();
137
+ }
138
+ const providedToken = this.accessTokenProvider();
139
+ const currentToken = this.tokenStore.getAccessToken();
140
+ if (providedToken) {
141
+ if (providedToken !== currentToken) {
142
+ this.tokenStore.setTokens(providedToken);
143
+ this.notifyTokenChange();
144
+ }
145
+ return providedToken;
146
+ }
147
+ if (currentToken) {
148
+ this.clearTokens();
149
+ }
150
+ return null;
151
+ }
133
152
  /**
134
153
  * Robust FormData detection that works in browser, React Native, and
135
154
  * Node.js polyfill environments.
@@ -685,7 +704,7 @@ export class HttpService {
685
704
  * Get auth header with automatic token refresh
686
705
  */
687
706
  async getAuthHeader() {
688
- const accessToken = this.tokenStore.getAccessToken();
707
+ const accessToken = this.syncAccessTokenFromProvider();
689
708
  if (!accessToken) {
690
709
  return null;
691
710
  }
@@ -803,6 +822,9 @@ export class HttpService {
803
822
  setAuthRefreshHandler(handler) {
804
823
  this.authRefreshHandler = handler;
805
824
  }
825
+ setAccessTokenProvider(provider) {
826
+ this.accessTokenProvider = provider;
827
+ }
806
828
  clearTokens() {
807
829
  this.tokenStore.clearTokens();
808
830
  this.tokenStore.clearCsrfToken();
@@ -110,12 +110,10 @@ export class OxyServicesBase {
110
110
  };
111
111
  syncToken(this.getAccessToken());
112
112
  const unsubscribe = this.onTokensChanged(syncToken);
113
+ client.setAccessTokenProvider(() => this.getAccessToken());
113
114
  client.setAuthRefreshHandler(async (reason) => {
114
115
  const refreshed = await this.httpService.refreshAccessToken(reason);
115
116
  if (!refreshed) {
116
- if (reason === 'response-401') {
117
- this.clearTokens();
118
- }
119
117
  return null;
120
118
  }
121
119
  syncToken(refreshed);
@@ -126,6 +124,7 @@ export class OxyServicesBase {
126
124
  dispose: () => {
127
125
  unsubscribe();
128
126
  client.setAuthRefreshHandler(null);
127
+ client.setAccessTokenProvider(null);
129
128
  client.clearTokens();
130
129
  },
131
130
  };
@@ -328,6 +328,25 @@ export function OxyServicesUserMixin(Base) {
328
328
  throw this.handleError(error);
329
329
  }
330
330
  }
331
+ /**
332
+ * Follow multiple users in a single request.
333
+ *
334
+ * POSTs `/users/follow/bulk` with `{ userIds }` (server caps the batch at
335
+ * 200). Returns the per-user outcomes and the count of users newly
336
+ * followed. An empty `userIds` array resolves immediately with an empty
337
+ * result and performs no network call.
338
+ */
339
+ async followUsers(userIds) {
340
+ if (userIds.length === 0) {
341
+ return { results: [], followedCount: 0 };
342
+ }
343
+ try {
344
+ return await this.makeRequest('POST', '/users/follow/bulk', { userIds }, { cache: false });
345
+ }
346
+ catch (error) {
347
+ throw this.handleError(error);
348
+ }
349
+ }
331
350
  /**
332
351
  * Unfollow a user
333
352
  */