mirror of
https://github.com/Alfresco/alfresco-community-repo.git
synced 2025-08-07 17:49:17 +00:00
Web Scripts as JSR-168 portlets
git-svn-id: https://svn.alfresco.com/repos/alfresco-enterprise/alfresco/HEAD/root@5627 c4b6b30b-aa2e-2d43-bbcb-ca4b014f7261
This commit is contained in:
@@ -41,11 +41,11 @@
|
|||||||
<td align=center height=40>
|
<td align=center height=40>
|
||||||
<table border=0 cellspacing=8 cellpadding=0>
|
<table border=0 cellspacing=8 cellpadding=0>
|
||||||
<tr>
|
<tr>
|
||||||
<th><a class="filterLink <#if filter=0>filterLinkSelected</#if>" href="${url.service}?f=0&p=${path}">All Items</a></th>
|
<th><a class="filterLink <#if filter=0>filterLinkSelected</#if>" href="${scripturl("?f=0&p=${path}")}">All Items</a></th>
|
||||||
<th><a class="filterLink <#if filter=1>filterLinkSelected</#if>" href="${url.service}?f=1&p=${path}">Word Documents</a></th>
|
<th><a class="filterLink <#if filter=1>filterLinkSelected</#if>" href="${scripturl("?f=1&p=${path}")}">Word Documents</a></th>
|
||||||
<th><a class="filterLink <#if filter=2>filterLinkSelected</#if>" href="${url.service}?f=2&p=${path}">HTML Documents</a></th>
|
<th><a class="filterLink <#if filter=2>filterLinkSelected</#if>" href="${scripturl("?f=2&p=${path}")}">HTML Documents</a></th>
|
||||||
<th><a class="filterLink <#if filter=3>filterLinkSelected</#if>" href="${url.service}?f=3&p=${path}">PDF Documents</a></th>
|
<th><a class="filterLink <#if filter=3>filterLinkSelected</#if>" href="${scripturl("?f=3&p=${path}")}">PDF Documents</a></th>
|
||||||
<th><a class="filterLink <#if filter=4>filterLinkSelected</#if>" href="${url.service}?f=4&p=${path}">Recently Modified</a></th>
|
<th><a class="filterLink <#if filter=4>filterLinkSelected</#if>" href="${scripturl("?f=4&p=${path}")}">Recently Modified</a></th>
|
||||||
</tr>
|
</tr>
|
||||||
</table>
|
</table>
|
||||||
</td>
|
</td>
|
||||||
|
@@ -27,11 +27,11 @@
|
|||||||
<td align=center height=40 style="border-left: 1px solid #EBE398;">
|
<td align=center height=40 style="border-left: 1px solid #EBE398;">
|
||||||
<table border=0 cellspacing=8 cellpadding=0>
|
<table border=0 cellspacing=8 cellpadding=0>
|
||||||
<tr>
|
<tr>
|
||||||
<th><a class="filterLink <#if filter=0>filterLinkSelected</#if>" href="${url.service}?f=0">Tasks to do</a></th>
|
<th><a class="filterLink <#if filter=0>filterLinkSelected</#if>" href="${scripturl("?f=0")}">Tasks to do</a></th>
|
||||||
<th><a class="filterLink <#if filter=1>filterLinkSelected</#if>" href="${url.service}?f=1">Due Today</a></th>
|
<th><a class="filterLink <#if filter=1>filterLinkSelected</#if>" href="${scripturl("?f=1")}">Due Today</a></th>
|
||||||
<th><a class="filterLink <#if filter=2>filterLinkSelected</#if>" href="${url.service}?f=2">Next 7 days</a></th>
|
<th><a class="filterLink <#if filter=2>filterLinkSelected</#if>" href="${scripturl("?f=2")}">Next 7 days</a></th>
|
||||||
<th><a class="filterLink <#if filter=3>filterLinkSelected</#if>" href="${url.service}?f=3">No due date</a></th>
|
<th><a class="filterLink <#if filter=3>filterLinkSelected</#if>" href="${scripturl("?f=3")}">No due date</a></th>
|
||||||
<th><a class="filterLink <#if filter=4>filterLinkSelected</#if>" href="${url.service}?f=4">Overdue</a></th>
|
<th><a class="filterLink <#if filter=4>filterLinkSelected</#if>" href="${scripturl("?f=4")}">Overdue</a></th>
|
||||||
</tr>
|
</tr>
|
||||||
</table>
|
</table>
|
||||||
</td>
|
</td>
|
||||||
@@ -94,7 +94,7 @@
|
|||||||
<table class="taskActions" style="padding-left:16px">
|
<table class="taskActions" style="padding-left:16px">
|
||||||
<tr>
|
<tr>
|
||||||
<#list t.transitions as wt>
|
<#list t.transitions as wt>
|
||||||
<td><a class="taskAction" href="#" onclick="MyTasks.transitionTask('/command/task/end/${t.id}/${wt.id}', '${url.service}?f=${filter}', 'Workflow action \'${wt.label?html}\' completed.');">${wt.label?html}</a></td>
|
<td><a class="taskAction" href="#" onclick="MyTasks.transitionTask('/command/task/end/${t.id}/${wt.id}', '${scripturl("?f=${filter}")}', 'Workflow action \'${wt.label?html}\' completed.');">${wt.label?html}</a></td>
|
||||||
</#list>
|
</#list>
|
||||||
</tr>
|
</tr>
|
||||||
</table>
|
</table>
|
||||||
|
@@ -4,5 +4,6 @@
|
|||||||
<url format="html" template="/search/keyword?q={searchTerms}&p={startPage?}&c={count?}&l={language?}&guest={alf:guest?}"/>
|
<url format="html" template="/search/keyword?q={searchTerms}&p={startPage?}&c={count?}&l={language?}&guest={alf:guest?}"/>
|
||||||
<url format="atom" template="/search/keyword?q={searchTerms}&p={startPage?}&c={count?}&l={language?}&guest={alf:guest?}&format=atom"/>
|
<url format="atom" template="/search/keyword?q={searchTerms}&p={startPage?}&c={count?}&l={language?}&guest={alf:guest?}&format=atom"/>
|
||||||
<url format="rss" template="/search/keyword?q={searchTerms}&p={startPage?}&c={count?}&l={language?}&guest={alf:guest?}&format=rss"/>
|
<url format="rss" template="/search/keyword?q={searchTerms}&p={startPage?}&c={count?}&l={language?}&guest={alf:guest?}&format=rss"/>
|
||||||
|
<url format="portlet" template="/search/keyword?q={searchTerms}&p={startPage?}&c={count?}&l={language?}&guest={alf:guest?}&format=portlet"/>
|
||||||
<authentication>guest</authentication>
|
<authentication>guest</authentication>
|
||||||
</webscript>
|
</webscript>
|
@@ -0,0 +1,33 @@
|
|||||||
|
<table>
|
||||||
|
<tr>
|
||||||
|
<td>Results <b>${search.startIndex}</b> - <b>${search.startIndex + search.totalPageItems - 1}</b> of <b>${search.totalResults}</b> for <b>${search.searchTerms}</b> visible to user <b><#if person??>${person.properties.userName}<#else>unknown</#if>.</b></td>
|
||||||
|
</tr>
|
||||||
|
</table>
|
||||||
|
<br>
|
||||||
|
<table>
|
||||||
|
<#list search.results as row>
|
||||||
|
<tr>
|
||||||
|
<td><img src="${url.context}${row.icon16}"/></td><td><a href="${url.context}${row.url}">${row.name}</a></td>
|
||||||
|
</tr>
|
||||||
|
<#if row.properties.description?? == true>
|
||||||
|
<tr>
|
||||||
|
<td></td>
|
||||||
|
<td>${row.properties.description}</td>
|
||||||
|
</tr>
|
||||||
|
</#if>
|
||||||
|
</#list>
|
||||||
|
</table>
|
||||||
|
<br>
|
||||||
|
<table>
|
||||||
|
<tr>
|
||||||
|
<td><a href="${scripturl("?q=${search.searchTerms?url}&p=1&c=${search.itemsPerPage}&l=${search.localeId}")}">first</a></td>
|
||||||
|
<#if search.startPage > 1>
|
||||||
|
<td><a href="${scripturl("?q=${search.searchTerms?url}&p=${search.startPage - 1}&c=${search.itemsPerPage}&l=${search.localeId}")}">previous</a></td>
|
||||||
|
</#if>
|
||||||
|
<td><a href="${scripturl("?q=${search.searchTerms?url}&p=${search.startPage}&c=${search.itemsPerPage}&l=${search.localeId}")}">${search.startPage}</a></td>
|
||||||
|
<#if search.startPage < search.totalPages>
|
||||||
|
<td><a href="${scripturl("?q=${search.searchTerms?url}&p=${search.startPage + 1}&c=${search.itemsPerPage}&l=${search.localeId}")}">next</a></td>
|
||||||
|
</#if>
|
||||||
|
<td><a href="${scripturl("?q=${search.searchTerms?url}&p=${search.totalPages}&c=${search.itemsPerPage}&l=${search.localeId}")}">last</a></td>
|
||||||
|
</tr>
|
||||||
|
</table>
|
@@ -8,11 +8,7 @@
|
|||||||
<!-- -->
|
<!-- -->
|
||||||
|
|
||||||
<bean id="webscripts.test" class="org.alfresco.web.scripts.TestWebScriptServer">
|
<bean id="webscripts.test" class="org.alfresco.web.scripts.TestWebScriptServer">
|
||||||
<property name="registry">
|
<property name="registry" ref="webscripts.registry" />
|
||||||
<bean parent="webscripts.registry">
|
|
||||||
<property name="authenticator" ref="webscripts.authenticator.trusted" />
|
|
||||||
</bean>
|
|
||||||
</property>
|
|
||||||
<property name="transactionService" ref="transactionComponent" />
|
<property name="transactionService" ref="transactionComponent" />
|
||||||
<property name="messages">
|
<property name="messages">
|
||||||
<bean class="org.springframework.context.support.ResourceBundleMessageSource">
|
<bean class="org.springframework.context.support.ResourceBundleMessageSource">
|
||||||
|
@@ -63,36 +63,24 @@
|
|||||||
|
|
||||||
<bean id="webscripts.registry" class="org.alfresco.web.scripts.DeclarativeWebScriptRegistry">
|
<bean id="webscripts.registry" class="org.alfresco.web.scripts.DeclarativeWebScriptRegistry">
|
||||||
<property name="storage" ref="webscripts.storage" />
|
<property name="storage" ref="webscripts.storage" />
|
||||||
<property name="authenticator" ref="webscripts.authenticator.webclient" />
|
|
||||||
<property name="serviceLogger" ref="webscripts.logger" />
|
|
||||||
<property name="serviceTransaction" ref="webscripts.transaction" />
|
|
||||||
<property name="formatRegistry" ref="webscripts.formatregistry" />
|
<property name="formatRegistry" ref="webscripts.formatregistry" />
|
||||||
<property name="defaultWebScript"><value>webscript_default</value></property>
|
<property name="defaultWebScript"><value>webscript_default</value></property>
|
||||||
</bean>
|
</bean>
|
||||||
|
|
||||||
<!-- Service Logger -->
|
<!-- Alfresco Web Client Authenticator (Servlet based) -->
|
||||||
<bean id="webscripts.logger" class="org.alfresco.web.scripts.WebScriptLogger" />
|
<bean id="webscripts.authenticator.webclient" class="org.alfresco.web.scripts.WebClientAuthenticator" />
|
||||||
|
|
||||||
<!-- Service Transaction -->
|
<!-- HTTP Basic Authenticator (Servlet based) -->
|
||||||
<bean id="webscripts.transaction" class="org.alfresco.web.scripts.WebScriptTransaction">
|
<bean id="webscripts.authenticator.basic" class="org.alfresco.web.scripts.BasicHttpAuthenticator">
|
||||||
<property name="transactionService" ref="transactionComponent" />
|
|
||||||
</bean>
|
|
||||||
|
|
||||||
<!-- Alfresco Web Client Authenticator -->
|
|
||||||
<bean id="webscripts.authenticator.webclient" class="org.alfresco.web.scripts.WebClientAuthenticator">
|
|
||||||
<property name="authenticationService" ref="AuthenticationService" />
|
<property name="authenticationService" ref="AuthenticationService" />
|
||||||
</bean>
|
</bean>
|
||||||
|
|
||||||
<!-- HTTP Basic Authenticator -->
|
<!-- JSR-168 Authenticator (Portal based) -->
|
||||||
<bean id="webscripts.authenticator.basic" class="org.alfresco.web.scripts.BasicAuthenticator">
|
<bean id="webscripts.authenticator.jsr168" class="org.alfresco.web.scripts.portlet.WebClientPortletAuthenticator">
|
||||||
|
<property name="scriptContext" ref="webscripts.context" />
|
||||||
<property name="authenticationService" ref="AuthenticationService" />
|
<property name="authenticationService" ref="AuthenticationService" />
|
||||||
</bean>
|
</bean>
|
||||||
|
|
||||||
<!-- System Authenticator -->
|
|
||||||
<bean id="webscripts.authenticator.system" class="org.alfresco.web.scripts.SystemAuthenticator" />
|
|
||||||
|
|
||||||
<!-- Trusted Authenticator -->
|
|
||||||
<bean id="webscripts.authenticator.trusted" class="org.alfresco.web.scripts.TrustedAuthenticator" />
|
|
||||||
|
|
||||||
|
|
||||||
<!-- -->
|
<!-- -->
|
||||||
@@ -119,6 +107,7 @@
|
|||||||
<prop key="json">application/json</prop>
|
<prop key="json">application/json</prop>
|
||||||
<prop key="opensearchdescription">application/opensearchdescription+xml</prop>
|
<prop key="opensearchdescription">application/opensearchdescription+xml</prop>
|
||||||
<prop key="wiki">text/plain</prop>
|
<prop key="wiki">text/plain</prop>
|
||||||
|
<prop key="portlet">text/html</prop>
|
||||||
</props>
|
</props>
|
||||||
</property>
|
</property>
|
||||||
</bean>
|
</bean>
|
||||||
|
@@ -26,7 +26,6 @@ package org.alfresco.web.scripts;
|
|||||||
|
|
||||||
import java.io.Writer;
|
import java.io.Writer;
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
import java.util.Enumeration;
|
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
|
||||||
@@ -36,7 +35,6 @@ import org.alfresco.repo.template.AbsoluteUrlMethod;
|
|||||||
import org.alfresco.service.ServiceRegistry;
|
import org.alfresco.service.ServiceRegistry;
|
||||||
import org.alfresco.service.cmr.repository.NodeRef;
|
import org.alfresco.service.cmr.repository.NodeRef;
|
||||||
import org.alfresco.service.cmr.repository.ScriptLocation;
|
import org.alfresco.service.cmr.repository.ScriptLocation;
|
||||||
import org.alfresco.service.cmr.repository.TemplateImageResolver;
|
|
||||||
import org.alfresco.service.cmr.repository.TemplateService;
|
import org.alfresco.service.cmr.repository.TemplateService;
|
||||||
import org.alfresco.service.descriptor.DescriptorService;
|
import org.alfresco.service.descriptor.DescriptorService;
|
||||||
import org.alfresco.web.scripts.WebScriptDescription.RequiredAuthentication;
|
import org.alfresco.web.scripts.WebScriptDescription.RequiredAuthentication;
|
||||||
@@ -174,10 +172,9 @@ public abstract class AbstractWebScript implements WebScript
|
|||||||
final protected Map<String, String> createArgModel(WebScriptRequest req)
|
final protected Map<String, String> createArgModel(WebScriptRequest req)
|
||||||
{
|
{
|
||||||
Map<String, String> args = new ScriptableHashMap<String, String>();
|
Map<String, String> args = new ScriptableHashMap<String, String>();
|
||||||
Enumeration names = req.getParameterNames();
|
String[] names = req.getParameterNames();
|
||||||
while (names.hasMoreElements())
|
for (String name : names)
|
||||||
{
|
{
|
||||||
String name = (String)names.nextElement();
|
|
||||||
args.put(name, req.getParameter(name));
|
args.put(name, req.getParameter(name));
|
||||||
}
|
}
|
||||||
return args;
|
return args;
|
||||||
@@ -269,6 +266,7 @@ public abstract class AbstractWebScript implements WebScript
|
|||||||
|
|
||||||
// add template support
|
// add template support
|
||||||
model.put("absurl", new AbsoluteUrlMethod(req.getServerPath()));
|
model.put("absurl", new AbsoluteUrlMethod(req.getServerPath()));
|
||||||
|
model.put("scripturl", new ScriptUrlMethod(req, res));
|
||||||
model.put("date", new Date());
|
model.put("date", new Date());
|
||||||
model.put(TemplateService.KEY_IMAGE_RESOLVER, getWebScriptRegistry().getTemplateImageResolver());
|
model.put(TemplateService.KEY_IMAGE_RESOLVER, getWebScriptRegistry().getTemplateImageResolver());
|
||||||
|
|
||||||
|
@@ -1,194 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2005-2007 Alfresco Software Limited.
|
|
||||||
*
|
|
||||||
* This program is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU General Public License
|
|
||||||
* as published by the Free Software Foundation; either version 2
|
|
||||||
* of the License, or (at your option) any later version.
|
|
||||||
|
|
||||||
* This program is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
* GNU General Public License for more details.
|
|
||||||
|
|
||||||
* You should have received a copy of the GNU General Public License
|
|
||||||
* along with this program; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
|
||||||
|
|
||||||
* As a special exception to the terms and conditions of version 2.0 of
|
|
||||||
* the GPL, you may redistribute this Program in connection with Free/Libre
|
|
||||||
* and Open Source Software ("FLOSS") applications as described in Alfresco's
|
|
||||||
* FLOSS exception. You should have recieved a copy of the text describing
|
|
||||||
* the FLOSS exception, and it is also available here:
|
|
||||||
* http://www.alfresco.com/legal/licensing"
|
|
||||||
*/
|
|
||||||
package org.alfresco.web.scripts;
|
|
||||||
|
|
||||||
import org.alfresco.repo.security.authentication.AuthenticationException;
|
|
||||||
import org.alfresco.repo.security.authentication.AuthenticationUtil;
|
|
||||||
import org.alfresco.service.cmr.security.AuthenticationService;
|
|
||||||
import org.alfresco.util.Base64;
|
|
||||||
import org.alfresco.web.scripts.WebScriptDescription.RequiredAuthentication;
|
|
||||||
import org.aopalliance.intercept.MethodInterceptor;
|
|
||||||
import org.aopalliance.intercept.MethodInvocation;
|
|
||||||
import org.apache.commons.logging.Log;
|
|
||||||
import org.apache.commons.logging.LogFactory;
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* HTTP Basic Authentication Interceptor
|
|
||||||
*
|
|
||||||
* @author davidc
|
|
||||||
*/
|
|
||||||
public class BasicAuthenticator implements MethodInterceptor
|
|
||||||
{
|
|
||||||
// Logger
|
|
||||||
private static final Log logger = LogFactory.getLog(BasicAuthenticator.class);
|
|
||||||
|
|
||||||
// dependencies
|
|
||||||
private AuthenticationService authenticationService;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @param authenticationService
|
|
||||||
*/
|
|
||||||
public void setAuthenticationService(AuthenticationService authenticationService)
|
|
||||||
{
|
|
||||||
this.authenticationService = authenticationService;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* (non-Javadoc)
|
|
||||||
* @see org.aopalliance.intercept.MethodInterceptor#invoke(org.aopalliance.intercept.MethodInvocation)
|
|
||||||
*/
|
|
||||||
public Object invoke(MethodInvocation invocation)
|
|
||||||
throws Throwable
|
|
||||||
{
|
|
||||||
boolean authorized = false;
|
|
||||||
String currentUser = null;
|
|
||||||
Object retVal = null;
|
|
||||||
Object[] args = invocation.getArguments();
|
|
||||||
WebScriptRequest request = (WebScriptRequest)args[0];
|
|
||||||
WebScript service = (WebScript)invocation.getThis();
|
|
||||||
WebScriptDescription description = service.getDescription();
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
//
|
|
||||||
// Determine if user already authenticated
|
|
||||||
//
|
|
||||||
|
|
||||||
currentUser = AuthenticationUtil.getCurrentUserName();
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
logger.debug("Current authentication: " + (currentUser == null ? "unauthenticated" : "authenticated as " + currentUser));
|
|
||||||
|
|
||||||
//
|
|
||||||
// validate credentials
|
|
||||||
//
|
|
||||||
|
|
||||||
boolean isGuest = request.isGuest();
|
|
||||||
String authorization = request.getHeader("Authorization");
|
|
||||||
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
{
|
|
||||||
logger.debug("Web Service authentication required: " + description.getRequiredAuthentication());
|
|
||||||
logger.debug("Guest login: " + isGuest);
|
|
||||||
logger.debug("Authorization provided (overrides Guest login): " + (authorization != null && authorization.length() > 0));
|
|
||||||
}
|
|
||||||
|
|
||||||
// authenticate as guest, if service allows
|
|
||||||
if (((authorization == null || authorization.length() == 0) || isGuest)
|
|
||||||
&& description.getRequiredAuthentication().equals(RequiredAuthentication.guest))
|
|
||||||
{
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
logger.debug("Authenticating as Guest");
|
|
||||||
|
|
||||||
authenticationService.authenticateAsGuest();
|
|
||||||
authorized = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
// authenticate as specified by HTTP Basic Authentication
|
|
||||||
else if (authorization != null && authorization.length() > 0)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
String[] authorizationParts = authorization.split(" ");
|
|
||||||
if (!authorizationParts[0].equalsIgnoreCase("basic"))
|
|
||||||
{
|
|
||||||
throw new WebScriptException("Authorization '" + authorizationParts[0] + "' not supported.");
|
|
||||||
}
|
|
||||||
String decodedAuthorisation = new String(Base64.decode(authorizationParts[1]));
|
|
||||||
String[] parts = decodedAuthorisation.split(":");
|
|
||||||
|
|
||||||
if (parts.length == 1)
|
|
||||||
{
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
logger.debug("Authenticating ticket " + parts[0]);
|
|
||||||
|
|
||||||
// assume a ticket has been passed
|
|
||||||
authenticationService.validate(parts[0]);
|
|
||||||
authorized = true;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
logger.debug("Authenticating user " + parts[0]);
|
|
||||||
|
|
||||||
// assume username and password passed
|
|
||||||
if (parts[0].equals(AuthenticationUtil.getGuestUserName()))
|
|
||||||
{
|
|
||||||
if (description.getRequiredAuthentication().equals(RequiredAuthentication.guest))
|
|
||||||
{
|
|
||||||
authenticationService.authenticateAsGuest();
|
|
||||||
authorized = true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
authenticationService.authenticate(parts[0], parts[1].toCharArray());
|
|
||||||
authorized = true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch(AuthenticationException e)
|
|
||||||
{
|
|
||||||
// failed authentication
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// execute web script or request authorization
|
|
||||||
//
|
|
||||||
|
|
||||||
if (authorized)
|
|
||||||
{
|
|
||||||
retVal = invocation.proceed();
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
logger.debug("Requesting authorization credentials");
|
|
||||||
|
|
||||||
WebScriptResponse response = (WebScriptResponse)args[1];
|
|
||||||
response.setStatus(401);
|
|
||||||
response.setHeader("WWW-Authenticate", "Basic realm=\"Alfresco\"");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
finally
|
|
||||||
{
|
|
||||||
// reset authentication
|
|
||||||
if (authorized)
|
|
||||||
{
|
|
||||||
authenticationService.clearCurrentSecurityContext();
|
|
||||||
if (currentUser != null)
|
|
||||||
{
|
|
||||||
AuthenticationUtil.setCurrentUser(currentUser);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
logger.debug("Authentication reset: " + (currentUser == null ? "unauthenticated" : "authenticated as " + currentUser));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return retVal;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
151
source/java/org/alfresco/web/scripts/BasicHttpAuthenticator.java
Normal file
151
source/java/org/alfresco/web/scripts/BasicHttpAuthenticator.java
Normal file
@@ -0,0 +1,151 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2005-2007 Alfresco Software Limited.
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License
|
||||||
|
* as published by the Free Software Foundation; either version 2
|
||||||
|
* of the License, or (at your option) any later version.
|
||||||
|
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
|
|
||||||
|
* As a special exception to the terms and conditions of version 2.0 of
|
||||||
|
* the GPL, you may redistribute this Program in connection with Free/Libre
|
||||||
|
* and Open Source Software ("FLOSS") applications as described in Alfresco's
|
||||||
|
* FLOSS exception. You should have recieved a copy of the text describing
|
||||||
|
* the FLOSS exception, and it is also available here:
|
||||||
|
* http://www.alfresco.com/legal/licensing"
|
||||||
|
*/
|
||||||
|
package org.alfresco.web.scripts;
|
||||||
|
|
||||||
|
import javax.servlet.http.HttpServletRequest;
|
||||||
|
import javax.servlet.http.HttpServletResponse;
|
||||||
|
|
||||||
|
import org.alfresco.repo.security.authentication.AuthenticationException;
|
||||||
|
import org.alfresco.repo.security.authentication.AuthenticationUtil;
|
||||||
|
import org.alfresco.service.cmr.security.AuthenticationService;
|
||||||
|
import org.alfresco.util.Base64;
|
||||||
|
import org.alfresco.web.scripts.WebScriptDescription.RequiredAuthentication;
|
||||||
|
import org.apache.commons.logging.Log;
|
||||||
|
import org.apache.commons.logging.LogFactory;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* HTTP Basic Authentication Interceptor
|
||||||
|
*
|
||||||
|
* @author davidc
|
||||||
|
*/
|
||||||
|
public class BasicHttpAuthenticator implements WebScriptServletAuthenticator
|
||||||
|
{
|
||||||
|
// Logger
|
||||||
|
private static final Log logger = LogFactory.getLog(BasicHttpAuthenticator.class);
|
||||||
|
|
||||||
|
// dependencies
|
||||||
|
private AuthenticationService authenticationService;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param authenticationService
|
||||||
|
*/
|
||||||
|
public void setAuthenticationService(AuthenticationService authenticationService)
|
||||||
|
{
|
||||||
|
this.authenticationService = authenticationService;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.aopalliance.intercept.MethodInterceptor#invoke(org.aopalliance.intercept.MethodInvocation)
|
||||||
|
*/
|
||||||
|
public void authenticate(RequiredAuthentication required, boolean isGuest, HttpServletRequest req, HttpServletResponse res)
|
||||||
|
{
|
||||||
|
boolean authorized = false;
|
||||||
|
|
||||||
|
//
|
||||||
|
// validate credentials
|
||||||
|
//
|
||||||
|
|
||||||
|
String authorization = req.getHeader("Authorization");
|
||||||
|
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
{
|
||||||
|
logger.debug("HTTP Authorization provided: " + (authorization != null && authorization.length() > 0));
|
||||||
|
}
|
||||||
|
|
||||||
|
// authenticate as guest, if service allows
|
||||||
|
if (isGuest)
|
||||||
|
{
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
logger.debug("Authenticating as Guest");
|
||||||
|
|
||||||
|
authenticationService.authenticateAsGuest();
|
||||||
|
authorized = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
// authenticate as specified by HTTP Basic Authentication
|
||||||
|
else if (authorization != null && authorization.length() > 0)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
String[] authorizationParts = authorization.split(" ");
|
||||||
|
if (!authorizationParts[0].equalsIgnoreCase("basic"))
|
||||||
|
{
|
||||||
|
throw new WebScriptException("Authorization '" + authorizationParts[0] + "' not supported.");
|
||||||
|
}
|
||||||
|
String decodedAuthorisation = new String(Base64.decode(authorizationParts[1]));
|
||||||
|
String[] parts = decodedAuthorisation.split(":");
|
||||||
|
|
||||||
|
if (parts.length == 1)
|
||||||
|
{
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
logger.debug("Authenticating ticket " + parts[0]);
|
||||||
|
|
||||||
|
// assume a ticket has been passed
|
||||||
|
authenticationService.validate(parts[0]);
|
||||||
|
authorized = true;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
logger.debug("Authenticating user " + parts[0]);
|
||||||
|
|
||||||
|
// assume username and password passed
|
||||||
|
if (parts[0].equals(AuthenticationUtil.getGuestUserName()))
|
||||||
|
{
|
||||||
|
if (required == RequiredAuthentication.guest)
|
||||||
|
{
|
||||||
|
authenticationService.authenticateAsGuest();
|
||||||
|
authorized = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
authenticationService.authenticate(parts[0], parts[1].toCharArray());
|
||||||
|
authorized = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch(AuthenticationException e)
|
||||||
|
{
|
||||||
|
// failed authentication
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// request credentials if not authorized
|
||||||
|
//
|
||||||
|
|
||||||
|
if (!authorized)
|
||||||
|
{
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
logger.debug("Requesting authorization credentials");
|
||||||
|
|
||||||
|
res.setStatus(401);
|
||||||
|
res.setHeader("WWW-Authenticate", "Basic realm=\"Alfresco\"");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@@ -37,23 +37,20 @@ import java.util.TreeMap;
|
|||||||
import javax.servlet.ServletContext;
|
import javax.servlet.ServletContext;
|
||||||
|
|
||||||
import org.alfresco.service.cmr.repository.TemplateImageResolver;
|
import org.alfresco.service.cmr.repository.TemplateImageResolver;
|
||||||
|
import org.alfresco.util.AbstractLifecycleBean;
|
||||||
import org.alfresco.web.scripts.WebScriptDescription.RequiredAuthentication;
|
import org.alfresco.web.scripts.WebScriptDescription.RequiredAuthentication;
|
||||||
import org.alfresco.web.scripts.WebScriptDescription.RequiredTransaction;
|
import org.alfresco.web.scripts.WebScriptDescription.RequiredTransaction;
|
||||||
import org.alfresco.web.scripts.WebScriptDescription.URI;
|
import org.alfresco.web.scripts.WebScriptDescription.URI;
|
||||||
import org.alfresco.web.ui.common.Utils;
|
import org.alfresco.web.ui.common.Utils;
|
||||||
import org.aopalliance.intercept.MethodInterceptor;
|
|
||||||
import org.apache.commons.logging.Log;
|
import org.apache.commons.logging.Log;
|
||||||
import org.apache.commons.logging.LogFactory;
|
import org.apache.commons.logging.LogFactory;
|
||||||
import org.dom4j.Document;
|
import org.dom4j.Document;
|
||||||
import org.dom4j.DocumentException;
|
import org.dom4j.DocumentException;
|
||||||
import org.dom4j.Element;
|
import org.dom4j.Element;
|
||||||
import org.dom4j.io.SAXReader;
|
import org.dom4j.io.SAXReader;
|
||||||
import org.springframework.aop.framework.ProxyFactory;
|
|
||||||
import org.springframework.aop.support.RegexpMethodPointcutAdvisor;
|
|
||||||
import org.springframework.beans.BeansException;
|
|
||||||
import org.springframework.beans.factory.InitializingBean;
|
import org.springframework.beans.factory.InitializingBean;
|
||||||
import org.springframework.context.ApplicationContext;
|
import org.springframework.context.ApplicationContext;
|
||||||
import org.springframework.context.ApplicationContextAware;
|
import org.springframework.context.ApplicationEvent;
|
||||||
import org.springframework.web.context.ServletContextAware;
|
import org.springframework.web.context.ServletContextAware;
|
||||||
|
|
||||||
|
|
||||||
@@ -62,17 +59,14 @@ import org.springframework.web.context.ServletContextAware;
|
|||||||
*
|
*
|
||||||
* @author davidc
|
* @author davidc
|
||||||
*/
|
*/
|
||||||
public class DeclarativeWebScriptRegistry implements WebScriptRegistry, ApplicationContextAware, ServletContextAware, InitializingBean
|
public class DeclarativeWebScriptRegistry extends AbstractLifecycleBean
|
||||||
|
implements WebScriptRegistry, ServletContextAware, InitializingBean
|
||||||
{
|
{
|
||||||
// Logger
|
// Logger
|
||||||
private static final Log logger = LogFactory.getLog(DeclarativeWebScriptRegistry.class);
|
private static final Log logger = LogFactory.getLog(DeclarativeWebScriptRegistry.class);
|
||||||
|
|
||||||
private ApplicationContext applicationContext;
|
|
||||||
private ServletContext servletContext;
|
private ServletContext servletContext;
|
||||||
private String defaultWebScript;
|
private String defaultWebScript;
|
||||||
private MethodInterceptor authenticator;
|
|
||||||
private MethodInterceptor serviceLogger;
|
|
||||||
private MethodInterceptor serviceTransaction;
|
|
||||||
private FormatRegistry formatRegistry;
|
private FormatRegistry formatRegistry;
|
||||||
private WebScriptStorage storage;
|
private WebScriptStorage storage;
|
||||||
private TemplateImageResolver imageResolver;
|
private TemplateImageResolver imageResolver;
|
||||||
@@ -101,36 +95,6 @@ public class DeclarativeWebScriptRegistry implements WebScriptRegistry, Applicat
|
|||||||
this.storage = storage;
|
this.storage = storage;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets the web script authenticator
|
|
||||||
*
|
|
||||||
* @param authenticator
|
|
||||||
*/
|
|
||||||
public void setAuthenticator(MethodInterceptor authenticator)
|
|
||||||
{
|
|
||||||
this.authenticator = authenticator;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets the web script logger
|
|
||||||
*
|
|
||||||
* @param serviceLogger
|
|
||||||
*/
|
|
||||||
public void setServiceLogger(MethodInterceptor serviceLogger)
|
|
||||||
{
|
|
||||||
this.serviceLogger = serviceLogger;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets the service transaction
|
|
||||||
*
|
|
||||||
* @param serviceTransaction
|
|
||||||
*/
|
|
||||||
public void setServiceTransaction(MethodInterceptor serviceTransaction)
|
|
||||||
{
|
|
||||||
this.serviceTransaction = serviceTransaction;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Sets the default service implementation bean
|
* Sets the default service implementation bean
|
||||||
*
|
*
|
||||||
@@ -159,14 +123,6 @@ public class DeclarativeWebScriptRegistry implements WebScriptRegistry, Applicat
|
|||||||
this.servletContext = context;
|
this.servletContext = context;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* (non-Javadoc)
|
|
||||||
* @see org.springframework.context.ApplicationContextAware#setApplicationContext(org.springframework.context.ApplicationContext)
|
|
||||||
*/
|
|
||||||
public void setApplicationContext(ApplicationContext applicationContext) throws BeansException
|
|
||||||
{
|
|
||||||
this.applicationContext = applicationContext;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* (non-Javadoc)
|
/* (non-Javadoc)
|
||||||
* @see org.springframework.beans.factory.InitializingBean#afterPropertiesSet()
|
* @see org.springframework.beans.factory.InitializingBean#afterPropertiesSet()
|
||||||
*/
|
*/
|
||||||
@@ -181,6 +137,33 @@ public class DeclarativeWebScriptRegistry implements WebScriptRegistry, Applicat
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRegistry#reset()
|
||||||
|
*/
|
||||||
|
public void reset()
|
||||||
|
{
|
||||||
|
getTemplateProcessor().resetCache();
|
||||||
|
getScriptProcessor().resetCache();
|
||||||
|
initWebScripts();
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.util.AbstractLifecycleBean#onBootstrap(org.springframework.context.ApplicationEvent)
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
protected void onBootstrap(ApplicationEvent event)
|
||||||
|
{
|
||||||
|
initWebScripts();
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.util.AbstractLifecycleBean#onShutdown(org.springframework.context.ApplicationEvent)
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
protected void onShutdown(ApplicationEvent event)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Initialise Web Scripts
|
* Initialise Web Scripts
|
||||||
*
|
*
|
||||||
@@ -245,56 +228,17 @@ public class DeclarativeWebScriptRegistry implements WebScriptRegistry, Applicat
|
|||||||
}
|
}
|
||||||
|
|
||||||
// construct service implementation
|
// construct service implementation
|
||||||
|
ApplicationContext applicationContext = getApplicationContext();
|
||||||
String serviceImplName = (applicationContext.containsBean("webscript." + id)) ? "webscript." + id : defaultWebScript;
|
String serviceImplName = (applicationContext.containsBean("webscript." + id)) ? "webscript." + id : defaultWebScript;
|
||||||
AbstractWebScript serviceImpl = (AbstractWebScript)applicationContext.getBean(serviceImplName);
|
AbstractWebScript serviceImpl = (AbstractWebScript)applicationContext.getBean(serviceImplName);
|
||||||
serviceImpl.setDescription(serviceDesc);
|
serviceImpl.setDescription(serviceDesc);
|
||||||
serviceImpl.init(this);
|
serviceImpl.init(this);
|
||||||
|
|
||||||
// wrap service implementation in appropriate interceptors (e.g. authentication)
|
|
||||||
WebScript serviceImplIF = (WebScript)serviceImpl;
|
|
||||||
if (serviceLogger != null && serviceTransaction != null && authenticator != null)
|
|
||||||
{
|
|
||||||
ProxyFactory authFactory = new ProxyFactory();
|
|
||||||
authFactory.addInterface(WebScript.class);
|
|
||||||
authFactory.setTarget(serviceImplIF);
|
|
||||||
|
|
||||||
// logging interceptor
|
|
||||||
if (serviceLogger != null)
|
|
||||||
{
|
|
||||||
RegexpMethodPointcutAdvisor advisor = new RegexpMethodPointcutAdvisor(".*execute", serviceLogger);
|
|
||||||
authFactory.addAdvisor(advisor);
|
|
||||||
}
|
|
||||||
|
|
||||||
// transaction interceptor
|
|
||||||
if (serviceDesc.getRequiredTransaction() != RequiredTransaction.none)
|
|
||||||
{
|
|
||||||
if (serviceTransaction == null)
|
|
||||||
{
|
|
||||||
throw new WebScriptException("Web Script Transaction not specified");
|
|
||||||
}
|
|
||||||
RegexpMethodPointcutAdvisor advisor = new RegexpMethodPointcutAdvisor(".*execute", serviceTransaction);
|
|
||||||
authFactory.addAdvisor(advisor);
|
|
||||||
}
|
|
||||||
|
|
||||||
// authentication interceptor
|
|
||||||
if (serviceDesc.getRequiredAuthentication() != RequiredAuthentication.none)
|
|
||||||
{
|
|
||||||
if (authenticator == null)
|
|
||||||
{
|
|
||||||
throw new WebScriptException("Web Script Authenticator not specified");
|
|
||||||
}
|
|
||||||
RegexpMethodPointcutAdvisor advisor = new RegexpMethodPointcutAdvisor(".*execute", authenticator);
|
|
||||||
authFactory.addAdvisor(advisor);
|
|
||||||
}
|
|
||||||
|
|
||||||
serviceImplIF = (WebScript)authFactory.getProxy();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (logger.isDebugEnabled())
|
if (logger.isDebugEnabled())
|
||||||
logger.debug("Found Web Script " + serviceDescPath + " (id: " + id + ", impl: " + serviceImplName + ", auth: " + serviceDesc.getRequiredAuthentication() + ", trx: " + serviceDesc.getRequiredTransaction() + ")");
|
logger.debug("Found Web Script " + serviceDescPath + " (id: " + id + ", impl: " + serviceImplName + ", auth: " + serviceDesc.getRequiredAuthentication() + ", trx: " + serviceDesc.getRequiredTransaction() + ")");
|
||||||
|
|
||||||
// register service and its urls
|
// register service and its urls
|
||||||
webscriptsById.put(id, serviceImplIF);
|
webscriptsById.put(id, serviceImpl);
|
||||||
for (URI uri : serviceDesc.getURIs())
|
for (URI uri : serviceDesc.getURIs())
|
||||||
{
|
{
|
||||||
// establish static part of url template
|
// establish static part of url template
|
||||||
@@ -323,7 +267,7 @@ public class DeclarativeWebScriptRegistry implements WebScriptRegistry, Applicat
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
webscriptsByURL.put(uriIdx, serviceImplIF);
|
webscriptsByURL.put(uriIdx, serviceImpl);
|
||||||
|
|
||||||
if (logger.isDebugEnabled())
|
if (logger.isDebugEnabled())
|
||||||
logger.debug("Registered Web Script URL '" + uriIdx + "'");
|
logger.debug("Registered Web Script URL '" + uriIdx + "'");
|
||||||
@@ -476,7 +420,6 @@ public class DeclarativeWebScriptRegistry implements WebScriptRegistry, Applicat
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/* (non-Javadoc)
|
/* (non-Javadoc)
|
||||||
* @see org.alfresco.web.scripts.WebScriptRegistry#getWebScripts()
|
* @see org.alfresco.web.scripts.WebScriptRegistry#getWebScripts()
|
||||||
*/
|
*/
|
||||||
@@ -554,17 +497,6 @@ public class DeclarativeWebScriptRegistry implements WebScriptRegistry, Applicat
|
|||||||
return this.storage.getScriptProcessor();
|
return this.storage.getScriptProcessor();
|
||||||
}
|
}
|
||||||
|
|
||||||
/* (non-Javadoc)
|
|
||||||
* @see org.alfresco.web.scripts.WebScriptRegistry#reset()
|
|
||||||
*/
|
|
||||||
public void reset()
|
|
||||||
{
|
|
||||||
getTemplateProcessor().resetCache();
|
|
||||||
getScriptProcessor().resetCache();
|
|
||||||
initWebScripts();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Web Script Match
|
* Web Script Match
|
||||||
*
|
*
|
||||||
|
84
source/java/org/alfresco/web/scripts/ScriptUrlMethod.java
Normal file
84
source/java/org/alfresco/web/scripts/ScriptUrlMethod.java
Normal file
@@ -0,0 +1,84 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2005-2007 Alfresco Software Limited.
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License
|
||||||
|
* as published by the Free Software Foundation; either version 2
|
||||||
|
* of the License, or (at your option) any later version.
|
||||||
|
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
|
|
||||||
|
* As a special exception to the terms and conditions of version 2.0 of
|
||||||
|
* the GPL, you may redistribute this Program in connection with Free/Libre
|
||||||
|
* and Open Source Software ("FLOSS") applications as described in Alfresco's
|
||||||
|
* FLOSS exception. You should have recieved a copy of the text describing
|
||||||
|
* the FLOSS exception, and it is also available here:
|
||||||
|
* http://www.alfresco.com/legal/licensing"
|
||||||
|
*/
|
||||||
|
package org.alfresco.web.scripts;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
import freemarker.template.TemplateMethodModelEx;
|
||||||
|
import freemarker.template.TemplateModelException;
|
||||||
|
import freemarker.template.TemplateScalarModel;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @author David Caruana
|
||||||
|
*
|
||||||
|
* Custom FreeMarker Template language method.
|
||||||
|
* <p>
|
||||||
|
* Render script url independent of script hosting environment e.g. render inside / outside
|
||||||
|
* portal.
|
||||||
|
* <p>
|
||||||
|
* Usage: scripturl(String url)
|
||||||
|
*/
|
||||||
|
public final class ScriptUrlMethod implements TemplateMethodModelEx
|
||||||
|
{
|
||||||
|
WebScriptRequest req;
|
||||||
|
WebScriptResponse res;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Construct
|
||||||
|
*
|
||||||
|
* @param basePath base path used to construct absolute url
|
||||||
|
*/
|
||||||
|
public ScriptUrlMethod(WebScriptRequest req, WebScriptResponse res)
|
||||||
|
{
|
||||||
|
this.req = req;
|
||||||
|
this.res = res;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @see freemarker.template.TemplateMethodModel#exec(java.util.List)
|
||||||
|
*/
|
||||||
|
public Object exec(List args) throws TemplateModelException
|
||||||
|
{
|
||||||
|
String result = "";
|
||||||
|
|
||||||
|
if (args.size() == 1)
|
||||||
|
{
|
||||||
|
Object arg0 = args.get(0);
|
||||||
|
if (arg0 instanceof TemplateScalarModel)
|
||||||
|
{
|
||||||
|
String arg = ((TemplateScalarModel)arg0).getAsString();
|
||||||
|
String url = req.getServicePath();
|
||||||
|
url += arg;
|
||||||
|
url += (arg.length() > 0) ? "&" : "";
|
||||||
|
url += "guest=" + (req.isGuest() ? "true" : "");
|
||||||
|
url += (req.getFormat().length() > 0) ? "&format=" + req.getFormat() : "";
|
||||||
|
result = res.encodeScriptUrl(url);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
}
|
@@ -1,94 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2005-2007 Alfresco Software Limited.
|
|
||||||
*
|
|
||||||
* This program is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU General Public License
|
|
||||||
* as published by the Free Software Foundation; either version 2
|
|
||||||
* of the License, or (at your option) any later version.
|
|
||||||
|
|
||||||
* This program is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
* GNU General Public License for more details.
|
|
||||||
|
|
||||||
* You should have received a copy of the GNU General Public License
|
|
||||||
* along with this program; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
|
||||||
|
|
||||||
* As a special exception to the terms and conditions of version 2.0 of
|
|
||||||
* the GPL, you may redistribute this Program in connection with Free/Libre
|
|
||||||
* and Open Source Software ("FLOSS") applications as described in Alfresco's
|
|
||||||
* FLOSS exception. You should have recieved a copy of the text describing
|
|
||||||
* the FLOSS exception, and it is also available here:
|
|
||||||
* http://www.alfresco.com/legal/licensing"
|
|
||||||
*/
|
|
||||||
package org.alfresco.web.scripts;
|
|
||||||
|
|
||||||
import org.alfresco.repo.security.authentication.AuthenticationUtil;
|
|
||||||
import org.aopalliance.intercept.MethodInterceptor;
|
|
||||||
import org.aopalliance.intercept.MethodInvocation;
|
|
||||||
import org.apache.commons.logging.Log;
|
|
||||||
import org.apache.commons.logging.LogFactory;
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* System Authentication Interceptor
|
|
||||||
*
|
|
||||||
* @author davidc
|
|
||||||
*/
|
|
||||||
public class SystemAuthenticator implements MethodInterceptor
|
|
||||||
{
|
|
||||||
// Logger
|
|
||||||
private static final Log logger = LogFactory.getLog(SystemAuthenticator.class);
|
|
||||||
|
|
||||||
|
|
||||||
/* (non-Javadoc)
|
|
||||||
* @see org.aopalliance.intercept.MethodInterceptor#invoke(org.aopalliance.intercept.MethodInvocation)
|
|
||||||
*/
|
|
||||||
public Object invoke(MethodInvocation invocation)
|
|
||||||
throws Throwable
|
|
||||||
{
|
|
||||||
String currentUser = null;
|
|
||||||
Object retVal = null;
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
//
|
|
||||||
// Determine if user already authenticated
|
|
||||||
//
|
|
||||||
|
|
||||||
currentUser = AuthenticationUtil.getCurrentUserName();
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
logger.debug("Current authentication: " + (currentUser == null ? "unauthenticated" : "authenticated as " + currentUser));
|
|
||||||
|
|
||||||
//
|
|
||||||
// Force system user
|
|
||||||
//
|
|
||||||
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
logger.debug("Authenticating as System");
|
|
||||||
|
|
||||||
AuthenticationUtil.setSystemUserAsCurrentUser();
|
|
||||||
|
|
||||||
//
|
|
||||||
// Invoke service
|
|
||||||
//
|
|
||||||
|
|
||||||
retVal = invocation.proceed();
|
|
||||||
}
|
|
||||||
finally
|
|
||||||
{
|
|
||||||
AuthenticationUtil.clearCurrentSecurityContext();
|
|
||||||
if (currentUser != null)
|
|
||||||
{
|
|
||||||
AuthenticationUtil.setCurrentUser(currentUser);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
logger.debug("Authentication reset: " + (currentUser == null ? "unauthenticated" : "authenticated as " + currentUser));
|
|
||||||
}
|
|
||||||
|
|
||||||
return retVal;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
@@ -88,6 +88,7 @@ public class TestWebScriptServer
|
|||||||
this.registry = registry;
|
this.registry = registry;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Sets the Messages resource bundle
|
* Sets the Messages resource bundle
|
||||||
*
|
*
|
||||||
@@ -162,15 +163,9 @@ public class TestWebScriptServer
|
|||||||
MockHttpServletRequest req = createRequest("get", uri);
|
MockHttpServletRequest req = createRequest("get", uri);
|
||||||
MockHttpServletResponse res = new MockHttpServletResponse();
|
MockHttpServletResponse res = new MockHttpServletResponse();
|
||||||
|
|
||||||
WebScriptMatch match = registry.findWebScript(req.getMethod(), uri);
|
WebScriptRuntime runtime = new WebScriptServletRuntime(registry, transactionService, null, req, res);
|
||||||
if (match == null)
|
runtime.executeScript();
|
||||||
{
|
|
||||||
throw new WebScriptException("No service bound to uri '" + uri + "'");
|
|
||||||
}
|
|
||||||
|
|
||||||
WebScriptRequest apiReq = new WebScriptRequest(req, match);
|
|
||||||
WebScriptResponse apiRes = new WebScriptResponse(res);
|
|
||||||
match.getWebScript().execute(apiReq, apiRes);
|
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -1,91 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2005-2007 Alfresco Software Limited.
|
|
||||||
*
|
|
||||||
* This program is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU General Public License
|
|
||||||
* as published by the Free Software Foundation; either version 2
|
|
||||||
* of the License, or (at your option) any later version.
|
|
||||||
|
|
||||||
* This program is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
* GNU General Public License for more details.
|
|
||||||
|
|
||||||
* You should have received a copy of the GNU General Public License
|
|
||||||
* along with this program; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
|
||||||
|
|
||||||
* As a special exception to the terms and conditions of version 2.0 of
|
|
||||||
* the GPL, you may redistribute this Program in connection with Free/Libre
|
|
||||||
* and Open Source Software ("FLOSS") applications as described in Alfresco's
|
|
||||||
* FLOSS exception. You should have recieved a copy of the text describing
|
|
||||||
* the FLOSS exception, and it is also available here:
|
|
||||||
* http://www.alfresco.com/legal/licensing"
|
|
||||||
*/
|
|
||||||
package org.alfresco.web.scripts;
|
|
||||||
|
|
||||||
import org.alfresco.repo.security.authentication.AuthenticationUtil;
|
|
||||||
import org.aopalliance.intercept.MethodInterceptor;
|
|
||||||
import org.aopalliance.intercept.MethodInvocation;
|
|
||||||
import org.apache.commons.logging.Log;
|
|
||||||
import org.apache.commons.logging.LogFactory;
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Trusted Authentication Interceptor
|
|
||||||
*
|
|
||||||
* Just use the currently authenticated user
|
|
||||||
*
|
|
||||||
* @author davidc
|
|
||||||
*/
|
|
||||||
public class TrustedAuthenticator implements MethodInterceptor
|
|
||||||
{
|
|
||||||
// Logger
|
|
||||||
private static final Log logger = LogFactory.getLog(TrustedAuthenticator.class);
|
|
||||||
|
|
||||||
|
|
||||||
/* (non-Javadoc)
|
|
||||||
* @see org.aopalliance.intercept.MethodInterceptor#invoke(org.aopalliance.intercept.MethodInvocation)
|
|
||||||
*/
|
|
||||||
public Object invoke(MethodInvocation invocation)
|
|
||||||
throws Throwable
|
|
||||||
{
|
|
||||||
String currentUser = null;
|
|
||||||
Object retVal = null;
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
//
|
|
||||||
// Determine if user already authenticated
|
|
||||||
//
|
|
||||||
|
|
||||||
currentUser = AuthenticationUtil.getCurrentUserName();
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
logger.debug("Current authentication: " + (currentUser == null ? "unauthenticated" : "authenticated as " + currentUser));
|
|
||||||
|
|
||||||
//
|
|
||||||
// Use current authentication
|
|
||||||
//
|
|
||||||
|
|
||||||
//
|
|
||||||
// Invoke service
|
|
||||||
//
|
|
||||||
|
|
||||||
retVal = invocation.proceed();
|
|
||||||
}
|
|
||||||
finally
|
|
||||||
{
|
|
||||||
AuthenticationUtil.clearCurrentSecurityContext();
|
|
||||||
if (currentUser != null)
|
|
||||||
{
|
|
||||||
AuthenticationUtil.setCurrentUser(currentUser);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
logger.debug("Authentication reset: " + (currentUser == null ? "unauthenticated" : "authenticated as " + currentUser));
|
|
||||||
}
|
|
||||||
|
|
||||||
return retVal;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
@@ -24,16 +24,16 @@
|
|||||||
*/
|
*/
|
||||||
package org.alfresco.web.scripts;
|
package org.alfresco.web.scripts;
|
||||||
|
|
||||||
import javax.servlet.ServletContext;
|
import java.io.IOException;
|
||||||
|
|
||||||
|
import javax.servlet.ServletContext;
|
||||||
|
import javax.servlet.http.HttpServletRequest;
|
||||||
|
import javax.servlet.http.HttpServletResponse;
|
||||||
|
|
||||||
import org.alfresco.repo.security.authentication.AuthenticationUtil;
|
|
||||||
import org.alfresco.service.cmr.security.AuthenticationService;
|
|
||||||
import org.alfresco.web.app.servlet.AuthenticationHelper;
|
import org.alfresco.web.app.servlet.AuthenticationHelper;
|
||||||
import org.alfresco.web.app.servlet.AuthenticationStatus;
|
import org.alfresco.web.app.servlet.AuthenticationStatus;
|
||||||
import org.alfresco.web.app.servlet.BaseServlet;
|
import org.alfresco.web.app.servlet.BaseServlet;
|
||||||
import org.alfresco.web.scripts.WebScriptDescription.RequiredAuthentication;
|
import org.alfresco.web.scripts.WebScriptDescription.RequiredAuthentication;
|
||||||
import org.aopalliance.intercept.MethodInterceptor;
|
|
||||||
import org.aopalliance.intercept.MethodInvocation;
|
|
||||||
import org.apache.commons.logging.Log;
|
import org.apache.commons.logging.Log;
|
||||||
import org.apache.commons.logging.LogFactory;
|
import org.apache.commons.logging.LogFactory;
|
||||||
import org.springframework.web.context.ServletContextAware;
|
import org.springframework.web.context.ServletContextAware;
|
||||||
@@ -44,14 +44,13 @@ import org.springframework.web.context.ServletContextAware;
|
|||||||
*
|
*
|
||||||
* @author davidc
|
* @author davidc
|
||||||
*/
|
*/
|
||||||
public class WebClientAuthenticator implements MethodInterceptor, ServletContextAware
|
public class WebClientAuthenticator implements WebScriptServletAuthenticator, ServletContextAware
|
||||||
{
|
{
|
||||||
// Logger
|
// Logger
|
||||||
private static final Log logger = LogFactory.getLog(WebClientAuthenticator.class);
|
private static final Log logger = LogFactory.getLog(WebClientAuthenticator.class);
|
||||||
|
|
||||||
// dependencies
|
// dependencies
|
||||||
private ServletContext context;
|
private ServletContext context;
|
||||||
private AuthenticationService authenticationService;
|
|
||||||
|
|
||||||
|
|
||||||
/* (non-Javadoc)
|
/* (non-Javadoc)
|
||||||
@@ -62,52 +61,25 @@ public class WebClientAuthenticator implements MethodInterceptor, ServletContext
|
|||||||
this.context = context;
|
this.context = context;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @param authenticationService
|
|
||||||
*/
|
|
||||||
public void setAuthenticationService(AuthenticationService authenticationService)
|
|
||||||
{
|
|
||||||
this.authenticationService = authenticationService;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* (non-Javadoc)
|
/* (non-Javadoc)
|
||||||
* @see org.aopalliance.intercept.MethodInterceptor#invoke(org.aopalliance.intercept.MethodInvocation)
|
* @see org.alfresco.web.scripts.WebScriptServletAuthenticator#authenticate(org.alfresco.web.scripts.WebScriptDescription.RequiredAuthentication, boolean, javax.servlet.http.HttpServletRequest, javax.servlet.http.HttpServletResponse)
|
||||||
*/
|
*/
|
||||||
public Object invoke(MethodInvocation invocation)
|
public void authenticate(RequiredAuthentication required, boolean isGuest, HttpServletRequest req, HttpServletResponse res)
|
||||||
throws Throwable
|
|
||||||
{
|
{
|
||||||
String currentUser = null;
|
|
||||||
Object retVal = null;
|
|
||||||
Object[] args = invocation.getArguments();
|
|
||||||
WebScriptRequest request = (WebScriptRequest)args[0];
|
|
||||||
WebScriptResponse response = (WebScriptResponse)args[1];
|
|
||||||
WebScript service = (WebScript)invocation.getThis();
|
|
||||||
WebScriptDescription description = service.getDescription();
|
|
||||||
AuthenticationStatus status = null;
|
AuthenticationStatus status = null;
|
||||||
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
|
|
||||||
//
|
|
||||||
// Determine if user already authenticated
|
|
||||||
//
|
|
||||||
|
|
||||||
currentUser = AuthenticationUtil.getCurrentUserName();
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
logger.debug("Current authentication: " + (currentUser == null ? "unauthenticated" : "authenticated as " + currentUser));
|
|
||||||
|
|
||||||
//
|
//
|
||||||
// validate credentials
|
// validate credentials
|
||||||
//
|
//
|
||||||
|
|
||||||
String ticket = request.getParameter("ticket");
|
String ticket = req.getParameter("ticket");
|
||||||
boolean isGuest = request.isGuest();
|
|
||||||
|
|
||||||
if (logger.isDebugEnabled())
|
if (logger.isDebugEnabled())
|
||||||
{
|
{
|
||||||
logger.debug("Web Script authentication required: " + description.getRequiredAuthentication());
|
logger.debug("Alfresco ticket provided: " + (ticket != null && ticket.length() > 0));
|
||||||
logger.debug("Guest login: " + isGuest);
|
|
||||||
logger.debug("Ticket provided: " + (ticket != null && ticket.length() > 0));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ticket != null && ticket.length() > 0)
|
if (ticket != null && ticket.length() > 0)
|
||||||
@@ -115,59 +87,43 @@ public class WebClientAuthenticator implements MethodInterceptor, ServletContext
|
|||||||
if (logger.isDebugEnabled())
|
if (logger.isDebugEnabled())
|
||||||
logger.debug("Authenticating ticket " + ticket);
|
logger.debug("Authenticating ticket " + ticket);
|
||||||
|
|
||||||
status = AuthenticationHelper.authenticate(context, request, response, ticket);
|
status = AuthenticationHelper.authenticate(context, req, res, ticket);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (isGuest && description.getRequiredAuthentication() == RequiredAuthentication.guest)
|
if (isGuest)
|
||||||
{
|
{
|
||||||
if (logger.isDebugEnabled())
|
if (logger.isDebugEnabled())
|
||||||
logger.debug("Authenticating as Guest");
|
logger.debug("Authenticating as Guest");
|
||||||
|
|
||||||
status = AuthenticationHelper.authenticate(context, request, response, true);
|
status = AuthenticationHelper.authenticate(context, req, res, true);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (logger.isDebugEnabled())
|
if (logger.isDebugEnabled())
|
||||||
logger.debug("Authenticating session");
|
logger.debug("Authenticating session");
|
||||||
|
|
||||||
status = AuthenticationHelper.authenticate(context, request, response, false);
|
status = AuthenticationHelper.authenticate(context, req, res, false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
//
|
//
|
||||||
// execute web script or request authorization
|
// if not authorized, redirect to login page
|
||||||
//
|
//
|
||||||
|
|
||||||
if (status != null && status != AuthenticationStatus.Failure)
|
if (status == null || status == AuthenticationStatus.Failure)
|
||||||
{
|
|
||||||
retVal = invocation.proceed();
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
{
|
||||||
// authentication failed - now need to display the login page to the user, if asked to
|
// authentication failed - now need to display the login page to the user, if asked to
|
||||||
if (logger.isDebugEnabled())
|
if (logger.isDebugEnabled())
|
||||||
logger.debug("Redirecting to Alfresco Login");
|
logger.debug("Redirecting to Alfresco Login");
|
||||||
|
|
||||||
BaseServlet.redirectToLoginPage(request, response, context);
|
BaseServlet.redirectToLoginPage(req, res, context);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
finally
|
catch(IOException e)
|
||||||
{
|
{
|
||||||
if (status != null && status != AuthenticationStatus.Failure)
|
throw new WebScriptException("Failed to authenticate", e);
|
||||||
{
|
|
||||||
authenticationService.clearCurrentSecurityContext();
|
|
||||||
if (currentUser != null)
|
|
||||||
{
|
|
||||||
AuthenticationUtil.setCurrentUser(currentUser);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
logger.debug("Authentication reset: " + (currentUser == null ? "unauthenticated" : "authenticated as " + currentUser));
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return retVal;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@@ -1,73 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2005-2007 Alfresco Software Limited.
|
|
||||||
*
|
|
||||||
* This program is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU General Public License
|
|
||||||
* as published by the Free Software Foundation; either version 2
|
|
||||||
* of the License, or (at your option) any later version.
|
|
||||||
|
|
||||||
* This program is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
* GNU General Public License for more details.
|
|
||||||
|
|
||||||
* You should have received a copy of the GNU General Public License
|
|
||||||
* along with this program; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
|
||||||
|
|
||||||
* As a special exception to the terms and conditions of version 2.0 of
|
|
||||||
* the GPL, you may redistribute this Program in connection with Free/Libre
|
|
||||||
* and Open Source Software ("FLOSS") applications as described in Alfresco's
|
|
||||||
* FLOSS exception. You should have recieved a copy of the text describing
|
|
||||||
* the FLOSS exception, and it is also available here:
|
|
||||||
* http://www.alfresco.com/legal/licensing"
|
|
||||||
*/
|
|
||||||
package org.alfresco.web.scripts;
|
|
||||||
|
|
||||||
import org.alfresco.i18n.I18NUtil;
|
|
||||||
import org.alfresco.repo.security.authentication.AuthenticationUtil;
|
|
||||||
import org.aopalliance.intercept.MethodInterceptor;
|
|
||||||
import org.aopalliance.intercept.MethodInvocation;
|
|
||||||
import org.apache.commons.logging.Log;
|
|
||||||
import org.apache.commons.logging.LogFactory;
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Web Script Logger
|
|
||||||
*
|
|
||||||
* @author davidc
|
|
||||||
*/
|
|
||||||
public class WebScriptLogger implements MethodInterceptor
|
|
||||||
{
|
|
||||||
// Logger
|
|
||||||
private static final Log logger = LogFactory.getLog(WebScriptLogger.class);
|
|
||||||
|
|
||||||
/* (non-Javadoc)
|
|
||||||
* @see org.aopalliance.intercept.MethodInterceptor#invoke(org.aopalliance.intercept.MethodInvocation)
|
|
||||||
*/
|
|
||||||
public Object invoke(MethodInvocation invocation)
|
|
||||||
throws Throwable
|
|
||||||
{
|
|
||||||
Object retVal = null;
|
|
||||||
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
{
|
|
||||||
WebScript service = (WebScript)invocation.getThis();
|
|
||||||
WebScriptDescription description = service.getDescription();
|
|
||||||
String user = AuthenticationUtil.getCurrentUserName();
|
|
||||||
String locale = I18NUtil.getLocale().toString();
|
|
||||||
logger.debug("Invoking Web Script " + description.getId() + (user == null ? " (unauthenticated)" : " (authenticated as " + user + ")" + " (" + locale + ")"));
|
|
||||||
long start = System.currentTimeMillis();
|
|
||||||
retVal = invocation.proceed();
|
|
||||||
long end = System.currentTimeMillis();
|
|
||||||
logger.debug("Web Script " + description.getId() + " executed in " + (end - start) + "ms");
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
retVal = invocation.proceed();
|
|
||||||
}
|
|
||||||
|
|
||||||
return retVal;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
318
source/java/org/alfresco/web/scripts/WebScriptRuntime.java
Normal file
318
source/java/org/alfresco/web/scripts/WebScriptRuntime.java
Normal file
@@ -0,0 +1,318 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2005-2007 Alfresco Software Limited.
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License
|
||||||
|
* as published by the Free Software Foundation; either version 2
|
||||||
|
* of the License, or (at your option) any later version.
|
||||||
|
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
|
|
||||||
|
* As a special exception to the terms and conditions of version 2.0 of
|
||||||
|
* the GPL, you may redistribute this Program in connection with Free/Libre
|
||||||
|
* and Open Source Software ("FLOSS") applications as described in Alfresco's
|
||||||
|
* FLOSS exception. You should have recieved a copy of the text describing
|
||||||
|
* the FLOSS exception, and it is also available here:
|
||||||
|
* http://www.alfresco.com/legal/licensing"
|
||||||
|
*/
|
||||||
|
package org.alfresco.web.scripts;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
|
import org.alfresco.i18n.I18NUtil;
|
||||||
|
import org.alfresco.repo.security.authentication.AuthenticationUtil;
|
||||||
|
import org.alfresco.repo.transaction.TransactionUtil;
|
||||||
|
import org.alfresco.service.transaction.TransactionService;
|
||||||
|
import org.alfresco.web.scripts.WebScriptDescription.RequiredAuthentication;
|
||||||
|
import org.alfresco.web.scripts.WebScriptDescription.RequiredTransaction;
|
||||||
|
import org.apache.commons.logging.Log;
|
||||||
|
import org.apache.commons.logging.LogFactory;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Encapsulates the execution of a single Web Script.
|
||||||
|
*
|
||||||
|
* Provides support for logging, transactions and authentication.
|
||||||
|
*
|
||||||
|
* Sub-classes of WebScriptRuntime maintain the execution environment e.g. servlet
|
||||||
|
* request & response.
|
||||||
|
*
|
||||||
|
* A new instance of WebScriptRuntime is required for each new execution environment.
|
||||||
|
*
|
||||||
|
* @author davidc
|
||||||
|
*/
|
||||||
|
public abstract class WebScriptRuntime
|
||||||
|
{
|
||||||
|
// Logger
|
||||||
|
protected static final Log logger = LogFactory.getLog(WebScriptRuntime.class);
|
||||||
|
|
||||||
|
/** Component Dependencies */
|
||||||
|
private WebScriptRegistry registry;
|
||||||
|
private TransactionService transactionService;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Construct
|
||||||
|
*
|
||||||
|
* @param registry web script registry
|
||||||
|
* @param transactionService transaction service
|
||||||
|
*/
|
||||||
|
public WebScriptRuntime(WebScriptRegistry registry, TransactionService transactionService)
|
||||||
|
{
|
||||||
|
this.registry = registry;
|
||||||
|
this.transactionService = transactionService;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Execute the Web Script encapsulated by this Web Script Runtime
|
||||||
|
*/
|
||||||
|
public void executeScript()
|
||||||
|
{
|
||||||
|
long startRuntime = System.currentTimeMillis();
|
||||||
|
|
||||||
|
String method = getScriptMethod();
|
||||||
|
String scriptUrl = getScriptUrl();
|
||||||
|
|
||||||
|
try
|
||||||
|
{
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
logger.debug("Processing script url (" + method + ") " + scriptUrl);
|
||||||
|
|
||||||
|
WebScriptMatch match = registry.findWebScript(method, scriptUrl);
|
||||||
|
if (match != null)
|
||||||
|
{
|
||||||
|
// setup web script context
|
||||||
|
final WebScriptRequest scriptReq = createRequest(match);
|
||||||
|
final WebScriptResponse scriptRes = createResponse();
|
||||||
|
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
logger.debug("Agent: " + scriptReq.getAgent());
|
||||||
|
|
||||||
|
long startScript = System.currentTimeMillis();
|
||||||
|
final WebScript script = match.getWebScript();
|
||||||
|
final WebScriptDescription description = script.getDescription();
|
||||||
|
|
||||||
|
try
|
||||||
|
{
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
{
|
||||||
|
String user = AuthenticationUtil.getCurrentUserName();
|
||||||
|
String locale = I18NUtil.getLocale().toString();
|
||||||
|
logger.debug("Invoking Web Script " + description.getId() + (user == null ? " (unauthenticated)" : " (authenticated as " + user + ")" + " (" + locale + ")"));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (description.getRequiredTransaction() == RequiredTransaction.none)
|
||||||
|
{
|
||||||
|
authenticatedExecute(scriptReq, scriptRes);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// encapsulate script within transaction
|
||||||
|
TransactionUtil.TransactionWork<Object> work = new TransactionUtil.TransactionWork<Object>()
|
||||||
|
{
|
||||||
|
public Object doWork() throws Throwable
|
||||||
|
{
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
logger.debug("Begin transaction: " + description.getRequiredTransaction());
|
||||||
|
|
||||||
|
authenticatedExecute(scriptReq, scriptRes);
|
||||||
|
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
logger.debug("End transaction: " + description.getRequiredTransaction());
|
||||||
|
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
if (description.getRequiredTransaction() == RequiredTransaction.required)
|
||||||
|
{
|
||||||
|
TransactionUtil.executeInUserTransaction(transactionService, work);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
TransactionUtil.executeInNonPropagatingUserTransaction(transactionService, work);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch(IOException e)
|
||||||
|
{
|
||||||
|
throw new WebScriptException("Failed to execute script", e);
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
{
|
||||||
|
long endScript = System.currentTimeMillis();
|
||||||
|
logger.debug("Web Script " + description.getId() + " executed in " + (endScript - startScript) + "ms");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
String msg = "Script url (" + method + ") " + scriptUrl + " does not map to a Web Script.";
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
logger.debug(msg);
|
||||||
|
|
||||||
|
throw new WebScriptException(msg);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
long endRuntime = System.currentTimeMillis();
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
logger.debug("Processed script url (" + method + ") " + scriptUrl + " in " + (endRuntime - startRuntime) + "ms");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Execute script whilst authenticated
|
||||||
|
*
|
||||||
|
* @param scriptReq Web Script Request
|
||||||
|
* @param scriptRes Web Script Response
|
||||||
|
* @throws IOException
|
||||||
|
*/
|
||||||
|
protected void authenticatedExecute(WebScriptRequest scriptReq, WebScriptResponse scriptRes)
|
||||||
|
throws IOException
|
||||||
|
{
|
||||||
|
WebScript script = scriptReq.getServiceMatch().getWebScript();
|
||||||
|
WebScriptDescription desc = script.getDescription();
|
||||||
|
RequiredAuthentication required = desc.getRequiredAuthentication();
|
||||||
|
boolean isGuest = scriptReq.isGuest();
|
||||||
|
|
||||||
|
if (required == RequiredAuthentication.none)
|
||||||
|
{
|
||||||
|
wrappedExecute(scriptReq, scriptRes);
|
||||||
|
}
|
||||||
|
else if (required == RequiredAuthentication.user && isGuest)
|
||||||
|
{
|
||||||
|
throw new WebScriptException("Web Script " + desc.getId() + " requires user authentication; however, a guest has attempted access.");
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
String currentUser = null;
|
||||||
|
|
||||||
|
try
|
||||||
|
{
|
||||||
|
//
|
||||||
|
// Determine if user already authenticated
|
||||||
|
//
|
||||||
|
|
||||||
|
currentUser = AuthenticationUtil.getCurrentUserName();
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
{
|
||||||
|
logger.debug("Current authentication: " + (currentUser == null ? "unauthenticated" : "authenticated as " + currentUser));
|
||||||
|
logger.debug("Authentication required: " + required);
|
||||||
|
logger.debug("Guest login: " + isGuest);
|
||||||
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// Apply appropriate authentication to Web Script invocation
|
||||||
|
//
|
||||||
|
|
||||||
|
authenticate(required, isGuest);
|
||||||
|
|
||||||
|
//
|
||||||
|
// Execute Web Script
|
||||||
|
wrappedExecute(scriptReq, scriptRes);
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
//
|
||||||
|
// Reset authentication for current thread
|
||||||
|
//
|
||||||
|
|
||||||
|
AuthenticationUtil.clearCurrentSecurityContext();
|
||||||
|
if (currentUser != null)
|
||||||
|
{
|
||||||
|
AuthenticationUtil.setCurrentUser(currentUser);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
logger.debug("Authentication reset: " + (currentUser == null ? "unauthenticated" : "authenticated as " + currentUser));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Execute Web Script with pre & post hooks
|
||||||
|
*
|
||||||
|
* @param scriptReq Web Script Request
|
||||||
|
* @param scriptRes Web Script Response
|
||||||
|
* @throws IOException
|
||||||
|
*/
|
||||||
|
protected void wrappedExecute(WebScriptRequest scriptReq, WebScriptResponse scriptRes)
|
||||||
|
throws IOException
|
||||||
|
{
|
||||||
|
boolean execute = preExecute(scriptReq, scriptRes);
|
||||||
|
if (execute)
|
||||||
|
{
|
||||||
|
WebScript script = scriptReq.getServiceMatch().getWebScript();
|
||||||
|
script.execute(scriptReq, scriptRes);
|
||||||
|
postExecute(scriptReq, scriptRes);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get the Web Script Method e.g. get, post
|
||||||
|
*
|
||||||
|
* @return web script method
|
||||||
|
*/
|
||||||
|
protected abstract String getScriptMethod();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get the Web Script Url
|
||||||
|
*
|
||||||
|
* @return web script url
|
||||||
|
*/
|
||||||
|
protected abstract String getScriptUrl();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a Web Script Request
|
||||||
|
*
|
||||||
|
* @param match web script matching the script method and url
|
||||||
|
* @return web script request
|
||||||
|
*/
|
||||||
|
protected abstract WebScriptRequest createRequest(WebScriptMatch match);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a Web Script Response
|
||||||
|
*
|
||||||
|
* @return web script response
|
||||||
|
*/
|
||||||
|
protected abstract WebScriptResponse createResponse();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Authenticate Web Script execution
|
||||||
|
*
|
||||||
|
* @param required required level of authentication
|
||||||
|
* @param isGuest is the request accessed as Guest
|
||||||
|
*/
|
||||||
|
protected abstract void authenticate(RequiredAuthentication required, boolean isGuest);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Pre-execution hook
|
||||||
|
*
|
||||||
|
* @param scriptReq Web Script Request
|
||||||
|
* @param scriptRes Web Script Response
|
||||||
|
* @return true => execute script, false => do not execute script
|
||||||
|
*/
|
||||||
|
protected abstract boolean preExecute(WebScriptRequest scriptReq, WebScriptResponse scriptRes);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Post-execution hook
|
||||||
|
*
|
||||||
|
* Note: this hook is not invoked if the script is not executed.
|
||||||
|
*
|
||||||
|
* @param scriptReq Web Script Request
|
||||||
|
* @param scriptRes Web Script Response
|
||||||
|
*/
|
||||||
|
protected abstract void postExecute(WebScriptRequest scriptReq, WebScriptResponse scriptRes);
|
||||||
|
|
||||||
|
}
|
@@ -31,6 +31,7 @@ import javax.servlet.http.HttpServlet;
|
|||||||
import javax.servlet.http.HttpServletRequest;
|
import javax.servlet.http.HttpServletRequest;
|
||||||
import javax.servlet.http.HttpServletResponse;
|
import javax.servlet.http.HttpServletResponse;
|
||||||
|
|
||||||
|
import org.alfresco.service.transaction.TransactionService;
|
||||||
import org.apache.commons.logging.Log;
|
import org.apache.commons.logging.Log;
|
||||||
import org.apache.commons.logging.LogFactory;
|
import org.apache.commons.logging.LogFactory;
|
||||||
import org.springframework.context.ApplicationContext;
|
import org.springframework.context.ApplicationContext;
|
||||||
@@ -49,8 +50,11 @@ public class WebScriptServlet extends HttpServlet
|
|||||||
// Logger
|
// Logger
|
||||||
private static final Log logger = LogFactory.getLog(WebScriptServlet.class);
|
private static final Log logger = LogFactory.getLog(WebScriptServlet.class);
|
||||||
|
|
||||||
// Web Scripts
|
// Component Dependencies
|
||||||
private DeclarativeWebScriptRegistry registry;
|
private DeclarativeWebScriptRegistry registry;
|
||||||
|
private TransactionService transactionService;
|
||||||
|
private WebScriptServletAuthenticator authenticator;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@@ -59,12 +63,21 @@ public class WebScriptServlet extends HttpServlet
|
|||||||
super.init();
|
super.init();
|
||||||
ApplicationContext context = WebApplicationContextUtils.getRequiredWebApplicationContext(getServletContext());
|
ApplicationContext context = WebApplicationContextUtils.getRequiredWebApplicationContext(getServletContext());
|
||||||
registry = (DeclarativeWebScriptRegistry)context.getBean("webscripts.registry");
|
registry = (DeclarativeWebScriptRegistry)context.getBean("webscripts.registry");
|
||||||
registry.initWebScripts();
|
transactionService = (TransactionService)context.getBean("transactionComponent");
|
||||||
|
|
||||||
|
// retrieve authenticator via servlet initialisation parameter
|
||||||
|
String authenticatorId = getInitParameter("authenticator");
|
||||||
|
if (authenticatorId == null || authenticatorId.length() == 0)
|
||||||
|
{
|
||||||
|
authenticatorId = "webscripts.authenticator.webclient";
|
||||||
|
}
|
||||||
|
Object bean = context.getBean(authenticatorId);
|
||||||
|
if (bean == null || !(bean instanceof WebScriptServletAuthenticator))
|
||||||
|
{
|
||||||
|
throw new ServletException("Initialisation parameter 'authenticator' does not refer to a Web Script authenticator (" + authenticatorId + ")");
|
||||||
|
}
|
||||||
|
authenticator = (WebScriptServletAuthenticator)bean;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// TODO:
|
|
||||||
// - authentication (as suggested in http://www.xml.com/pub/a/2003/12/17/dive.html)
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -75,48 +88,17 @@ public class WebScriptServlet extends HttpServlet
|
|||||||
*/
|
*/
|
||||||
protected void service(HttpServletRequest req, HttpServletResponse res) throws ServletException, IOException
|
protected void service(HttpServletRequest req, HttpServletResponse res) throws ServletException, IOException
|
||||||
{
|
{
|
||||||
long start = System.currentTimeMillis();
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
//
|
|
||||||
// Execute appropriate web scripy
|
|
||||||
//
|
|
||||||
// TODO: Handle errors (with appropriate HTTP error responses)
|
|
||||||
|
|
||||||
String uri = req.getPathInfo();
|
|
||||||
|
|
||||||
if (logger.isDebugEnabled())
|
if (logger.isDebugEnabled())
|
||||||
logger.debug("Processing request (" + req.getMethod() + ") " + req.getRequestURL() + (req.getQueryString() != null ? "?" + req.getQueryString() : ""));
|
logger.debug("Processing request (" + req.getMethod() + ") " + req.getRequestURL() + (req.getQueryString() != null ? "?" + req.getQueryString() : ""));
|
||||||
|
|
||||||
WebScriptMatch match = registry.findWebScript(req.getMethod(), uri);
|
try
|
||||||
if (match != null)
|
|
||||||
{
|
{
|
||||||
// setup web script context
|
WebScriptRuntime runtime = new WebScriptServletRuntime(registry, transactionService, authenticator, req, res);
|
||||||
WebScriptRequest apiReq = new WebScriptRequest(req, match);
|
runtime.executeScript();
|
||||||
WebScriptResponse apiRes = new WebScriptResponse(res);
|
|
||||||
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
logger.debug("Agent: " + apiReq.getAgent());
|
|
||||||
|
|
||||||
// execute service
|
|
||||||
match.getWebScript().execute(apiReq, apiRes);
|
|
||||||
}
|
}
|
||||||
else
|
catch(Throwable e)
|
||||||
{
|
{
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
logger.debug("Request does not map to service.");
|
|
||||||
|
|
||||||
res.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
|
res.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
|
||||||
// TODO: add appropriate error detail
|
|
||||||
}
|
|
||||||
}
|
|
||||||
// TODO: exception handling
|
|
||||||
finally
|
|
||||||
{
|
|
||||||
long end = System.currentTimeMillis();
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
logger.debug("Processed request (" + req.getMethod() + ") " + req.getRequestURL() + (req.getQueryString() != null ? "?" + req.getQueryString() : "") + " in " + (end - start) + "ms");
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -24,33 +24,28 @@
|
|||||||
*/
|
*/
|
||||||
package org.alfresco.web.scripts;
|
package org.alfresco.web.scripts;
|
||||||
|
|
||||||
|
import javax.servlet.http.HttpServletRequest;
|
||||||
import javax.servlet.http.HttpServletResponse;
|
import javax.servlet.http.HttpServletResponse;
|
||||||
import javax.servlet.http.HttpServletResponseWrapper;
|
|
||||||
|
import org.alfresco.web.scripts.WebScriptDescription.RequiredAuthentication;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* API Service Response
|
* Web Script Authenticator for the HTTP Servlet environment
|
||||||
*
|
*
|
||||||
* @author davidc
|
* @author davidc
|
||||||
*/
|
*/
|
||||||
public class WebScriptResponse extends HttpServletResponseWrapper
|
public interface WebScriptServletAuthenticator
|
||||||
{
|
{
|
||||||
// API Formats
|
|
||||||
public static final String HTML_FORMAT = "html";
|
|
||||||
public static final String ATOM_FORMAT = "atom";
|
|
||||||
public static final String RSS_FORMAT = "rss";
|
|
||||||
public static final String XML_FORMAT = "xml";
|
|
||||||
public static final String JSON_FORMAT = "json";
|
|
||||||
public static final String OPENSEARCH_DESCRIPTION_FORMAT = "opensearchdescription";
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Construct
|
* Authenticate Web Script execution
|
||||||
*
|
*
|
||||||
* @param res
|
* @param required required level of authentication
|
||||||
|
* @param isGuest is Guest accessing the web script
|
||||||
|
* @param req http servlet request
|
||||||
|
* @param res http servlet response
|
||||||
*/
|
*/
|
||||||
WebScriptResponse(HttpServletResponse res)
|
public void authenticate(RequiredAuthentication required, boolean isGuest, HttpServletRequest req, HttpServletResponse res);
|
||||||
{
|
|
||||||
super(res);
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
@@ -24,17 +24,21 @@
|
|||||||
*/
|
*/
|
||||||
package org.alfresco.web.scripts;
|
package org.alfresco.web.scripts;
|
||||||
|
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
import javax.servlet.http.HttpServletRequest;
|
import javax.servlet.http.HttpServletRequest;
|
||||||
import javax.servlet.http.HttpServletRequestWrapper;
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Web Script Request
|
* HTTP Servlet Web Script Request
|
||||||
*
|
*
|
||||||
* @author davidc
|
* @author davidc
|
||||||
*/
|
*/
|
||||||
public class WebScriptRequest extends HttpServletRequestWrapper
|
public class WebScriptServletRequest implements WebScriptRequest
|
||||||
{
|
{
|
||||||
|
/** HTTP Request */
|
||||||
|
private HttpServletRequest req;
|
||||||
|
|
||||||
/** Service bound to this request */
|
/** Service bound to this request */
|
||||||
private WebScriptMatch serviceMatch;
|
private WebScriptMatch serviceMatch;
|
||||||
|
|
||||||
@@ -45,12 +49,22 @@ public class WebScriptRequest extends HttpServletRequestWrapper
|
|||||||
* @param req
|
* @param req
|
||||||
* @param serviceMatch
|
* @param serviceMatch
|
||||||
*/
|
*/
|
||||||
WebScriptRequest(HttpServletRequest req, WebScriptMatch serviceMatch)
|
WebScriptServletRequest(HttpServletRequest req, WebScriptMatch serviceMatch)
|
||||||
{
|
{
|
||||||
super(req);
|
this.req = req;
|
||||||
this.serviceMatch = serviceMatch;
|
this.serviceMatch = serviceMatch;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the HTTP Servlet Request
|
||||||
|
*
|
||||||
|
* @return HTTP Servlet Request
|
||||||
|
*/
|
||||||
|
public HttpServletRequest getHttpServletRequest()
|
||||||
|
{
|
||||||
|
return req;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets the matching API Service for this request
|
* Gets the matching API Service for this request
|
||||||
*
|
*
|
||||||
@@ -70,7 +84,15 @@ public class WebScriptRequest extends HttpServletRequestWrapper
|
|||||||
*/
|
*/
|
||||||
public String getServerPath()
|
public String getServerPath()
|
||||||
{
|
{
|
||||||
return getScheme() + "://" + getServerName() + ":" + getServerPort();
|
return req.getScheme() + "://" + req.getServerName() + ":" + req.getServerPort();
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRequest#getContextPath()
|
||||||
|
*/
|
||||||
|
public String getContextPath()
|
||||||
|
{
|
||||||
|
return req.getContextPath();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -80,7 +102,7 @@ public class WebScriptRequest extends HttpServletRequestWrapper
|
|||||||
*/
|
*/
|
||||||
public String getServiceContextPath()
|
public String getServiceContextPath()
|
||||||
{
|
{
|
||||||
return getContextPath() + getServletPath();
|
return req.getContextPath() + req.getServletPath();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -90,7 +112,7 @@ public class WebScriptRequest extends HttpServletRequestWrapper
|
|||||||
*/
|
*/
|
||||||
public String getServicePath()
|
public String getServicePath()
|
||||||
{
|
{
|
||||||
return getServiceContextPath() + getPathInfo();
|
return getServiceContextPath() + req.getPathInfo();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -100,7 +122,34 @@ public class WebScriptRequest extends HttpServletRequestWrapper
|
|||||||
*/
|
*/
|
||||||
public String getURL()
|
public String getURL()
|
||||||
{
|
{
|
||||||
return getServicePath() + (getQueryString() != null ? "?" + getQueryString() : "");
|
return getServicePath() + (req.getQueryString() != null ? "?" + req.getQueryString() : "");
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRequest#getQueryString()
|
||||||
|
*/
|
||||||
|
public String getQueryString()
|
||||||
|
{
|
||||||
|
return req.getQueryString();
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRequest#getParameterNames()
|
||||||
|
*/
|
||||||
|
public String[] getParameterNames()
|
||||||
|
{
|
||||||
|
Set<String> keys = req.getParameterMap().keySet();
|
||||||
|
String[] names = new String[keys.size()];
|
||||||
|
keys.toArray(names);
|
||||||
|
return names;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRequest#getParameter(java.lang.String)
|
||||||
|
*/
|
||||||
|
public String getParameter(String name)
|
||||||
|
{
|
||||||
|
return req.getParameter(name);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -117,7 +166,7 @@ public class WebScriptRequest extends HttpServletRequestWrapper
|
|||||||
public String getExtensionPath()
|
public String getExtensionPath()
|
||||||
{
|
{
|
||||||
String servicePath = serviceMatch.getPath();
|
String servicePath = serviceMatch.getPath();
|
||||||
String extensionPath = getPathInfo();
|
String extensionPath = req.getPathInfo();
|
||||||
int extIdx = extensionPath.indexOf(servicePath);
|
int extIdx = extensionPath.indexOf(servicePath);
|
||||||
if (extIdx != -1)
|
if (extIdx != -1)
|
||||||
{
|
{
|
||||||
@@ -157,7 +206,7 @@ public class WebScriptRequest extends HttpServletRequestWrapper
|
|||||||
*/
|
*/
|
||||||
public String getAgent()
|
public String getAgent()
|
||||||
{
|
{
|
||||||
String userAgent = getHeader("user-agent");
|
String userAgent = req.getHeader("user-agent");
|
||||||
if (userAgent != null)
|
if (userAgent != null)
|
||||||
{
|
{
|
||||||
if (userAgent.indexOf("Firefox/") != -1)
|
if (userAgent.indexOf("Firefox/") != -1)
|
||||||
@@ -171,4 +220,5 @@ public class WebScriptRequest extends HttpServletRequestWrapper
|
|||||||
}
|
}
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
@@ -0,0 +1,95 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2005-2007 Alfresco Software Limited.
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License
|
||||||
|
* as published by the Free Software Foundation; either version 2
|
||||||
|
* of the License, or (at your option) any later version.
|
||||||
|
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
|
|
||||||
|
* As a special exception to the terms and conditions of version 2.0 of
|
||||||
|
* the GPL, you may redistribute this Program in connection with Free/Libre
|
||||||
|
* and Open Source Software ("FLOSS") applications as described in Alfresco's
|
||||||
|
* FLOSS exception. You should have recieved a copy of the text describing
|
||||||
|
* the FLOSS exception, and it is also available here:
|
||||||
|
* http://www.alfresco.com/legal/licensing"
|
||||||
|
*/
|
||||||
|
package org.alfresco.web.scripts;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.io.OutputStream;
|
||||||
|
import java.io.Writer;
|
||||||
|
|
||||||
|
import javax.servlet.http.HttpServletRequest;
|
||||||
|
import javax.servlet.http.HttpServletResponse;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* HTTP Servlet Web Script Response
|
||||||
|
*
|
||||||
|
* @author davidc
|
||||||
|
*/
|
||||||
|
public class WebScriptServletResponse implements WebScriptResponse
|
||||||
|
{
|
||||||
|
private HttpServletResponse res;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Construct
|
||||||
|
*
|
||||||
|
* @param res
|
||||||
|
*/
|
||||||
|
WebScriptServletResponse(HttpServletResponse res)
|
||||||
|
{
|
||||||
|
this.res = res;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the HTTP Servlet Response
|
||||||
|
*
|
||||||
|
* @return HTTP Servlet Response
|
||||||
|
*/
|
||||||
|
public HttpServletResponse getHttpServletResponse()
|
||||||
|
{
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptResponse#setContentType(java.lang.String)
|
||||||
|
*/
|
||||||
|
public void setContentType(String contentType)
|
||||||
|
{
|
||||||
|
res.setContentType(contentType);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptResponse#getWriter()
|
||||||
|
*/
|
||||||
|
public Writer getWriter() throws IOException
|
||||||
|
{
|
||||||
|
return res.getWriter();
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptResponse#getOutputStream()
|
||||||
|
*/
|
||||||
|
public OutputStream getOutputStream() throws IOException
|
||||||
|
{
|
||||||
|
return res.getOutputStream();
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptResponse#encodeScriptUrl(java.lang.String)
|
||||||
|
*/
|
||||||
|
public String encodeScriptUrl(String url)
|
||||||
|
{
|
||||||
|
return url;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@@ -0,0 +1,128 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2005-2007 Alfresco Software Limited.
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License
|
||||||
|
* as published by the Free Software Foundation; either version 2
|
||||||
|
* of the License, or (at your option) any later version.
|
||||||
|
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
|
|
||||||
|
* As a special exception to the terms and conditions of version 2.0 of
|
||||||
|
* the GPL, you may redistribute this Program in connection with Free/Libre
|
||||||
|
* and Open Source Software ("FLOSS") applications as described in Alfresco's
|
||||||
|
* FLOSS exception. You should have recieved a copy of the text describing
|
||||||
|
* the FLOSS exception, and it is also available here:
|
||||||
|
* http://www.alfresco.com/legal/licensing"
|
||||||
|
*/
|
||||||
|
package org.alfresco.web.scripts;
|
||||||
|
|
||||||
|
import javax.servlet.http.HttpServletRequest;
|
||||||
|
import javax.servlet.http.HttpServletResponse;
|
||||||
|
|
||||||
|
import org.alfresco.service.transaction.TransactionService;
|
||||||
|
import org.alfresco.web.scripts.WebScriptDescription.RequiredAuthentication;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* HTTP Servlet Web Script Runtime
|
||||||
|
*
|
||||||
|
* @author davidc
|
||||||
|
*/
|
||||||
|
public class WebScriptServletRuntime extends WebScriptRuntime
|
||||||
|
{
|
||||||
|
private HttpServletRequest req;
|
||||||
|
private HttpServletResponse res;
|
||||||
|
private WebScriptServletAuthenticator authenticator;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Construct
|
||||||
|
*
|
||||||
|
* @param registry
|
||||||
|
* @param transactionService
|
||||||
|
* @param authenticator
|
||||||
|
* @param req
|
||||||
|
* @param res
|
||||||
|
*/
|
||||||
|
public WebScriptServletRuntime(WebScriptRegistry registry, TransactionService transactionService, WebScriptServletAuthenticator authenticator, HttpServletRequest req, HttpServletResponse res)
|
||||||
|
{
|
||||||
|
super(registry, transactionService);
|
||||||
|
this.req = req;
|
||||||
|
this.res = res;
|
||||||
|
this.authenticator = authenticator;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRuntime#getScriptMethod()
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
protected String getScriptMethod()
|
||||||
|
{
|
||||||
|
return req.getMethod();
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRuntime#getScriptUrl()
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
protected String getScriptUrl()
|
||||||
|
{
|
||||||
|
return req.getPathInfo();
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRuntime#createRequest(org.alfresco.web.scripts.WebScriptMatch)
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
protected WebScriptRequest createRequest(WebScriptMatch match)
|
||||||
|
{
|
||||||
|
return new WebScriptServletRequest(req, match);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRuntime#createResponse()
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
protected WebScriptResponse createResponse()
|
||||||
|
{
|
||||||
|
return new WebScriptServletResponse(res);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRuntime#authenticate(org.alfresco.web.scripts.WebScriptDescription.RequiredAuthentication, boolean)
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
protected void authenticate(RequiredAuthentication required, boolean isGuest)
|
||||||
|
{
|
||||||
|
if (authenticator != null)
|
||||||
|
{
|
||||||
|
authenticator.authenticate(required, isGuest, req, res);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRuntime#preExecute(org.alfresco.web.scripts.WebScriptRequest, org.alfresco.web.scripts.WebScriptResponse)
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
protected boolean preExecute(WebScriptRequest scriptReq, WebScriptResponse scriptRes)
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRuntime#postExecute(org.alfresco.web.scripts.WebScriptRequest, org.alfresco.web.scripts.WebScriptResponse)
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
protected void postExecute(WebScriptRequest scriptReq, WebScriptResponse scriptRes)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@@ -1,100 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2005-2007 Alfresco Software Limited.
|
|
||||||
*
|
|
||||||
* This program is free software; you can redistribute it and/or
|
|
||||||
* modify it under the terms of the GNU General Public License
|
|
||||||
* as published by the Free Software Foundation; either version 2
|
|
||||||
* of the License, or (at your option) any later version.
|
|
||||||
|
|
||||||
* This program is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
* GNU General Public License for more details.
|
|
||||||
|
|
||||||
* You should have received a copy of the GNU General Public License
|
|
||||||
* along with this program; if not, write to the Free Software
|
|
||||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
|
||||||
|
|
||||||
* As a special exception to the terms and conditions of version 2.0 of
|
|
||||||
* the GPL, you may redistribute this Program in connection with Free/Libre
|
|
||||||
* and Open Source Software ("FLOSS") applications as described in Alfresco's
|
|
||||||
* FLOSS exception. You should have recieved a copy of the text describing
|
|
||||||
* the FLOSS exception, and it is also available here:
|
|
||||||
* http://www.alfresco.com/legal/licensing"
|
|
||||||
*/
|
|
||||||
package org.alfresco.web.scripts;
|
|
||||||
|
|
||||||
import org.alfresco.repo.transaction.TransactionUtil;
|
|
||||||
import org.alfresco.service.transaction.TransactionService;
|
|
||||||
import org.alfresco.web.scripts.WebScriptDescription.RequiredTransaction;
|
|
||||||
import org.aopalliance.intercept.MethodInterceptor;
|
|
||||||
import org.aopalliance.intercept.MethodInvocation;
|
|
||||||
import org.apache.commons.logging.Log;
|
|
||||||
import org.apache.commons.logging.LogFactory;
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Web Script Transaction
|
|
||||||
*
|
|
||||||
* @author davidc
|
|
||||||
*/
|
|
||||||
public class WebScriptTransaction implements MethodInterceptor
|
|
||||||
{
|
|
||||||
// Logger
|
|
||||||
protected static final Log logger = LogFactory.getLog(WebScriptTransaction.class);
|
|
||||||
|
|
||||||
// dependencies
|
|
||||||
private TransactionService transactionService;
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets the transaction service
|
|
||||||
*
|
|
||||||
* @param transactionService
|
|
||||||
*/
|
|
||||||
public void setTransactionService(TransactionService transactionService)
|
|
||||||
{
|
|
||||||
this.transactionService = transactionService;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* (non-Javadoc)
|
|
||||||
* @see org.aopalliance.intercept.MethodInterceptor#invoke(org.aopalliance.intercept.MethodInvocation)
|
|
||||||
*/
|
|
||||||
public Object invoke(final MethodInvocation invocation)
|
|
||||||
throws Throwable
|
|
||||||
{
|
|
||||||
WebScript service = (WebScript)invocation.getThis();
|
|
||||||
final WebScriptDescription description = service.getDescription();
|
|
||||||
|
|
||||||
// encapsulate service call within transaction
|
|
||||||
TransactionUtil.TransactionWork<Object> work = new TransactionUtil.TransactionWork<Object>()
|
|
||||||
{
|
|
||||||
public Object doWork() throws Throwable
|
|
||||||
{
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
logger.debug("Begin transaction: " + description.getRequiredTransaction());
|
|
||||||
|
|
||||||
Object retVal = invocation.proceed();
|
|
||||||
|
|
||||||
if (logger.isDebugEnabled())
|
|
||||||
logger.debug("End transaction: " + description.getRequiredTransaction());
|
|
||||||
|
|
||||||
return retVal;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
// execute call within transaction
|
|
||||||
Object retVal;
|
|
||||||
if (description.getRequiredTransaction() == RequiredTransaction.required)
|
|
||||||
{
|
|
||||||
retVal = TransactionUtil.executeInUserTransaction(transactionService, work);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
retVal = TransactionUtil.executeInNonPropagatingUserTransaction(transactionService, work);
|
|
||||||
}
|
|
||||||
return retVal;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
@@ -47,6 +47,7 @@ import org.alfresco.web.scripts.FormatRegistry;
|
|||||||
import org.alfresco.web.scripts.WebScriptException;
|
import org.alfresco.web.scripts.WebScriptException;
|
||||||
import org.alfresco.web.scripts.WebScriptRequest;
|
import org.alfresco.web.scripts.WebScriptRequest;
|
||||||
import org.alfresco.web.scripts.WebScriptResponse;
|
import org.alfresco.web.scripts.WebScriptResponse;
|
||||||
|
import org.alfresco.web.scripts.WebScriptServletResponse;
|
||||||
import org.apache.commons.logging.Log;
|
import org.apache.commons.logging.Log;
|
||||||
import org.apache.commons.logging.LogFactory;
|
import org.apache.commons.logging.LogFactory;
|
||||||
import org.dom4j.Attribute;
|
import org.dom4j.Attribute;
|
||||||
@@ -164,7 +165,13 @@ public class SearchProxy extends AbstractWebScript implements InitializingBean
|
|||||||
logger.debug("Mapping engine '" + engine + "' (mimetype '" + mimetype + "') to url '" + engineUrl + "'");
|
logger.debug("Mapping engine '" + engine + "' (mimetype '" + mimetype + "') to url '" + engineUrl + "'");
|
||||||
|
|
||||||
// issue request against search engine
|
// issue request against search engine
|
||||||
SearchEngineHttpProxy proxy = new SearchEngineHttpProxy(req.getServicePath() + "/" + req.getContextPath(), engine, engineUrl, res);
|
// NOTE: This web script must be executed in a HTTP servlet environment
|
||||||
|
if (!(res instanceof WebScriptServletResponse))
|
||||||
|
{
|
||||||
|
throw new WebScriptException("Search Proxy must be executed in HTTP Servlet environment");
|
||||||
|
}
|
||||||
|
HttpServletResponse servletRes = ((WebScriptServletResponse)req).getHttpServletResponse();
|
||||||
|
SearchEngineHttpProxy proxy = new SearchEngineHttpProxy(req.getServicePath() + "/" + req.getContextPath(), engine, engineUrl, servletRes);
|
||||||
proxy.service();
|
proxy.service();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -0,0 +1,158 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2005-2007 Alfresco Software Limited.
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License
|
||||||
|
* as published by the Free Software Foundation; either version 2
|
||||||
|
* of the License, or (at your option) any later version.
|
||||||
|
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
|
|
||||||
|
* As a special exception to the terms and conditions of version 2.0 of
|
||||||
|
* the GPL, you may redistribute this Program in connection with Free/Libre
|
||||||
|
* and Open Source Software ("FLOSS") applications as described in Alfresco's
|
||||||
|
* FLOSS exception. You should have recieved a copy of the text describing
|
||||||
|
* the FLOSS exception, and it is also available here:
|
||||||
|
* http://www.alfresco.com/legal/licensing"
|
||||||
|
*/
|
||||||
|
package org.alfresco.web.scripts.portlet;
|
||||||
|
|
||||||
|
import javax.portlet.PortletSession;
|
||||||
|
import javax.portlet.RenderRequest;
|
||||||
|
import javax.portlet.RenderResponse;
|
||||||
|
|
||||||
|
import org.alfresco.repo.security.authentication.AuthenticationUtil;
|
||||||
|
import org.alfresco.service.cmr.repository.NodeRef;
|
||||||
|
import org.alfresco.service.cmr.security.AuthenticationService;
|
||||||
|
import org.alfresco.web.app.servlet.AuthenticationHelper;
|
||||||
|
import org.alfresco.web.bean.repository.User;
|
||||||
|
import org.alfresco.web.scripts.WebScriptContext;
|
||||||
|
import org.alfresco.web.scripts.WebScriptDescription.RequiredAuthentication;
|
||||||
|
import org.apache.commons.logging.Log;
|
||||||
|
import org.apache.commons.logging.LogFactory;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Portlet authenticator which synchronizes with the Alfresco Web Client authentication
|
||||||
|
*
|
||||||
|
* @author davidc
|
||||||
|
*/
|
||||||
|
public class WebClientPortletAuthenticator implements WebScriptPortletAuthenticator
|
||||||
|
{
|
||||||
|
// Logger
|
||||||
|
private static final Log logger = LogFactory.getLog(WebClientPortletAuthenticator.class);
|
||||||
|
|
||||||
|
// dependencies
|
||||||
|
private AuthenticationService authenticationService;
|
||||||
|
private WebScriptContext scriptContext;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param authenticationService
|
||||||
|
*/
|
||||||
|
public void setAuthenticationService(AuthenticationService authenticationService)
|
||||||
|
{
|
||||||
|
this.authenticationService = authenticationService;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param scriptContext
|
||||||
|
*/
|
||||||
|
public void setScriptContext(WebScriptContext scriptContext)
|
||||||
|
{
|
||||||
|
this.scriptContext = scriptContext;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.portlet.WebScriptPortletAuthenticator#authenticate(org.alfresco.web.scripts.WebScriptDescription.RequiredAuthentication, boolean, javax.portlet.RenderRequest, javax.portlet.RenderResponse)
|
||||||
|
*/
|
||||||
|
public void authenticate(RequiredAuthentication required, boolean isGuest, RenderRequest req, RenderResponse res)
|
||||||
|
{
|
||||||
|
PortletSession session = req.getPortletSession();
|
||||||
|
String portalUser = req.getRemoteUser();
|
||||||
|
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
{
|
||||||
|
logger.debug("JSR-168 Remote user: " + portalUser);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (isGuest || portalUser == null)
|
||||||
|
{
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
logger.debug("Authenticating as Guest");
|
||||||
|
|
||||||
|
// authenticate as guest
|
||||||
|
AuthenticationUtil.setCurrentUser(AuthenticationUtil.getGuestUserName());
|
||||||
|
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
logger.debug("Setting Web Client authentication context for guest");
|
||||||
|
|
||||||
|
createWebClientUser(session);
|
||||||
|
removeSessionInvalidated(session);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
logger.debug("Authenticating as user " + portalUser);
|
||||||
|
|
||||||
|
AuthenticationUtil.setCurrentUser(portalUser);
|
||||||
|
|
||||||
|
// determine if Web Client context needs to be updated
|
||||||
|
User user = getWebClientUser(session);
|
||||||
|
if (user == null || !portalUser.equals(user.getUserName()))
|
||||||
|
{
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
logger.debug("Setting Web Client authentication context for user " + portalUser);
|
||||||
|
|
||||||
|
createWebClientUser(session);
|
||||||
|
removeSessionInvalidated(session);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Helper. Remove Web Client session invalidated flag
|
||||||
|
*
|
||||||
|
* @param session
|
||||||
|
*/
|
||||||
|
private void removeSessionInvalidated(PortletSession session)
|
||||||
|
{
|
||||||
|
session.removeAttribute(AuthenticationHelper.SESSION_INVALIDATED, PortletSession.APPLICATION_SCOPE);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Helper. Create Web Client session user
|
||||||
|
*
|
||||||
|
* @param session
|
||||||
|
*/
|
||||||
|
private void createWebClientUser(PortletSession session)
|
||||||
|
{
|
||||||
|
NodeRef personRef = scriptContext.getPerson();
|
||||||
|
User user = new User(authenticationService.getCurrentUserName(), authenticationService.getCurrentTicket(), personRef);
|
||||||
|
NodeRef homeRef = scriptContext.getUserHome(personRef);
|
||||||
|
if (homeRef != null)
|
||||||
|
{
|
||||||
|
user.setHomeSpaceId(homeRef.getId());
|
||||||
|
}
|
||||||
|
session.setAttribute(AuthenticationHelper.AUTHENTICATION_USER, user, PortletSession.APPLICATION_SCOPE);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Helper. Get Web Client session user
|
||||||
|
*
|
||||||
|
* @param session
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
private User getWebClientUser(PortletSession session)
|
||||||
|
{
|
||||||
|
return (User)session.getAttribute(AuthenticationHelper.AUTHENTICATION_USER, PortletSession.APPLICATION_SCOPE);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@@ -0,0 +1,287 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2005-2007 Alfresco Software Limited.
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License
|
||||||
|
* as published by the Free Software Foundation; either version 2
|
||||||
|
* of the License, or (at your option) any later version.
|
||||||
|
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
|
|
||||||
|
* As a special exception to the terms and conditions of version 2.0 of
|
||||||
|
* the GPL, you may redistribute this Program in connection with Free/Libre
|
||||||
|
* and Open Source Software ("FLOSS") applications as described in Alfresco's
|
||||||
|
* FLOSS exception. You should have recieved a copy of the text describing
|
||||||
|
* the FLOSS exception, and it is also available here:
|
||||||
|
* http://www.alfresco.com/legal/licensing"
|
||||||
|
*/
|
||||||
|
package org.alfresco.web.scripts.portlet;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
|
import javax.portlet.ActionRequest;
|
||||||
|
import javax.portlet.ActionResponse;
|
||||||
|
import javax.portlet.Portlet;
|
||||||
|
import javax.portlet.PortletConfig;
|
||||||
|
import javax.portlet.PortletContext;
|
||||||
|
import javax.portlet.PortletException;
|
||||||
|
import javax.portlet.PortletMode;
|
||||||
|
import javax.portlet.PortletSecurityException;
|
||||||
|
import javax.portlet.RenderRequest;
|
||||||
|
import javax.portlet.RenderResponse;
|
||||||
|
import javax.portlet.WindowState;
|
||||||
|
|
||||||
|
import org.alfresco.service.transaction.TransactionService;
|
||||||
|
import org.alfresco.web.scripts.DeclarativeWebScriptRegistry;
|
||||||
|
import org.alfresco.web.scripts.WebScript;
|
||||||
|
import org.alfresco.web.scripts.WebScriptDescription;
|
||||||
|
import org.alfresco.web.scripts.WebScriptMatch;
|
||||||
|
import org.alfresco.web.scripts.WebScriptRequest;
|
||||||
|
import org.alfresco.web.scripts.WebScriptResponse;
|
||||||
|
import org.alfresco.web.scripts.WebScriptRuntime;
|
||||||
|
import org.alfresco.web.scripts.WebScriptDescription.RequiredAuthentication;
|
||||||
|
import org.apache.commons.logging.Log;
|
||||||
|
import org.apache.commons.logging.LogFactory;
|
||||||
|
import org.springframework.web.context.WebApplicationContext;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Generic JSR-168 Portlet for hosting an Alfresco Web Script as a Portlet.
|
||||||
|
*
|
||||||
|
* Accepts the following init-config:
|
||||||
|
*
|
||||||
|
* scriptUrl => the url of the web script to host e.g. /alfresco/service/mytasks
|
||||||
|
*
|
||||||
|
* @author davidc
|
||||||
|
*/
|
||||||
|
public class WebScriptPortlet implements Portlet
|
||||||
|
{
|
||||||
|
private static Log logger = LogFactory.getLog(WebScriptPortlet.class);
|
||||||
|
|
||||||
|
// Portlet initialisation
|
||||||
|
protected String initScriptUrl = null;
|
||||||
|
|
||||||
|
// Component Dependencies
|
||||||
|
protected DeclarativeWebScriptRegistry registry;
|
||||||
|
protected TransactionService transactionService;
|
||||||
|
protected WebScriptPortletAuthenticator authenticator;
|
||||||
|
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see javax.portlet.Portlet#init(javax.portlet.PortletConfig)
|
||||||
|
*/
|
||||||
|
public void init(PortletConfig config) throws PortletException
|
||||||
|
{
|
||||||
|
initScriptUrl = config.getInitParameter("scriptUrl");
|
||||||
|
PortletContext portletCtx = config.getPortletContext();
|
||||||
|
WebApplicationContext ctx = (WebApplicationContext)portletCtx.getAttribute(WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE);
|
||||||
|
registry = (DeclarativeWebScriptRegistry)ctx.getBean("webscripts.registry");
|
||||||
|
transactionService = (TransactionService)ctx.getBean("transactionComponent");
|
||||||
|
authenticator = (WebScriptPortletAuthenticator)ctx.getBean("webscripts.authenticator.jsr168");
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see javax.portlet.Portlet#processAction(javax.portlet.ActionRequest, javax.portlet.ActionResponse)
|
||||||
|
*/
|
||||||
|
public void processAction(ActionRequest req, ActionResponse res) throws PortletException, PortletSecurityException, IOException
|
||||||
|
{
|
||||||
|
Map<String, String[]> params = req.getParameterMap();
|
||||||
|
for (Map.Entry<String, String[]> param : params.entrySet())
|
||||||
|
{
|
||||||
|
String name = param.getKey();
|
||||||
|
if (name.equals("scriptUrl") || name.startsWith("arg."))
|
||||||
|
{
|
||||||
|
res.setRenderParameter(name, param.getValue());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see javax.portlet.Portlet#render(javax.portlet.RenderRequest, javax.portlet.RenderResponse)
|
||||||
|
*/
|
||||||
|
public void render(RenderRequest req, RenderResponse res) throws PortletException, PortletSecurityException, IOException
|
||||||
|
{
|
||||||
|
PortletMode portletMode = req.getPortletMode();
|
||||||
|
if (PortletMode.VIEW.equals(portletMode))
|
||||||
|
{
|
||||||
|
doView(req, res);
|
||||||
|
}
|
||||||
|
// else if (PortletMode.HELP.equals(portletMode))
|
||||||
|
// {
|
||||||
|
// doHelp(request, response);
|
||||||
|
// }
|
||||||
|
// else if (PortletMode.EDIT.equals(portletMode))
|
||||||
|
// {
|
||||||
|
// doEdit(request, response);
|
||||||
|
// }
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see javax.portlet.Portlet#destroy()
|
||||||
|
*/
|
||||||
|
public void destroy()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Render Web Script view
|
||||||
|
*
|
||||||
|
* @param req
|
||||||
|
* @param res
|
||||||
|
* @throws PortletException
|
||||||
|
* @throws PortletSecurityException
|
||||||
|
* @throws IOException
|
||||||
|
*/
|
||||||
|
protected void doView(RenderRequest req, RenderResponse res) throws PortletException, PortletSecurityException, IOException
|
||||||
|
{
|
||||||
|
//
|
||||||
|
// Establish Web Script URL
|
||||||
|
//
|
||||||
|
|
||||||
|
String scriptUrl = req.getParameter("scriptUrl");
|
||||||
|
if (scriptUrl != null)
|
||||||
|
{
|
||||||
|
// build web script url from render request
|
||||||
|
String scriptUrlArgs = "";
|
||||||
|
Map<String, String[]> params = req.getParameterMap();
|
||||||
|
for (Map.Entry<String, String[]> param : params.entrySet())
|
||||||
|
{
|
||||||
|
String name = param.getKey();
|
||||||
|
if (name.startsWith("arg."))
|
||||||
|
{
|
||||||
|
String argName = name.substring("arg.".length());
|
||||||
|
for (String argValue : param.getValue())
|
||||||
|
{
|
||||||
|
scriptUrlArgs += (scriptUrlArgs.length() == 0) ? "" : "&";
|
||||||
|
scriptUrlArgs += argName + "=" + argValue;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
scriptUrl += "?" + scriptUrlArgs;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// retrieve initial scriptUrl as configured by Portlet
|
||||||
|
scriptUrl = initScriptUrl;
|
||||||
|
if (scriptUrl == null)
|
||||||
|
{
|
||||||
|
throw new PortletException("Initial Web script URL has not been specified.");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// Execute Web Script
|
||||||
|
//
|
||||||
|
|
||||||
|
if (logger.isDebugEnabled())
|
||||||
|
logger.debug("Processing portal render request " + req.getScheme() + "://" + req.getServerName() + ":" + req.getServerPort() + "/" + req.getContextPath() + " (scriptUrl=" + scriptUrl + ")");
|
||||||
|
|
||||||
|
WebScriptRuntime runtime = new WebScriptPortalRuntime(req, res, scriptUrl);
|
||||||
|
runtime.executeScript();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* JSR-168 Web Script Runtime
|
||||||
|
*
|
||||||
|
* @author davidc
|
||||||
|
*/
|
||||||
|
private class WebScriptPortalRuntime extends WebScriptRuntime
|
||||||
|
{
|
||||||
|
private RenderRequest req;
|
||||||
|
private RenderResponse res;
|
||||||
|
private String[] requestUrlParts;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Construct
|
||||||
|
* @param req
|
||||||
|
* @param res
|
||||||
|
* @param requestUrl
|
||||||
|
*/
|
||||||
|
public WebScriptPortalRuntime(RenderRequest req, RenderResponse res, String requestUrl)
|
||||||
|
{
|
||||||
|
super(registry, transactionService);
|
||||||
|
this.req = req;
|
||||||
|
this.res = res;
|
||||||
|
this.requestUrlParts = WebScriptPortletRequest.getScriptUrlParts(requestUrl);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRuntime#getScriptMethod()
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
protected String getScriptMethod()
|
||||||
|
{
|
||||||
|
return "get";
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRuntime#getScriptUrl()
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
protected String getScriptUrl()
|
||||||
|
{
|
||||||
|
return requestUrlParts[2];
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRuntime#createRequest(org.alfresco.web.scripts.WebScriptMatch)
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
protected WebScriptRequest createRequest(WebScriptMatch match)
|
||||||
|
{
|
||||||
|
return new WebScriptPortletRequest(req, requestUrlParts, match);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRuntime#createResponse()
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
protected WebScriptResponse createResponse()
|
||||||
|
{
|
||||||
|
return new WebScriptPortletResponse(res);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRuntime#authenticate(org.alfresco.web.scripts.WebScriptDescription.RequiredAuthentication, boolean)
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
protected void authenticate(RequiredAuthentication required, boolean isGuest)
|
||||||
|
{
|
||||||
|
authenticator.authenticate(required, isGuest, req, res);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRuntime#preExecute(org.alfresco.web.scripts.WebScriptRequest, org.alfresco.web.scripts.WebScriptResponse)
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
protected boolean preExecute(WebScriptRequest scriptReq, WebScriptResponse scriptRes)
|
||||||
|
{
|
||||||
|
// Set Portlet title based on Web Script
|
||||||
|
WebScript script = scriptReq.getServiceMatch().getWebScript();
|
||||||
|
WebScriptDescription desc = script.getDescription();
|
||||||
|
res.setTitle(desc.getShortName());
|
||||||
|
|
||||||
|
// Note: Do not render script if portlet window is minimized
|
||||||
|
return !WindowState.MINIMIZED.equals(req.getWindowState());
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRuntime#postExecute(org.alfresco.web.scripts.WebScriptRequest, org.alfresco.web.scripts.WebScriptResponse)
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
protected void postExecute(WebScriptRequest scriptReq, WebScriptResponse scriptRes)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@@ -0,0 +1,51 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2005-2007 Alfresco Software Limited.
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License
|
||||||
|
* as published by the Free Software Foundation; either version 2
|
||||||
|
* of the License, or (at your option) any later version.
|
||||||
|
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
|
|
||||||
|
* As a special exception to the terms and conditions of version 2.0 of
|
||||||
|
* the GPL, you may redistribute this Program in connection with Free/Libre
|
||||||
|
* and Open Source Software ("FLOSS") applications as described in Alfresco's
|
||||||
|
* FLOSS exception. You should have recieved a copy of the text describing
|
||||||
|
* the FLOSS exception, and it is also available here:
|
||||||
|
* http://www.alfresco.com/legal/licensing"
|
||||||
|
*/
|
||||||
|
package org.alfresco.web.scripts.portlet;
|
||||||
|
|
||||||
|
import javax.portlet.RenderRequest;
|
||||||
|
import javax.portlet.RenderResponse;
|
||||||
|
|
||||||
|
import org.alfresco.web.scripts.WebScriptDescription.RequiredAuthentication;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Web Script Authenticator for the JSR-168 environment
|
||||||
|
*
|
||||||
|
* @author davidc
|
||||||
|
*/
|
||||||
|
public interface WebScriptPortletAuthenticator
|
||||||
|
{
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Authenticate Web Script execution
|
||||||
|
*
|
||||||
|
* @param required required level of authentication
|
||||||
|
* @param isGuest is Guest accessing the web script
|
||||||
|
* @param req portlet render request
|
||||||
|
* @param res portlet render response
|
||||||
|
*/
|
||||||
|
public void authenticate(RequiredAuthentication required, boolean isGuest, RenderRequest req, RenderResponse res);
|
||||||
|
|
||||||
|
}
|
@@ -0,0 +1,265 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2005-2007 Alfresco Software Limited.
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License
|
||||||
|
* as published by the Free Software Foundation; either version 2
|
||||||
|
* of the License, or (at your option) any later version.
|
||||||
|
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
|
|
||||||
|
* As a special exception to the terms and conditions of version 2.0 of
|
||||||
|
* the GPL, you may redistribute this Program in connection with Free/Libre
|
||||||
|
* and Open Source Software ("FLOSS") applications as described in Alfresco's
|
||||||
|
* FLOSS exception. You should have recieved a copy of the text describing
|
||||||
|
* the FLOSS exception, and it is also available here:
|
||||||
|
* http://www.alfresco.com/legal/licensing"
|
||||||
|
*/
|
||||||
|
package org.alfresco.web.scripts.portlet;
|
||||||
|
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
|
import javax.portlet.PortletRequest;
|
||||||
|
|
||||||
|
import org.alfresco.web.scripts.WebScriptMatch;
|
||||||
|
import org.alfresco.web.scripts.WebScriptRequest;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* JSR-168 Web Script Request
|
||||||
|
*
|
||||||
|
* @author davidc
|
||||||
|
*/
|
||||||
|
public class WebScriptPortletRequest implements WebScriptRequest
|
||||||
|
{
|
||||||
|
/** Portlet Request */
|
||||||
|
private PortletRequest req;
|
||||||
|
|
||||||
|
/** Script Url components */
|
||||||
|
private String contextPath;
|
||||||
|
private String servletPath;
|
||||||
|
private String pathInfo;
|
||||||
|
private String queryString;
|
||||||
|
private Map<String, String> queryArgs;
|
||||||
|
|
||||||
|
/** Service bound to this request */
|
||||||
|
private WebScriptMatch serviceMatch;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Splits a portlet scriptUrl into its component parts
|
||||||
|
*
|
||||||
|
* @param scriptUrl url e.g. /alfresco/service/mytasks?f=1
|
||||||
|
* @return url parts [0] = context (e.g. alfresco), [1] = servlet (e.g. service), [2] = script (e.g. mytasks), [3] = args (e.g. f=1)
|
||||||
|
*/
|
||||||
|
public static String[] getScriptUrlParts(String scriptUrl)
|
||||||
|
{
|
||||||
|
String[] urlParts = new String[4];
|
||||||
|
String path;
|
||||||
|
String queryString;
|
||||||
|
|
||||||
|
int argsIndex = scriptUrl.indexOf("?");
|
||||||
|
if (argsIndex != -1)
|
||||||
|
{
|
||||||
|
path = scriptUrl.substring(0, argsIndex);
|
||||||
|
queryString = scriptUrl.substring(argsIndex + 1);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
path = scriptUrl;
|
||||||
|
queryString = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
String[] pathSegments = path.split("/");
|
||||||
|
String pathInfo = "";
|
||||||
|
for (int i = 3; i < pathSegments.length; i++)
|
||||||
|
{
|
||||||
|
pathInfo += "/" + pathSegments[i];
|
||||||
|
}
|
||||||
|
|
||||||
|
urlParts[0] = "/" + pathSegments[1]; // context path
|
||||||
|
urlParts[1] = "/" + pathSegments[2]; // servlet path
|
||||||
|
urlParts[2] = pathInfo; // path info
|
||||||
|
urlParts[3] = queryString; // query string
|
||||||
|
|
||||||
|
return urlParts;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Construct
|
||||||
|
*
|
||||||
|
* @param req
|
||||||
|
* @param scriptUrl
|
||||||
|
* @param serviceMatch
|
||||||
|
*/
|
||||||
|
WebScriptPortletRequest(PortletRequest req, String scriptUrl, WebScriptMatch serviceMatch)
|
||||||
|
{
|
||||||
|
this(req, getScriptUrlParts(scriptUrl), serviceMatch);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Construct
|
||||||
|
*
|
||||||
|
* @param req
|
||||||
|
* 'param scriptUrlParts
|
||||||
|
* @param serviceMatch
|
||||||
|
*/
|
||||||
|
WebScriptPortletRequest(PortletRequest req, String[] scriptUrlParts, WebScriptMatch serviceMatch)
|
||||||
|
{
|
||||||
|
this.req = req;
|
||||||
|
this.contextPath = scriptUrlParts[0];
|
||||||
|
this.servletPath = scriptUrlParts[1];
|
||||||
|
this.pathInfo = scriptUrlParts[2];
|
||||||
|
this.queryString = scriptUrlParts[3];
|
||||||
|
this.queryArgs = new HashMap<String, String>();
|
||||||
|
if (this.queryString != null)
|
||||||
|
{
|
||||||
|
String[] args = this.queryString.split("&");
|
||||||
|
for (String arg : args)
|
||||||
|
{
|
||||||
|
String[] parts = arg.split("=");
|
||||||
|
// TODO: Handle multi-value parameters
|
||||||
|
this.queryArgs.put(parts[0], parts.length == 2 ? parts[1] : "");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
this.serviceMatch = serviceMatch;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the Portlet Request
|
||||||
|
*
|
||||||
|
* @return Portlet Request
|
||||||
|
*/
|
||||||
|
public PortletRequest getPortletRequest()
|
||||||
|
{
|
||||||
|
return req;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRequest#getServiceMatch()
|
||||||
|
*/
|
||||||
|
public WebScriptMatch getServiceMatch()
|
||||||
|
{
|
||||||
|
return serviceMatch;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRequest#getServerPath()
|
||||||
|
*/
|
||||||
|
public String getServerPath()
|
||||||
|
{
|
||||||
|
return req.getScheme() + "://" + req.getServerName() + ":" + req.getServerPort();
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRequest#getContextPath()
|
||||||
|
*/
|
||||||
|
public String getContextPath()
|
||||||
|
{
|
||||||
|
return contextPath;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRequest#getServiceContextPath()
|
||||||
|
*/
|
||||||
|
public String getServiceContextPath()
|
||||||
|
{
|
||||||
|
return getContextPath() + servletPath;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRequest#getServicePath()
|
||||||
|
*/
|
||||||
|
public String getServicePath()
|
||||||
|
{
|
||||||
|
return getServiceContextPath() + pathInfo;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRequest#getURL()
|
||||||
|
*/
|
||||||
|
public String getURL()
|
||||||
|
{
|
||||||
|
return getServicePath() + (queryString != null ? "?" + queryString : "");
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRequest#getQueryString()
|
||||||
|
*/
|
||||||
|
public String getQueryString()
|
||||||
|
{
|
||||||
|
return queryString;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRequest#getParameterNames()
|
||||||
|
*/
|
||||||
|
public String[] getParameterNames()
|
||||||
|
{
|
||||||
|
Set<String> keys = queryArgs.keySet();
|
||||||
|
String[] names = new String[keys.size()];
|
||||||
|
keys.toArray(names);
|
||||||
|
return names;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRequest#getParameter(java.lang.String)
|
||||||
|
*/
|
||||||
|
public String getParameter(String name)
|
||||||
|
{
|
||||||
|
return queryArgs.get(name);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRequest#getExtensionPath()
|
||||||
|
*/
|
||||||
|
public String getExtensionPath()
|
||||||
|
{
|
||||||
|
String servicePath = serviceMatch.getPath();
|
||||||
|
String extensionPath = pathInfo;
|
||||||
|
int extIdx = extensionPath.indexOf(servicePath);
|
||||||
|
if (extIdx != -1)
|
||||||
|
{
|
||||||
|
int extLength = (servicePath.endsWith("/") ? servicePath.length() : servicePath.length() + 1);
|
||||||
|
extensionPath = extensionPath.substring(extIdx + extLength);
|
||||||
|
}
|
||||||
|
return extensionPath;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRequest#isGuest()
|
||||||
|
*/
|
||||||
|
public boolean isGuest()
|
||||||
|
{
|
||||||
|
return Boolean.valueOf(queryArgs.get("guest"));
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRequest#getFormat()
|
||||||
|
*/
|
||||||
|
public String getFormat()
|
||||||
|
{
|
||||||
|
String format = queryArgs.get("format");
|
||||||
|
return (format == null || format.length() == 0) ? "" : format;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptRequest#getAgent()
|
||||||
|
*/
|
||||||
|
public String getAgent()
|
||||||
|
{
|
||||||
|
// NOTE: rely on default agent mappings
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@@ -0,0 +1,109 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2005-2007 Alfresco Software Limited.
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License
|
||||||
|
* as published by the Free Software Foundation; either version 2
|
||||||
|
* of the License, or (at your option) any later version.
|
||||||
|
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
|
|
||||||
|
* As a special exception to the terms and conditions of version 2.0 of
|
||||||
|
* the GPL, you may redistribute this Program in connection with Free/Libre
|
||||||
|
* and Open Source Software ("FLOSS") applications as described in Alfresco's
|
||||||
|
* FLOSS exception. You should have recieved a copy of the text describing
|
||||||
|
* the FLOSS exception, and it is also available here:
|
||||||
|
* http://www.alfresco.com/legal/licensing"
|
||||||
|
*/
|
||||||
|
package org.alfresco.web.scripts.portlet;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.io.OutputStream;
|
||||||
|
import java.io.Writer;
|
||||||
|
|
||||||
|
import javax.portlet.PortletURL;
|
||||||
|
import javax.portlet.RenderResponse;
|
||||||
|
|
||||||
|
import org.alfresco.web.scripts.WebScriptRequest;
|
||||||
|
import org.alfresco.web.scripts.WebScriptResponse;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* JSR-168 Web Script Response
|
||||||
|
*
|
||||||
|
* @author davidc
|
||||||
|
*/
|
||||||
|
public class WebScriptPortletResponse implements WebScriptResponse
|
||||||
|
{
|
||||||
|
/** Portlet response */
|
||||||
|
private RenderResponse res;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Construct
|
||||||
|
*
|
||||||
|
* @param res
|
||||||
|
*/
|
||||||
|
WebScriptPortletResponse(RenderResponse res)
|
||||||
|
{
|
||||||
|
this.res = res;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the Portlet Render Response
|
||||||
|
*
|
||||||
|
* @return render response
|
||||||
|
*/
|
||||||
|
public RenderResponse getRenderResponse()
|
||||||
|
{
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptResponse#setContentType(java.lang.String)
|
||||||
|
*/
|
||||||
|
public void setContentType(String contentType)
|
||||||
|
{
|
||||||
|
res.setContentType(contentType);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptResponse#getWriter()
|
||||||
|
*/
|
||||||
|
public Writer getWriter() throws IOException
|
||||||
|
{
|
||||||
|
return res.getWriter();
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptResponse#getOutputStream()
|
||||||
|
*/
|
||||||
|
public OutputStream getOutputStream() throws IOException
|
||||||
|
{
|
||||||
|
return res.getPortletOutputStream();
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.alfresco.web.scripts.WebScriptResponse#encodeScriptUrl(java.lang.String)
|
||||||
|
*/
|
||||||
|
public String encodeScriptUrl(String url)
|
||||||
|
{
|
||||||
|
WebScriptRequest req = new WebScriptPortletRequest(null, url, null);
|
||||||
|
PortletURL portletUrl = res.createActionURL();
|
||||||
|
portletUrl.setParameter("scriptUrl", req.getServicePath());
|
||||||
|
String[] parameterNames = req.getParameterNames();
|
||||||
|
for (String parameterName : parameterNames)
|
||||||
|
{
|
||||||
|
portletUrl.setParameter("arg." + parameterName, req.getParameter(parameterName));
|
||||||
|
}
|
||||||
|
return portletUrl.toString();
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@@ -21,4 +21,68 @@
|
|||||||
<short-title>alfresco-client-portlet</short-title>
|
<short-title>alfresco-client-portlet</short-title>
|
||||||
</portlet-info>
|
</portlet-info>
|
||||||
</portlet>
|
</portlet>
|
||||||
|
|
||||||
|
<portlet>
|
||||||
|
<description>My Tasks</description>
|
||||||
|
<portlet-name>AlfrescoMyTasks</portlet-name>
|
||||||
|
<portlet-class>org.alfresco.web.scripts.portlet.WebScriptPortlet</portlet-class>
|
||||||
|
|
||||||
|
<init-param>
|
||||||
|
<name>scriptUrl</name>
|
||||||
|
<value>/alfresco/service/mytasks</value>
|
||||||
|
</init-param>
|
||||||
|
|
||||||
|
<supports>
|
||||||
|
<mime-type>text/html</mime-type>
|
||||||
|
<portlet-mode>VIEW</portlet-mode>
|
||||||
|
</supports>
|
||||||
|
|
||||||
|
<portlet-info>
|
||||||
|
<title>My Tasks</title>
|
||||||
|
<short-title>My Tasks</short-title>
|
||||||
|
</portlet-info>
|
||||||
|
</portlet>
|
||||||
|
|
||||||
|
<portlet>
|
||||||
|
<description>Document List</description>
|
||||||
|
<portlet-name>AlfrescoDocList</portlet-name>
|
||||||
|
<portlet-class>org.alfresco.web.scripts.portlet.WebScriptPortlet</portlet-class>
|
||||||
|
|
||||||
|
<init-param>
|
||||||
|
<name>scriptUrl</name>
|
||||||
|
<value>/alfresco/service/doclist?p=/Company Home/Guest Home</value>
|
||||||
|
</init-param>
|
||||||
|
|
||||||
|
<supports>
|
||||||
|
<mime-type>text/html</mime-type>
|
||||||
|
<portlet-mode>VIEW</portlet-mode>
|
||||||
|
</supports>
|
||||||
|
|
||||||
|
<portlet-info>
|
||||||
|
<title>Document List</title>
|
||||||
|
<short-title>Document List</short-title>
|
||||||
|
</portlet-info>
|
||||||
|
</portlet>
|
||||||
|
|
||||||
|
<portlet>
|
||||||
|
<description>My Web Forms</description>
|
||||||
|
<portlet-name>AlfrescoMyWebForms</portlet-name>
|
||||||
|
<portlet-class>org.alfresco.web.scripts.portlet.WebScriptPortlet</portlet-class>
|
||||||
|
|
||||||
|
<init-param>
|
||||||
|
<name>scriptUrl</name>
|
||||||
|
<value>/alfresco/service/mywebforms</value>
|
||||||
|
</init-param>
|
||||||
|
|
||||||
|
<supports>
|
||||||
|
<mime-type>text/html</mime-type>
|
||||||
|
<portlet-mode>VIEW</portlet-mode>
|
||||||
|
</supports>
|
||||||
|
|
||||||
|
<portlet-info>
|
||||||
|
<title>My Web Forms</title>
|
||||||
|
<short-title>My Web Forms</short-title>
|
||||||
|
</portlet-info>
|
||||||
|
</portlet>
|
||||||
|
|
||||||
</portlet-app>
|
</portlet-app>
|
||||||
|
@@ -250,6 +250,10 @@
|
|||||||
<servlet>
|
<servlet>
|
||||||
<servlet-name>apiServlet</servlet-name>
|
<servlet-name>apiServlet</servlet-name>
|
||||||
<servlet-class>org.alfresco.web.scripts.WebScriptServlet</servlet-class>
|
<servlet-class>org.alfresco.web.scripts.WebScriptServlet</servlet-class>
|
||||||
|
<init-param>
|
||||||
|
<param-name>authenticator</param-name>
|
||||||
|
<param-value>webscripts.authenticator.webclient</param-value>
|
||||||
|
</init-param>
|
||||||
</servlet>
|
</servlet>
|
||||||
|
|
||||||
<servlet>
|
<servlet>
|
||||||
|
Reference in New Issue
Block a user