Skip to content

Commit e45798b

Browse files
authored
Merge pull request #43 from session-foundation/feat/pro-backend-request-response-wrappers
feat: add pro backend request response wrappers
2 parents 60f407b + 972c3e4 commit e45798b

File tree

4 files changed

+321
-3
lines changed

4 files changed

+321
-3
lines changed

include/pro/pro.hpp

Lines changed: 212 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,11 +8,19 @@
88
#include "../../node_modules/node-addon-api/napi.h"
99
#include "../meta/meta_base_wrapper.hpp"
1010
#include "../utilities.hpp"
11+
#include "./types.hpp"
1112
#include "meta/meta_base_wrapper.hpp"
13+
#include "session/pro_backend.h"
1214
#include "session/pro_backend.hpp"
15+
#include "session/session_protocol.h"
1316
#include "session/session_protocol.hpp"
1417

1518
namespace session::nodeapi {
19+
std::string_view ProBackendEnumToString(SESSION_PRO_BACKEND_PAYMENT_PROVIDER v);
20+
std::string_view ProBackendEnumToString(SESSION_PRO_BACKEND_PAYMENT_STATUS v);
21+
std::string_view ProBackendEnumToString(SESSION_PRO_BACKEND_PLAN v);
22+
std::string_view ProBackendEnumToString(SESSION_PRO_BACKEND_USER_PRO_STATUS v);
23+
std::string_view ProBackendEnumToString(SESSION_PRO_BACKEND_GET_PRO_STATUS_ERROR_REPORT v);
1624

1725
class ProWrapper : public Napi::ObjectWrap<ProWrapper> {
1826

@@ -36,6 +44,26 @@ class ProWrapper : public Napi::ObjectWrap<ProWrapper> {
3644
"proProofRequestBody",
3745
static_cast<napi_property_attributes>(
3846
napi_writable | napi_configurable)),
47+
StaticMethod<&ProWrapper::proProofResponseBody>(
48+
"proProofResponseBody",
49+
static_cast<napi_property_attributes>(
50+
napi_writable | napi_configurable)),
51+
StaticMethod<&ProWrapper::proRevocationsRequestBody>(
52+
"proRevocationsRequestBody",
53+
static_cast<napi_property_attributes>(
54+
napi_writable | napi_configurable)),
55+
StaticMethod<&ProWrapper::proRevocationsResponseBody>(
56+
"proRevocationsResponseBody",
57+
static_cast<napi_property_attributes>(
58+
napi_writable | napi_configurable)),
59+
StaticMethod<&ProWrapper::proStatusRequestBody>(
60+
"proStatusRequestBody",
61+
static_cast<napi_property_attributes>(
62+
napi_writable | napi_configurable)),
63+
StaticMethod<&ProWrapper::proStatusResponseBody>(
64+
"proStatusResponseBody",
65+
static_cast<napi_property_attributes>(
66+
napi_writable | napi_configurable)),
3967
});
4068
}
4169

