dunni
dunni

Reputation: 44565

Mapping a URL to the most specific context root

i have the following situation:
I want to map incoming queries (i use a servlet filter to access the queries) to the suitable applications. For this, i have a table where i map the applications to their contextroots, e.g.:

/application1/             |  Application1 Rootcontext 
/application1/subcontext1  |  Application1 Subcontext 1  
/application1/subcontext2  |  Application1 Subcontext 2  
/application2/             |  Application2

So when i have a query with the path /application1/subcontext1/someotherpath, i want to get Application1 Subcontext 1, when i have a query URL /application1/sompath, i want to get Application 1 Rootcontext.

My first guess was, that i build some sort of tree with my mappings of the contextroots (every part of that URL as a node), and then split up the query URL and walk down the tree to get the most specific application mapping.

Would that be the best solution, or do you have any other suggestions for my problem?

Upvotes: 2

Views: 119

Answers (1)

ShyJ
ShyJ

Reputation: 4650

Instead of a tree and walking forwards you can have your map as a Map<String, ApplicationContext> and walk backwards until you find the first non-null fit. This code should give you a rough idea of how to do it:

import java.util.HashMap;
import java.util.Map;

public class Main {
    public static final class ApplicationContext {
        private final String app;
        private final String ctx;

        public ApplicationContext(final String app, final String ctx) {
            this.app = app;
            this.ctx = ctx;
        }

        @Override
        public String toString() {
            return "ApplicationContext[" + app + "/" + ctx + "]";
        }
    }

    private static ApplicationContext ac(final String app, final String ctx) {
        return new ApplicationContext(app, ctx);
    }

    private static ApplicationContext getApplicationContext(final String url,
            final Map<String, ApplicationContext> urlMap) {
        String specificUrl = url;
        ApplicationContext result = null;
        while (specificUrl != null && result == null) {
            result = urlMap.get(specificUrl);
            specificUrl = shortenUrl(specificUrl);
        }

        return result;
    }

    public static void main(final String[] args) throws Exception {
        final Map<String, ApplicationContext> urlMap = new HashMap<String, ApplicationContext>();
        urlMap.put("/application1", ac("Application1", "Root"));
        urlMap.put("/application1/subcontext1", ac("Application1", "SubContext1"));
        urlMap.put("/application1/subcontext2", ac("Application1", "SubContext2"));
        urlMap.put("/application1/subcontext2/subcontext3", ac("Application1", "SubContext3"));
        urlMap.put("/application2", ac("Application2", null));

        System.out.println(getApplicationContext("/application1/", urlMap));
        System.out.println(getApplicationContext("/application1/abc", urlMap));
        System.out.println(getApplicationContext("/application1/subcontext2/abc", urlMap));
    }

    private static String shortenUrl(final String url) {
        final int index = url.lastIndexOf('/');
        if (index > 0) {
            return url.substring(0, index);
        }
        else {
            return null;
        }
    }
}

And a fiddle for it.

Upvotes: 1

Related Questions