Menu

Rate this page:

Thanks for rating this page!

We are always striving to improve our documentation quality, and your feedback is valuable to us. How could this documentation serve you better?

Usage and Migration Guide for Twilio's Java Helper Library 7.x

Deprecation notice: New functionality will only be added to the new libraries (Java 7.x). The old libraries (Java 6.x) are deprecated and Twilio will no longer provide bug fixes. Support might ask you to upgrade before debugging issues.

The Twilio Java SDK has undergone significant changes from version 6.x to 7.x - we'll break down the major changes here to make migrating to the new version as painless as possible. If you're integrating Twilio in your Java app for the first time, you can skip straight to the install page.

Java Version Compatibility

The 7.x version of the Twilio SDK is compatible with Java versions 7 and higher.

Import

In prior versions of the Twilio Java SDK, you would import clients like this:

import com.twilio.sdk.LookupsClient;
import com.twilio.sdk.TwilioIPMessagingClient;
import com.twilio.sdk.TwilioRestClient;

In 7.x there is only one Twilio.

import com.twilio.Twilio;

You can initialize Twilio by using:

Twilio.init(ACCOUNT_SID, AUTH_TOKEN);

Actions

Performing actions with 7.x has been abstracted into 5 distinct types: Fetcher, Creator, Updater, Deleter, and Reader.

These actions can be created by calling the fetch, create, update, delete, and read static methods on the resource class. Only at this point HTTP requests are being made. This allows for better network efficiency and makes it clear when the library will perform HTTP requests.

Fetcher

To get an instance of a resource, use a fetcher:

import com.twilio.Twilio;
import com.twilio.rest.api.v2010.account.Message;
...

Twilio.init(ACCOUNT_SID, AUTH_TOKEN);
Message message = Message.fetcher("SMXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX").fetch();

System.out.println("message sid: " + message.getSid());
// message sid: SMXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX

Creator

To make a new instance of a resource, use a creator:

import com.twilio.Twilio;
import com.twilio.rest.api.v2010.account.Message;
import com.twilio.type.PhoneNumber;
...

Twilio.init(ACCOUNT_SID, AUTH_TOKEN);
Message message = Message.creator(
    new PhoneNumber("+15558675309"),
    new PhoneNumber("+15017250604"),
    "Hello world!"
).create();

System.out.println("message body: " + message.getBody());
// message body: Hello world!

Updater

To modify an instance of a resource, use an updater:

import com.twilio.Twilio;
import com.twilio.rest.api.v2010.account.Message;
import com.twilio.type.PhoneNumber;
...

Twilio.init(ACCOUNT_SID, AUTH_TOKEN);

// First, create a new message we can work with:
Message message = Message.creator(
    new PhoneNumber("+15558675309"),
    new PhoneNumber("+15017250604"),
    "Hello world!"
).create();

System.out.println("message sid: " + message.getSid());
// message sid: SMXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX

System.out.println("message body: " + message.getBody());
// message body: Hello world!

// Now use an updater to modify the body of the message
// (redacting the message with empty body)
Message updatedMessage = Message.updater(message.getSid())
    .setBody("")
    .update();

System.out.println("message sid: " + updatedMessage.getSid());
// message sid: SMXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX

System.out.println("message body: " + updatedMessage.getBody());
// message body: 

Deleter

To remove an instance of a resource, use a deleter:

import com.twilio.Twilio;
import com.twilio.rest.api.v2010.account.Message;
...

Twilio.init(ACCOUNT_SID, AUTH_TOKEN);
boolean deleted = Message.deleter("SMXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX").delete();

System.out.println(deleted);
// true

Reader

To list resources, use a reader:

import com.twilio.Twilio;
import com.twilio.rest.api.v2010.account.Message;
...

Twilio.init(ACCOUNT_SID, AUTH_TOKEN);
Iterable<Message> messages = Message.reader().read();
for (Message message : messages) {
   System.out.println("message sid: " + message.getSid());
   // message sid: SMXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
}

Paging

7.x now handles paging for you. As you iterate over the Iterable it will fetch the next page as necessary. For further customization, you may use setPageSize on the Reader action to set the size of each page that is fetched.

Builders

7.x now uses the Builder pattern. This uses the type system to expose what parameters can be used when Creating or Updating a resource.

In older versions of the library, all that was provided to the user was:

public void update(Map<String, String> params)

While this may work, this isn't self-documenting. You don't know what you can pass into this request. For example, we could do:

Map<String, String> params = new HashMap<>();
params.put("foo", "bar");

resource.update(params);

The older versions of the Java SDK would accept this and continue on to the HTTP request that would do nothing.

Now, 7.x only allows you to pass parameters that are supported. For example, the Updater action for a Message has the following method:

public MessageUpdater setBody(String body)

This makes it clear that the only field you can update on an existing message is the Body field. On the other hand, the Creator has these methods:

public MessageCreator setStatusCallback(URI statusCallback)
public MessageCreator setStatusCallback(String statusCallback)
public MessageCreator setApplicationSid(String applicationSid)
public MessageCreator setMaxPrice(BigDecimal maxPrice)
public MessageCreator setProvideFeedback(Boolean provideFeedback)
public MessageCreator setFrom(PhoneNumber from)
public MessageCreator setMessagingServiceSid(String messagingServiceSid)
public MessageCreator setBody(String body)
public MessageCreator setMediaUrl(List<URI> mediaUrl)
public MessageCreator setMediaUrl(URI mediaUrl)
public MessageCreator setMediaUrl(String mediaUrl)

Here's an example showing how you can instantiate a Creator, set any parameters on it you wish, and then call Create:

import com.twilio.Twilio;
import com.twilio.rest.api.v2010.account.Message;
import com.twilio.type.PhoneNumber;
...

Twilio.init(ACCOUNT_SID, AUTH_TOKEN);
Message message = Message.creator(
        new PhoneNumber("+15558675309"),
        new PhoneNumber("+15017250604"),
        "This is the ship that made the Kessel Run in fourteen parsecs?"
        )
    .setMediaUrl("https://c1.staticflickr.com/3/2899/14341091933_1e92e62d12_b.jpg")
    .create();

Exposed Actions

7.x only exposes the Actions that a Resources supports. For example, the request below would be an accepted action in older versions:

LookupsClient lc = new LookupsClient(ACCOUNT_SID, AUTH_TOKEN);
PhoneNumber number = lc.getPhoneNumber("+18089263410");
number.update(new HashMap<String, String>());

This request would throw an Exception, as updating a PhoneNumber is not allowed through the Twilio API.

In 7.x, this is not allowed because there is no Updater for the PhoneNumber class.

TwiML

7.x has also moved TwiML creation to the builder pattern.

Attributes

It only allows you to set attributes that are supported by the TwiML resource. In the older versions of the SDK you could set any arbitrary attribute on an element whether or not it causes any action. For example, in the old library, this was acceptable:

Say say = new Say();
say.set("foo", "bar");

The builder in 7.x only supports the attributes that Say will accept:

public static class Builder {
    public Builder loop(int loop)
    public Builder language(Language language)
    public Builder voice(Voice voice)
    public Say build()
}

Elements

By using the builder pattern, we can guarantee valid child elements at compile time. Now you will no longer have to deal with potential TwiMLExceptions due to adding child elements.

Voice TwiML

The TwiMLResponse class has been replaced by VoiceResponse and MessagingResponse, each one encapsulating the relevant functionality for voice and messaging TwiML generation.

Apart from the builder pattern, another change in version 7.x regarding TwiML is the use of enums for certain attributes. Below you can see this change for a basic Say TwiML VoiceResponse:

Loading Code Sample...
      
      
          
          
          
          
        

      Nesting verbs now also takes advantage of the builder pattern, as you can see in the example below.

      Loading Code Sample...
          
          
              
              
              
              
            

          Messaging TwiML

          MessagingResponse works in a similar way as VoiceResponse, check a basic example below.

          Loading Code Sample...
              
              
                  
                  
                  
                  
                

              And another example with nested verbs.

              Loading Code Sample...
                  
                  
                      
                      
                      
                      
                    

                  Generating TwiML in Your Apps

                  For a full example of generating TwiML, check out our guides Respond to Incoming Phone Calls and Receive and Reply to SMS and MMS Messages.

                  Exceptions

                  7.x has added more descriptive exception types.

                  Twilio Client

                  In version 6.x, client authentication issues were handled with the generic TwilioRestException and only when an api call was made:

                  import com.twilio.sdk.TwilioRestClient;
                  import com.twilio.sdk.resource.instance.*;
                  import com.twilio.sdk.TwilioRestException;
                  
                  public class Example { 
                  
                    private static final String ACCOUNT_SID = "ACXXX";
                    private static final String AUTH_TOKEN = "xxxxx";
                  
                    Account getAccount() throws TwilioRestException {
                       TwilioRestClient client = new TwilioRestClient(ACCOUNT_SID, AUTH_TOKEN);
                  
                       return client.getAccount();
                    } 
                  } 
                  

                  In version 7.x you can see that authentication exceptions can be handled when initializing the client with AuthenticationException:

                  import com.twilio.Twilio;
                  import com.twilio.exception.AuthenticationException;
                  
                  public class Example { 
                  
                    private static final String ACCOUNT_SID = "ACXXX";
                    private static final String AUTH_TOKEN = "xxxxx";
                  
                    void setupClient() throws AuthenticationException { 
                       Twilio.init(ACCOUNT_SID, AUTH_TOKEN);
                    } 
                  } 
                  

                  Actions

                  As with the TwilioRestClient in version 6.x, Factories used the same TwilioRestException. In version 7.x, you can see that more fine grained exceptions are available. In this case, Message.creator throws TwilioException.

                  import com.twilio.Twilio;
                  import com.twilio.exception.AuthenticationException;
                  import com.twilio.exception.TwilioException;
                  import com.twilio.rest.api.v2010.account.Message;
                  import com.twilio.type.PhoneNumber;
                  
                  public class Example { 
                  
                    private static final String ACCOUNT_SID = "ACXXX";
                    private static final String AUTH_TOKEN = "xxxxx";
                  
                    void sendMessage() throws AuthenticationException, TwilioException { 
                       Twilio.init(ACCOUNT_SID, AUTH_TOKEN);
                  
                       Message message = Message.creator(
                           new PhoneNumber("+15558675309"),
                           new PhoneNumber("+15017250604"),
                           "Hello world!"
                       ).create();
                    } 
                  } 
                  

                  ClientCapabilty

                  TwilioCapability has been replaced with CapabilityToken. TwilioCapability would typically throw a generic DomainException. In version 7.x there is a more descriptive exception: JwtEncodingException.

                  import com.twilio.sdk.client.TwilioCapability;
                  import com.twilio.jwt.Jwt;
                  import java.util.List;
                  import javax.servlet.http.HttpServlet;
                  import javax.servlet.http.HttpServletRequest;
                  import javax.servlet.http.HttpServletResponse;
                  import java.io.IOException;
                  
                  public class TwilioServlet extends HttpServlet {
                  
                      private static final String ACCOUNT_SID = "ACXX";
                      private static final String AUTH_TOKEN = "your_auth_token";
                  
                      public void service(
                              HttpServletRequest request,
                              HttpServletResponse response
                          ) throws JwtEncodingException, IOException {
                  
                          List<Scope> scopes = Lists.newArrayList(
                              new IncomingClientScope("joey")
                          );
                          Jwt jwt = new ClientCapability.Builder(ACCOUNT_SID, SECRET)
                                        .scopes(scopes).build();
                  
                          Claims claims = Jwts.parser()
                                              .setSigningKey(SECRET.getBytes())
                                              .parseClaimsJws(jwt.toJwt())
                                              .getBody();
                  
                          String token = capability.generateToken();
                  
                          response.setContentType("application/jwt");
                          response.getWriter().print(token);
                      }
                  }
                  

                  TwiML

                  TwiML builder classes in both version 6.x and 7.x use the same exception TwimlException.

                  import com.twilio.sdk.client.TwilioCapability;
                  import com.twilio.jwt.Jwt;
                  import com.twilio.twiml.voice.Say;
                  import com.twilio.twiml.TwiMLException;
                  import com.twilio.twiml.VoiceResponse;
                  import java.util.List;
                  import javax.servlet.http.HttpServlet;
                  import javax.servlet.http.HttpServletRequest;
                  import javax.servlet.http.HttpServletResponse;
                  
                  public class TwilioServlet extends HttpServlet {
                  
                      private static final String ACCOUNT_SID = "ACXX";
                      private static final String AUTH_TOKEN = "your_auth_token";
                  
                      public void service(
                              HttpServletRequest request,
                              HttpServletResponse response
                          ) throws TwimlException {
                          Say say = new Say.Builder("Hello World!")
                              .voice(Say.Voice.MAN)
                              .loop(5)
                              .build();
                  
                          VoiceResponse voiceResponse = new VoiceResponse.Builder()
                              .say(say)
                              .build();
                  
                          response.setContentType("application/xml");
                          response.getWriter().print(voiceResponse.toXml());
                      }
                  }
                  

                  Debugging API Requests

                  To assist with debugging, the library allows you to access the underlying request and response objects. This capability is built into the default HTTP client that ships with the library.

                  For example, you can retrieve the status code of the last response like so:

                  // Install the Java helper library from twilio.com/docs/java/install
                  import com.twilio.Twilio;
                  import com.twilio.rest.api.v2010.account.Message;
                  import com.twilio.type.PhoneNumber;
                  
                  public class Example {
                      // Find your Account Sid and Token at twilio.com/user/account
                      public static final String ACCOUNT_SID = "ACXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX";
                      public static final String AUTH_TOKEN = "your_auth_token";
                  
                      public static void main(String[] args) {
                          Twilio.init(ACCOUNT_SID, AUTH_TOKEN);
                  
                          Message message = Message
                                  .creator(new PhoneNumber("+14158675309"),
                                           new PhoneNumber("+14258675310"),
                                           "Ahoy!")
                                  .create();
                  
                          // Retrieve the status code of the last response from the HTTP client
                          int statusCode = Twilio.getRestClient().getHttpClient().getLastResponse()
                                  .getStatusCode();
                  
                          System.out.println(statusCode);
                      }
                  }
                  

                  Need some help?

                  We all do sometimes; code is hard. Get help now from our support team, or lean on the wisdom of the crowd browsing the Twilio tag on Stack Overflow.