73
Roy Clarkson & Josh Long SpringSource, a division of VMware 1 Native Android Development Practices

Native Android Development Practices

Embed Size (px)

DESCRIPTION

Presented at SpringOne 2GX 2011

Citation preview

Page 1: Native Android Development Practices

• Roy Clarkson & Josh LongSpringSource, a division of VMware

1

Native Android Development Practices

Page 2: Native Android Development Practices

@royclarkson

2

About Roy Clarkson (Spring Android Lead)

Page 3: Native Android Development Practices

@royclarkson

2

About Roy Clarkson (Spring Android Lead)

Page 4: Native Android Development Practices

@royclarkson

2

About Roy Clarkson (Spring Android Lead)

Page 5: Native Android Development Practices

@starbuxman

3

About Josh Long (Spring Developer Advocate)

[email protected]

Page 6: Native Android Development Practices

Spring Mobile

• Provides support for developing mobile web applications– Builds on Spring MVC, focuses on server-side support– Compliments client-side mobile frameworks

• Key Features– Device Detection– Site Preference Management– Site Switcher

4

Page 7: Native Android Development Practices

Device Detection

• Useful when requests by mobile devices need to be handled differently from requests made by desktop browsers

• Introspects HTTP requests to determine the device that originated the request.– Achieved by analyzing the User-Agent header and other

request headers– In contrast to “Feature Detection” where client detects

available features

• Spring Mobile provides a DeviceResolver abstraction and interceptor

5

Page 8: Native Android Development Practices

Device Detection Demo

6

Page 9: Native Android Development Practices

Site Preference Management

• Device detection is often used to determine which "site" will be served to the user– Mobile site vs. desktop site

• Spring Mobile also provides support for “site preference management”

• Allows the user to indicate whether he or she prefers the mobile site or the normal site

• Remembers the user’s preference for their session

7

Page 10: Native Android Development Practices

Site Preference Demo

8

Page 11: Native Android Development Practices

Site Switcher

• Some applications may wish to host their "mobile site" at a different domain from their "normal site"– For example, Google will switch you to m.google.com if you

access google.com from your mobile phone

• SiteSwitcherHandlerInterceptor can be used to redirect mobile users to a dedicated mobile site

• Supported SiteSwitchers– mDot - m.example.com– dotMobi - example.mobi

9

Page 12: Native Android Development Practices

Site Switcher Demo

10

Page 13: Native Android Development Practices

Limitations of Mobile web sites

• they can’t access the native capabilities of the phone• they require network access (no offline support)• formatting an application to look mobile is different than

actually being a mobile application

11

Page 14: Native Android Development Practices

Agenda

12

Page 15: Native Android Development Practices

Agenda

12

Page 16: Native Android Development Practices

Agenda

12

Page 17: Native Android Development Practices

An Introduction to Android!

13

More than 500,000 activations every day

Page 18: Native Android Development Practices

An Introduction to Android!

• Huge and growing ecosystem ofapplications and a market to boot

14

8.1 billion app downloadsAndroid Market PlaceApple App Store 6 billion

* http://news.cnet.com/8301-1035_3-20103230-94/android-to-overtake-apple-in-app-downloads/

Expected downloads in 2011

Page 19: Native Android Development Practices

Easy to get started

15

• Programs are written in Java ( )

Page 20: Native Android Development Practices

Easy to get started

15

• Programs are written in Java ( )

Page 21: Native Android Development Practices

Easy to get started

15

• Programs are written in Java ( )

Page 22: Native Android Development Practices

Easy APIs and concepts

• no real “applications,” only loosely coupled components

16

Activities describes the unit of work for one screen

Services does background work like synchronization with a cloud service

Content Providers component that knows how to render and manipulate content of a certain type

Broadcast Receivers knows how to receive and respond to system-wide events like screen shutoff.

* http://developer.android.com/guide/topics/fundamentals.html

Page 23: Native Android Development Practices

A Simple Activity

17

package org.springframework.android.activities;

import android.app.Activity;import android.os.Bundle;

public class HelloAndroid extends Activity {     @Override    public void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.main);    }

}

Page 24: Native Android Development Practices

