@yume-chan/adb 0.0.16 → 0.0.18
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/CHANGELOG.json +18 -0
- package/CHANGELOG.md +13 -1
- package/LICENSE +1 -1
- package/esm/adb.d.ts +13 -8
- package/esm/adb.d.ts.map +1 -1
- package/esm/adb.js +63 -38
- package/esm/adb.js.map +1 -1
- package/esm/auth.d.ts +4 -4
- package/esm/auth.d.ts.map +1 -1
- package/esm/auth.js +6 -6
- package/esm/auth.js.map +1 -1
- package/esm/backend.d.ts +3 -3
- package/esm/backend.d.ts.map +1 -1
- package/esm/commands/base.d.ts +2 -2
- package/esm/commands/base.d.ts.map +1 -1
- package/esm/commands/base.js +1 -1
- package/esm/commands/base.js.map +1 -1
- package/esm/commands/framebuffer.d.ts +22 -6
- package/esm/commands/framebuffer.d.ts.map +1 -1
- package/esm/commands/framebuffer.js +33 -45
- package/esm/commands/framebuffer.js.map +1 -1
- package/esm/commands/install.d.ts +2 -2
- package/esm/commands/install.d.ts.map +1 -1
- package/esm/commands/install.js +12 -5
- package/esm/commands/install.js.map +1 -1
- package/esm/commands/power.d.ts.map +1 -1
- package/esm/commands/power.js +13 -9
- package/esm/commands/power.js.map +1 -1
- package/esm/commands/reverse.d.ts +5 -5
- package/esm/commands/reverse.d.ts.map +1 -1
- package/esm/commands/reverse.js +20 -18
- package/esm/commands/reverse.js.map +1 -1
- package/esm/commands/subprocess/command.d.ts +52 -0
- package/esm/commands/subprocess/command.d.ts.map +1 -0
- package/esm/commands/subprocess/command.js +81 -0
- package/esm/commands/subprocess/command.js.map +1 -0
- package/esm/commands/subprocess/index.d.ts +1 -53
- package/esm/commands/subprocess/index.d.ts.map +1 -1
- package/esm/commands/subprocess/index.js +1 -85
- package/esm/commands/subprocess/index.js.map +1 -1
- package/esm/commands/subprocess/protocols/none.d.ts +5 -5
- package/esm/commands/subprocess/protocols/none.d.ts.map +1 -1
- package/esm/commands/subprocess/protocols/none.js +5 -3
- package/esm/commands/subprocess/protocols/none.js.map +1 -1
- package/esm/commands/subprocess/protocols/shell.d.ts +4 -4
- package/esm/commands/subprocess/protocols/shell.d.ts.map +1 -1
- package/esm/commands/subprocess/protocols/shell.js +28 -20
- package/esm/commands/subprocess/protocols/shell.js.map +1 -1
- package/esm/commands/subprocess/protocols/types.d.ts +7 -7
- package/esm/commands/subprocess/protocols/types.d.ts.map +1 -1
- package/esm/commands/sync/index.d.ts +1 -1
- package/esm/commands/sync/index.d.ts.map +1 -1
- package/esm/commands/sync/index.js +1 -1
- package/esm/commands/sync/index.js.map +1 -1
- package/esm/commands/sync/list.d.ts +7 -7
- package/esm/commands/sync/list.d.ts.map +1 -1
- package/esm/commands/sync/list.js +34 -50
- package/esm/commands/sync/list.js.map +1 -1
- package/esm/commands/sync/pull.d.ts +5 -4
- package/esm/commands/sync/pull.d.ts.map +1 -1
- package/esm/commands/sync/pull.js +21 -22
- package/esm/commands/sync/pull.js.map +1 -1
- package/esm/commands/sync/push.d.ts +4 -4
- package/esm/commands/sync/push.d.ts.map +1 -1
- package/esm/commands/sync/push.js +7 -11
- package/esm/commands/sync/push.js.map +1 -1
- package/esm/commands/sync/request.d.ts +4 -4
- package/esm/commands/sync/request.d.ts.map +1 -1
- package/esm/commands/sync/request.js +6 -6
- package/esm/commands/sync/request.js.map +1 -1
- package/esm/commands/sync/response.d.ts +5 -10
- package/esm/commands/sync/response.d.ts.map +1 -1
- package/esm/commands/sync/response.js +35 -26
- package/esm/commands/sync/response.js.map +1 -1
- package/esm/commands/sync/stat.d.ts +7 -7
- package/esm/commands/sync/stat.d.ts.map +1 -1
- package/esm/commands/sync/stat.js +48 -55
- package/esm/commands/sync/stat.js.map +1 -1
- package/esm/commands/sync/sync.d.ts +7 -7
- package/esm/commands/sync/sync.d.ts.map +1 -1
- package/esm/commands/sync/sync.js +25 -22
- package/esm/commands/sync/sync.js.map +1 -1
- package/esm/crypto.d.ts.map +1 -1
- package/esm/crypto.js +26 -16
- package/esm/crypto.js.map +1 -1
- package/esm/index.d.ts +9 -10
- package/esm/index.d.ts.map +1 -1
- package/esm/index.js +9 -10
- package/esm/index.js.map +1 -1
- package/esm/packet.d.ts +8 -8
- package/esm/packet.d.ts.map +1 -1
- package/esm/packet.js +14 -12
- package/esm/packet.js.map +1 -1
- package/esm/socket/dispatcher.d.ts +11 -6
- package/esm/socket/dispatcher.d.ts.map +1 -1
- package/esm/socket/dispatcher.js +28 -20
- package/esm/socket/dispatcher.js.map +1 -1
- package/esm/socket/index.d.ts +1 -1
- package/esm/socket/index.d.ts.map +1 -1
- package/esm/socket/index.js +1 -1
- package/esm/socket/index.js.map +1 -1
- package/esm/socket/socket.d.ts +5 -5
- package/esm/socket/socket.d.ts.map +1 -1
- package/esm/socket/socket.js +37 -17
- package/esm/socket/socket.js.map +1 -1
- package/esm/utils/auto-reset-event.d.ts +1 -1
- package/esm/utils/auto-reset-event.d.ts.map +1 -1
- package/esm/utils/auto-reset-event.js +2 -2
- package/esm/utils/base64.d.ts +23 -0
- package/esm/utils/base64.d.ts.map +1 -1
- package/esm/utils/base64.js +36 -29
- package/esm/utils/base64.js.map +1 -1
- package/package.json +19 -17
- package/src/adb.ts +140 -86
- package/src/auth.ts +27 -18
- package/src/backend.ts +7 -4
- package/src/commands/base.ts +3 -2
- package/src/commands/framebuffer.ts +48 -47
- package/src/commands/install.ts +20 -10
- package/src/commands/power.ts +14 -10
- package/src/commands/reverse.ts +53 -33
- package/src/commands/subprocess/command.ts +134 -0
- package/src/commands/subprocess/index.ts +1 -137
- package/src/commands/subprocess/protocols/none.ts +10 -6
- package/src/commands/subprocess/protocols/shell.ts +72 -39
- package/src/commands/subprocess/protocols/types.ts +12 -8
- package/src/commands/sync/index.ts +1 -1
- package/src/commands/sync/list.ts +63 -68
- package/src/commands/sync/pull.ts +53 -37
- package/src/commands/sync/push.ts +26 -15
- package/src/commands/sync/request.ts +20 -21
- package/src/commands/sync/response.ts +63 -53
- package/src/commands/sync/stat.ts +91 -90
- package/src/commands/sync/sync.ts +56 -34
- package/src/crypto.ts +61 -33
- package/src/features.ts +1 -1
- package/src/index.ts +9 -11
- package/src/packet.ts +40 -30
- package/src/socket/dispatcher.ts +119 -77
- package/src/socket/index.ts +1 -1
- package/src/socket/socket.ts +68 -26
- package/src/utils/auto-reset-event.ts +3 -3
- package/src/utils/base64.ts +75 -42
- package/tsconfig.build.json +1 -1
- package/tsconfig.build.tsbuildinfo +1 -1
- package/esm/stream/buffered.d.ts +0 -39
- package/esm/stream/buffered.d.ts.map +0 -1
- package/esm/stream/buffered.js +0 -143
- package/esm/stream/buffered.js.map +0 -1
- package/esm/stream/detect.d.ts +0 -2
- package/esm/stream/detect.d.ts.map +0 -1
- package/esm/stream/detect.js +0 -6
- package/esm/stream/detect.js.map +0 -1
- package/esm/stream/detect.native.d.ts +0 -240
- package/esm/stream/detect.native.d.ts.map +0 -1
- package/esm/stream/detect.native.js +0 -60
- package/esm/stream/detect.native.js.map +0 -1
- package/esm/stream/detect.polyfill.d.ts +0 -18
- package/esm/stream/detect.polyfill.d.ts.map +0 -1
- package/esm/stream/detect.polyfill.js +0 -4
- package/esm/stream/detect.polyfill.js.map +0 -1
- package/esm/stream/index.d.ts +0 -4
- package/esm/stream/index.d.ts.map +0 -1
- package/esm/stream/index.js +0 -4
- package/esm/stream/index.js.map +0 -1
- package/esm/stream/transform.d.ts +0 -124
- package/esm/stream/transform.d.ts.map +0 -1
- package/esm/stream/transform.js +0 -379
- package/esm/stream/transform.js.map +0 -1
- package/src/stream/buffered.ts +0 -168
- package/src/stream/detect.native.ts +0 -362
- package/src/stream/detect.polyfill.ts +0 -22
- package/src/stream/detect.ts +0 -7
- package/src/stream/index.ts +0 -3
- package/src/stream/transform.ts +0 -474
- package/tsconfig.test.json +0 -9
- package/web-streams-polyfill-4.0.0-beta.2.tgz +0 -0
package/esm/commands/install.js
CHANGED
|
@@ -1,22 +1,29 @@
|
|
|
1
|
-
import { WrapWritableStream } from "
|
|
1
|
+
import { WrapWritableStream, } from "@yume-chan/stream-extra";
|
|
2
2
|
import { escapeArg } from "./subprocess/index.js";
|
|
3
3
|
export function install(adb) {
|
|
4
|
-
const filename = `/data/local/tmp/${Math.random()
|
|
4
|
+
const filename = `/data/local/tmp/${Math.random()
|
|
5
|
+
.toString()
|
|
6
|
+
.substring(2)}.apk`;
|
|
5
7
|
let sync;
|
|
6
8
|
return new WrapWritableStream({
|
|
7
9
|
async start() {
|
|
8
10
|
// TODO: install: support other install apk methods (streaming, etc.)
|
|
11
|
+
// TODO: install: support split apk formats (`adb install-multiple`)
|
|
9
12
|
// Upload apk file to tmp folder
|
|
10
13
|
sync = await adb.sync();
|
|
11
14
|
return sync.write(filename, undefined, undefined);
|
|
12
15
|
},
|
|
13
16
|
async close() {
|
|
14
|
-
sync.dispose();
|
|
17
|
+
await sync.dispose();
|
|
15
18
|
// Invoke `pm install` to install it
|
|
16
|
-
await adb.subprocess.spawnAndWaitLegacy([
|
|
19
|
+
await adb.subprocess.spawnAndWaitLegacy([
|
|
20
|
+
"pm",
|
|
21
|
+
"install",
|
|
22
|
+
escapeArg(filename),
|
|
23
|
+
]);
|
|
17
24
|
// Remove the temp file
|
|
18
25
|
await adb.rm(filename);
|
|
19
|
-
}
|
|
26
|
+
},
|
|
20
27
|
});
|
|
21
28
|
}
|
|
22
29
|
//# sourceMappingURL=install.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"install.js","sourceRoot":"","sources":["../../src/commands/install.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"install.js","sourceRoot":"","sources":["../../src/commands/install.ts"],"names":[],"mappings":"AAAA,OAAO,EACH,kBAAkB,GAErB,MAAM,yBAAyB,CAAC;AAIjC,OAAO,EAAE,SAAS,EAAE,MAAM,uBAAuB,CAAC;AAGlD,MAAM,UAAU,OAAO,CAAC,GAAQ;IAC5B,MAAM,QAAQ,GAAG,mBAAmB,IAAI,CAAC,MAAM,EAAE;SAC5C,QAAQ,EAAE;SACV,SAAS,CAAC,CAAC,CAAC,MAAM,CAAC;IAExB,IAAI,IAAc,CAAC;IACnB,OAAO,IAAI,kBAAkB,CAAa;QACtC,KAAK,CAAC,KAAK;YACP,qEAAqE;YACrE,oEAAoE;YAEpE,gCAAgC;YAChC,IAAI,GAAG,MAAM,GAAG,CAAC,IAAI,EAAE,CAAC;YACxB,OAAO,IAAI,CAAC,KAAK,CAAC,QAAQ,EAAE,SAAS,EAAE,SAAS,CAAC,CAAC;QACtD,CAAC;QACD,KAAK,CAAC,KAAK;YACP,MAAM,IAAI,CAAC,OAAO,EAAE,CAAC;YAErB,oCAAoC;YACpC,MAAM,GAAG,CAAC,UAAU,CAAC,kBAAkB,CAAC;gBACpC,IAAI;gBACJ,SAAS;gBACT,SAAS,CAAC,QAAQ,CAAC;aACtB,CAAC,CAAC;YAEH,uBAAuB;YACvB,MAAM,GAAG,CAAC,EAAE,CAAC,QAAQ,CAAC,CAAC;QAC3B,CAAC;KACJ,CAAC,CAAC;AACP,CAAC"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"power.d.ts","sourceRoot":"","sources":["../../src/commands/power.ts"],"names":[],"mappings":"AAKA,OAAO,EAAE,cAAc,EAAE,MAAM,WAAW,CAAC;AAE3C,qBAAa,QAAS,SAAQ,cAAc;IACjC,MAAM,CAAC,IAAI,
|
|
1
|
+
{"version":3,"file":"power.d.ts","sourceRoot":"","sources":["../../src/commands/power.ts"],"names":[],"mappings":"AAKA,OAAO,EAAE,cAAc,EAAE,MAAM,WAAW,CAAC;AAE3C,qBAAa,QAAS,SAAQ,cAAc;IACjC,MAAM,CAAC,IAAI,SAAK;IAIhB,UAAU;IAIV,QAAQ;IAIR,QAAQ;IAIR,QAAQ;IAIf;;;;OAIG;IACI,eAAe;IAIf,QAAQ;IAIR,WAAW,CAAC,SAAS,UAAQ;IAQpC;;;;OAIG;IACI,WAAW;CAGrB"}
|
package/esm/commands/power.js
CHANGED
|
@@ -4,20 +4,20 @@
|
|
|
4
4
|
// cspell: ignore longpress
|
|
5
5
|
import { AdbCommandBase } from "./base.js";
|
|
6
6
|
export class AdbPower extends AdbCommandBase {
|
|
7
|
-
reboot(name =
|
|
7
|
+
reboot(name = "") {
|
|
8
8
|
return this.adb.createSocketAndWait(`reboot:${name}`);
|
|
9
9
|
}
|
|
10
10
|
bootloader() {
|
|
11
|
-
return this.reboot(
|
|
11
|
+
return this.reboot("bootloader");
|
|
12
12
|
}
|
|
13
13
|
fastboot() {
|
|
14
|
-
return this.reboot(
|
|
14
|
+
return this.reboot("fastboot");
|
|
15
15
|
}
|
|
16
16
|
recovery() {
|
|
17
|
-
return this.reboot(
|
|
17
|
+
return this.reboot("recovery");
|
|
18
18
|
}
|
|
19
19
|
sideload() {
|
|
20
|
-
return this.reboot(
|
|
20
|
+
return this.reboot("sideload");
|
|
21
21
|
}
|
|
22
22
|
/**
|
|
23
23
|
* Reboot to Qualcomm Emergency Download (EDL) Mode.
|
|
@@ -25,13 +25,17 @@ export class AdbPower extends AdbCommandBase {
|
|
|
25
25
|
* Only works on some Qualcomm devices.
|
|
26
26
|
*/
|
|
27
27
|
qualcommEdlMode() {
|
|
28
|
-
return this.reboot(
|
|
28
|
+
return this.reboot("edl");
|
|
29
29
|
}
|
|
30
30
|
powerOff() {
|
|
31
|
-
return this.adb.subprocess.spawnAndWaitLegacy([
|
|
31
|
+
return this.adb.subprocess.spawnAndWaitLegacy(["reboot", "-p"]);
|
|
32
32
|
}
|
|
33
33
|
powerButton(longPress = false) {
|
|
34
|
-
return this.adb.subprocess.spawnAndWaitLegacy([
|
|
34
|
+
return this.adb.subprocess.spawnAndWaitLegacy([
|
|
35
|
+
"input",
|
|
36
|
+
"keyevent",
|
|
37
|
+
longPress ? "--longpress POWER" : "POWER",
|
|
38
|
+
]);
|
|
35
39
|
}
|
|
36
40
|
/**
|
|
37
41
|
* Reboot to Samsung Odin download mode.
|
|
@@ -39,7 +43,7 @@ export class AdbPower extends AdbCommandBase {
|
|
|
39
43
|
* Only works on Samsung devices.
|
|
40
44
|
*/
|
|
41
45
|
samsungOdin() {
|
|
42
|
-
return this.reboot(
|
|
46
|
+
return this.reboot("download");
|
|
43
47
|
}
|
|
44
48
|
}
|
|
45
49
|
//# sourceMappingURL=power.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"power.js","sourceRoot":"","sources":["../../src/commands/power.ts"],"names":[],"mappings":"AAAA,4BAA4B;AAC5B,0BAA0B;AAC1B,0BAA0B;AAC1B,2BAA2B;AAE3B,OAAO,EAAE,cAAc,EAAE,MAAM,WAAW,CAAC;AAE3C,MAAM,OAAO,QAAS,SAAQ,cAAc;IACjC,MAAM,CAAC,
|
|
1
|
+
{"version":3,"file":"power.js","sourceRoot":"","sources":["../../src/commands/power.ts"],"names":[],"mappings":"AAAA,4BAA4B;AAC5B,0BAA0B;AAC1B,0BAA0B;AAC1B,2BAA2B;AAE3B,OAAO,EAAE,cAAc,EAAE,MAAM,WAAW,CAAC;AAE3C,MAAM,OAAO,QAAS,SAAQ,cAAc;IACjC,MAAM,CAAC,IAAI,GAAG,EAAE;QACnB,OAAO,IAAI,CAAC,GAAG,CAAC,mBAAmB,CAAC,UAAU,IAAI,EAAE,CAAC,CAAC;IAC1D,CAAC;IAEM,UAAU;QACb,OAAO,IAAI,CAAC,MAAM,CAAC,YAAY,CAAC,CAAC;IACrC,CAAC;IAEM,QAAQ;QACX,OAAO,IAAI,CAAC,MAAM,CAAC,UAAU,CAAC,CAAC;IACnC,CAAC;IAEM,QAAQ;QACX,OAAO,IAAI,CAAC,MAAM,CAAC,UAAU,CAAC,CAAC;IACnC,CAAC;IAEM,QAAQ;QACX,OAAO,IAAI,CAAC,MAAM,CAAC,UAAU,CAAC,CAAC;IACnC,CAAC;IAED;;;;OAIG;IACI,eAAe;QAClB,OAAO,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;IAC9B,CAAC;IAEM,QAAQ;QACX,OAAO,IAAI,CAAC,GAAG,CAAC,UAAU,CAAC,kBAAkB,CAAC,CAAC,QAAQ,EAAE,IAAI,CAAC,CAAC,CAAC;IACpE,CAAC;IAEM,WAAW,CAAC,SAAS,GAAG,KAAK;QAChC,OAAO,IAAI,CAAC,GAAG,CAAC,UAAU,CAAC,kBAAkB,CAAC;YAC1C,OAAO;YACP,UAAU;YACV,SAAS,CAAC,CAAC,CAAC,mBAAmB,CAAC,CAAC,CAAC,OAAO;SAC5C,CAAC,CAAC;IACP,CAAC;IAED;;;;OAIG;IACI,WAAW;QACd,OAAO,IAAI,CAAC,MAAM,CAAC,UAAU,CAAC,CAAC;IACnC,CAAC;CACJ"}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { AutoDisposable } from
|
|
2
|
-
import type
|
|
3
|
-
import type
|
|
1
|
+
import { AutoDisposable } from "@yume-chan/event";
|
|
2
|
+
import { type Adb } from "../adb.js";
|
|
3
|
+
import { type AdbIncomingSocketHandler, type AdbSocket } from "../socket/index.js";
|
|
4
4
|
export interface AdbForwardListener {
|
|
5
5
|
deviceSerial: string;
|
|
6
6
|
localName: string;
|
|
@@ -19,8 +19,8 @@ export declare class AdbReverseCommand extends AutoDisposable {
|
|
|
19
19
|
/**
|
|
20
20
|
* @param deviceAddress The address adbd on device is listening on. Can be `tcp:0` to let adbd choose an available TCP port by itself.
|
|
21
21
|
* @param localAddress Native ADB client will open a connection to this address when reverse connection received. In WebADB, it's only used to uniquely identify a reverse tunnel registry, `handler` will be called to handle the connection.
|
|
22
|
-
* @param handler A callback to handle incoming connections
|
|
23
|
-
* @returns If `deviceAddress` is `tcp:0
|
|
22
|
+
* @param handler A callback to handle incoming connections. It must return `true` if it accepts the connection.
|
|
23
|
+
* @returns `tcp:{ACTUAL_LISTENING_PORT}`, If `deviceAddress` is `tcp:0`; otherwise, `deviceAddress`.
|
|
24
24
|
*/
|
|
25
25
|
add(deviceAddress: string, localAddress: string, handler: AdbIncomingSocketHandler): Promise<string>;
|
|
26
26
|
remove(deviceAddress: string): Promise<void>;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"reverse.d.ts","sourceRoot":"","sources":["../../src/commands/reverse.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,cAAc,EAAE,MAAM,kBAAkB,CAAC;
|
|
1
|
+
{"version":3,"file":"reverse.d.ts","sourceRoot":"","sources":["../../src/commands/reverse.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,cAAc,EAAE,MAAM,kBAAkB,CAAC;AAOlD,OAAO,EAAE,KAAK,GAAG,EAAE,MAAM,WAAW,CAAC;AACrC,OAAO,EACH,KAAK,wBAAwB,EAC7B,KAAK,SAAS,EACjB,MAAM,oBAAoB,CAAC;AAG5B,MAAM,WAAW,kBAAkB;IAC/B,YAAY,EAAE,MAAM,CAAC;IAErB,SAAS,EAAE,MAAM,CAAC;IAElB,UAAU,EAAE,MAAM,CAAC;CACtB;AAYD,qBAAa,iBAAkB,SAAQ,cAAc;IACjD,SAAS,CAAC,qBAAqB,wCAG3B;IAEJ,SAAS,CAAC,2BAA2B,sBAA6B;IAElE,SAAS,CAAC,GAAG,EAAE,GAAG,CAAC;IAEnB,SAAS,CAAC,SAAS,UAAS;gBAET,GAAG,EAAE,GAAG;IAS3B,SAAS,CAAC,oBAAoB,WAAkB,SAAS,sBAKvD;YAEY,oBAAoB;YAKpB,WAAW;IASZ,IAAI,IAAI,OAAO,CAAC,kBAAkB,EAAE,CAAC;IAgBlD;;;;;OAKG;IACU,GAAG,CACZ,aAAa,EAAE,MAAM,EACrB,YAAY,EAAE,MAAM,EACpB,OAAO,EAAE,wBAAwB,GAClC,OAAO,CAAC,MAAM,CAAC;IAoCL,MAAM,CAAC,aAAa,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAa5C,SAAS,IAAI,OAAO,CAAC,IAAI,CAAC;CAQ1C"}
|
package/esm/commands/reverse.js
CHANGED
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
// cspell: ignore killforward
|
|
2
|
-
import { AutoDisposable } from
|
|
3
|
-
import
|
|
4
|
-
import
|
|
2
|
+
import { AutoDisposable } from "@yume-chan/event";
|
|
3
|
+
import { BufferedReadableStream, BufferedReadableStreamEndedError, } from "@yume-chan/stream-extra";
|
|
4
|
+
import Struct from "@yume-chan/struct";
|
|
5
5
|
import { decodeUtf8 } from "../utils/index.js";
|
|
6
6
|
const AdbReverseStringResponse = new Struct()
|
|
7
|
-
.string(
|
|
8
|
-
.string(
|
|
7
|
+
.string("length", { length: 4 })
|
|
8
|
+
.string("content", { lengthField: "length", lengthFieldRadix: 16 });
|
|
9
9
|
const AdbReverseErrorResponse = new Struct()
|
|
10
10
|
.fields(AdbReverseStringResponse)
|
|
11
11
|
.postDeserialize((value) => {
|
|
@@ -19,31 +19,31 @@ export class AdbReverseCommand extends AutoDisposable {
|
|
|
19
19
|
constructor(adb) {
|
|
20
20
|
super();
|
|
21
21
|
this.adb = adb;
|
|
22
|
-
this.addDisposable(this.adb.
|
|
22
|
+
this.addDisposable(this.adb.onIncomingSocket(this.handleIncomingSocket));
|
|
23
23
|
}
|
|
24
24
|
handleIncomingSocket = async (socket) => {
|
|
25
25
|
let address = socket.serviceString;
|
|
26
26
|
// ADB daemon appends `\0` to the service string
|
|
27
|
-
address = address.replace(/\0/g,
|
|
27
|
+
address = address.replace(/\0/g, "");
|
|
28
28
|
return !!(await this.localAddressToHandler.get(address)?.(socket));
|
|
29
29
|
};
|
|
30
30
|
async createBufferedStream(service) {
|
|
31
31
|
const socket = await this.adb.createSocket(service);
|
|
32
|
-
return new
|
|
32
|
+
return new BufferedReadableStream(socket.readable);
|
|
33
33
|
}
|
|
34
34
|
async sendRequest(service) {
|
|
35
35
|
const stream = await this.createBufferedStream(service);
|
|
36
|
-
const success = decodeUtf8(await stream.read(4)) ===
|
|
36
|
+
const success = decodeUtf8(await stream.read(4)) === "OKAY";
|
|
37
37
|
if (!success) {
|
|
38
38
|
await AdbReverseErrorResponse.deserialize(stream);
|
|
39
39
|
}
|
|
40
40
|
return stream;
|
|
41
41
|
}
|
|
42
42
|
async list() {
|
|
43
|
-
const stream = await this.createBufferedStream(
|
|
43
|
+
const stream = await this.createBufferedStream("reverse:list-forward");
|
|
44
44
|
const response = await AdbReverseStringResponse.deserialize(stream);
|
|
45
|
-
return response.content.split(
|
|
46
|
-
const [deviceSerial, localName, remoteName] = line.split(
|
|
45
|
+
return response.content.split("\n").map((line) => {
|
|
46
|
+
const [deviceSerial, localName, remoteName] = line.split(" ");
|
|
47
47
|
return { deviceSerial, localName, remoteName };
|
|
48
48
|
});
|
|
49
49
|
// No need to close the stream, device will close it
|
|
@@ -51,23 +51,25 @@ export class AdbReverseCommand extends AutoDisposable {
|
|
|
51
51
|
/**
|
|
52
52
|
* @param deviceAddress The address adbd on device is listening on. Can be `tcp:0` to let adbd choose an available TCP port by itself.
|
|
53
53
|
* @param localAddress Native ADB client will open a connection to this address when reverse connection received. In WebADB, it's only used to uniquely identify a reverse tunnel registry, `handler` will be called to handle the connection.
|
|
54
|
-
* @param handler A callback to handle incoming connections
|
|
55
|
-
* @returns If `deviceAddress` is `tcp:0
|
|
54
|
+
* @param handler A callback to handle incoming connections. It must return `true` if it accepts the connection.
|
|
55
|
+
* @returns `tcp:{ACTUAL_LISTENING_PORT}`, If `deviceAddress` is `tcp:0`; otherwise, `deviceAddress`.
|
|
56
56
|
*/
|
|
57
57
|
async add(deviceAddress, localAddress, handler) {
|
|
58
|
+
// TODO(reverse): handle ADB bug
|
|
59
|
+
// https://issuetracker.google.com/issues/37066218
|
|
58
60
|
const stream = await this.sendRequest(`reverse:forward:${deviceAddress};${localAddress}`);
|
|
59
61
|
// `tcp:0` tells the device to pick an available port.
|
|
60
|
-
//
|
|
61
|
-
if (deviceAddress.startsWith(
|
|
62
|
+
// On Android >=8, device will respond with the selected port for all `tcp:` requests.
|
|
63
|
+
if (deviceAddress.startsWith("tcp:")) {
|
|
62
64
|
let length;
|
|
63
65
|
try {
|
|
64
66
|
length = Number.parseInt(decodeUtf8(await stream.read(4)), 16);
|
|
65
67
|
}
|
|
66
68
|
catch (e) {
|
|
67
|
-
if (!(e instanceof
|
|
69
|
+
if (!(e instanceof BufferedReadableStreamEndedError)) {
|
|
68
70
|
throw e;
|
|
69
71
|
}
|
|
70
|
-
//
|
|
72
|
+
// Android <8 doesn't have this response.
|
|
71
73
|
// (the stream is closed now)
|
|
72
74
|
// Can be safely ignored.
|
|
73
75
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"reverse.js","sourceRoot":"","sources":["../../src/commands/reverse.ts"],"names":[],"mappings":"AAAA,6BAA6B;AAE7B,OAAO,EAAE,cAAc,EAAE,MAAM,kBAAkB,CAAC;AAClD,OAAO,
|
|
1
|
+
{"version":3,"file":"reverse.js","sourceRoot":"","sources":["../../src/commands/reverse.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
import { AdbCommandBase } from "../base.js";
|
|
2
|
+
import { type AdbSubprocessProtocol, type AdbSubprocessProtocolConstructor } from "./protocols/index.js";
|
|
3
|
+
export interface AdbSubprocessOptions {
|
|
4
|
+
/**
|
|
5
|
+
* A list of `AdbSubprocessProtocolConstructor`s to be used.
|
|
6
|
+
*
|
|
7
|
+
* Different `AdbSubprocessProtocol` has different capabilities, thus requires specific adaptations.
|
|
8
|
+
* Check their documentations for details.
|
|
9
|
+
*
|
|
10
|
+
* The first protocol whose `isSupported` returns `true` will be used.
|
|
11
|
+
* If no `AdbSubprocessProtocol` is supported, an error will be thrown.
|
|
12
|
+
*
|
|
13
|
+
* @default [AdbSubprocessShellProtocol, AdbSubprocessNoneProtocol]
|
|
14
|
+
*/
|
|
15
|
+
protocols: AdbSubprocessProtocolConstructor[];
|
|
16
|
+
}
|
|
17
|
+
export interface AdbSubprocessWaitResult {
|
|
18
|
+
stdout: string;
|
|
19
|
+
stderr: string;
|
|
20
|
+
exitCode: number;
|
|
21
|
+
}
|
|
22
|
+
export declare class AdbSubprocess extends AdbCommandBase {
|
|
23
|
+
private createProtocol;
|
|
24
|
+
/**
|
|
25
|
+
* Spawns an executable in PTY (interactive) mode.
|
|
26
|
+
* @param command The command to run. If omitted, the default shell will be spawned.
|
|
27
|
+
* @param options The options for creating the `AdbSubprocessProtocol`
|
|
28
|
+
* @returns A new `AdbSubprocessProtocol` instance connecting to the spawned process.
|
|
29
|
+
*/
|
|
30
|
+
shell(command?: string | string[], options?: Partial<AdbSubprocessOptions>): Promise<AdbSubprocessProtocol>;
|
|
31
|
+
/**
|
|
32
|
+
* Spawns an executable and pipe the output.
|
|
33
|
+
* @param command The command to run, or an array of strings containing both command and args.
|
|
34
|
+
* @param options The options for creating the `AdbSubprocessProtocol`
|
|
35
|
+
* @returns A new `AdbSubprocessProtocol` instance connecting to the spawned process.
|
|
36
|
+
*/
|
|
37
|
+
spawn(command: string | string[], options?: Partial<AdbSubprocessOptions>): Promise<AdbSubprocessProtocol>;
|
|
38
|
+
/**
|
|
39
|
+
* Spawns a new process, waits until it exits, and returns the entire output.
|
|
40
|
+
* @param command The command to run
|
|
41
|
+
* @param options The options for creating the `AdbSubprocessProtocol`
|
|
42
|
+
* @returns The entire output of the command
|
|
43
|
+
*/
|
|
44
|
+
spawnAndWait(command: string | string[], options?: Partial<AdbSubprocessOptions>): Promise<AdbSubprocessWaitResult>;
|
|
45
|
+
/**
|
|
46
|
+
* Spawns a new process, waits until it exits, and returns the entire output.
|
|
47
|
+
* @param command The command to run
|
|
48
|
+
* @returns The entire output of the command
|
|
49
|
+
*/
|
|
50
|
+
spawnAndWaitLegacy(command: string | string[]): Promise<string>;
|
|
51
|
+
}
|
|
52
|
+
//# sourceMappingURL=command.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"command.d.ts","sourceRoot":"","sources":["../../../src/commands/subprocess/command.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,cAAc,EAAE,MAAM,YAAY,CAAC;AAE5C,OAAO,EAGH,KAAK,qBAAqB,EAC1B,KAAK,gCAAgC,EACxC,MAAM,sBAAsB,CAAC;AAE9B,MAAM,WAAW,oBAAoB;IACjC;;;;;;;;;;OAUG;IACH,SAAS,EAAE,gCAAgC,EAAE,CAAC;CACjD;AAMD,MAAM,WAAW,uBAAuB;IACpC,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;CACpB;AAED,qBAAa,aAAc,SAAQ,cAAc;YAC/B,cAAc;IA6B5B;;;;;OAKG;IACI,KAAK,CACR,OAAO,CAAC,EAAE,MAAM,GAAG,MAAM,EAAE,EAC3B,OAAO,CAAC,EAAE,OAAO,CAAC,oBAAoB,CAAC,GACxC,OAAO,CAAC,qBAAqB,CAAC;IAIjC;;;;;OAKG;IACI,KAAK,CACR,OAAO,EAAE,MAAM,GAAG,MAAM,EAAE,EAC1B,OAAO,CAAC,EAAE,OAAO,CAAC,oBAAoB,CAAC,GACxC,OAAO,CAAC,qBAAqB,CAAC;IAIjC;;;;;OAKG;IACU,YAAY,CACrB,OAAO,EAAE,MAAM,GAAG,MAAM,EAAE,EAC1B,OAAO,CAAC,EAAE,OAAO,CAAC,oBAAoB,CAAC,GACxC,OAAO,CAAC,uBAAuB,CAAC;IAmBnC;;;;OAIG;IACU,kBAAkB,CAC3B,OAAO,EAAE,MAAM,GAAG,MAAM,EAAE,GAC3B,OAAO,CAAC,MAAM,CAAC;CAMrB"}
|
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
import { DecodeUtf8Stream, GatherStringStream } from "@yume-chan/stream-extra";
|
|
2
|
+
import { AdbCommandBase } from "../base.js";
|
|
3
|
+
import { AdbSubprocessNoneProtocol, AdbSubprocessShellProtocol, } from "./protocols/index.js";
|
|
4
|
+
const DEFAULT_OPTIONS = {
|
|
5
|
+
protocols: [AdbSubprocessShellProtocol, AdbSubprocessNoneProtocol],
|
|
6
|
+
};
|
|
7
|
+
export class AdbSubprocess extends AdbCommandBase {
|
|
8
|
+
async createProtocol(mode, command, options) {
|
|
9
|
+
const { protocols } = { ...DEFAULT_OPTIONS, ...options };
|
|
10
|
+
let Constructor;
|
|
11
|
+
for (const item of protocols) {
|
|
12
|
+
// It's async so can't use `Array#find`
|
|
13
|
+
if (await item.isSupported(this.adb)) {
|
|
14
|
+
Constructor = item;
|
|
15
|
+
break;
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
if (!Constructor) {
|
|
19
|
+
throw new Error("No specified protocol is supported by the device");
|
|
20
|
+
}
|
|
21
|
+
if (Array.isArray(command)) {
|
|
22
|
+
command = command.join(" ");
|
|
23
|
+
}
|
|
24
|
+
else if (command === undefined) {
|
|
25
|
+
// spawn the default shell
|
|
26
|
+
command = "";
|
|
27
|
+
}
|
|
28
|
+
return await Constructor[mode](this.adb, command);
|
|
29
|
+
}
|
|
30
|
+
/**
|
|
31
|
+
* Spawns an executable in PTY (interactive) mode.
|
|
32
|
+
* @param command The command to run. If omitted, the default shell will be spawned.
|
|
33
|
+
* @param options The options for creating the `AdbSubprocessProtocol`
|
|
34
|
+
* @returns A new `AdbSubprocessProtocol` instance connecting to the spawned process.
|
|
35
|
+
*/
|
|
36
|
+
shell(command, options) {
|
|
37
|
+
return this.createProtocol("pty", command, options);
|
|
38
|
+
}
|
|
39
|
+
/**
|
|
40
|
+
* Spawns an executable and pipe the output.
|
|
41
|
+
* @param command The command to run, or an array of strings containing both command and args.
|
|
42
|
+
* @param options The options for creating the `AdbSubprocessProtocol`
|
|
43
|
+
* @returns A new `AdbSubprocessProtocol` instance connecting to the spawned process.
|
|
44
|
+
*/
|
|
45
|
+
spawn(command, options) {
|
|
46
|
+
return this.createProtocol("raw", command, options);
|
|
47
|
+
}
|
|
48
|
+
/**
|
|
49
|
+
* Spawns a new process, waits until it exits, and returns the entire output.
|
|
50
|
+
* @param command The command to run
|
|
51
|
+
* @param options The options for creating the `AdbSubprocessProtocol`
|
|
52
|
+
* @returns The entire output of the command
|
|
53
|
+
*/
|
|
54
|
+
async spawnAndWait(command, options) {
|
|
55
|
+
const shell = await this.spawn(command, options);
|
|
56
|
+
const stdout = new GatherStringStream();
|
|
57
|
+
const stderr = new GatherStringStream();
|
|
58
|
+
const [, , exitCode] = await Promise.all([
|
|
59
|
+
shell.stdout.pipeThrough(new DecodeUtf8Stream()).pipeTo(stdout),
|
|
60
|
+
shell.stderr.pipeThrough(new DecodeUtf8Stream()).pipeTo(stderr),
|
|
61
|
+
shell.exit,
|
|
62
|
+
]);
|
|
63
|
+
return {
|
|
64
|
+
stdout: stdout.result,
|
|
65
|
+
stderr: stderr.result,
|
|
66
|
+
exitCode,
|
|
67
|
+
};
|
|
68
|
+
}
|
|
69
|
+
/**
|
|
70
|
+
* Spawns a new process, waits until it exits, and returns the entire output.
|
|
71
|
+
* @param command The command to run
|
|
72
|
+
* @returns The entire output of the command
|
|
73
|
+
*/
|
|
74
|
+
async spawnAndWaitLegacy(command) {
|
|
75
|
+
const { stdout } = await this.spawnAndWait(command, {
|
|
76
|
+
protocols: [AdbSubprocessNoneProtocol],
|
|
77
|
+
});
|
|
78
|
+
return stdout;
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
//# sourceMappingURL=command.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"command.js","sourceRoot":"","sources":["../../../src/commands/subprocess/command.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,gBAAgB,EAAE,kBAAkB,EAAE,MAAM,yBAAyB,CAAC;AAE/E,OAAO,EAAE,cAAc,EAAE,MAAM,YAAY,CAAC;AAE5C,OAAO,EACH,yBAAyB,EACzB,0BAA0B,GAG7B,MAAM,sBAAsB,CAAC;AAiB9B,MAAM,eAAe,GAAyB;IAC1C,SAAS,EAAE,CAAC,0BAA0B,EAAE,yBAAyB,CAAC;CACrE,CAAC;AAQF,MAAM,OAAO,aAAc,SAAQ,cAAc;IACrC,KAAK,CAAC,cAAc,CACxB,IAAmB,EACnB,OAA2B,EAC3B,OAAuC;QAEvC,MAAM,EAAE,SAAS,EAAE,GAAG,EAAE,GAAG,eAAe,EAAE,GAAG,OAAO,EAAE,CAAC;QAEzD,IAAI,WAAyD,CAAC;QAC9D,KAAK,MAAM,IAAI,IAAI,SAAS,EAAE;YAC1B,uCAAuC;YACvC,IAAI,MAAM,IAAI,CAAC,WAAW,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE;gBAClC,WAAW,GAAG,IAAI,CAAC;gBACnB,MAAM;aACT;SACJ;QAED,IAAI,CAAC,WAAW,EAAE;YACd,MAAM,IAAI,KAAK,CAAC,kDAAkD,CAAC,CAAC;SACvE;QAED,IAAI,KAAK,CAAC,OAAO,CAAC,OAAO,CAAC,EAAE;YACxB,OAAO,GAAG,OAAO,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;SAC/B;aAAM,IAAI,OAAO,KAAK,SAAS,EAAE;YAC9B,0BAA0B;YAC1B,OAAO,GAAG,EAAE,CAAC;SAChB;QACD,OAAO,MAAM,WAAW,CAAC,IAAI,CAAC,CAAC,IAAI,CAAC,GAAG,EAAE,OAAO,CAAC,CAAC;IACtD,CAAC;IAED;;;;;OAKG;IACI,KAAK,CACR,OAA2B,EAC3B,OAAuC;QAEvC,OAAO,IAAI,CAAC,cAAc,CAAC,KAAK,EAAE,OAAO,EAAE,OAAO,CAAC,CAAC;IACxD,CAAC;IAED;;;;;OAKG;IACI,KAAK,CACR,OAA0B,EAC1B,OAAuC;QAEvC,OAAO,IAAI,CAAC,cAAc,CAAC,KAAK,EAAE,OAAO,EAAE,OAAO,CAAC,CAAC;IACxD,CAAC;IAED;;;;;OAKG;IACI,KAAK,CAAC,YAAY,CACrB,OAA0B,EAC1B,OAAuC;QAEvC,MAAM,KAAK,GAAG,MAAM,IAAI,CAAC,KAAK,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;QAEjD,MAAM,MAAM,GAAG,IAAI,kBAAkB,EAAE,CAAC;QACxC,MAAM,MAAM,GAAG,IAAI,kBAAkB,EAAE,CAAC;QAExC,MAAM,CAAC,EAAE,AAAD,EAAG,QAAQ,CAAC,GAAG,MAAM,OAAO,CAAC,GAAG,CAAC;YACrC,KAAK,CAAC,MAAM,CAAC,WAAW,CAAC,IAAI,gBAAgB,EAAE,CAAC,CAAC,MAAM,CAAC,MAAM,CAAC;YAC/D,KAAK,CAAC,MAAM,CAAC,WAAW,CAAC,IAAI,gBAAgB,EAAE,CAAC,CAAC,MAAM,CAAC,MAAM,CAAC;YAC/D,KAAK,CAAC,IAAI;SACb,CAAC,CAAC;QAEH,OAAO;YACH,MAAM,EAAE,MAAM,CAAC,MAAM;YACrB,MAAM,EAAE,MAAM,CAAC,MAAM;YACrB,QAAQ;SACX,CAAC;IACN,CAAC;IAED;;;;OAIG;IACI,KAAK,CAAC,kBAAkB,CAC3B,OAA0B;QAE1B,MAAM,EAAE,MAAM,EAAE,GAAG,MAAM,IAAI,CAAC,YAAY,CAAC,OAAO,EAAE;YAChD,SAAS,EAAE,CAAC,yBAAyB,CAAC;SACzC,CAAC,CAAC;QACH,OAAO,MAAM,CAAC;IAClB,CAAC;CACJ"}
|
|
@@ -1,56 +1,4 @@
|
|
|
1
|
-
|
|
2
|
-
import { type AdbSubprocessProtocol, type AdbSubprocessProtocolConstructor } from './protocols/index.js';
|
|
1
|
+
export * from './command.js';
|
|
3
2
|
export * from './protocols/index.js';
|
|
4
3
|
export * from './utils.js';
|
|
5
|
-
export interface AdbSubprocessOptions {
|
|
6
|
-
/**
|
|
7
|
-
* A list of `AdbSubprocessProtocolConstructor`s to be used.
|
|
8
|
-
*
|
|
9
|
-
* Different `AdbSubprocessProtocol` has different capabilities, thus requires specific adaptations.
|
|
10
|
-
* Check their documentations for details.
|
|
11
|
-
*
|
|
12
|
-
* The first protocol whose `isSupported` returns `true` will be used.
|
|
13
|
-
* If no `AdbSubprocessProtocol` is supported, an error will be thrown.
|
|
14
|
-
*
|
|
15
|
-
* @default [AdbSubprocessShellProtocol, AdbSubprocessNoneProtocol]
|
|
16
|
-
*/
|
|
17
|
-
protocols: AdbSubprocessProtocolConstructor[];
|
|
18
|
-
}
|
|
19
|
-
export interface AdbSubprocessWaitResult {
|
|
20
|
-
stdout: string;
|
|
21
|
-
stderr: string;
|
|
22
|
-
exitCode: number;
|
|
23
|
-
}
|
|
24
|
-
export declare class AdbSubprocess {
|
|
25
|
-
readonly adb: Adb;
|
|
26
|
-
constructor(adb: Adb);
|
|
27
|
-
private createProtocol;
|
|
28
|
-
/**
|
|
29
|
-
* Spawns an executable in PTY (interactive) mode.
|
|
30
|
-
* @param command The command to run. If omitted, the default shell will be spawned.
|
|
31
|
-
* @param options The options for creating the `AdbSubprocessProtocol`
|
|
32
|
-
* @returns A new `AdbSubprocessProtocol` instance connecting to the spawned process.
|
|
33
|
-
*/
|
|
34
|
-
shell(command?: string | string[], options?: Partial<AdbSubprocessOptions>): Promise<AdbSubprocessProtocol>;
|
|
35
|
-
/**
|
|
36
|
-
* Spawns an executable and pipe the output.
|
|
37
|
-
* @param command The command to run, or an array of strings containing both command and args.
|
|
38
|
-
* @param options The options for creating the `AdbSubprocessProtocol`
|
|
39
|
-
* @returns A new `AdbSubprocessProtocol` instance connecting to the spawned process.
|
|
40
|
-
*/
|
|
41
|
-
spawn(command: string | string[], options?: Partial<AdbSubprocessOptions>): Promise<AdbSubprocessProtocol>;
|
|
42
|
-
/**
|
|
43
|
-
* Spawns a new process, waits until it exits, and returns the entire output.
|
|
44
|
-
* @param command The command to run
|
|
45
|
-
* @param options The options for creating the `AdbSubprocessProtocol`
|
|
46
|
-
* @returns The entire output of the command
|
|
47
|
-
*/
|
|
48
|
-
spawnAndWait(command: string | string[], options?: Partial<AdbSubprocessOptions>): Promise<AdbSubprocessWaitResult>;
|
|
49
|
-
/**
|
|
50
|
-
* Spawns a new process, waits until it exits, and returns the entire output.
|
|
51
|
-
* @param command The command to run
|
|
52
|
-
* @returns The entire output of the command
|
|
53
|
-
*/
|
|
54
|
-
spawnAndWaitLegacy(command: string | string[]): Promise<string>;
|
|
55
|
-
}
|
|
56
4
|
//# sourceMappingURL=index.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/commands/subprocess/index.ts"],"names":[],"mappings":"AAAA,
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/commands/subprocess/index.ts"],"names":[],"mappings":"AAAA,cAAc,cAAc,CAAC;AAC7B,cAAc,sBAAsB,CAAC;AACrC,cAAc,YAAY,CAAC"}
|
|
@@ -1,88 +1,4 @@
|
|
|
1
|
-
|
|
2
|
-
import { AdbSubprocessNoneProtocol, AdbSubprocessShellProtocol } from './protocols/index.js';
|
|
1
|
+
export * from './command.js';
|
|
3
2
|
export * from './protocols/index.js';
|
|
4
3
|
export * from './utils.js';
|
|
5
|
-
const DEFAULT_OPTIONS = {
|
|
6
|
-
protocols: [AdbSubprocessShellProtocol, AdbSubprocessNoneProtocol],
|
|
7
|
-
};
|
|
8
|
-
export class AdbSubprocess {
|
|
9
|
-
adb;
|
|
10
|
-
constructor(adb) {
|
|
11
|
-
this.adb = adb;
|
|
12
|
-
}
|
|
13
|
-
async createProtocol(mode, command, options) {
|
|
14
|
-
const { protocols } = { ...DEFAULT_OPTIONS, ...options };
|
|
15
|
-
let Constructor;
|
|
16
|
-
for (const item of protocols) {
|
|
17
|
-
// It's async so can't use `Array#find`
|
|
18
|
-
if (await item.isSupported(this.adb)) {
|
|
19
|
-
Constructor = item;
|
|
20
|
-
break;
|
|
21
|
-
}
|
|
22
|
-
}
|
|
23
|
-
if (!Constructor) {
|
|
24
|
-
throw new Error('No specified protocol is supported by the device');
|
|
25
|
-
}
|
|
26
|
-
if (Array.isArray(command)) {
|
|
27
|
-
command = command.join(' ');
|
|
28
|
-
}
|
|
29
|
-
else if (command === undefined) {
|
|
30
|
-
// spawn the default shell
|
|
31
|
-
command = '';
|
|
32
|
-
}
|
|
33
|
-
return await Constructor[mode](this.adb, command);
|
|
34
|
-
}
|
|
35
|
-
/**
|
|
36
|
-
* Spawns an executable in PTY (interactive) mode.
|
|
37
|
-
* @param command The command to run. If omitted, the default shell will be spawned.
|
|
38
|
-
* @param options The options for creating the `AdbSubprocessProtocol`
|
|
39
|
-
* @returns A new `AdbSubprocessProtocol` instance connecting to the spawned process.
|
|
40
|
-
*/
|
|
41
|
-
shell(command, options) {
|
|
42
|
-
return this.createProtocol('pty', command, options);
|
|
43
|
-
}
|
|
44
|
-
/**
|
|
45
|
-
* Spawns an executable and pipe the output.
|
|
46
|
-
* @param command The command to run, or an array of strings containing both command and args.
|
|
47
|
-
* @param options The options for creating the `AdbSubprocessProtocol`
|
|
48
|
-
* @returns A new `AdbSubprocessProtocol` instance connecting to the spawned process.
|
|
49
|
-
*/
|
|
50
|
-
spawn(command, options) {
|
|
51
|
-
return this.createProtocol('raw', command, options);
|
|
52
|
-
}
|
|
53
|
-
/**
|
|
54
|
-
* Spawns a new process, waits until it exits, and returns the entire output.
|
|
55
|
-
* @param command The command to run
|
|
56
|
-
* @param options The options for creating the `AdbSubprocessProtocol`
|
|
57
|
-
* @returns The entire output of the command
|
|
58
|
-
*/
|
|
59
|
-
async spawnAndWait(command, options) {
|
|
60
|
-
const shell = await this.spawn(command, options);
|
|
61
|
-
const stdout = new GatherStringStream();
|
|
62
|
-
const stderr = new GatherStringStream();
|
|
63
|
-
const [, , exitCode] = await Promise.all([
|
|
64
|
-
shell.stdout
|
|
65
|
-
.pipeThrough(new DecodeUtf8Stream())
|
|
66
|
-
.pipeTo(stdout),
|
|
67
|
-
shell.stderr
|
|
68
|
-
.pipeThrough(new DecodeUtf8Stream())
|
|
69
|
-
.pipeTo(stderr),
|
|
70
|
-
shell.exit
|
|
71
|
-
]);
|
|
72
|
-
return {
|
|
73
|
-
stdout: stdout.result,
|
|
74
|
-
stderr: stderr.result,
|
|
75
|
-
exitCode,
|
|
76
|
-
};
|
|
77
|
-
}
|
|
78
|
-
/**
|
|
79
|
-
* Spawns a new process, waits until it exits, and returns the entire output.
|
|
80
|
-
* @param command The command to run
|
|
81
|
-
* @returns The entire output of the command
|
|
82
|
-
*/
|
|
83
|
-
async spawnAndWaitLegacy(command) {
|
|
84
|
-
const { stdout } = await this.spawnAndWait(command, { protocols: [AdbSubprocessNoneProtocol] });
|
|
85
|
-
return stdout;
|
|
86
|
-
}
|
|
87
|
-
}
|
|
88
4
|
//# sourceMappingURL=index.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/commands/subprocess/index.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/commands/subprocess/index.ts"],"names":[],"mappings":"AAAA,cAAc,cAAc,CAAC;AAC7B,cAAc,sBAAsB,CAAC;AACrC,cAAc,YAAY,CAAC"}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
import
|
|
2
|
-
import type
|
|
3
|
-
import {
|
|
4
|
-
import type
|
|
1
|
+
import { ReadableStream } from '@yume-chan/stream-extra';
|
|
2
|
+
import { type Adb } from "../../../adb.js";
|
|
3
|
+
import { type AdbSocket } from "../../../socket/index.js";
|
|
4
|
+
import { type AdbSubprocessProtocol } from "./types.js";
|
|
5
5
|
/**
|
|
6
6
|
* The legacy shell
|
|
7
7
|
*
|
|
@@ -16,7 +16,7 @@ export declare class AdbSubprocessNoneProtocol implements AdbSubprocessProtocol
|
|
|
16
16
|
static raw(adb: Adb, command: string): Promise<AdbSubprocessNoneProtocol>;
|
|
17
17
|
private readonly socket;
|
|
18
18
|
private readonly duplex;
|
|
19
|
-
get stdin(): import("
|
|
19
|
+
get stdin(): import("@yume-chan/stream-extra").WritableStream<Uint8Array>;
|
|
20
20
|
private _stdout;
|
|
21
21
|
/**
|
|
22
22
|
* Legacy shell mixes stdout and stderr.
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"none.d.ts","sourceRoot":"","sources":["../../../../src/commands/subprocess/protocols/none.ts"],"names":[],"mappings":"AAAA,OAAO,
|
|
1
|
+
{"version":3,"file":"none.d.ts","sourceRoot":"","sources":["../../../../src/commands/subprocess/protocols/none.ts"],"names":[],"mappings":"AAAA,OAAO,EAAuB,cAAc,EAAE,MAAM,yBAAyB,CAAC;AAE9E,OAAO,EAAE,KAAK,GAAG,EAAE,MAAM,iBAAiB,CAAC;AAC3C,OAAO,EAAE,KAAK,SAAS,EAAE,MAAM,0BAA0B,CAAC;AAE1D,OAAO,EAAE,KAAK,qBAAqB,EAAE,MAAM,YAAY,CAAC;AAExD;;;;;;;GAOG;AACH,qBAAa,yBAA0B,YAAW,qBAAqB;WACrD,WAAW;WAEL,GAAG,CAAC,GAAG,EAAE,GAAG,EAAE,OAAO,EAAE,MAAM;WAI7B,GAAG,CAAC,GAAG,EAAE,GAAG,EAAE,OAAO,EAAE,MAAM;IAMjD,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAY;IAEnC,OAAO,CAAC,QAAQ,CAAC,MAAM,CAA8C;IAGrE,IAAW,KAAK,iEAAmC;IAEnD,OAAO,CAAC,OAAO,CAA6B;IAC5C;;OAEG;IACH,IAAW,MAAM,+BAA2B;IAE5C,OAAO,CAAC,OAAO,CAA6B;IAC5C;;OAEG;IACH,IAAW,MAAM,+BAA2B;IAE5C,OAAO,CAAC,KAAK,CAAkB;IAC/B,IAAW,IAAI,oBAAyB;gBAErB,MAAM,EAAE,SAAS;IAgB7B,MAAM;IAIN,IAAI;CAGd"}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { DuplexStreamFactory, ReadableStream } from
|
|
1
|
+
import { DuplexStreamFactory, ReadableStream } from '@yume-chan/stream-extra';
|
|
2
2
|
/**
|
|
3
3
|
* The legacy shell
|
|
4
4
|
*
|
|
@@ -14,7 +14,7 @@ export class AdbSubprocessNoneProtocol {
|
|
|
14
14
|
}
|
|
15
15
|
static async raw(adb, command) {
|
|
16
16
|
// `shell,raw:${command}` also triggers raw mode,
|
|
17
|
-
// But is not supported
|
|
17
|
+
// But is not supported on Android version <7.
|
|
18
18
|
return new AdbSubprocessNoneProtocol(await adb.createSocket(`exec:${command}`));
|
|
19
19
|
}
|
|
20
20
|
socket;
|
|
@@ -35,6 +35,8 @@ export class AdbSubprocessNoneProtocol {
|
|
|
35
35
|
get exit() { return this._exit; }
|
|
36
36
|
constructor(socket) {
|
|
37
37
|
this.socket = socket;
|
|
38
|
+
// Link `stdout`, `stderr` and `stdin` together,
|
|
39
|
+
// so closing any of them will close the others.
|
|
38
40
|
this.duplex = new DuplexStreamFactory({
|
|
39
41
|
close: async () => {
|
|
40
42
|
await this.socket.close();
|
|
@@ -45,7 +47,7 @@ export class AdbSubprocessNoneProtocol {
|
|
|
45
47
|
this._exit = this.duplex.closed.then(() => 0);
|
|
46
48
|
}
|
|
47
49
|
resize() {
|
|
48
|
-
// Not supported
|
|
50
|
+
// Not supported, but don't throw.
|
|
49
51
|
}
|
|
50
52
|
kill() {
|
|
51
53
|
return this.duplex.close();
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"none.js","sourceRoot":"","sources":["../../../../src/commands/subprocess/protocols/none.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"none.js","sourceRoot":"","sources":["../../../../src/commands/subprocess/protocols/none.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,mBAAmB,EAAE,cAAc,EAAE,MAAM,yBAAyB,CAAC;AAO9E;;;;;;;GAOG;AACH,MAAM,OAAO,yBAAyB;IAC3B,MAAM,CAAC,WAAW,KAAK,OAAO,IAAI,CAAC,CAAC,CAAC;IAErC,MAAM,CAAC,KAAK,CAAC,GAAG,CAAC,GAAQ,EAAE,OAAe;QAC7C,OAAO,IAAI,yBAAyB,CAAC,MAAM,GAAG,CAAC,YAAY,CAAC,SAAS,OAAO,EAAE,CAAC,CAAC,CAAC;IACrF,CAAC;IAEM,MAAM,CAAC,KAAK,CAAC,GAAG,CAAC,GAAQ,EAAE,OAAe;QAC7C,iDAAiD;QACjD,8CAA8C;QAC9C,OAAO,IAAI,yBAAyB,CAAC,MAAM,GAAG,CAAC,YAAY,CAAC,QAAQ,OAAO,EAAE,CAAC,CAAC,CAAC;IACpF,CAAC;IAEgB,MAAM,CAAY;IAElB,MAAM,CAA8C;IAErE,2CAA2C;IAC3C,IAAW,KAAK,KAAK,OAAO,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC,CAAC;IAE3C,OAAO,CAA6B;IAC5C;;OAEG;IACH,IAAW,MAAM,KAAK,OAAO,IAAI,CAAC,OAAO,CAAC,CAAC,CAAC;IAEpC,OAAO,CAA6B;IAC5C;;OAEG;IACH,IAAW,MAAM,KAAK,OAAO,IAAI,CAAC,OAAO,CAAC,CAAC,CAAC;IAEpC,KAAK,CAAkB;IAC/B,IAAW,IAAI,KAAK,OAAO,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC;IAExC,YAAmB,MAAiB;QAChC,IAAI,CAAC,MAAM,GAAG,MAAM,CAAC;QAErB,gDAAgD;QAChD,gDAAgD;QAChD,IAAI,CAAC,MAAM,GAAG,IAAI,mBAAmB,CAAyB;YAC1D,KAAK,EAAE,KAAK,IAAI,EAAE;gBACd,MAAM,IAAI,CAAC,MAAM,CAAC,KAAK,EAAE,CAAC;YAC9B,CAAC;SACJ,CAAC,CAAC;QAEH,IAAI,CAAC,OAAO,GAAG,IAAI,CAAC,MAAM,CAAC,YAAY,CAAC,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC;QAC9D,IAAI,CAAC,OAAO,GAAG,IAAI,CAAC,MAAM,CAAC,YAAY,CAAC,IAAI,cAAc,EAAE,CAAC,CAAC;QAC9D,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,EAAE,CAAC,CAAC,CAAC,CAAC;IAClD,CAAC;IAEM,MAAM;QACT,kCAAkC;IACtC,CAAC;IAEM,IAAI;QACP,OAAO,IAAI,CAAC,MAAM,CAAC,KAAK,EAAE,CAAC;IAC/B,CAAC;CACJ"}
|