View Javadoc

1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one
3    * or more contributor license agreements.  See the NOTICE file
4    * distributed with this work for additional information
5    * regarding copyright ownership.  The ASF licenses this file
6    * to you under the Apache License, Version 2.0 (the
7    * "License"); you may not use this file except in compliance
8    * with the License.  You may obtain a copy of the License at
9    *
10   *   http://www.apache.org/licenses/LICENSE-2.0
11   *
12   * Unless required by applicable law or agreed to in writing,
13   * software distributed under the License is distributed on an
14   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15   * KIND, either express or implied.  See the License for the
16   * specific language governing permissions and limitations
17   * under the License.
18   */
19  
20  package org.apache.myfaces.tobago.context;
21  
22  import org.apache.commons.lang.ObjectUtils;
23  import org.apache.myfaces.tobago.config.TobagoConfig;
24  import org.apache.myfaces.tobago.internal.context.ClientPropertiesKey;
25  import org.apache.myfaces.tobago.layout.Measure;
26  import org.apache.myfaces.tobago.util.VariableResolverUtils;
27  import org.slf4j.Logger;
28  import org.slf4j.LoggerFactory;
29  
30  import javax.faces.component.UIViewRoot;
31  import javax.faces.context.ExternalContext;
32  import javax.faces.context.FacesContext;
33  import java.io.Serializable;
34  import java.util.ArrayList;
35  import java.util.List;
36  import java.util.Locale;
37  
38  /**
39   * The ClientProperties contains data, which are individual for each user.
40   * It is stored in the session by default, but the application can override this in the faces-config.xml.
41   * <p/>
42   * The managed bean name which is Tobago using for the instance is {@link #MANAGED_BEAN_NAME}.
43   * <p/>
44   * Please use {@link org.apache.myfaces.tobago.util.VariableResolverUtils#resolveClientProperties(FacesContext)}
45   * to access to the users client properties.
46   */
47  
48  public class ClientProperties implements Serializable {
49  
50    /**
51     * The name of the managed bean
52     */
53    public static final String MANAGED_BEAN_NAME = "tobagoClientProperties";
54  
55    private static final long serialVersionUID = 2L;
56  
57    private static final Logger LOG = LoggerFactory.getLogger(ClientProperties.class);
58  
59    private String contentType = "html";
60    private Theme theme;
61    private UserAgent userAgent = UserAgent.DEFAULT;
62    private boolean debugMode;
63  
64    private Locale locale;
65  
66    private Measure verticalScrollbarWeight;
67    private Measure horizontalScrollbarWeight;
68  
69    /** 
70     * managed bean constructor
71     */
72    public ClientProperties() {
73      this(FacesContext.getCurrentInstance());
74    }
75  
76    /**
77     * @deprecated since 1.5.
78     */
79    private ClientProperties(TobagoConfig tobagoConfig) {
80      theme = tobagoConfig.getDefaultTheme();
81      reset();
82    }
83  
84    private ClientProperties(FacesContext facesContext) {
85  
86      ExternalContext externalContext = facesContext.getExternalContext();
87  
88      // content type
89      String accept = (String) externalContext.getRequestHeaderMap().get("Accept");
90      if (accept != null) {
91        if (accept.indexOf("text/vnd.wap.wml") > -1) {
92          contentType = "wml";
93        }
94      }
95      if (LOG.isDebugEnabled()) {
96        LOG.debug("contentType='" + contentType + "' from header " + "Accept='" + accept + "'");
97      }
98  
99      // user agent
100     String requestUserAgent = (String) externalContext.getRequestHeaderMap().get("User-Agent");
101     this.userAgent = UserAgent.getInstance(requestUserAgent);
102     if (LOG.isDebugEnabled()) {
103       LOG.debug("userAgent='" + this.userAgent + "' from header " + "'User-Agent: " + requestUserAgent + "'");
104     }
105 
106     // theme
107     String requestTheme = (String) externalContext.getRequestParameterMap().get("tobago.theme");
108     TobagoConfig config = TobagoConfig.getInstance(facesContext);
109     // TODO log error if tobago config is not initialized
110     this.theme = config.getTheme(requestTheme);
111     if (LOG.isDebugEnabled()) {
112       LOG.debug("theme='" + theme.getName() + "' from requestParameter " + "tobago.theme='" + requestTheme + "'");
113     }
114 
115     reset();
116   }
117 
118   /**
119    * @deprecated since 1.5.
120    */
121   @Deprecated
122   public static ClientProperties getDefaultInstance(FacesContext facesContext) {
123     return new ClientProperties(TobagoConfig.getInstance(facesContext));
124   }
125 
126   /**
127    * @deprecated since 1.5. Please use 
128    * {@link 
129    * org.apache.myfaces.tobago.util.VariableResolverUtils#resolveClientProperties(javax.faces.context.FacesContext)} 
130    */
131   @Deprecated
132   public static ClientProperties getInstance(UIViewRoot viewRoot) {
133     return getInstance(FacesContext.getCurrentInstance());
134   }
135 
136   /**
137    * @deprecated since 1.5. Please use 
138    * {@link 
139    * org.apache.myfaces.tobago.util.VariableResolverUtils#resolveClientProperties(javax.faces.context.FacesContext)} 
140    */
141   @Deprecated
142   public static ClientProperties getInstance(FacesContext facesContext) {
143     return (ClientProperties) VariableResolverUtils.resolveClientProperties(facesContext);
144   }
145 
146   /**
147    * @deprecated since 1.5. Please use 
148    * {@link org.apache.myfaces.tobago.util.LocaleUtils#getLocaleSuffixList(java.util.Locale)} 
149    */
150   @Deprecated
151   public static List<String> getLocaleList(Locale locale, boolean propertyPathMode) {
152     String string = locale.toString();
153     String prefix = propertyPathMode ? "" : "_";
154     List<String> locales = new ArrayList<String>(4);
155     locales.add(prefix + string);
156     int underscore;
157     while ((underscore = string.lastIndexOf('_')) > 0) {
158       string = string.substring(0, underscore);
159       locales.add(prefix + string);
160     }
161 
162     locales.add(propertyPathMode ? "default" : ""); // default suffix
163 
164     return locales;
165   }
166 
167   private void reset() {
168     ClientPropertiesKey.reset(FacesContext.getCurrentInstance());
169   }
170 
171   public String getContentType() {
172     return contentType;
173   }
174 
175   public void setContentType(String contentType) {
176     this.contentType = contentType;
177     reset();
178   }
179 
180   public Theme getTheme() {
181     return theme;
182   }
183   
184   public void setTheme(Theme theme) {
185     this.theme = theme;
186     reset();
187   }
188 
189   public UserAgent getUserAgent() {
190     return userAgent;
191   }
192 
193   public void setUserAgent(UserAgent userAgent) {
194     this.userAgent = userAgent;
195     reset();
196   }
197 
198   public boolean isDebugMode() {
199     return debugMode;
200   }
201 
202   public void setDebugMode(boolean debugMode) {
203     this.debugMode = debugMode;
204   }
205 
206   public Locale getLocale() {
207     return locale;
208   }
209 
210   /**
211    * Holds the locale of the user, which is located in the UIViewRoot.
212    * This setter should not be called from the application directly, 
213    * but via {@link UIViewRoot#setLocale(Locale locale)} 
214    */
215   public void setLocale(Locale locale) {
216     // set locale will be called "too often" from the JSF
217     if (!ObjectUtils.equals(this.locale, locale)) {
218       this.locale = locale;
219       reset();
220     }
221   }
222 
223   public Measure getVerticalScrollbarWeight() {
224     return verticalScrollbarWeight;
225   }
226 
227   public void setVerticalScrollbarWeight(Measure verticalScrollbarWeight) {
228     this.verticalScrollbarWeight = verticalScrollbarWeight;
229   }
230 
231   public Measure getHorizontalScrollbarWeight() {
232     return horizontalScrollbarWeight;
233   }
234 
235   public void setHorizontalScrollbarWeight(Measure horizontalScrollbarWeight) {
236     this.horizontalScrollbarWeight = horizontalScrollbarWeight;
237   }
238 
239   public void updateUserAgent(FacesContext facesContext) {
240     ExternalContext externalContext = facesContext.getExternalContext();
241     String requestUserAgent = (String) externalContext.getRequestHeaderMap().get("User-Agent");
242     final UserAgent newUserAgent = UserAgent.getInstance(requestUserAgent);
243     if (newUserAgent != userAgent) {
244       userAgent = newUserAgent;
245       reset();
246     }
247   }
248 }