View Javadoc
1   /**
2    * This file Copyright (c) 2003-2018 Magnolia International
3    * Ltd.  (http://www.magnolia-cms.com). All rights reserved.
4    *
5    *
6    * This file is dual-licensed under both the Magnolia
7    * Network Agreement and the GNU General Public License.
8    * You may elect to use one or the other of these licenses.
9    *
10   * This file is distributed in the hope that it will be
11   * useful, but AS-IS and WITHOUT ANY WARRANTY; without even the
12   * implied warranty of MERCHANTABILITY or FITNESS FOR A
13   * PARTICULAR PURPOSE, TITLE, or NONINFRINGEMENT.
14   * Redistribution, except as permitted by whichever of the GPL
15   * or MNA you select, is prohibited.
16   *
17   * 1. For the GPL license (GPL), you can redistribute and/or
18   * modify this file under the terms of the GNU General
19   * Public License, Version 3, as published by the Free Software
20   * Foundation.  You should have received a copy of the GNU
21   * General Public License, Version 3 along with this program;
22   * if not, write to the Free Software Foundation, Inc., 51
23   * Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
24   *
25   * 2. For the Magnolia Network Agreement (MNA), this file
26   * and the accompanying materials are made available under the
27   * terms of the MNA which accompanies this distribution, and
28   * is available at http://www.magnolia-cms.com/mna.html
29   *
30   * Any modifications to this file must keep this entire header
31   * intact.
32   *
33   */
34  package info.magnolia.context;
35  
36  import info.magnolia.cms.core.HierarchyManager;
37  import info.magnolia.cms.core.search.QueryManager;
38  import info.magnolia.cms.i18n.Messages;
39  import info.magnolia.cms.i18n.MessagesManager;
40  import info.magnolia.cms.security.AccessManager;
41  import info.magnolia.cms.security.PermissionUtil;
42  import info.magnolia.cms.security.Security;
43  import info.magnolia.cms.security.User;
44  import info.magnolia.cms.util.HierarchyManagerUtil;
45  import info.magnolia.jcr.RuntimeRepositoryException;
46  
47  import java.io.Serializable;
48  import java.util.Collection;
49  import java.util.HashMap;
50  import java.util.Iterator;
51  import java.util.Locale;
52  import java.util.Map;
53  import java.util.Set;
54  
55  import javax.jcr.LoginException;
56  import javax.jcr.RepositoryException;
57  import javax.jcr.Session;
58  import javax.security.auth.Subject;
59  
60  import org.slf4j.Logger;
61  import org.slf4j.LoggerFactory;
62  
63  
64  /**
65   * Default implementation of the Context interface.
66   */
67  public abstract class AbstractContext implements Context, Serializable {
68      private static final Logger log = LoggerFactory.getLogger(AbstractContext.class);
69  
70      @Override
71      public User getUser() {
72          return Security.getSystemUser();
73      }
74  
75      @Override
76      public Subject getSubject() {
77          return Security.getSystemSubject();
78      }
79  
80      /**
81       * The locale for this context.
82       */
83      protected Locale locale;
84  
85      private AttributeStrategy attributeStrategy;
86  
87      private JCRSessionStrategy repositoryStrategy;
88  
89      public AttributeStrategy getAttributeStrategy() {
90          return attributeStrategy;
91      }
92  
93      public void setAttributeStrategy(AttributeStrategy strategy) {
94          this.attributeStrategy = strategy;
95      }
96  
97      public JCRSessionStrategy getRepositoryStrategy() {
98          return repositoryStrategy;
99      }
100 
101     public void setRepositoryStrategy(JCRSessionStrategy strategy) {
102         this.repositoryStrategy = strategy;
103     }
104 
105     @Override
106     public Object getAttribute(String name, int scope) {
107         return getAttributeStrategy().getAttribute(name, scope);
108     }
109 
110     @Override
111     public Map<String, Object> getAttributes(int scope) {
112         return getAttributeStrategy().getAttributes(scope);
113     }
114 
115     @Override
116     public void removeAttribute(String name, int scope) {
117         getAttributeStrategy().removeAttribute(name, scope);
118     }
119 
120     @Override
121     public void setAttribute(String name, Object value, int scope) {
122         getAttributeStrategy().setAttribute(name, value, scope);
123     }
124 
125     @Override
126     public AccessManager getAccessManager(String workspace) {
127         return PermissionUtil.getAccessManager(workspace, getSubject());
128     }
129 
130     @Override
131     public Session getJCRSession(String workspaceName) throws LoginException, RepositoryException {
132         return getRepositoryStrategy().getSession(workspaceName);
133     }
134 
135     /**
136      * Get the attribute value.
137      *
138      * @param name to which value is associated to
139      * @return attribute value
140      */
141     @Override
142     public Object getAttribute(String name) {
143         Object value = this.getAttribute(name, Context.LOCAL_SCOPE);
144         if (null == value) {
145             value = this.getAttribute(name, Context.SESSION_SCOPE);
146         }
147         if (null == value) {
148             value = this.getAttribute(name, Context.APPLICATION_SCOPE);
149         }
150         return value;
151     }
152 
153     /**
154      * Merge the scopes maps.
155      */
156     @Override
157     public Map<String, Object> getAttributes() {
158         final Map<String, Object> map = new HashMap<String, Object>();
159         map.putAll(this.getAttributes(Context.LOCAL_SCOPE));
160         map.putAll(this.getAttributes(Context.SESSION_SCOPE));
161         map.putAll(this.getAttributes(Context.APPLICATION_SCOPE));
162         return map;
163     }
164 
165     /**
166      * If not yet set try to get the locale of the user. Else use the locale of the system context.
167      *
168      * @see Context#getLocale()
169      */
170     @Override
171     public Locale getLocale() {
172         if (locale == null) {
173             final SystemContext sysctx = MgnlContext.getSystemContext();
174             if (this == sysctx) {
175                 // do not fall in the endless loop
176                 return null;
177             }
178             locale = sysctx.getLocale();
179         }
180         return locale;
181     }
182 
183     @Override
184     public void setLocale(Locale locale) {
185         this.locale = locale;
186     }
187 
188     /**
189      * TODO: This duplicates methods from MessagesManager : remove either.
190      */
191     @Override
192     public Messages getMessages() {
193         return getMessages(MessagesManager.DEFAULT_BASENAME);
194     }
195 
196     /**
197      * TODO: This duplicates methods from MessagesManager : remove either.
198      */
199     @Override
200     public Messages getMessages(String basename) {
201         return MessagesManager.getMessages(basename, getLocale());
202     }
203 
204     @Override
205     public HierarchyManager getHierarchyManager(String workspaceName) {
206         try {
207             return HierarchyManagerUtil.asHierarchyManager(getJCRSession(workspaceName));
208         } catch (RepositoryException e) {
209             throw new RuntimeRepositoryException(e);
210         }
211     }
212 
213     @Override
214     public QueryManager getQueryManager(String workspaceName) {
215         return this.getHierarchyManager(workspaceName).getQueryManager();
216     }
217 
218     // ------ Map interface methods -------
219 
220     /**
221      * {@inheritDoc}
222      */
223     @Override
224     public Object get(Object key) {
225         return this.getAttribute(key.toString());
226     }
227 
228     /**
229      * {@inheritDoc}
230      */
231     @Override
232     public Object put(Object key, Object value) {
233         this.setAttribute(key.toString(), value, Context.LOCAL_SCOPE);
234         return value;
235     }
236 
237     /**
238      * {@inheritDoc}
239      */
240     @Override
241     public void clear() {
242         for (String key : this.getAttributes().keySet()) {
243             this.removeAttribute(key, Context.LOCAL_SCOPE);
244         }
245         throw new UnsupportedOperationException("you can not clear a magnolia context");
246     }
247 
248     /**
249      * This implementation is very slow!
250      */
251     @Override
252     public boolean containsValue(Object value) {
253         return this.getAttributes().containsValue(value);
254     }
255 
256     /**
257      * {@inheritDoc}
258      */
259     @Override
260     public Set<Entry<String, Object>> entrySet() {
261         return this.getAttributes().entrySet();
262     }
263 
264     /**
265      * {@inheritDoc}
266      */
267     @Override
268     public boolean isEmpty() {
269         return this.getAttributes().isEmpty();
270     }
271 
272     /**
273      * {@inheritDoc}
274      */
275     @Override
276     public Set<String> keySet() {
277         return this.getAttributes().keySet();
278     }
279 
280     /**
281      * {@inheritDoc}
282      */
283     @Override
284     public void putAll(Map map) {
285         for (Iterator iter = map.entrySet().iterator(); iter.hasNext(); ) {
286             Entry entry = (Entry) iter.next();
287             this.setAttribute(entry.getKey().toString(), entry.getValue(), Context.LOCAL_SCOPE);
288         }
289     }
290 
291     /**
292      * {@inheritDoc}
293      */
294     @Override
295     public Object remove(Object key) {
296         Object obj = this.getAttribute(key.toString());
297         this.removeAttribute(key.toString(), Context.LOCAL_SCOPE);
298         return obj;
299     }
300 
301     /**
302      * {@inheritDoc}
303      */
304     @Override
305     public Collection<Object> values() {
306         return this.getAttributes().values();
307     }
308 
309     /**
310      * {@inheritDoc}
311      */
312     @Override
313     public boolean containsKey(Object arg0) {
314         return this.getAttributes().containsKey(arg0);
315     }
316 
317     /**
318      * {@inheritDoc}
319      */
320     @Override
321     public int size() {
322         return this.getAttributes().size();
323     }
324 
325     /**
326      * {@inheritDoc}
327      */
328     @Override
329     public void release() {
330         getRepositoryStrategy().release();
331     }
332 }