From: Jan Kupec Date: Mon, 21 May 2007 02:02:35 +0000 (+0000) Subject: - FilelistsFileReader complete X-Git-Tag: BASE-SuSE-Linux-10_3-Branch~739 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=d081bf2aca3ee21bb416052aae0b458195f27889;p=platform%2Fupstream%2Flibzypp.git - FilelistsFileReader complete - YUMParser changed to use ResolvableDataConsumer iface instead of CacheStore --- diff --git a/devel/devel.jkupec/YUMParser.cc b/devel/devel.jkupec/YUMParser.cc index ad97c89..d1cc85e 100644 --- a/devel/devel.jkupec/YUMParser.cc +++ b/devel/devel.jkupec/YUMParser.cc @@ -16,6 +16,7 @@ #include "zypp/parser/yum/PatchesFileReader.h" #include "zypp/parser/yum/PatchFileReader.h" #include "zypp/parser/yum/OtherFileReader.h" +#include "zypp/parser/yum/FilelistsFileReader.h" #include "YUMParser.h" @@ -38,16 +39,16 @@ namespace zypp return true; } + YUMParser::YUMParser( - const zypp::data::RecordId &catalog_id, - zypp::cache::CacheStore &consumer, + const data::RecordId & catalog_id, + data::ResolvableDataConsumer & consumer, const ProgressData::ReceiverFnc & progress) : _consumer(consumer), _catalog_id(catalog_id) { _ticks.name("YUMParser"); _ticks.sendTo(progress); - MIL << "constructed" << endl; } @@ -61,6 +62,7 @@ namespace zypp return true; } + bool YUMParser::primary_CB(const data::Package_Ptr & package_r) { _consumer.consumePackage( _catalog_id, package_r ); @@ -114,6 +116,21 @@ namespace zypp } + bool YUMParser::filelist_CB(const data::Resolvable_Ptr & res_ptr, const data::Filenames & filenames) + { + _consumer.consumeFilelist(_catalog_id, res_ptr, filenames); +/* + DBG << "got filelist for " + << res_ptr->name << res_ptr->edition << " " + << res_ptr->arch + << endl; + + DBG << "last entry: " << filenames.front() << endl; +*/ + return true; + } + + void YUMParser::start(const Pathname &cache_dir) { zypp::parser::yum::RepomdFileReader( @@ -178,6 +195,15 @@ namespace zypp break; } + case YUMResourceType::FILELISTS_e: + { + zypp::parser::yum::FilelistsFileReader( + cache_dir + job.filename(), + bind(&YUMParser::filelist_CB, this, _1, _2), + &progress_function); + break; + } + default: { WAR << "Don't know how to read " diff --git a/devel/devel.jkupec/YUMParser.h b/devel/devel.jkupec/YUMParser.h index c1a6fb9..ce16b83 100644 --- a/devel/devel.jkupec/YUMParser.h +++ b/devel/devel.jkupec/YUMParser.h @@ -11,7 +11,7 @@ #define YUMPARSER_H_ #include "zypp/base/Logger.h" -#include "zypp2/cache/CacheStore.h" +#include "zypp/data/ResolvableDataConsumer.h" #include "zypp/data/ResolvableData.h" #include "zypp/source/yum/YUMResourceType.h" #include "zypp/ProgressData.h" @@ -27,8 +27,9 @@ namespace zypp namespace yum { + /** - * + * Structure encapsulating YUM parser data type and filename. */ struct YUMParserJob { @@ -39,7 +40,9 @@ namespace zypp const YUMResourceType & type() const { return _type; } private: + /** File to be processed */ Pathname _filename; + /** Type of YUM file */ YUMResourceType _type; }; @@ -51,8 +54,8 @@ namespace zypp { public: YUMParser( - const zypp::data::RecordId & catalog_id, - zypp::cache::CacheStore & consumer, + const data::RecordId & catalog_id, + data::ResolvableDataConsumer & consumer, const ProgressData::ReceiverFnc & progress = ProgressData::ReceiverFnc() ); @@ -66,17 +69,18 @@ namespace zypp bool patches_CB(const OnMediaLocation &loc, const std::string & patch_id); bool patch_CB(const data::Patch_Ptr & patch); bool other_CB(const data::Resolvable_Ptr & res_ptr, const Changelog & changelog); + bool filelist_CB(const data::Resolvable_Ptr & res_ptr, const data::Filenames & filenames); private: - zypp::cache::CacheStore & _consumer; - + data::ResolvableDataConsumer & _consumer; + /** ID of the repository record in the DB (catalogs.id) */ - zypp::data::RecordId _catalog_id; + data::RecordId _catalog_id; /** List of parser jobs read from repomd.xml and patches.xml files. */ std::list _jobs; - /** Progress reporting object. */ + /** Progress reporting object for overall YUM parser progress. */ ProgressData _ticks; }; @@ -88,3 +92,4 @@ namespace zypp #endif /*YUMPARSER_H_*/ // vim: set ts=2 sts=2 sw=2 et ai: + diff --git a/devel/devel.jkupec/YUMParser_test.cc b/devel/devel.jkupec/YUMParser_test.cc index d334775..d4b2a07 100644 --- a/devel/devel.jkupec/YUMParser_test.cc +++ b/devel/devel.jkupec/YUMParser_test.cc @@ -2,10 +2,9 @@ #include "zypp/ZYppFactory.h" #include "zypp/base/Logger.h" #include "zypp/base/LogControl.h" -#include "zypp/parser/yum/PrimaryFileReader.h" -#include "YUMParser.h" -#include "zypp/parser/ParserProgress.h" #include "zypp/base/Measure.h" +#include "zypp2/cache/CacheStore.h" +#include "YUMParser.h" diff --git a/zypp/CMakeLists.txt b/zypp/CMakeLists.txt index 5b96ee7..51e6559 100644 --- a/zypp/CMakeLists.txt +++ b/zypp/CMakeLists.txt @@ -555,6 +555,7 @@ SET( zypp_parser_yum_SRCS parser/yum/PatchesFileReader.cc parser/yum/PrimaryFileReader.cc parser/yum/OtherFileReader.cc + parser/yum/FilelistsFileReader.cc parser/yum/PatchFileReader.cc ) @@ -575,6 +576,7 @@ SET( zypp_parser_yum_HEADERS parser/yum/PatchesFileReader.h parser/yum/PrimaryFileReader.h parser/yum/OtherFileReader.h + parser/yum/FilelistsFileReader.h parser/yum/PatchFileReader.h parser/yum/schemanames.h ) diff --git a/zypp/data/ResolvableData.h b/zypp/data/ResolvableData.h index a80edac..de05d8b 100644 --- a/zypp/data/ResolvableData.h +++ b/zypp/data/ResolvableData.h @@ -42,6 +42,10 @@ namespace data typedef DefaultIntegral MediaNr; + /** List of files contained in a package (info for UI) */ + typedef std::list Filenames; + + /** Data to retrieve a file from some media. */ struct Location { diff --git a/zypp/data/ResolvableDataConsumer.h b/zypp/data/ResolvableDataConsumer.h index af0b313..69b343d 100644 --- a/zypp/data/ResolvableDataConsumer.h +++ b/zypp/data/ResolvableDataConsumer.h @@ -34,7 +34,8 @@ namespace data virtual void consumeMessage( const data::RecordId &catalog_id, data::Message_Ptr ) = 0; virtual void consumeScript( const data::RecordId &catalog_id, data::Script_Ptr ) = 0; - virtual void consumeChangelog( const data::RecordId &catalog_id, data::Resolvable_Ptr, Changelog ) = 0; + virtual void consumeChangelog( const data::RecordId & catalog_id, const data::Resolvable_Ptr &, const Changelog & ) = 0; + virtual void consumeFilelist( const data::RecordId & catalog_id, const data::Resolvable_Ptr &, const data::Filenames & ) = 0; //virtual void consumeSourcePackage( const data::SrcPackage_Ptr ) = 0; }; diff --git a/zypp/parser/yum/FilelistsFileReader.cc b/zypp/parser/yum/FilelistsFileReader.cc new file mode 100644 index 0000000..b5d2498 --- /dev/null +++ b/zypp/parser/yum/FilelistsFileReader.cc @@ -0,0 +1,141 @@ +/*---------------------------------------------------------------------\ +| ____ _ __ __ ___ | +| |__ / \ / / . \ . \ | +| / / \ V /| _/ _/ | +| / /__ | | | | | | | +| /_____||_| |_| |_| | +| | +\---------------------------------------------------------------------*/ + +#include + +#include "zypp/parser/yum/FilelistsFileReader.h" + +#undef ZYPP_BASE_LOGGER_LOGGROUP +#define ZYPP_BASE_LOGGER_LOGGROUP "parser" + +using namespace std; +using namespace zypp::xml; + +namespace zypp +{ + namespace parser + { + namespace yum + { + + + // -------------------------------------------------------------------------- + + /* + * xpath and multiplicity of processed nodes are included in the code + * for convenience: + * + * // xpath: (?|*|+) + * + * if multiplicity is ommited, then the node has multiplicity 'one'. + */ + + // -------------------------------------------------------------------------- + + FilelistsFileReader::FilelistsFileReader( + const Pathname & filelist_file, + const ProcessPackage & callback, + const ProgressData::ReceiverFnc & progress) + : + _callback(callback) + { + _ticks.sendTo(progress); + _ticks.name("filelist.xml.gz"); + + Reader reader(filelist_file); + MIL << "Reading " << filelist_file << endl; + reader.foreachNode(bind(&FilelistsFileReader::consumeNode, this, _1)); + } + + // -------------------------------------------------------------------------- + + bool FilelistsFileReader::consumeNode(Reader & reader_r) + { + if (reader_r->nodeType() == XML_READER_TYPE_ELEMENT) + { + // xpath: /filelists + if (reader_r->name() == "filelists") + { + unsigned total_packages; + zypp::str::strtonum(reader_r->getAttribute("packages").asString(), total_packages); + _ticks.range(total_packages); + _ticks.toMin(); + return true; + } + + // xpath: /filelists/package (+) + if (reader_r->name() == "package") + { + _resolvable = new data::Resolvable; + _filenames.clear(); + + _resolvable->name = reader_r->getAttribute("name").asString(); + _resolvable->arch = Arch(reader_r->getAttribute("arch").asString()); + + return true; + } + + // xpath: /filelists/package/version + if (reader_r->name() == "version") + { + _resolvable->edition = Edition(reader_r->getAttribute("ver").asString(), + reader_r->getAttribute("rel").asString(), + reader_r->getAttribute("epoch").asString()); + return true; + } + + // xpath: /filelists/package/file (*) + if (reader_r->name() == "file") + { + // ignoring type dir/ghost reader_r->getAttribute("type").asString(); + _filenames.push_back(reader_r.nodeText().asString()); + return true; + } + } + + else if (reader_r->nodeType() == XML_READER_TYPE_END_ELEMENT) + { + // xpath: /filelists/package + if (reader_r->name() == "package") + { + if (_callback && !_filenames.empty()) + _callback(handoutResolvable(), _filenames); + + _ticks.incr(); + + return true; + } + + // xpath: /filelists + if (reader_r->name() == "filelists") + { + _ticks.toMax(); + return true; + } + } + + return true; + } + + // -------------------------------------------------------------------------- + + data::Resolvable_Ptr FilelistsFileReader::handoutResolvable() + { + data::Resolvable_Ptr ret; + ret.swap(_resolvable); + return ret; + } + + + } // ns yum + } // ns parser +} // ns zypp + +// vim: set ts=2 sts=2 sw=2 et ai: + diff --git a/zypp/parser/yum/FilelistsFileReader.h b/zypp/parser/yum/FilelistsFileReader.h new file mode 100644 index 0000000..ca9c241 --- /dev/null +++ b/zypp/parser/yum/FilelistsFileReader.h @@ -0,0 +1,108 @@ +/*---------------------------------------------------------------------\ +| ____ _ __ __ ___ | +| |__ / \ / / . \ . \ | +| / / \ V /| _/ _/ | +| / /__ | | | | | | | +| /_____||_| |_| |_| | +| | +\---------------------------------------------------------------------*/ + +#ifndef FILELISTFILEREADER_H_ +#define FILELISTFILEREADER_H_ + +#include "zypp/base/Function.h" +#include "zypp/base/Logger.h" +#include "zypp/parser/xml/Reader.h" +#include "zypp/data/ResolvableData.h" +#include "zypp/ProgressData.h" + +namespace zypp +{ + namespace parser + { + namespace yum + { + + + /** + * Reads through a filelists.xml.gz file and collects list of file contained + * in packages. + * + * After each package is read, a \ref data::Resolvable + * and \ref data::Filenames is prepared and \ref _callback + * is called with these two objects passed in. + * + * The \ref _callback is provided on construction. + * + * \code + * FilelistsFileReader reader(filelists_file, + * bind(&SomeClass::callbackfunc, &SomeClassInstance, _1, _2)); + * \endcode + */ + class FilelistsFileReader + { + public: + /** + * Callback definition. + */ + typedef function ProcessPackage; + + /** + * Constructor + * \param filelists_file the filelists.xml.gz file you want to read + * \param callback function to process \ref _resolvable data. + * \param progress progress reporting object + * + * \see FilelistsFileReader::ProcessPackage + */ + FilelistsFileReader( + const Pathname & filelists_file, + const ProcessPackage & callback, + const ProgressData::ReceiverFnc & progress = ProgressData::ReceiverFnc()); + + private: + + /** + * Callback provided to the XML parser. + */ + bool consumeNode(xml::Reader & reader_r); + + /** + * Creates a new \ref data::Resolvable_Ptr, swaps its contents with + * \ref _resolvable and returns it. Used to hand-out the data object to its consumer + * (a \ref ProcessPackage function) after it has been read. + */ + data::Resolvable_Ptr handoutResolvable(); + + private: + + /** + * Pointer to the \ref zypp::data::Resolvable object for storing the NVRA + * data. + */ + zypp::data::Resolvable_Ptr _resolvable; + + /** + * Changelog of \ref _resolvable. + */ + data::Filenames _filenames; + + /** + * Callback for processing package metadata passed in through constructor. + */ + ProcessPackage _callback; + + /** + * Progress reporting object. + */ + ProgressData _ticks; + }; + + + } // ns zypp + } // ns parser +} // ns yum + +#endif /*FILELISTFILEREADER_H_*/ + +// vim: set ts=2 sts=2 sw=2 et ai: diff --git a/zypp2/cache/CacheStore.cpp b/zypp2/cache/CacheStore.cpp index 5780301..b004ebc 100644 --- a/zypp2/cache/CacheStore.cpp +++ b/zypp2/cache/CacheStore.cpp @@ -264,7 +264,7 @@ void CacheStore::consumeProduct( const data::RecordId &catalog_id, data::Product consumeResObject( id, product ); } -void CacheStore::consumeChangelog( const data::RecordId &catalog_id, data::Resolvable_Ptr resolvable, Changelog changelog ) +void CacheStore::consumeChangelog( const data::RecordId &catalog_id, const data::Resolvable_Ptr & resolvable, const Changelog & changelog ) { // TODO // maybe consumeChangelog(const data::RecordId & resolvable_id, Changelog changelog) will @@ -272,6 +272,14 @@ void CacheStore::consumeChangelog( const data::RecordId &catalog_id, data::Resol // resolvable. (first, we'll see how fast is the inserting without remembering those ids) } +void CacheStore::consumeFilelist( const data::RecordId &catalog_id, const data::Resolvable_Ptr & resolvable, const data::Filenames & filenames ) +{ + // TODO + // maybe consumeFilelist(const data::RecordId & resolvable_id, data::Filenames &) will + // be needed +} + + void CacheStore::consumeResObject( const data::RecordId &rid, data::ResObject_Ptr res ) { appendTranslatedStringAttribute( rid, "ResObject", "description", res->description ); diff --git a/zypp2/cache/CacheStore.h b/zypp2/cache/CacheStore.h index 3e08a5e..a758575 100644 --- a/zypp2/cache/CacheStore.h +++ b/zypp2/cache/CacheStore.h @@ -131,7 +131,17 @@ namespace zypp * \param resolvable resolvable for which the changelog data are to be saved * \param changelog the changelog */ - virtual void consumeChangelog( const data::RecordId &catalog_id, data::Resolvable_Ptr resolvable, Changelog changelog ); + virtual void consumeChangelog( const data::RecordId &catalog_id, const data::Resolvable_Ptr & resolvable, const Changelog & changelog ); + + /** + * Implementation of the \ref ResolvableConsumer interface + * + * Consume filelist of a resolvable, inserting it in the cache. + * \param catalog_id ownership. + * \param resolvable resolvable for which the filelist is to be saved + * \param filenames list of filenames the resolvable contains + */ + virtual void consumeFilelist( const data::RecordId &catalog_id, const data::Resolvable_Ptr & resolvable, const data::Filenames & filenames ); /** * Appends a resolvable to the store.