1
0
mirror of https://github.com/gryf/mc_adbfs.git synced 2025-12-18 20:10:21 +01:00

Added a functionality for accessing single directory

This commit is contained in:
2016-09-20 20:40:10 +02:00
parent ae08a7329a
commit 210d7f2962
2 changed files with 100 additions and 11 deletions

View File

@@ -13,7 +13,9 @@ Rquirements
* An Android device or emulator preferably rooted * An Android device or emulator preferably rooted
* Busybox installed and available in the path on the device * Busybox installed and available in the path on the device
Make sure, that issuing from command line:: Make sure, that issuing from command line:
.. code:: shell-session
$ adb shell busybox ls $ adb shell busybox ls
@@ -39,15 +41,43 @@ if needed.
Usage Usage
===== =====
To use it, just issue:: To use it, just issue:
cd adbfs:// .. code:: shell-session
cd adbfs://
under MC - after some time you should see the files and directories on your under MC - after some time you should see the files and directories on your
device. For convenience you can add a bookmark (accessible under CTRL+\) for device. For convenience you can add a bookmark (accessible under CTRL+\) for
fast access. The time is depended on how many files and directories you have on fast access. The time is depended on how many files and directories you have on
your device and how fast it is :) your device and how fast it is :)
Configuration
=============
You can use configure behaviour of this plugin using ``.ini`` file located under
``$XDG_CONFIG_HOME/mc/adbfs.ini`` (which usually is located under
``~/.config/mc/adbfs.ini``), and have default values, like:
.. code:: ini
[adbfs]
debug = false
skip_dirs = true
dirs_to_skip = ["acct", "charger", "d", "dev", "proc", "sys"]
root =
where:
* ``debug`` will provide a little bit more verbose information, useful for
debugging
* ``dirs_to_skip`` list of paths to directories which will be skipped during
reading. If leaved empty, or setted to empty list (``[]``) will read
everything (slow!)
* ``root`` root directory to read. Everything outside of that directory will be
omitted. That would be the fastest way to access certain location on the
device. Note, that ``dirs_to_skip`` still apply inside this directory.
Limitations Limitations
=========== ===========

75
adbfs
View File

@@ -54,8 +54,8 @@ class Conf(object):
def __init__(self): def __init__(self):
self.box = None self.box = None
self.debug = False self.debug = False
self.skip_dirs = True
self.dirs_to_skip = ["acct", "charger", "d", "dev", "proc", "sys"] self.dirs_to_skip = ["acct", "charger", "d", "dev", "proc", "sys"]
self.root = None
self.get_the_box() self.get_the_box()
self.read() self.read()
@@ -105,8 +105,8 @@ class Conf(object):
cfg = ConfigParser.SafeConfigParser() cfg = ConfigParser.SafeConfigParser()
cfg_map = {'debug': (cfg.getboolean, 'debug'), cfg_map = {'debug': (cfg.getboolean, 'debug'),
'skip_dirs': (cfg.getboolean, 'skip_dirs'), 'dirs_to_skip': (cfg.get, 'dirs_to_skip'),
'dirs_to_skip': (cfg.get, 'dirs_to_skip')} 'root': (cfg.get, 'root')}
cfg.read(conf_fname) cfg.read(conf_fname)
for key, (function, attr) in cfg_map.items(): for key, (function, attr) in cfg_map.items():
@@ -115,8 +115,11 @@ class Conf(object):
except (ConfigParser.NoSectionError, ConfigParser.NoOptionError): except (ConfigParser.NoSectionError, ConfigParser.NoOptionError):
pass pass
if isinstance(self.dirs_to_skip, str): if self.dirs_to_skip and isinstance(self.dirs_to_skip, str):
self.dirs_to_skip = json.loads(self.dirs_to_skip, encoding="ascii") self.dirs_to_skip = json.loads(self.dirs_to_skip, encoding="ascii")
self.dirs_to_skip = [x.encode('utf-8') for x in self.dirs_to_skip]
else:
self.dirs_to_skip = []
class File(object): class File(object):
@@ -227,7 +230,6 @@ class File(object):
class Adb(object): class Adb(object):
"""Class for interact with android rooted device through adb""" """Class for interact with android rooted device through adb"""
dirs_to_skip = ["acct", "charger", "d", "dev", "proc", "sys"]
file_re = None file_re = None
current_re = re.compile(r"^(\./)?(?P<dir>.+):$") current_re = re.compile(r"^(\./)?(?P<dir>.+):$")
@@ -294,10 +296,63 @@ class Adb(object):
for idx in sorted(elems_to_remove, reverse=True): for idx in sorted(elems_to_remove, reverse=True):
del self._entries[idx] del self._entries[idx]
def _retrieve_single_dir_list(self, dir_):
"""Retrieve file list using adb"""
command = ["adb", "shell", "su", "-c"]
command.append(self.conf.box['rls'].format(dir_))
try:
if self.conf.debug:
print "executing", " ".join(command)
lines = subprocess.check_output(command)
except subprocess.CalledProcessError:
sys.stderr.write("Cannot read directory. Is device connected?\n")
return 1
lines = [l.strip() for l in lines.split('\n') if l.strip()]
if len(lines) == 1:
reg_match = self.file_re.match(lines[0])
entry = File(**reg_match.groupdict())
entry.update('/')
if entry.filepath in self.conf.dirs_to_skip:
return
self._entries.append(entry)
if entry.type == "l":
self._links[entry.filepath] = entry
self._retrieve_single_dir_list(entry.link_target)
else:
for line in lines:
current_dir_re = self.current_re.match(line)
if current_dir_re:
current_dir = current_dir_re.groupdict()["dir"]
if not current_dir:
current_dir = "/"
continue
reg_match = self.file_re.match(line)
if not reg_match:
continue
entry = File(**reg_match.groupdict())
if entry.name in (".", ".."):
continue
entry.update(current_dir)
if entry.filepath in self.conf.dirs_to_skip:
continue
self._entries.append(entry)
if entry.type == "l":
self._links[entry.filepath] = entry
def _retrieve_file_list(self, root=None): def _retrieve_file_list(self, root=None):
"""Retrieve file list using adb""" """Retrieve file list using adb"""
command = ["adb", "shell", "su", "-c"] command = ["adb", "shell", "su", "-c"]
skip_dirs = self.conf.skip_dirs
if not root: if not root:
command.append(self.conf.box['ls']) command.append(self.conf.box['ls'])
@@ -333,7 +388,7 @@ class Adb(object):
entry.update(current_dir) entry.update(current_dir)
if skip_dirs and entry.filepath in self.conf.dirs_to_skip: if entry.filepath in self.conf.dirs_to_skip:
continue continue
self._entries.append(entry) self._entries.append(entry)
@@ -355,7 +410,11 @@ class Adb(object):
sys.stderr.write(self.error) sys.stderr.write(self.error)
return 1 return 1
self._retrieve_file_list() if self.conf.root:
self._retrieve_single_dir_list(self.conf.root)
else:
self._retrieve_file_list()
self._normalize_links() self._normalize_links()
# with open(os.path.join(os.path.dirname(os.path.realpath(__file__)), # with open(os.path.join(os.path.dirname(os.path.realpath(__file__)),
# # "list.pcl"), "w") as fob: # # "list.pcl"), "w") as fob: