001    // Copyright 2005 The Apache Software Foundation
002    //
003    // Licensed under the Apache License, Version 2.0 (the "License");
004    // you may not use this file except in compliance with the License.
005    // You may obtain a copy of the License at
006    //
007    //     http://www.apache.org/licenses/LICENSE-2.0
008    //
009    // Unless required by applicable law or agreed to in writing, software
010    // distributed under the License is distributed on an "AS IS" BASIS,
011    // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
012    // See the License for the specific language governing permissions and
013    // limitations under the License.
014    
015    package org.trails.record;
016    
017    import org.apache.commons.logging.Log;
018    import org.apache.commons.logging.LogFactory;
019    import org.apache.hivemind.util.Defense;
020    import org.apache.tapestry.engine.ServiceEncoding;
021    import org.apache.tapestry.record.PropertyChange;
022    import org.apache.tapestry.record.PropertyPersistenceStrategy;
023    import org.apache.tapestry.record.RecordUtils;
024    import org.apache.tapestry.record.WebSessionAttributeCallback;
025    import org.apache.tapestry.web.WebRequest;
026    import org.apache.tapestry.web.WebSession;
027    
028    import java.util.ArrayList;
029    import java.util.Collection;
030    import java.util.Collections;
031    
032    /**
033     * A basic {@link org.apache.tapestry.record.PropertyPersistenceStrategy},
034     * which stores properties in the HttpSession as attributes. This is a clone of
035     * {@link org.apache.tapestry.record.SessionPropertyPersistenceStrategy} with one difference, it allows you to specify
036     * a different strategyId
037     */
038    public abstract class AbstractSessionPropertyPersistenceStrategy implements PropertyPersistenceStrategy
039    {
040            private static final Log LOG = LogFactory.getLog(AbstractSessionPropertyPersistenceStrategy.class);
041    
042            private String applicationId;
043            private WebRequest request;
044    
045            protected abstract String getStrategyId();
046    
047            // Really, the name of the servlet; used as a prefix on all
048            // HttpSessionAttribute keys
049            // to keep things straight if multiple Tapestry apps are deployed
050            // in the same WAR.
051    
052            public void store(String pageName, String idPath, String propertyName, Object newValue)
053            {
054                    Defense.notNull(pageName, "pageName");
055                    Defense.notNull(propertyName, "propertyName");
056                    WebSession session = request.getSession(true);
057                    String attributeName = RecordUtils.buildChangeKey(getStrategyId(), applicationId, pageName, idPath, propertyName);
058                    session.setAttribute(attributeName, newValue);
059            }
060    
061            public Collection getStoredChanges(String pageName)
062            {
063                    Defense.notNull(pageName, "pageName");
064    
065                    WebSession session = request.getSession(false);
066    
067                    if (session == null)
068                            return Collections.EMPTY_LIST;
069    
070                    final Collection result = new ArrayList();
071    
072                    WebSessionAttributeCallback callback = new WebSessionAttributeCallback()
073                    {
074                            public void handleAttribute(WebSession sess, String name)
075                            {
076                                    PropertyChange change = RecordUtils.buildChange(name, sess.getAttribute(name));
077    
078                                    result.add(change);
079                            }
080                    };
081    
082                    RecordUtils.iterateOverMatchingAttributes(getStrategyId(), applicationId, pageName, session, callback);
083    
084                    return result;
085            }
086    
087            public void discardStoredChanges(String pageName)
088            {
089                    WebSession session = request.getSession(false);
090    
091                    if (session == null) return;
092    
093                    WebSessionAttributeCallback callback = new WebSessionAttributeCallback()
094                    {
095                            public void handleAttribute(WebSession sess, String name)
096                            {
097                                    sess.setAttribute(name, null);
098                            }
099                    };
100    
101                    RecordUtils.iterateOverMatchingAttributes(getStrategyId(), applicationId, pageName, session, callback);
102            }
103    
104            /**
105             * Does nothing; session persistence does not make use of query parameters.
106             */
107    
108            public void addParametersForPersistentProperties(ServiceEncoding encoding,
109                                                                                                             boolean post)
110            {
111            }
112    
113            public void setApplicationId(String applicationName)
114            {
115                    this.applicationId = applicationName;
116            }
117    
118            public void setRequest(WebRequest request)
119            {
120                    this.request = request;
121            }
122    }