除了扩展 SlingPostServlet 之外,还有更好的选择吗?

Is there a better alternative to extending the SlingPostServlet?

在 Sling 应用程序中,我想确保使用特定 sling:resourceType 创建的节点始终具有使用特定属性创建的子节点。实现此目标的方式符合最佳实践?

  1. 扩展 SlingPostServlet class 并添加功能以在 doPost() 方法中添加子节点。这看起来很合适,因为乍一看,可以 link 特定资源类型的 servlet,然后调用 super.doPost() 以使用默认的 SlingPostServlet 处理。但是,在安装捆绑包时,org.apache.sling.servlets.post.impl 无法解析 (a similar problem was encountered by another user),这完全阻止了捆绑包 运行。

  2. 正在创建 SlingPostProcessor 并在 process() 方法中添加功能。这似乎不太理想,因为它不依赖于一种特定的资源类型。

  3. 使用Sling Eventing.

我想避免扩展 SlingAllMethodsServlet,因为它有助于保持对 SlingPostServlet 中所有默认功能的访问。但是,是否有可能扩展 SlingPostServlet,而不是 SlingAllMethodsServlet

我认为没有一种简单的解决方案可以将该行为绑定到单个资源类型。您将需要检查新资源并在需要时应用您的更改。 我认为两个最佳选择是您提到的 SlingPostProcessor 和 Resource observation.

资源观察允许您'listen'了解资源的变化并执行您认为合适的任何操作。

实现也相当简单。创建一个实现 ResourceChangeListener 接口的新 OSGi 服务,并添加一些属性来过滤您感兴趣的更改类型。这类似于使用 JCR 事件和作业,但更直接。

这样做的好处是它独立于任何 post 请求。缺点是您需要使用新会话来执行更改。 (您可以使用 ResourceResolverFactory.getServiceResourceResolver

例如

@Component(property = {
    ResourceChangeListener.CHANGES + "=ADDED",
    ResourceChangeListener.PATHS + "=glob:/content/*",
})
public class ResourceObserver implements ResourceChangeListener {

  @Override
  public void onChange(@Nonnull List<ResourceChange> changes) {
      //go through the list of changes and do what you need to do.
  }
}