次の方法で共有


Java sample application for Windows Azure

I have published on GitHub the source code for a very simple Java Web application, that includes all the basic building blocks you would need to start developing a “real” Java application for Windows Azure. It takes the form of an Eclipse project that contains the following elements:

  • A “classic” JSP application (very 20th century ;-) created using the “Dynamic Web Project” template in Eclipse
  • The Windows Azure SDK for Java, including all its pre-requisites in terms of third-party libraries
  • The JDBC Driver for SQL Server and SQL Azure (version 3.0) that will allow you to connect to SQL Azure
  • The almost-latest version of Hibernate (3.6.4), because that’s what most people use to access their database
  • A simple Hibernate configuration for SQL Azure
  • A micro-application that show how to use Blob Storage and SQL Azure

The idea is to provide Java developers something that is “ready to use” and does not require to gather all the components. I hope to make the sample application a little bit more complete to show additional elements, notably Table Storage.

Here is what the application looks like:

image_thumb1

And here is some information about the various components in the application.

First, the Hibernate configuration:

 <!-- Database connection settings -->
<property name="connection.driver_class">com.microsoft.sqlserver.jdbc.SQLServerDriver</property>
<!-- Local database settings (e.g. SQL Express) -->

<property name="connection.url">jdbc:sqlserver://localhost:1433;databaseName=Chinook;</property>

<property name="connection.username">sa</property>

<property name="connection.password">Pass123!</property>
<!-- SQL Azure connection settings -->

<!--<property name="connection.url">jdbc:sqlserver://YOURSERVER.database.windows.net:1433;databaseName=Chinook</property>-->

<!--<property name="connection.username">YOURLOGIN@YOURSERVER</property>-->

<!--<property name="connection.password">YOURPASSWORD</property>-->
<!-- JDBC connection pool (use C3P0) -->

<property name="hibernate.c3p0.min_size">5</property>

<property name="hibernate.c3p0.max_size">20</property>

<property name="hibernate.c3p0.idle_test_period">60</property>

<property name="hibernate.c3p0.max_statements">100</property>
  

I have included two possible configurations: “localhost” for local development, where you would typically use a local SQL Express database, and a sample SQL Azure configuration, with a typical URL and the login string that has to follow a slightly specific format (user@host).

I have also configured a C3P0 connection pool, with an “idle_test_period” set to 60 seconds, which is required when connection to SQL Azure: the Windows Azure infrastructure will automatically drop all TCP connections idle for more than 60 seconds!

The rest of the configuration is very simple, I have modeled three classes (Album, Artist, Track) from the Chinook sample database you can download from CodePlex.

I then have a very simple class showing how you can access SQL Azure, and also use the Windows Azure Blob Storage to store some pictures.

 public class AlbumService {
 protected static final String BLOB_HOST_NAME = "https://tcontepub.blob.core.windows.net/";
  protected static final String BLOB_CONTAINER_NAME = "ledzep";
  
 public List<DisplayAlbum> getAlbumsForArtist(String artistName) {
      List<DisplayAlbum> displayAlbums = new ArrayList<DisplayAlbum>();
        
     Session session = HibernateUtil.getSessionFactory().getCurrentSession();
     
        session.beginTransaction();
        List albums = session.createQuery("from Album a where a.artist.name='" + artistName + "'").list();
        for (int i=0; i < albums.size(); i++) {
          Album a = (Album)albums.get(i);
          
         String blobName = a.getTitle() + ".jpg";
           String containerName = BLOB_CONTAINER_NAME;
          String img = null;
           
         if (BlobUtil.blobExists(containerName, blobName)) {
              img = BLOB_HOST_NAME + containerName + "/" + blobName;
         }
         DisplayAlbum da = new DisplayAlbum();
            da.setTitle(a.getTitle());
           da.setAlbumId(a.getAlbumId());
           if (img != null) {
               da.setCover(img);
            }
            displayAlbums.add(da);
        }
        session.getTransaction().commit();
        
        return displayAlbums;
    }
}

Here, I use Hibernate to issue a SQL request and find a list of albums corresponding to a given artist name. Once I have a list of albums, I issue requests to the Blob Storage to see if I can find a JPEG file bearing the same name (representing the picture of the album cover). If I find a picture, I add it to the view object I will use to display the information. This is a trivial example, but allows me to demonstrate, in the BlobUtil class, how to access Blob Storage:

 public class BlobUtil {
   //protected static final String BLOB_HOST_NAME      = "https://blob.core.windows.net/";
   //protected static final String AZURE_ACCOUNT_NAME  = "YOURACCOUNT";
   //protected static final String AZURE_ACCOUNT_KEY   = "YOURKEY";
   //protected static final boolean PATH_STYLE_URIS = false;
   protected static final String BLOB_HOST_NAME      = "https://127.0.0.1:10000/";
     protected static final String AZURE_ACCOUNT_NAME  = "devstoreaccount1";
    protected static final String AZURE_ACCOUNT_KEY   = "Eby8vdM02xNOcqFlqUwJPLlmEtlCDXJ1OUzFT50uSRZ6IFsuFq2UVErCz4I6tq/K1SZFPTOtr/KBHBeksoGMGw==";
    protected static final boolean PATH_STYLE_URIS    = true;
        
     public static boolean blobExists(String containerName, String blobName) {
        BlobStorageClient storageClient = BlobStorageClient.create(
                  URI.create(BLOB_HOST_NAME),
                  PATH_STYLE_URIS,
                 AZURE_ACCOUNT_NAME,
                  AZURE_ACCOUNT_KEY);
          
         IBlobContainer container = storageClient.getBlobContainer(containerName);
        
         return container.isBlobExist(blobName);
      }
}

As you can see in this example, the API is very simple: a call to container.isBlobExist() will test for the existence of a given Blob.

The static parameters are by default configured to point to the storage emulator, running locally; the Storage Emulator is part of the Windows Azure SDK you installed on your development machine. For a live deployment to Windows Azure, you will use the other set of parameters, where you will enter your storage account and secret key. You will find both these values in the Windows Azure administration portal, when you create a Storage account.

And finally, a little JSP page will assemble everything:

 <jsp:useBean id="AlbumService" class="org.azurejava.sample.AlbumService" scope="page" />
<div id="albums">
<%
 List<DisplayAlbum> albums = AlbumService.getAlbumsForArtist("Led Zeppelin");
 Iterator<DisplayAlbum> i = albums.iterator();
  while (i.hasNext()) {
        DisplayAlbum a = i.next();
%>
   <div class="album">
      <div><%= a.getCover() != null ? "<img class=\"albumcover\" src=\"" + a.getCover() + "\">" : "" %></div>
        <div><%= a.getTitle() %></div>
 </div>
<%
 }
%>
</div>

You can execute this application in a local Tomcat instance installed on your machine. You do not need to execute it within the Windows Azure Compute Emulator, because it does not use any specific Compute features (like multiple Roles). However you will need the Storage Emulator if you want to develop storage code locally.

However, in order to deploy it into Windows Azure (either the local Emulator or the live Fabric), you will need to package it; this is where you can use the Windows Azure Starter Kit for Java, as I will show you in a future post! :-)

I will certainly evolve this Java sample, so follow it on GitHub!

Comments

  • Anonymous
    June 16, 2011
    The comment has been removed

  • Anonymous
    June 22, 2011
    This is very interesting and informative. I do appreciate for posting and sharing this information to us. thanks again! :) johnbriner.wordpress.com

  • Anonymous
    April 29, 2012
    Does this example run in a linux environment?