1 /*---------------------------------------------------------------------\
3 | |__ / \ / / . \ . \ |
8 \---------------------------------------------------------------------*/
9 /** \file zypp/PoolQuery.cc
17 #include "zypp/base/Logger.h"
18 #include "zypp/base/PtrTypes.h"
19 #include "zypp/base/DefaultIntegral.h"
20 #include "zypp/PoolQuery.h"
21 #include "zypp/base/UserRequestException.h"
23 #include "zypp/sat/Pool.h"
24 #include "zypp/sat/Solvable.h"
25 #include "zypp/sat/SolvAttr.h"
29 #include "satsolver/repo.h"
34 ///////////////////////////////////////////////////////////////////
36 { /////////////////////////////////////////////////////////////////
38 struct PoolQuery::Impl
42 : _flags( 0 | SEARCH_NOCASE | SEARCH_SUBSTRING )
53 static int repo_search_cb(void *cbdata, ::Solvable *s, ::Repodata *data, ::Repokey *key, ::KeyValue *kv)
55 PoolQuery *me = (PoolQuery*) cbdata;
59 sat::Solvable solvable(s - sat::Pool::instance().get()->solvables);
61 // now filter by kind here (we cant do it before)
62 if ( ! me->_pimpl->_kinds.empty() )
64 // the user wants to filter by kind.
65 if ( find( me->_pimpl->_kinds.begin(),
66 me->_pimpl->_kinds.end(),
68 == me->_pimpl->_kinds.end() )
70 // we did not find the kind in the list
71 // so this is not a result.
72 return SEARCH_NEXT_SOLVABLE;
77 r = me->_pimpl->_fnc( makeResObject(solvable) );
81 return SEARCH_NEXT_SOLVABLE;
84 vector<string> _repos;
85 vector<string> _names;
86 vector<Resolvable::Kind> _kinds;
89 mutable PoolQuery::ProcessResolvable _fnc;
91 friend Impl * rwcowClone<Impl>( const Impl * rhs );
92 /** clone for RWCOW_pointer */
94 { return new Impl( *this ); }
96 ///////////////////////////////////////////////////////////////////
98 /** \relates PoolQuery::Impl Stream output */
99 inline std::ostream & operator<<( std::ostream & str, const PoolQuery::Impl & obj )
101 return str << "PoolQuery::Impl";
104 ///////////////////////////////////////////////////////////////////
106 // CLASS NAME : PoolQuery
108 ///////////////////////////////////////////////////////////////////
110 PoolQuery::PoolQuery()
114 PoolQuery::~PoolQuery()
117 void PoolQuery::addKind(const Resolvable::Kind &kind)
118 { _pimpl->_kinds.push_back(kind); }
120 void PoolQuery::setCaseSensitive(const bool value)
123 _pimpl->_flags = (_pimpl->_flags & ~SEARCH_NOCASE);
125 _pimpl->_flags = (_pimpl->_flags | SEARCH_NOCASE);
128 void PoolQuery::setMatchExact(const bool value)
132 _pimpl->_flags = (_pimpl->_flags | SEARCH_STRING);
133 _pimpl->_flags = (_pimpl->_flags & ~SEARCH_REGEX);
134 _pimpl->_flags = (_pimpl->_flags & ~SEARCH_SUBSTRING);
135 _pimpl->_flags = (_pimpl->_flags & ~SEARCH_GLOB);
139 _pimpl->_flags = (_pimpl->_flags & ~SEARCH_STRING);
143 void PoolQuery::addRepo(const std::string &repoalias)
144 { _pimpl->_repos.push_back(repoalias); }
146 void PoolQuery::setFlags(int flags)
147 { _pimpl->_flags = flags; }
149 void PoolQuery::setInstalledOnly()
151 _pimpl->_status_flags = (_pimpl->_status_flags | INSTALLED_ONLY);
154 void PoolQuery::setUninstalledOnly()
156 _pimpl->_status_flags = (_pimpl->_status_flags | UNINSTALLED_ONLY);
159 void PoolQuery::setStatusFilterFlags( int flags )
161 _pimpl->_status_flags = (_pimpl->_status_flags | flags);
164 void PoolQuery::execute(const string &term, ProcessResolvable fnc) const
168 sat::Pool pool(sat::Pool::instance());
169 for ( sat::Pool::RepositoryIterator itr = pool.reposBegin();
170 itr != pool.reposEnd();
173 // filter by installed uninstalled
174 if ( ( _pimpl->_status_flags & INSTALLED_ONLY ) && (itr->name() != sat::Pool::instance().systemRepoName()) )
177 if ( ( _pimpl->_status_flags & UNINSTALLED_ONLY ) && (itr->name() == sat::Pool::instance().systemRepoName()) )
180 // is this repo in users repos?
181 bool included = ( find(_pimpl->_repos.begin(), _pimpl->_repos.end(), itr->name()) != _pimpl->_repos.end() );
183 // only look in user repos filter if the filter is not empty
184 // in this case we search in all
185 if ( _pimpl->_repos.empty() || included )
187 repo_search( itr->get(), 0, 0, term.c_str(), _pimpl->_flags, Impl::repo_search_cb, (void*) (this));
193 /******************************************************************
195 ** FUNCTION NAME : operator<<
196 ** FUNCTION TYPE : ostream &
198 ostream & operator<<( ostream & str, const PoolQuery & obj )
205 * represents all atributes in PoolQuery except SolvAtributes, which is
206 * used as is (not needed extend anythink if someone add new solv attr)
208 struct PoolQueryAttr : public IdStringType<PoolQueryAttr>
211 friend class IdStringType<PoolQueryAttr>;
217 PoolQueryAttr():isSolvAttr(false){}
219 explicit PoolQueryAttr( const char* cstr_r )
220 : _str( cstr_r ),isSolvAttr(false){}
222 explicit PoolQueryAttr( const std::string & str_r )
223 : _str( str_r ),isSolvAttr(false)
226 sat::SolvAttr sa(str_r);
227 if( sa != sat::SolvAttr::noAttr )
235 static const PoolQueryAttr noAttr;
238 static const PoolQueryAttr nameAttr;
239 static const PoolQueryAttr repoAttr;
240 static const PoolQueryAttr kindAttr;
242 // exported attributes from SolvAtributes
246 const PoolQueryAttr PoolQueryAttr::noAttr;
248 const PoolQueryAttr PoolQueryAttr::nameAttr( "name" );
249 const PoolQueryAttr PoolQueryAttr::repoAttr( "repo" );
250 const PoolQueryAttr PoolQueryAttr::kindAttr( "kind" );
252 //\TODO maybe ctor with stream can be usefull
253 bool PoolQuery::recover( istream &str, char delim )
255 bool finded_something = false; //indicates some atributes is finded
261 getline( str, s, delim );
263 if ((!s.empty()) && s[0]=='#') //comment
268 string::size_type pos = s.find(':');
269 if (s.empty() || pos == s.npos) // some garbage on line... act like blank line
271 if (finded_something) //is first blank line after record?
281 finded_something = true;
283 string atrName(str::trim(string(s,0,pos))); // trimmed name of atribute
284 string atrValue(str::trim(string(s,pos+1,s.npos))); //trimmed value
286 PoolQueryAttr attribute( atrName );
288 if ( attribute==PoolQueryAttr::nameAttr)
290 //setName...maybe some regex test
293 else if ( attribute==PoolQueryAttr::repoAttr )
297 else if ( attribute==PoolQueryAttr::kindAttr )
299 addKind( Resolvable::Kind(atrValue) );
301 else if ( attribute==PoolQueryAttr::noAttr )
303 if (attribute.isSolvAttr)
309 //log unknwon atribute
314 //some forget handle new atribute
320 return finded_something;
323 void PoolQuery::serialize( ostream &str, char delim )
327 //iterate thrue all settings and write it
329 for_( it, _pimpl->_repos.begin(), _pimpl->_repos.end() )
331 str << "repo: " << *it << delim ;
334 for_( it, _pimpl->_kinds.begin(), _pimpl->_kinds.end() )
336 str << "kind: " << it->idStr() << delim ;
339 //separating delim - protection
345 /////////////////////////////////////////////////////////////////
347 ///////////////////////////////////////////////////////////////////