Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Improve rosdep on Archlinux #560

Open
hauptmech opened this issue Oct 20, 2017 · 4 comments
Open

Improve rosdep on Archlinux #560

hauptmech opened this issue Oct 20, 2017 · 4 comments

Comments

@hauptmech
Copy link

This is a continuation of the discussion generated by #559.

To summarize: Arch has two installation methods; official binaries and community managed source (AUR) installs. Since Arch is a rolling release distro, it's common for application and library versions used by ROS to be no longer officially supported on Arch. Source (AUR) installs are necessary to provide these ROS dependencies. Furthermore, ROS itself is not officially supported on Arch, and is itself installed via AUR.

The expectation of Arch users is that AUR installs are an exception and should be done intentionally and only if you understand the consequences.

The rosdep database currently has AUR packages and trying to use rosdep when an AUR package is in the dependency chain (true for desktop and desktop-full source installs) will cause rosdep to error and do nothing. #559 proposed using an AUR installer to fix this.

Due to the difference between ROS releases and Arch releases, I don't think the rosdep database will be correct much of the time. However there is still benefit if rosdep can install as much as it can, leaving only a few packages to be installed by hand (or better yet, have database updates pushed to rosdistro).

I also think it's worth adding a package manager for AUR packages that can be invoked by users comfortable using AUR packages.

@hauptmech
Copy link
Author

hauptmech commented Oct 20, 2017

Modifying rosdep to install as many packages as it can, even if the database holds AUR packages or packages that are no longer supported can be done by using separate pacman commands for each package. (Note that one needs to add the -r flag to the rosdep command)

diff --git a/src/rosdep2/platforms/arch.py b/src/rosdep2/platforms/arch.py
index 8c1f676..2b27b13 100644
--- a/src/rosdep2/platforms/arch.py
+++ b/src/rosdep2/platforms/arch.py
@@ -69,4 +69,4 @@ class PacmanInstaller(PackageManagerInstaller):
         if quiet:
             command.append('-q')
 
-        return [self.elevate_priv(command + packages)]
+        return [self.elevate_priv(command + [package]) for package in packages]

The cost is a reduction in install speed. A more complex fix that checks rosdep database entries against pacman database entries in the pacman_detect function could improve this.

@hauptmech
Copy link
Author

Adding a package manager for AUR would look something like the changes below. rosdep install uses pacman by default, but given an os override, will use the AUR pacage manager. For instance:
rosdep install --os=arch:aur --from-paths src --ignore-src --rosdistro kinetic -r

The design of the rosdep yaml format requires an extra key for the version. Using 'aur' as I have is a little bit of a hack, but a reasonable one I think since Arch has no versions.

The command line given above will use yaourt interactively, giving the user the option to check the build scripts, which is the typical way it's used.

diff --git a/rosdep/base.yaml b/rosdep/base.yaml
index d46cb55eb..29c635d47 100644
--- a/rosdep/base.yaml
+++ b/rosdep/base.yaml
@@ -2128,7 +2128,9 @@ libogg:
   slackware: [libogg]
   ubuntu: [libogg-dev]
 libogre-dev:
-  arch: [ogre-1.9]
+  arch:
+    aur: 
+      yaourt: [ogre-1.9]
   debian:
     buster: [libogre-1.9-dev]
     jessie: [libogre-1.9-dev]
diff --git a/src/rosdep2/platforms/arch.py b/src/rosdep2/platforms/arch.py
index 8c1f676..0b5f282 100644
--- a/src/rosdep2/platforms/arch.py
+++ b/src/rosdep2/platforms/arch.py
@@ -30,19 +30,24 @@
 
 import subprocess
 
+from rospkg.os_detect import OS_DEBIAN, OS_LINARO, OS_UBUNTU, OS_ELEMENTARY, OsDetect
 from ..installers import PackageManagerInstaller
 from .source import SOURCE_INSTALLER
 
 ARCH_OS_NAME = 'arch'
 PACMAN_INSTALLER = 'pacman'
+AUR_INSTALLER = 'yaourt'
 
 def register_installers(context):
     context.set_installer(PACMAN_INSTALLER, PacmanInstaller())
+    context.set_installer(AUR_INSTALLER, AURInstaller())
 
 def register_platforms(context):
     context.add_os_installer_key(ARCH_OS_NAME, SOURCE_INSTALLER)
+    context.add_os_installer_key(ARCH_OS_NAME, AUR_INSTALLER)
     context.add_os_installer_key(ARCH_OS_NAME, PACMAN_INSTALLER)
     context.set_default_os_installer_key(ARCH_OS_NAME, lambda self: PACMAN_INSTALLER)
+    context.set_os_version_type(ARCH_OS_NAME, OsDetect.get_codename)
 
 def pacman_detect_single(p):
     return not subprocess.call(['pacman', '-T', p], stdout=subprocess.PIPE, stderr=subprocess.PIPE)
@@ -69,4 +74,26 @@ class PacmanInstaller(PackageManagerInstaller):
         if quiet:
             command.append('-q')
 
-        return [self.elevate_priv(command + packages)]
+        return [self.elevate_priv(command + [package]) for package in packages]
+
+class AURInstaller(PackageManagerInstaller):
+
+    def __init__(self):
+        super(AURInstaller, self).__init__(pacman_detect)
+
+    def get_install_command(self, resolved, interactive=True, reinstall=False, quiet=False):
+        packages = self.get_packages_to_install(resolved, reinstall=reinstall)
+        if not packages:
+            return []
+
+        command  = ['yaourt', '-S']
+
+        if not interactive:
+            command.append('--noconfirm')
+        if not reinstall:
+            command.append('--needed')
+        if quiet:
+            command.append('-q')
+
+        return [command + [package] for package in packages]
+

@hauptmech
Copy link
Author

@zootboy Suggested forcing the user to add their preferred aur-helper and leaving it blank/broken until then as an extra measure (above needing to explicitly specify the arch:aur package manager on the command line).

I don't see a good way to pass this through rosdep, but one could use a dummy script rosdep-aur-helper and leave it to the user to create a softlink on the PATH to their aur helper of choice.

@patrickelectric
Copy link

patrickelectric commented Oct 23, 2017

@hauptmech, thanks, your patch is great! I'll try to test this today.
For me this PR, if applied, can overwrite #559 proposal.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants