About Samuel Santos

Java and Open Source evangelist, JUG leader and Web advocate for web standards and semantic technologies.

Comparing OpenDDR to WURFL

Web content delivered to mobile devices usually benefits from being tailored to take into account a range of factors such as screen size, markup language support and image format support. Such information is stored in “Device Description Repositories” (DDRs).

Both WURFL and OpenDDR projects provide an API to access the DDRs, in order to ease and promote the development of Web content that adapts to its Delivery Context.

WURFL recently changed its license to AGPL (Affero GPL) v3. Meaning that it is not free to use commercially anymore. Consequently some free open source alternatives have recently started to show up. OpenDDR is one of them.

In this post I will share my findings on how the OpenDDR Java API compares to WURFL.

Add dependencies to project

This section describes how to add WURFL and OpenDDR to a Maven project. WURFL

WURFL is really straightforward since it is available on Maven central repository. All you have to do is to include the dependency on your project:

<dependency>
    <groupId>net.sourceforge.wurfl</groupId>
    <artifactId>wurfl</artifactId>
    <version>1.2.2</version><!-- the last free version -->
</dependency>

OpenDDR

OpenDDR on the other hand is quite difficult to configure. Follow these steps to include OpenDDR in your project:

  1. Download OpenDDR-Simple-API zip.
  2. Unzip it and create a new Java project on Eclipse based on the resulting folder.
  3. Export OpenDDR-Simple-API JAR using Eclipse File >> Export..., include only the content of the src folder excluding oddr.properties file.
  4. Install the resulting JAR and DDR-Simple-API.jar from the lib folder into your local Maven repository
    mvn install:install-file -DgroupId=org.w3c.ddr.simple -DartifactId=DDR-Simple-API -Dversion=2008-03-30 -Dpackaging=jar -Dfile=DDR-Simple-API.jar -DgeneratePom=true -DcreateChecksum=true
    mvn install:install-file -DgroupId=org.openddr.simpleapi.oddr -DartifactId=OpenDDR -Dversion=1.0.0.6 -Dpackaging=jar -Dfile=OpenDDR-1.0.0.6.jar -DgeneratePom=true -DcreateChecksum=true
    
  5. Add the dependencies to your project pom.xml file:
    <dependency>
        <groupId>org.w3c.ddr.simple</groupId>
        <artifactId>DDR-Simple-API</artifactId>
        <version>2008-03-30</version>
    </dependency>
    <dependency>
        <groupId>org.openddr.simpleapi.oddr</groupId>
        <artifactId>OpenDDR</artifactId>
        <version>1.0.0.6</version>
    </dependency>
    <dependency>
        <groupId>org.apache.commons</groupId>
        <artifactId>commons-jexl</artifactId>
        <version>2.1.1</version>
    </dependency>
    <dependency>
        <groupId>commons-lang</groupId>
        <artifactId>commons-lang</artifactId>
        <version>2.6</version>
    </dependency>
    

Load repository/capabilities file

This section describes how to load WURFL and OpenDDR repository file(s) and import it in your project. WURFL

Copy wurfl-2.1.1.xml.gz file (the last free version) into your project src/main/resources folder and import it using:

WURFLHolder wurflHolder = new CustomWURFLHolder(getClass().getResource("/wurfl-2.1.1.xml.gz").toString());

OpenDDR

Copy oddr.properties from the OpenDDR-Simple-API src folder and all the files inside OpenDDR-Simple-API resources folder into your project src/main/resources folder. Import them using:

Service identificationService = null;
try {
    Properties initializationProperties = new Properties();
    initializationProperties.load(getClass().getResourceAsStream("/oddr.properties"));
    identificationService = ServiceFactory
            .newService("org.openddr.simpleapi.oddr.ODDRService",
                    initializationProperties.getProperty(ODDRService.ODDR_VOCABULARY_IRI),
                    initializationProperties);
} catch (IOException e) {
    LOGGER.error(e.getMessage(), e);
} catch (InitializationException e) {
    LOGGER.error(e.getMessage(), e);
} catch (NameException e) {
    LOGGER.error(e.getMessage(), e);
}

Using the API

This section describes how use WURFL and OpenDDR Java APIs to access the device capabilities. WURFL

WURFL API is very easy to use and has the big advantage of having a fall-back hierarchy inferring capabilities for devices not yet in its repository file.

Device device = wurflHolder.getWURFLManager().getDeviceForRequest(getContext().getRequest());
int resolutionWidth = Integer.valueOf(device.getCapability("resolution_width"));
int resolutionHeight = Integer.valueOf(device.getCapability("resolution_height"));

There’s no need to validate device.getCapability("resolution_width") against null value when no data is available.

OpenDDR