You *must* extend Android classes to build proper components

A Simple Activity

17

package org.springframework.android.activities;

import android.app.Activity;import android.os.Bundle;

public class HelloAndroid extends Activity {     @Override    public void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.main);    }

}

Page 25: Native Android Development Practices

You *must* extend Android classes to build proper components

R.* refers to constants that Android code generates for you that correspond to “resources”

A Simple Activity

17

package org.springframework.android.activities;

import android.app.Activity;import android.os.Bundle;

public class HelloAndroid extends Activity {     @Override    public void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.main);    }

}

Page 26: Native Android Development Practices

Declaring the Simple Activity

18

<?xml version="1.0" encoding="utf-8"?><TextView xmlns:android="http://schemas.android.com/apk/res/android"  android:id="@+id/textview"  android:layout_width="fill_parent"  android:layout_height="fill_parent"  android:text="@string/hello"/>

/res/layout/main.xml

<?xml version="1.0" encoding="utf-8"?><resources>    <string name="hello">Hello, Android! I am a string resource!</string>    <string name="app_name">Hello, Android</string></resources>

/res/values/strings.xml

Page 27: Native Android Development Practices

Lifecycle

• Android controls lifecycles of these components• Registered in manifest

19

<activity android:name=".activities.HelloAndroid          android:label="@string/app_name"           android:theme="@android:style/Theme.NoTitleBar"> <intent-filter> <action android:name="android.intent.action.MAIN" /> <category android:name="android.intent.category.LAUNCHER" /> </intent-filter></activity>

Page 28: Native Android Development Practices

Class is set relative to root package specified in manifest

Lifecycle

• Android controls lifecycles of these components• Registered in manifest

19

<activity android:name=".activities.HelloAndroid          android:label="@string/app_name"           android:theme="@android:style/Theme.NoTitleBar"> <intent-filter> <action android:name="android.intent.action.MAIN" /> <category android:name="android.intent.category.LAUNCHER" /> </intent-filter></activity>

Page 29: Native Android Development Practices

you specify that an Activity is the primary one like this

Class is set relative to root package specified in manifest

Lifecycle

• Android controls lifecycles of these components• Registered in manifest

19

<activity android:name=".activities.HelloAndroid          android:label="@string/app_name"           android:theme="@android:style/Theme.NoTitleBar"> <intent-filter> <action android:name="android.intent.action.MAIN" /> <category android:name="android.intent.category.LAUNCHER" /> </intent-filter></activity>

Page 30: Native Android Development Practices

Android Sample Demo

• How to use STS and the Android Eclipse plugin

20

Page 31: Native Android Development Practices

How can Maven help?

• Android4Maven– This project compiles android.jar from source and pulls out

source and resource files to replicate android.jar in the SDK– http://sourceforge.net/projects/android4maven/

• Maven Android SDK Deployer– If you need to use Google maps, then you have to go this

route– https://github.com/mosabua/maven-android-sdk-deployer

• Maven Android Plugin– Provides support for Maven dependency management within

Android projects– http://code.google.com/p/maven-android-plugin/

21

Page 32: Native Android Development Practices

Maven Android Plugin Configuration

22

<plugins> <plugin> <groupId>com.jayway.maven.plugins.android.generation2</groupId> <artifactId>maven-android-plugin</artifactId> <version>2.8.4</version> <configuration> <sdk> <platform>3</platform> </sdk> <emulator> <avd>3</avd> </emulator> <deleteConflictingFiles>true</deleteConflictingFiles> <undeployBeforeDeploy>true</undeployBeforeDeploy> </configuration> <extensions>true</extensions> </plugin>

Page 33: Native Android Development Practices

m2eclipse Support

• Maven Integration for Android Development Tools– An Eclipse plugin that adds support for integrating

m2eclipse, Android Developer Tools, and the Maven Android Plugin

– http://code.google.com/a/eclipselabs.org/p/m2eclipse-android-integration/

• Maven Android archetypes– This projects provides several Maven archetypes for

Android. These archetypes allow you to quickly bootstrap a Maven project to develop an android application.

– https://github.com/akquinet/android-archetypes

