• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2009 Mike Cumings
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *   http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package com.kenai.jbosh;
18 
19 import java.util.HashMap;
20 import java.util.Map;
21 
22 /**
23  * Terminal binding conditions and their associated messages.
24  */
25 final class TerminalBindingCondition {
26 
27     /**
28      * Map of condition names to condition instances.
29      */
30     private static final Map<String, TerminalBindingCondition>
31             COND_TO_INSTANCE = new HashMap<String, TerminalBindingCondition>();
32 
33     /**
34      * Map of HTTP response codes to condition instances.
35      */
36     private static final Map<Integer, TerminalBindingCondition>
37             CODE_TO_INSTANCE = new HashMap<Integer, TerminalBindingCondition>();
38 
39     static final TerminalBindingCondition BAD_REQUEST =
40             createWithCode("bad-request", "The format of an HTTP header or "
41             + "binding element received from the client is unacceptable "
42             + "(e.g., syntax error).", Integer.valueOf(400));
43 
44     static final TerminalBindingCondition HOST_GONE =
45             create("host-gone", "The target domain specified in the 'to' "
46             + "attribute or the target host or port specified in the 'route' "
47             + "attribute is no longer serviced by the connection manager.");
48 
49     static final TerminalBindingCondition HOST_UNKNOWN =
50             create("host-unknown", "The target domain specified in the 'to' "
51             + "attribute or the target host or port specified in the 'route' "
52             + "attribute is unknown to the connection manager.");
53 
54     static final TerminalBindingCondition IMPROPER_ADDRESSING =
55             create("improper-addressing", "The initialization element lacks a "
56             + "'to' or 'route' attribute (or the attribute has no value) but "
57             + "the connection manager requires one.");
58 
59     static final TerminalBindingCondition INTERNAL_SERVER_ERROR =
60             create("internal-server-error", "The connection manager has "
61             + "experienced an internal error that prevents it from servicing "
62             + "the request.");
63 
64     static final TerminalBindingCondition ITEM_NOT_FOUND =
65             createWithCode("item-not-found", "(1) 'sid' is not valid, (2) "
66             + "'stream' is not valid, (3) 'rid' is larger than the upper limit "
67             + "of the expected window, (4) connection manager is unable to "
68             + "resend response, (5) 'key' sequence is invalid.",
69             Integer.valueOf(404));
70 
71     static final TerminalBindingCondition OTHER_REQUEST =
72             create("other-request", "Another request being processed at the "
73             + "same time as this request caused the session to terminate.");
74 
75     static final TerminalBindingCondition POLICY_VIOLATION =
76             createWithCode("policy-violation", "The client has broken the "
77             + "session rules (polling too frequently, requesting too "
78             + "frequently, sending too many simultaneous requests).",
79             Integer.valueOf(403));
80 
81     static final TerminalBindingCondition REMOTE_CONNECTION_FAILED =
82             create("remote-connection-failed", "The connection manager was "
83             + "unable to connect to, or unable to connect securely to, or has "
84             + "lost its connection to, the server.");
85 
86     static final TerminalBindingCondition REMOTE_STREAM_ERROR =
87             create("remote-stream-error", "Encapsulated transport protocol "
88             + "error.");
89 
90     static final TerminalBindingCondition SEE_OTHER_URI =
91             create("see-other-uri", "The connection manager does not operate "
92             + "at this URI (e.g., the connection manager accepts only SSL or "
93             + "TLS connections at some https: URI rather than the http: URI "
94             + "requested by the client).");
95 
96     static final TerminalBindingCondition SYSTEM_SHUTDOWN =
97             create("system-shutdown", "The connection manager is being shut "
98             + "down. All active HTTP sessions are being terminated. No new "
99             + "sessions can be created.");
100 
101     static final TerminalBindingCondition UNDEFINED_CONDITION =
102             create("undefined-condition", "Unknown or undefined error "
103             + "condition.");
104 
105     /**
106      * Condition name.
107      */
108     private final String cond;
109 
110     /**
111      * Descriptive message.
112      */
113     private final String msg;
114 
115     /**
116      * Private constructor to pre
117      */
TerminalBindingCondition( final String condition, final String message)118     private TerminalBindingCondition(
119             final String condition,
120             final String message) {
121         cond = condition;
122         msg = message;
123     }
124 
125     /**
126      * Helper method to call the helper method to add entries.
127      */
create( final String condition, final String message)128     private static TerminalBindingCondition create(
129             final String condition,
130             final String message) {
131         return createWithCode(condition, message, null);
132     }
133 
134     /**
135      * Helper method to add entries.
136      */
createWithCode( final String condition, final String message, final Integer code)137     private static TerminalBindingCondition createWithCode(
138             final String condition,
139             final String message,
140             final Integer code) {
141         if (condition == null) {
142             throw(new IllegalArgumentException(
143                     "condition may not be null"));
144         }
145         if (message == null) {
146             throw(new IllegalArgumentException(
147                     "message may not be null"));
148         }
149         if (COND_TO_INSTANCE.get(condition) != null) {
150             throw(new IllegalStateException(
151                     "Multiple definitions of condition: " + condition));
152         }
153         TerminalBindingCondition result =
154                 new TerminalBindingCondition(condition, message);
155         COND_TO_INSTANCE.put(condition, result);
156         if (code != null) {
157             if (CODE_TO_INSTANCE.get(code) != null) {
158                 throw(new IllegalStateException(
159                         "Multiple definitions of code: " + code));
160             }
161             CODE_TO_INSTANCE.put(code, result);
162         }
163         return result;
164     }
165 
166     /**
167      * Lookup the terminal binding condition instance with the condition
168      * name specified.
169      *
170      * @param condStr condition name
171      * @return terminal binding condition instance, or {@code null} if no
172      *  instance is known by the name specified
173      */
forString(final String condStr)174     static TerminalBindingCondition forString(final String condStr) {
175         return COND_TO_INSTANCE.get(condStr);
176     }
177 
178     /**
179      * Lookup the terminal binding condition instance associated with the
180      * HTTP response code specified.
181      *
182      * @param httpRespCode HTTP response code
183      * @return terminal binding condition instance, or {@code null} if no
184      *  instance is known by the response code specified
185      */
forHTTPResponseCode(final int httpRespCode)186     static TerminalBindingCondition forHTTPResponseCode(final int httpRespCode) {
187         return CODE_TO_INSTANCE.get(Integer.valueOf(httpRespCode));
188     }
189 
190     /**
191      * Get the name of the condition.
192      *
193      * @return condition name
194      */
getCondition()195     String getCondition() {
196         return cond;
197     }
198 
199     /**
200      * Get the human readable error message associated with this condition.
201      *
202      * @return error message
203      */
getMessage()204     String getMessage() {
205         return msg;
206     }
207 
208 }
209