Over a million developers have joined DZone.

Basic WS with Scala, Sbt and JEE 6

DZone's Guide to

Basic WS with Scala, Sbt and JEE 6

· Java Zone ·
Free Resource

Verify, standardize, and correct the Big 4 + more– name, email, phone and global addresses – try our Data Quality APIs now at Melissa Developer Portal!

I recently had a chance to work on building an SOA platform using JEE 6 and Scala. I will share here some snippets that may be helpfull to start publishing web services using Scala, Sbt and JAX-WS.

Consider the example to calculate the quotient and remainder using a euclidean algorithm. Not very complex if the inputs are positives numbers.

I- Sbt

Let’s create an sbt projet and add required dependencies

$ mkdir sws
$ cd sws
$ touch build.sbt
$ edit build.sbt as following :

name := "Euclide"

version := "1.0"

organization := "me.ouertani"

scalaVersion := "2.9.1"

scalaSource in Compile <<= baseDirectory(_ / "src")

scalaSource in Test <<= baseDirectory(_ / "test")

libraryDependencies += "javax" % "javaee-api" % "6.0" % "provided" 

libraryDependencies += "log4j" % "log4j" % "1.2.16" % "provided" 

libraryDependencies += "junit" % "junit" % "4.8.2" % "test"

$ mkdir src
$ touch src/Euclide.scala

That’a all for project configuration.

II- Create the WS

We will use a single Euclide.scala file for all class this will be easier for visibility

1 – Create a Request Class and don’t forget :
a – default constructor
b – field access annotation

case class Request(a : Int, b : Int ){ def this(){this(0,0)}}

2- Create a Response Class

@XmlType(name = "output")
case class Response (c: Int, d: Int){ def this(){this(0,0)}}

3- Why not create an exception class to handle exceptions like b is equal to 0?

case class ResponseException(why : String){  def this(){this("")}}

case class FaultResponse(@BeanProperty faultInfo : ResponseException) extends Exception { def this(){this(ResponseException(""))}}

Don’t forget to add BeanProperty annotation to faultInfo input !

4- Let’s add an interceptor to log all ws method call

object TracingInterceptor{
  import org.apache.log4j.Logger
  val L = Logger.getLogger(classOf[TracingInterceptor])

import TracingInterceptor._
class TracingInterceptor { 

  def  log( context:InvocationContext):Object ={
    try {
      if (L.isDebugEnabled()) {
        val clazz = context.getMethod().getDeclaringClass().getName()
        val method = context.getMethod().getName()        
        L.debug(clazz + " : Is invoking method: " + method + " With Parameters : " + context.getParameters().mkString("[", ",","]"))
    } catch { 
      case  ex :Exception =>    L.warn("Unable to Intercept Method Call", ex)

5- The WS class and it’s divide method using intercpetor and stateless EJB 3.1

@WebService(serviceName = "Euclide", targetNamespace = "http://slim.ouertani.me/")
class Euclide {
  def divide( @WebParam(name="input" )  @XmlElement(required = true, nillable = false)
    req :Request):Response =  req match {
      case Request(_, 0 ) => throw FaultResponse(ResponseException("Can't divide by ZERO!"))
      case Request(a, b ) =>  Response(a / b ,a % b) 

6- Don’t forget package , imports at the head of file and it’s all :

package me.ouertani.scala.ws

import javax.interceptor.Interceptors
import javax.xml.bind.annotation.XmlElement
import javax.interceptor.{ AroundInvoke , InvocationContext }
import javax.xml.bind.annotation. { XmlAccessType , XmlAccessorType, XmlElement, XmlType}
import javax.ejb. { EJB ,Stateless }
import javax.jws. {WebService , WebParam }
import scala.reflect.BeanProperty

III- packaging and run WS

1- Let’s start compiling our projet
$ xsbt compile
2- package the jar
$ xsbt package
3- deploy it to your JEE 6 container ( mine is Glassfish 3.1.1 )

IV – test it
1- After depoyed let’s test it using soapUI tool

Request 1 :

<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:slim="http://slim.ouertani.me/">


Response 1 :

<S:Envelope xmlns:S="http://schemas.xmlsoap.org/soap/envelope/">
      <ns2:divideResponse xmlns:ns2="http://slim.ouertani.me/">

Request 2 :

<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:slim="http://slim.ouertani.me/">

Response 2 :

<S:Envelope xmlns:S="http://schemas.xmlsoap.org/soap/envelope/">
      <S:Fault xmlns:ns4="http://www.w3.org/2003/05/soap-envelope">
            <ns2:FaultResponse xmlns:ns2="http://slim.ouertani.me/">
                  <why>Can't divide by ZERO!</why>


Developers! Quickly and easily gain access to the tools and information you need! Explore, test and combine our data quality APIs at Melissa Developer Portal – home to tools that save time and boost revenue. Our APIs verify, standardize, and correct the Big 4 + more – name, email, phone and global addresses – to ensure accurate delivery, prevent blacklisting and identify risks in real-time.


Opinions expressed by DZone contributors are their own.

{{ parent.title || parent.header.title}}

{{ parent.tldr }}

{{ parent.urlSource.name }}