feeef 0.8.5 → 0.8.10
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.
- package/README.md +8 -0
- package/build/index.js +142 -0
- package/build/index.js.map +1 -1
- package/build/src/core/entities/store.d.ts +2 -0
- package/build/src/core/entities/user.d.ts +9 -4
- package/build/src/feeef/repositories/apps.d.ts +40 -1
- package/build/src/feeef/repositories/users.d.ts +19 -1
- package/build/src/index.d.ts +1 -0
- package/build/src/realtime/crud_event.d.ts +9 -0
- package/build/src/realtime/index.d.ts +2 -0
- package/build/src/realtime/transmit.d.ts +59 -0
- package/package.json +2 -1
package/README.md
CHANGED
|
@@ -2,6 +2,14 @@
|
|
|
2
2
|
|
|
3
3
|
`feeefjs` is a TypeScript library for managing feeef e-commerce platforms for self-hosted stores. It provides a wrapper for feeef rest api such like send order..., also have frontend srvices like the `CartService` class for managing cart items, shipping methods, and calculating totals. The library also includes a `NotifiableService` base class for handling listeners that react to changes in the service state.
|
|
4
4
|
|
|
5
|
+
## Developer OAuth (third-party apps)
|
|
6
|
+
|
|
7
|
+
Use `OAuthRepository.buildAuthorizeUrl` (point `baseUrl` at the **accounts** host, e.g. `https://accounts.feeef.org`) and `FeeeF` client `oauth.exchangeAuthorizationCode` / `revokeToken` / `introspectToken` against the **API** base (`.../v1`). Full flow, scopes, and troubleshooting: Feeef backend **`docs/OAUTH2_DEVELOPER.md`** (in the Adonis API repo).
|
|
8
|
+
|
|
9
|
+
## Realtime (AdonisJS Transmit)
|
|
10
|
+
|
|
11
|
+
Server-Sent Events use the same **API origin** as the REST client, but **without** the `/v1` or `/api/v1` prefix (e.g. `https://api.feeef.org/__transmit/events`). Use `createFeeefTransmit({ apiBaseUrl, getAccessToken })` so subscribe/unsubscribe POSTs get a proper `Authorization: Bearer …` header. The underlying client is the official [`@adonisjs/transmit-client`](https://www.npmjs.com/package/@adonisjs/transmit-client) (`Transmit`, `Subscription` are re-exported).
|
|
12
|
+
|
|
5
13
|
---
|
|
6
14
|
|
|
7
15
|
# CartService & NotifiableService
|
package/build/index.js
CHANGED
|
@@ -661,6 +661,27 @@ var UserRepository = class extends ModelRepository {
|
|
|
661
661
|
const res = await this.client.get(`/${this.resource}/auth/tokens`);
|
|
662
662
|
return res.data;
|
|
663
663
|
}
|
|
664
|
+
/**
|
|
665
|
+
* Revokes an access token (session) by opaque identifier from {@link tokens}.
|
|
666
|
+
*/
|
|
667
|
+
async revokeAccessToken(identifier) {
|
|
668
|
+
if (!identifier || identifier === "undefined") {
|
|
669
|
+
throw new Error("Missing access token identifier");
|
|
670
|
+
}
|
|
671
|
+
await this.client.delete(`/${this.resource}/auth/tokens/${encodeURIComponent(identifier)}`);
|
|
672
|
+
}
|
|
673
|
+
/** Revokes every access token for the current user (sign out everywhere). */
|
|
674
|
+
async revokeAllAccessTokens() {
|
|
675
|
+
const res = await this.client.post(`/${this.resource}/auth/tokens/revoke-all`);
|
|
676
|
+
return res.data;
|
|
677
|
+
}
|
|
678
|
+
/**
|
|
679
|
+
* Lists OAuth apps that have per-user stored data for the current user (`app_user` rows).
|
|
680
|
+
*/
|
|
681
|
+
async connectedApps() {
|
|
682
|
+
const res = await this.client.get(`/${this.resource}/auth/connected-apps`);
|
|
683
|
+
return res.data;
|
|
684
|
+
}
|
|
664
685
|
/**
|
|
665
686
|
* Signs in with Google OAuth.
|
|
666
687
|
* @param options - The OAuth code and optional FCM token.
|
|
@@ -848,6 +869,9 @@ var AppRepository = class extends ModelRepository {
|
|
|
848
869
|
* Builds the OAuth authorize URL to which the user should be redirected.
|
|
849
870
|
* This is the first step of the authorization-code flow (similar UX to Google OAuth).
|
|
850
871
|
*
|
|
872
|
+
* Production: opening this URL on the **API** host (`api.*`) issues a redirect to the same path on
|
|
873
|
+
* **accounts.*** so the consent screen appears on the trusted accounts domain; query params are preserved.
|
|
874
|
+
*
|
|
851
875
|
* If the user is not logged in yet, API `GET /oauth/authorize` returns:
|
|
852
876
|
* - `401 login_required`
|
|
853
877
|
* - `login_url` (accounts sign-in URL with `next=...`)
|
|
@@ -880,6 +904,47 @@ var AppRepository = class extends ModelRepository {
|
|
|
880
904
|
}
|
|
881
905
|
return url.toString();
|
|
882
906
|
}
|
|
907
|
+
/**
|
|
908
|
+
* Public `apps.public_data` (no auth). Pass [config] to skip Authorization if your axios instance adds it globally.
|
|
909
|
+
*/
|
|
910
|
+
async getPublicData(id, config) {
|
|
911
|
+
const res = await this.client.get(`/${this.resource}/${id}/public-data`, config);
|
|
912
|
+
return res.data;
|
|
913
|
+
}
|
|
914
|
+
async getPrivateData(id) {
|
|
915
|
+
const res = await this.client.get(`/${this.resource}/${id}/private-data`);
|
|
916
|
+
return res.data;
|
|
917
|
+
}
|
|
918
|
+
async putPublicData(id, publicNamespaces) {
|
|
919
|
+
const res = await this.client.put(`/${this.resource}/${id}/public-data`, {
|
|
920
|
+
public: publicNamespaces
|
|
921
|
+
});
|
|
922
|
+
return res.data;
|
|
923
|
+
}
|
|
924
|
+
async putPrivateData(id, privateNamespaces) {
|
|
925
|
+
const res = await this.client.put(`/${this.resource}/${id}/private-data`, {
|
|
926
|
+
private: privateNamespaces
|
|
927
|
+
});
|
|
928
|
+
return res.data;
|
|
929
|
+
}
|
|
930
|
+
async getUserDataMe(id) {
|
|
931
|
+
const res = await this.client.get(`/${this.resource}/${id}/user-data/me`);
|
|
932
|
+
return res.data;
|
|
933
|
+
}
|
|
934
|
+
async putUserDataMe(id, publicNamespaces) {
|
|
935
|
+
const res = await this.client.put(`/${this.resource}/${id}/user-data/me`, {
|
|
936
|
+
public: publicNamespaces
|
|
937
|
+
});
|
|
938
|
+
return res.data;
|
|
939
|
+
}
|
|
940
|
+
async getUserDataForUser(appId, userId) {
|
|
941
|
+
const res = await this.client.get(`/${this.resource}/${appId}/user-data/users/${userId}`);
|
|
942
|
+
return res.data;
|
|
943
|
+
}
|
|
944
|
+
async putUserDataForUser(appId, userId, body) {
|
|
945
|
+
const res = await this.client.put(`/${this.resource}/${appId}/user-data/users/${userId}`, body);
|
|
946
|
+
return res.data;
|
|
947
|
+
}
|
|
883
948
|
};
|
|
884
949
|
|
|
885
950
|
// src/feeef/repositories/oauth.ts
|
|
@@ -4056,6 +4121,77 @@ var EmbaddedContactType = /* @__PURE__ */ ((EmbaddedContactType2) => {
|
|
|
4056
4121
|
return EmbaddedContactType2;
|
|
4057
4122
|
})(EmbaddedContactType || {});
|
|
4058
4123
|
|
|
4124
|
+
// src/realtime/transmit.ts
|
|
4125
|
+
import { Transmit } from "@adonisjs/transmit-client";
|
|
4126
|
+
import { Subscription, Transmit as Transmit2 } from "@adonisjs/transmit-client";
|
|
4127
|
+
function transmitRootFromApiBaseUrl(apiBaseUrl) {
|
|
4128
|
+
let u = apiBaseUrl.trim().replace(/\/+$/, "");
|
|
4129
|
+
if (u.endsWith("/api/v1")) {
|
|
4130
|
+
u = u.slice(0, -"/api/v1".length);
|
|
4131
|
+
} else if (u.endsWith("/v1")) {
|
|
4132
|
+
u = u.slice(0, -"/v1".length);
|
|
4133
|
+
}
|
|
4134
|
+
return u;
|
|
4135
|
+
}
|
|
4136
|
+
function retrieveXsrfTokenFromCookie() {
|
|
4137
|
+
const cookie = globalThis.document?.cookie;
|
|
4138
|
+
if (!cookie) return null;
|
|
4139
|
+
const match = cookie.match(new RegExp("(^|;\\s*)(XSRF-TOKEN)=([^;]*)"));
|
|
4140
|
+
return match ? decodeURIComponent(match[3]) : null;
|
|
4141
|
+
}
|
|
4142
|
+
var FeeefTransmitHttpClient = class {
|
|
4143
|
+
constructor(options, getAuthorizationHeader) {
|
|
4144
|
+
this.options = options;
|
|
4145
|
+
this.getAuthorizationHeader = getAuthorizationHeader;
|
|
4146
|
+
}
|
|
4147
|
+
send(request) {
|
|
4148
|
+
return fetch(request);
|
|
4149
|
+
}
|
|
4150
|
+
createRequest(path, body) {
|
|
4151
|
+
const headers = {
|
|
4152
|
+
"Content-Type": "application/json",
|
|
4153
|
+
"X-XSRF-TOKEN": retrieveXsrfTokenFromCookie() ?? ""
|
|
4154
|
+
};
|
|
4155
|
+
const auth = this.getAuthorizationHeader();
|
|
4156
|
+
if (auth) {
|
|
4157
|
+
headers.Authorization = auth.startsWith("Bearer ") ? auth : `Bearer ${auth}`;
|
|
4158
|
+
}
|
|
4159
|
+
return new Request(`${this.options.baseUrl}${path}`, {
|
|
4160
|
+
method: "POST",
|
|
4161
|
+
headers,
|
|
4162
|
+
body: JSON.stringify({ uid: this.options.uid, ...body }),
|
|
4163
|
+
credentials: "include"
|
|
4164
|
+
});
|
|
4165
|
+
}
|
|
4166
|
+
};
|
|
4167
|
+
function createFeeefTransmit(options) {
|
|
4168
|
+
const baseUrl = transmitRootFromApiBaseUrl(options.apiBaseUrl);
|
|
4169
|
+
const getToken = options.getAccessToken ?? (() => void 0);
|
|
4170
|
+
return new Transmit({
|
|
4171
|
+
...options.transmit,
|
|
4172
|
+
baseUrl,
|
|
4173
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any -- Transmit’s HttpClient is not exported; FeeefTransmitHttpClient matches its shape.
|
|
4174
|
+
httpClientFactory: (url, uid) => new FeeefTransmitHttpClient({ baseUrl: url, uid }, () => {
|
|
4175
|
+
const t = getToken();
|
|
4176
|
+
if (t === null || t === void 0 || t === "") return void 0;
|
|
4177
|
+
const s = String(t).trim();
|
|
4178
|
+
return s.startsWith("Bearer ") ? s : `Bearer ${s}`;
|
|
4179
|
+
})
|
|
4180
|
+
});
|
|
4181
|
+
}
|
|
4182
|
+
function createFeeefTransmitFromAxios(client, options) {
|
|
4183
|
+
const apiBaseUrl = client.defaults.baseURL ?? "";
|
|
4184
|
+
return createFeeefTransmit({
|
|
4185
|
+
...options,
|
|
4186
|
+
apiBaseUrl,
|
|
4187
|
+
getAccessToken: () => {
|
|
4188
|
+
const raw = client.defaults.headers.common?.Authorization;
|
|
4189
|
+
if (typeof raw !== "string") return void 0;
|
|
4190
|
+
return raw.replace(/^Bearer\s+/i, "").trim() || void 0;
|
|
4191
|
+
}
|
|
4192
|
+
});
|
|
4193
|
+
}
|
|
4194
|
+
|
|
4059
4195
|
// src/utils.ts
|
|
4060
4196
|
var convertDartColorToCssNumber = (dartColor) => {
|
|
4061
4197
|
const alpha = dartColor >> 24 & 255;
|
|
@@ -4158,6 +4294,7 @@ export {
|
|
|
4158
4294
|
FeedbackRepository,
|
|
4159
4295
|
FeedbackStatus,
|
|
4160
4296
|
FeeeF,
|
|
4297
|
+
FeeefTransmitHttpClient,
|
|
4161
4298
|
GoogleSheetIntegrationApi,
|
|
4162
4299
|
ImageGenerationsRepository,
|
|
4163
4300
|
ImagePromptTemplatesRepository,
|
|
@@ -4192,8 +4329,10 @@ export {
|
|
|
4192
4329
|
StoreRepository,
|
|
4193
4330
|
StoreSubscriptionStatus,
|
|
4194
4331
|
StoreSubscriptionType,
|
|
4332
|
+
Subscription,
|
|
4195
4333
|
TiktokPixelEvent,
|
|
4196
4334
|
TransferRepository,
|
|
4335
|
+
Transmit2 as Transmit,
|
|
4197
4336
|
UserRepository,
|
|
4198
4337
|
VariantOptionType,
|
|
4199
4338
|
WebhookEvent,
|
|
@@ -4202,6 +4341,8 @@ export {
|
|
|
4202
4341
|
ZimouDeliveryIntegrationApi,
|
|
4203
4342
|
convertDartColorToCssNumber,
|
|
4204
4343
|
convertOrderEntityToOrderTrackEntity,
|
|
4344
|
+
createFeeefTransmit,
|
|
4345
|
+
createFeeefTransmitFromAxios,
|
|
4205
4346
|
createImageGenerationFormData,
|
|
4206
4347
|
cssColorToHslString,
|
|
4207
4348
|
dartColorToCssColor,
|
|
@@ -4237,6 +4378,7 @@ export {
|
|
|
4237
4378
|
serializeAttachmentPayloads,
|
|
4238
4379
|
serializeImagePromptTemplateCreate,
|
|
4239
4380
|
serializeImagePromptTemplateUpdate,
|
|
4381
|
+
transmitRootFromApiBaseUrl,
|
|
4240
4382
|
tryFixPhoneNumber,
|
|
4241
4383
|
validatePhoneNumber
|
|
4242
4384
|
};
|