Signed-off-by: Johannes Löthberg <johan...@kyriasis.com>
---
The vercmp logic is relatively complicated, so shelling out to the 
official vercmp binary is much simpler, and will be available on any 
system with pacman installed.

 conf/config.proto        |  1 +
 web/lib/pkgfuncs.inc.php | 36 ++++++++++++++++++++++++++++++++++--
 2 files changed, 35 insertions(+), 2 deletions(-)

diff --git a/conf/config.proto b/conf/config.proto
index c56141c..37c455e 100644
--- a/conf/config.proto
+++ b/conf/config.proto
@@ -31,6 +31,7 @@ log_uri = https://aur.archlinux.org/cgit/aur.git/log/?h=%s
 snapshot_uri = /cgit/aur.git/snapshot/%s.tar.gz
 enable-maintenance = 1
 maintenance-exceptions = 127.0.0.1
+vercmp-cmd = /usr/bin/vercmp
 
 [notifications]
 notify-cmd = /srv/http/aurweb/scripts/notify.py
diff --git a/web/lib/pkgfuncs.inc.php b/web/lib/pkgfuncs.inc.php
index 4b0fdba..a697e69 100644
--- a/web/lib/pkgfuncs.inc.php
+++ b/web/lib/pkgfuncs.inc.php
@@ -204,14 +204,14 @@ function pkg_groups($pkgid) {
  */
 function pkg_providers($name) {
        $dbh = DB::connect();
-       $q = "SELECT p.ID, p.Name FROM Packages p ";
+       $q = "SELECT p.ID, p.Name, p.Version FROM Packages p ";
        $q.= "LEFT JOIN PackageRelations pr ON pr.PackageID = p.ID ";
        $q.= "LEFT JOIN RelationTypes rt ON rt.ID = pr.RelTypeID ";
        $q.= "WHERE p.Name = " . $dbh->quote($name) . " ";
        $q.= "OR (rt.Name = 'provides' ";
        $q.= "AND pr.RelName = " . $dbh->quote($name) . ")";
        $q.= "UNION ";
-       $q.= "SELECT 0, Name FROM OfficialProviders ";
+       $q.= "SELECT 0, Name, 0 FROM OfficialProviders ";
        $q.= "WHERE Provides = " . $dbh->quote($name);
        $result = $dbh->query($q);
 
@@ -349,6 +349,33 @@ function pkg_provider_link($name, $official) {
        return $link;
 }
 
+function cmp_provider_ver($version, $cond) {
+       if (!$cond) {
+               return True;
+       }
+
+       $condition = preg_split("/^([<=>]{0,2})/", $cond, -1, 
PREG_SPLIT_DELIM_CAPTURE);
+
+       $cmd = config_get('options', 'vercmp-cmd');
+       $cmd .= ' ' . escapeshellarg($version) . ' ' . 
escapeshellarg($condition[2]);
+       $handle = popen($cmd, 'r');
+       $result = fread($handle, 2);
+       pclose($handle);
+
+       switch ($condition[1]) {
+       case ">=":
+               return $result >= 0;
+       case "<=":
+               return $result <= 0;
+       case ">":
+               return $result > 0;
+       case "<":
+               return $result < 0;
+       case "==":
+               return $result == 0;
+       }
+}
+
 /**
  * Get the HTML code to display a package dependency link
  *
@@ -407,6 +434,11 @@ function pkg_depend_link($name, $type, $cond, $arch, 
$pkg_id) {
        if (count($providers) > 0) {
                $link .= '<span class="virtual-dep">(';
                foreach ($providers as $provider) {
+                       $version = $provider[2];
+                       if (!cmp_provider_ver($version, $cond)) {
+                               break;
+                       }
+
                        $is_official = ($provider[0] == 0);
                        $name = $provider[1];
                        $link .= pkg_provider_link($name, $is_official) . ', ';
-- 
2.10.0

Reply via email to