Packages

  • package root
    Definition Classes
    root
  • package scamper

    At the core Scamper is HttpMessage, which is a trait that defines the fundamental characteristics of an HTTP message.

    HTTP Messages

    At the core Scamper is HttpMessage, which is a trait that defines the fundamental characteristics of an HTTP message. HttpRequest and HttpResponse extend the specification to define characteristics specific to their respective message types.

    An HttpRequest is created using one of the factory methods defined in its companion object. Or you can start with a RequestMethod and use builder methods to further define the request.

    import scamper.Header
    import scamper.Implicits.stringToUri
    import scamper.RequestMethods.GET
    
    val request = GET("/motd").withHeaders(
      Header("Host", "localhost:8080"),
      Header("Accept", "text/plain")
    )
    
    printf("Request Method: %s%n", request.method)
    printf("Target URI: %s%n", request.target)
    
    request.headers.foreach(println)
    
    val host: Option[String] = request.getHeaderValue("Host")

    An HttpResponse is created using one of the factory methods defined in its companion object. Or you can start with a ResponseStatus and use builder methods to further define the response.

    import scamper.{ BodyParsers, Header }
    import scamper.Implicits.stringToEntity
    import scamper.ResponseStatuses.Ok
    
    val response = Ok("There is an answer.").withHeaders(
      Header("Content-Type", "text/plain"),
      Header("Connection", "close")
    )
    
    printf("Status Code: %s%n", response.status.code)
    printf("Reason Phrase: %s%n", response.status.reason)
    
    response.headers.foreach(println)
    
    val contentType: Option[String] = response.getHeaderValue("Content-Type")
    
    implicit val parser = BodyParsers.text()
    
    printf("Body: %s%n", response.as[String])
    Definition Classes
    root
  • package auth

    Provides access to authethentication types and headers.

    Provides access to authethentication types and headers.

    Challenges and Credentials

    When working with authentication, a Challenge is presented in the response, and Credentials in the request. Each of these has an assigned scheme, which is associated with either a token or a set of parameters.

    import scamper.Implicits.stringToUri
    import scamper.RequestMethods.GET
    import scamper.ResponseStatuses.Unauthorized
    import scamper.auth.{ Authorization, Challenge, Credentials, WwwAuthenticate }
    
    // Present response challenge (scheme and parameters)
    val challenge = Challenge("Bearer", "realm" -> "developer")
    val res = Unauthorized().withWwwAuthenticate(challenge)
    
    // Present request credentials (scheme and token)
    val credentials = Credentials("Bearer", "QWxsIEFjY2VzcyEhIQo=")
    val req = GET("/dev/projects").withAuthorization(credentials)
    Basic Authentication

    There are subclasses defined for Basic authentication: BasicChallenge and BasicCredentials.

    import scamper.Implicits.stringToUri
    import scamper.RequestMethods.GET
    import scamper.ResponseStatuses.Unauthorized
    import scamper.auth.{ Authorization, BasicChallenge, BasicCredentials, WwwAuthenticate }
    
    // Provide realm and optional parameters
    val challenge = BasicChallenge("admin", "title" -> "Admin Console")
    val res = Unauthorized().withWwwAuthenticate(challenge)
    
    // Provide user and password
    val credentials = BasicCredentials("sa", "l3tm31n")
    val req = GET("/admin/users").withAuthorization(credentials)

    In addition, there are methods for Basic authentication defined in the header classes.

    import scamper.Implicits.stringToUri
    import scamper.RequestMethods.GET
    import scamper.ResponseStatuses.Unauthorized
    import scamper.auth.{ Authorization, WwwAuthenticate }
    
    // Provide realm and optional parameters
    val res = Unauthorized().withBasic("admin", "title" -> "Admin Console")
    
    // Access basic auth in response
    printf(s"Realm: %s%n", res.basic.realm)
    printf(s"Title: %s%n", res.basic.params("title"))
    
    // Provide user and password
    val req = GET("/admin/users").withBasic("sa", "l3tm3m1n")
    
    // Access basic auth in request
    printf(s"User: %s%n", req.basic.user)
    printf(s"Password: %s%n", req.basic.password)
    Bearer Authentication

    There are subclasses defined for Bearer authentication: BearerChallenge and BearerCredentials. And, similar to Basic, there are Bearer-specific methods available in the header classes.

    import scamper.Implicits.stringToUri
    import scamper.RequestMethods.GET
    import scamper.ResponseStatuses.Unauthorized
    import scamper.auth.{ Authorization, WwwAuthenticate }
    
    // Provide challenge parameters
    val res = Unauthorized().withBearer(
      "scope" -> "user profile",
      "error" -> "invalid_token",
      "error_description" -> "Expired access token"
    )
    
    // Print optional realm parameter
    res.bearer.realm.foreach(println)
    
    // Print scope from space-delimited parameter
    val scope: Seq[String] = res.bearer.scope
    scope.foreach(println)
    
    // Print error parameters
    res.bearer.error.foreach(println)
    res.bearer.errorDescription.foreach(println)
    res.bearer.errorUri.foreach(println)
    
    // Test for error conditions
    println(res.bearer.isInvalidToken)
    println(res.bearer.isInvalidRequest)
    println(res.bearer.isInsufficientScope)
    
    // Create request with Bearer token
    val req = GET("/users").withBearer("R290IDUgb24gaXQhCg==")
  • package client

    Provides HTTP client implementation.

    Provides HTTP client implementation.

    Using HTTP Client

    The HttpClient object can be used to send a request and handle the response.

    import scamper.BodyParsers
    import scamper.Implicits.stringToUri
    import scamper.RequestMethods.GET
    import scamper.client.HttpClient
    
    implicit val parser = BodyParsers.text()
    
    def getMessageOfTheDay(): Either[Int, String] = {
      val req = GET("localhost:8080/motd")
    
      // Send request and handle response
      HttpClient.send(req) { res =>
        res.status.isSuccessful match {
          case true  => Right(res.as[String])
          case false => Left(res.status.code)
        }
      }
    }

    Note the request must be created with an absolute URI to make effective use of the client.

    Creating HTTP Client

    When using the HttpClient object as the client, it creates an instance of HttpClient for one-time usage. If you plan to send multiple requests, you can create and maintain a reference to an instance, and use it as the client. With that, you also get access to methods corresponding to the standard HTTP request methods.

    import scamper.BodyParsers
    import scamper.Implicits.stringToUri
    import scamper.client.HttpClient
    
    implicit val parser = BodyParsers.text()
    
    // Create HttpClient instance
    val client = HttpClient(bufferSize = 4096, readTimeout = 3000)
    
    def getMessageOfTheDay(): Either[Int, String] = {
      // Use client instance
      client.get("http://localhost:8080/motd") { res =>
        res.status.isSuccessful match {
          case true  => Right(res.as[String])
          case false => Left(res.status.code)
        }
      }
    }

    And if the client is declared as an implicit value, you can make use of send() on the request itself.

    import scamper.BodyParsers
    import scamper.Implicits.stringToUri
    import scamper.RequestMethods.GET
    import scamper.client.HttpClient
    import scamper.client.Implicits.ClientHttpRequestType // Adds send method to request
    import scamper.headers.{ Accept, AcceptLanguage }
    import scamper.types.Implicits.{ stringToMediaRange, stringToLanguageRange }
    
    implicit val client = HttpClient(bufferSize = 8192, readTimeout = 1000)
    implicit val parser = BodyParsers.text(4096)
    
    GET("http://localhost:8080/motd")
      .withAccept("text/plain")
      .withAcceptLanguage("en-US; q=0.6", "fr-CA; q=0.4")
      .send(res => println(res.as[String])) // Send request and print response
  • package cookies

    Provides specialized access to message cookies.

    Provides specialized access to message cookies.

    Request Cookies

    In HttpRequest, cookies are stringed together in the Cookie header. You can access them using the extension methods provided by RequestCookies, with each cookie represented as PlainCookie.

    import scamper.Implicits.stringToUri
    import scamper.RequestMethods.GET
    import scamper.cookies.{ PlainCookie, RequestCookies }
    
    // Build request with cookies
    val req = GET("https://localhost:8080/motd").withCookies(
      PlainCookie("ID", "bG9zCg"), PlainCookie("Region", "SE-US")
    )
    
    // Access and print all cookies
    req.cookies.foreach(println)
    
    // Get cookies by name
    val id: Option[PlainCookie] = req.getCookie("ID")
    val region: Option[PlainCookie] = req.getCookie("Region")
    
    // Get cookie values by name
    assert(req.getCookieValue("ID").contains("bG9zCg"))
    assert(req.getCookieValue("Region").contains("SE-US"))
    Response Cookies

    In HttpResponse, the cookies are a collection of Set-Cookie header values. Specialized access is provided by ResponseCookies, with each cookie represented as SetCookie.

    import scamper.Implicits.stringToEntity
    import scamper.ResponseStatuses.Ok
    import scamper.cookies.{ ResponseCookies, SetCookie }
    
    // Build response with cookies
    val res = Ok("There is an answer.").withCookies(
      SetCookie("ID", "bG9zCg", path = Some("/motd"), secure = true),
      SetCookie("Region", "SE-US")
    )
    
    // Access and print all cookies
    res.cookies.foreach(println)
    
    // Get cookies by name
    val id: Option[SetCookie] = res.getCookie("ID")
    val region: Option[SetCookie] = res.getCookie("Region")
    
    // Get attributes of ID cookie
    val path: String = id.flatMap(_.path).getOrElse("/")
    val secure: Boolean = id.map(_.secure).getOrElse(false)
    
    // Get cookie values by name
    assert(res.getCookieValue("ID").contains("bG9zCg"))
    assert(res.getCookieValue("Region").contains("SE-US"))
  • package headers

    Provides specialized access to message headers.

    Provides specialized access to message headers.

    Using Header Classes

    Specialized header access is provided by type classes. Some headers are available to both requests and responses, and others are available only to a specific message type. This behavior is driven by the HTTP specification.

    import scamper.Implicits.stringToUri
    import scamper.RequestMethods.GET
    import scamper.headers.{ Accept, Host }
    import scamper.types.Implicits.stringToMediaRange
    
    // Build request using 'Host' and 'Accept' headers
    val req = GET("/motd").withHost("localhost:8080").withAccept("text/plain")
    
    // Access and print header values
    printf("Host: %s%n", req.host)
    printf("Accept: %s%n", req.accept.head)
  • package logging

    Provides logging facilities.

  • package server

    Provides HTTP server implementation.

    Provides HTTP server implementation.

    Building HTTP Server

    To build a server, you begin with ServerApplication. This is a mutable structure to which you apply changes to configure the server. Once the desired settings are applied, you invoke one of several methods to create the server.

    import java.io.File
    import scamper.BodyParsers
    import scamper.Implicits.{ stringToEntity, inputStreamToEntity }
    import scamper.ResponseStatuses.{ NotFound, Ok }
    import scamper.headers.TransferEncoding
    import scamper.server.HttpServer
    import scamper.server.Implicits.ServerHttpRequestType
    import scamper.types.Implicits.stringToTransferCoding
    
    // Get server application
    val app = HttpServer.app()
    
    // Add request handler to log all requests
    app.request { req =>
      println(req.startLine)
      req
    }
    
    // Add request handler to specific request method and path
    app.get("/about") { req => Ok("This server is powered by Scamper.") }
    
    // Add request handler using path parameter
    app.put("/data/:id") { req =>
      def update(id: Int, data: String): Boolean = ???
    
      implicit val parser = BodyParsers.text()
    
      // Get path parameter
      val id = req.params.getInt("id")
    
      update(id, req.as[String]) match {
        case true  => Ok()
        case false => NotFound()
      }
    }
    
    // Serve static files
    app.files("/main", new File("/path/to/public"))
    
    // Tell server to compress response
    app.response { res =>
      res.withTransferEncoding("gzip", "chunked")
    }
    
    // Create server
    val server = app.create(8080)
    
    printf("Host: %s%n", server.host)
    printf("Port: %d%n", server.port)
    
    Thread.sleep(60 * 1000)
    
    // Close server when done
    server.close()
  • package types

    Defines standardized types for header classes in scamper.headers.

    Defines standardized types for header classes in scamper.headers.

    import scamper.Implicits.{ stringToEntity, stringToUri }
    import scamper.RequestMethods.GET
    import scamper.ResponseStatuses.Ok
    import scamper.headers.{ Accept, ContentType, TransferEncoding }
    import scamper.types.{ MediaRange, MediaType, TransferCoding }
    
    val json = MediaRange("application", "json", 0.9f)
    val html = MediaRange.parse("text/html; q=0.1")
    
    val req = GET("/motd").withAccept(json, html)
    
    val text = MediaType.parse("text/plain")
    val gzip = TransferCoding("gzip")
    
    val res = Ok("There is an answer.").withContentType(text).withTransferEncoding(gzip)

    Using values defined in Implicits, properly formatted strings can be implicitly converted to standardized types.

    import scamper.Implicits.{ stringToEntity, stringToUri }
    import scamper.RequestMethods.GET
    import scamper.ResponseStatuses.Ok
    import scamper.headers.{ Accept, ContentType, TransferEncoding }
    import scamper.types.Implicits._
    
    val req = GET("/motd").withAccept("application/json; q=0.9", "text/html; q=0.1")
    
    val res = Ok("There is an answer.").withContentType("text/plain").withTransferEncoding("gzip")
  • BodyDecoding
  • BodyParser
  • BodyParsers
  • Entity
  • EntityTooLarge
  • FilePart
  • Header
  • HeaderNotFound
  • HttpException
  • HttpMessage
  • HttpRequest
  • HttpResponse
  • HttpVersion
  • Implicits
  • MessageBuilder
  • Multipart
  • Part
  • QueryString
  • ReadLimitExceeded
  • RequestLine
  • RequestMethod
  • RequestMethods
  • ResponseStatus
  • ResponseStatuses
  • StartLine
  • StatusLine
  • TextPart
