Imported Upstream version 14.45.0
[platform/upstream/libzypp.git] / zypp / repo / yum / Downloader.cc
index c381175..a27dd2f 100644 (file)
 #include "zypp/base/Logger.h"
 #include "zypp/base/Function.h"
 
-#include "zypp/Date.h"
-
 #include "zypp/parser/yum/RepomdFileReader.h"
 #include "zypp/parser/yum/PatchesFileReader.h"
 #include "Downloader.h"
+#include "zypp/repo/MediaInfoDownloader.h"
 #include "zypp/base/UserRequestException.h"
+#include "zypp/parser/xml/Reader.h"
 
 using namespace std;
 using namespace zypp::xml;
@@ -30,100 +30,117 @@ namespace repo
 namespace yum
 {
 
-Downloader::Downloader( const Url &url, const Pathname &path )
-  : _url(url), _path(path), _media(url, path)
+Downloader::Downloader( const RepoInfo &repoinfo , const Pathname &delta_dir)
+  : repo::Downloader(repoinfo), _delta_dir(delta_dir), _media_ptr(0L)
 {
 }
 
-RepoStatus Downloader::status()
+
+RepoStatus Downloader::status( MediaSetAccess &media )
 {
-  Pathname repomd = _media.provideFile("/repodata/repomd.xml");
+  Pathname repomd = media.provideFile( repoInfo().path() + "/repodata/repomd.xml");
   return RepoStatus(repomd);
 }
 
-bool Downloader::patches_Callback( const OnMediaLocation &loc, const string &id )
+static OnMediaLocation
+loc_with_path_prefix(const OnMediaLocation & loc,
+                     const Pathname & prefix)
 {
-  MIL << id << " : " << loc << endl;
-  _fetcher.enqueueDigested(loc);
-  return true;
+  if (prefix.empty() || prefix == "/")
+    return loc;
+
+  OnMediaLocation loc_with_path(loc);
+  loc_with_path.changeFilename(prefix / loc.filename());
+  return loc_with_path;
 }
 
+// search old repository file file to run the delta algorithm on
+static Pathname search_deltafile( const Pathname &dir, const Pathname &file )
+{
+  Pathname deltafile;
+  if (!PathInfo(dir).isDir())
+    return deltafile;
+  string base = file.basename();
+  size_t hypoff = base.find("-");
+  if (hypoff != string::npos)
+    base.replace(0, hypoff + 1, "");
+  size_t basesize = base.size();
+  std::list<Pathname> retlist;
+  if (!filesystem::readdir(retlist, dir, false))
+  {
+    for_( it, retlist.begin(), retlist.end() )
+    {
+      string fn = it->asString();
+      if (fn.size() >= basesize && fn.substr(fn.size() - basesize, basesize) == base)
+       deltafile = *it;
+    }
+  }
+  return deltafile;
+}
 
-bool Downloader::repomd_Callback( const OnMediaLocation &loc, const ResourceType &dtype )
+bool Downloader::patches_Callback( const OnMediaLocation &loc,
+                                   const string &id )
 {
-  MIL << dtype << " : " << loc << endl;
-  
+  OnMediaLocation loc_with_path(loc_with_path_prefix(loc, repoInfo().path()));
+  MIL << id << " : " << loc_with_path << endl;
+  this->enqueueDigested(loc_with_path,  FileChecker(), search_deltafile(_delta_dir + "repodata", loc.filename()));
+  return true;
+}
+
+bool Downloader::repomd_Callback( const OnMediaLocation &loc,
+                                  const ResourceType &dtype )
+{
+  OnMediaLocation loc_with_path(loc_with_path_prefix(loc, repoInfo().path()));
+  MIL << dtype << " : " << loc_with_path << endl;
+
+  //! \todo do this through a ZConfig call so that it is always in sync with parser
   // skip other
   if ( dtype == ResourceType::OTHER )
   {
     MIL << "Skipping other.xml" << endl;
     return true;
   }
-  
-  _fetcher.enqueueDigested(loc);
-  
+  // skip filelists
+  if ( dtype == ResourceType::FILELISTS )
+  {
+    MIL << "Skipping filelists.xml.gz" << endl;
+    return true;
+  }
+
+  this->enqueueDigested(loc_with_path, FileChecker(), search_deltafile(_delta_dir + "repodata", loc.filename()));
+
   // We got a patches file we need to read, to add patches listed
-  // there, so we transfer what we have in the queue, and 
+  // there, so we transfer what we have in the queue, and
   // queue the patches in the patches callback
   if ( dtype == ResourceType::PATCHES )
   {
-    _fetcher.start( _dest_dir, _media);
+    this->start( _dest_dir, *_media_ptr );
     // now the patches.xml file must exists
-    PatchesFileReader( _dest_dir + loc.filename(), bind( &Downloader::patches_Callback, this, _1, _2));
+    PatchesFileReader( _dest_dir + repoInfo().path() + loc.filename(),
+                       bind( &Downloader::patches_Callback, this, _1, _2));
   }
-    
+
   return true;
 }
 
-void Downloader::download( const Pathname &dest_dir,
+/** \todo: Downloading/sigcheck of master index shoudl be common in base class */
+void Downloader::download( MediaSetAccess &media,
+                           const Pathname &dest_dir,
                            const ProgressData::ReceiverFnc & progressrcv )
 {
-  Pathname repomdpath =  "/repodata/repomd.xml";
-  Pathname keypath =  "/repodata/repomd.xml.key";
-  Pathname sigpath =  "/repodata/repomd.xml.asc";
-  
-  ProgressData progress;
-  progress.sendTo(progressrcv);
-  progress.toMin();
+  Pathname masterIndex( repoInfo().path() / "/repodata/repomd.xml" );
+  defaultDownloadMasterIndex( media, dest_dir, masterIndex );
 
+  _media_ptr = (&media);
   _dest_dir = dest_dir;
-  if ( _media.doesFileExist(keypath) )
-    _fetcher.enqueue( OnMediaLocation().setFilename(keypath) );
-
-  if ( _media.doesFileExist(sigpath) )
-     _fetcher.enqueue( OnMediaLocation().setFilename(sigpath) );
-  
-  _fetcher.start( dest_dir, _media );
-  
-  if ( ! progress.tick() )
-    ZYPP_THROW(AbortRequestException());
-
-  SignatureFileChecker sigchecker;
-  
-  if ( PathInfo( dest_dir + sigpath ).isExist() )
-    sigchecker = SignatureFileChecker(dest_dir + sigpath);
-  
-  if ( PathInfo( dest_dir + keypath ).isExist() )
-    sigchecker.addPublicKey(dest_dir + keypath );
-  
-  _fetcher.enqueue( OnMediaLocation().setFilename(repomdpath), sigchecker );
-  _fetcher.start( dest_dir, _media);
-  
-  if ( ! progress.tick() )
-        ZYPP_THROW(AbortRequestException());
-
-  _fetcher.reset();
-
-  Reader reader( dest_dir + "/repodata/repomd.xml" );
-  RepomdFileReader( dest_dir + "/repodata/repomd.xml", bind( &Downloader::repomd_Callback, this, _1, _2));
+  RepomdFileReader( dest_dir / masterIndex, bind( &Downloader::repomd_Callback, this, _1, _2));
 
   // ready, go!
-  _fetcher.start( dest_dir, _media);
-  progress.toMax();
+  start( dest_dir, media );
 }
 
 }// ns yum
-}// ns source 
+}// ns source
 } // ns zypp