Android - создайте символическую ссылку в приложении
Я хочу создать программно символическую ссылку в моем приложении. Возможно ли это в Android (4.4+)?
В Java мы можем использовать:
Path newLink = ...;
Path target = ...;
try {
Files.createSymbolicLink(newLink, target);
} catch (IOException x) {
System.err.println(x);
} catch (UnsupportedOperationException x) {
// Some file systems do not support symbolic links.
System.err.println(x);
}
от java.nio.file
но что я должен использовать в Android?
https://docs.oracle.com/javase/tutorial/essential/io/links.html
РЕДАКТИРОВАТЬ:
Я тестировал используя reflection/native code/OS.symlink() method
и ничего не работает. Я всегда получаю Операцию не разрешено (EPERM). Я думаю, что вы должны иметь права root для создания символической ссылки.
Проблема может быть с этим /mnt/sdcard
это прокладка FUSE, которая оборачивает /data/media/xxx
, Итак, я начал использовать /data/media/xxx
но я всегда получаю Permission denied
Я думаю, что это проблема с рут правами.
2 ответа
Вот решение, которое сработало для меня, которое возвращает true, если успешно:
public static boolean createSymLink(String symLinkFilePath, String originalFilePath) {
try {
if (VERSION.SDK_INT >= VERSION_CODES.LOLLIPOP) {
Os.symlink(originalFilePath, symLinkFilePath);
return true;
}
final Class<?> libcore = Class.forName("libcore.io.Libcore");
final java.lang.reflect.Field fOs = libcore.getDeclaredField("os");
fOs.setAccessible(true);
final Object os = fOs.get(null);
final java.lang.reflect.Method method = os.getClass().getMethod("symlink", String.class, String.class);
method.invoke(os, originalFilePath, symLinkFilePath);
return true;
} catch (Exception e) {
e.printStackTrace();
}
return false;
}
Или в Котлине:
companion object {
@JvmStatic
fun createSymLink(symLinkFilePath: String, originalFilePath: String): Boolean {
try {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
Os.symlink(originalFilePath, symLinkFilePath)
return true
}
val libcore = Class.forName("libcore.io.Libcore")
val fOs = libcore.getDeclaredField("os")
fOs.isAccessible = true
val os = fOs.get(null)
val method = os.javaClass.getMethod("symlink", String::class.java, String::class.java)
method.invoke(os, originalFilePath, symLinkFilePath)
return true
} catch (e: Exception) {
e.printStackTrace()
}
return false
}
}
Теперь у Android есть системные вызовы, которые вы можете использовать. Вот
android.system.Os.symlink
есть также
java.nio.file.Files.createSymbolicLink
метод
но я думаю, что это действительно не сработало для вас