01: // Copyright 2006, 2007 The Apache Software Foundation
02: //
03: // Licensed under the Apache License, Version 2.0 (the "License");
04: // you may not use this file except in compliance with the License.
05: // You may obtain a copy of the License at
06: //
07: // http://www.apache.org/licenses/LICENSE-2.0
08: //
09: // Unless required by applicable law or agreed to in writing, software
10: // distributed under the License is distributed on an "AS IS" BASIS,
11: // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12: // See the License for the specific language governing permissions and
13: // limitations under the License.
14:
15: package org.apache.tapestry.internal.services;
16:
17: import static org.apache.tapestry.ioc.IOCConstants.PERTHREAD_SCOPE;
18: import static org.apache.tapestry.ioc.internal.util.CollectionFactory.newLinkedList;
19: import static org.apache.tapestry.ioc.internal.util.CollectionFactory.newMap;
20:
21: import java.util.LinkedList;
22: import java.util.List;
23: import java.util.Map;
24:
25: import org.apache.tapestry.ioc.annotations.Scope;
26: import org.apache.tapestry.ioc.internal.util.CollectionFactory;
27: import org.apache.tapestry.services.Environment;
28:
29: /**
30: * A non-threadsafe implementation (expects to use the "perthread" service lifecyle).
31: */
32: @Scope(PERTHREAD_SCOPE)
33: public class EnvironmentImpl implements Environment {
34: // My generics mojo breaks down when we talk about the key and the value being related
35: // types.
36:
37: private final Map<Class, LinkedList> _stacks = newMap();
38:
39: @SuppressWarnings("unchecked")
40: private <T> LinkedList<T> stackFor(Class<T> type) {
41: LinkedList<T> result = _stacks.get(type);
42:
43: if (result == null) {
44: result = newLinkedList();
45: _stacks.put(type, result);
46: }
47:
48: return result;
49: }
50:
51: public <T> T peek(Class<T> type) {
52: LinkedList<T> stack = stackFor(type);
53:
54: return stack.isEmpty() ? null : stack.getFirst();
55: }
56:
57: public <T> T peekRequired(Class<T> type) {
58: T result = peek(type);
59:
60: if (result == null) {
61: List<Class> types = CollectionFactory.newList();
62: for (Map.Entry<Class, LinkedList> e : _stacks.entrySet()) {
63: LinkedList list = e.getValue();
64:
65: if (list != null && !list.isEmpty())
66: types.add(e.getKey());
67: }
68:
69: throw new RuntimeException(ServicesMessages
70: .missingFromEnvironment(type, types));
71: }
72:
73: return result;
74: }
75:
76: public <T> T pop(Class<T> type) {
77: LinkedList<T> stack = stackFor(type);
78:
79: return stack.removeFirst();
80: }
81:
82: public <T> T push(Class<T> type, T instance) {
83: LinkedList<T> stack = stackFor(type);
84:
85: T result = stack.isEmpty() ? null : stack.getFirst();
86:
87: stack.addFirst(instance);
88:
89: return result;
90: }
91:
92: public void clear() {
93: _stacks.clear();
94: }
95: }
|