-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathapi.ts
120 lines (104 loc) · 3.44 KB
/
api.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
import { from, Observable } from "rxjs";
import { catchError, mergeMap } from "rxjs/operators";
import { isElectron, sendMessageToParent } from "./common/appUtil";
import { GetbalanceResponse } from "./models/GetbalanceResponse";
import { Info } from "./models/Info";
import { SetupStatusResponse } from "./models/SetupStatusResponse";
import { Status } from "./models/Status";
import { TradehistoryResponse } from "./models/TradehistoryResponse";
import { TradinglimitsResponse } from "./models/TradinglimitsResponse";
const url =
process.env.NODE_ENV === "development"
? process.env.REACT_APP_API_URL
: window.location.origin;
const path = `${url}/api/v1`;
const xudPath = `${path}/xud`;
const logError = (url: string, err: string) => {
if (isElectron()) {
sendMessageToParent(`logError: requestUrl: ${url}; error: ${err}`);
}
};
const logAndThrow = (url: string, err: string) => {
logError(url, err);
throw err;
};
const fetchJsonResponse = <T>(url: string): Observable<T> => {
return from(fetch(`${url}`)).pipe(
mergeMap((resp: Response) => resp.json()),
catchError((err) => logAndThrow(url, err))
);
};
const fetchStreamResponse = <T>(url: string): Observable<T | null> => {
return new Observable((subscriber) => {
fetch(url)
.then((response) => {
if (!response.body) {
subscriber.next(null);
return;
}
const reader = response.body.getReader();
const processText = ({
done,
value,
}: any): Promise<
| ReadableStreamReadResult<T>
| ReadableStreamReadDoneResult<T>
| undefined
> => {
if (done) {
subscriber.complete();
return Promise.resolve(undefined);
}
const stringValue = new TextDecoder("utf-8").decode(value);
const items = stringValue
.split("\n")
.map((item) => item.trim())
.filter((item) => !!item);
const newestItem = items[items.length - 1];
try {
const jsonValue = JSON.parse(newestItem);
subscriber.next(jsonValue);
} catch (err) {
subscriber.next(null);
}
return reader.read().then(processText);
};
reader.read().then(processText);
})
.catch((e) => {
logError(url, e);
subscriber.error(e);
});
});
};
export default {
setupStatus$(): Observable<SetupStatusResponse | null> {
const requestUrl = `${path}/setup-status`;
return fetchStreamResponse(requestUrl);
},
status$(): Observable<Status[]> {
return fetchJsonResponse(`${path}/status`);
},
statusByService$(serviceName: string): Observable<Status> {
return fetchJsonResponse(`${path}/status/${serviceName}`);
},
logs$(serviceName: string): Observable<string> {
const requestUrl = `${path}/logs/${serviceName}`;
return from(fetch(requestUrl)).pipe(
mergeMap((resp) => resp.text()),
catchError((err) => logAndThrow(requestUrl, err))
);
},
getinfo$(): Observable<Info> {
return fetchJsonResponse(`${xudPath}/getinfo`);
},
getbalance$(): Observable<GetbalanceResponse> {
return fetchJsonResponse(`${xudPath}/getbalance`);
},
tradinglimits$(): Observable<TradinglimitsResponse> {
return fetchJsonResponse(`${xudPath}/tradinglimits`);
},
tradehistory$(): Observable<TradehistoryResponse> {
return fetchJsonResponse(`${xudPath}/tradehistory`);
},
};