Move environment preparations to new class

This commit is contained in:
René Pfeuffer
2019-03-27 10:57:09 +01:00
parent b65e84249d
commit daaa50f08c
2 changed files with 104 additions and 105 deletions

View File

@@ -34,7 +34,6 @@
package sonia.scm.web; package sonia.scm.web;
import com.google.common.base.Stopwatch; import com.google.common.base.Stopwatch;
import com.google.common.base.Strings;
import com.google.inject.Inject; import com.google.inject.Inject;
import com.google.inject.Singleton; import com.google.inject.Singleton;
import org.slf4j.Logger; import org.slf4j.Logger;
@@ -42,16 +41,12 @@ import org.slf4j.LoggerFactory;
import sonia.scm.SCMContext; import sonia.scm.SCMContext;
import sonia.scm.config.ScmConfiguration; import sonia.scm.config.ScmConfiguration;
import sonia.scm.repository.HgConfig; import sonia.scm.repository.HgConfig;
import sonia.scm.repository.HgEnvironment;
import sonia.scm.repository.HgHookManager;
import sonia.scm.repository.HgPythonScript; import sonia.scm.repository.HgPythonScript;
import sonia.scm.repository.HgRepositoryHandler; import sonia.scm.repository.HgRepositoryHandler;
import sonia.scm.repository.Repository; import sonia.scm.repository.Repository;
import sonia.scm.repository.RepositoryRequestListenerUtil; import sonia.scm.repository.RepositoryRequestListenerUtil;
import sonia.scm.repository.spi.ScmProviderHttpServlet; import sonia.scm.repository.spi.ScmProviderHttpServlet;
import sonia.scm.security.CipherUtil;
import sonia.scm.util.AssertUtil; import sonia.scm.util.AssertUtil;
import sonia.scm.util.HttpUtil;
import sonia.scm.web.cgi.CGIExecutor; import sonia.scm.web.cgi.CGIExecutor;
import sonia.scm.web.cgi.CGIExecutorFactory; import sonia.scm.web.cgi.CGIExecutorFactory;
import sonia.scm.web.cgi.EnvList; import sonia.scm.web.cgi.EnvList;
@@ -62,14 +57,12 @@ import java.io.File;
import java.io.IOException; import java.io.IOException;
import java.util.Enumeration; import java.util.Enumeration;
import java.util.Map;
import javax.servlet.ServletException; import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet; 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 javax.servlet.http.HttpSession; import javax.servlet.http.HttpSession;
import java.util.Base64;
/** /**
* *
@@ -79,25 +72,9 @@ import java.util.Base64;
public class HgCGIServlet extends HttpServlet implements ScmProviderHttpServlet public class HgCGIServlet extends HttpServlet implements ScmProviderHttpServlet
{ {
private static final String ENV_PYTHON_HTTPS_VERIFY = "PYTHONHTTPSVERIFY";
/** Field description */
public static final String ENV_REPOSITORY_NAME = "REPO_NAME";
/** Field description */
public static final String ENV_REPOSITORY_PATH = "SCM_REPOSITORY_PATH";
/** Field description */
public static final String ENV_REPOSITORY_ID = "SCM_REPOSITORY_ID";
private static final String ENV_HTTP_POST_ARGS = "SCM_HTTP_POST_ARGS";
/** Field description */ /** Field description */
public static final String ENV_SESSION_PREFIX = "SCM_"; public static final String ENV_SESSION_PREFIX = "SCM_";
/** Field description */
private static final String SCM_CREDENTIALS = "SCM_CREDENTIALS";
/** Field description */ /** Field description */
private static final long serialVersionUID = -3492811300905099810L; private static final long serialVersionUID = -3492811300905099810L;
@@ -107,30 +84,18 @@ public class HgCGIServlet extends HttpServlet implements ScmProviderHttpServlet
//~--- constructors --------------------------------------------------------- //~--- constructors ---------------------------------------------------------
/**
* Constructs ...
*
*
*
*
*
* @param cgiExecutorFactory
* @param configuration
* @param handler
* @param hookManager
* @param requestListenerUtil
*/
@Inject @Inject
public HgCGIServlet(CGIExecutorFactory cgiExecutorFactory, public HgCGIServlet(CGIExecutorFactory cgiExecutorFactory,
ScmConfiguration configuration, ScmConfiguration configuration,
HgRepositoryHandler handler, HgHookManager hookManager, HgRepositoryHandler handler,
RepositoryRequestListenerUtil requestListenerUtil) RepositoryRequestListenerUtil requestListenerUtil,
HgRepositoryEnvironmentBuilder hgRepositoryEnvironmentBuilder)
{ {
this.cgiExecutorFactory = cgiExecutorFactory; this.cgiExecutorFactory = cgiExecutorFactory;
this.configuration = configuration; this.configuration = configuration;
this.handler = handler; this.handler = handler;
this.hookManager = hookManager;
this.requestListenerUtil = requestListenerUtil; this.requestListenerUtil = requestListenerUtil;
this.hgRepositoryEnvironmentBuilder = hgRepositoryEnvironmentBuilder;
this.exceptionHandler = new HgCGIExceptionHandler(); this.exceptionHandler = new HgCGIExceptionHandler();
this.command = HgPythonScript.HGWEB.getFile(SCMContext.getContext()); this.command = HgPythonScript.HGWEB.getFile(SCMContext.getContext());
} }
@@ -163,40 +128,6 @@ public class HgCGIServlet extends HttpServlet implements ScmProviderHttpServlet
} }
} }
/**
* Method description
*
*
* @param env
* @param request
*/
private void addCredentials(EnvList env, HttpServletRequest request)
{
String authorization = request.getHeader(HttpUtil.HEADER_AUTHORIZATION);
if (!Strings.isNullOrEmpty(authorization))
{
if (authorization.startsWith(HttpUtil.AUTHORIZATION_SCHEME_BASIC))
{
String encodedUserInfo =
authorization.substring(
HttpUtil.AUTHORIZATION_SCHEME_BASIC.length()).trim();
// TODO check encoding of user-agent ?
String userInfo = new String(Base64.getDecoder().decode(encodedUserInfo));
env.set(SCM_CREDENTIALS, CipherUtil.getInstance().encode(userInfo));
}
else
{
logger.warn("unknow authentication scheme used");
}
}
else
{
logger.trace("no authorization header found");
}
}
/** /**
* Method description * Method description
* *
@@ -262,7 +193,6 @@ public class HgCGIServlet extends HttpServlet implements ScmProviderHttpServlet
HttpServletResponse response, Repository repository) HttpServletResponse response, Repository repository)
throws IOException, ServletException throws IOException, ServletException
{ {
File directory = handler.getDirectory(repository.getId());
CGIExecutor executor = cgiExecutorFactory.createExecutor(configuration, CGIExecutor executor = cgiExecutorFactory.createExecutor(configuration,
getServletContext(), request, response); getServletContext(), request, response);
@@ -271,33 +201,7 @@ public class HgCGIServlet extends HttpServlet implements ScmProviderHttpServlet
executor.setExceptionHandler(exceptionHandler); executor.setExceptionHandler(exceptionHandler);
executor.setStatusCodeHandler(exceptionHandler); executor.setStatusCodeHandler(exceptionHandler);
executor.setContentLengthWorkaround(true); executor.setContentLengthWorkaround(true);
executor.getEnvironment().set(ENV_REPOSITORY_NAME, repository.getNamespace() + "/" + repository.getName()); hgRepositoryEnvironmentBuilder.buildFor(repository, request, executor.getEnvironment());
executor.getEnvironment().set(ENV_REPOSITORY_ID, repository.getId());
executor.getEnvironment().set(ENV_REPOSITORY_PATH,
directory.getAbsolutePath());
// add hook environment
Map<String, String> environment = executor.getEnvironment().asMutableMap();
if (handler.getConfig().isDisableHookSSLValidation()) {
// disable ssl validation
// Issue 959: https://goo.gl/zH5eY8
environment.put(ENV_PYTHON_HTTPS_VERIFY, "0");
}
// enable experimental httppostargs protocol of mercurial
// Issue 970: https://goo.gl/poascp
environment.put(ENV_HTTP_POST_ARGS, String.valueOf(handler.getConfig().isEnableHttpPostArgs()));
//J-
HgEnvironment.prepareEnvironment(
environment,
handler,
hookManager,
request
);
//J+
addCredentials(executor.getEnvironment(), request);
// unused ??? // unused ???
HttpSession session = request.getSession(false); HttpSession session = request.getSession(false);
@@ -358,9 +262,8 @@ public class HgCGIServlet extends HttpServlet implements ScmProviderHttpServlet
/** Field description */ /** Field description */
private final HgRepositoryHandler handler; private final HgRepositoryHandler handler;
/** Field description */
private final HgHookManager hookManager;
/** Field description */ /** Field description */
private final RepositoryRequestListenerUtil requestListenerUtil; private final RepositoryRequestListenerUtil requestListenerUtil;
private final HgRepositoryEnvironmentBuilder hgRepositoryEnvironmentBuilder;
} }