@@ -99,7 +127,7 @@ class ProWrapper : public Napi::ObjectWrap<ProWrapper> {
99127
return wrapResult(info, [&] {
100128
// we expect arguments that match:
101129
// first: {
102-
// "requestVersion": string,
130+
// "requestVersion": number,
103131
// "masterPrivkey": Uint8Array,
104132
// "rotatingPrivkey": Uint8Array,
105133
// "unixTsMs": number,
@@ -141,6 +169,189 @@ class ProWrapper : public Napi::ObjectWrap<ProWrapper> {
141169
return json;
142170
});
143171
};
172+
173+
static Napi::Value proProofResponseBody(const Napi::CallbackInfo& info) {
174+
return wrapResult(info, [&] {
175+
// we expect arguments that match:
176+
// first: {
177+
// "json": string,
178+
// }
179+
180+
assertInfoLength(info, 1);
181+
assertIsObject(info[0]);
182+
auto env = info.Env();
183+
184+
auto first = info[0].As<Napi::Object>();
185+
186+
if (first.IsEmpty())
187+
throw std::invalid_argument("proProofResponseBody first received empty");
188+
189+
assertIsString(first.Get("json"), "proProofResponseBody.jsonStr");
190+
auto json_str = toCppString(first.Get("json"), "proProofResponseBody.jsonStr");
191+
auto json = pro_backend::AddProPaymentOrGetProProofResponse::parse(json_str);
192+
193+
auto obj = Napi::Object::New(env);
194+
195+
obj["status"] = toJs(env, json.status);
196+
obj["errors"] = toJs(env, json.errors);
197+
obj["proof"] = json.errors.empty() ? toJs(env, json.proof) : env.Null();
198+
199+
return obj;
200+
});
201+
};
202+
203+
static Napi::Value proRevocationsRequestBody(const Napi::CallbackInfo& info) {
204+
return wrapResult(info, [&] {
205+
// we expect arguments that match:
206+
// first: {
207+
// "requestVersion": number,
208+
// "ticket": number,
209+
// }
210+
211+
assertInfoLength(info, 1);
212+
assertIsObject(info[0]);
213+
auto env = info.Env();
214+
215+
auto first = info[0].As<Napi::Object>();
216+
217+
if (first.IsEmpty())
218+
throw std::invalid_argument("proRevocationsRequestBody first received empty");
219+
220+
assertIsNumber(first.Get("requestVersion"), "proRevocationsRequestBody.requestVersion");
221+
assertIsNumber(first.Get("ticket"), "proRevocationsRequestBody.ticket");
222+
auto requestVersion = first.Get("requestVersion").As<Napi::Number>();
223+
auto ticket = first.Get("ticket").As<Napi::Number>();
224+
225+
auto revocationsRequest = pro_backend::GetProRevocationsRequest{
226+
.version = static_cast<uint8_t>(requestVersion.Int32Value()),
227+
.ticket = ticket.Uint32Value(),
228+
};
229+
230+
auto json = revocationsRequest.to_json();
231+
232+
return json;
233+
});
234+
};
235+
236+
static Napi::Value proRevocationsResponseBody(const Napi::CallbackInfo& info) {
237+
return wrapResult(info, [&] {
238+
// we expect arguments that match:
239+
// first: {
240+
// "json": string,
241+
// }
242+
243+
assertInfoLength(info, 1);
244+
assertIsObject(info[0]);
245+
auto env = info.Env();
246+
247+
auto first = info[0].As<Napi::Object>();
248+
249+
if (first.IsEmpty())
250+
throw std::invalid_argument("proRevocationsResponseBody first received empty");
251+
252+
assertIsString(first.Get("json"), "proRevocationsResponseBody.jsonStr");
253+
auto json_str = toCppString(first.Get("json"), "proRevocationsResponseBody.jsonStr");
254+
auto json = pro_backend::GetProRevocationsResponse::parse(json_str);
255+
256+
auto obj = Napi::Object::New(env);
257+
258+
obj["status"] = toJs(env, json.status);
259+
obj["errors"] = toJs(env, json.errors);
260+
obj["ticket"] = json.errors.empty() ? toJs(env, json.ticket) : env.Null();
261+
// FIXME: implement
262+
// obj["items"] = json.errors.empty() ? toJs(env, json.items) : env.Null();
263+
264+
return obj;
265+
});
266+
};
267+
268+
static Napi::Value proStatusRequestBody(const Napi::CallbackInfo& info) {
269+
return wrapResult(info, [&] {
270+
// we expect arguments that match:
271+
// first: {
272+
// "requestVersion": number,
273+
// "masterPrivkey": Uint8Array,
274+
// "unixTsMs": number,
275+
// "withPaymentHistory": boolean,
276+
// }
277+
278+
assertInfoLength(info, 1);
279+
assertIsObject(info[0]);
280+
auto env = info.Env();
281+
282+
auto first = info[0].As<Napi::Object>();
283+
284+
if (first.IsEmpty())
285+
throw std::invalid_argument("proStatusRequestBody first received empty");
286+
287+
assertIsNumber(first.Get("requestVersion"), "proStatusRequestBody.requestVersion");
288+
assertIsNumber(first.Get("unixTsMs"), "proStatusRequestBody.unixTsMs");
289+
assertIsBoolean(
290+
first.Get("withPaymentHistory"), "proStatusRequestBody.withPaymentHistory");
291+
auto requestVersion = first.Get("requestVersion").As<Napi::Number>();
292+
auto unix_ts_ms = toCppSysMs(first.Get("unixTsMs"), "proStatusRequestBody.unixTsMs");
293+
auto withPaymentHistory = toCppBoolean(
294+
first.Get("withPaymentHistory"), "proStatusRequestBody.withPaymentHistory");
295+
assertIsUInt8Array(first.Get("masterPrivkey"), "proStatusRequestBody.masterPrivkey");
296+
297+
auto master_privkey_js = first.Get("masterPrivkey");
298+
auto master_privkey =
299+
toCppBuffer(master_privkey_js, "proStatusRequestBody.masterPrivkey");
300+
301+
assert_length(master_privkey, 64, "master_privkey");
302+
303+
auto json = pro_backend::GetProStatusRequest::build_to_json(
304+
static_cast<uint8_t>(requestVersion.Int32Value()),
305+
master_privkey,
306+
unix_ts_ms,
307+
withPaymentHistory);
308+
309+
return json;
310+
});
311+
};
312+
313+
static Napi::Value proStatusResponseBody(const Napi::CallbackInfo& info) {
314+
return wrapResult(info, [&] {
315+
// we expect arguments that match:
316+
// first: {
317+
// "json": string,
318+
// }
319+
320+
assertInfoLength(info, 1);
321+
assertIsObject(info[0]);
322+
auto env = info.Env();
323+
324+
auto first = info[0].As<Napi::Object>();
325+
326+
if (first.IsEmpty())
327+
throw std::invalid_argument("proStatusResponseBody first received empty");
328+
329+
assertIsString(first.Get("json"), "proStatusResponseBody.jsonStr");
330+
auto json_str = toCppString(first.Get("json"), "proStatusResponseBody.jsonStr");
331+
auto json = pro_backend::GetProStatusResponse::parse(json_str);
332+
333+
auto obj = Napi::Object::New(env);
334+
335+
obj["status"] = toJs(env, json.status);
336+
obj["errors"] = toJs(env, json.errors);
337+
// FIXME: implement
338+
// obj["items"] = json.errors.empty() ? toJs(env, json.items) : env.Null();
339+
obj["userStatus"] = json.errors.empty()
340+
? toJs(env, ProBackendEnumToString(json.user_status))
341+
: env.Null();
342+
obj["errorReport"] = json.errors.empty()
343+
? toJs(env, ProBackendEnumToString(json.error_report))
344+
: env.Null();
345+
obj["autoRenewing"] = json.errors.empty() ? toJs(env, json.auto_renewing) : env.Null();
346+
347+
// FIXME: implement
348+
// obj["expiryUnixTsMs"] = json.errors.empty() ? toJs(env, json.expiry_unix_ts_ms) :
349+
// env.Null(); obj["gracePeriodDurationMs"] = json.errors.empty() ? toJs(env,
350+
// json.grace_period_duration_ms) : env.Null();
351+
352+
return obj;
353+
});
354+
};
144355
};
145356