23

http://blog.springsource.com/2010/12/17/spring-android-and-maven-part-1/http://blog.springsource.com/2010/12/17/spring-android-and-maven-part-2/

Page 34: Native Android Development Practices

Running the simple Activity

24

Page 35: Native Android Development Practices

Running the simple Activity

24

Page 36: Native Android Development Practices

25

...what about something a bit more non-trivial?

Page 37: Native Android Development Practices

26

Spring’s aim:

bring simplicity to java development

modern web data access integration mobile social security

tc ServerTomcatJetty

lightweightCloudFoundry

Google App EngineAmazon Web Services

BeanStalkHeroku

the cloud: WebSphereJBoss ASWebLogic

(on legacy versions, too!)

traditional

The Spring framework

security

Enter Spring Android!

Page 38: Native Android Development Practices

What problem are we trying to solve?

• Concerns– REST has become a popular choice for architecting both

public and private web services– The Android runtime provides HTTP clients capable of

making HTTP connections and requests, but it does not have a fully featured REST client

• Spring Android Solution– The goal of Spring Android Rest Template is to provide an

easy to use, and functional REST client that supports marshaling objects from XML and JSON.

27

Page 39: Native Android Development Practices

REST

• Origin– The term Representational State Transfer was introduced and

defined in 2000 by Roy Fielding in his doctoral dissertation.• His paper suggests these four design principles:

– Use HTTP methods explicitly.• POST, GET, PUT, DELETE• CRUD operations can be mapped to these existing methods

– Be stateless.• State dependencies limit or restrict scalability

– Expose directory structure-like URIs.• URI’s should be easily understood

– Transfer XML, JavaScript Object Notation (JSON), or both.• Use XML or JSON to represent data objects or attributes

28

Page 40: Native Android Development Practices

Basic Rest Template Example

29

RestTemplate restTemplate = new RestTemplate();String url = "https://ajax.googleapis.com/ajax/services/search/web?v=1.0&q={query}";String result = restTemplate.getForObject(url, String.class, "SpringSource");

RestTemplate restTemplate = new RestTemplate();String url = "http://example.com/hotels/{hotel}/bookings/{booking}";String result = restTemplate.getForObject(url, String.class, "42", “21”);

§ Google search example

§ Multiple parameters

Page 41: Native Android Development Practices

Demo

• Using Spring Android to communicate with a RESTful web service (Google Search Demo)

30

Page 42: Native Android Development Practices

Spring Android Rest Template

• Based on SpringFramework– The majority of the supporting classes are pulled from

SpringFramework.– Modifications were made to support Android.

• RestTemplate class is the heart of the library– Entry points for the six main HTTP methods

• DELETE - delete(...)• GET - getForObject(...)• HEAD - headForHeaders(...)• OPTIONS - optionsForAllow(...)• POST - postForLocation(...)• PUT - put(...)• any HTTP operation - exchange(...) and execute(...)

31

Page 43: Native Android Development Practices

Spring Android Rest Template

• Http Client– The HttpComponents HttpClient is a native HTTP client

available on the Android platform.– HttpComponentsClientHttpRequestFactory

• Message Converters– MappingJacksonHttpMessageConverter - object to

JSON marshaling supported via the Jackson JSON Processor

– SimpleXmlHttpMessageConverter - object to XML marshaling supported via the Simple XML Serializer

– SyndFeedHttpMessageConverter - RSS and Atom feeds supported via the Android ROME Feed Reader

32

Page 44: Native Android Development Practices

Spring Android Showcase

• Examples– HTTP GET

• JSON• XML

– HTTP GET with Parameters• JSON• XML

– HTTP POST• String• JSON• XML• MultiValueMap

– HTTP and GZIP

33

Page 45: Native Android Development Practices

Spring Android Demos

• Spring Android Showcase Demo

34

Page 46: Native Android Development Practices

Spring Social on Android

• Supports connecting to supported Spring Social services• uses same RESTful connectivity based on RestTemplate

35

Page 47: Native Android Development Practices

Enter Spring Android!

36

Page 48: Native Android Development Practices

37

do NOT reinvent the Wheel!

