From 11f8b7625788d747eaadd59af6efdf88587ed058 Mon Sep 17 00:00:00 2001 From: Avocado Date: Tue, 13 Oct 2026 19:20:03 +1100 Subject: [PATCH] fix(apktool): accept --no-strings CLI option (#2707) --- src/cli/apktoolCommands.ts | 10 ++- .../cli/apktoolBooleanOptions.test.ts | 85 +++++++++++++++++++ 2 files changed, 91 insertions(+), 4 deletions(-) create mode 100644 tests/boundary/cli/apktoolBooleanOptions.test.ts diff --git a/src/cli/apktoolCommands.ts b/src/cli/apktoolCommands.ts index d7b30a6170..c7795f9d4f 100644 --- a/src/cli/apktoolCommands.ts +++ b/src/cli/apktoolCommands.ts @@ -62,15 +62,17 @@ export const registerApktoolCommands = ( .describe( "Project strings from res/values- instead of the default", ), - "no-strings": z + strings: z .boolean() - .default(false) - .describe("Skip projecting string resources"), + .default(true) + .describe( + "Include string resources; use --no-strings to skip projecting them", + ), }), run: ({ args, options }) => execute(CLI_COMMANDS.decodeAndroidResources, "decode_android_resources", { path: args.path, - include_strings: !options["no-strings"], + include_strings: options.strings, ...(options.locale === undefined ? {} : { locale: options.locale }), }), }); diff --git a/tests/boundary/cli/apktoolBooleanOptions.test.ts b/tests/boundary/cli/apktoolBooleanOptions.test.ts new file mode 100644 index 0000000000..5c5578c18a --- /dev/null +++ b/tests/boundary/cli/apktoolBooleanOptions.test.ts @@ -0,0 +1,85 @@ +import { expect, it } from "vitest"; +import { Cli } from "incur"; +import pino from "pino"; + +import type { ApktoolResourceAnalysisPort } from "../../../src/application/apktool/ApktoolResourceAnalysisPort.js"; +import { createAnalysisExecution } from "../../../src/application/AnalysisProvider.js"; +import { registerApktoolCommands } from "../../../src/cli/apktoolCommands.js"; +import { presentOmittableDefaults } from "../../../src/cli/omittableDefaults.js"; +import type { ApktoolRequest } from "../../../src/domain/apktool/apktoolResourceAnalysis.js"; +import { ok } from "../../../src/domain/result.js"; + +const invoke = async (argv: readonly string[]) => { + const requests: ApktoolRequest[] = []; + const provider: ApktoolResourceAnalysisPort = { + async inspectAvailability() { + throw new Error("unexpected provider probe"); + }, + async close() {}, + async execute(request) { + requests.push(request); + return ok( + createAnalysisExecution( + { strings: [] }, + { id: "apktool", name: "Apktool", version: null }, + ), + ); + }, + }; + const cli = Cli.create("rea", { sync: false }); + registerApktoolCommands(cli, pino({ level: "silent" }), {}, provider); + presentOmittableDefaults(cli); + + let stdout = ""; + let exitCode = 0; + await cli.serve([...argv], { + env: {}, + exit: (code) => { + exitCode = code; + }, + stdout: (text) => { + stdout += text; + }, + }); + return { exitCode, stdout, requests }; +}; + +it("dispatches --no-strings as include_strings false", async () => { + const result = await invoke([ + "decode-android-resources", + "/targets/app.apk", + "--no-strings", + "--json", + ]); + + expect(result.exitCode).toBe(0); + expect(result.requests).toEqual([ + { + operation: "decode_android_resources", + input: { path: "/targets/app.apk", include_strings: false }, + }, + ]); +}); + +it("keeps string projection enabled when the flag is omitted", async () => { + const result = await invoke([ + "decode-android-resources", + "/targets/app.apk", + "--json", + ]); + + expect(result.exitCode).toBe(0); + expect(result.requests).toEqual([ + { + operation: "decode_android_resources", + input: { path: "/targets/app.apk", include_strings: true }, + }, + ]); +}); + +it("documents the supported negative flag in command help", async () => { + const result = await invoke(["decode-android-resources", "--help"]); + + expect(result.exitCode).toBe(0); + expect(result.stdout).toContain("--no-strings"); +});