p

scamper

package scamper

HTTP Messages

At the core Scamper is HttpMessage, which is a trait that defines the fundamental characteristics of an HTTP message. HttpRequest and HttpResponse extend the specification to define characteristics specific to their respective message types.

An HttpRequest is created using one of the factory methods defined in its companion object. Or you can start with a RequestMethod and use builder methods to further define the request.

import scamper.Header
import scamper.Implicits.stringToUri
import scamper.RequestMethods.GET

val request = GET("/motd").withHeaders(
  Header("Host", "localhost:8080"),
  Header("Accept", "text/plain")
)

printf("Request Method: %s%n", request.method)
printf("Target URI: %s%n", request.target)

request.headers.foreach(println)

val host: Option[String] = request.getHeaderValue("Host")

An HttpResponse is created using one of the factory methods defined in its companion object. Or you can start with a ResponseStatus and use builder methods to further define the response.

import scamper.{ BodyParsers, Header }
import scamper.Implicits.stringToEntity
import scamper.ResponseStatuses.Ok

val response = Ok("There is an answer.").withHeaders(
  Header("Content-Type", "text/plain"),
  Header("Connection", "close")
)

printf("Status Code: %s%n", response.status.code)
printf("Reason Phrase: %s%n", response.status.reason)

response.headers.foreach(println)