Page 49: Native Android Development Practices

38

Dependency Injection on Android

• Problems with DI on Android– hard reliance on base classes– hard reliance on Android to manage the runtime lifecycle

• a POJO peer system would have been onerous

Page 50: Native Android Development Practices

39

Dependency Injection on Android

• Lots of options– RoboGuice– Android Annotations– the Android way

Page 51: Native Android Development Practices

40

Dependency Injection on Android

• RoboGuice (http://code.google.com/p/roboguice/)– Pros:

• requires you to extend RoboApplication• You must configure your beans using the

AbstractAndroidModule• Each Activity must extend from RoboActivity

– Cons:• no AOP• not small, at all!

– (400kb to a mobile application may as well be 400MBs to your enterprise application!)

Page 52: Native Android Development Practices

public class MyActivity extends Activity {     private TextView label;     private Drawable image;     private SearchManager searchManager;     @Override    public void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.myactivity);        this.label = (TextView) findViewById(R.id.mylabel);        this.image = getResources().getDrawable(R.drawable.myimage);        this.searchManager = (SearchManager) getSystemService(Activity.SEARCH_SERVICE);    }}

before RoboGuice

41

Dependency Injection on Android

• RoboGuice (http://code.google.com/p/roboguice/)

Page 53: Native Android Development Practices

41

Dependency Injection on Android

• RoboGuice (http://code.google.com/p/roboguice/)

Page 54: Native Android Development Practices

public class MyActivity extends RoboActivity {     @InjectView(R.id.mylabel)    TextView label;     @InjectResource(R.drawable.myimage)    Drawable image;     @Inject    SearchManager searchManager;     @Override    public void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.myactivity);    }}

with RoboGuice

41

Dependency Injection on Android

• RoboGuice (http://code.google.com/p/roboguice/)

Page 55: Native Android Development Practices

used to inject other widgets or “views”

public class MyActivity extends RoboActivity {     @InjectView(R.id.mylabel)    TextView label;     @InjectResource(R.drawable.myimage)    Drawable image;     @Inject    SearchManager searchManager;     @Override    public void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.myactivity);    }}

with RoboGuice

41

Dependency Injection on Android

• RoboGuice (http://code.google.com/p/roboguice/)

Page 56: Native Android Development Practices

used to inject Resources

used to inject other widgets or “views”

public class MyActivity extends RoboActivity {     @InjectView(R.id.mylabel)    TextView label;     @InjectResource(R.drawable.myimage)    Drawable image;     @Inject    SearchManager searchManager;     @Override    public void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.myactivity);    }}

with RoboGuice

41

Dependency Injection on Android

• RoboGuice (http://code.google.com/p/roboguice/)

Page 57: Native Android Development Practices

used to inject other objects

used to inject Resources

used to inject other widgets or “views”

public class MyActivity extends RoboActivity {     @InjectView(R.id.mylabel)    TextView label;     @InjectResource(R.drawable.myimage)    Drawable image;     @Inject    SearchManager searchManager;     @Override    public void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.myactivity);    }}

with RoboGuice

41

Dependency Injection on Android

