Package org.geoserver.flow.controller

Source Code of org.geoserver.flow.controller.IpBlacklistFilter

/* (c) 2014 Open Source Geospatial Foundation - all rights reserved
* (c) 2001 - 2013 OpenPlans
* This code is licensed under the GPL 2.0 license, available at the root
* application directory.
*/
package org.geoserver.flow.controller;

import java.io.File;
import java.io.IOException;
import java.util.Collections;
import java.util.HashSet;
import java.util.Properties;
import java.util.Set;
import java.util.logging.Level;
import java.util.logging.Logger;

import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.geoserver.filters.GeoServerFilter;
import org.geoserver.platform.GeoServerExtensions;
import org.geoserver.platform.GeoServerResourceLoader;
import org.geoserver.platform.resource.Resource;
import org.geoserver.security.PropertyFileWatcher;
import org.geotools.util.logging.Logging;

/**
* A class that allows the configuration of an ip black list, rejecting requests from ip addresses configured in the controlflow.properties file
*
* @author Juan Marin, OpenGeo
*
*/

public class IpBlacklistFilter implements GeoServerFilter {

    static final Logger LOGGER = Logging.getLogger(IpBlacklistFilter.class);
    static final String PROPERTYFILENAME="controlflow.properties";
    static final String BLPROPERTY="ip.blacklist";
    static final String WLPROPERTY="ip.whitelist";
    private Set<String> blackListedAddresses;
    private Set<String> whiteListedAddresses;

    private final PropertyFileWatcher configFile;
   
    /**
     * Constructor used for testing purposes
     *
     * @param props
     */
    public IpBlacklistFilter(Properties props) {
        this.blackListedAddresses = loadConfiguration(props, BLPROPERTY);
        this.whiteListedAddresses = loadConfiguration(props, WLPROPERTY);
        configFile = null;
    }

    /**
     * Default constructor
     */
    public IpBlacklistFilter() {
        try {
            GeoServerResourceLoader loader = GeoServerExtensions.bean(GeoServerResourceLoader.class);
            Resource resource = loader.get(PROPERTYFILENAME);
            configFile = new PropertyFileWatcher(resource);
            blackListedAddresses = reloadConfiguration(BLPROPERTY);
            whiteListedAddresses = reloadConfiguration(WLPROPERTY);
        } catch (Exception e) {
            LOGGER.log(Level.FINER, e.getMessage(), e);
            throw new RuntimeException(e);
        }
    }

    /**
     * Filters ip black list
     */
    @Override
    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain)
            throws IOException, ServletException {

        HttpServletRequest httpRequest = (HttpServletRequest) request;
       
        if (isBlackListed(httpRequest)) {
            if (response instanceof HttpServletResponse) {
                HttpServletResponse httpResponse = (HttpServletResponse) response;
                    httpResponse.sendError(HttpServletResponse.SC_FORBIDDEN,
                            "This IP has been blocked. Please contact the server administrator");
                    return;
            }
        }

        chain.doFilter(request, response);
    }

    private boolean isBlackListed(HttpServletRequest httpRequest) throws IOException {
        if(configFile != null && configFile.isStale()){
            synchronized(configFile){
                if(configFile.isStale()){
                    this.blackListedAddresses = reloadConfiguration(BLPROPERTY);
                    this.whiteListedAddresses = reloadConfiguration(WLPROPERTY);
                }
            }
        }
        if(blackListedAddresses.isEmpty()){
            return false;
        }
        String incomingIp = IpFlowController.getRemoteAddr(httpRequest);
        boolean blocked=false;
        //Check IP on blackList roles (to block)
        for(String blackListRole: blackListedAddresses){
          if(incomingIp.matches(blackListRole)){
            blocked=true;
            break;
          }
        }
       
        //Check IP (if blocked) on whiteList roles (to unlock)
        if(blocked && !whiteListedAddresses.isEmpty()){
          for(String whiteListRole: whiteListedAddresses){
              if(incomingIp.matches(whiteListRole)){
                blocked=false;
                break;
              }
            }
        }
        return blocked;
    }

    private Set<String> reloadConfiguration(String property) throws IOException {
        Properties props = configFile.getProperties();
        if(props == null){
            //file doesn't exist
            return Collections.emptySet();
        }
        return loadConfiguration(props,property);
    }

    private Set<String> loadConfiguration(Properties props, String property) {
        String rawList = props.getProperty(property);
        if(null == rawList){
            return Collections.emptySet();
        }
        Set<String> ipAddresses = new HashSet<String>();
        for(String ip : rawList.split(",")){
            ipAddresses.add(ip.trim().replaceAll("\\*","(.{0,1}[0-9]+.{0,1}){0,4}"));
        }
        return ipAddresses;
    }

    @Override
    public void init(FilterConfig config) throws ServletException {
        // TODO Auto-generated method stub
    }

    @Override
    public void destroy() {
        // TODO Auto-generated method stub
    }

}
TOP

Related Classes of org.geoserver.flow.controller.IpBlacklistFilter

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.