OpenDDR is quite the opposite. Very cumbersome and does not have a fall-back hierarchy, forcing the developer to validate each property value.

PropertyRef displayWidthRef;
PropertyRef displayHeightRef;

try {
    displayWidthRef = identificationService.newPropertyRef("displayWidth");
    displayHeightRef = identificationService.newPropertyRef("displayHeight");
} catch (NameException ex) {
    throw new RuntimeException(ex);
}

PropertyRef[] propertyRefs = new PropertyRef[] { displayWidthRef, displayHeightRef };
Evidence e = new ODDRHTTPEvidence();
e.put("User-Agent", getContext().getRequest().getHeader("User-Agent"));

int maxImageWidth = 320; // A default value
int maxImageHeight = 480; // A default value
try {
    PropertyValues propertyValues = identificationService.getPropertyValues(e, propertyRefs);
    PropertyValue displayWidth = propertyValues.getValue(displayWidthRef);
    PropertyValue displayHeight = propertyValues.getValue(displayHeightRef);

    if (displayWidth.exists()) {
        maxImageWidth = displayWidth.getInteger();
    }
    if (displayHeight.exists()) {
        maxImageHeight = displayHeight.getInteger();
    }
} catch (Exception ex) {
    throw new RuntimeException(ex);
}

Results

The following table shows the results of tests run against an application for server-side image adaptation using both WURFL and OpenDDR.
These tests were performed on real devices and pages were served as XHTML BASIC (same as XHTML MP).

PlatformDevicePropertyWURFL max_image_width (1) / max_image_heightWURFL resolution_width / resolution_heightOpenDDR displayWidth / displayHeight
N/AFirefox desktopwidth650640Not supported
height600480Not supported
iOSiPhone 4Swidth320320320
height480480480
AndroidHTC One Vwidth320540Not supported
height400960Not supported
HTC Herowidth300320320
height460480480
Windows Phone 7.5Nokia Lumia 710width600640480
height600480800
BlackBerryBlackBerry Bold 9900width228480640
height280640480
Symbian S60Nokia E52 (Webkit)width234240240
height280320320
Nokia E52 (Opera Mobile)width240240Not supported
height280320Not supported
Windows Mobile 6.1HTC Touch HD T8282width440480480
height700800800

(1) max_image_width capability is very handy:

Width of the images viewable (usable) width expressed in pixels. This capability refers to the image when used in “mobile mode”, i.e. when the page is served as XHTML MP, or it uses meta-tags such as “viewport”, “handheldfriendly”, “mobileoptimised” to disable “web rendering” and force a mobile user-experience.

Note: The color #9f9 highlights the results that performed better. Pros and Cons

ProsCons
WURFL
  • A Device Hierarchy that yields a high-chance that the value of capabilities is inferred correctly even when the device is not yet recognized.
  • Lots and lots of capabilities.
  • Easier to configure.
  • Cleaner API.
OpenDDR
  • Free to use, even commercially.
  • Growing community.

Related Posts

Reference: Comparing Device Description Repositories from our JCG partner Samuel Santos at the Samaxes blog.

Related Whitepaper:

Functional Programming in Java: Harnessing the Power of Java 8 Lambda Expressions

Get ready to program in a whole new way!

Functional Programming in Java will help you quickly get on top of the new, essential Java 8 language features and the functional style that will change and improve your code. This short, targeted book will help you make the paradigm shift from the old imperative way to a less error-prone, more elegant, and concise coding style that’s also a breeze to parallelize. You’ll explore the syntax and semantics of lambda expressions, method and constructor references, and functional interfaces. You’ll design and write applications better using the new standards in Java 8 and the JDK.

Get it Now!  

One Response to "Comparing OpenDDR to WURFL"

  1. dubBike says:

    Have you tried comparing it to Deviceatlas?

Leave a Reply


six + 5 =



Java Code Geeks and all content copyright © 2010-2014, Exelixis Media Ltd | Terms of Use
All trademarks and registered trademarks appearing on Java Code Geeks are the property of their respective owners.
Java is a trademark or registered trademark of Oracle Corporation in the United States and other countries.
Java Code Geeks is not connected to Oracle Corporation and is not sponsored by Oracle Corporation.

Sign up for our Newsletter

15,153 insiders are already enjoying weekly updates and complimentary whitepapers! Join them now to gain exclusive access to the latest news in the Java world, as well as insights about Android, Scala, Groovy and other related technologies.

As an extra bonus, by joining you will get our brand new e-books, published by Java Code Geeks and their JCG partners for your reading pleasure! Enter your info and stay on top of things,

  • Fresh trends
  • Cases and examples
  • Research and insights
  • Two complimentary e-books
Get tutored by the Geeks! JCG Academy is a fact... Join Now
Hello. Add your message here.