1 /*---------------------------------------------------------------------\
3 | |__ / \ / / . \ . \ |
8 \---------------------------------------------------------------------*/
9 /** \file zypp/repo/RepoFileReader.cc
13 #include "zypp/base/LogTools.h"
14 #include "zypp/base/String.h"
15 #include "zypp/base/Regex.h"
16 #include "zypp/base/InputStream.h"
17 #include "zypp/base/UserRequestException.h"
19 #include "zypp/parser/IniDict.h"
20 #include "zypp/parser/RepoFileReader.h"
24 ///////////////////////////////////////////////////////////////////
27 ///////////////////////////////////////////////////////////////////
30 ///////////////////////////////////////////////////////////////////
33 ///////////////////////////////////////////////////////////////////
34 /// \class RepoFileParser
35 /// \brief Modified \ref IniDict to allow parsing multiple 'baseurl=' entries
36 ///////////////////////////////////////////////////////////////////
37 class RepoFileParser : public IniDict
40 RepoFileParser( const InputStream & is_r )
43 using IniDict::consume; // don't hide overloads we don't redefine here
45 virtual void consume( const std::string & section_r, const std::string & key_r, const std::string & value_r )
47 if ( key_r == "baseurl" )
49 setInBaseurls( true );
50 _baseurls[section_r].push_back( Url(value_r) );
54 setInBaseurls( false );
55 IniDict::consume( section_r, key_r, value_r );
59 virtual void garbageLine( const std::string & section_r, const std::string & line_r )
62 _baseurls[section_r].push_back( Url(line_r) );
64 IniDict::garbageLine( section_r, line_r ); // throw
67 std::list<Url> & baseurls( const std::string & section_r )
68 { return _baseurls[section_r]; }
71 void setInBaseurls( bool yesno_r )
72 { if ( _inBaseurls != yesno_r ) _inBaseurls = yesno_r; }
74 DefaultIntegral<bool,false> _inBaseurls;
75 std::map<std::string,std::list<Url>> _baseurls;
79 ///////////////////////////////////////////////////////////////////
82 * \short List of RepoInfo's from a file.
83 * \param file pathname of the file to read.
85 static void repositories_in_stream( const InputStream &is,
86 const RepoFileReader::ProcessRepo &callback,
87 const ProgressData::ReceiverFnc &progress )
89 RepoFileParser dict(is);
90 for_( its, dict.sectionsBegin(), dict.sectionsEnd() )
95 std::string proxyport;
97 for_( it, dict.entriesBegin(*its), dict.entriesEnd(*its) )
99 //MIL << (*it).first << endl;
100 if (it->first == "name" )
101 info.setName(it-> second);
102 else if ( it->first == "enabled" )
103 info.setEnabled( str::strToTrue( it->second ) );
104 else if ( it->first == "priority" )
105 info.setPriority( str::strtonum<unsigned>( it->second ) );
106 else if ( it->first == "path" )
107 info.setPath( Pathname(it->second) );
108 else if ( it->first == "type" )
109 info.setType(repo::RepoType(it->second));
110 else if ( it->first == "autorefresh" )
111 info.setAutorefresh( str::strToTrue( it->second ) );
112 else if ( it->first == "mirrorlist" && !it->second.empty())
113 info.setMirrorListUrl(Url(it->second));
114 else if ( it->first == "metalink" && !it->second.empty())
115 info.setMetalinkUrl(Url(it->second));
116 else if ( it->first == "gpgkey" && !it->second.empty())
118 std::vector<std::string> keys;
119 str::split( it->second, std::back_inserter(keys) );
120 if ( ! keys.empty() )
121 info.setGpgKeyUrl( Url(*keys.begin()) );
123 else if ( it->first == "gpgcheck" )
124 info.setGpgCheck( str::strToTriBool( it->second ) );
125 else if ( it->first == "repo_gpgcheck" )
126 info.setRepoGpgCheck( str::strToTrue( it->second ) );
127 else if ( it->first == "pkg_gpgcheck" )
128 info.setPkgGpgCheck( str::strToTrue( it->second ) );
129 else if ( it->first == "keeppackages" )
130 info.setKeepPackages( str::strToTrue( it->second ) );
131 else if ( it->first == "service" )
132 info.setService( it->second );
133 else if ( it->first == "proxy" )
135 // Translate it into baseurl queryparams
136 // NOTE: The hack here does not add proxy to mirrorlist urls but the
137 // original code worked without complains, so keep it for now.
138 static const str::regex ex( ":[0-9]+$" ); // portspec
140 if ( str::regex_match( it->second, what, ex ) )
142 proxy = it->second.substr( 0, it->second.size() - what[0].size() );
143 proxyport = what[0].substr( 1 );
151 ERR << "Unknown attribute in [" << *its << "]: " << it->first << "=" << it->second << " ignored" << endl;
154 for ( auto & url : dict.baseurls( *its ) )
156 if ( ! proxy.empty() && url.getQueryParam( "proxy" ).empty() )
158 url.setQueryParam( "proxy", proxy );
159 url.setQueryParam( "proxyport", proxyport );
161 info.addBaseUrl( url );
164 info.setFilepath(is.path());
166 // add it to the list.
168 //if (!progress.tick())
169 // ZYPP_THROW(AbortRequestException());
173 ///////////////////////////////////////////////////////////////////
175 // CLASS NAME : RepoFileReader
177 ///////////////////////////////////////////////////////////////////
179 RepoFileReader::RepoFileReader( const Pathname & repo_file,
180 const ProcessRepo & callback,
181 const ProgressData::ReceiverFnc &progress )
182 : _callback(callback)
184 repositories_in_stream(InputStream(repo_file), _callback, progress);
187 RepoFileReader::RepoFileReader( const InputStream &is,
188 const ProcessRepo & callback,
189 const ProgressData::ReceiverFnc &progress )
190 : _callback(callback)
192 repositories_in_stream(is, _callback, progress);
195 RepoFileReader::~RepoFileReader()
199 std::ostream & operator<<( std::ostream & str, const RepoFileReader & obj )
204 } // namespace parser
205 ///////////////////////////////////////////////////////////////////
207 ///////////////////////////////////////////////////////////////////