You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@sling.apache.org by cz...@apache.org on 2020/01/16 06:31:38 UTC
[sling-org-apache-sling-engine] branch master updated: SLING-9002 :
Improve service registrations
This is an automated email from the ASF dual-hosted git repository.
cziegeler pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/sling-org-apache-sling-engine.git
The following commit(s) were added to refs/heads/master by this push:
new 4ad175f SLING-9002 : Improve service registrations
4ad175f is described below
commit 4ad175f11d172973fa8e05071c32eaa2a2cfb322
Author: Carsten Ziegeler <cz...@apache.org>
AuthorDate: Thu Jan 16 07:31:24 2020 +0100
SLING-9002 : Improve service registrations
---
.../apache/sling/engine/impl/SlingMainServlet.java | 53 +--
.../engine/impl/SlingRequestProcessorImpl.java | 2 +-
.../engine/impl/SlingSettingsServiceImpl.java | 4 +
.../impl/console/RequestHistoryConsolePlugin.java | 346 ++++++++++++++++++++
.../{ => console}/WebConsoleConfigPrinter.java | 23 +-
.../debug/RequestProgressTrackerLogFilter.java | 7 +-
.../engine/impl/filter/ServletFilterManager.java | 20 ++
.../sling/engine/impl/log/RequestLogger.java | 5 +-
.../sling/engine/impl/log/RequestLoggerFilter.java | 21 +-
.../engine/impl/log/RequestLoggerService.java | 10 +-
.../RequestParameterSupportConfigurer.java | 32 +-
.../impl/request/RequestHistoryConsolePlugin.java | 362 ---------------------
12 files changed, 427 insertions(+), 458 deletions(-)
diff --git a/src/main/java/org/apache/sling/engine/impl/SlingMainServlet.java b/src/main/java/org/apache/sling/engine/impl/SlingMainServlet.java
index 26670b2..5f94c31 100644
--- a/src/main/java/org/apache/sling/engine/impl/SlingMainServlet.java
+++ b/src/main/java/org/apache/sling/engine/impl/SlingMainServlet.java
@@ -21,13 +21,12 @@ package org.apache.sling.engine.impl;
import java.util.ArrayList;
import java.util.Dictionary;
import java.util.Hashtable;
-import java.util.List;
import java.util.Map;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.atomic.AtomicBoolean;
-import java.util.regex.Pattern;
+import javax.management.NotCompliantMBeanException;
import javax.servlet.GenericServlet;
import javax.servlet.Servlet;
import javax.servlet.ServletException;
@@ -43,12 +42,12 @@ import org.apache.sling.api.servlets.ServletResolver;
import org.apache.sling.auth.core.AuthenticationSupport;
import org.apache.sling.commons.mime.MimeTypeService;
import org.apache.sling.engine.SlingRequestProcessor;
+import org.apache.sling.engine.impl.console.RequestHistoryConsolePlugin;
import org.apache.sling.engine.impl.filter.ServletFilterManager;
import org.apache.sling.engine.impl.helper.ClientAbortException;
import org.apache.sling.engine.impl.helper.RequestListenerManager;
import org.apache.sling.engine.impl.helper.SlingServletContext;
import org.apache.sling.engine.impl.request.RequestData;
-import org.apache.sling.engine.impl.request.RequestHistoryConsolePlugin;
import org.apache.sling.engine.jmx.RequestProcessorMBean;
import org.apache.sling.engine.servlets.ErrorHandler;
import org.osgi.framework.BundleContext;
@@ -62,6 +61,8 @@ import org.osgi.service.component.annotations.Modified;
import org.osgi.service.component.annotations.Reference;
import org.osgi.service.component.annotations.ReferenceCardinality;
import org.osgi.service.component.annotations.ReferencePolicy;
+import org.osgi.service.component.propertytypes.ServiceDescription;
+import org.osgi.service.component.propertytypes.ServiceVendor;
import org.osgi.service.http.context.ServletContextHelper;
import org.osgi.service.http.whiteboard.HttpWhiteboardConstants;
import org.osgi.service.metatype.annotations.AttributeDefinition;
@@ -74,13 +75,14 @@ import org.slf4j.LoggerFactory;
* The <code>SlingMainServlet</code>
*/
@SuppressWarnings("serial")
-@Component(property = {
- Constants.SERVICE_VENDOR + "=The Apache Software Foundation",
- Constants.SERVICE_DESCRIPTION + "=Sling Servlet"
-})
+@Component(configurationPid = SlingMainServlet.PID, service = {})
+@ServiceDescription("Sling Servlet")
+@ServiceVendor("The Apache Software Foundation")
@Designate(ocd=SlingMainServlet.Config.class)
public class SlingMainServlet extends GenericServlet {
+ public static final String PID = "org.apache.sling.engine.impl.SlingMainServlet";
+
@ObjectClassDefinition(name ="Apache Sling Main Servlet",
description="Main processor of the Sling framework controlling all " +
"aspects of processing requests inside of Sling, namely authentication, " +
@@ -185,8 +187,6 @@ public class SlingMainServlet extends GenericServlet {
private volatile boolean allowTrace;
- private volatile Object printerRegistration;
-
// new properties
private final SlingHttpContext slingHttpContext = new SlingHttpContext();
@@ -451,23 +451,6 @@ public class SlingMainServlet extends GenericServlet {
this.servletRegistration.setProperties(getServletContextRegistrationProps(servletName));
}
}
-
- // setup the request info recorder
- try {
- int maxRequests = config.sling_max_record_requests();
- String[] patterns = config.sling_store_pattern_requests();
- if ( patterns == null ) patterns = new String[0];
- List<Pattern> compiledPatterns = new ArrayList<>(patterns.length);
- for (String pattern : patterns) {
- if(pattern != null && pattern.trim().length() > 0) {
- compiledPatterns.add(Pattern.compile(pattern));
- }
- }
- RequestHistoryConsolePlugin.initPlugin(bundleContext, maxRequests, compiledPatterns);
- } catch (Throwable t) {
- log.debug(
- "Unable to register web console request recorder plugin.", t);
- }
}
@Activate
@@ -517,9 +500,6 @@ public class SlingMainServlet extends GenericServlet {
// initialize requestListenerManager
requestListenerManager = new RequestListenerManager(bundleContext, slingServletContext);
- // Setup configuration printer
- printerRegistration = WebConsoleConfigPrinter.register(bundleContext, filterManager);
-
try {
Dictionary<String, String> mbeanProps = new Hashtable<>();
mbeanProps.put("jmx.objectname", "org.apache.sling:type=engine,service=RequestProcessor");
@@ -527,7 +507,7 @@ public class SlingMainServlet extends GenericServlet {
RequestProcessorMBeanImpl mbean = new RequestProcessorMBeanImpl();
requestProcessorMBeanRegistration = bundleContext.registerService(RequestProcessorMBean.class, mbean, mbeanProps);
requestProcessor.setMBean(mbean);
- } catch (Throwable t) {
+ } catch (NotCompliantMBeanException t) {
log.debug("Unable to register mbean");
}
@@ -553,14 +533,6 @@ public class SlingMainServlet extends GenericServlet {
"being called. There is a risk that objects are not properly destroyed.");
}
- // unregister request recorder plugin
- try {
- RequestHistoryConsolePlugin.destroyPlugin();
- } catch (Throwable t) {
- log.debug(
- "Problem unregistering web console request recorder plugin.", t);
- }
-
// second unregister the servlet context *before* unregistering
// and destroying the the sling main servlet
if (this.contextRegistration != null) {
@@ -602,11 +574,6 @@ public class SlingMainServlet extends GenericServlet {
requestProcessorMBeanRegistration = null;
}
- // this reverses the activation setup
- if ( this.printerRegistration != null ) {
- WebConsoleConfigPrinter.unregister(this.printerRegistration);
- this.printerRegistration = null;
- }
// destroy servlet filters before destroying the sling servlet
// context because the filters depend on that context
if (filterManager != null) {
diff --git a/src/main/java/org/apache/sling/engine/impl/SlingRequestProcessorImpl.java b/src/main/java/org/apache/sling/engine/impl/SlingRequestProcessorImpl.java
index 90af1ee..d70283b 100644
--- a/src/main/java/org/apache/sling/engine/impl/SlingRequestProcessorImpl.java
+++ b/src/main/java/org/apache/sling/engine/impl/SlingRequestProcessorImpl.java
@@ -47,6 +47,7 @@ import org.apache.sling.api.resource.ResourceResolver;
import org.apache.sling.api.servlets.ServletResolver;
import org.apache.sling.api.wrappers.SlingHttpServletResponseWrapper;
import org.apache.sling.engine.SlingRequestProcessor;
+import org.apache.sling.engine.impl.console.RequestHistoryConsolePlugin;
import org.apache.sling.engine.impl.filter.AbstractSlingFilterChain;
import org.apache.sling.engine.impl.filter.FilterHandle;
import org.apache.sling.engine.impl.filter.RequestSlingFilterChain;
@@ -56,7 +57,6 @@ import org.apache.sling.engine.impl.filter.SlingComponentFilterChain;
import org.apache.sling.engine.impl.parameters.ParameterSupport;
import org.apache.sling.engine.impl.request.ContentData;
import org.apache.sling.engine.impl.request.RequestData;
-import org.apache.sling.engine.impl.request.RequestHistoryConsolePlugin;
import org.apache.sling.engine.servlets.ErrorHandler;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
diff --git a/src/main/java/org/apache/sling/engine/impl/SlingSettingsServiceImpl.java b/src/main/java/org/apache/sling/engine/impl/SlingSettingsServiceImpl.java
index 646b014..dd6ddec 100644
--- a/src/main/java/org/apache/sling/engine/impl/SlingSettingsServiceImpl.java
+++ b/src/main/java/org/apache/sling/engine/impl/SlingSettingsServiceImpl.java
@@ -21,6 +21,8 @@ package org.apache.sling.engine.impl;
import org.apache.sling.engine.SlingSettingsService;
import org.osgi.service.component.annotations.Component;
import org.osgi.service.component.annotations.Reference;
+import org.osgi.service.component.propertytypes.ServiceDescription;
+import org.osgi.service.component.propertytypes.ServiceVendor;
/**
* The implementation of the settings service has moved to the
@@ -29,6 +31,8 @@ import org.osgi.service.component.annotations.Reference;
* @deprecated
*/
@Component(service = SlingSettingsService.class)
+@ServiceDescription("deprecated")
+@ServiceVendor("The Apache Software Foundation")
@Deprecated
public class SlingSettingsServiceImpl
implements SlingSettingsService {
diff --git a/src/main/java/org/apache/sling/engine/impl/console/RequestHistoryConsolePlugin.java b/src/main/java/org/apache/sling/engine/impl/console/RequestHistoryConsolePlugin.java
new file mode 100644
index 0000000..dd0dafd
--- /dev/null
+++ b/src/main/java/org/apache/sling/engine/impl/console/RequestHistoryConsolePlugin.java
@@ -0,0 +1,346 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.sling.engine.impl.console;
+
+import java.io.IOException;
+import java.io.PrintWriter;
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.LinkedHashMap;
+import java.util.List;
+import java.util.concurrent.atomic.AtomicLong;
+import java.util.regex.Pattern;
+
+import javax.servlet.Servlet;
+import javax.servlet.ServletException;
+import javax.servlet.http.HttpServlet;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+import org.apache.sling.api.SlingHttpServletRequest;
+import org.apache.sling.api.request.RequestProgressTracker;
+import org.apache.sling.api.request.ResponseUtil;
+import org.apache.sling.api.resource.ResourceUtil;
+import org.apache.sling.engine.impl.SlingMainServlet;
+import org.osgi.service.component.annotations.Activate;
+import org.osgi.service.component.annotations.Component;
+import org.osgi.service.component.annotations.Deactivate;
+import org.osgi.service.component.annotations.Modified;
+import org.osgi.service.component.propertytypes.ServiceDescription;
+import org.osgi.service.component.propertytypes.ServiceVendor;
+
+/**
+ * Felix OSGi console plugin that displays info about recent requests processed
+ * by Sling. Info about all requests can be found in the logs, but this is
+ * useful when testing or explaining things.
+ */
+@Component(service = Servlet.class,
+ configurationPid = SlingMainServlet.PID,
+ property = {
+ "felix.webconsole.label=" + RequestHistoryConsolePlugin.LABEL,
+ "felix.webconsole.title=Recent requests",
+ "felix.webconsole.category=Sling"
+ })
+@ServiceDescription("Web Console Plugin to display information about recent Sling requests")
+@ServiceVendor("The Apache Software Foundation")
+public class RequestHistoryConsolePlugin extends HttpServlet {
+
+ private static final long serialVersionUID = -5738101314957623511L;
+
+ public static final String LABEL = "requests";
+
+ public static final String INDEX = "index";
+
+ public static final String CLEAR = "clear";
+
+ private static volatile RequestHistoryConsolePlugin instance;
+
+ public static final int STORED_REQUESTS_COUNT = 20;
+
+ private volatile RequestInfoMap requests;
+
+ private volatile List<Pattern> storePatterns;
+
+ @Activate
+ public RequestHistoryConsolePlugin(final SlingMainServlet.Config config) {
+ update(config);
+ instance = this;
+ }
+
+
+ @Modified
+ protected void update(final SlingMainServlet.Config config) {
+ this.requests = (config.sling_max_record_requests() > 0)
+ ? new RequestInfoMap(config.sling_max_record_requests())
+ : null;
+ final List<Pattern> compiledPatterns = new ArrayList<>();
+ if (config.sling_store_pattern_requests() != null) {
+ for (String pattern : config.sling_store_pattern_requests()) {
+ if (pattern != null && pattern.trim().length() > 0) {
+ compiledPatterns.add(Pattern.compile(pattern));
+ }
+ }
+ }
+ this.storePatterns = compiledPatterns;
+
+ }
+
+ @Deactivate
+ protected void deactivate() {
+ instance = null;
+ clear();
+ }
+
+ public static void recordRequest(final SlingHttpServletRequest r) {
+ final RequestHistoryConsolePlugin local = instance;
+ if (local != null) {
+ local.addRequest(r);
+ }
+ }
+
+ private void addRequest(SlingHttpServletRequest r) {
+ if (requests != null) {
+ String requestPath = r.getPathInfo();
+ boolean accept = true;
+ if (storePatterns != null && storePatterns.size() > 0) {
+ accept = false;
+ for (Pattern pattern : storePatterns) {
+ if (pattern.matcher(requestPath).matches()) {
+ accept = true;
+ break;
+ }
+ }
+ }
+
+ if (accept) {
+ synchronized (requests) {
+ RequestInfo info = new RequestInfo(r);
+ requests.put(info.getKey(), info);
+ }
+ }
+ }
+ }
+
+ private void clear() {
+ if (requests != null) {
+ synchronized (requests) {
+ requests.clear();
+ }
+ }
+ }
+
+ private String getLinksTable(String currentRequestIndex) {
+ final List<String> links = new ArrayList<String>();
+ if (requests != null) {
+ synchronized (requests) {
+ for (RequestInfo info : requests.values()) {
+ final String key = ResponseUtil.escapeXml(info.getKey());
+ final boolean isCurrent = info.getKey().equals(
+ currentRequestIndex);
+ final StringBuilder sb = new StringBuilder();
+ sb.append("<span style='white-space: pre; text-align:right; font-size:80%'>");
+ sb.append(String.format("%1$8s", key));
+ sb.append("</span> ");
+ sb.append("<a href='" + LABEL + "?index=" + key + "'>");
+ if (isCurrent) {
+ sb.append("<b>");
+ }
+ sb.append(ResponseUtil.escapeXml(info.getLabel()));
+ if (isCurrent) {
+ sb.append("</b>");
+ }
+ sb.append("</a> ");
+ links.add(sb.toString());
+ }
+ }
+ }
+
+ final int nCols = 5;
+ while ((links.size() % nCols) != 0) {
+ links.add(" ");
+ }
+
+ final StringBuilder tbl = new StringBuilder();
+
+ tbl.append("<table class='nicetable ui-widget'>\n<tr>\n");
+ if (links.isEmpty()) {
+ tbl.append("No Requests recorded");
+ } else {
+ int i = 0;
+ for (String str : links) {
+ if ((i++ % nCols) == 0) {
+ tbl.append("</tr>\n<tr>\n");
+ }
+ tbl.append("<td>");
+ tbl.append(str);
+ tbl.append("</td>\n");
+ }
+ }
+ tbl.append("</tr>\n");
+
+ tbl.append("</table>\n");
+ return tbl.toString();
+ }
+
+ @Override
+ protected void doGet(HttpServletRequest req, HttpServletResponse resp)
+ throws ServletException, IOException {
+
+ // Select request to display
+ RequestInfo info = null;
+ String key = req.getParameter(INDEX);
+ if (key != null && requests != null) {
+ synchronized (requests) {
+ info = requests.get(key);
+ }
+ }
+
+ final PrintWriter pw = resp.getWriter();
+
+ if (requests != null) {
+ pw.println("<p class='statline ui-state-highlight'>Recorded "
+ + requests.size() + " requests (max: "
+ + requests.getMaxSize() + ")</p>");
+ } else {
+ pw.println("<p class='statline ui-state-highlight'>Request Recording disabled</p>");
+ }
+
+ pw.println("<div class='ui-widget-header ui-corner-top buttonGroup'>");
+ pw.println("<span style='float: left; margin-left: 1em'>Recent Requests</span>");
+ pw.println("<form method='POST'><input type='hidden' name='clear' value='clear'><input type='submit' value='Clear' class='ui-state-default ui-corner-all'></form>");
+ pw.println("</div>");
+
+ pw.println(getLinksTable(key));
+ pw.println("<br/>");
+
+ if (info != null) {
+
+ pw.println("<table class='nicetable ui-widget'>");
+
+ // Links to other requests
+ pw.println("<thead>");
+ pw.println("<tr>");
+ pw.printf(
+ "<th class='ui-widget-header'>Request %s (%s %s) by %s - RequestProgressTracker Info</th>%n",
+ key, ResponseUtil.escapeXml(info.getMethod()),
+ ResponseUtil.escapeXml(info.getPathInfo()), ResponseUtil.escapeXml(info.getUser()));
+ pw.println("</tr>");
+ pw.println("</thead>");
+
+ pw.println("<tbody>");
+
+ // Request Progress Tracker Info
+ pw.println("<tr><td>");
+ final Iterator<String> it = info.getTracker().getMessages();
+ pw.print("<pre>");
+ while (it.hasNext()) {
+ pw.print(ResponseUtil.escapeXml(it.next()));
+ }
+ pw.println("</pre></td></tr>");
+ pw.println("</tbody></table>");
+ }
+ }
+
+ @Override
+ protected void doPost(HttpServletRequest req, HttpServletResponse resp)
+ throws IOException {
+ if (req.getParameter(CLEAR) != null) {
+ clear();
+ resp.sendRedirect(req.getRequestURI());
+ }
+ }
+
+ private static class RequestInfo {
+
+ private static AtomicLong requestCounter = new AtomicLong(0);
+
+ private final String key;
+
+ private final String method;
+
+ private final String pathInfo;
+
+ private final String user;
+
+ private final RequestProgressTracker tracker;
+
+ RequestInfo(SlingHttpServletRequest request) {
+ this.key = String.valueOf(requestCounter.incrementAndGet());
+ this.method = request.getMethod();
+ this.pathInfo = request.getPathInfo();
+ this.user = request.getRemoteUser();
+ this.tracker = request.getRequestProgressTracker();
+ }
+
+ public String getKey() {
+ return key;
+ }
+
+ public String getMethod() {
+ return method;
+ }
+
+ public String getPathInfo() {
+ return pathInfo;
+ }
+
+ public String getUser() {
+ return user;
+ }
+
+ public String getLabel() {
+ final StringBuilder sb = new StringBuilder();
+
+ sb.append(getMethod());
+ sb.append(' ');
+
+ final String path = getPathInfo();
+ if (path != null && path.length() > 0) {
+ sb.append(ResourceUtil.getName(getPathInfo()));
+ } else {
+ sb.append('/');
+ }
+
+ return sb.toString();
+ }
+
+ public RequestProgressTracker getTracker() {
+ return tracker;
+ }
+ }
+
+ private static class RequestInfoMap extends LinkedHashMap<String, RequestInfo> {
+
+ private static final long serialVersionUID = 4120391774146501524L;
+ private int maxSize;
+
+ RequestInfoMap(int maxSize) {
+ this.maxSize = maxSize;
+ }
+
+ @Override
+ protected boolean removeEldestEntry(java.util.Map.Entry<String, RequestInfo> eldest) {
+ return size() > maxSize;
+ }
+
+ public int getMaxSize() {
+ return maxSize;
+ }
+ }
+}
\ No newline at end of file
diff --git a/src/main/java/org/apache/sling/engine/impl/WebConsoleConfigPrinter.java b/src/main/java/org/apache/sling/engine/impl/console/WebConsoleConfigPrinter.java
similarity index 83%
rename from src/main/java/org/apache/sling/engine/impl/WebConsoleConfigPrinter.java
rename to src/main/java/org/apache/sling/engine/impl/console/WebConsoleConfigPrinter.java
index 1b83ba3..e36dd74 100644
--- a/src/main/java/org/apache/sling/engine/impl/WebConsoleConfigPrinter.java
+++ b/src/main/java/org/apache/sling/engine/impl/console/WebConsoleConfigPrinter.java
@@ -16,7 +16,7 @@
* specific language governing permissions and limitations
* under the License.
*/
-package org.apache.sling.engine.impl;
+package org.apache.sling.engine.impl.console;
import java.io.PrintWriter;
import java.util.Dictionary;
@@ -42,14 +42,8 @@ public class WebConsoleConfigPrinter {
this.filterManager = filterManager;
}
- private static final class Registration {
- public ServiceRegistration filterPlugin;
- }
-
- public static Object register(final BundleContext bundleContext,
+ public static ServiceRegistration register(final BundleContext bundleContext,
final ServletFilterManager filterManager) {
- final Registration reg = new Registration();
-
// first we register the plugin for the filters
final WebConsoleConfigPrinter filterPrinter = new WebConsoleConfigPrinter(filterManager);
final Dictionary<String, String> serviceProps = new Hashtable<String, String>();
@@ -60,19 +54,14 @@ public class WebConsoleConfigPrinter {
serviceProps.put("felix.webconsole.title", "Sling Servlet Filter");
serviceProps.put("felix.webconsole.configprinter.modes", "always");
- reg.filterPlugin = bundleContext.registerService(WebConsoleConfigPrinter.class.getName(),
+ return bundleContext.registerService(WebConsoleConfigPrinter.class.getName(),
filterPrinter,
serviceProps);
- return reg;
}
- public static void unregister(final Object reg) {
- if ( reg instanceof Registration ) {
- final Registration registration = (Registration)reg;
- if ( registration.filterPlugin != null) {
- registration.filterPlugin.unregister();
- registration.filterPlugin = null;
- }
+ public static void unregister(final ServiceRegistration reg) {
+ if (reg != null) {
+ reg.unregister();
}
}
diff --git a/src/main/java/org/apache/sling/engine/impl/debug/RequestProgressTrackerLogFilter.java b/src/main/java/org/apache/sling/engine/impl/debug/RequestProgressTrackerLogFilter.java
index 7ff83ac..6798beb 100644
--- a/src/main/java/org/apache/sling/engine/impl/debug/RequestProgressTrackerLogFilter.java
+++ b/src/main/java/org/apache/sling/engine/impl/debug/RequestProgressTrackerLogFilter.java
@@ -34,9 +34,10 @@ import org.apache.sling.api.request.RequestPathInfo;
import org.apache.sling.api.request.RequestProgressTracker;
import org.apache.sling.engine.EngineConstants;
import org.apache.sling.engine.impl.request.SlingRequestProgressTracker;
-import org.osgi.framework.Constants;
import org.osgi.service.component.annotations.Activate;
import org.osgi.service.component.annotations.Component;
+import org.osgi.service.component.propertytypes.ServiceDescription;
+import org.osgi.service.component.propertytypes.ServiceVendor;
import org.osgi.service.metatype.annotations.AttributeDefinition;
import org.osgi.service.metatype.annotations.Designate;
import org.osgi.service.metatype.annotations.ObjectClassDefinition;
@@ -51,10 +52,10 @@ import org.slf4j.LoggerFactory;
@Designate(ocd=RequestProgressTrackerLogFilter.Config.class)
@Component(service=Filter.class,
property={
- Constants.SERVICE_DESCRIPTION + "=RequestProgressTracker dump filter",
- Constants.SERVICE_VENDOR + "=The Apache Software Foundation",
EngineConstants.SLING_FILTER_SCOPE + "=" + EngineConstants.FILTER_SCOPE_REQUEST
})
+@ServiceDescription("RequestProgressTracker dump filte")
+@ServiceVendor("The Apache Software Foundation")
public class RequestProgressTrackerLogFilter implements Filter {
@ObjectClassDefinition(name="Apache Sling Request Progress Tracker Log Filter",
diff --git a/src/main/java/org/apache/sling/engine/impl/filter/ServletFilterManager.java b/src/main/java/org/apache/sling/engine/impl/filter/ServletFilterManager.java
index 53ef9f2..d22676a 100644
--- a/src/main/java/org/apache/sling/engine/impl/filter/ServletFilterManager.java
+++ b/src/main/java/org/apache/sling/engine/impl/filter/ServletFilterManager.java
@@ -29,6 +29,7 @@ import javax.servlet.ServletException;
import org.apache.sling.commons.osgi.OsgiUtil;
import org.apache.sling.engine.EngineConstants;
+import org.apache.sling.engine.impl.console.WebConsoleConfigPrinter;
import org.apache.sling.engine.impl.helper.SlingFilterConfig;
import org.apache.sling.engine.impl.helper.SlingServletContext;
import org.apache.sling.engine.jmx.FilterProcessorMBean;
@@ -103,6 +104,8 @@ public class ServletFilterManager extends ServiceTracker<Filter, Filter> {
private final Map<Long, MBeanReg> mbeanMap = new ConcurrentHashMap<>();
+ private volatile ServiceRegistration printerRegistration;
+
private static final org.osgi.framework.Filter SERVICE_FILTER;
static {
org.osgi.framework.Filter f = null;
@@ -125,6 +128,23 @@ public class ServletFilterManager extends ServiceTracker<Filter, Filter> {
}
}
+ @Override
+ public void open() {
+ super.open();
+ // Setup configuration printer
+ printerRegistration = WebConsoleConfigPrinter.register(context, this);
+
+ }
+
+ @Override
+ public void close() {
+ if (this.printerRegistration != null) {
+ WebConsoleConfigPrinter.unregister(this.printerRegistration);
+ this.printerRegistration = null;
+ }
+ super.close();
+ }
+
public SlingFilterChainHelper getFilterChain(final FilterChainType chain) {
return filterChains[chain.ordinal()];
}
diff --git a/src/main/java/org/apache/sling/engine/impl/log/RequestLogger.java b/src/main/java/org/apache/sling/engine/impl/log/RequestLogger.java
index 3fff3bf..edd2178 100644
--- a/src/main/java/org/apache/sling/engine/impl/log/RequestLogger.java
+++ b/src/main/java/org/apache/sling/engine/impl/log/RequestLogger.java
@@ -37,10 +37,7 @@ import org.osgi.service.metatype.annotations.Option;
* The <code>RequestLogger</code> just registers {@link RequestLoggerService}
* instance on behalf of the provided configuration.
*/
-@Component(property = {
- "service.description=Request Logger",
- "service.vendor=The Apache Software Foundation"
-})
+@Component
@Designate(ocd = RequestLogger.Config.class)
public class RequestLogger {
diff --git a/src/main/java/org/apache/sling/engine/impl/log/RequestLoggerFilter.java b/src/main/java/org/apache/sling/engine/impl/log/RequestLoggerFilter.java
index 4a0479e..ed58511 100644
--- a/src/main/java/org/apache/sling/engine/impl/log/RequestLoggerFilter.java
+++ b/src/main/java/org/apache/sling/engine/impl/log/RequestLoggerFilter.java
@@ -30,24 +30,27 @@ import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.sling.engine.impl.SlingMainServlet;
-import org.osgi.framework.Constants;
import org.osgi.service.component.annotations.Component;
import org.osgi.service.component.annotations.ConfigurationPolicy;
import org.osgi.service.component.annotations.Reference;
import org.osgi.service.component.annotations.ReferenceCardinality;
import org.osgi.service.component.annotations.ReferencePolicy;
+import org.osgi.service.component.propertytypes.ServiceDescription;
+import org.osgi.service.component.propertytypes.ServiceRanking;
+import org.osgi.service.component.propertytypes.ServiceVendor;
import org.osgi.service.http.whiteboard.HttpWhiteboardConstants;
+import org.osgi.service.http.whiteboard.propertytypes.HttpWhiteboardContextSelect;
+import org.osgi.service.http.whiteboard.propertytypes.HttpWhiteboardFilterPattern;
import org.slf4j.LoggerFactory;
@Component(configurationPolicy = ConfigurationPolicy.IGNORE,
- service = Filter.class,
- property = {
- HttpWhiteboardConstants.HTTP_WHITEBOARD_CONTEXT_SELECT+ "=(" + HttpWhiteboardConstants.HTTP_WHITEBOARD_CONTEXT_NAME + "=" + SlingMainServlet.SERVLET_CONTEXT_NAME + ")",
- HttpWhiteboardConstants.HTTP_WHITEBOARD_FILTER_PATTERN + "=/",
- Constants.SERVICE_RANKING + ":Integer=32768",
- Constants.SERVICE_DESCRIPTION + "=Request Logger Filter",
- Constants.SERVICE_VENDOR + "=The Apache Software Foundation"
- })
+ service = Filter.class)
+@HttpWhiteboardContextSelect("(" + HttpWhiteboardConstants.HTTP_WHITEBOARD_CONTEXT_NAME + "="
+ + SlingMainServlet.SERVLET_CONTEXT_NAME + ")")
+@HttpWhiteboardFilterPattern("/")
+@ServiceRanking(32768)
+@ServiceDescription("Request Logger Filter")
+@ServiceVendor("The Apache Software Foundation")
public final class RequestLoggerFilter implements Filter {
private static final RequestLoggerService[] NONE = new RequestLoggerService[0];
diff --git a/src/main/java/org/apache/sling/engine/impl/log/RequestLoggerService.java b/src/main/java/org/apache/sling/engine/impl/log/RequestLoggerService.java
index b3b7f04..ac1c00e 100644
--- a/src/main/java/org/apache/sling/engine/impl/log/RequestLoggerService.java
+++ b/src/main/java/org/apache/sling/engine/impl/log/RequestLoggerService.java
@@ -27,6 +27,8 @@ import org.osgi.service.component.annotations.Activate;
import org.osgi.service.component.annotations.Component;
import org.osgi.service.component.annotations.ConfigurationPolicy;
import org.osgi.service.component.annotations.Deactivate;
+import org.osgi.service.component.propertytypes.ServiceDescription;
+import org.osgi.service.component.propertytypes.ServiceVendor;
import org.osgi.service.metatype.annotations.AttributeDefinition;
import org.osgi.service.metatype.annotations.Designate;
import org.osgi.service.metatype.annotations.ObjectClassDefinition;
@@ -36,11 +38,9 @@ import org.osgi.service.metatype.annotations.Option;
* The <code>RequestLoggerService</code> is a factory component which gets
* configuration to register loggers for the {@link RequestLogger}.
*/
-@Component(service = RequestLoggerService.class, configurationPolicy = ConfigurationPolicy.REQUIRE,
- property = {
- "service.description=Factory for configuration based request/access loggers",
- "service.vendor=The Apache Software Foundation"
- })
+@Component(service = RequestLoggerService.class, configurationPolicy = ConfigurationPolicy.REQUIRE)
+@ServiceDescription("Factory for configuration based request/access loggers")
+@ServiceVendor("The Apache Software Foundation")
@Designate(ocd = RequestLoggerService.Config.class, factory = true)
public class RequestLoggerService {
diff --git a/src/main/java/org/apache/sling/engine/impl/parameters/RequestParameterSupportConfigurer.java b/src/main/java/org/apache/sling/engine/impl/parameters/RequestParameterSupportConfigurer.java
index a915342..7e64f9b 100644
--- a/src/main/java/org/apache/sling/engine/impl/parameters/RequestParameterSupportConfigurer.java
+++ b/src/main/java/org/apache/sling/engine/impl/parameters/RequestParameterSupportConfigurer.java
@@ -21,34 +21,38 @@ package org.apache.sling.engine.impl.parameters;
import java.io.File;
import java.io.IOException;
+import javax.servlet.Filter;
+import javax.servlet.FilterChain;
+import javax.servlet.FilterConfig;
+import javax.servlet.ServletException;
+import javax.servlet.ServletRequest;
+import javax.servlet.ServletResponse;
+import javax.servlet.http.HttpServletRequest;
+
import org.apache.sling.api.SlingHttpServletRequest;
import org.apache.sling.settings.SlingSettingsService;
-import org.osgi.framework.Constants;
import org.osgi.service.component.annotations.Activate;
import org.osgi.service.component.annotations.Component;
import org.osgi.service.component.annotations.Reference;
+import org.osgi.service.component.propertytypes.ServiceDescription;
+import org.osgi.service.component.propertytypes.ServiceRanking;
+import org.osgi.service.component.propertytypes.ServiceVendor;
+import org.osgi.service.http.whiteboard.propertytypes.HttpWhiteboardContextSelect;
+import org.osgi.service.http.whiteboard.propertytypes.HttpWhiteboardFilterPattern;
import org.osgi.service.metatype.annotations.AttributeDefinition;
import org.osgi.service.metatype.annotations.Designate;
import org.osgi.service.metatype.annotations.ObjectClassDefinition;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
-import javax.servlet.Filter;
-import javax.servlet.FilterChain;
-import javax.servlet.FilterConfig;
-import javax.servlet.ServletException;
-import javax.servlet.ServletRequest;
-import javax.servlet.ServletResponse;
-import javax.servlet.http.HttpServletRequest;
-
@Component(
name = RequestParameterSupportConfigurer.PID,
- property = {
- Constants.SERVICE_RANKING + ":Integer=" + Integer.MAX_VALUE,
- "osgi.http.whiteboard.context.select=(osgi.http.whiteboard.context.name=org.apache.sling)",
- "osgi.http.whiteboard.filter.pattern=/"
- },
service = Filter.class)
+@HttpWhiteboardContextSelect("(osgi.http.whiteboard.context.name=org.apache.sling)")
+@HttpWhiteboardFilterPattern("/")
+@ServiceDescription("Filter for request parameter support")
+@ServiceVendor("The Apache Software Foundation")
+@ServiceRanking(Integer.MAX_VALUE)
@Designate(ocd=RequestParameterSupportConfigurer.Config.class)
public class RequestParameterSupportConfigurer implements Filter {
diff --git a/src/main/java/org/apache/sling/engine/impl/request/RequestHistoryConsolePlugin.java b/src/main/java/org/apache/sling/engine/impl/request/RequestHistoryConsolePlugin.java
deleted file mode 100644
index c15f5ea..0000000
--- a/src/main/java/org/apache/sling/engine/impl/request/RequestHistoryConsolePlugin.java
+++ /dev/null
@@ -1,362 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements. See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership. The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License. You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied. See the License for the
- * specific language governing permissions and limitations
- * under the License.
- */
-package org.apache.sling.engine.impl.request;
-
-import java.io.IOException;
-import java.io.PrintWriter;
-import java.util.ArrayList;
-import java.util.Dictionary;
-import java.util.Hashtable;
-import java.util.Iterator;
-import java.util.LinkedHashMap;
-import java.util.List;
-import java.util.concurrent.atomic.AtomicLong;
-import java.util.regex.Pattern;
-
-import javax.servlet.Servlet;
-import javax.servlet.ServletException;
-import javax.servlet.http.HttpServlet;
-import javax.servlet.http.HttpServletRequest;
-import javax.servlet.http.HttpServletResponse;
-
-import org.apache.sling.api.SlingHttpServletRequest;
-import org.apache.sling.api.request.RequestProgressTracker;
-import org.apache.sling.api.request.ResponseUtil;
-import org.apache.sling.api.resource.ResourceUtil;
-import org.osgi.framework.BundleContext;
-import org.osgi.framework.Constants;
-import org.osgi.framework.ServiceRegistration;
-
-/**
- * Felix OSGi console plugin that displays info about recent requests processed
- * by Sling. Info about all requests can be found in the logs, but this is
- * useful when testing or explaining things.
- */
-@SuppressWarnings("serial")
-public class RequestHistoryConsolePlugin {
-
- public static final String LABEL = "requests";
-
- public static final String INDEX = "index";
-
- public static final String CLEAR = "clear";
-
- private static Plugin instance;
-
- private static ServiceRegistration<Servlet> serviceRegistration;
-
- public static final int STORED_REQUESTS_COUNT = 20;
-
- private RequestHistoryConsolePlugin() {
- }
-
- public static void recordRequest(SlingHttpServletRequest r) {
- if (instance != null) {
- instance.addRequest(r);
- }
- }
-
- public static void initPlugin(BundleContext context, int maxRequests, List<Pattern> storePatterns) {
- if (instance == null) {
- final Plugin tmp = new Plugin();
- instance.update(maxRequests, storePatterns);
- final Dictionary<String, Object> props = new Hashtable<String, Object>();
- props.put(Constants.SERVICE_DESCRIPTION,
- "Web Console Plugin to display information about recent Sling requests");
- props.put(Constants.SERVICE_VENDOR,
- "The Apache Software Foundation");
- props.put(Constants.SERVICE_PID, tmp.getClass().getName());
- props.put("felix.webconsole.label", LABEL);
- props.put("felix.webconsole.title", "Recent requests");
- props.put("felix.webconsole.category", "Sling");
-
- serviceRegistration = context.registerService(Servlet.class, tmp, props);
- instance = tmp;
- } else {
- instance.update(maxRequests, storePatterns);
- }
- }
-
- public static void destroyPlugin() {
- if (instance != null) {
- try {
- if (serviceRegistration != null) {
- serviceRegistration.unregister();
- serviceRegistration = null;
- }
- } finally {
- instance = null;
- }
- }
- }
-
- public static final class Plugin extends HttpServlet {
-
- private volatile RequestInfoMap requests;
-
- private volatile List<Pattern> storePatterns;
-
- public void update(int maxRequests, List<Pattern> storePatterns) {
- this.requests = (maxRequests > 0)
- ? new RequestInfoMap(maxRequests)
- : null;
- this.storePatterns = storePatterns;
- }
-
- public void deactivate() {
- if (serviceRegistration != null) {
- serviceRegistration.unregister();
- serviceRegistration = null;
- }
-
- clear();
- }
-
- private void addRequest(SlingHttpServletRequest r) {
- if (requests != null) {
- String requestPath = r.getPathInfo();
- boolean accept = true;
- if (storePatterns != null && storePatterns.size() > 0) {
- accept = false;
- for (Pattern pattern : storePatterns) {
- if (pattern.matcher(requestPath).matches()) {
- accept = true;
- break;
- }
- }
- }
-
- if (accept) {
- synchronized (requests) {
- RequestInfo info = new RequestInfo(r);
- requests.put(info.getKey(), info);
- }
- }
- }
- }
-
- private void clear() {
- if (requests != null) {
- synchronized (requests) {
- requests.clear();
- }
- }
- }
-
- private String getLinksTable(String currentRequestIndex) {
- final List<String> links = new ArrayList<String>();
- if (requests != null) {
- synchronized (requests) {
- for (RequestInfo info : requests.values()) {
- final String key = ResponseUtil.escapeXml(info.getKey());
- final boolean isCurrent = info.getKey().equals(
- currentRequestIndex);
- final StringBuilder sb = new StringBuilder();
- sb.append("<span style='white-space: pre; text-align:right; font-size:80%'>");
- sb.append(String.format("%1$8s", key));
- sb.append("</span> ");
- sb.append("<a href='" + LABEL + "?index=" + key + "'>");
- if (isCurrent) {
- sb.append("<b>");
- }
- sb.append(ResponseUtil.escapeXml(info.getLabel()));
- if (isCurrent) {
- sb.append("</b>");
- }
- sb.append("</a> ");
- links.add(sb.toString());
- }
- }
- }
-
- final int nCols = 5;
- while ((links.size() % nCols) != 0) {
- links.add(" ");
- }
-
- final StringBuilder tbl = new StringBuilder();
-
- tbl.append("<table class='nicetable ui-widget'>\n<tr>\n");
- if (links.isEmpty()) {
- tbl.append("No Requests recorded");
- } else {
- int i = 0;
- for (String str : links) {
- if ((i++ % nCols) == 0) {
- tbl.append("</tr>\n<tr>\n");
- }
- tbl.append("<td>");
- tbl.append(str);
- tbl.append("</td>\n");
- }
- }
- tbl.append("</tr>\n");
-
- tbl.append("</table>\n");
- return tbl.toString();
- }
-
- @Override
- protected void doGet(HttpServletRequest req, HttpServletResponse resp)
- throws ServletException, IOException {
-
- // Select request to display
- RequestInfo info = null;
- String key = req.getParameter(INDEX);
- if (key != null && requests != null) {
- synchronized (requests) {
- info = requests.get(key);
- }
- }
-
- final PrintWriter pw = resp.getWriter();
-
- if (requests != null) {
- pw.println("<p class='statline ui-state-highlight'>Recorded "
- + requests.size() + " requests (max: "
- + requests.getMaxSize() + ")</p>");
- } else {
- pw.println("<p class='statline ui-state-highlight'>Request Recording disabled</p>");
- }
-
- pw.println("<div class='ui-widget-header ui-corner-top buttonGroup'>");
- pw.println("<span style='float: left; margin-left: 1em'>Recent Requests</span>");
- pw.println("<form method='POST'><input type='hidden' name='clear' value='clear'><input type='submit' value='Clear' class='ui-state-default ui-corner-all'></form>");
- pw.println("</div>");
-
- pw.println(getLinksTable(key));
- pw.println("<br/>");
-
- if (info != null) {
-
- pw.println("<table class='nicetable ui-widget'>");
-
- // Links to other requests
- pw.println("<thead>");
- pw.println("<tr>");
- pw.printf(
- "<th class='ui-widget-header'>Request %s (%s %s) by %s - RequestProgressTracker Info</th>%n",
- key, ResponseUtil.escapeXml(info.getMethod()),
- ResponseUtil.escapeXml(info.getPathInfo()), ResponseUtil.escapeXml(info.getUser()));
- pw.println("</tr>");
- pw.println("</thead>");
-
- pw.println("<tbody>");
-
- // Request Progress Tracker Info
- pw.println("<tr><td>");
- final Iterator<String> it = info.getTracker().getMessages();
- pw.print("<pre>");
- while (it.hasNext()) {
- pw.print(ResponseUtil.escapeXml(it.next()));
- }
- pw.println("</pre></td></tr>");
- pw.println("</tbody></table>");
- }
- }
-
- @Override
- protected void doPost(HttpServletRequest req, HttpServletResponse resp)
- throws IOException {
- if (req.getParameter(CLEAR) != null) {
- clear();
- resp.sendRedirect(req.getRequestURI());
- }
- }
- }
-
- private static class RequestInfo {
-
- private static AtomicLong requestCounter = new AtomicLong(0);
-
- private final String key;
-
- private final String method;
-
- private final String pathInfo;
-
- private final String user;
-
- private final RequestProgressTracker tracker;
-
- RequestInfo(SlingHttpServletRequest request) {
- this.key = String.valueOf(requestCounter.incrementAndGet());
- this.method = request.getMethod();
- this.pathInfo = request.getPathInfo();
- this.user = request.getRemoteUser();
- this.tracker = request.getRequestProgressTracker();
- }
-
- public String getKey() {
- return key;
- }
-
- public String getMethod() {
- return method;
- }
-
- public String getPathInfo() {
- return pathInfo;
- }
-
- public String getUser() {
- return user;
- }
-
- public String getLabel() {
- final StringBuilder sb = new StringBuilder();
-
- sb.append(getMethod());
- sb.append(' ');
-
- final String path = getPathInfo();
- if (path != null && path.length() > 0) {
- sb.append(ResourceUtil.getName(getPathInfo()));
- } else {
- sb.append('/');
- }
-
- return sb.toString();
- }
-
- public RequestProgressTracker getTracker() {
- return tracker;
- }
- }
-
- private static class RequestInfoMap extends
- LinkedHashMap<String, RequestInfo> {
-
- private int maxSize;
-
- RequestInfoMap(int maxSize) {
- this.maxSize = maxSize;
- }
-
- @Override
- protected boolean removeEldestEntry(
- java.util.Map.Entry<String, RequestInfo> eldest) {
- return size() > maxSize;
- }
-
- public int getMaxSize() {
- return maxSize;
- }
- }
-}
\ No newline at end of file