val contentType: Option[String] = response.getHeaderValue("Content-Type")

implicit val parser = BodyParsers.text()

printf("Body: %s%n", response.as[String])
Linear Supertypes
AnyRef, Any
Ordering
  1. Alphabetic
  2. By Inheritance
Inherited
  1. scamper
  2. AnyRef
  3. Any
  1. Hide All
  2. Show All
Visibility
  1. Public
  2. All

Type Members

  1. trait BodyDecoding extends AnyRef

    A mixin providing access to decoded message body.

  2. trait BodyParser[T] extends AnyRef

    Provides utility for parsing HTTP message body.

    Provides utility for parsing HTTP message body.

    See also

    BodyParsers

  3. trait Entity extends AnyRef

    Representation of message body.

  4. case class EntityTooLarge(limit: Long) extends HttpException with Product with Serializable

    Indicates entity exceeds established limit.

    Indicates entity exceeds established limit.

    EntityTooLarge is a complement to ReadLimitExceeded. Whereas ReadLimitExceeded applies to the raw bytes of an input stream, EntityTooLarge pertains to the entity itself, potentially subjected to decompression.

    See also

    ReadLimitExceeded

  5. trait FilePart extends Part

    Represents file content in multipart form data.

    Represents file content in multipart form data.

    See also

    TextPart

  6. trait Header extends AnyRef

    HTTP header

  7. case class HeaderNotFound(name: String) extends HttpException with Product with Serializable

    Indicates absence of specified header.

  8. class HttpException extends RuntimeException

    Indicates exception in HTTP processing.

  9. trait HttpMessage extends AnyRef

    HTTP message

  10. trait HttpRequest extends HttpMessage with MessageBuilder[HttpRequest]

    HTTP request

    HTTP request

    See also

    HttpResponse

  11. trait HttpResponse extends HttpMessage with MessageBuilder[HttpResponse]

    HTTP response

    HTTP response

    See also

    HttpRequest

  12. trait HttpVersion extends AnyRef

    HTTP version

  13. trait MessageBuilder[T <: HttpMessage] extends AnyRef

    Provides builder pattern for HTTP message.

  14. trait Multipart extends AnyRef

    Represents multipart form data.

    Represents multipart form data.

    See also

    Part

  15. trait Part extends AnyRef

    Represents part in multipart form data.

    Represents part in multipart form data.

    See also

    Multipart

  16. trait QueryString extends AnyRef

    Represents query string as mapped parameters.

  17. case class ReadLimitExceeded(limit: Long) extends IOException with Product with Serializable

    Indicates attempt to read beyond an InputStream's established limit.

    Indicates attempt to read beyond an InputStream's established limit.

    ReadLimitExceeded is a complement to EntityTooLarge. Whereas ReadLimitExceeded applies to the raw bytes of an input stream, EntityTooLarge pertains to the entity itself, potentially subjected to decompression.

    See also

    EntityTooLarge

  18. trait RequestLine extends StartLine

    HTTP request line

    HTTP request line

    See also

    StatusLine

  19. trait RequestMethod extends AnyRef

    HTTP request method

    HTTP request method

    See also

    RequestMethods

  20. trait ResponseStatus extends AnyRef

    HTTP response status

    HTTP response status

    See also

    ResponseStatuses

  21. trait StartLine extends AnyRef

    HTTP message start line

  22. trait StatusLine extends StartLine

    HTTP status line

    HTTP status line

    See also

    RequestLine

  23. trait TextPart extends Part

    Represents text content in multipart form data.

    Represents text content in multipart form data.

    See also

    FilePart

Value Members

  1. object BodyParsers

    Includes default body parser implementations.

  2. object Entity

    Provides factory for Entity.

  3. object FilePart

    Provides factory for FilePart.

  4. object Header

    Provided for factory for Header.

  5. object HttpRequest

    HttpRequest factory

  6. object HttpResponse

    HttpResponse factory

  7. object HttpVersion

    HttpVersion factory

  8. object Implicits

    Includes implicit converter functions.

  9. object Multipart

    Provides factory for Multipart.

  10. object QueryString

    Provides factory methods for QueryString.

  11. object RequestLine

    RequestLine factory

  12. object RequestMethod

    Provided factory for RequestMethod.

    Provided factory for RequestMethod.

    See also

    RequestMethods

  13. object RequestMethods

    Includes registered request methods.

  14. object ResponseStatus

    Provided factory for ResponseStatus.

    Provided factory for ResponseStatus.

    See also

    ResponseStatuses

  15. object ResponseStatuses

    Includes standard HTTP statuses.

  16. object StatusLine

    StatusLine factory

  17. object TextPart

    Provides factory for TextPart.

Inherited from AnyRef

Inherited from Any

Ungrouped