146357
}; // namespace session::nodeapi

include/utilities.hpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22

33
#include <napi.h>
44

5+
#include <chrono>
56
#include <optional>
67
#include <span>
78
#include <stdexcept>

src/pro/pro.cpp

Lines changed: 61 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1,61 @@
1-
#include "pro/pro.hpp"
1+
#include "pro/pro.hpp"
2+
3+
namespace session::nodeapi {
4+
std::string_view ProBackendEnumToString(SESSION_PRO_BACKEND_PAYMENT_PROVIDER v) {
5+
switch (v) {
6+
case SESSION_PRO_BACKEND_PAYMENT_PROVIDER_NIL: return "NIL";
7+
case SESSION_PRO_BACKEND_PAYMENT_PROVIDER_GOOGLE_PLAY_STORE: return "GOOGLE_PLAY_STORE";
8+
case SESSION_PRO_BACKEND_PAYMENT_PROVIDER_IOS_APP_STORE: return "IOS_APP_STORE";
9+
case SESSION_PRO_BACKEND_PAYMENT_PROVIDER_COUNT:
10+
// TODO: do we want to assert this cant happen? or should it be allowed?
11+
return "Count";
12+
}
13+
}
14+
15+
std::string_view ProBackendEnumToString(SESSION_PRO_BACKEND_PAYMENT_STATUS v) {
16+
switch (v) {
17+
case SESSION_PRO_BACKEND_PAYMENT_STATUS_NIL: return "NIL";
18+
case SESSION_PRO_BACKEND_PAYMENT_STATUS_UNREDEEMED: return "UNREDEEMED";
19+
case SESSION_PRO_BACKEND_PAYMENT_STATUS_REDEEMED: return "REDEEMED";
20+
case SESSION_PRO_BACKEND_PAYMENT_STATUS_EXPIRED: return "EXPIRED";
21+
case SESSION_PRO_BACKEND_PAYMENT_STATUS_REFUNDED: return "REFUNDED";
22+
case SESSION_PRO_BACKEND_PAYMENT_STATUS_COUNT:
23+
// TODO: do we want to assert this cant happen? or should it be allowed?
24+
return "COUNT";
25+
}
26+
}
27+
28+
std::string_view ProBackendEnumToString(SESSION_PRO_BACKEND_PLAN v) {
29+
switch (v) {
30+
case SESSION_PRO_BACKEND_PLAN_NIL: return "NIL";
31+
case SESSION_PRO_BACKEND_PLAN_ONE_MONTH: return "ONE_MONTH";
32+
case SESSION_PRO_BACKEND_PLAN_THREE_MONTHS: return "THREE_MONTHS";
33+
case SESSION_PRO_BACKEND_PLAN_TWELVE_MONTHS: return "TWELVE_MONTHS";
34+
case SESSION_PRO_BACKEND_PLAN_COUNT:
35+
// TODO: do we want to assert this cant happen? or should it be allowed?
36+
return "COUNT";
37+
}
38+
}
39+
40+
std::string_view ProBackendEnumToString(SESSION_PRO_BACKEND_USER_PRO_STATUS v) {
41+
switch (v) {
42+
case SESSION_PRO_BACKEND_USER_PRO_STATUS_NEVER_BEEN_PRO: return "NEVER_BEEN_PRO";
43+
case SESSION_PRO_BACKEND_USER_PRO_STATUS_ACTIVE: return "ACTIVE";
44+
case SESSION_PRO_BACKEND_USER_PRO_STATUS_EXPIRED: return "EXPIRED";
45+
case SESSION_PRO_BACKEND_USER_PRO_STATUS_COUNT:
46+
// TODO: do we want to assert this cant happen? or should it be allowed?
47+
return "COUNT";
48+
}
49+
}
50+
51+
std::string_view ProBackendEnumToString(SESSION_PRO_BACKEND_GET_PRO_STATUS_ERROR_REPORT v) {
52+
switch (v) {
53+
case SESSION_PRO_BACKEND_GET_PRO_STATUS_ERROR_REPORT_SUCCESS: return "SUCCESS";
54+
case SESSION_PRO_BACKEND_GET_PRO_STATUS_ERROR_REPORT_GENERIC_ERROR: return "GENERIC_ERROR";
55+
case SESSION_PRO_BACKEND_GET_PRO_STATUS_ERROR_REPORT_COUNT:
56+
// TODO: do we want to assert this cant happen? or should it be allowed?
57+
return "COUNT";
58+
}
59+
}
60+
61+
}

