Skip to content

Commit b8aeef6

Browse files
authored
Merge pull request #1097 from JKRhb/http-strict-boolean
chore(binding-http): enable eslint/strict-boolean-expressions
2 parents 63b31c6 + 4624a03 commit b8aeef6

18 files changed

+272
-201
lines changed
Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,6 @@
11
{
2-
"extends": "../../.eslintrc.js"
2+
"extends": "../../.eslintrc.js",
3+
"rules": {
4+
"@typescript-eslint/strict-boolean-expressions": ["error"]
5+
}
36
}

packages/binding-http/src/codecs/tuya-codec.ts

Lines changed: 18 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -17,17 +17,30 @@ import { ContentCodec } from "@node-wot/core";
1717
import * as TD from "@node-wot/td-tools";
1818
import { DataSchemaValue } from "wot-typescript-definitions";
1919

20+
interface TuyaOutput {
21+
success?: boolean;
22+
msg?: string;
23+
result?: {
24+
code?: string;
25+
}[];
26+
}
27+
2028
export default class HttpTuyaCodec implements ContentCodec {
2129
getMediaType(): string {
2230
return "application/json+tuya";
2331
}
2432

2533
bytesToValue(bytes: Buffer, schema: TD.DataSchema, parameters: { [key: string]: string }): DataSchemaValue {
26-
const parsedBody = JSON.parse(bytes.toString());
27-
if (!parsedBody.success) throw new Error(parsedBody.msg ? parsedBody.msg : JSON.stringify(parsedBody));
28-
for (const key in parsedBody.result) {
29-
if (parsedBody.result[key].code === schema["tuya:PropertyName"]) {
30-
return parsedBody.result[key].value;
34+
const parsedBody: TuyaOutput = JSON.parse(bytes.toString());
35+
const success = parsedBody.success ?? false;
36+
37+
if (!success) {
38+
throw new Error(parsedBody.msg != null ? parsedBody.msg : JSON.stringify(parsedBody));
39+
}
40+
41+
for (const value of Object.values(parsedBody.result ?? {})) {
42+
if (value.code === schema["tuya:PropertyName"]) {
43+
return value;
3144
}
3245
}
3346
throw new Error("Property not found");

packages/binding-http/src/credential.ts

Lines changed: 43 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -163,6 +163,18 @@ export interface TuyaCustomBearerCredentialConfiguration {
163163
secret: string;
164164
}
165165

166+
interface TokenResponse {
167+
success?: boolean;
168+
result?: {
169+
// eslint-disable-next-line camelcase
170+
access_token?: string;
171+
// eslint-disable-next-line camelcase
172+
refresh_token?: string;
173+
// eslint-disable-next-line camelcase
174+
expire_time?: number;
175+
};
176+
}
177+
166178
export class TuyaCustomBearer extends Credential {
167179
protected key: string;
168180
protected secret: string;
@@ -184,14 +196,15 @@ export class TuyaCustomBearer extends Credential {
184196
await this.requestAndRefreshToken(isTokenExpired);
185197

186198
const url: string = request.url;
187-
const body = request.body ? request.body.read().toString() : "";
188-
const headers = this.getHeaders(true, request.headers.raw(), body, url, request.method);
199+
const body = request.body?.read().toString();
200+
const method = request.method;
201+
const headers = this.getHeaders(true, request.headers.raw(), body, url, method);
189202
Object.assign(headers, request.headers.raw());
190-
return new Request(url, { method: request.method, body: body !== "" ? body : undefined, headers });
203+
return new Request(url, { method, body: body !== "" ? body : undefined, headers });
191204
}
192205

193206
protected async requestAndRefreshToken(refresh: boolean): Promise<void> {
194-
const headers = this.getHeaders(false, {}, "");
207+
const headers = this.getHeaders(false, {});
195208
const request = {
196209
headers,
197210
method: "GET",
@@ -200,36 +213,51 @@ export class TuyaCustomBearer extends Credential {
200213
if (refresh) {
201214
url = `${this.baseUri}/token/${this.refreshToken}`;
202215
}
203-
const data = await (await fetch(url, request)).json();
204-
if (data.success) {
205-
this.token = data.result.access_token;
206-
this.refreshToken = data.result.refresh_token;
207-
this.expireTime = new Date(Date.now() + data.result.expire_time * 1000);
216+
const data: TokenResponse = await (await fetch(url, request)).json();
217+
const success = data.success ?? false;
218+
219+
if (success) {
220+
this.token = data.result?.access_token;
221+
this.refreshToken = data.result?.refresh_token;
222+
223+
const expireTime = data.result?.expire_time;
224+
if (expireTime != null) {
225+
this.expireTime = new Date(Date.now() + expireTime * 1000);
226+
}
208227
} else {
209228
throw new Error("token fetch failed");
210229
}
211230
}
212231

213-
private getHeaders(NormalRequest: boolean, headers: unknown, body: string, url?: string, method?: string) {
232+
private getHeaders(NormalRequest: boolean, headers: unknown, body?: string, url?: string, method?: string) {
214233
const requestTime = Date.now().toString();
215234
const replaceUri = this.baseUri.replace("/v1.0", "");
216-
const _url = url ? url.replace(`${replaceUri}`, "") : undefined;
235+
const _url = url?.replace(replaceUri, "");
217236
const sign = this.requestSign(NormalRequest, requestTime, body, _url, method);
218237
return {
219238
t: requestTime,
220239
client_id: this.key,
221240
sign_method: "HMAC-SHA256",
222241
sign,
223-
access_token: this.token || "",
242+
access_token: this.token ?? "",
224243
};
225244
}
226245

227-
private requestSign(NormalRequest: boolean, requestTime: string, body: string, path = "", method?: string): string {
228-
const bodyHash = crypto.createHash("sha256").update(body).digest("hex");
246+
private requestSign(
247+
NormalRequest: boolean,
248+
requestTime: string,
249+
body?: string,
250+
path = "",
251+
method?: string
252+
): string {
253+
const bodyHash = crypto
254+
.createHash("sha256")
255+
.update(body ?? "")
256+
.digest("hex");
229257
let signUrl = "/v1.0/token?grant_type=1";
230258
const headerString = "";
231259
let useToken = "";
232-
const _method = method || "GET";
260+
const _method = method ?? "GET";
233261
if (NormalRequest) {
234262
useToken = this.token ?? "";
235263
const pathQuery = queryString.parse(path.split("?")[1]);

packages/binding-http/src/http-client-impl.ts

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -175,7 +175,7 @@ export default class HttpClient implements ProtocolClient {
175175
}
176176

177177
public async invokeResource(form: HttpForm, content?: Content): Promise<Content> {
178-
const headers = content ? [["content-type", content.type]] : [];
178+
const headers = content != null ? [["content-type", content.type]] : [];
179179

180180
const request = await this.generateFetchRequest(form, "POST", {
181181
headers,
@@ -184,8 +184,8 @@ export default class HttpClient implements ProtocolClient {
184184

185185
debug(
186186
`HttpClient (invokeResource) sending ${request.method} ${
187-
content ? "with '" + request.headers.get("Content-Type") + "' " : " "
188-
}to ${request.url}`
187+
content != null ? `with '"${request.headers.get("Content-Type")}"` : ""
188+
} to ${request.url}`
189189
);
190190

191191
const result = await this.fetch(request);
@@ -218,7 +218,7 @@ export default class HttpClient implements ProtocolClient {
218218

219219
public async stop(): Promise<void> {
220220
// When running in browser mode, Agent.destroy() might not exist.
221-
if (this.agent && this.agent.destroy) this.agent.destroy();
221+
this.agent?.destroy?.();
222222
}
223223

224224
public setSecurity(metadata: Array<TD.SecurityScheme>, credentials?: unknown): boolean {
@@ -280,7 +280,7 @@ export default class HttpClient implements ProtocolClient {
280280
return false;
281281
}
282282

283-
if (security.proxy) {
283+
if (security.proxy != null) {
284284
if (this.proxyRequest !== null) {
285285
debug(`HttpClient overriding client-side proxy with security proxy '${security.proxy}`);
286286
}

0 commit comments

Comments
 (0)