Spray routing multiple depth paths
Asked Answered
H

1

6

I have 4 levels of response based on URL. So for:
* GET on /abc -> response should be abc
* GET on /abc/def -> response should be def
* GET on /abc/def/ghi -> response should be ghi
* GET on /abc/def/ghi/jkl -> response should be (surprisingly) jkl

So my question is how to design that kind of request-response property with Spray.io?

I know that using pathPrefix with path is possible but that is only for two levels? With that kind of approach it should look something like:

val route = {
  path("/abc") {
    // complete with response 'abc'
  } ~
  path("/abc/def") {
    // complete with response 'def'
  } ~
  path("/abc/def/ghi") {
    // complete with response 'ghi'
  } ~
  path("/abc/def/ghi/jkl") {
    // complete with response 'jkl'
  }
}

Is there any way to "nest paths"? I know this is not working but just an idea like:

val route = {
  path("/abc") {
    // complete with response 'abc'
    'sub'path("/def") {
      // complete with response 'def'
      'sub'path("/ghi") {
        // complete with response 'ghi'
        'sub'path("/jkl") {
          // complete with response 'jkl'
        }
      }
    }
  }
}

Or any other proper way of nesting paths?

Best, zmeda

Hilaryhilbert answered 28/2, 2014 at 15:20 Comment(2)
Your first example wouldn't work at all because you need to break out paths as path("abc" / "def" / "ghi") etc.Larrylars
What do you mean by "I know that using pathPrefix with path is possible but that is only for two levels" ? You can nest pathPrefix as deep as you want, just make sure to use path on the innermost level.Larrylars
L
13

I think the question is about how to do both, complete with something on one level if the path is finished or go one level deeper if there's still more path available.

Try this:

val route = {
  pathPrefix("abc") {
    // complete with response 'abc'
    pathEnd { complete("abc") } ~ // don't forget the twiggles
    pathPrefix("def") {
      pathEnd { complete("def") } ~
      pathPrefix("ghi") {
        pathEnd { complete("ghi") } ~
        path("jkl") { // path already includes pathEnd, path(x) = pathPrefix(x ~ PathEnd)
          complete("jkl")
        }
      }
    }
  }
}

Btw. this doesn't match "/abc/" etc., i.e. a path with a trailing slash. If you want to match trailing slashes mandatorily or optionally use pathSingleSlash or pathEndOrSingleSlash instead of pathEnd.

Larrylars answered 28/2, 2014 at 15:59 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.