001://** Copyright Statement ***************************************************
002://The Salmon Open Framework for Internet Applications (SOFIA)
003:// Copyright (C) 1999 - 2002, Salmon LLC
004://
005:// This program is free software; you can redistribute it and/or
006:// modify it under the terms of the GNU General Public License version 2
007:// as published by the Free Software Foundation;
008://
009:// This program is distributed in the hope that it will be useful,
010:// but WITHOUT ANY WARRANTY; without even the implied warranty of
011:// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
012:// GNU General Public License for more details.
013://
014:// You should have received a copy of the GNU General Public License
015:// along with this program; if not, write to the Free Software
016:// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
017://
018:// For more information please visit http://www.salmonllc.com
019://** End Copyright Statement ***************************************************
020:package com.salmonllc.portlet;
021:
022:import java.io.IOException;
023:import java.io.InputStream;
024:import java.io.PrintWriter;
025:import java.net.HttpURLConnection;
026:import java.net.MalformedURLException;
027:import java.net.URL;
028:import java.util.Enumeration;
029:
030:import javax.portlet.ActionRequest;
031:import javax.portlet.ActionResponse;
032:import javax.portlet.GenericPortlet;
033:import javax.portlet.PortletContext;
034:import javax.portlet.PortletException;
035:import javax.portlet.PortletMode;
036:import javax.portlet.PortletRequestDispatcher;
037:import javax.portlet.PortletSession;
038:import javax.portlet.RenderRequest;
039:import javax.portlet.RenderResponse;
040:import javax.portlet.WindowState;
041:import javax.servlet.http.HttpServletRequest;
042:
043:import com.salmonllc.html.HttpServletRequestWrapper;
044:import com.salmonllc.html.HttpServletResponseWrapper;
045:import com.salmonllc.html.HttpSessionWrapper;
046:import com.salmonllc.jsp.JspController;
047:import com.salmonllc.jsp.tags.PageTag;
048:import com.salmonllc.properties.Props;
049:import com.salmonllc.util.ApplicationContext;
050:import com.salmonllc.util.MessageLog;
051:import com.salmonllc.util.URLGenerator;
052:
053:/**
054: * Provides an interface between the portlet api and a SOFIA JSP page
055: **/
056:public class SalmonPortlet extends GenericPortlet {
057:
058: public static final String PORTLET_INFO_TOKEN = "$$$SalmonPortletInfo$$$";
059: private static final String PORTLET_CREATE_TOKEN = "SalmonPortletCreateToken";
060:
061: /* (non-Javadoc)
062: * @see javax.portlet.Portlet#render(javax.portlet.RenderRequest, javax.portlet.RenderResponse)
063: */
064: public void render(RenderRequest req, RenderResponse res) throws PortletException, IOException {
065: res.setContentType("text/html");
066: if (req.getWindowState().equals(WindowState.MINIMIZED))
067: return;
068: setUpApplicationContext(getPortletContext());
069:
070: String url = getPortletJsp(req.getPortletMode());
071: PortletRequestDispatcher rd = getPortletContext().getRequestDispatcher(url);
072: PortletInfo info = new PortletInfo();
073:
074: info.setPortletRenderURL(res.createRenderURL().toString());
075: info.setPortletActionURL(res.createActionURL().toString());
076: info.setPortletName(getPortletName());
077: info.setNameSpace(res.getNamespace());
078: info.setParmameterMap(req.getParameterMap());
079: info.setPortletJsp(url);
080: info.setRenderRequest(req);
081: info.setRenderResponse(res);
082: info.setPortletTitle(getTitle(req));
083:
084: JspController cont = getJspController(req, info);
085: if (!handleException(cont, true, res))
086: return;
087:
088: if (cont != null) {
089: PortletInfo oldInfo = cont.getPortletInfo();
090: if (oldInfo != null)
091: info.setFromPost(oldInfo.isFromPost());
092: } else {
093: PortletSession sess = req.getPortletSession(true);
094: Props p = Props.getSystemProps();
095: String sessKey = "$jsp$" + PageTag.generateSessionName(info) + "createPage";
096: if (sess.getAttribute(sessKey, PortletSession.APPLICATION_SCOPE) == null) {
097: sess.setAttribute(sessKey, "true", PortletSession.APPLICATION_SCOPE);
098: if (!p.getBooleanProperty(Props.SYS_REPLACE_JSP_FACTORY, true)) {
099: String rUrl = info.getPortletRenderURL();
100: createPage(req, res, req.getPortletSession(true), rUrl, sessKey);
101: }
102: sess.removeAttribute(sessKey, PortletSession.APPLICATION_SCOPE);
103: }
104: }
105:
106: req.setAttribute(PORTLET_INFO_TOKEN, info);
107:
108: try {
109: rd.include(req, res);
110: cont = getJspController(req, info);
111: } catch (Exception e) {
112: MessageLog.writeErrorMessage("Error rendering portlet", e, this );
113: throw new PortletException(e);
114: }
115: handleException(cont, true, res);
116:
117: }
118:
119: /* (non-Javadoc)
120: * @see javax.portlet.Portlet#processAction(javax.portlet.ActionRequest, javax.portlet.ActionResponse)
121: */
122: public void processAction(ActionRequest req, ActionResponse res) throws PortletException, IOException {
123: setUpApplicationContext(getPortletContext());
124: PortletInfo info = new PortletInfo();
125: info.setPortletName(getPortletName());
126: info.setParmameterMap(req.getParameterMap());
127: info.setPortletJsp(getPortletJsp(req.getPortletMode()));
128: info.setFromPost(true);
129: info.setActionRequest(req);
130: info.setActionResponse(res);
131: req.setAttribute(PORTLET_INFO_TOKEN, info);
132: JspController cont = getJspController(req, res, info);
133: try {
134: if (cont != null) {
135: cont.setPortletInfo(info);
136: cont.doPost(new HttpServletRequestWrapper(req), new HttpServletResponseWrapper(res, req, cont));
137: }
138: } catch (SalmonPortletException ex) {
139: handleException(cont, false, null);
140: } catch (Exception e) {
141: MessageLog.writeErrorMessage("Error posting to portlet", e, this );
142: throw new PortletException(e);
143: }
144:
145: }
146:
147: private JspController getJspController(RenderRequest req) {
148: PortletInfo info = new PortletInfo();
149: info.setPortletName(getPortletName());
150: info.setPortletJsp(getPortletJsp(req.getPortletMode()));
151: info.setRenderRequest(req);
152: return getJspController(req, info);
153:
154: }
155: private JspController getJspController(RenderRequest req, PortletInfo info) {
156: JspController cont = null;
157: String sessKey = PageTag.generateSessionName(info);
158: String sessName = "$jsp$" + sessKey;
159:
160: PortletSession sess = req.getPortletSession(true);
161: Object o = sess.getAttribute(sessName, PortletSession.APPLICATION_SCOPE);
162: if (o == null)
163: return null;
164: else
165: return (JspController) o;
166: }
167:
168: private JspController getJspController(ActionRequest req, ActionResponse res, PortletInfo info) {
169: JspController cont = null;
170: String sessKey = PageTag.generateSessionName(info);
171: String sessName = "$jsp$" + sessKey;
172:
173: PortletSession sess = req.getPortletSession(true);
174: Object o = sess.getAttribute(sessName, PortletSession.APPLICATION_SCOPE);
175: if (o == null)
176: return null;
177: else {
178: cont = (JspController) o;
179:
180: //since the namespace isn't passed in an action request, get it from the render request
181: PortletInfo oldInfo = cont.getPortletInfo();
182: info.setNameSpace(oldInfo.getNameSpace());
183: cont.setCurrentRequest(req);
184: cont.setCurrentResponse(res, req);
185: cont.setSession(new HttpSessionWrapper(sess));
186: cont.setSessionExpired(false);
187:
188: cont.setServletBaseURL(req.getContextPath());
189: cont.setForwardPerformed(false);
190: cont.setUpLanguagePreferences();
191: HttpServletRequest sReq = cont.getCurrentRequest();
192: if (req.getScheme() == null || req.getScheme().equalsIgnoreCase("http"))
193: cont.setServerURL(URLGenerator.generateServerURL(sReq));
194: else
195: cont.setServerURL(URLGenerator.generateSecureServerURL(sReq));
196: }
197: return cont;
198:
199: }
200:
201: private String getPortletJsp(PortletMode mode) {
202: String modeSt = mode.toString();
203: int pos = modeSt.indexOf(";");
204: if (pos > -1)
205: modeSt=modeSt.substring(0,pos);
206: String url = getPortletConfig().getInitParameter(modeSt + "JSP");
207: if (url == null)
208: url = getPortletConfig().getInitParameter("JSP");
209: return url;
210: }
211:
212: private void createPage(RenderRequest req, RenderResponse res, PortletSession sess, String url, String pageID) {
213: try {
214: int questionPos = url.indexOf("?");
215: String page = "";
216: String parms = "";
217: if (questionPos != -1) {
218: parms = url.substring(questionPos);
219: page = url.substring(0, questionPos);
220: } else
221: page = url;
222: int semiPos = page.indexOf(";");
223: if (semiPos != -1)
224: page = page.substring(0, semiPos);
225: page = page + ";JSESSIONID=" + sess.getId() + parms;
226: URL u = new URL(page + parms);
227: HttpURLConnection conn = (HttpURLConnection) u.openConnection();
228:
229: conn.setRequestProperty("Cookie", "sesessionid=" + sess.getId() + ";session=" + sess.getId() + ";sessionid=" + sess.getId() + ";JSESSIONID=" + sess.getId());
230: conn.setRequestProperty("Accept-Language", constructLanguageString(req.getLocales()));
231: conn.setDoInput(true);
232: conn.setUseCaches(false);
233: HttpURLConnection.setFollowRedirects(false);
234: InputStream in = conn.getInputStream();
235: while (in.read() > -1);
236: in.close();
237: conn.disconnect();
238: } catch (Exception e) {
239: MessageLog.writeErrorMessage("Error creating page", e, this );
240: }
241: }
242:
243: public static String constructLanguageString(Enumeration enum) {
244: StringBuffer langString = new StringBuffer();
245: while (enum.hasMoreElements()) {
246: langString.append(enum.nextElement().toString());
247: langString.append(",");
248: }
249: if (langString.length() > 0)
250: langString.setLength(langString.length() - 1);
251: return langString.toString();
252: }
253: /* (non-Javadoc)
254: * @see javax.portlet.GenericPortlet#getTitle(javax.portlet.RenderRequest)
255: */
256: protected String getTitle(RenderRequest req) {
257: JspController cont = getJspController(req);
258: if (cont != null && cont.getTitle() != null)
259: return cont.getTitle();
260: else
261: return super .getTitle(req);
262: }
263:
264: private boolean handleException(JspController cont, boolean throwError, RenderResponse res) throws PortletException, IOException {
265: if (cont != null && cont.getPortletException() != null) {
266: SalmonPortletException ex1 = cont.getPortletException();
267: if (throwError)
268: cont.clearPortletException();
269: if (ex1.getLogMessage()) {
270: MessageLog.writeErrorMessage("Error in portlet", ex1.getRealException(), this );
271: ex1.messageLogged();
272: }
273: if (ex1.getThrowMessage() && throwError)
274: throw (ex1.getRealException());
275:
276: if (res != null && ex1.getDisplayMessage() != null) {
277: PrintWriter pw = res.getWriter();
278: pw.print(ex1.getDisplayMessage());
279: pw.flush();
280: pw.close();
281: }
282:
283: return false;
284:
285: }
286: return true;
287:
288: }
289:
290: public static void setUpApplicationContext(PortletContext sContext) {
291: ApplicationContext context=ApplicationContext.getContext();
292: if (context == null) {
293: context=new ApplicationContext();
294: ApplicationContext.setContext(context);
295: }
296: context.setAppDocumentRoot(sContext.getRealPath("/"));
297: String webAppName;
298: try {
299: webAppName = sContext.getResource("/").toString();
300: if (webAppName.endsWith("/"))
301: webAppName=webAppName.substring(0,webAppName.length() - 1);
302: int pos = webAppName.lastIndexOf("/");
303: if (pos > -1)
304: webAppName=webAppName.substring(pos + 1);
305: if (webAppName==null)
306: webAppName="";
307: context.setAppID(webAppName);
308: context.setLogger(MessageLog.getLoggerForApplication(webAppName));
309:
310: } catch (MalformedURLException e) {
311: MessageLog.writeErrorMessage ("setUpApplicationContext", e, null);
312: }
313: }
314:}
|