From 5cfced0eec1c360bf51851569f9b10a2197e8f9e Mon Sep 17 00:00:00 2001 From: Michael Andres Date: Wed, 23 Apr 2014 11:11:07 +0200 Subject: [PATCH] SolvIdentFile: Save and restore a list of solvable names --- zypp/CMakeLists.txt | 2 + zypp/target/SolvIdentFile.cc | 95 +++++++++++++++++++++++++++++++++++ zypp/target/SolvIdentFile.h | 115 +++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 212 insertions(+) create mode 100644 zypp/target/SolvIdentFile.cc create mode 100644 zypp/target/SolvIdentFile.h diff --git a/zypp/CMakeLists.txt b/zypp/CMakeLists.txt index de601e3..fd6dfcd 100644 --- a/zypp/CMakeLists.txt +++ b/zypp/CMakeLists.txt @@ -571,6 +571,7 @@ INSTALL( FILES SET( zypp_target_SRCS target/RpmPostTransCollector.cc target/RequestedLocalesFile.cc + target/SolvIdentFile.cc target/HardLocksFile.cc target/CommitPackageCache.cc target/CommitPackageCacheImpl.cc @@ -585,6 +586,7 @@ SET( zypp_target_SRCS SET( zypp_target_HEADERS target/RpmPostTransCollector.h target/RequestedLocalesFile.h + target/SolvIdentFile.h target/HardLocksFile.h target/CommitPackageCache.h target/CommitPackageCacheImpl.h diff --git a/zypp/target/SolvIdentFile.cc b/zypp/target/SolvIdentFile.cc new file mode 100644 index 0000000..f09074a --- /dev/null +++ b/zypp/target/SolvIdentFile.cc @@ -0,0 +1,95 @@ +/*---------------------------------------------------------------------\ +| ____ _ __ __ ___ | +| |__ / \ / / . \ . \ | +| / / \ V /| _/ _/ | +| / /__ | | | | | | | +| /_____||_| |_| |_| | +| | +\---------------------------------------------------------------------*/ +/** \file zypp/target/SolvIdentFile.cc + * +*/ +#include +#include + +#include "zypp/base/LogTools.h" +#include "zypp/base/IOStream.h" +#include "zypp/base/String.h" + +#include "zypp/PathInfo.h" +#include "zypp/TmpPath.h" +#include "zypp/Date.h" + +#include "zypp/target/SolvIdentFile.h" + +using std::endl; + +/////////////////////////////////////////////////////////////////// +namespace zypp +{ ///////////////////////////////////////////////////////////////// + /////////////////////////////////////////////////////////////////// + namespace target + { ///////////////////////////////////////////////////////////////// + + void SolvIdentFile::load( const Pathname & file_r, Data & data_r ) + { + PathInfo pi( file_r ); + if ( ! pi.isFile() ) + { + WAR << "Can't read " << pi << endl; + return; + } + std::ifstream infile( file_r.c_str() ); + for( iostr::EachLine in( infile ); in; in.next() ) + { + std::string l( str::trim(*in) ); + if ( ! l.empty() && l[0] != '#' ) + { + data_r.insert( IdString(l) ); + } + } + MIL << "Read " << pi << endl; + } + + void SolvIdentFile::store( const Pathname & file_r, const Data & data_r ) + { + filesystem::TmpFile tmp( filesystem::TmpFile::makeSibling( file_r ) ); + filesystem::chmod( tmp.path(), 0644 ); + + std::ofstream outs( tmp.path().c_str() ); + outs << "# " << file_r.basename() << " generated " << Date::now() << endl; + dumpRange( outs, data_r.begin(), data_r.end(), "#", "\n", "\n", "\n", "#\n" ); + outs.close(); + + if ( outs.good() ) + { + filesystem::rename( tmp.path(), file_r ); + MIL << "Wrote " << PathInfo(file_r) << endl; + } + else + { + ERR << "Can't write " << PathInfo(tmp.path()) << endl; + } + } + + /****************************************************************** + ** + ** FUNCTION NAME : operator<< + ** FUNCTION TYPE : std::ostream & + */ + std::ostream & operator<<( std::ostream & str, const SolvIdentFile & obj ) + { + str << obj.file() << ' '; + if ( obj._dataPtr ) + str << obj.data(); + else + str << "(unloaded)"; + return str; + } + + ///////////////////////////////////////////////////////////////// + } // namespace target + /////////////////////////////////////////////////////////////////// + ///////////////////////////////////////////////////////////////// +} // namespace zypp +/////////////////////////////////////////////////////////////////// diff --git a/zypp/target/SolvIdentFile.h b/zypp/target/SolvIdentFile.h new file mode 100644 index 0000000..b44e2dd --- /dev/null +++ b/zypp/target/SolvIdentFile.h @@ -0,0 +1,115 @@ +/*---------------------------------------------------------------------\ +| ____ _ __ __ ___ | +| |__ / \ / / . \ . \ | +| / / \ V /| _/ _/ | +| / /__ | | | | | | | +| /_____||_| |_| |_| | +| | +\---------------------------------------------------------------------*/ +/** \file zypp/target/SolvIdentFile.h + * +*/ +#ifndef ZYPP_TARGET_SOLVIDENTFILE_H +#define ZYPP_TARGET_SOLVIDENTFILE_H + +#include + +#include "zypp/base/PtrTypes.h" + +#include "zypp/IdString.h" +#include "zypp/Pathname.h" + +/////////////////////////////////////////////////////////////////// +namespace zypp +{ ///////////////////////////////////////////////////////////////// + /////////////////////////////////////////////////////////////////// + namespace target + { ///////////////////////////////////////////////////////////////// + + /////////////////////////////////////////////////////////////////// + /// \class SolvIdentFile + /// \short Save and restore a list of solvable names (ident IdString) + /////////////////////////////////////////////////////////////////// + class SolvIdentFile + { + friend std::ostream & operator<<( std::ostream & str, const SolvIdentFile & obj ); + public: + typedef std::tr1::unordered_set Data; + + public: + /** Ctor taking the file to read/write. */ + SolvIdentFile( const Pathname & file_r ) + : _file( file_r ) + {} + + /** Return the file path. */ + const Pathname & file() const + { return _file; } + + /** Return the data. + * The file is read once on demand. Returns empty \ref Data if + * the file does not exist or is not readable. + */ + const Data & data() const + { + if ( !_dataPtr ) + { + _dataPtr.reset( new Data ); + Data & mydata( *_dataPtr ); + load( _file, mydata ); + } + return *_dataPtr; + } + + /** Store new \ref Data. + * Write the new \ref Data to file, unless we know it + * did not change. The directory containing file must + * exist. + */ + void setData( const Data & data_r ) + { + if ( !_dataPtr ) + _dataPtr.reset( new Data ); + + if ( differs( *_dataPtr, data_r ) ) + { + store( _file, data_r ); + *_dataPtr = data_r; + } + } + + private: + /** Helper testing whether two \ref Data differ. */ + bool differs( const Data & lhs, const Data & rhs ) const + { + + if ( lhs.size() != rhs.size() ) + return true; + for_( it, lhs.begin(), lhs.end() ) + { + if ( rhs.find( *it ) == rhs.end() ) + return true; + } + return false; + } + /** Read \ref Data from \c file_r. */ + static void load( const Pathname & file_r, Data & data_r ); + /** Write \ref Data to \c file_r. */ + static void store( const Pathname & file_r, const Data & data_r ); + + private: + Pathname _file; + mutable scoped_ptr _dataPtr; + }; + /////////////////////////////////////////////////////////////////// + + /** \relates SolvIdentFile Stream output */ + std::ostream & operator<<( std::ostream & str, const SolvIdentFile & obj ); + + ///////////////////////////////////////////////////////////////// + } // namespace target + /////////////////////////////////////////////////////////////////// + ///////////////////////////////////////////////////////////////// +} // namespace zypp +/////////////////////////////////////////////////////////////////// +#endif // ZYPP_TARGET_SOLVIDENTFILE_H -- 2.7.4