1 /*---------------------------------------------------------------------\
3 | |__ / \ / / . \ . \ |
8 \---------------------------------------------------------------------*/
9 /** \file zypp/target/rpm/RpmDb.h
15 #ifndef ZYPP_TARGET_RPM_RPMDB_H
16 #define ZYPP_TARGET_RPM_RPMDB_H
23 #include "zypp/Pathname.h"
24 #include "zypp/ExternalProgram.h"
26 #include "zypp/Package.h"
27 #include "zypp/KeyRing.h"
29 #include "zypp/target/rpm/RpmFlags.h"
30 #include "zypp/target/rpm/RpmHeader.h"
31 #include "zypp/target/rpm/RpmCallbacks.h"
32 #include "zypp/ZYppCallbacks.h"
41 ///////////////////////////////////////////////////////////////////
45 * @short Interface to the rpm program
47 class RpmDb : public base::ReferenceCounted, private base::NonCopyable
54 typedef class InstTargetError Error;
56 ///////////////////////////////////////////////////////////////////
60 ///////////////////////////////////////////////////////////////////
63 enum DbStateInfoBits {
64 DbSI_NO_INIT = 0x0000,
65 DbSI_HAVE_V4 = 0x0001,
66 DbSI_MADE_V4 = 0x0002,
67 DbSI_MODIFIED_V4 = 0x0004,
68 DbSI_HAVE_V3 = 0x0008,
69 DbSI_HAVE_V3TOV4 = 0x0010,
70 DbSI_MADE_V3TOV4 = 0x0020
73 friend std::ostream & operator<<( std::ostream & str, const DbStateInfoBits & obj );
75 void dbsi_set( DbStateInfoBits & val_r, const unsigned & bits_r ) const
77 val_r = (DbStateInfoBits)(val_r | bits_r);
79 void dbsi_clr( DbStateInfoBits & val_r, const unsigned & bits_r ) const
81 val_r = (DbStateInfoBits)(val_r & ~bits_r);
83 bool dbsi_has( const DbStateInfoBits & val_r, const unsigned & bits_r ) const
85 return( (val_r & bits_r) == bits_r );
91 DbStateInfoBits _dbStateInfo;
94 * Root directory for all operations.
99 * Directory that contains the rpmdb.
104 * Internal helper for @ref initDatabase.
106 * \throws RpmException
109 void internal_initDatabase( const Pathname & root_r, const Pathname & dbPath_r,
110 DbStateInfoBits & info_r );
113 * Remove the rpm4 database in dbdir_r and optionally any backup created
116 static void removeV4( const Pathname & dbdir_r, bool v3backup_r );
119 * Remove the rpm3 database in dbdir_r. Create a backup copy named
120 * packages.rpm3 if it does not already exist.
122 static void removeV3( const Pathname & dbdir_r, bool v3backup_r );
125 * Called before the database is modified by installPackage/removePackage.
126 * Invalidates Packages list and moves away any old database.
128 void modifyDatabase();
133 * Constructor. There's no rpmdb access until @ref initDatabase
144 * timestamp of the rpm database (last modification)
146 Date timestamp() const;
149 * @return Root directory for all operations (empty if not initialized).
151 const Pathname & root() const
157 * @return Directory that contains the rpmdb (empty if not initialized).
159 const Pathname & dbPath() const
165 * @return Whether we are initialized.
167 bool initialized() const
169 return( ! _root.empty() );
173 * Prepare access to the rpm database. Optional arguments may denote the
174 * root directory for all operations and the directory (below root) that
175 * contains the rpmdb (usg. you won't need to set this).
177 * On empty Pathnames the default is used:
180 * dbPath: /var/lib/rpm
183 * Calling initDatabase a second time with different arguments will return
184 * an error but leave the database in it's original state.
186 * Converting an old batabase is done if necessary. On update: The converted
187 * database will be removed by @ref closeDatabase, if it was not modified
188 * (no packages were installed or deleted). Otherwise the new database
189 * is kept, and the old one is removed.
191 * If the database alredy exists and \c doRebuild_r is true, \ref rebuildDatabase
194 * \throws RpmException
197 void initDatabase( Pathname root_r = Pathname(),
198 Pathname dbPath_r = Pathname(),
199 bool doRebuild_r = false );
202 * Block further access to the rpm database and go back to uninitialized
203 * state. On update: Decides what to do with any converted database
204 * (see @ref initDatabase).
206 * \throws RpmException
209 void closeDatabase();
212 * Rebuild the rpm database (rpm --rebuilddb).
214 * \throws RpmException
217 void rebuildDatabase();
220 * Import ascii armored public key in file pubkey_r.
222 * \throws RpmException
225 void importPubkey( const PublicKey & pubkey_r );
228 * Remove a public key from the rpm database
230 * \throws RpmException
233 void removePubkey( const PublicKey & pubkey_r );
236 * Return the long ids of all installed public keys.
238 std::list<PublicKey> pubkeys() const;
241 * Return the edition of all installed public keys.
243 std::set<Edition> pubkeyEditions() const;
245 ///////////////////////////////////////////////////////////////////
247 // Direct RPM database retrieval via librpm.
249 ///////////////////////////////////////////////////////////////////
253 * return complete file list for installed package name_r (in FileInfo.filename)
254 * if edition_r != Edition::noedition, check for exact edition
255 * if full==true, fill all attributes of FileInfo
257 std::list<FileInfo> fileList( const std::string & name_r, const Edition & edition_r ) const;
260 * Return true if at least one package owns a certain file (name_r empty)
261 * Return true if package name_r owns file file_r (name_r nonempty).
263 bool hasFile( const std::string & file_r, const std::string & name_r = "" ) const;
266 * Return name of package owning file
267 * or empty string if no installed package owns file
269 std::string whoOwnsFile( const std::string & file_r ) const;
272 * Return true if at least one package provides a certain tag.
274 bool hasProvides( const std::string & tag_r ) const;
277 * Return true if at least one package requires a certain tag.
279 bool hasRequiredBy( const std::string & tag_r ) const;
282 * Return true if at least one package conflicts with a certain tag.
284 bool hasConflicts( const std::string & tag_r ) const;
287 * Return true if package is installed.
289 bool hasPackage( const std::string & name_r ) const;
292 * Return true if package is installed in a certain edition.
294 bool hasPackage( const std::string & name_r, const Edition & ed_r ) const;
297 * Get an installed packages data from rpmdb. Package is
298 * identified by name. Data returned via result are NULL,
299 * if packge is not installed (PMError is not set), or RPM database
300 * could not be read (PMError is set).
302 * \throws RpmException
304 * FIXME this and following comment
307 void getData( const std::string & name_r,
308 RpmHeader::constPtr & result_r ) const;
311 * Get an installed packages data from rpmdb. Package is
312 * identified by name and edition. Data returned via result are NULL,
313 * if packge is not installed (PMError is not set), or RPM database
314 * could not be read (PMError is set).
316 * \throws RpmException
319 void getData( const std::string & name_r, const Edition & ed_r,
320 RpmHeader::constPtr & result_r ) const;
322 ///////////////////////////////////////////////////////////////////
324 ///////////////////////////////////////////////////////////////////
326 /** Sync mode for \ref syncTrustedKeys */
327 enum SyncTrustedKeyBits
329 SYNC_TO_KEYRING = 1<<0, //! export rpm trusted keys into zypp trusted keyring
330 SYNC_FROM_KEYRING = 1<<1, //! import zypp trusted keys into rpm database.
331 SYNC_BOTH = SYNC_TO_KEYRING | SYNC_FROM_KEYRING
334 * Sync trusted keys stored in rpm database and zypp trusted keyring.
336 void syncTrustedKeys( SyncTrustedKeyBits mode_r = SYNC_BOTH );
338 * iterates through zypp keyring and import all non existant keys
341 void importZyppKeyRingTrustedKeys();
343 * insert all rpm trusted keys into zypp trusted keyring
345 void exportTrustedKeysInZyppKeyRing();
349 * The connection to the rpm process.
351 ExternalProgram *process;
353 typedef std::vector<const char*> RpmArgVec;
356 * Run rpm with the specified arguments and handle stderr.
357 * @param n_opts The number of arguments
358 * @param options Array of the arguments, @ref n_opts elements
359 * @param stderr_disp How to handle stderr, merged with stdout by default
361 * \throws RpmException
364 void run_rpm( const RpmArgVec& options,
365 ExternalProgram::Stderr_Disposition stderr_disp =
366 ExternalProgram::Stderr_To_Stdout);
370 * Read a line from the general rpm query
372 bool systemReadLine(std::string &line);
375 * Return the exit status of the general rpm process,
376 * closing the connection if not already done.
381 * Forcably kill the system process
386 * The exit code of the rpm process, or -1 if not yet known.
391 * Error message from running rpm as external program.
392 * Use only if something fail.
394 std::string error_message;
396 /** /var/adm/backup */
397 Pathname _backuppath;
399 /** create package backups? */
400 bool _packagebackups;
402 /** whether <_root>/<WARNINGMAILPATH> was already created */
406 * handle rpm messages like "/etc/testrc saved as /etc/testrc.rpmorig"
408 * @param line rpm output starting with warning:
409 * @param name name of package, appears in subject line
410 * @param typemsg " saved as " or " created as "
411 * @param difffailmsg what to put into mail if diff failed, must contain two %s for the two files
412 * @param diffgenmsg what to put into mail if diff succeeded, must contain two %s for the two files
414 void processConfigFiles(const std::string& line,
415 const std::string& name,
417 const char* difffailmsg,
418 const char* diffgenmsg);
423 typedef std::set<std::string> FileList;
426 * checkPackage result
429 enum CheckPackageResult
431 CHK_OK = 0, /*!< Signature is OK. */
432 CHK_NOTFOUND = 1, /*!< Signature is unknown type. */
433 CHK_FAIL = 2, /*!< Signature does not verify. */
434 CHK_NOTTRUSTED = 3, /*!< Signature is OK, but key is not trusted. */
435 CHK_NOKEY = 4, /*!< Public key is unavailable. */
436 CHK_ERROR = 5, /*!< File does not exist or can't be opened. */
437 CHK_NOSIG = 6, /*!< File has no gpg signature (only digests). */
440 /** Detailed rpm signature check log messages
441 * A single multiline message if \ref CHK_OK. Otherwise each message line
442 * together with it's \ref CheckPackageResult.
444 struct CheckPackageDetail : std::vector<std::pair<CheckPackageResult,std::string>>
448 * Check signature of rpm file on disk (legacy version returning CHK_OK if file is unsigned, like 'rpm -K')
450 * @param path_r which file to check
451 * @param detail_r Return detailed rpm log messages
453 * @return CheckPackageResult (CHK_OK if file is unsigned)
455 * \see also \ref checkPackageSignature
457 CheckPackageResult checkPackage( const Pathname & path_r, CheckPackageDetail & detail_r );
458 /** \overload Ignoring the \a details_r */
459 CheckPackageResult checkPackage( const Pathname & path_r );
462 * Check signature of rpm file on disk (strict check returning CHK_NOSIG if file is unsigned).
464 * @param path_r which file to check
465 * @param detail_r Return detailed rpm log messages
467 * @return CheckPackageResult (CHK_NOSIG if file is unsigned)
469 * \see also \ref checkPackage
471 CheckPackageResult checkPackageSignature( const Pathname & path_r, CheckPackageDetail & detail_r );
473 /** install rpm package
475 * @param filename file to install
476 * @param flags which rpm options to use
480 * \throws RpmException
483 void installPackage ( const Pathname & filename, RpmInstFlags flags = RPMINST_NONE );
485 /** remove rpm package
487 * @param name_r Name of the rpm package to remove.
488 * @param iflags which rpm options to use
492 * \throws RpmException
495 void removePackage( const std::string & name_r, RpmInstFlags flags = RPMINST_NONE );
496 void removePackage( Package::constPtr package, RpmInstFlags flags = RPMINST_NONE );
499 * get backup dir for rpm config files
502 Pathname getBackupPath (void)
508 * create tar.gz of all changed files in a Package
510 * @param packageName name of the Package to backup
514 bool backupPackage(const std::string& packageName);
517 * queries file for name and then calls above backupPackage
518 * function. For convenience.
520 * @param filename rpm file that is about to be installed
522 bool backupPackage(const Pathname& filename);
525 * set path where package backups are stored
529 void setBackupPath(const Pathname& path);
532 * whether to create package backups during install or
535 * @param yes true or false
537 void createPackageBackups(bool yes)
539 _packagebackups = yes;
543 * determine which files of an installed package have been
546 * @param fileList (output) where to store modified files
547 * @param packageName name of package to query
549 * @return false if package couln't be queried for some
552 bool queryChangedFiles(FileList & fileList, const std::string& packageName);
559 virtual std::ostream & dumpOn( std::ostream & str ) const;
562 void doRemovePackage( const std::string & name_r, RpmInstFlags flags, callback::SendReport<RpmRemoveReport> & report );
563 void doInstallPackage( const Pathname & filename, RpmInstFlags flags, callback::SendReport<RpmInstallReport> & report );
564 void doRebuildDatabase(callback::SendReport<RebuildDBReport> & report);
567 /** \relates RpmDb::CheckPackageResult Stream output */
568 std::ostream & operator<<( std::ostream & str, RpmDb::CheckPackageResult obj );
570 /** \relates RpmDb::checkPackageDetail Stream output */
571 std::ostream & operator<<( std::ostream & str, const RpmDb::CheckPackageDetail & obj );
574 } // namespace target
577 #endif // ZYPP_TARGET_RPM_RPMDB_H