Преглед изворни кода

fix progress report for upgrade and reinstall

APT treats upgrades like installs and dpkg is very similar in this, but
prints still a slightly different processing message indicating that it
is really an upgrade which we hadn't parsed so far, but this wasn't
really visible as we quickly moved on to a 'known' state.

More problematic was the reinstall case as apt hadn't recognized this
for the package name detection, so that reinstalls had no progress since
we introduced MultiArch.
David Kalnischkies пре 12 година
родитељ
комит
4c559e97ba
2 измењених фајлова са 57 додато и 38 уклоњено
  1. 41 38
      apt-pkg/deb/dpkgpm.cc
  2. 16 0
      test/integration/test-apt-progress-fd

+ 41 - 38
apt-pkg/deb/dpkgpm.cc

@@ -564,8 +564,8 @@ void pkgDPkgPM::ProcessDpkgStatusLine(char *line)
       'status:   <pkg>: <pkg  qstate>'
       'status:   <pkg>:<arch>: <pkg  qstate>'
       
-      'processing: {install,configure,remove,purge,disappear,trigproc}: pkg'
-      'processing: {install,configure,remove,purge,disappear,trigproc}: trigger'
+      'processing: {install,upgrade,configure,remove,purge,disappear,trigproc}: pkg'
+      'processing: {install,upgrade,configure,remove,purge,disappear,trigproc}: trigger'
    */
 
    // we need to split on ": " (note the appended space) as the ':' is
@@ -589,12 +589,15 @@ void pkgDPkgPM::ProcessDpkgStatusLine(char *line)
    std::string action;
 
    // "processing" has the form "processing: action: pkg or trigger"
-   // with action = ["install", "configure", "remove", "purge", "disappear",
-   //                "trigproc"]
+   // with action = ["install", "upgrade", "configure", "remove", "purge",
+   //                "disappear", "trigproc"]
    if (prefix == "processing")
    {
       pkgname = APT::String::Strip(list[2]);
       action = APT::String::Strip(list[1]);
+      // we don't care for the difference (as dpkg doesn't really either)
+      if (action == "upgrade")
+	 action = "install";
    }
    // "status" has the form: "status: pkg: state"
    // with state in ["half-installed", "unpacked", "half-configured", 
@@ -638,27 +641,26 @@ void pkgDPkgPM::ProcessDpkgStatusLine(char *line)
    // at this point we know that we should have a valid pkgname, so build all 
    // the info from it
 
-   // dpkg does not send always send "pkgname:arch" so we add it here 
-   // if needed
+   // dpkg does not always send "pkgname:arch" so we add it here if needed
    if (pkgname.find(":") == std::string::npos)
    {
-      // find the package in the group that is in a touched by dpkg
-      // if there are multiple dpkg will send us a full pkgname:arch
+      // find the package in the group that is touched by dpkg
+      // if there are multiple pkgs dpkg would send us a full pkgname:arch
       pkgCache::GrpIterator Grp = Cache.FindGrp(pkgname);
-      if (Grp.end() == false) 
+      if (Grp.end() == false)
       {
-          pkgCache::PkgIterator P = Grp.PackageList();
-          for (; P.end() != true; P = Grp.NextPkg(P))
-          {
-              if(Cache[P].Mode != pkgDepCache::ModeKeep)
-              {
-                  pkgname = P.FullName();
-                  break;
-              }
-          }
+	 pkgCache::PkgIterator P = Grp.PackageList();
+	 for (; P.end() != true; P = Grp.NextPkg(P))
+	 {
+	    if(Cache[P].Keep() == false || Cache[P].ReInstall() == true)
+	    {
+	       pkgname = P.FullName();
+	       break;
+	    }
+	 }
       }
    }
-   
+
    const char* const pkg = pkgname.c_str();
    std::string short_pkgname = StringSplit(pkgname, ":")[0];
    std::string arch = "";
@@ -697,28 +699,29 @@ void pkgDPkgPM::ProcessDpkgStatusLine(char *line)
    if (prefix == "status")
    {
       vector<struct DpkgState> const &states = PackageOps[pkg];
-      const char *next_action = NULL;
       if(PackageOpsDone[pkg] < states.size())
-         next_action = states[PackageOpsDone[pkg]].state;
-      // check if the package moved to the next dpkg state
-      if(next_action && (action == next_action))
       {
-         // only read the translation if there is actually a next
-         // action
-         const char *translation = _(states[PackageOpsDone[pkg]].str);
-         std::string msg;
-
-         // we moved from one dpkg state to a new one, report that
-         PackageOpsDone[pkg]++;
-         PackagesDone++;
-
-         strprintf(msg, translation, i18n_pkgname.c_str());
-         d->progress->StatusChanged(pkgname, PackagesDone, PackagesTotal, msg);
-         
+         char const * const next_action = states[PackageOpsDone[pkg]].state;
+	 if (next_action && Debug == true)
+	    std::clog << "(parsed from dpkg) pkg: " << short_pkgname
+	       << " action: " << action << " (expected: '" << next_action << "' "
+	       << PackageOpsDone[pkg] << " of " << states.size() << ")" << endl;
+
+	 // check if the package moved to the next dpkg state
+	 if(next_action && (action == next_action))
+	 {
+	    // only read the translation if there is actually a next action
+	    char const * const translation = _(states[PackageOpsDone[pkg]].str);
+
+	    // we moved from one dpkg state to a new one, report that
+	    ++PackageOpsDone[pkg];
+	    ++PackagesDone;
+
+	    std::string msg;
+	    strprintf(msg, translation, i18n_pkgname.c_str());
+	    d->progress->StatusChanged(pkgname, PackagesDone, PackagesTotal, msg);
+	 }
       }
-      if (Debug == true) 
-         std::clog << "(parsed from dpkg) pkg: " << short_pkgname
-                   << " action: " << action << endl;
    }
 }
 									/*}}}*/

+ 16 - 0
test/integration/test-apt-progress-fd

@@ -33,6 +33,22 @@ testsuccess aptget install testing=0.8.15 -y -o APT::Status-Fd=3
 testequal "dlstatus:1:0:Retrieving file 1 of 1
 dlstatus:1:0:Retrieving file 1 of 1
 pmstatus:dpkg-exec:0:Running dpkg
+pmstatus:testing:0:Installing testing (amd64)
+pmstatus:testing:20:Preparing testing (amd64)
+pmstatus:testing:40:Unpacking testing (amd64)
+pmstatus:testing:60:Preparing to configure testing (amd64)
+pmstatus:dpkg-exec:60:Running dpkg
+pmstatus:testing:60:Configuring testing (amd64)
+pmstatus:testing:80:Configuring testing (amd64)
+pmstatus:testing:100:Installed testing (amd64)" cat apt-progress.log
+
+# reinstall
+exec 3> apt-progress.log
+testsuccess aptget install testing=0.8.15 --reinstall -y -o APT::Status-Fd=3
+testequal "dlstatus:1:0:Retrieving file 1 of 1
+dlstatus:1:0:Retrieving file 1 of 1
+pmstatus:dpkg-exec:0:Running dpkg
+pmstatus:testing:0:Installing testing (amd64)
 pmstatus:testing:20:Preparing testing (amd64)
 pmstatus:testing:40:Unpacking testing (amd64)
 pmstatus:testing:60:Preparing to configure testing (amd64)