Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Bending APIs to Your Will Using Windows Phone

Kamran Ayub
September 25, 2013

Bending APIs to Your Will Using Windows Phone

A talk I gave at the Minnesota Developers Conference 2013 on building connected apps on the Windows Phone platform

Kamran Ayub

September 25, 2013
Tweet

More Decks by Kamran Ayub

Other Decks in Programming

Transcript

  1. Bending APIs to Your Will
    Using Windows Phone 8
    Kamran Ayub (MDC 2013)
    [email protected]
    @kamranayub
    kamranicus.com
    Follow along:
    http://mdc.ilmservice.com/download

    View Slide

  2. About Me
    Connected Apps
    App Walkthrough
    MVVM
    Async/Await
    Offline Caching
    Event Aggregator
    Tips & Tricks
    Closing Comments
    Questions
    Let’s talk about bending APIs
    http://www.fanpop.com/clubs/avatar-the-last-airbender/images/461375/title/aang-air-bending-wallpaper

    View Slide

  3. About me

    View Slide

  4. Play (too many) video games
    Watch (too many) TV shows
    Hang out with (just enough) friends
    Am getting married (thanks Cassie!)
    Other than developing software, I…

    View Slide

  5. The other woman in my life
    Chalupa, thanks
    for keeping me
    company while I
    code.

    View Slide

  6. Started programming in 2001
    Classic ASP
    , HTML & CSS (FrontPage)
    Moved onto ASP
    .NET 1.1
    VB.NET, Web Forms, HTML & CSS (Server d)
    Spent some time freelancing
    PHP
    , MySQL, ASP
    .NET, C#, HTML & CSS (“hand-crafted”)
    Got a job in college
    PHP
    , MySQL, HTML & CSS (Actually OK)
    Got hired at General Mills (3 years ago)
    ASP
    .NET 4.0/4.5, ASP
    .NET MVC, C#, HTML & CSS
    Meanwhile, after hours…
    JavaScript frameworks, ASP
    .NET Web API, Windows Phone apps, Windows 8 apps, open source
    Where I’m Coming From

    View Slide

  7. Coderbits Profile

    View Slide

  8. Keep Track of My Games
    keeptrackofmygames.com

    View Slide

  9. Centwise
    centwiseapp.com

    View Slide

  10. Underscore-KO
    Mashup library that adds Underscore.js functions to Knockout arrays
    Giantbomb-CSharp
    .NET API SDK for GiantBomb site
    .JSON
    Tiny dynamic JSON API to parse and create JSON
    Other random gists and scripts
    Other contributions
    github.com/kamranayub

    View Slide

  11. Connected Apps

    View Slide

  12. It’s easy to answer the question…

    View Slide

  13. What kind of app
    should I build?

    View Slide

  14. Ask yourself 3 questions

    View Slide

  15. 1. Is there a website I use a lot?

    View Slide

  16. 2. Would I use it on my phone?

    View Slide

  17. 3. Can I interface with it in any way?

    View Slide

  18. If the answer to all three questions is YES,
    THERE’S YOUR NEXT APP

    View Slide

  19. Notice what questions I left out

    View Slide

  20. I didn’t ask
    Is there already an app for it?
    Doesn’t matter, it probably sucks or it’s
    missing something.

    View Slide

  21. I didn’t ask
    Is there a RESTful API for it?
    As long as there’s a programmatic way to
    access data on the site, REST or not, you can
    create a front-end for it.
    Also, it’s probably not really RESTful.

    View Slide

  22. I didn’t ask
    Can I make money off it?
    Let the app speak for itself before trying to
    think of ways to make money off it.
    And whatever you do, provide a way for people to try before they buy or offer in-app upgrades.

    View Slide

  23. I didn’t ask
    Is there a website someone else uses a lot?
    If you don’t use it regularly, chances are good
    you’ll miss what’s really important for the
    mobile experience.

    View Slide

  24. Let’s do a little brainstorming session

    View Slide

  25. Think about all the
    websites you use in a typical week

    View Slide

  26. Then, for each site, think about whether or
    not there’s a public API of some sort
    If you’re at home, research!

    View Slide

  27. Here are my results (for myself)

    View Slide

  28. Websites I use in a typical week
    Website Has a way to access data Website Has a way to access data
    StackOverflow Yes Mint No
    Facebook Yes Medium Sort of (Microformats)
    Feedly Yes GiantBomb Yes
    Amazon Yes Reddit Yes
    Gmail Yes GameTrailers Limited (RSS feeds)
    Forecast.io Yes Wikipedia Yes
    Tweetdeck (Twitter) Yes Codeplex Yes
    Github Yes Splitwise Yes
    MSDN No Springpad Yes
    Youtube Yes
    Foursquare Yes
    USAA No
    Steam Store Yes

    View Slide

  29. Even in my (limited) list, there are already
    potential app ideas!
    Don’t let the lack of any APIs get you down either, you can build your own as well.

    View Slide

  30. Still looking for inspiration?
    There are always niche needs that need to be met…

    View Slide

  31. Building Connected Apps

    View Slide

  32. MVVM
    Async / Await
    Event Aggregator
    Offline Caching / Storage
    Patterns

    View Slide

  33. Caliburn.Micro (or equivalent MVVM)
    MVVM framework to speed up development
    Microsoft.Bcl.Async
    Async/Await support, even for WP7.1+
    Microsoft.Net.Http
    Easy-to-use lightweight async-compatible HttpClient
    Windows Phone Toolkit
    Provides tons of controls
    Modern UI Icons
    modernuiicons.com
    Essential Packages and Tools

    View Slide

  34. GovTalk is a soon-to-be-released
    Windows Phone application that makes
    it easy to contact and learn about your
    congressional representatives.
    It is built on top of the public Sunlight
    Labs API.
    GovTalk Walkthrough

    View Slide

  35. MVVM

    View Slide

  36. Model View
    View
    Model
    Model-View-ViewModel
    • State
    • Domain
    • Renders the
    interface to the
    user
    • Accepts input
    from the user
    • Logic for
    controlling the
    view
    • Transforms
    Model to View-
    friendly model
    (View Model)
    Services
    • Dependencies
    • Business logic
    • Encapsulate
    device features

    View Slide

  37. MVVM Framework
    Use Caliburn to simplify your code when building apps
    Install Caliburn.Micro Nuget package
    This installs the required framework
    Install Caliburn.Micro.Start Nuget package
    This gets you started with using Caliburn
    Bonus: Install Caliburn.Micro.BindableAppBar to make it easier to create
    dynamic context-sensitive app bars
    Guess who made this?

    View Slide

  38. Async / Await

    View Slide

  39. Connecting to Sunlight Labs
    Wrap your connection-logic into an API client class
    Create a repository to manage working with the API client and
    any local storage solutions
    Register the two services with Caliburn
    Inject and consume the repository in your view models

    View Slide

  40. App Request Flow
    Connect
    Send
    Request
    Receive
    Response
    Activate
    View Model
    Request
    Data
    Cached or
    Live Data?
    Client-Side API/Server-Side

    View Slide

  41. Create an API Client Interface

    View Slide

  42. API Client: Wrap the connection logic
    It’s easy to use the HttpClient to connect to an API
    Create a generic request helper to assist in sending requests

    View Slide

  43. API Client: Generic request method
    First, check if we have a network available Then, set up the request
    Next, we send the request.

    View Slide

  44. API Client: Generic request method (cont’d)
    If there is no response content, we’ll
    throw.
    Then, we deserialize the response
    content (using JSON.NET in this case) and
    returning the expected type.
    Gotcha: “Root Element”
    Example response from server
    {
    "legislator": {
    "first_name": "Kamran",
    "last_name": "Ayub"
    }
    }

    View Slide

  45. API Client: Call the private helper

    View Slide

  46. Register with container
    Use the bootstrapper code and add your own services
    Your repository and client can be
    PerRequest but I’ve used Singleton for
    my app.
    Since the main page is a Panorama, I’ve
    also made that a Singleton as well.
    SettingsModel is used to store
    cacheable settings, so that’s a Singleton.

    View Slide

  47. Dependency Injection
    Finally, inject your dependencies into your view model’s ctor
    In addition, you can inject other view models as well,
    either as an instance
    public MyRepsViewModel(SettingsModel settings)
    or a factory that generates new instances:
    public MyRepsViewModel(Func settingsFactory)

    View Slide

  48. Offline Caching / Storage

    View Slide

  49. Feeding the Data Into the View
    Load the data when the view is activated or initialized
    Bind the data to an observable
    Display the data in the UI in a sexy fashion
    Cache the data

    View Slide

  50. Caliburn View Model Request Lifecycle
    Request View Model
    • MyRepsViewModel
    • Inject dependencies
    Find Corresponding
    View
    • MyRepsView.xaml
    View Model Lifecycle
    • OnInitialize
    • OnActivate
    • OnDeactivate

    View Slide

  51. Load the data when the view model activates

    View Slide

  52. Representatives is a flat collection that I use for caching and storage.
    Expose public observable properties
    Due to differences in the API
    for WP7/WP8, you might
    need to use compile
    constants.
    LongListSelector differs for
    each platform.

    View Slide

  53. Caliburn exposes any public properties on
    the view model for binding
    Bind to those properties in the XAML
    Caliburn let’s you use mock data in Visual Studio design view, very useful for UI design

    View Slide

  54. Then, you need a parameterless constructor on your view
    model. Set up any fake data you want in the ctor.
    Use Caliburn’s InDesignMode to determine whether or not to set
    up your mocked data.
    You will see your fake data populated in the design-time view in
    Visual Studio, making it way easier to design!
    Design-Time Binding

    View Slide

  55. Finally, cache the data
    For simple apps, you can use Caliburn’s StorageHandler

    View Slide

  56. Event Aggregator

    View Slide

  57. How do you communicate between two view models?
    Pub/Sub mechanism
    Caliburn provides the IEventAggregator service
    View
    Model 1
    View
    Model 2
    IEventAggregator
    Publish Subscribe

    View Slide

  58. Inject the aggregator
    To send events
    Call the Publish method

    View Slide

  59. To receive events
    Subscribe when view model is activated
    Unsubscribe when view model is deactivated
    Implement the IHandle interface

    View Slide

  60. Event Aggregator: Perfect for Panoramas
    UserLocationUpdated

    View Slide

  61. Event Aggregator: Avoid Anti-Patterns
    Use consistent event interfaces (naming, structure, etc.)
    Avoid using event messaging for internal events (single VM)
    Be cognizant of other events triggering your events and plan
    accordingly
    Don’t modify the message contents (keep it immutable)
    Order of subscribers shouldn’t matter

    View Slide

  62. Summary

    View Slide

  63. Use a framework like Caliburn to provide structure
    Connect to your APIs intelligently and cache data
    Degrade gracefully (connection, platform, device features, etc.)
    Be respectful of your users time and constraints
    Creating compelling connected apps

    View Slide

  64. What makes a great connected app?
    Offline Support
    Globalization &
    Localization
    Error Reporting &
    Logging
    Full API Support
    Extra App-Only
    Features
    Live Tiles
    Push Notifications
    Hardware
    Integration
    Features that make any app great Features that make a connected app great
    Queuing Write
    Methods
    Background Tasks
    Local Device
    Caching

    View Slide

  65. Tips & Tricks

    View Slide

  66. Network Service
    Listens to network
    changes
    Uses event aggregation to
    notify view models of
    network changes
    Hooked into Caliburn’s DI
    system

    View Slide

  67. Network Service (Cont’d)
    View models can listen for the event and handle appropriately
    Registered as a singleton with Caliburn container

    View Slide

  68. MainViewModel.cs
    Supporting Deep Linking (“The Right Way”)
    Pinned
    Tile
    • User taps tile on start
    screen
    • URI
    MainViewModel.xaml
    ?LegislatorId=xxx
    Main
    Page
    •Caliburn injects
    query string
    values into view
    model
    •LegislatorId
    Navigate
    forward
    • Preserves
    back stack
    • Smooth UX

    View Slide

  69. Extending the Navigation Service
    You can extend the navigation service easily using
    extension methods
    In a POST-Redirect-GET pattern, it works a little
    differently in a native app environment but the same
    logic applies. Redirect then raise a message:

    View Slide

  70. OAuth
    Use the AsyncOAuth library (works well with HttpClient)
    Use DPAPI to store consumer access token and secret
    Use WebBrowser control to embed OAuth login page

    View Slide

  71. Supporting Cancellation
    Create a new CancellationTokenSource for each request
    Pass the CancellationTokenSource.Token to your
    repository/client
    If you need to cancel, call CancellationTokenSource.Cancel()
    Handle the TaskCanceledException

    View Slide

  72. Logging Errors
    Use the BugSense SDK (WP8/WP7)
    Register the handler on application start
    Done!

    View Slide

  73. Thank you!
    Kamran Ayub
    [email protected]
    @kamranayub
    kamranicus.com
    Slides
    http://mdc.ilmservice.com/download
    http://speakerdeck.com/kamranayub
    Evaluations
    http://mdc.ilmservice.com/eval

    View Slide