View File

@@ -0,0 +1,96 @@
package sonia.scm.web;
import com.google.common.base.Strings;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import sonia.scm.repository.HgEnvironment;
import sonia.scm.repository.HgHookManager;
import sonia.scm.repository.HgRepositoryHandler;
import sonia.scm.repository.Repository;
import sonia.scm.security.CipherUtil;
import sonia.scm.util.HttpUtil;
import sonia.scm.web.cgi.EnvList;
import javax.inject.Inject;
import javax.servlet.http.HttpServletRequest;
import java.io.File;
import java.util.Base64;
import java.util.Map;
public class HgRepositoryEnvironmentBuilder {
private static final Logger LOG = LoggerFactory.getLogger(HgRepositoryEnvironmentBuilder.class);
private static final String ENV_REPOSITORY_NAME = "REPO_NAME";
private static final String ENV_REPOSITORY_PATH = "SCM_REPOSITORY_PATH";
private static final String ENV_REPOSITORY_ID = "SCM_REPOSITORY_ID";
private static final String ENV_PYTHON_HTTPS_VERIFY = "PYTHONHTTPSVERIFY";
private static final String ENV_HTTP_POST_ARGS = "SCM_HTTP_POST_ARGS";
private static final String SCM_CREDENTIALS = "SCM_CREDENTIALS";
private final HgRepositoryHandler handler;
private final HgHookManager hookManager;
@Inject
public HgRepositoryEnvironmentBuilder(HgRepositoryHandler handler, HgHookManager hookManager) {
this.handler = handler;
this.hookManager = hookManager;
}
void buildFor(Repository repository, HttpServletRequest request, EnvList environment) {
File directory = handler.getDirectory(repository.getId());
environment.set(ENV_REPOSITORY_NAME, repository.getNamespace() + "/" + repository.getName());
environment.set(ENV_REPOSITORY_ID, repository.getId());
environment.set(ENV_REPOSITORY_PATH,
directory.getAbsolutePath());
// add hook environment
Map<String, String> environmentMap = environment.asMutableMap();
if (handler.getConfig().isDisableHookSSLValidation()) {
// disable ssl validation
// Issue 959: https://goo.gl/zH5eY8
environmentMap.put(ENV_PYTHON_HTTPS_VERIFY, "0");
}
// enable experimental httppostargs protocol of mercurial
// Issue 970: https://goo.gl/poascp
environmentMap.put(ENV_HTTP_POST_ARGS, String.valueOf(handler.getConfig().isEnableHttpPostArgs()));
HgEnvironment.prepareEnvironment(
environmentMap,
handler,
hookManager,
request
);
addCredentials(environment, request);
}
private void addCredentials(EnvList env, HttpServletRequest request)
{
String authorization = request.getHeader(HttpUtil.HEADER_AUTHORIZATION);
if (!Strings.isNullOrEmpty(authorization))
{
if (authorization.startsWith(HttpUtil.AUTHORIZATION_SCHEME_BASIC))
{
String encodedUserInfo =
authorization.substring(
HttpUtil.AUTHORIZATION_SCHEME_BASIC.length()).trim();
// TODO check encoding of user-agent ?
String userInfo = new String(Base64.getDecoder().decode(encodedUserInfo));
env.set(SCM_CREDENTIALS, CipherUtil.getInstance().encode(userInfo));
}
else
{
LOG.warn("unknown authentication scheme used");
}
}
else
{
LOG.trace("no authorization header found");
}
}
}