types/pro/pro.d.ts

Lines changed: 47 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,11 @@ declare module 'libsession_util_nodejs' {
3333
proProof: ProProof;
3434
};
3535

36+
type WithProBackendResponse = {
37+
status: number;
38+
errors: Array<string>;
39+
}
40+
3641
// Must match session-desktop
3742
export enum ProOriginatingPlatform {
3843
Nil = 'Nil',
@@ -75,12 +80,53 @@ declare module 'libsession_util_nodejs' {
7580
proFeatures: ProFeatures;
7681
}) => WithProFeatures & { success: boolean; error: string | null; codepointCount: number };
7782
proProofRequestBody: (args: {
78-
requestVersion: string,
83+
requestVersion: number,
7984
masterPrivkey: Uint8Array,
8085
rotatingPrivkey: Uint8Array,
8186
unixTsMs: number,
8287
}
8388
) => string;
89+
90+
proProofResponseBody: (args: {
91+
json: string,
92+
}
93+
) => WithProBackendResponse & { proof: ProProof | null };
94+
95+
proRevocationsRequestBody: (args: {
96+
requestVersion: number,
97+
ticket: number,
98+
}
99+
) => string;
100+
101+
proRevocationsResponseBody: (args: {
102+
json: string,
103+
}
104+
) => WithProBackendResponse & {
105+
ticket: number | null;
106+
items: Array<ProRevocationItem>
107+
};
108+
109+
proStatusRequestBody: (args: {
110+
requestVersion: number,
111+
masterPrivkey: Uint8Array,
112+
unixTsMs: number,
113+
withPaymentHistory: boolean,
114+
}
115+
) => string;
116+
117+
proStatusResponseBody: (args: {
118+
json: string,
119+
}
120+
) => WithProBackendResponse & {
121+
ticket: number | null;
122+
items: Array<ProPaymentItem>;
123+
userStatus: number;
124+
errorReport: number;
125+
autoRenewing: boolean;
126+
expiryUnixTsMs: number;
127+
gracePeriodDurationMs: number;
128+
};
129+
84130
};
85131

86132
export type ProActionsCalls = MakeWrapperActionCalls<ProWrapper>;

0 commit comments

Comments
 (0)