• RoboGuice (http://code.google.com/p/roboguice/)

Page 58: Native Android Development Practices

42

Dependency Injection on Android

• RoboGuice (http://code.google.com/p/roboguice/)– Pros:

• requires you to extend RoboApplication• You must configure your beans using the

AbstractAndroidModule• Each Activity must extend from RoboActivity

– Cons:• no AOP• not small, at all!

– (400kb to a mobile application may as well be 400MBs to your enterprise application!)

• runtime inefficiency

Page 59: Native Android Development Practices

43

Beyond Dependency Injection

• Android Annotations(http://code.google.com/p/androidannotations/)– Pros:

• compile-time code generation means no runtime cost• can be used side-by-side with RoboGuice

– Cons:• extra build step• some redundancy with RoboGuice

Page 60: Native Android Development Practices

44

Beyond Dependency Injection

• Android Annotations(http://code.google.com/p/androidannotations/)

@EActivity(R.layout.myactivity) public class MyActivity extends Activity {     @InjectView     TextView mylabel;     @DrawableRes(R.drawable.myimage)    Drawable image;     @SystemService    SearchManager searchManager;}

Page 61: Native Android Development Practices

sets the layout

44

Beyond Dependency Injection

• Android Annotations(http://code.google.com/p/androidannotations/)

@EActivity(R.layout.myactivity) public class MyActivity extends Activity {     @InjectView     TextView mylabel;     @DrawableRes(R.drawable.myimage)    Drawable image;     @SystemService    SearchManager searchManager;}

Page 62: Native Android Development Practices

sets the layout

Inject another widget or “view”

44

Beyond Dependency Injection

• Android Annotations(http://code.google.com/p/androidannotations/)

@EActivity(R.layout.myactivity) public class MyActivity extends Activity {     @InjectView     TextView mylabel;     @DrawableRes(R.drawable.myimage)    Drawable image;     @SystemService    SearchManager searchManager;}

Page 63: Native Android Development Practices

sets the layout

Inject another widget or “view”

specify a resource id (it is optional)

44

Beyond Dependency Injection

• Android Annotations(http://code.google.com/p/androidannotations/)

@EActivity(R.layout.myactivity) public class MyActivity extends Activity {     @InjectView     TextView mylabel;     @DrawableRes(R.drawable.myimage)    Drawable image;     @SystemService    SearchManager searchManager;}

Page 64: Native Android Development Practices

sets the layout

Inject another widget or “view”

specify a resource id (it is optional)

Inject objects configured manually

44

Beyond Dependency Injection

• Android Annotations(http://code.google.com/p/androidannotations/)

@EActivity(R.layout.myactivity) public class MyActivity extends Activity {     @InjectView     TextView mylabel;     @DrawableRes(R.drawable.myimage)    Drawable image;     @SystemService    SearchManager searchManager;}

Page 65: Native Android Development Practices

45

Dependency Injection on Android

• The Android way – android applications all have required access to a single

“Application” class– You can override the Application class– Thus, instant singleton!

Page 66: Native Android Development Practices

46

Dependency Injection on Android

• The Android way public class MainApplication extends Application  {     private MyService service;     @Override    public void onCreate() {        super.onCreate();        service = new MyServiceImpl();    }     public MyService getMyService() {        return this.service;    }}

Page 67: Native Android Development Practices

extend the Application

46

Dependency Injection on Android

• The Android way public class MainApplication extends Application  {     private MyService service;     @Override    public void onCreate() {        super.onCreate();        service = new MyServiceImpl();    }     public MyService getMyService() {        return this.service;    }}

Page 68: Native Android Development Practices

register your global singleton services

extend the Application

46

Dependency Injection on Android

• The Android way public class MainApplication extends Application  {     private MyService service;     @Override    public void onCreate() {        super.onCreate();        service = new MyServiceImpl();    }     public MyService getMyService() {        return this.service;    }}

Page 69: Native Android Development Practices

public class MainActivity extends Activity  {     private MyService service;     @Override    public void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        MainApplication app = (MainApplication) getApplication();        service = app.getMyService();    }}

47

Dependency Injection on Android

• The Android way

Page 70: Native Android Development Practices

get a pointer to the Application

public class MainActivity extends Activity  {     private MyService service;     @Override    public void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        MainApplication app = (MainApplication) getApplication();        service = app.getMyService();    }}

47

Dependency Injection on Android

• The Android way

Page 71: Native Android Development Practices

access your service

get a pointer to the Application

public class MainActivity extends Activity  {     private MyService service;     @Override    public void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        MainApplication app = (MainApplication) getApplication();        service = app.getMyService();    }}

47

Dependency Injection on Android

• The Android way

Page 72: Native Android Development Practices

Additional Resources

• Project Home– http://www.springsource.org/spring-android– http://www.springsource.org/spring-mobile

• Sample Code– https://github.com/SpringSource/spring-android-samples.git– https://github.com/SpringSource/spring-mobile-samples.git

• Blog Posts– http://blog.springsource.org

48

Page 73: Native Android Development Practices

© 2011 SpringOne 2GX 2011. All rights reserved. Do not distribute without permission.

Q&A

49