1 /*
2 * Licensed to the Apache Software Foundation (ASF) under one or more
3 * contributor license agreements. See the NOTICE file distributed with
4 * this work for additional information regarding copyright ownership.
5 * The ASF licenses this file to You under the Apache License, Version 2.0
6 * (the "License"); you may not use this file except in compliance with
7 * the License. You may obtain a copy of the License at
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 */
17
18 package org.apache.commons.proxy2.interceptor;
19
20 import java.io.Serializable;
21 import java.util.List;
22 import java.util.concurrent.CopyOnWriteArrayList;
23
24 import org.apache.commons.lang3.tuple.ImmutablePair;
25 import org.apache.commons.lang3.tuple.Pair;
26 import org.apache.commons.proxy2.Interceptor;
27 import org.apache.commons.proxy2.Invocation;
28 import org.apache.commons.proxy2.interceptor.matcher.InvocationMatcher;
29
30 /**
31 * A {@link SwitchInterceptor} maintains a list of
32 * {@link org.apache.commons.proxy2.interceptor.matcher.InvocationMatcher}/{@link Interceptor} pairs. Each invocation
33 * will be checked against the registered InvocationMatchers. If one matches the current invocation, then the
34 * corresponding Interceptor will be called. If no InvocationMatchers match, the
35 * {@link org.apache.commons.proxy2.Invocation#proceed()} method is called with no interception.
36 */
37 public class SwitchInterceptor implements Interceptor, Serializable
38 {
39 //******************************************************************************************************************
40 // Fields
41 //******************************************************************************************************************
42
43 private static final long serialVersionUID = 1L;
44
45 private final List<Pair<InvocationMatcher, Interceptor>> cases
46 = new CopyOnWriteArrayList<Pair<InvocationMatcher, Interceptor>>();
47
48 //******************************************************************************************************************
49 // Constructors
50 //******************************************************************************************************************
51
52 public SwitchInterceptor()
53 {
54 }
55
56 //******************************************************************************************************************
57 // Interceptor Implementation
58 //******************************************************************************************************************
59
60 @Override
61 public Object intercept(Invocation invocation) throws Throwable
62 {
63 for (Pair<InvocationMatcher, Interceptor> currentCase : cases)
64 {
65 if (currentCase.getLeft().matches(invocation))
66 {
67 return currentCase.getRight().intercept(invocation);
68 }
69 }
70 return invocation.proceed();
71 }
72
73 //******************************************************************************************************************
74 // Other Methods
75 //******************************************************************************************************************
76
77 public CaseBuilder when(InvocationMatcher matcher)
78 {
79 return new CaseBuilder(matcher);
80 }
81
82 //******************************************************************************************************************
83 // Inner Classes
84 //******************************************************************************************************************
85
86 public class CaseBuilder
87 {
88 private final InvocationMatcher matcher;
89
90 private CaseBuilder(InvocationMatcher matcher)
91 {
92 this.matcher = matcher;
93 }
94
95 public SwitchInterceptor then(Interceptor interceptor)
96 {
97 cases.add(new ImmutablePair<InvocationMatcher, Interceptor>(matcher, interceptor));
98 return SwitchInterceptor.this;
99 }
100 }
101 }