All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.picketlink.http.internal.PathMatcher Maven / Gradle / Ivy

/*
 * JBoss, Home of Professional Open Source.
 * Copyright 2012, Red Hat, Inc., and individual contributors
 * as indicated by the @author tags. See the copyright.txt file in the
 * distribution for a full listing of individual contributors.
 *
 * This is free software; you can redistribute it and/or modify it
 * under the terms of the GNU Lesser General Public License as
 * published by the Free Software Foundation; either version 2.1 of
 * the License, or (at your option) any later version.
 *
 * This software is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this software; if not, write to the Free
 * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
 * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
 */
package org.picketlink.http.internal;

import org.picketlink.config.http.InboundHeaderConfiguration;
import org.picketlink.config.http.PathConfiguration;
import org.picketlink.http.HttpMethod;
import org.picketlink.internal.el.ELProcessor;

import javax.servlet.http.HttpServletRequest;
import java.util.Arrays;
import java.util.Enumeration;
import java.util.List;
import java.util.Map;
import java.util.Set;

/**
 * @author Pedro Igor
 */
public class PathMatcher {

    private static final String ANY_RESOURCE_PATTERN = "/*";
    private final Map> uriConfiguration;
    private final ELProcessor elProcessor;

    public PathMatcher(Map> uriConfiguration, ELProcessor elProcessor) {
        this.uriConfiguration = uriConfiguration;
        this.elProcessor = elProcessor;
    }

    public PathConfiguration matches(HttpServletRequest request) {
        String requestedUri = request.getRequestURI();
        int contextPathIndex = requestedUri.indexOf(request.getContextPath());

        if (contextPathIndex != -1) {
            requestedUri = requestedUri.substring(contextPathIndex + request.getContextPath().length());
        }

        List configurations = null;
        String actualConfig = null;

        for (Map.Entry> entry : this.uriConfiguration.entrySet()) {
            String protectedUri = entry.getKey();
            String selectedUri = null;

            if (protectedUri.equals(ANY_RESOURCE_PATTERN) && actualConfig == null) {
                configurations = this.uriConfiguration.get(entry.getKey());
                selectedUri = protectedUri;
            }

            int suffixIndex = protectedUri.indexOf(ANY_RESOURCE_PATTERN + ".");

            if (suffixIndex != -1) {
                String protectedSuffix = protectedUri.substring(suffixIndex + ANY_RESOURCE_PATTERN.length());

                if (requestedUri.endsWith(protectedSuffix)) {
                    configurations = this.uriConfiguration.get(entry.getKey());
                    selectedUri = protectedUri;
                }
            }

            if (protectedUri.equals(requestedUri)) {
                configurations = this.uriConfiguration.get(entry.getKey());
                selectedUri = protectedUri;
            }

            if (protectedUri.endsWith(ANY_RESOURCE_PATTERN)) {
                String formattedPattern = removeWildCardsFromUri(protectedUri);

                if (!formattedPattern.equals("/") && requestedUri.startsWith(formattedPattern)) {
                    configurations = this.uriConfiguration.get(entry.getKey());
                    selectedUri = protectedUri;
                }

                if (!formattedPattern.equals("/") && formattedPattern.endsWith("/") && formattedPattern.substring(0, formattedPattern.length() - 1).equals(requestedUri)) {
                    configurations = this.uriConfiguration.get(entry.getKey());
                    selectedUri = protectedUri;
                }
            }

            int startRegex = protectedUri.indexOf('{');

            if (startRegex != -1) {
                String prefix = protectedUri.substring(0, startRegex);

                if (requestedUri.startsWith(prefix)) {
                    configurations = this.uriConfiguration.get(entry.getKey());
                    selectedUri = protectedUri;
                }
            }

            if (selectedUri != null) {
                configurations = this.uriConfiguration.get(entry.getKey());
                selectedUri = protectedUri;
            }

            if (selectedUri != null) {
                if (actualConfig == null) {
                    actualConfig = entry.getKey();
                } else {
                    if (actualConfig.equals(ANY_RESOURCE_PATTERN)) {
                        actualConfig = entry.getKey();
                    }

                    if (protectedUri.startsWith(removeWildCardsFromUri(actualConfig))) {
                        actualConfig = entry.getKey();
                    }
                }
            }
        }

        if (configurations != null) {
            if (configurations.size() == 1) {
                return configurations.get(0);
            }

            int configIndex = -1;
            int lastMatchCount = 0;

            for (int i = 0; i < configurations.size(); i++) {
                PathConfiguration pathConfiguration = configurations.get(i);
                InboundHeaderConfiguration headerConfiguration = pathConfiguration.getInboundHeaderConfiguration();
                Set methods = pathConfiguration.getMethods();

                if (!methods.contains(HttpMethod.valueOf(request.getMethod().toUpperCase()))) {
                    continue;
                }

                if (headerConfiguration == null) {
                    if (configIndex == -1) {
                        configIndex = i;
                    }
                } else {
                    Map inboundHeaders = headerConfiguration.getHeaders();

                    if (inboundHeaders.isEmpty()) {
                        configIndex = i;
                    } else {
                        for (String inboundHeaderName : inboundHeaders.keySet()) {
                            Enumeration requestHeaderValues = request.getHeaders(inboundHeaderName);

                            if (requestHeaderValues == null) {
                                break;
                            }

                            List inboundHeaderValues = Arrays.asList(inboundHeaders.get(inboundHeaderName));
                            int matchCount = 0;

                            while (requestHeaderValues.hasMoreElements()) {
                                String requestHeaderValue = requestHeaderValues.nextElement();

                                if (inboundHeaderValues.contains(requestHeaderValue)) {
                                    matchCount++;
                                }
                            }

                            if (matchCount > lastMatchCount) {
                                lastMatchCount = matchCount;
                                configIndex = i;
                            }
                        }
                    }
                }
            }

            if (configIndex >= 0) {
                return configurations.get(configIndex);
            }
        }

        return null;
    }

    private String removeWildCardsFromUri(String protectedUri) {
        return protectedUri.replaceAll("/[*]", "/");
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy