Consuming Exchange Web Services with Java using Glassfish and Metro: Using ExchangeServicePortType with Authentication Credentials

Posted by r24mille on Sun, 11/23/2008 - 21:24

In my first article, Consuming Exchange Web Services with Java using Glassfish and Metro: Creating the Web Service Client, we left off having created a corrected exchange.wsdl, messages.xsd, and types.xsd files. From those files, we generated the web service client and copied the .java source files from the build into our project's source directory. In this article you will clean up a few loose ends from the generation of the Exchange Web Service stubs and create a method to return an ExchangeServicePortType bound with authentication credentials.

Correct Web Service Reference

The first thing you need to do is correct some duplication we've created in the project. With my previous article I had the reader copy the .java source files generated by Exchange's WSDL and drop them into the source folder of the NetBeans project. We also still have NetBeans configured with a “Web Service Reference” named “exchange”. If we were to fast forward into our development a bit, NetBeans defaults to use the “Web Service Reference” class files that are generated instead of the source packages we copied. When you make web service requests for findItem(...), findFolder(...), or any of the other methods in ExchangeServicePortType, these methods require that ExchangeImpersonationType and SerializedSecurityContextType objects be passed to them. In most cases we will not need either of those objects so normally we're supposed to pass them null values. In my experience, and despite scouring the Internet for information I have not been able to get around the xsi:nil attribute error that is thrown.

Exception in thread "main" The request failed schema validation: If the 'nillable' attribute is false in the schema, the 'xsi:nil' attribute must not be present in the instance.
        at $Proxy40.findItem(Unknown Source)

I found a bit of discussion on this topic over at the Microsoft TechNet forums but they seem largely frustrated as well. The developers at Metro attribute the inconsistency to the .Net framework incorrectly enforcing Basic Profile v1.1 compliance. Based on my experience with Microsoft, I'm going to trust the Metro folks and blame it on the .Net framework. Nonetheless it's kind of annoying to deal with. In my series I will advise method overloading ExchangeServicePortType to work around the xsi:nil errors. We will not get into this method overloading until later articles, but I wanted to briefly address how I propose getting around the xsi:nil error.

First, because in my last article I advised copying the generated .java files rather than using NetBeans Web Service client context menus, we must remove the “Web Service Reference” from NetBeans so that it uses our source packages instead. To do this:

  1. Using the “Projects” navigation along the left-hand side open your project. → Expand the “Web Service References” category.
  2. You should see a client named “exchange” listed. Right-click on it and delete it.
  3. Now right-click on your project and select “Clean and Build”.

All of the references to this web service client have now been removed from NetBeans and it will use our source packages to communicate with the Exchange server now.

Deploy your exchange.wsdl

The second bit of house cleaning needed is to deploy the corrected exchange.wsdl, messages.xsd, and types.xsd files to Glassfish. So even though there isn't much developed yet, deploy the project out to Glassfish:

  1. Right-click on your project and select “Run”
  2. After deploying visit: http://localhost:8080/[Your Project Name]/exchange.wsdl

You should see the WSDL file. In Firefox sometimes I've noticed it'll display it as a blank page. If you view the source all the WSDL XML should be there. Now that it's deployed, leave the server up. The SOAP requests depend on that file being available.

Write a class to bind authentication credentials to ExchangeServicePortType

Finally, we're ready to start writing some Java to interact with Exchange. This assumes that you have an account on the Exchange environment you're developing against and need to authenticate. I was originally pointed down the path of using which worked, sort of, but it authenticated the entire application with my credentials, which is obviously not desirable for a web application environment. You'll see that I've followed up with some appropriate notes at the forum topic :)

To get started, let's write an ExchangeAuthenticator class. A method in that class will return a ExchangeServicePortType with authentication credentials. I think the clearest way to explain this is through some well-commented code.

import javax.xml.namespace.QName;

 * This class manages web services authentication requests to the Exchange
 * server. 
 * @author Reid Miller
public class ExchangeAuthenticator {	
     * Obtains an authenticated ExchangeServicePortType with given credentials.
     * See
     * @param username
     * @param password
     * @param domain 
     * @param wsdlURL
     * @return ExchangeServicePortType
     * @throws MalformedURLException 
    public ExchangeServicePortType getExchangeServicePort(String username, String password, String domain, URL wsdlURL) throws MalformedURLException {
    	// Concatinate our domain and username for the UID needed in authentication.
    	String uid = domain + "\\" + username;

        // Create an ExchangeWebService object that uses the supplied WSDL file, wsdlURL.
        ExchangeWebService exchangeWebService = new ExchangeWebService(wsdlURL, new QName("", "ExchangeWebService"));
        ExchangeServicePortType port = exchangeWebService.getExchangeWebPort();
        // Supply your username and password when the ExchangeServicePortType is used for binding in the SOAP request.
        ((BindingProvider)port).getRequestContext().put(BindingProvider.USERNAME_PROPERTY, uid);
        ((BindingProvider)port).getRequestContext().put(BindingProvider.PASSWORD_PROPERTY, password);
        return port;

Next, create a throw-away class with a main method for testing ExchangeAuthenticator.

import java.util.logging.Level;
import java.util.logging.Logger;

 * Throw-away class for doing quick tests of features and classes during 
 * development.
 * @author Reid Miller
public class ExchangeDevelopmentTest {
     * Main method so we can quickly test things.
     * @param args
    public static void main (String[] args) {
        ExchangeAuthenticator exchangeAuthenticator = new ExchangeAuthenticator();

        // Print statement so we can easily see where our statements start in the Java console.
        System.out.println("Let's get started!");

        try {
            // Create a URL object which points at the .wsdl we deployed in the previous step.
            URL wsdlURL = new URL("http://localhost:8080/[Your Project Name]/exchange.wsdl");
            // Call to the class we just created to return an ExchangeServicePortType with authentication credentials.
            ExchangeServicePortType port = exchangeAuthenticator.getExchangeServicePort("username", "password", "domain", wsdlURL);

            // Prints out the default toString() for the ExchangeServicePortType.
        } catch (MalformedURLException ex) {
            // Catch any errors that may occur.
            Logger.getLogger(ExchangeDevelopmentTest.class.getName()).log(Level.SEVERE, null, ex);

Run your work

Let's run our work!

  1. Using the “Projects” column on the left-hand side, find the package you created ExchangeDevelopmentTest in. Right-click on and select “Run”.

In the Java console below you should see something similar to the following message if all went well:

Compiling 1 source file to /home/oreomasta/ExchangeWebServices/build/web/WEB-INF/classes
Let's get started!
JAX-WS RI 2.1.2_01-hudson-189-: Stub for
BUILD SUCCESSFUL (total time: 2 seconds)


It wasn't much but you're now writing some Java to interact with Exchange Web Services. In my next articles I will be going over the many methods in ExchangeServicePortType for doing work on Exchange. Many of the articles will simply be translations of Microsoft's C# and .Net examples out at MSDN.


I've updated this article a few times as I receive user comments and look into questions further:

  • Jan 16, 2009: Updated the "Correct Web Service Reference" section to elaborate a bit on the xsi:nil error, and I included a link to the Metro documentation for the developers' explanation.


hi can u send me more code for evet notification for Exchange 2007 and java

r24mille's picture


Thank you for the comment. Actually, at my job (where most of my web services knowledge has been gleaned) my co-worker wrote the portion of our application that deals with event notification. I'm not entirely convinced he's working with it correctly either :) But due to your request I will include a short sample on event notifications and I will bump it up in the order.

I'm sorry this series is taking me so long. Life has been keeping me busy. But with both your and Felix's comments, I'm energized to put the rubber to the road on this Exchange Web Services series.


Hello Reid,
I’m a student writing in the moment my Bachelor thesis. Within this thesis I’m trying to use the Web services offered by Microsoft Exchange 2007. I have special interest to use the Availability Service. I tried to follow your example but till now I didn’t had any success with that. It is getting really frustrating now, I just spend nearly the whole week with different solutions I found in the Internet.
Could you please send me a full working example.
Or is there any possibility to disable SSL for the Web service connection?
Thanks a lot!


r24mille's picture


That's an ambitious undergraduate project :) I hope to finish my 3rd article tonight, which will make use of port.findItem(...) to return the user's Inbox. That will effectively provide a basic working sample, and from there the MSDN documentation starts to make a lot more sense.

However, you left me no contact info! :) Please use the contact form on my site and I will get in touch with you. I may be able to help you out a bit with your project.

With regard to your SSL question, I do not know if EWS will work without SSL. I know that our Exchange admin has everything running over SSL and there was never any time I was operating without SSL, and it was actually quite a bear to get SSL working. Not because of Metro or EWS, but because my workplace buys crappy certs and I needed to add the cert as a trusted signer to the Glassfish installation :) I can give direction on that too if that's where you're getting hung up.

Please check back and contact me, thanks!


Hi all,
I have a problem when i changed my web service location or path on server, the java web application which consume that web service shows error- org.apache.jasper.JasperException: Failed to access the WSDL at: So any one know how to change the web service path in my project using netbeans.

r24mille's picture

Hello Ajay,

Your question sounds like a general WSDL/Web Service Client question, so if it's something specific to Exchange Web Services please let me know. If you have the WSDL set up as a Web Service Client in NetBeans, you can update the location by:

  1. Opening up your NetBeans project and expanding it.
  2. Expand the Web Service References section.
  3. Right-click on the web service client in question and select "Refresh Client"
  4. In the dialog box that comes up check "Also replace local WSDL file with original WSDL located at:" and fill in the input field with the new location of your WSDL

This should generate the WSDL client in NetBeans again. Did I address your question? Let me know.

Reid Miller

First of all, congratulations for the article!

I am following it and I am getting the following answer:

Let's get started!
JAX-WS RI Stub for
Exception in thread "main" The server sent HTTP status code 405: Method Not Allowed

Do you what it can be?
Thanks in advance!

r24mille's picture


I assume, from your comment on my next article, that you got past this problem. What ended up being the issue? Were you pointing at the WSDL on the Exchange server rather than the local copy of the WSDL? A commenter on my 3rd article had a similar issue (although not the same error message) which I replied to.

Let me know if this is still an issue. I'll try to get back to you in a more timely manner next time.

Reid Miller

Hi Miller!
Thanks for you reply! It was already solved!

First off thank you for your blog, it has helped move me in the right direction. Secondly I keep getting a ClientTransport Exception returned when trying to create a PushSubscriptionRequest. If you have time I started a post here: that explains my problem. Thanks again for the blog!


Thanks to your instructions I'm almost there.
I had things working when I referenced the original WSDL file - up until the point where I rebuild and it erased all my modifications in ExchangeServicePortType - you warned against that and I wouldn't listen.
In order to prevent this from happening I used the local copy of the WSDL and XSD and re-added the web service reference.

That's all good except now in

ExchangeWebService exchangeWebService = new ExchangeWebService(wsdlURL, new QName("", "ExchangeWebService"));

JAXWS craps out - since my webservice reference is an offline reference, it somehow want so validate the schema before proceeding.. so it loads the WSDL and notes that there's no service element and aborts right there.

How did you manage to get past that? If I initialize as

ExchangeWebService exchangeWebService = new ExchangeWebService();

that works but then it uses the address that I put in the WSDL file.. and we're supposed to use autodiscovery to get the appropriate endpoint so this will only work until I work in a multi CAS server environment where I'm supposed to use another server for a particular mailbox.

How to send back the respons to the client if there is some problem in the webservice due to network or any other problem.pls help me out in solving the issue

Hi Reid,

Thanks for info about CXF. I am able to read my own email when I run client from my desktop, but even if I provide other user credentials and running on my desktop I am still reading my own emails. Infact even if I do not provide my credentails , I am able to read my emails. It looks like httpclient somehow getting my credentials from my desktop.

Appreciate your help on this.


Was anyone able to figure out this issue where the credentials get stored for the first person logging in and the server has to be restarted to authenticate a different user?

Manuel_B's picture

great article helped me a lot. Here are two hints just in case your Exchange server requires NTLM or has an invalid certificate:

TrustManager[] trustAllCerts = new TrustManager[]{
new X509TrustManager() {

public[] getAcceptedIssuers() {
return null;

public void checkClientTrusted([] certs, String authType) {
//No need to implement.

public void checkServerTrusted([] certs, String authType) {
//No need to implement.

// Let us create the factory where we can set some parameters for the connection
SSLContext sc = SSLContext.getInstance("SSL");
sc.init(null, trustAllCerts, new;

SSLSocketFactory socketFactory =sc.getSocketFactory();

((BindingProvider)serviceBinding).getRequestContext().put("", socketFactory);

Holder findItemResult = new Holder();
Holder serverVersion = new Holder();

// Make NTLM work
Authenticator.setDefault(new Authenticator() {
public PasswordAuthentication getPasswordAuthentication () {
return new PasswordAuthentication ("DOMAIN\\your.username", "password".toCharArray());

Hi Reid,

Thanks for this great tutorial. We are in the process of building a Java application to interact with Microsoft Exchange. This series of articles of yours will be very helpful to us since we are new to web service.

I have a clarification. You have stated that the SOAP request depends on the "exchange.wsdl" being available. Hence, the server should always be up.

Example: http://localhost:8080/[Your Project Name]/exchange.wsdl

My question is does the SOAP request is submitted by the running server (i.e. http://localhost:8080/[Your Project Name] ) to Microsoft Exchange? Or the SOAP request is directly submitted by the Java application (i.e. ExchangeDevelopmentTest)?

Though it is clear that you mentioned "Create an ExchangeWebService object that uses the supplied WSDL file, wsdlURL."

I just want to clarify who delivers the SOAP request and who accepts the SOAP response?

Again, thank you very much.

Add new comment