CQ中的Sling Servlet - 资源不可修改

时间:2014-04-19 19:07:05

标签: servlets osgi cq5 sling aem

我在CQ中遇到了Sling Servelt的一些问题。虽然rquest the servlet我得到一个例外

    Caused by: org.apache.sling.api.resource.PersistenceException: Resource at '/bin/feedServlet' is not modifiable.
    at org.apache.sling.servlets.post.impl.helper.SlingPropertyValueHandler.setProperty(SlingPropertyValueHandler.java:153)
    at org.apache.sling.servlets.post.impl.operations.ModifyOperation.writeContent(ModifyOperation.java:411)
    at org.apache.sling.servlets.post.impl.operations.ModifyOperation.doRun(ModifyOperation.java:101)

在servlet中,我正在尝试使用“@Reference”注释注入2个服务。

请给我一些解决这个问题的建议。请在下面找到我的Servlet代码(不完整)

    @Component(immediate = true, metatype = false, label = "feedServlet")
@Service(Servlet.class)
@Properties(value = { @org.apache.felix.scr.annotations.Property(name = "sling.servlet.methods", value = "POST"),
        @org.apache.felix.scr.annotations.Property(name = "sling.servlet.paths", value = "/bin/feedServlet") })
public class FeedServlet extends SlingAllMethodsServlet {
    private static final long serialVersionUID = -2139716879248038562L;
     @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY, policy = ReferencePolicy.STATIC)
     private ContentSearchService searchService;

     @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY, policy = ReferencePolicy.STATIC)
     private FeedGeneratorService feedService;

    @Override
    protected void doPost(SlingHttpServletRequest request, SlingHttpServletResponse response) throws ServerException,
            IOException {
         ResourceResolver resourceResolver = request.getResourceResolver();
         List<Hit> list = null;
         String feed = null;
        try {
         list = search(request, searchService);
         feed = feedService.generateFeed(list, resourceResolver);
         } catch (Throwable e) {
         }
        response.getWriter().write(feed);
    }

注意:如果没有这些服务,servlet现在工作正常(previous thread)。这是依赖注入的问题吗?此捆绑包的serviceComponets.xml将这些服务定义为

    <scr:component enabled="true" immediate="true" name="com.acme.wcm.cq.servlet.FeedServlet">
        <implementation class="com.acme.wcm.cq.servlet.FeedServlet"/>
        <service servicefactory="false">
            <provide interface="javax.servlet.Servlet"/>
        </service>
        <property name="sling.servlet.methods" type="String" value="POST"/>
        <property name="sling.servlet.paths" type="String" value="/bin/feedServlet"/>
        <property name="service.pid" value="com.acme.wcm.cq.servlet.FeedServlet"/>
        <reference name="searchService" interface="com.acme.wcm.cq.search.ContentSearchService" cardinality="1..1" policy="static" bind="bindSearchService" unbind="unbindSearchService"/>
        <reference name="feedService" interface="com.acme.wcm.cq.feed.FeedGeneratorService" cardinality="1..1" policy="static" bind="bindFeedService" unbind="unbindFeedService"/>
    </scr:component>

2 个答案:

答案 0 :(得分:2)

我认为您发出的POST请求并非由您的servlet处理。

查看SlingProprtyValueHandler的代码: src of SlingProprtyValueHandler

CQ没有使用您的servlet,所以它在/#34; / bin / feedServlet&#34;有一个资源,它试图修改它(因为它是一个POST请求),但没有任何资源,这就是你得到异常的原因。

请为您的serlvet创建一个doGet方法并尝试发出get请求,我相信它不会起作用。

在/ system / console / components下检查您的servlet是否处于活动状态。

您还可以检查/ system / console / configMgr / check&#34; Apache Sling Servlet / Script Resolver和Error Handler&#34;是否允许/ bin路径。

我希望这有帮助!

P.S。最好将servlet映射到资源而不是路径。示例代码how to map a servlet to a resource

因此,您可以创建/ etc / myApp / services之类的路径,并且在此路径下,您可以使用类似etc / myApp / services / myService的类型创建myService节点,并且可以将servlet映射到此资源类型。 / p>

答案 1 :(得分:1)

我遇到了类似的问题,其中maven-scr-plugin没有为@Reference属性生成绑定/取消绑定方法。当我部署捆绑包时,在服务器端日志中这样说,因此servlet从未注册过,因此CQ不知道如何处理您的请求。

一个解决方法是手动生成bind / unbind方法。

另一个修复是更新maven-scr-plugin版本和org.apache.felix.scr.annotations依赖项。请参阅this post