001    /**
002     * Copyright (c) 2000-2011 Liferay, Inc. All rights reserved.
003     *
004     * This library is free software; you can redistribute it and/or modify it under
005     * the terms of the GNU Lesser General Public License as published by the Free
006     * Software Foundation; either version 2.1 of the License, or (at your option)
007     * any later version.
008     *
009     * This library is distributed in the hope that it will be useful, but WITHOUT
010     * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
011     * FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
012     * details.
013     */
014    
015    package com.liferay.portal.kernel.webdav;
016    
017    import com.liferay.portal.NoSuchGroupException;
018    import com.liferay.portal.NoSuchUserException;
019    import com.liferay.portal.kernel.dao.orm.QueryUtil;
020    import com.liferay.portal.kernel.log.Log;
021    import com.liferay.portal.kernel.log.LogFactoryUtil;
022    import com.liferay.portal.kernel.util.CharPool;
023    import com.liferay.portal.kernel.util.GetterUtil;
024    import com.liferay.portal.kernel.util.HttpUtil;
025    import com.liferay.portal.kernel.util.OrderByComparator;
026    import com.liferay.portal.kernel.util.StringPool;
027    import com.liferay.portal.kernel.util.StringUtil;
028    import com.liferay.portal.kernel.util.Time;
029    import com.liferay.portal.kernel.util.Validator;
030    import com.liferay.portal.kernel.xml.Namespace;
031    import com.liferay.portal.kernel.xml.SAXReaderUtil;
032    import com.liferay.portal.model.Group;
033    import com.liferay.portal.model.GroupConstants;
034    import com.liferay.portal.model.User;
035    import com.liferay.portal.service.GroupLocalServiceUtil;
036    import com.liferay.portal.service.UserLocalServiceUtil;
037    import com.liferay.portal.util.comparator.GroupFriendlyURLComparator;
038    
039    import java.util.ArrayList;
040    import java.util.Collection;
041    import java.util.Collections;
042    import java.util.LinkedHashMap;
043    import java.util.List;
044    import java.util.Map;
045    import java.util.TreeMap;
046    
047    import javax.servlet.http.HttpServletRequest;
048    
049    /**
050     * @author Brian Wing Shun Chan
051     * @author Alexander Chow
052     */
053    public class WebDAVUtil {
054    
055            public static final Namespace DAV_URI = SAXReaderUtil.createNamespace(
056                    "D", "DAV:");
057    
058            public static final int SC_MULTI_STATUS = 207;
059    
060            public static final int SC_LOCKED = 423;
061    
062            public static final String TOKEN_PREFIX = "opaquelocktoken:";
063    
064            public static void addStorage(WebDAVStorage storage) {
065                    _instance._addStorage(storage);
066            }
067    
068            public static Namespace createNamespace(String prefix, String uri) {
069                    Namespace namespace = null;
070    
071                    if (uri.equals(WebDAVUtil.DAV_URI.getURI())) {
072                            namespace = WebDAVUtil.DAV_URI;
073                    }
074                    else if (Validator.isNull(prefix)) {
075                            namespace = SAXReaderUtil.createNamespace(uri);
076                    }
077                    else {
078                            namespace = SAXReaderUtil.createNamespace(prefix, uri);
079                    }
080    
081                    return namespace;
082            }
083    
084            public static void deleteStorage(WebDAVStorage storage) {
085                    _instance._deleteStorage(storage);
086            }
087    
088            public static long getDepth(HttpServletRequest request) {
089                    String value = GetterUtil.getString(request.getHeader("Depth"));
090    
091                    if (_log.isDebugEnabled()) {
092                            _log.debug("\"Depth\" header is " + value);
093                    }
094    
095                    if (value.equals("0")) {
096                            return 0;
097                    }
098                    else {
099                            return -1;
100                    }
101            }
102    
103            public static String getDestination(
104                    HttpServletRequest request, String rootPath) {
105    
106                    String headerDestination = request.getHeader("Destination");
107                    String[] pathSegments = StringUtil.split(headerDestination, rootPath);
108    
109                    String destination = pathSegments[pathSegments.length - 1];
110    
111                    destination = HttpUtil.decodePath(destination);
112    
113                    if (_log.isDebugEnabled()) {
114                            _log.debug("Destination " + destination);
115                    }
116    
117                    return destination;
118            }
119    
120            public static long getGroupId(long companyId, String path)
121                    throws WebDAVException {
122    
123                    String[] pathArray = getPathArray(path);
124    
125                    return getGroupId(companyId, pathArray);
126            }
127    
128            public static long getGroupId(long companyId, String[] pathArray)
129                    throws WebDAVException {
130    
131                    try {
132                            if (pathArray.length == 0) {
133                                    return 0;
134                            }
135    
136                            String name = pathArray[0];
137    
138                            try {
139                                    Group group = GroupLocalServiceUtil.getGroup(companyId, name);
140    
141                                    return group.getGroupId();
142                            }
143                            catch (NoSuchGroupException nsge) {
144                            }
145    
146                            try {
147                                    Group group = GroupLocalServiceUtil.getFriendlyURLGroup(
148                                            companyId, StringPool.SLASH + name);
149    
150                                    return group.getGroupId();
151                            }
152                            catch (NoSuchGroupException nsge) {
153                            }
154    
155                            try {
156                                    User user = UserLocalServiceUtil.getUserByScreenName(
157                                            companyId, name);
158    
159                                    Group group = user.getGroup();
160    
161                                    return group.getGroupId();
162                            }
163                            catch (NoSuchUserException nsue) {
164                            }
165                    }
166                    catch (Exception e) {
167                            throw new WebDAVException(e);
168                    }
169    
170                    return 0;
171            }
172    
173            public static List<Group> getGroups(long userId) throws Exception {
174                    User user = UserLocalServiceUtil.getUser(userId);
175    
176                    return getGroups(user);
177            }
178    
179            public static List<Group> getGroups(User user) throws Exception {
180    
181                    // Guest
182    
183                    if (user.isDefaultUser()) {
184                            List<Group> groups = new ArrayList<Group>();
185    
186                            Group group = GroupLocalServiceUtil.getGroup(
187                                    user.getCompanyId(), GroupConstants.GUEST);
188    
189                            groups.add(group);
190    
191                            return groups;
192                    }
193    
194                    // Communities
195    
196                    LinkedHashMap<String, Object> params =
197                            new LinkedHashMap<String, Object>();
198    
199                    params.put("usersGroups", user.getUserId());
200    
201                    OrderByComparator orderByComparator = new GroupFriendlyURLComparator(
202                            true);
203    
204                    List<Group> groups = GroupLocalServiceUtil.search(
205                            user.getCompanyId(), null, null, params, QueryUtil.ALL_POS,
206                            QueryUtil.ALL_POS, orderByComparator);
207    
208                    // Organizations
209    
210                    groups.addAll(
211                            GroupLocalServiceUtil.getUserOrganizationsGroups(
212                                    user.getUserId(), QueryUtil.ALL_POS, QueryUtil.ALL_POS));
213    
214                    // User
215    
216                    if (!user.isDefaultUser()) {
217                            groups.add(user.getGroup());
218                    }
219    
220                    Collections.sort(groups, orderByComparator);
221    
222                    return groups;
223            }
224    
225            public static String getLockUuid(HttpServletRequest request)
226                    throws WebDAVException {
227    
228                    String token = StringPool.BLANK;
229    
230                    String value = GetterUtil.getString(request.getHeader("If"));
231    
232                    if (_log.isDebugEnabled()) {
233                            _log.debug("\"If\" header is " + value);
234                    }
235    
236                    if (value.contains("(<DAV:no-lock>)")) {
237                            if (_log.isWarnEnabled()) {
238                                    _log.warn("Lock tokens can never be <DAV:no-lock>");
239                            }
240    
241                            throw new WebDAVException();
242                    }
243    
244                    int beg = value.indexOf(TOKEN_PREFIX);
245    
246                    if (beg >= 0) {
247                            beg += TOKEN_PREFIX.length();
248    
249                            if (beg < value.length()) {
250                                    int end = value.indexOf(CharPool.GREATER_THAN, beg);
251    
252                                    token = GetterUtil.getString(value.substring(beg, end));
253                            }
254                    }
255    
256                    return token;
257            }
258    
259            public static String[] getPathArray(String path) {
260                    return getPathArray(path, false);
261            }
262    
263            public static String[] getPathArray(String path, boolean fixTrailing) {
264                    path = HttpUtil.fixPath(path, true, fixTrailing);
265    
266                    return StringUtil.split(path, CharPool.SLASH);
267            }
268    
269            public static String getResourceName(String[] pathArray) {
270                    if (pathArray.length <= 2) {
271                            return StringPool.BLANK;
272                    }
273                    else {
274                            return pathArray[pathArray.length - 1];
275                    }
276            }
277    
278            public static WebDAVStorage getStorage(String token) {
279                    return _instance._getStorage(token);
280            }
281    
282            public static Collection<String> getStorageTokens() {
283                    return _instance._getStorageTokens();
284            }
285    
286            public static long getTimeout(HttpServletRequest request) {
287                    final String TIME_PREFIX = "Second-";
288    
289                    long timeout = 0;
290    
291                    String value = GetterUtil.getString(request.getHeader("Timeout"));
292    
293                    if (_log.isDebugEnabled()) {
294                            _log.debug("\"Timeout\" header is " + value);
295                    }
296    
297                    int index = value.indexOf(TIME_PREFIX);
298    
299                    if (index >= 0) {
300                            index += TIME_PREFIX.length();
301    
302                            if (index < value.length()) {
303                                    timeout = GetterUtil.getLong(value.substring(index));
304                            }
305                    }
306    
307                    return timeout * Time.SECOND;
308            }
309    
310            public static boolean isOverwrite(HttpServletRequest request) {
311                    return _instance._isOverwrite(request);
312            }
313    
314            private WebDAVUtil() {
315                    _storageMap = new TreeMap<String, WebDAVStorage>();
316            }
317    
318            private void _addStorage(WebDAVStorage storage) {
319                    _storageMap.put(storage.getToken(), storage);
320            }
321    
322            private void _deleteStorage(WebDAVStorage storage) {
323                    if (storage != null) {
324                            _storageMap.remove(storage.getToken());
325                    }
326            }
327    
328            private WebDAVStorage _getStorage(String token) {
329                    return _storageMap.get(token);
330            }
331    
332            private Collection<String> _getStorageTokens() {
333                    return _storageMap.keySet();
334            }
335    
336            private boolean _isOverwrite(HttpServletRequest request) {
337                    String value = GetterUtil.getString(request.getHeader("Overwrite"));
338    
339                    if (value.equalsIgnoreCase("F") || !GetterUtil.getBoolean(value)) {
340                            return false;
341                    }
342                    else {
343                            return true;
344                    }
345            }
346    
347            private static Log _log = LogFactoryUtil.getLog(WebDAVUtil.class);
348    
349            private static WebDAVUtil _instance = new WebDAVUtil();
350    
351            private Map<String, WebDAVStorage> _storageMap;
352    
353    }