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

Introducing DeftJS

Introducing DeftJS

Essential extensions for enterprise web and mobile application development with Ext JS and Sencha Touch

ryancampbell

April 19, 2012
Tweet

Other Decks in Technology

Transcript

  1. Universal Mind | Introducing DeftJS Essential extensions for enterprise web

    and mobile application development with Ext JS and Sencha Touch. Thursday, April 19, 12
  2. Universal Mind | Introducing DeftJS About Me Hi I’m Ryan!

    Solutions Architect at Universal Mind Flash, iOS and Web Development @bobjim on Twitter ryancampbell.com on the Web Thursday, April 19, 12
  3. Universal Mind | Identity Guide 2010 About DeftJS Started by

    the great John Yanarella Open source (MIT) Full test suite (using Jasmine) JavaScript and CoffeeScript implementations Essential extensions for enterprise web and mobile application development with Ext JS and Sencha Touch. deftjs.org github.com/deftjs/DeftJS @deftjs on Twitter Has a sweet logo! Thursday, April 19, 12
  4. Universal Mind | Introducing DeftJS Development Team John Yanarella (Creator)

    David Tucker Ryan Campbell (Hey that’s me!) Anyone else? Thursday, April 19, 12
  5. Universal Mind | Introducing DeftJS Goals Approachability Builds on familiar

    Ext JS API syntax conventions. Simplicity Eliminates boilerplate code Testability Promotes loose coupling through class annotation driven dependency injection. Extensibility Takes advantage of extend and mixins Reusability Enables business layer code reuse between Ext JS and Sencha Touch applications. Thursday, April 19, 12
  6. Universal Mind | Introducing DeftJS Features IoC Container Provides class

    annotation driven dependency injection. Maps dependencies by user-defined identifiers. Resolves dependencies by class instance, factory function or value. Supports singleton and prototype resolution of class instance and factory function dependencies. Offers eager and lazy instantiation of dependencies. Injects dependencies into Ext JS class configs and properties before the class constructor is executed. Thursday, April 19, 12
  7. Universal Mind | Introducing DeftJS Features MVC with View Controllers

    Provides class annotation driven association between a given view and its view controller. Clarifies the role of the controller - i.e. controlling a view and delegating work to injected business services (ex. Stores). Supports multiple independent instances of a given view, each with their own view controller instance. Reduces memory usage by automatically creating and destroying view controllers in tandem with their associated views. Supports concise configuration for referencing view components and registering event listeners with view controller methods. Integrates with the view destruction lifecycle to allow the view controller to potentially cancel removal and destruction. Simplifies clean-up by automatically removing view and view component references and event listeners. Thursday, April 19, 12
  8. Universal Mind | Introducing DeftJS Features Promises and Deferreds Provides

    an elegant way to represent a ‘future value’ resulting from an asynchronous operation. Offers a consistent, readable API for registering success, failure, cancellation or progress callbacks. Allows chaining of transformation and processing of future values. Simplifies processing of a set of future values via utility functions including all(), any(), map() and reduce(). Implements the CommonJS Promises/A specification. Thursday, April 19, 12
  9. Universal Mind | Introducing DeftJS API Injector Configuration Deft.Injector.configure({ contactStore:

    'MyApp.store.ContactStore', contactManager: 'MyApp.manager.ContactManager', ... }); Creates singletons of classes mapped by identifiers Thursday, April 19, 12
  10. Universal Mind | Introducing DeftJS API Constructor Params Deft.Injector.configure({ contactStore:

    { className: 'MyApp.store.ContactStore', parameters: [{ proxy: { type: 'ajax', url: '/contacts.json', reader: { type: 'json', root: 'contacts' } } }] }, contactManager: 'MyApp.manager.ContactManager', ... }); Thursday, April 19, 12
  11. Universal Mind | Introducing DeftJS API Singleton vs Prototype Deft.Injector.configure({

    contactManager: { className: 'MyApp.manager.ContactManager', singleton: false }, ... }); Thursday, April 19, 12
  12. Universal Mind | Introducing DeftJS API Eager vs Lazy (Default)

    Deft.Injector.configure({ preferences: { className: 'MyApp.preferences.Preferences', eager: true }, ... }); Thursday, April 19, 12
  13. Universal Mind | Introducing DeftJS API Factory Functions Deft.Injector.configure({ contactStore:

    { fn: function() { if ( useMocks ) { return Ext.create( 'MyApp.mock.store.ContactStore' ); } else { return Ext.create( 'MyApp.store.ContactStore' ); } }, eager: true }, contactManager: { fn: function( instance ) { if ( instance.session.getIsAdmin() ) { return Ext.create( 'MyApp.manager.admin.ContactManager' ); } else { return Ext.create( 'MyApp.manager.user.ContactManager' ); } }, singleton: false }, ... }); Thursday, April 19, 12
  14. Universal Mind | Introducing DeftJS API Injectable Values Deft.Injector.configure({ brandedApplicationName:

    { value: "Contact Manager" }, versionNumber: { value: 1.0 }, modules: { value: [ 'contacts', 'customers', 'orders' ] }, ... }); Thursday, April 19, 12
  15. Universal Mind | Introducing DeftJS API Add the Deft.Mixin.Injectable mixin

    Ext.define( 'MyApp.manager.ContactManager', { extend: 'MyApp.manager.AbstractManager', mixins: [ 'Deft.mixin.Injectable' ], ... }); Thursday, April 19, 12
  16. Universal Mind | Introducing DeftJS API Specify what to inject

    Ext.define( 'MyApp.manager.ContactManager', { extend: 'MyApp.manager.AbstractManager', mixins: [ 'Deft.mixin.Injectable' ], inject: [ 'contactStore' ], ... }); Thursday, April 19, 12
  17. Universal Mind | Introducing DeftJS API Optionally specify the property

    or config name to inject in to Ext.define( 'MyApp.manager.ContactManager', { extend: 'MyApp.manager.AbstractManager', mixins: [ 'Deft.mixin.Injectable' ], inject: { store: 'contactStore' }, ... }); Thursday, April 19, 12
  18. Universal Mind | Introducing DeftJS API Deft.Mixin.Injectable Ext.define( 'MyApp.manager.ContactManager', {

    extend: 'MyApp.manager.AbstractManager', mixins: [ 'Deft.mixin.Injectable' ], inject: { store: 'contactStore' }, config: { store: null }, constructor: function( config ) { this.initConfig( config ); // this.getStore() will return the injected value. return this.callParent( arguments ) } ... }); Thursday, April 19, 12
  19. Universal Mind | Introducing DeftJS API View Controllers (this is

    where I actually helped!) Thursday, April 19, 12
  20. Universal Mind | Introducing DeftJS API Specifiy what ViewController controls

    your view Ext.define( 'MyApp.view.ContactsView', { extend: 'Ext.panel.Panel', mixins: [ 'Deft.mixin.Controllable' ], controller: 'MyApp.controller.ContactsViewController' ... }); Add Deft.mixin.Controllable mixin Thursday, April 19, 12
  21. Universal Mind | Introducing DeftJS API Specifiy what ViewController controls

    your view Ext.define( 'MyApp.view.ContactsView', { extend: 'Ext.panel.Panel', mixins: [ 'Deft.mixin.Controllable' ], controller: 'MyApp.controller.ContactsViewController' ... }); Specify the controller class Thursday, April 19, 12
  22. Universal Mind | Introducing DeftJS API Specifiy what ViewController controls

    your view Ext.define( 'MyApp.view.ContactsView', { extend: 'Ext.panel.Panel', mixins: [ 'Deft.mixin.Controllable' ], controller: 'MyApp.controller.ContactsViewController' ... }); View must extend Ext.Component or things will blow up Thursday, April 19, 12
  23. Universal Mind | Introducing DeftJS API Define a View Controller

    Ext.define( 'MyApp.controller.ContactsViewController', { extend: 'Deft.mvc.ViewController', ... }); Simply extend Deft.mvc.ViewController Thursday, April 19, 12
  24. Universal Mind | Introducing DeftJS API Define the control of

    your view Ext.define( 'MyApp.controller.ContactsViewController', { extend: 'Deft.mvc.ViewController', ... control: { submitButton: 'panel > button[text="Submit"]', cancelButton: 'panel > button[text="Cancel"]', ... } ... }); Thursday, April 19, 12
  25. Universal Mind | Introducing DeftJS API Map components by query

    Ext.define( 'MyApp.controller.ContactsViewController', { extend: 'Deft.mvc.ViewController', ... control: { submitButton: 'panel > button[text="Submit"]', cancelButton: 'panel > button[text="Cancel"]', ... } ... }); Query for component. Uses view.query(selector) Thursday, April 19, 12
  26. Universal Mind | Introducing DeftJS API Map components by query

    Ext.define( 'MyApp.controller.ContactsViewController', { extend: 'Deft.mvc.ViewController', ... control: { submitButton: 'panel > button[text="Submit"]', cancelButton: 'panel > button[text="Cancel"]', ... } ... init: function() { // getSubmitButton() accessor will be automatically created. this.getSubmitButton().disable(); return this.callParent( arguments ); } ... }); Creates getter method based on identifier Thursday, April 19, 12
  27. Universal Mind | Introducing DeftJS API Map components by itemId

    Ext.define( 'MyApp.controller.ContactsViewController', { extend: 'Deft.mvc.ViewController', ... control: { // indicates the Button in the view has an itemId of 'submitButton' submitButton: true, ... } }); Alternatively, use itemId Thursday, April 19, 12
  28. Universal Mind | Introducing DeftJS API Add a listener Ext.define(

    'MyApp.controller.ContactsViewController', { extend: 'Deft.mvc.ViewController', ... control: { submitButton: 'click': 'onSubmitButtonClick' } ... onSubmitButtonClick: function() { // executed in the view controller's scope ... } ... }); Thursday, April 19, 12
  29. Universal Mind | Introducing DeftJS API If you like complexity..

    Ext.define( 'MyApp.controller.ContactsViewController', { extend: 'Deft.mvc.ViewController', ... control: { submitButton: selector: 'panel > button[text="Submit"]' listeners: 'click': 'onSubmitButtonClick' } ... }); Thursday, April 19, 12
  30. Universal Mind | Introducing DeftJS API Add listeners to the

    view Ext.define( 'MyApp.controller.ContactsViewController', { extend: 'Deft.mvc.ViewController', ... control: { view: 'show': 'onViewShow' 'hide': 'onViewHide' } ... init: function() { this.getView().show() return this.callParent( arguments ); } }); Use view as the identifier Thursday, April 19, 12
  31. Universal Mind | Introducing DeftJS API Add listeners to the

    view Ext.define( 'MyApp.controller.ContactsViewController', { extend: 'Deft.mvc.ViewController', ... control: { view: 'show': 'onViewShow' 'hide': 'onViewHide' } ... init: function() { this.getView().show() return this.callParent( arguments ); } }); View instance always available through getView() method Thursday, April 19, 12
  32. Universal Mind | Introducing DeftJS API Add a init() function

    Ext.define( 'MyApp.controller.ContactsViewController', { extend: 'Deft.mvc.ViewController', ... control: { ... } ... init: function() { // all accessors will have been created // all event listeners will have been added return this.callParent( arguments ); } }); For ExtJS called after view dispatches “afterrender” event For Sencha called after view dispatches “initiallize” event Thursday, April 19, 12
  33. Universal Mind | Introducing DeftJS API Add a destroy() function

    Ext.define( 'MyApp.controller.ContactsViewController', { extend: 'Deft.mvc.ViewController', ... control: { ... } ... destroy: function() { if (this.hasUnsavedChanges) { // cancel destruction return false } // burn baby burn return this.callParent( arguments ); } }); Called when the view dispatches “beforedistroy” event Thursday, April 19, 12
  34. Universal Mind | Introducing DeftJS API Cancel the destroy() Ext.define(

    'MyApp.controller.ContactsViewController', { extend: 'Deft.mvc.ViewController', ... control: { ... } ... destroy: function() { if (this.hasUnsavedChanges) { // cancel destruction return false } // burn baby burn return this.callParent( arguments ); } }); Cancelable! Thursday, April 19, 12
  35. Universal Mind | Introducing DeftJS API Injection and View Controllers

    working together Ext.define( 'MyApp.controller.ContactsViewController', { extend: 'Deft.mvc.ViewController', mixins: [ 'Deft.mixin.Injectable' ] inject: [ 'contactStore' ] ... control: { refreshButton: 'click': 'onRefreshButtonClick' } ... onRefreshButtonClick: function() { contactStore.load() } }); Configure the injection Thursday, April 19, 12
  36. Universal Mind | Introducing DeftJS API Injection and View Controllers

    working together Ext.define( 'MyApp.controller.ContactsViewController', { extend: 'Deft.mvc.ViewController', mixins: [ 'Deft.mixin.Injectable' ] inject: [ 'contactStore' ] ... control: { refreshButton: 'click': 'onRefreshButtonClick' } ... onRefreshButtonClick: function() { contactStore.load() } }); Configure the refresh button click handler Thursday, April 19, 12
  37. Universal Mind | Introducing DeftJS API Injection and View Controllers

    working together Ext.define( 'MyApp.controller.ContactsViewController', { extend: 'Deft.mvc.ViewController', mixins: [ 'Deft.mixin.Injectable' ] inject: [ 'contactStore' ] ... control: { refreshButton: 'click': 'onRefreshButtonClick' } ... onRefreshButtonClick: function() { contactStore.load() } }); Re-load the contact store when the handler fires Thursday, April 19, 12
  38. Universal Mind | Introducing DeftJS API Promises Based on CommonJS

    Promises/A spec Implements: when() all() any() map() reduce() then() always() cancel() Thursday, April 19, 12
  39. Universal Mind | Introducing DeftJS Version History 0.6.2 - Added

    support for View Controller event listener options. Ext JS 4.1rc3 compatibility fixes. 0.6.1 - Sencha Touch compatibility fixes. 0.6.0 - Introducing View Controller and Controllable. Preview release of Deferred and Promise. 0.1.1 - Preview release, added Jasmine test suite. 0.1.0 - Preview release, introducing an IoC container for dependency injection Thursday, April 19, 12
  40. Universal Mind | Introducing DeftJS Roadmap Deferreds / Promises (in

    progress) Forum (in progress) FAQ Example Ext JS and Sencha Touch applications Routing Navigation - support for hierarchical views, route-aware AOP with an Ext JS-style API (i.e. JSON style configuration) Occasionally-Connected Store (simplifing online / offline capabilities) Thursday, April 19, 12