001/*
002 *  Copyright 2010 Anyware Services
003 *
004 *  Licensed under the Apache License, Version 2.0 (the "License");
005 *  you may not use this file except in compliance with the License.
006 *  You may obtain a copy of the License at
007 *
008 *      http://www.apache.org/licenses/LICENSE-2.0
009 *
010 *  Unless required by applicable law or agreed to in writing, software
011 *  distributed under the License is distributed on an "AS IS" BASIS,
012 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 *  See the License for the specific language governing permissions and
014 *  limitations under the License.
015 */
016package org.ametys.web.workflow;
017
018import java.io.IOException;
019import java.util.Locale;
020
021import org.apache.avalon.framework.service.ServiceException;
022import org.apache.avalon.framework.service.ServiceManager;
023import org.apache.cocoon.ProcessingException;
024import org.apache.cocoon.components.source.impl.SitemapSource;
025import org.apache.cocoon.environment.ObjectModelHelper;
026import org.apache.cocoon.environment.Request;
027import org.apache.cocoon.generation.ServiceableGenerator;
028import org.apache.cocoon.xml.AttributesImpl;
029import org.apache.cocoon.xml.XMLUtils;
030import org.apache.commons.lang3.LocaleUtils;
031import org.apache.commons.lang3.StringUtils;
032import org.apache.excalibur.source.SourceResolver;
033import org.xml.sax.SAXException;
034
035import org.ametys.cms.content.ContentHelper;
036import org.ametys.cms.repository.Content;
037import org.ametys.core.util.DateUtils;
038import org.ametys.core.util.IgnoreRootHandler;
039import org.ametys.plugins.repository.AmetysObjectResolver;
040import org.ametys.plugins.repository.UnknownAmetysObjectException;
041import org.ametys.plugins.repository.provider.RequestAttributeWorkspaceSelector;
042import org.ametys.plugins.repository.version.VersionableAmetysObject;
043import org.ametys.web.WebConstants;
044import org.ametys.web.renderingcontext.RenderingContext;
045import org.ametys.web.renderingcontext.RenderingContextHandler;
046import org.ametys.web.repository.site.SiteManager;
047
048/**
049 * SAX the contents with id passed from request parameters
050 *
051 */
052public class GetLastPublishedContents extends ServiceableGenerator
053{
054    private SourceResolver _sourceResolver;
055    private AmetysObjectResolver _resolver;
056    private SiteManager _siteManager;
057    private RenderingContextHandler _renderingContextHandler;
058    private ContentHelper _contentHelper;
059    
060    @Override
061    public void service(ServiceManager smanager) throws ServiceException
062    {
063        _sourceResolver = (SourceResolver) smanager.lookup(SourceResolver.ROLE);
064        _resolver = (AmetysObjectResolver) smanager.lookup(AmetysObjectResolver.ROLE);
065        _siteManager = (SiteManager) smanager.lookup(SiteManager.ROLE);
066        _renderingContextHandler = (RenderingContextHandler) smanager.lookup(RenderingContextHandler.ROLE);
067        _contentHelper = (ContentHelper) smanager.lookup(ContentHelper.ROLE);
068    }
069    
070    @Override
071    public void generate() throws IOException, SAXException, ProcessingException
072    {
073        Request request = ObjectModelHelper.getRequest(objectModel);
074        String[] contentIds = request.getParameterValues("contentId");
075        String viewName = request.getParameter("viewName");
076        String lang = request.getParameter("lang");
077        
078        contentHandler.startDocument();
079        XMLUtils.startElement(contentHandler, "contents");
080        
081        String originalWorkspace = RequestAttributeWorkspaceSelector.getForcedWorkspace(request);
082        
083        RequestAttributeWorkspaceSelector.setForcedWorkspace(request, WebConstants.LIVE_WORKSPACE);
084        
085        for (String id : contentIds)
086        {
087            try
088            {
089                Content content = _resolver.resolveById(id);
090                if (content instanceof VersionableAmetysObject)
091                {
092                    Locale locale = StringUtils.isNotEmpty(lang) ? LocaleUtils.toLocale(lang) : null;
093                    saxContent(request, content, viewName != null ? viewName : "main", locale);
094                }
095            }
096            catch (UnknownAmetysObjectException e)
097            {
098                // The content just doesn't have a live version: ignore.
099            }
100        }
101        
102        RequestAttributeWorkspaceSelector.setForcedWorkspace(request, originalWorkspace);
103        
104        XMLUtils.endElement(contentHandler, "contents");
105        contentHandler.endDocument();
106    }
107    
108    /**
109     * SAX a content in its specific view
110     * @param request the request
111     * @param content The content to SAX
112     * @param viewName The view to use
113     * @param locale The current locale
114     * @throws SAXException If an error occurs while SAXing
115     * @throws IOException If an error occurs while retrieving content.
116     */
117    protected void saxContent (Request request, Content content, String viewName, Locale locale) throws SAXException, IOException
118    {
119        RenderingContext currentContext = _renderingContextHandler.getRenderingContext();
120        _renderingContextHandler.setRenderingContext(RenderingContext.FRONT);
121        
122        // FIXME CMS-2611 Force absolute
123        // FIXME CMS-4059 Force base64 encoding.
124        String siteName = (String) request.getAttribute("siteName");
125        String baseUrl = _siteManager.getSite(siteName).getUrl();
126        request.setAttribute("_baseServerPath", baseUrl);
127        request.setAttribute("_contextPath", "");
128        request.setAttribute("forceAbsoluteUrl", true);
129        request.setAttribute("forceBase64Encoding", true);
130        
131        AttributesImpl attrs = new AttributesImpl();
132        attrs.addCDATAAttribute("id", content.getId());
133        attrs.addCDATAAttribute("name", content.getName());
134        attrs.addCDATAAttribute("title", content.getTitle(locale));
135        attrs.addCDATAAttribute("lastModifiedAt", DateUtils.zonedDateTimeToString(content.getLastModified()));
136        
137        XMLUtils.startElement(contentHandler, "content", attrs);
138        
139        String uri = _contentHelper.getContentHtmlViewUrl(content, viewName);
140        SitemapSource src = null;
141        
142        try
143        {
144            src = (SitemapSource) _sourceResolver.resolveURI(uri);
145            src.toSAX(new IgnoreRootHandler(contentHandler));
146        }
147        finally
148        {
149            _sourceResolver.release(src);
150        }
151        
152        XMLUtils.endElement(contentHandler, "content");
153        
154        _renderingContextHandler.setRenderingContext(currentContext);
155        request.removeAttribute("forceAbsoluteUrl");
156        request.removeAttribute("forceBase64Encoding");
157        request.removeAttribute("_baseServerPath");
158        request.removeAttribute("_contextPath");
159    }
160}