/** * Licensed to Apereo under one or more contributor license agreements. See the NOTICE file * distributed with this work for additional information regarding copyright ownership. Apereo * licenses this file to you under the Apache License, Version 2.0 (the "License"); you may not use * this file except in compliance with the License. You may obtain a copy of the License at the * following location: * * <p>http://www.apache.org/licenses/LICENSE-2.0 * * <p>Unless required by applicable law or agreed to in writing, software distributed under the * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either * express or implied. See the License for the specific language governing permissions and * limitations under the License. */ package org.apereo.portal.json.rendering; import java.io.IOException; import java.io.PrintWriter; import javax.servlet.ServletException; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import org.apereo.portal.character.stream.CharacterEventReader; import org.apereo.portal.character.stream.events.CharacterDataEvent; import org.apereo.portal.character.stream.events.CharacterEvent; import org.apereo.portal.character.stream.events.CharacterEventTypes; import org.apereo.portal.events.IPortletExecutionEventFactory; import org.apereo.portal.rendering.CharacterPipelineComponent; import org.apereo.portal.rendering.IPortalRenderingPipeline; import org.apereo.portal.rendering.PipelineEventReader; import org.apereo.portal.rendering.RenderingPipelineConfigurationException; import org.apereo.portal.url.IPortalRequestInfo; import org.apereo.portal.url.IUrlSyntaxProvider; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.beans.factory.annotation.Autowired; public class JsonLayoutRenderingPipeline implements IPortalRenderingPipeline { public static final String CHARACTER_SET = "UTF-8"; protected final Logger logger = LoggerFactory.getLogger(getClass()); private CharacterPipelineComponent pipeline; private IPortletExecutionEventFactory portalEventFactory; private IUrlSyntaxProvider urlSyntaxProvider; @Autowired public void setUrlSyntaxProvider(IUrlSyntaxProvider urlSyntaxProvider) { this.urlSyntaxProvider = urlSyntaxProvider; } @Autowired public void setPortalEventFactory(IPortletExecutionEventFactory portalEventFactory) { this.portalEventFactory = portalEventFactory; } /** * The root element in the rendering pipeline. This element MUST only return {@link * CharacterEventTypes#CHARACTER} type events. */ public void setPipeline(CharacterPipelineComponent pipeline) { this.pipeline = pipeline; } @Override public void renderState(HttpServletRequest req, HttpServletResponse res) throws ServletException, IOException { //Disable page caching res.setHeader("pragma", "no-cache"); res.setHeader("Cache-Control", "no-cache, max-age=0, must-revalidate"); res.setDateHeader("Expires", 0); final long startTime = System.nanoTime(); final PipelineEventReader<CharacterEventReader, CharacterEvent> pipelineEventReader = this.pipeline.getEventReader(req, res); // set the response mime type final String contentType = "application/json; charset=" + CHARACTER_SET; res.setContentType(contentType); final PrintWriter writer = res.getWriter(); for (final CharacterEvent event : pipelineEventReader) { if (CharacterEventTypes.CHARACTER != event.getEventType()) { throw new RenderingPipelineConfigurationException( "Only " + CharacterEventTypes.CHARACTER + " events are supported in the top level renderer. " + event.getEventType() + " is not supported."); } final String data = ((CharacterDataEvent) event).getData(); writer.print(data); writer.flush(); res.flushBuffer(); } final long executionTime = System.nanoTime() - startTime; final IPortalRequestInfo portalRequestInfo = this.urlSyntaxProvider.getPortalRequestInfo(req); this.portalEventFactory.publishPortalRenderEvent( req, this, req.getPathInfo(), executionTime, portalRequestInfo); } }