Hello community, here is the log from the commit of package libzypp for openSUSE:Factory checked in at 2016-04-30 23:28:45 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Comparing /work/SRC/openSUSE:Factory/libzypp (Old) and /work/SRC/openSUSE:Factory/.libzypp.new (New) ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "libzypp" Changes: -------- --- /work/SRC/openSUSE:Factory/libzypp/libzypp.changes 2016-03-26 15:11:12.000000000 +0100 +++ /work/SRC/openSUSE:Factory/.libzypp.new/libzypp.changes 2016-04-30 23:28:48.000000000 +0200 @@ -1,0 +2,23 @@ +Mon Apr 25 14:59:41 CEST 2016 - [email protected] + +- Fix credential file parser losing entries with known URL but + different user name (bsc#933760) +- RepoManager: allow extraction of multiple baseurls for service + repos (bsc#964932) +- addRepository: fix to use the correct history file for logging +- specfile: add /etc/zypp/credentials.d to the file list +- version 15.22.0 (19) + +------------------------------------------------------------------- +Mon Apr 18 15:03:13 CEST 2016 - [email protected] + +- RepoindexFileReader: fix service metadata TTL default value (bsc#967828) +- version 15.21.7 (19) + +------------------------------------------------------------------- +Fri Apr 15 11:31:08 CEST 2016 - [email protected] + +- DiskUsageCounter: Limit estimated waste per file (bsc#974275) +- version 15.21.6 (19) + +------------------------------------------------------------------- Old: ---- libzypp-15.21.5.tar.bz2 New: ---- libzypp-15.22.0.tar.bz2 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Other differences: ------------------ ++++++ libzypp.spec ++++++ --- /var/tmp/diff_new_pack.WY7OPz/_old 2016-04-30 23:28:49.000000000 +0200 +++ /var/tmp/diff_new_pack.WY7OPz/_new 2016-04-30 23:28:49.000000000 +0200 @@ -19,7 +19,7 @@ %define force_gcc_46 0 Name: libzypp -Version: 15.21.5 +Version: 15.22.0 Release: 0 Url: git://gitorious.org/opensuse/libzypp.git Summary: Package, Patch, Pattern, and Product Management @@ -35,7 +35,7 @@ Provides: libzypp(plugin) = 0 Provides: libzypp(plugin:appdata) = 0 Provides: libzypp(plugin:commit) = 1 -Provides: libzypp(plugin:services) = 0 +Provides: libzypp(plugin:services) = 1 Provides: libzypp(plugin:system) = 1 Provides: libzypp(plugin:urlresolver) = 0 Provides: libzypp(repovarexpand) = 0 @@ -242,6 +242,7 @@ mkdir -p $RPM_BUILD_ROOT%{_sysconfdir}/zypp/systemCheck.d mkdir -p $RPM_BUILD_ROOT%{_sysconfdir}/zypp/vendors.d mkdir -p $RPM_BUILD_ROOT%{_sysconfdir}/zypp/multiversion.d +mkdir -p $RPM_BUILD_ROOT%{_sysconfdir}/zypp/credentials.d mkdir -p $RPM_BUILD_ROOT%{_prefix}/lib/zypp mkdir -p $RPM_BUILD_ROOT%{_prefix}/lib/zypp/plugins mkdir -p $RPM_BUILD_ROOT%{_prefix}/lib/zypp/plugins/appdata @@ -339,6 +340,7 @@ %dir %{_sysconfdir}/zypp/systemCheck.d %dir %{_sysconfdir}/zypp/vendors.d %dir %{_sysconfdir}/zypp/multiversion.d +%dir %{_sysconfdir}/zypp/credentials.d %config(noreplace) %{_sysconfdir}/zypp/zypp.conf %config(noreplace) %{_sysconfdir}/zypp/systemCheck %config(noreplace) %{_sysconfdir}/logrotate.d/zypp-history.lr ++++++ libzypp-15.21.5.tar.bz2 -> libzypp-15.22.0.tar.bz2 ++++++ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/libzypp-15.21.5/VERSION.cmake new/libzypp-15.22.0/VERSION.cmake --- old/libzypp-15.21.5/VERSION.cmake 2016-03-18 13:40:46.000000000 +0100 +++ new/libzypp-15.22.0/VERSION.cmake 2016-04-25 15:05:27.000000000 +0200 @@ -60,9 +60,9 @@ # SET(LIBZYPP_MAJOR "15") SET(LIBZYPP_COMPATMINOR "19") -SET(LIBZYPP_MINOR "21") -SET(LIBZYPP_PATCH "5") +SET(LIBZYPP_MINOR "22") +SET(LIBZYPP_PATCH "0") # -# LAST RELEASED: 15.21.5 (19) +# LAST RELEASED: 15.22.0 (19) # (The number in parenthesis is LIBZYPP_COMPATMINOR) #======= diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/libzypp-15.21.5/doc/autoinclude/FeatureTest.doc new/libzypp-15.22.0/doc/autoinclude/FeatureTest.doc --- old/libzypp-15.21.5/doc/autoinclude/FeatureTest.doc 2016-03-18 13:28:44.000000000 +0100 +++ new/libzypp-15.22.0/doc/autoinclude/FeatureTest.doc 2016-04-25 15:49:26.000000000 +0200 @@ -41,6 +41,8 @@ <DT>\ref plugin-services </DT> <DT>version 0</DT> <DD>Provide a client a list of repositories.</DD> + <DT>version 1</DT> + <DD>Support multiple repo baseurls in plugin services.</DD> </DL></DD> <DT>plugin:system</DT> diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/libzypp-15.21.5/libzypp.spec.cmake new/libzypp-15.22.0/libzypp.spec.cmake --- old/libzypp-15.21.5/libzypp.spec.cmake 2016-03-18 13:28:44.000000000 +0100 +++ new/libzypp-15.22.0/libzypp.spec.cmake 2016-04-25 15:49:26.000000000 +0200 @@ -35,7 +35,7 @@ Provides: libzypp(plugin) = 0 Provides: libzypp(plugin:appdata) = 0 Provides: libzypp(plugin:commit) = 1 -Provides: libzypp(plugin:services) = 0 +Provides: libzypp(plugin:services) = 1 Provides: libzypp(plugin:system) = 1 Provides: libzypp(plugin:urlresolver) = 0 Provides: libzypp(repovarexpand) = 0 @@ -242,6 +242,7 @@ mkdir -p $RPM_BUILD_ROOT%{_sysconfdir}/zypp/systemCheck.d mkdir -p $RPM_BUILD_ROOT%{_sysconfdir}/zypp/vendors.d mkdir -p $RPM_BUILD_ROOT%{_sysconfdir}/zypp/multiversion.d +mkdir -p $RPM_BUILD_ROOT%{_sysconfdir}/zypp/credentials.d mkdir -p $RPM_BUILD_ROOT%{_prefix}/lib/zypp mkdir -p $RPM_BUILD_ROOT%{_prefix}/lib/zypp/plugins mkdir -p $RPM_BUILD_ROOT%{_prefix}/lib/zypp/plugins/appdata @@ -339,6 +340,7 @@ %dir %{_sysconfdir}/zypp/systemCheck.d %dir %{_sysconfdir}/zypp/vendors.d %dir %{_sysconfdir}/zypp/multiversion.d +%dir %{_sysconfdir}/zypp/credentials.d %config(noreplace) %{_sysconfdir}/zypp/zypp.conf %config(noreplace) %{_sysconfdir}/zypp/systemCheck %config(noreplace) %{_sysconfdir}/logrotate.d/zypp-history.lr diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/libzypp-15.21.5/package/libzypp.changes new/libzypp-15.22.0/package/libzypp.changes --- old/libzypp-15.21.5/package/libzypp.changes 2016-03-18 13:40:46.000000000 +0100 +++ new/libzypp-15.22.0/package/libzypp.changes 2016-04-25 15:05:27.000000000 +0200 @@ -1,4 +1,27 @@ ------------------------------------------------------------------- +Mon Apr 25 14:59:41 CEST 2016 - [email protected] + +- Fix credential file parser losing entries with known URL but + different user name (bsc#933760) +- RepoManager: allow extraction of multiple baseurls for service + repos (bsc#964932) +- addRepository: fix to use the correct history file for logging +- specfile: add /etc/zypp/credentials.d to the file list +- version 15.22.0 (19) + +------------------------------------------------------------------- +Mon Apr 18 15:03:13 CEST 2016 - [email protected] + +- RepoindexFileReader: fix service metadata TTL default value (bsc#967828) +- version 15.21.7 (19) + +------------------------------------------------------------------- +Fri Apr 15 11:31:08 CEST 2016 - [email protected] + +- DiskUsageCounter: Limit estimated waste per file (bsc#974275) +- version 15.21.6 (19) + +------------------------------------------------------------------- Fri Mar 18 13:37:22 CET 2016 - [email protected] - Use PluginExecutor for commit- and system-hooks (bnc#971637) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/libzypp-15.21.5/tests/media/CredentialFileReader_test.cc new/libzypp-15.22.0/tests/media/CredentialFileReader_test.cc --- old/libzypp-15.21.5/tests/media/CredentialFileReader_test.cc 2016-02-11 17:22:14.000000000 +0100 +++ new/libzypp-15.22.0/tests/media/CredentialFileReader_test.cc 2016-04-26 18:01:29.000000000 +0200 @@ -34,5 +34,5 @@ CredentialFileReader reader(credfile, bind( &CredCollector::collect, &collector, _1 )); - BOOST_CHECK(collector.creds.size() == 2); + BOOST_CHECK_EQUAL(collector.creds.size(), 3); } diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/libzypp-15.21.5/tests/media/CredentialManager_test.cc new/libzypp-15.22.0/tests/media/CredentialManager_test.cc --- old/libzypp-15.21.5/tests/media/CredentialManager_test.cc 2016-02-11 17:22:14.000000000 +0100 +++ new/libzypp-15.22.0/tests/media/CredentialManager_test.cc 2016-04-26 18:01:29.000000000 +0200 @@ -13,38 +13,47 @@ using namespace zypp; using namespace zypp::media; +inline void testGetCreds( CredentialManager & cm_r, const std::string & url_r, + const std::string & user_r = "", + const std::string & pass_r = "" ) +{ + Url url( url_r ); + AuthData_Ptr cred = cm_r.getCred( url ); + //cout << "FOR: " << url << endl; + //cout << "GOT: " << cred << endl; + if ( user_r.empty() && pass_r.empty() ) + { + BOOST_CHECK_EQUAL( cred, AuthData_Ptr() ); + } + else + { + BOOST_CHECK_EQUAL( cred->username(), user_r ); + BOOST_CHECK_EQUAL( cred->password(), pass_r ); + } +} BOOST_AUTO_TEST_CASE(read_cred_for_url) { CredManagerOptions opts; opts.globalCredFilePath = TESTS_SRC_DIR "/media/data/credentials.cat"; opts.userCredFilePath = Pathname(); + CredentialManager cm( opts ); - CredentialManager cm(opts); - BOOST_CHECK(cm.credsGlobalSize() == 2); + BOOST_CHECK_EQUAL( cm.credsGlobalSize(), 3 ); - Url url("https://drink.it/repo/roots"); - AuthData_Ptr credentials = cm.getCred(url); - BOOST_CHECK(credentials.get() != NULL); - if (!credentials) - return; - BOOST_CHECK(credentials->username() == "ginger"); - BOOST_CHECK(credentials->password() == "ale"); - - Url url2("ftp://[email protected]/download/opensuse/110"); - credentials = cm.getCred(url2); - BOOST_CHECK(credentials.get() != NULL); - if (!credentials) - return; - BOOST_CHECK(credentials->username() == "magda"); - BOOST_CHECK(credentials->password() == "richard"); + testGetCreds( cm, "https://drink.it/repo/roots", "ginger", "ale" ); + testGetCreds( cm, "ftp://weprovidesoft.fr/download/opensuse/110", "agda", "ichard" ); + testGetCreds( cm, "ftp://[email protected]/download/opensuse/110", "magda", "richard" ); + testGetCreds( cm, "ftp://[email protected]/download/opensuse/110", "agda", "ichard" ); + testGetCreds( cm, "ftp://[email protected]/download/opensuse/110" ); // NULL + testGetCreds( cm, "http://url.ok/but/not/creds" ); // NULL } struct CredCollector { bool collect(AuthData_Ptr & cred) { - cout << "got: " << endl << *cred << endl; + //cout << "got: " << endl << *cred << endl; creds.insert(cred); return true; } @@ -56,13 +65,13 @@ BOOST_AUTO_TEST_CASE(save_creds) { filesystem::TmpDir tmp; - CredManagerOptions opts; opts.globalCredFilePath = tmp / "fooha"; - CredentialManager cm1(opts); + AuthData cr1("benson","absolute"); cr1.setUrl(Url("http://joooha.com")); + AuthData cr2("pat","vymetheny"); cr2.setUrl(Url("ftp://filesuck.org")); @@ -70,27 +79,19 @@ cm1.saveInGlobal(cr1); CredCollector collector; - CredentialFileReader reader(opts.globalCredFilePath, - bind( &CredCollector::collect, &collector, _1 )); - BOOST_CHECK(collector.creds.size() == 1); + CredentialFileReader( opts.globalCredFilePath, bind( &CredCollector::collect, &collector, _1 ) ); + BOOST_CHECK_EQUAL( collector.creds.size(), 1 ); - cout << "----" << endl; collector.creds.clear(); - cm1.saveInGlobal(cr2); + CredentialFileReader( opts.globalCredFilePath, bind( &CredCollector::collect, &collector, _1 ) ); + BOOST_CHECK_EQUAL(collector.creds.size(), 2 ); - CredentialFileReader reader1(opts.globalCredFilePath, - bind( &CredCollector::collect, &collector, _1 )); - BOOST_CHECK(collector.creds.size() == 2); - - cout << "----" << endl; collector.creds.clear(); - // save the same creds again cm1.saveInGlobal(cr2); - CredentialFileReader reader2(opts.globalCredFilePath, - bind( &CredCollector::collect, &collector, _1 )); - BOOST_CHECK(collector.creds.size() == 2); + CredentialFileReader( opts.globalCredFilePath, bind( &CredCollector::collect, &collector, _1 ) ); + BOOST_CHECK_EQUAL(collector.creds.size(), 2 ); // todo check created file permissions } @@ -98,30 +99,15 @@ BOOST_AUTO_TEST_CASE(service_base_url) { filesystem::TmpDir tmp; - CredManagerOptions opts; opts.globalCredFilePath = tmp / "fooha"; + CredentialManager cm( opts ); - CredentialManager cm1(opts); - AuthData cr1("benson","absolute"); - cr1.setUrl(Url("http://joooha.com/service/path")); - cm1.addGlobalCred(cr1); - - AuthData_Ptr creds; - creds = cm1.getCred(Url("http://joooha.com/service/path/repo/repofoo")); - - BOOST_CHECK(creds.get() != NULL); - if (!creds) - return; - BOOST_CHECK(creds->username() == "benson"); - - creds = cm1.getCred(Url("http://[email protected]/service/path/repo/repofoo")); - - BOOST_CHECK(creds.get() != NULL); - if (!creds) - return; - BOOST_CHECK(creds->username() == "benson"); - - creds = cm1.getCred(Url("http://[email protected]/service/path/repo/repofoo")); - BOOST_CHECK(creds.get() == NULL); + AuthData cred( "benson","absolute" ); + cred.setUrl( Url( "http://joooha.com/service/path" ) ); + cm.addGlobalCred( cred ); + + testGetCreds( cm, "http://joooha.com/service/path/repo/repofoo", "benson", "absolute" ); + testGetCreds( cm, "http://[email protected]/service/path/repo/repofoo", "benson", "absolute" ); + testGetCreds( cm, "http://[email protected]/service/path/repo/repofoo" ); // NULL } diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/libzypp-15.21.5/tests/media/data/credentials.cat new/libzypp-15.22.0/tests/media/data/credentials.cat --- old/libzypp-15.21.5/tests/media/data/credentials.cat 2016-02-11 17:22:14.000000000 +0100 +++ new/libzypp-15.22.0/tests/media/data/credentials.cat 2016-04-26 18:01:29.000000000 +0200 @@ -1,15 +1,24 @@ +# no 1 [https://drink.it/repo/roots] username=ginger password=ale +#no 2 [ftp://weprovidesoft.fr/download/opensuse/110] username=magda password=richard +# no 3 - same urla s 2 but different user (lex less than magda) +[ftp://weprovidesoft.fr/download/opensuse/110] +username=agda +password=ichard + +# fail [http://url.ok/but/not/creds] username= password=any +# fail [badurl] username=foo password=bar diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/libzypp-15.21.5/zypp/DiskUsageCounter.cc new/libzypp-15.22.0/zypp/DiskUsageCounter.cc --- old/libzypp-15.21.5/zypp/DiskUsageCounter.cc 2016-02-11 17:22:14.000000000 +0100 +++ new/libzypp-15.22.0/zypp/DiskUsageCounter.cc 2016-04-15 11:32:37.000000000 +0200 @@ -71,10 +71,13 @@ unsigned idx = 0; for_( it, result.begin(), result.end() ) { - static const ByteCount blockAdjust( 2, ByteCount::K ); // (files * blocksize) / (2 * 1K) + // Limit estimated waste (half block per file) as it does not apply to + // btrfs, which reports up to 64K blocksize (bsc#974275,bsc#965322) + static const ByteCount blockAdjust( 2, ByteCount::K ); // (files * blocksize) / 2 / 1K; result value in K! + it->pkg_size = it->used_size // current usage + duchanges[idx].kbytes // package data size - + ( duchanges[idx].files * it->block_size / blockAdjust ); // half block per file + + ( duchanges[idx].files * ( it->fstype == "btrfs" ? 4096 : it->block_size ) / blockAdjust ); // half block per file ++idx; } } diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/libzypp-15.21.5/zypp/RepoInfo.cc new/libzypp-15.22.0/zypp/RepoInfo.cc --- old/libzypp-15.21.5/zypp/RepoInfo.cc 2016-02-11 17:22:14.000000000 +0100 +++ new/libzypp-15.22.0/zypp/RepoInfo.cc 2016-04-25 15:05:27.000000000 +0200 @@ -347,6 +347,9 @@ _pimpl->baseUrls().raw().push_back( url_r ); } + void RepoInfo::setBaseUrls( url_set urls ) + { _pimpl->baseUrls().raw().swap( urls ); } + void RepoInfo::setPath( const Pathname &path ) { _pimpl->path = path; } diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/libzypp-15.21.5/zypp/RepoInfo.h new/libzypp-15.22.0/zypp/RepoInfo.h --- old/libzypp-15.21.5/zypp/RepoInfo.h 2016-02-11 17:22:14.000000000 +0100 +++ new/libzypp-15.22.0/zypp/RepoInfo.h 2016-04-25 15:05:27.000000000 +0200 @@ -159,6 +159,10 @@ * Clears current base URL list and adds \a url. */ void setBaseUrl( const Url &url ); + /** + * Clears current base URL list and adds an \ref url_set. + */ + void setBaseUrls( url_set urls ); /** * \short Repository path diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/libzypp-15.21.5/zypp/RepoManager.cc new/libzypp-15.22.0/zypp/RepoManager.cc --- old/libzypp-15.21.5/zypp/RepoManager.cc 2016-02-11 17:22:14.000000000 +0100 +++ new/libzypp-15.22.0/zypp/RepoManager.cc 2016-04-25 15:05:27.000000000 +0200 @@ -64,6 +64,76 @@ /////////////////////////////////////////////////////////////////// namespace { + /////////////////////////////////////////////////////////////////// + /// \class UrlCredentialExtractor + /// \brief Extract credentials in \ref Url authority and store them via \ref CredentialManager. + /// + /// Lazy init CredentialManager and save collected credentials when + /// going out of scope. + /// + /// Methods return whether a password has been collected/extracted. + /// + /// \code + /// UrlCredentialExtractor( "/rootdir" ).collect( oneUrlOrUrlContainer ); + /// \endcode + /// \code + /// { + /// UrlCredentialExtractor extractCredentials; + /// extractCredentials.collect( oneUrlOrUrlContainer ); + /// extractCredentials.extract( oneMoreUrlOrUrlContainer ); + /// .... + /// } + /// \endcode + /// + class UrlCredentialExtractor + { + public: + UrlCredentialExtractor( Pathname & root_r ) + : _root( root_r ) + {} + + ~UrlCredentialExtractor() + { if ( _cmPtr ) _cmPtr->save(); } + + /** Remember credentials stored in URL authority leaving the password in \a url_r. */ + bool collect( const Url & url_r ) + { + bool ret = url_r.hasCredentialsInAuthority(); + if ( ret ) + { + if ( !_cmPtr ) _cmPtr.reset( new media::CredentialManager( _root ) ); + _cmPtr->addUserCred( url_r ); + } + return ret; + } + /** \overload operating on Url container */ + template<class TContainer> + bool collect( const TContainer & urls_r ) + { bool ret = false; for ( const Url & url : urls_r ) { if ( collect( url ) && !ret ) ret = true; } return ret; } + + /** Remember credentials stored in URL authority stripping the passowrd from \a url_r. */ + bool extract( Url & url_r ) + { + bool ret = collect( url_r ); + if ( ret ) + url_r.setPassword( std::string() ); + return ret; + } + /** \overload operating on Url container */ + template<class TContainer> + bool extract( TContainer & urls_r ) + { bool ret = false; for ( Url & url : urls_r ) { if ( extract( url ) && !ret ) ret = true; } return ret; } + + private: + const Pathname & _root; + scoped_ptr<media::CredentialManager> _cmPtr; + }; + } // namespace + /////////////////////////////////////////////////////////////////// + + /////////////////////////////////////////////////////////////////// + namespace + { /** Simple media mounter to access non-downloading URLs e.g. for non-local plaindir repos. * \ingroup g_RAII */ @@ -1596,26 +1666,9 @@ progress.set(90); // check for credentials in Urls - bool havePasswords = false; - for_( urlit, tosave.baseUrlsBegin(), tosave.baseUrlsEnd() ) - if ( urlit->hasCredentialsInAuthority() ) - { - havePasswords = true; - break; - } - // save the credentials - if ( havePasswords ) - { - media::CredentialManager cm( - media::CredManagerOptions(_options.rootDir) ); - - for_(urlit, tosave.baseUrlsBegin(), tosave.baseUrlsEnd()) - if (urlit->hasCredentialsInAuthority()) - //! \todo use a method calling UI callbacks to ask where to save creds? - cm.saveInUser(media::AuthData(*urlit)); - } + UrlCredentialExtractor( _options.rootDir ).collect( tosave.baseUrls() ); - HistoryLog().addRepository(tosave); + HistoryLog(_options.rootDir).addRepository(tosave); progress.toMax(); MIL << "done" << endl; @@ -1823,6 +1876,8 @@ newinfo.setFilepath(toedit.filepath()); reposManip().erase(toedit); reposManip().insert(newinfo); + // check for credentials in Urls + UrlCredentialExtractor( _options.rootDir ).collect( newinfo.baseUrls() ); HistoryLog(_options.rootDir).modifyRepository(toedit, newinfo); MIL << "repo " << alias << " modified" << endl; } @@ -1876,15 +1931,8 @@ saveService( toSave ); _services.insert( toSave ); - // check for credentials in Url (username:password, not ?credentials param) - if ( toSave.url().hasCredentialsInAuthority() ) - { - media::CredentialManager cm( - media::CredManagerOptions(_options.rootDir) ); - - //! \todo use a method calling UI callbacks to ask where to save creds? - cm.saveInUser(media::AuthData(toSave.url())); - } + // check for credentials in Url + UrlCredentialExtractor( _options.rootDir ).collect( toSave.url() ); MIL << "added service " << toSave.alias() << endl; } @@ -1972,7 +2020,7 @@ assert_url( service ); MIL << "Going to refresh service '" << service.alias() << "', url: " << service.url() << ", opts: " << options_r << endl; - if ( service.ttl() && !options_r.testFlag( RefreshService_forceRefresh ) ) + if ( service.ttl() && !( options_r.testFlag( RefreshService_forceRefresh) || options_r.testFlag( RefreshService_restoreStatus ) ) ) { // Service defines a TTL; maybe we can re-use existing data without refresh. Date lrf = service.lrf(); @@ -2051,34 +2099,41 @@ { // First of all: Prepend service alias: it->setAlias( str::form( "%s:%s", service.alias().c_str(), it->alias().c_str() ) ); - // set refrence to the parent service + // set reference to the parent service it->setService( service.alias() ); // remember the new parsed repo state newRepoStates[it->alias()] = *it; - // if the repo url was not set by the repoindex parser, set service's url - Url url; - if ( it->baseUrlsEmpty() ) - url = service.rawUrl(); - else + // - If the repo url was not set by the repoindex parser, set service's url. + // - Libzypp currently has problem with separate url + path handling so just + // append a path, if set, to the baseurls + // - Credentials in the url authority will be extracted later, either if the + // repository is added or if we check for changed urls. + Pathname path; + if ( !it->path().empty() ) { - // service repo can contain only one URL now, so no need to iterate. - url = it->rawUrl(); // raw! + if ( it->path() != "/" ) + path = it->path(); + it->setPath(""); } - // libzypp currently has problem with separate url + path handling - // so just append the path to the baseurl - if ( !it->path().empty() ) + if ( it->baseUrlsEmpty() ) { - Pathname path(url.getPathName()); - path /= it->path(); - url.setPathName( path.asString() ); - it->setPath(""); + Url url( service.rawUrl() ); + if ( !path.empty() ) + url.setPathName( url.getPathName() / path ); + it->setBaseUrl( std::move(url) ); + } + else if ( !path.empty() ) + { + RepoInfo::url_set urls( it->rawBaseUrls() ); + for ( Url & url : urls ) + { + url.setPathName( url.getPathName() / path ); + } + it->setBaseUrls( std::move(urls) ); } - - // save the url - it->setBaseUrl( url ); } //////////////////////////////////////////////////////////////////////////// @@ -2114,7 +2169,8 @@ } //////////////////////////////////////////////////////////////////////////// - // create missing repositories and modify exising ones if needed... + // create missing repositories and modify existing ones if needed... + UrlCredentialExtractor urlCredentialExtractor( _options.rootDir ); // To collect any credentials stored in repo URLs for_( it, collector.repos.begin(), collector.repos.end() ) { // User explicitly requested the repo being enabled? @@ -2239,13 +2295,16 @@ } // changed url? - // service repo can contain only one URL now, so no need to iterate. - if ( oldRepo->rawUrl() != it->rawUrl() ) { - DBG << "Service repo " << it->alias() << " gets new URL " << it->rawUrl() << endl; - oldRepo->setBaseUrl( it->rawUrl() ); - oldRepoModified = true; - } + RepoInfo::url_set newUrls( it->rawBaseUrls() ); + urlCredentialExtractor.extract( newUrls ); // Extract! to prevent passwds from disturbing the comparison below + if ( oldRepo->rawBaseUrls() != newUrls ) + { + DBG << "Service repo " << it->alias() << " gets new URLs " << newUrls << endl; + oldRepo->setBaseUrls( std::move(newUrls) ); + oldRepoModified = true; + } + } // changed gpg check settings? // ATM only plugin services can set GPG values. @@ -2353,6 +2412,9 @@ _services.erase(oldAlias); _services.insert(service); + // check for credentials in Urls + UrlCredentialExtractor( _options.rootDir ).collect( service.url() ); + // changed properties affecting also repositories if ( oldAlias != service.alias() // changed alias diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/libzypp-15.21.5/zypp/media/CredentialFileReader.cc new/libzypp-15.22.0/zypp/media/CredentialFileReader.cc --- old/libzypp-15.21.5/zypp/media/CredentialFileReader.cc 2016-02-11 17:22:14.000000000 +0100 +++ new/libzypp-15.22.0/zypp/media/CredentialFileReader.cc 2016-04-25 15:05:27.000000000 +0200 @@ -22,79 +22,123 @@ #undef ZYPP_BASE_LOGGER_LOGGROUP #define ZYPP_BASE_LOGGER_LOGGROUP "parser" - /////////////////////////////////////////////////////////////////// namespace zypp -{ ///////////////////////////////////////////////////////////////// +{ /////////////////////////////////////////////////////////////////// namespace media - { ///////////////////////////////////////////////////////////////// - - - ////////////////////////////////////////////////////////////////////// - // - // CLASS NAME : CredentialFileReader - // - ////////////////////////////////////////////////////////////////////// - - CredentialFileReader::CredentialFileReader( - const Pathname & crfile, - const ProcessCredentials & callback) { - InputStream is(crfile); - parser::IniDict dict(is); - for (parser::IniDict::section_const_iterator its = dict.sectionsBegin(); - its != dict.sectionsEnd(); - ++its) + /////////////////////////////////////////////////////////////////// + namespace { - Url storedUrl; - if (!its->empty()) + // Looks like INI but allows multiple sections for the same URL + // but different user (in .cat files). So don't use an Ini + // Also support a global section without '[URL]' which is used + // in credential files. + // ------------------------------------- + // username = emptyUSER + // password = emptyPASS + // ------------------------------------- + // [http://server/tmp/sumafake222] + // username = USER + // password = PASS + // + // [http://server/tmp/sumafake222] + // username = USER2 + // password = PASS + // ------------------------------------- + struct CredentialFileReaderImpl : public parser::IniParser { - try { storedUrl = Url(*its); } - catch (const url::UrlException &) - { - ERR << "invalid URL '" << *its << "' in credentials in file: " - << crfile << endl; - continue; - } - } - - AuthData_Ptr credentials; - credentials.reset(new AuthData()); - - // set url - if (storedUrl.isValid()) - credentials->setUrl(storedUrl); - - for (parser::IniDict::entry_const_iterator it = dict.entriesBegin(*its); - it != dict.entriesEnd(*its); - ++it) - { - if (it->first == "username") - credentials->setUsername(it->second); - else if (it->first == "password") - credentials->setPassword(it->second); - else - ERR << "Unknown attribute in [" << crfile << "]: " - << it->second << " ignored" << endl; - } - - if (credentials->valid()) - callback(credentials); - else - ERR << "invalid credentials in file: " << crfile << endl; - } // sections - } + typedef CredentialFileReader::ProcessCredentials ProcessCredentials; + + struct StopParsing {}; + CredentialFileReaderImpl( const Pathname & input_r, const ProcessCredentials & callback_r ) + : _input( input_r ) + , _callback( callback_r ) + { + try + { + parse( input_r ); + } + catch ( StopParsing ) + { /* NO error but consumer aborted parsing */ } + } + + // NO-OP; new sections are opened in consume() + virtual void beginParse() + { /*EMPTY*/ } + + // start a new section [url] + virtual void consume( const std::string & section_r ) + { + endParse(); // close any open section + _secret.reset( new AuthData ); + try + { + _secret->setUrl( Url(section_r) ); + } + catch ( const url::UrlException & ) + { + ERR << "Ignore invalid URL '" << section_r << "' in file " << _input << endl; + _secret.reset(); // ignore this section + } + } + + virtual void consume( const std::string & section_r, const std::string & key_r, const std::string & value_r ) + { + if ( !_secret && section_r.empty() ) + _secret.reset( new AuthData ); // a initial global section without [URL] + + if ( _secret ) + { + if ( key_r == "username" ) + _secret->setUsername( value_r ); + else if ( key_r == "password" ) + _secret->setPassword( value_r ); + else + WAR << "Ignore unknown attribute '" << key_r << "=" << value_r << "' in file " << _input << endl; + } + // else: ignored section due to wrong URL + } + + // send any valid pending section + virtual void endParse() + { + if ( _secret ) + { + if ( _secret->valid() ) + { + if ( !_callback( _secret ) ) + throw( StopParsing() ); + } + else + ERR << "Ignore invalid credentials for URL '" << _secret->url() << "' in file " << _input << endl; + } + } + + private: + const Pathname & _input; + const ProcessCredentials & _callback; + AuthData_Ptr _secret; + }; + } // namespace + /////////////////////////////////////////////////////////////////// + + ////////////////////////////////////////////////////////////////////// + // + // CLASS NAME : CredentialFileReader + // + ////////////////////////////////////////////////////////////////////// - CredentialFileReader::~CredentialFileReader() - {} + CredentialFileReader::CredentialFileReader( const Pathname & crfile_r, const ProcessCredentials & callback_r ) + { CredentialFileReaderImpl( crfile_r, callback_r ); } + CredentialFileReader::~CredentialFileReader() + {} - ///////////////////////////////////////////////////////////////// - } // media + } // namespace media /////////////////////////////////////////////////////////////////// - ///////////////////////////////////////////////////////////////// -} // zypp +} // namespace zypp /////////////////////////////////////////////////////////////////// diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/libzypp-15.21.5/zypp/media/CredentialFileReader.h new/libzypp-15.22.0/zypp/media/CredentialFileReader.h --- old/libzypp-15.21.5/zypp/media/CredentialFileReader.h 2016-02-11 17:22:14.000000000 +0100 +++ new/libzypp-15.22.0/zypp/media/CredentialFileReader.h 2016-04-25 15:05:27.000000000 +0200 @@ -20,43 +20,31 @@ /////////////////////////////////////////////////////////////////// namespace zypp -{ ///////////////////////////////////////////////////////////////// +{ /////////////////////////////////////////////////////////////////// namespace media - { ///////////////////////////////////////////////////////////////// - - - ////////////////////////////////////////////////////////////////////// - // - // CLASS NAME : CredentialFileReader - // - class CredentialFileReader { - public: - /** - * Callback definition. - * First parameter is the \ref Url with which the credentials are - * associated, the second are the credentials. - * - * Return false from the callback to get a \ref AbortRequestException - * to be thrown and the processing to be cancelled. - */ - typedef function<bool(AuthData_Ptr &)> ProcessCredentials; - - CredentialFileReader(const Pathname & crfile, - const ProcessCredentials & callback); - ~CredentialFileReader(); - private: - ProcessCredentials _callback; - }; - ////////////////////////////////////////////////////////////////////// - + ////////////////////////////////////////////////////////////////////// + /// \class CredentialFileReader + /// \brief Parse credentials files and catalogs + class CredentialFileReader + { + public: + /** Callback invoked for each entry found in the file. + * Return \c false to abort parsing. + */ + typedef function<bool(AuthData_Ptr &)> ProcessCredentials; + + CredentialFileReader( const Pathname & crfile_r, const ProcessCredentials & callback_r ); + ~CredentialFileReader(); + private: + ProcessCredentials _callback; + }; + ////////////////////////////////////////////////////////////////////// - ///////////////////////////////////////////////////////////////// - } // media + } // namespace media /////////////////////////////////////////////////////////////////// - ///////////////////////////////////////////////////////////////// -} // zypp +} // namespace zypp /////////////////////////////////////////////////////////////////// #endif /* ZYPP_MEDIA_CREDENTIALFILEREADER_H */ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/libzypp-15.21.5/zypp/media/CredentialManager.cc new/libzypp-15.22.0/zypp/media/CredentialManager.cc --- old/libzypp-15.21.5/zypp/media/CredentialManager.cc 2016-02-11 17:22:14.000000000 +0100 +++ new/libzypp-15.22.0/zypp/media/CredentialManager.cc 2016-04-25 15:05:27.000000000 +0200 @@ -39,23 +39,17 @@ // ////////////////////////////////////////////////////////////////////// - bool - AuthDataComparator::operator()( - const AuthData_Ptr & lhs, const AuthData_Ptr & rhs) + bool AuthDataComparator::operator()( const AuthData_Ptr & lhs, const AuthData_Ptr & rhs ) { - static const url::ViewOption vopt = - url::ViewOption::DEFAULTS - - url::ViewOption::WITH_USERNAME - - url::ViewOption::WITH_PASSWORD - - url::ViewOption::WITH_QUERY_STR; - - if (lhs->username() != rhs->username()) - return true; - - if (lhs->url().asString(vopt) != rhs->url().asString(vopt)) - return true; - - return false; + static const url::ViewOption vopt = url::ViewOption::DEFAULTS + - url::ViewOption::WITH_USERNAME + - url::ViewOption::WITH_PASSWORD + - url::ViewOption::WITH_QUERY_STR; + // std::less semantic! + int cmp = lhs->url().asString(vopt).compare( rhs->url().asString(vopt) ); + if ( ! cmp ) + cmp = lhs->username().compare( rhs->username() ); + return( cmp < 0 ); } ////////////////////////////////////////////////////////////////////// diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/libzypp-15.21.5/zypp/media/MediaUserAuth.cc new/libzypp-15.22.0/zypp/media/MediaUserAuth.cc --- old/libzypp-15.21.5/zypp/media/MediaUserAuth.cc 2016-02-11 17:22:14.000000000 +0100 +++ new/libzypp-15.22.0/zypp/media/MediaUserAuth.cc 2016-04-25 15:05:27.000000000 +0200 @@ -41,9 +41,12 @@ std::ostream & AuthData::dumpOn( std::ostream & str ) const { + if (_url.isValid()) + str << "[" << _url.asString( url::ViewOptions() - url::ViewOptions::WITH_USERNAME - url::ViewOptions::WITH_PASSWORD ) << "]" << endl; + else + str << "[<no-url>]" << endl; str << "username: '" << _username << "'" << std::endl - << "password: " << (_password.empty() ? "<empty>" : "<non-empty>") - << std::endl; + << "password: " << (_password.empty() ? "<empty>" : "<non-empty>"); return str; } @@ -83,8 +86,8 @@ std::ostream & CurlAuthData::dumpOn( std::ostream & str ) const { - AuthData::dumpOn(str) << " auth_type: " << _auth_type_str - << " (" << _auth_type << ")" << std::endl; + AuthData::dumpOn(str) << endl + << " auth_type: " << _auth_type_str << " (" << _auth_type << ")"; return str; } diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/libzypp-15.21.5/zypp/parser/RepoindexFileReader.cc new/libzypp-15.22.0/zypp/parser/RepoindexFileReader.cc --- old/libzypp-15.21.5/zypp/parser/RepoindexFileReader.cc 2016-02-11 17:22:14.000000000 +0100 +++ new/libzypp-15.22.0/zypp/parser/RepoindexFileReader.cc 2016-04-18 15:04:47.000000000 +0200 @@ -113,7 +113,7 @@ */ bool consumeNode( Reader & reader_r ); - DefaultIntegral<Date::Duration,2> _ttl; + DefaultIntegral<Date::Duration,0> _ttl; private: bool getAttrValue( const std::string & key_r, Reader & reader_r, std::string & value_r ) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/libzypp-15.21.5/zypp/target/rpm/RpmDb.cc new/libzypp-15.22.0/zypp/target/rpm/RpmDb.cc --- old/libzypp-15.21.5/zypp/target/rpm/RpmDb.cc 2016-02-11 17:22:14.000000000 +0100 +++ new/libzypp-15.22.0/zypp/target/rpm/RpmDb.cc 2016-04-13 10:24:44.000000000 +0200 @@ -1525,7 +1525,8 @@ if ( res == 0 ) { - detail_r.push_back( CheckPackageDetail::value_type( CHK_OK, std::move(vresult) ) ); + // remove trailing NL! + detail_r.push_back( CheckPackageDetail::value_type( CHK_OK, str::rtrim( std::move(vresult) ) ) ); return CHK_OK; }
