You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@sling.apache.org by Alexander Klimetschek <ak...@day.com> on 2009/02/11 16:24:34 UTC

Servlet handling POST/PUT for non-existing resources?

Hi all,

when working on "Import" servlets I stumbled upon the problem that
servlets registered under selectors don't get called for non-existing
resources.

The use case is that you POST or PUT a file to a certain path, eg.
/content/foo/i18n, which does not exist yet, and there should be a
servlet handling the import and create a custom jcr node structure
from the file contents (eg. an i18n dictionary in the example).

Now in current Sling, if you register the servlet for the
"sling/servlet/default" resource type and make it handle a special
selector (say "i18n"), it won't get triggered if the path does not
exist, but rather the standard sling POST servlet is triggered and
creates unwanted nodes/properties depending of the request's contents.
It would be cool to get the NonExistingResource in the servlet and
have the servlet create the path itself.

Did I miss something or is this really not possible at the moment? And
if not, would it make sense to change the servlet resolution for that
case?

Regards,
Alex

-- 
Alexander Klimetschek
alexander.klimetschek@day.com

Re: Servlet handling POST/PUT for non-existing resources?

Posted by Alexander Klimetschek <ak...@day.com>.
On Thu, Feb 12, 2009 at 8:39 AM, Felix Meschberger <fm...@gmail.com> wrote:
> Using the absolute path mechanism you can do that: just register the
> servlet for two paths, say:
>
>    /apps/sling/nonexisting/i18n.servlet
>    /apps/i18n/dictionary.servlet
>
> This should do the trick. I fear, though, that selectors and extensions
> are no supported on non existing resources, since Sling does not apply
> wild guessing (any more) as to how long the resource path is and where
> selectors and extensions start.

Thanks, I got it now working. But with sling/nonexisting I face a
serious problem now: since it does not parse any extension or
selectors, the servlet resolution for it will also only allow for
exactly one POST servlet: /apps/sling/nonexisting/POST.servlet (also
exactly one for GET, PUT etc.).

Using an extension or selector in that servlet path, eg.
/apps/sling/nonexisting/POST.ics.servlet, does not work, because Sling
won't even pick it up. This makes the sling/nonexisting not very
flexible, because you can only have one to handle it, even the
OptingServlet does not help, because the list of candidates will only
contain the "winner" of the /apps/sling/nonexisting/POST.servlet path
+ the webdav servlet as fallback. But I think it is feasible to allow
for different "importer" servlets that act on the extension (or
additionally selectors), eg. importing /content/translations.xliff,
/content/calendar.ics, /content/whatever.ext.

Therefore I would suggest to "turn around" the non-existing path
parsing case and instead of assuming the full URL to be the resource
path and setting selectors and extension to null, just use the part
after the last "." as extension and the previous parts as selectors.
If you want a different handling, you can still register for
sling/nonexisting and create a resource based on the full path anyway
- sling would not force what resource you create, only how the
servlets are resolved.

WDYT?

Regards,
Alex

-- 
Alexander Klimetschek
alexander.klimetschek@day.com

Re: Servlet handling POST/PUT for non-existing resources?

Posted by Felix Meschberger <fm...@gmail.com>.
Hi,

Alexander Klimetschek schrieb:
> Hi Felix!
> 
> On Wed, Feb 11, 2009 at 6:45 PM, Felix Meschberger <fm...@gmail.com> wrote:
>> Well, the mention of the NonExistingResource may be the key in your use
>> case: Since NonExistingResources have their own resource type
>> (sling:nonexisting IIRC), you may register a servlet for that resource
>> type and act upon it as desired. If you don't want to handle the
>> concrete request for any one reason, you can -- as a servlet --
>> implement the OptingServlet interface and return false on the respective
>> method.
> 
> Ah, that concept totally makes sense. Didn't thought so far ;-)
> 
> This probably means I would need two different servlets if I want to
> handle both requests to non-existing resources and to existing ones,
> where the servlet would "update" an existing import. With the scr
> javadoc annotations, one can only register the servlet for one
> resource type / selector combination at a time, right? (eg. 1)
> resource type = "sling:nonexisting", selector = "i18n" and 2) resource
> type = "i18n/dictionary" in my example).

