Android应用中无法通过代码执行Shell脚本问题求助
解决Android代码中执行本地Shell脚本的问题
错误原因
你在Android代码里调用了电脑端的adb命令路径/opt/homebrew/bin/adb,但Android应用运行在设备内部,这个路径根本不存在,这是触发No such file or directory异常的直接原因。Android应用执行设备本地Shell命令,无需通过adb,直接调用系统自带的Shell工具即可。
第一步:修正Shell脚本
你的脚本存在两个问题:重复的shebang、路径拼写错误。修正后脚本如下:
#!/system/bin/sh echo "Hello from testSharath.sh" ps -e
- 仅保留一个正确的shebang:
/system/bin/sh是Android设备默认的Shell路径; - 移除错误的
#!/system/bib/sh(路径里的bib是笔误,应为bin)。
第二步:修正Android执行代码
直接调用设备内部的Shell命令完成权限修改与脚本执行,同时处理输出流避免进程阻塞:
private void testShellScript() { File testPath = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS); String fileName = "testSharath.sh"; File scriptFilePath = new File(testPath, fileName); String scriptPath = scriptFilePath.getAbsolutePath(); try { // 给脚本添加执行权限(非root设备可跳过此步,直接用sh运行脚本) Process chmodProcess = Runtime.getRuntime().exec(new String[]{ "sh", "-c", "chmod +x " + scriptPath }); chmodProcess.waitFor(); // 等待权限修改完成 // 执行脚本 Process scriptProcess = Runtime.getRuntime().exec(new String[]{ "sh", scriptPath }); // 读取标准输出 BufferedReader stdoutReader = new BufferedReader( new InputStreamReader(scriptProcess.getInputStream()) ); // 读取错误输出(必须处理,否则输出缓冲区满时进程会阻塞) BufferedReader stderrReader = new BufferedReader( new InputStreamReader(scriptProcess.getErrorStream()) ); String line; System.out.println("脚本标准输出:"); while ((line = stdoutReader.readLine()) != null) { System.out.println("Sharath@@@@@@" + line); } System.out.println("脚本错误输出:"); while ((line = stderrReader.readLine()) != null) { System.err.println("Sharath@@@@@@" + line); } // 关闭流 stdoutReader.close(); stderrReader.close(); // 获取脚本执行退出码 int exitCode = scriptProcess.waitFor(); System.out.println("脚本执行完成,退出码:" + exitCode); } catch (IOException | InterruptedException e) { e.printStackTrace(); } }
关键注意事项
- 权限处理:
- Android 6.0(API 23)及以上需动态申请
READ_EXTERNAL_STORAGE、WRITE_EXTERNAL_STORAGE权限;Android 10+若访问公共Download目录,可能需要MANAGE_EXTERNAL_STORAGE权限,或考虑将脚本放在应用私有目录避免权限问题。 - 若设备未root,
chmod +x操作可能失败,此时直接用sh scriptPath运行脚本即可。
- Android 6.0(API 23)及以上需动态申请
- 路径验证:可通过
Log.d("ScriptDebug", scriptPath)打印路径,确认脚本实际存在。 - 流处理:必须同时读取标准输出和错误输出,否则进程会因输出缓冲区满而卡住。
内容的提问来源于stack exchange,提问作者kgsharathkumar
相关产品推荐
相关产品推荐

