1 | /* |
2 | This file is part of libkldap. |
3 | Copyright (c) 2004-2006 Szombathelyi György <gyurco@freemail.hu> |
4 | |
5 | This library is free software; you can redistribute it and/or |
6 | modify it under the terms of the GNU Library General Public |
7 | License as published by the Free Software Foundation; either |
8 | version 2 of the License, or (at your option) any later version. |
9 | |
10 | This library is distributed in the hope that it will be useful, |
11 | but WITHOUT ANY WARRANTY; without even the implied warranty of |
12 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
13 | Library General Public License for more details. |
14 | |
15 | You should have received a copy of the GNU Library General Public License |
16 | along with this library; see the file COPYING.LIB. If not, write to |
17 | the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, |
18 | Boston, MA 02110-1301, USA. |
19 | */ |
20 | |
21 | #include "ldapurl.h" |
22 | |
23 | #include <kdebug.h> |
24 | |
25 | #include <QtCore/QStringList> |
26 | |
27 | using namespace KLDAP; |
28 | |
29 | class LdapUrl::LdapUrlPrivate |
30 | { |
31 | public: |
32 | LdapUrlPrivate() |
33 | : m_scope( Base ) |
34 | { |
35 | } |
36 | |
37 | QMap<QString, Extension> m_extensions; |
38 | QStringList m_attributes; |
39 | Scope m_scope; |
40 | QString m_filter; |
41 | }; |
42 | |
43 | LdapUrl::LdapUrl() |
44 | : d( new LdapUrlPrivate ) |
45 | { |
46 | } |
47 | |
48 | LdapUrl::LdapUrl( const KUrl &_url ) |
49 | : KUrl( _url ), d( new LdapUrlPrivate ) |
50 | { |
51 | QString tmp = path(); |
52 | if ( tmp.startsWith( QLatin1Char('/') ) ) { |
53 | tmp = tmp.mid( 1 ); |
54 | } |
55 | setPath( tmp ); |
56 | parseQuery(); |
57 | } |
58 | |
59 | LdapUrl::LdapUrl( const LdapUrl &that ) |
60 | : KUrl( that ), d( new LdapUrlPrivate ) |
61 | { |
62 | *d = *that.d; |
63 | } |
64 | |
65 | LdapUrl &LdapUrl::operator=( const LdapUrl &that ) |
66 | { |
67 | if ( this == &that ) { |
68 | return *this; |
69 | } |
70 | |
71 | KUrl::operator=( that ); |
72 | *d = *that.d; |
73 | |
74 | return *this; |
75 | } |
76 | |
77 | LdapUrl::~LdapUrl() |
78 | { |
79 | delete d; |
80 | } |
81 | |
82 | void LdapUrl::setDn( const LdapDN &dn ) |
83 | { |
84 | QString tmp = dn.toString(); |
85 | if ( tmp.startsWith( QLatin1Char('/') ) ) { |
86 | tmp = tmp.mid( 1 ); |
87 | } |
88 | setPath( tmp ); |
89 | } |
90 | |
91 | LdapDN LdapUrl::dn() const |
92 | { |
93 | QString tmp = path(); |
94 | if ( tmp.startsWith( QLatin1Char('/') ) ) { |
95 | tmp = tmp.mid( 1 ); |
96 | } |
97 | LdapDN tmpDN( tmp ); |
98 | return tmpDN; |
99 | } |
100 | |
101 | QStringList LdapUrl::attributes() const |
102 | { |
103 | return d->m_attributes; |
104 | } |
105 | |
106 | void LdapUrl::setAttributes( const QStringList &attributes ) |
107 | { |
108 | d->m_attributes=attributes; |
109 | updateQuery(); |
110 | } |
111 | |
112 | LdapUrl::Scope LdapUrl::scope() const |
113 | { |
114 | return d->m_scope; |
115 | } |
116 | |
117 | void LdapUrl::setScope( Scope scope ) |
118 | { |
119 | d->m_scope = scope; |
120 | updateQuery(); |
121 | } |
122 | |
123 | QString LdapUrl::filter() const |
124 | { |
125 | return d->m_filter; |
126 | } |
127 | |
128 | void LdapUrl::setFilter( const QString &filter ) |
129 | { |
130 | d->m_filter = filter; |
131 | updateQuery(); |
132 | } |
133 | |
134 | bool LdapUrl::hasExtension( const QString &key ) const |
135 | { |
136 | return d->m_extensions.contains( key ); |
137 | } |
138 | |
139 | LdapUrl::Extension LdapUrl::extension( const QString &key ) const |
140 | { |
141 | QMap<QString, Extension>::const_iterator it; |
142 | |
143 | it = d->m_extensions.constFind( key ); |
144 | if ( it != d->m_extensions.constEnd() ) { |
145 | return ( *it ); |
146 | } else { |
147 | Extension ext; |
148 | ext.value = QLatin1String("" ); |
149 | ext.critical = false; |
150 | return ext; |
151 | } |
152 | } |
153 | |
154 | QString LdapUrl::extension( const QString &key, bool &critical ) const |
155 | { |
156 | Extension ext; |
157 | |
158 | ext = extension( key ); |
159 | critical = ext.critical; |
160 | return ext.value; |
161 | } |
162 | |
163 | void LdapUrl::setExtension( const QString &key, const LdapUrl::Extension &ext ) |
164 | { |
165 | d->m_extensions[ key ] = ext; |
166 | updateQuery(); |
167 | } |
168 | |
169 | void LdapUrl::setExtension( const QString &key, const QString &value, bool critical ) |
170 | { |
171 | Extension ext; |
172 | ext.value = value; |
173 | ext.critical = critical; |
174 | setExtension( key, ext ); |
175 | } |
176 | |
177 | void LdapUrl::setExtension( const QString &key, int value, bool critical ) |
178 | { |
179 | Extension ext; |
180 | ext.value = QString::number( value ); |
181 | ext.critical = critical; |
182 | setExtension( key, ext ); |
183 | } |
184 | |
185 | void LdapUrl::removeExtension( const QString &key ) |
186 | { |
187 | d->m_extensions.remove( key ); |
188 | updateQuery(); |
189 | } |
190 | |
191 | void LdapUrl::updateQuery() |
192 | { |
193 | QMap<QString, Extension>::const_iterator it; |
194 | QString q( QLatin1Char('?') ); |
195 | |
196 | // set the attributes to query |
197 | if ( !d->m_attributes.isEmpty() ) { |
198 | q += d->m_attributes.join( QLatin1String("," ) ); |
199 | } |
200 | |
201 | // set the scope |
202 | q += QLatin1Char('?'); |
203 | switch ( d->m_scope ) { |
204 | case Sub: |
205 | q += QLatin1String("sub" ); |
206 | break; |
207 | case One: |
208 | q += QLatin1String("one" ); |
209 | break; |
210 | case Base: |
211 | q += QLatin1String("base" ); |
212 | break; |
213 | } |
214 | |
215 | // set the filter |
216 | q += QLatin1Char('?'); |
217 | if ( d->m_filter != QLatin1String("(objectClass=*)" ) && !d->m_filter.isEmpty() ) { |
218 | q += QLatin1String(toPercentEncoding( d->m_filter )); |
219 | } |
220 | |
221 | // set the extensions |
222 | q += QLatin1Char('?'); |
223 | for ( it = d->m_extensions.constBegin(); it != d->m_extensions.constEnd(); ++it ) { |
224 | if ( it.value().critical ) { |
225 | q += QLatin1Char('!'); |
226 | } |
227 | q += it.key(); |
228 | if ( !it.value().value.isEmpty() ) { |
229 | q += QLatin1Char('=') + QLatin1String(toPercentEncoding( it.value().value )); |
230 | } |
231 | q += QLatin1Char(','); |
232 | } |
233 | while ( q.endsWith( QLatin1Char('?') ) || q.endsWith( QLatin1Char(',') ) ) { |
234 | q.remove( q.length() - 1, 1 ); |
235 | } |
236 | |
237 | setQuery( q ); |
238 | kDebug() << "LDAP URL updateQuery():" << prettyUrl(); |
239 | } |
240 | |
241 | void LdapUrl::parseQuery() |
242 | { |
243 | Extension ext; |
244 | QStringList extensions; |
245 | QString q = query(); |
246 | // remove first ? |
247 | if ( q.startsWith( QLatin1Char('?') ) ) { |
248 | q.remove( 0, 1 ); |
249 | } |
250 | |
251 | // split into a list |
252 | QStringList url_items = q.split( QLatin1Char('?') ); |
253 | |
254 | d->m_attributes.clear(); |
255 | d->m_scope = Base; |
256 | d->m_filter = QLatin1String("(objectClass=*)" ); |
257 | d->m_extensions.clear(); |
258 | |
259 | int i = 0; |
260 | QStringList::const_iterator end( url_items.constEnd() ); |
261 | for ( QStringList::const_iterator it=url_items.constBegin(); |
262 | it != end; ++it, i++ ) { |
263 | switch ( i ) { |
264 | case 0: |
265 | d->m_attributes = ( *it ).split( QLatin1Char(','), QString::SkipEmptyParts ); |
266 | break; |
267 | case 1: |
268 | if ( ( *it ) == QLatin1String( "sub" ) ) { |
269 | d->m_scope = Sub; |
270 | } else if ( ( *it ) == QLatin1String( "one" ) ) { |
271 | d->m_scope = One; |
272 | } |
273 | break; |
274 | case 2: |
275 | d->m_filter = fromPercentEncoding( ( *it ).toLatin1() ); |
276 | break; |
277 | case 3: |
278 | extensions = ( *it ).split( QLatin1Char(','), QString::SkipEmptyParts ); |
279 | break; |
280 | } |
281 | } |
282 | |
283 | QString name, value; |
284 | QStringList::const_iterator end2( extensions.constEnd() ); |
285 | for ( QStringList::const_iterator it=extensions.constBegin(); |
286 | it != end2; ++it ) { |
287 | ext.critical = false; |
288 | name = fromPercentEncoding( ( *it ).section( QLatin1Char('='), 0, 0 ).toLatin1() ).toLower(); |
289 | value = fromPercentEncoding( ( *it ).section( QLatin1Char('='), 1 ).toLatin1() ); |
290 | if ( name.startsWith( QLatin1Char('!') ) ) { |
291 | ext.critical = true; |
292 | name.remove( 0, 1 ); |
293 | } |
294 | kDebug() << "LdapUrl extensions name=" << name << "value:" << value; |
295 | ext.value = value.replace( QLatin1String("%2" ), QLatin1String("," ) ); |
296 | setExtension( name, ext ); |
297 | } |
298 | } |
299 | |