Using the absolute path mechanism you can do that: just register the
servlet for two paths, say:

    /apps/sling/nonexisting/i18n.servlet
    /apps/i18n/dictionary.servlet

This should do the trick. I fear, though, that selectors and extensions
are no supported on non existing resources, since Sling does not apply
wild guessing (any more) as to how long the resource path is and where
selectors and extensions start.

Regards
Felix

> 
> 
>> I am not a big fan of extending or changing the servlet resolution just
>> for this.
>>
>> What we might do is provide some plugin functionality based on the
>> sling:nonexisting resource type, where one might register its interest
>> in handling requests to such resources.
> 
> The sling:nonexisting mechanism makes sense for that case, so we don't
> have to change the servlet resolution. The only thing that might be
> needed is registering a single servlet for multiple
> resources/paths/selectors etc. Is that possible?
> 
> Regards,
> Alex
> 

Re: Servlet handling POST/PUT for non-existing resources?

Posted by Alexander Klimetschek <ak...@day.com>.
Hi Felix!

On Wed, Feb 11, 2009 at 6:45 PM, Felix Meschberger <fm...@gmail.com> wrote:
> Well, the mention of the NonExistingResource may be the key in your use
> case: Since NonExistingResources have their own resource type
> (sling:nonexisting IIRC), you may register a servlet for that resource
> type and act upon it as desired. If you don't want to handle the
> concrete request for any one reason, you can -- as a servlet --
> implement the OptingServlet interface and return false on the respective
> method.

Ah, that concept totally makes sense. Didn't thought so far ;-)

This probably means I would need two different servlets if I want to
handle both requests to non-existing resources and to existing ones,
where the servlet would "update" an existing import. With the scr
javadoc annotations, one can only register the servlet for one
resource type / selector combination at a time, right? (eg. 1)
resource type = "sling:nonexisting", selector = "i18n" and 2) resource
type = "i18n/dictionary" in my example).


> I am not a big fan of extending or changing the servlet resolution just
> for this.
>
> What we might do is provide some plugin functionality based on the
> sling:nonexisting resource type, where one might register its interest
> in handling requests to such resources.

The sling:nonexisting mechanism makes sense for that case, so we don't
have to change the servlet resolution. The only thing that might be
needed is registering a single servlet for multiple
resources/paths/selectors etc. Is that possible?

Regards,
Alex

-- 
Alexander Klimetschek
alexander.klimetschek@day.com

Re: Servlet handling POST/PUT for non-existing resources?

Posted by Felix Meschberger <fm...@gmail.com>.
Hi,

Alexander Klimetschek schrieb:
> Hi all,
> 
> when working on "Import" servlets I stumbled upon the problem that
> servlets registered under selectors don't get called for non-existing
> resources.
> 
> The use case is that you POST or PUT a file to a certain path, eg.
> /content/foo/i18n, which does not exist yet, and there should be a
> servlet handling the import and create a custom jcr node structure
> from the file contents (eg. an i18n dictionary in the example).
> 
> Now in current Sling, if you register the servlet for the
> "sling/servlet/default" resource type and make it handle a special
> selector (say "i18n"), it won't get triggered if the path does not
> exist, but rather the standard sling POST servlet is triggered and
> creates unwanted nodes/properties depending of the request's contents.
> It would be cool to get the NonExistingResource in the servlet and
> have the servlet create the path itself.

Well, the mention of the NonExistingResource may be the key in your use
case: Since NonExistingResources have their own resource type
(sling:nonexisting IIRC), you may register a servlet for that resource
type and act upon it as desired. If you don't want to handle the
concrete request for any one reason, you can -- as a servlet --
implement the OptingServlet interface and return false on the respective
method.

It is a bit hacky, but it should work -- the problem is, that it is
limited to your special use case.

> 
> Did I miss something or is this really not possible at the moment? And
> if not, would it make sense to change the servlet resolution for that
> case?

I am not a big fan of extending or changing the servlet resolution just
for this.

What we might do is provide some plugin functionality based on the
sling:nonexisting resource type, where one might register its interest
in handling requests to such resources.


Regards
Felix