SlideShare una empresa de Scribd logo
1 de 42
Descargar para leer sin conexión
Parsley                        &
                       framework for Flex/Flash/AIR




Alexander Budjakov
Flex Developer
prideconan@gmail.com
Parsley is all about decoupling
Overview
Parsley is Open Source, licensed under the Apache License 2.0
Written by Jens Halm
First version 1.0.RC1 (2007-12-09)
Last version 3.0.0 (2012-02-06)    > 4 years

Parsley is an Application Framework for Flex and Flash Applications built upon an IOC
Container and Messaging Framework that can be used to create highly decoupled
architectures.
Features


           Parsley                           Spicelib
Flexible IOC Container              Command Framework
Dependency Injection                XML-Mapper
Decoupled Bindings                  Reflection API
Messaging Framework                 Logging
Managed Commands
Dynamic View Wiring
Advanced Modularity
Object Lifecycle
Localization
Extensibility
Inversion of Control (IoC)
Inversion of Control (IoC)
 Hollywood Principle: Don't call us, we'll call you.




                           Program logic runs against abstractions
                           such as callbacks
IoC Example
Here is the simplest possible                          Here are a common smells that should lead
IoC component                                          you to refactor to IoC
package com {                                          package com {
   public interface IMap {                                public class GPSNavigator implements INavigator {
      //methods                                              private var map:IMap;
   }                                                         public function GPSNavigator() {
}                                                               this.map = new UkraineMapImpl();
                                                             }
package com {                                                //other methods
   public class GPSNavigator implements INavigator {      }
      private var map:IMap;                            }
      public function GPSNavigator(map:IMap) {

      }
         this.map = map;                                              Some other smells.
      //other methods                                  package com {
   }                                                      public class GPSNavigator implements INavigator {
}                                                            private static var map:IMap = MapFactory.getMap();
                                                             public function GPSNavigator() {
                                                             }
                                                             //other methods
                                                          }
                                                       }


                                                                    It is hard coded
                                                                    Not reusable.
IOC Container
 We may ask for the object from the container and the
 container creates the object and its dependencies


                                              <interface>
    EBookReader
                                                  File


     inject

                     creates
                                  PDFFileImpl               TXTFileImpl

   IoC Container



Parsley is a classic IOC Container. It provides support for Dependency Injection,
Object Lifecycle Management and Messaging
Dependency Injection (DI)
Dependency Injection (DI)
[Inject]       The core feature of any IOC Container




                             How objects obtain references to each other
Dependency Injection (DI)

       You may have these different tools
Dependency Injection (DI)

        You may have these different tools




       OR just one tool with attachments
Dependency Injection (DI)

        You may have these different tools




       OR just one tool with attachments

             This brings us to the Design Principles -
             Program to an interface, not an implementation
Dependency Injection (DI)




    Three ways of classic DI
Dependency Injection (DI)
                        public class Controller {
                           private var model:Model;
                           public function Controller(model:Model) {
Constructor Injection         this.model = model;
                           }
                        }
Dependency Injection (DI)
                        public class Controller {
                           private var model:Model;
                           public function Controller(model:Model) {
Constructor Injection         this.model = model;
                           }
                        }




                        public class Controller {
                           private var _model:Model;
                           public function set model(value:Model):void {
  Setter Injection            _model = value;
                           }
                        }
Dependency Injection (DI)
                        public class Controller {
                           private var model:Model;
                           public function Controller(model:Model) {
Constructor Injection         this.model = model;
                           }
                        }




                        public class Controller {
                           private var _model:Model;
                           public function set model(value:Model):void {
  Setter Injection            _model = value;
                           }
                        }



                        public interface IController {
                           function injectModel(model:Model):void
                        }
 Interface Injection    public class Controller implements IController {
                           private var model:Model;
                           public function injectModel(model:Model):void {
                              this.model = model;
                           }
                        }
NOT Dependency Injection

           public class Controller {
              private var model:Model;
              public function Controller() {
                 model = new Model();
              }
           }


           public class Controller {
              private var model:Model;
              public function Controller() {
                 model = ModelFactory.create(Model);
              }
           }


           public class Controller {
              private var model:Model;
              public function Controller() {
                 model = Model.getInstance();
              }
           }
IoC and DI Benefits
•   Dependency management
•   Simplify the reuse of classes or components
•   Offers configuration flexibility
•   Simplify unit-testing
•   The "cleaner" code
Configuration and Initialization
Configuration and Initialization

       • Telling the IOC Container which classes it
         should manage
   1   • MXML, XML, AS
<?xml version="1.0" encoding="utf-8"?>
UserConfig.mxml   <parsley:Objects xmlns:fx="http://ns.adobe.com/mxml/2009"
                     xmlns:s="library://ns.adobe.com/flex/spark"
                     xmlns:mx="library://ns.adobe.com/flex/mx"
                     xmlns:parsley="http://www.spicefactory.org/parsley">

                  // *hidden imports

                  <fx:Declarations>
                     <parsley:Object id="userModel" type="{Model}" lazy="true"/>

                    <parsley:DynamicObject type="{Counter}">
                       <parsley:Property name="maxCount" value="100" />
                    </parsley:DynamicObject>

                    <parsley:View type="{UsersView}"/>

                    <service:MockUsersService />

                     <parsley:MapCommand type="{GetUsersCommand}"
                                         messageType="{GetUsersMessage}"/>
                  </fx:Declarations>

                  </parsley:Objects>
Configuration and Initialization

       • Telling the IOC Container which classes it
         should manage
   1   • MXML, XML, AS.

       • Configure DI or Messaging for each
         individual class
   2   • MXML, XML, Metadata tags
public class GetUsersCommand {
GetUsersCommand.as
                         [Inject]
                         public var service:IUsersService;

                         [Inject(id="userModel")]
                         public var model:Model;

                         public function execute():AsyncToken {
                            return service.getUsers();
                         }

                         public function result(users:ArrayCollection):void {
                            model.users = users;
                         }
                     }




                     public class UsersView extends SkinnableComponent {
UserView.as
                         [Inject]
                         public var model:Model;

                         [Publish(objectId="selectedUser")]
                         [Bindable]
                         public var seletedUser:User;

                         [MessageHandler(selector="user")]
                         public function externalUserSelection(msg:SelectMessage):void {
                            //do something
                         }
                     }
Configuration and Initialization

       • Telling the IOC Container which classes it
         should manage.
   1   • MXML, XML, AS.

       • Configure DI or Messaging for each
         individual class
   2   • MXML, XML, Metadata tags



       • Initialize IOC Container
   3
<s:Application xmlns:fx="http://ns.adobe.com/mxml/2009"
You can use one big          xmlns:s="library://ns.adobe.com/flex/spark"
configuration file           xmlns:mx="library://ns.adobe.com/flex/mx"
                             xmlns:parsley="http://www.spicefactory.org/parsley"

                             <fx:Declarations>
                                <parsley:ContextBuilder config="{UserConfig}"/>
                             </fx:Declarations>
                          </s:Application>


                          <s:Application xmlns:fx="http://ns.adobe.com/mxml/2009"
Or several files with        xmlns:s="library://ns.adobe.com/flex/spark"
separated configuration      xmlns:mx="library://ns.adobe.com/flex/mx"
                             xmlns:parsley="http://www.spicefactory.org/parsley"

                             <fx:Declarations>
                                <parsley:ContextBuilder>
                                   <parsley:FlexConfig type="{UserConfig}"/>
                                   <parsley:FlexConfig type="{ServiceConfig}"/>
                                   <parsley:FlexConfig type="{MockServiceConfig}"/>
                               </parsley:ContextBuilder
                          </fx:Declarations>
                          </s:Application>



                          ContextBuilder.newBuilder()
Configuration DSL           .config(FlexConfig.forClass(UserConfig))
                            .config(FlexConfig.forClass(ServiceConfig))
                            .config(XmlConfig.forFile("logging.xml"))
                            .build();
Decoupled Bindings
[Publish]
[Subscribe]
[PublishSubscribe]




• This feature is much more dynamic than Dependency Injection.
• It is really more the decoupled equivalent of the typical usage of Flex Bindings.
• The published object does not even have to be a container managed object.
Decoupled Bindings
ActionScript Examples
[Bindable]
[Publish(objectId="selectedUser")]
public var selectedUser:User;

[Subscribe(scope="window")]
public var selectedUser:User;                                             uses Local
[Bindable]
                                                                        SharedObjects
[PublishSubscribe(persistent="true", objectId="selectedUserId")]
public var selectedUserId:int;



MXML Example
<parsley:View type="{UsersView}">
   <parsley:Publish property="selectedUser“ objectId="selectedUser"/>
</parsley:View>
Messaging
[ManagedEvents]
[MessageDispatcher]
[MessageHandler]
[MessageBinding]
[MessageError]




• The exchange messages between objects in a fully decoupled manner (sender
  and the receiver do not have to know each other)
• Messaging Framework is generic, it does not impose a particular usage style
ActionScript Examples
[Event(name="userSelected",type="com.xyz.UserSelectedEvent")]        UserSelectedEvent.as
[ManagedEvents("userSelected, somethingSelected")]
public class UsersView extends SkinnableComponent {                  Event based class
    private function handleUserSelect(user:User):void {
       dispatchEvent(new UserSelectedEvent("userSelected", user));
    }
}

public class UsersView extends SkinnableComponent {
                                                                     UserSeletedMessage.as
    [MessageDispatcher]                                              Simple class
    public var dispatcher:Function;

    private function handleUserSelect(user:User):void {
       dispatcher(new UserSeletedMessage(user));
    }
}



[MessageHandler(type="com.xyz.UserSelectedEvent", messageProperties="user, role“)]
public function handleUserSelect(user:User, role:String):void {
}


[MessageBinding(messageProperty="user", type="com.xyz.UserSelectedEvent")]
public var user:User;
Object Lifecycle
[Init]
[Destroy]

                        Lifecycle phases
      preConfigure   preInit   postInit    preDestroy   postDestroy
Object Lifecycle
[Init]
[Destroy]

                                   Lifecycle phases
        preConfigure            preInit   postInit       preDestroy      postDestroy


The methods marked with [Init] get invoked after the object has been instantiated and all
injections have been processed.
[Init]
public function init():void {
   //
}


The methods marked with [Destroy] get invoked after the Context instance they belong
to has been destroyed with Context.destroy() or when the object was removed from
the Context.
[Destroy]
public function destroy():void {
   //
}
Managed Commands
•   Dynamically add a command to a Context only for the time it executes
•   Declarative way to configure Commands
•   Grouping commands (parallel, sequence, flow)
•   Map command to message
Managed Commands
[CommandResult]                   <parsley:MapCommand type="{GetUserProfileCommand}"/>
[CommandError]
                                  public class GetUserProfileCommand {
[CommandComplete]
[CommandStatus]                       [Inject("userService")]
                                      public var service:RemoteObject;

                                      public function execute(msg:GetUserMessage):AsyncToken {
                                         return service.getUserProfile(msg.userId);
                                      }

                                      public function result(profile:Profile):void {
                                         //
                                      }
                                  }

 [CommandResult]
 public function profileResult(profile:Profile, message:GetUserMessage):void {

 [CommandError]
 public function handleResult(fault:FaultEvent, trigger:GetUserMessage):void {



[Bindable]
[CommandStatus(type="com.xyz.GetUserMessage")]
public var isGettingProfile:Boolean;

<s:Button label="GetProfile" enabled="{isGettingProfile}" click="..." />
Managed Commands
 Declaring Groups in MXML
<parsley:MapCommand messageType="{FindUserMessage}">
   <parsley:CommandSequence>
      <parsley:Command type="{GetUsersCommand}"/>
      <parsley:Command type="{FindUserCommand}"/>
   </parsley:CommandSequence>
</parsley:MapCommand>


<parsley:MapCommand messageType="{FindUserMessage}">
   <parsley:ParallelCommands>
      <parsley:Command type="{FindUserCommand}"/>
      <parsley:Command type="{OutputDataComand}"/>
   </parsley:ParallelCommands>
</parsley:MapCommand>
Building MVC Architectures
Custom Scopes
Custom Scopes
Default scope is global

<parsley:ContextBuilder>                                     Add new “window” scope
   <parsley:FlexConfig type="{UserConfig}"/>
   <parsley:FlexConfig type="{ServiceConfig}"/>
   <parsley:Scope name="window" inherited="true"/>           Change default scope to local.
   <parsley:MessageSettings defaultReceiverScope="local"/>
</parsley:ContextBuilder>




Actionscript Examples
[ManagedEvents("add, remove", scope=“global")]

[MessageDispatcher(scope="local")]
public var dispatcher:Function;

[MessageHandler(selector="add", scope="local")]
public function save (event:UdpateUser):void {

[Subscribe(objectId="selectedUser", scope="window")]
public var selectedUser:User;
Localization
Usual using with flex binding
<s:Label text="{resourceManager.getString('resources', ‘user.profile')}"/>




It is useful for properties of objects managed by the IOC Container
[ResourceBinding(bundle="resources", key="user.profile")]
public var message:String;




MXML Example
<parsley:View type="{ProfileView}">
   <parsley:ResourceBinding property="header" bundle="resources" key="user.profile" />
</parsley:View>
Configuration Properties
       project.properties
       dev_url = http://www.dev.xyz.com
       prod_url = http://www.prod.xyx.com
       version = 1.0.0


Property File compiled into the Application
<fx:Declarations>
   <fx:String id="properties" source="project.properties" />
</fx:Declarations>

<parsley:ContextBuilder
   <parsley:PropertiesString source="{properties}"/>
</parsley:ContextBuilder>


External Property File
<parsley:ContextBuilder
   <parsley:PropertiesFile file="project.properties" />
</parsley:ContextBuilder>


 Using Properties in MXML Configuration
<parsley:Object type="{Config}">
   <parsley:Property name="dev" value="{properties.dev_url}" />
   <parsley:Property name="prod" value="{properties.prod_url}" />
   <parsley:Property name="version" value="{properties.version}" />
</parsley:Object>
Conclusion
Questions?
Understanding




                             Information

Más contenido relacionado

La actualidad más candente

Serialization & De-serialization in Java
Serialization & De-serialization in JavaSerialization & De-serialization in Java
Serialization & De-serialization in JavaInnovationM
 
Core java interview questions
Core java interview questionsCore java interview questions
Core java interview questionsRohit Singh
 
Packages and inbuilt classes of java
Packages and inbuilt classes of javaPackages and inbuilt classes of java
Packages and inbuilt classes of javakamal kotecha
 
Desing Patterns Summary - by Jim Fawcett
Desing Patterns Summary - by Jim FawcettDesing Patterns Summary - by Jim Fawcett
Desing Patterns Summary - by Jim FawcettDareen Alhiyari
 
Java Annotation Processing: A Beginner Walkthrough
Java Annotation Processing: A Beginner WalkthroughJava Annotation Processing: A Beginner Walkthrough
Java Annotation Processing: A Beginner WalkthroughMahfuz Islam Bhuiyan
 
Testable JavaScript: Application Architecture
Testable JavaScript:  Application ArchitectureTestable JavaScript:  Application Architecture
Testable JavaScript: Application ArchitectureMark Trostler
 
Introduction to Robotlegs 2
Introduction to Robotlegs 2Introduction to Robotlegs 2
Introduction to Robotlegs 2Justin J. Moses
 
JavaFX Dependency Injection with FxContainer
JavaFX Dependency Injection with FxContainerJavaFX Dependency Injection with FxContainer
JavaFX Dependency Injection with FxContainerSrikanth Shenoy
 
Java Beans Unit 4(part 2)
Java Beans Unit 4(part 2)Java Beans Unit 4(part 2)
Java Beans Unit 4(part 2)SURBHI SAROHA
 
Hibernate Interview Questions
Hibernate Interview QuestionsHibernate Interview Questions
Hibernate Interview QuestionsSyed Shahul
 

La actualidad más candente (20)

Devoxx 2012 (v2)
Devoxx 2012 (v2)Devoxx 2012 (v2)
Devoxx 2012 (v2)
 
Serialization & De-serialization in Java
Serialization & De-serialization in JavaSerialization & De-serialization in Java
Serialization & De-serialization in Java
 
02 basic java programming and operators
02 basic java programming and operators02 basic java programming and operators
02 basic java programming and operators
 
Java Beans
Java BeansJava Beans
Java Beans
 
ExtJs Basic Part-1
ExtJs Basic Part-1ExtJs Basic Part-1
ExtJs Basic Part-1
 
Core java interview questions
Core java interview questionsCore java interview questions
Core java interview questions
 
Packages and inbuilt classes of java
Packages and inbuilt classes of javaPackages and inbuilt classes of java
Packages and inbuilt classes of java
 
Java basic
Java basicJava basic
Java basic
 
Best interview questions
Best interview questionsBest interview questions
Best interview questions
 
Spring boot
Spring bootSpring boot
Spring boot
 
Desing Patterns Summary - by Jim Fawcett
Desing Patterns Summary - by Jim FawcettDesing Patterns Summary - by Jim Fawcett
Desing Patterns Summary - by Jim Fawcett
 
Java Annotation Processing: A Beginner Walkthrough
Java Annotation Processing: A Beginner WalkthroughJava Annotation Processing: A Beginner Walkthrough
Java Annotation Processing: A Beginner Walkthrough
 
Testable JavaScript: Application Architecture
Testable JavaScript:  Application ArchitectureTestable JavaScript:  Application Architecture
Testable JavaScript: Application Architecture
 
Introduction to Robotlegs 2
Introduction to Robotlegs 2Introduction to Robotlegs 2
Introduction to Robotlegs 2
 
JavaFX Dependency Injection with FxContainer
JavaFX Dependency Injection with FxContainerJavaFX Dependency Injection with FxContainer
JavaFX Dependency Injection with FxContainer
 
Java Beans Unit 4(part 2)
Java Beans Unit 4(part 2)Java Beans Unit 4(part 2)
Java Beans Unit 4(part 2)
 
Advance Java
Advance JavaAdvance Java
Advance Java
 
Core java
Core javaCore java
Core java
 
Technical Interview
Technical InterviewTechnical Interview
Technical Interview
 
Hibernate Interview Questions
Hibernate Interview QuestionsHibernate Interview Questions
Hibernate Interview Questions
 

Similar a Parsley & Flex

Inversion of Control and Dependency Injection
Inversion of Control and Dependency InjectionInversion of Control and Dependency Injection
Inversion of Control and Dependency InjectionDinesh Sharma
 
Pointer to implementation idiom
Pointer to implementation idiomPointer to implementation idiom
Pointer to implementation idiomDimitrios Platis
 
SOLID & IoC Principles
SOLID & IoC PrinciplesSOLID & IoC Principles
SOLID & IoC PrinciplesPavlo Hodysh
 
Application Frameworks: The new kids on the block
Application Frameworks: The new kids on the blockApplication Frameworks: The new kids on the block
Application Frameworks: The new kids on the blockRichard Lord
 
Android architecture
Android architecture Android architecture
Android architecture Trong-An Bui
 
Java design patterns
Java design patternsJava design patterns
Java design patternsShawn Brito
 
Building maintainable app #droidconzg
Building maintainable app #droidconzgBuilding maintainable app #droidconzg
Building maintainable app #droidconzgKristijan Jurković
 
Architecting ActionScript 3 applications using PureMVC
Architecting ActionScript 3 applications using PureMVCArchitecting ActionScript 3 applications using PureMVC
Architecting ActionScript 3 applications using PureMVCmarcocasario
 
Design pattern proxy介紹 20130805
Design pattern proxy介紹 20130805Design pattern proxy介紹 20130805
Design pattern proxy介紹 20130805LearningTech
 
Design pattern proxy介紹 20130805
Design pattern proxy介紹 20130805Design pattern proxy介紹 20130805
Design pattern proxy介紹 20130805LearningTech
 
MicroProfile, Docker, Kubernetes, Istio and Open Shift lab @dev nexus
MicroProfile, Docker, Kubernetes, Istio and Open Shift lab @dev nexusMicroProfile, Docker, Kubernetes, Istio and Open Shift lab @dev nexus
MicroProfile, Docker, Kubernetes, Istio and Open Shift lab @dev nexusEmily Jiang
 
WPF and Prism 4.1 Workshop at BASTA Austria
WPF and Prism 4.1 Workshop at BASTA AustriaWPF and Prism 4.1 Workshop at BASTA Austria
WPF and Prism 4.1 Workshop at BASTA AustriaRainer Stropek
 
Java programming concept
Java programming conceptJava programming concept
Java programming conceptSanjay Gunjal
 
OpenWebBeans and DeltaSpike at ApacheCon
OpenWebBeans and DeltaSpike at ApacheConOpenWebBeans and DeltaSpike at ApacheCon
OpenWebBeans and DeltaSpike at ApacheConos890
 
Introduction to design_patterns
Introduction to design_patternsIntroduction to design_patterns
Introduction to design_patternsamitarcade
 

Similar a Parsley & Flex (20)

Dependency injection in iOS
Dependency injection in iOSDependency injection in iOS
Dependency injection in iOS
 
Inversion of Control and Dependency Injection
Inversion of Control and Dependency InjectionInversion of Control and Dependency Injection
Inversion of Control and Dependency Injection
 
Pointer to implementation idiom
Pointer to implementation idiomPointer to implementation idiom
Pointer to implementation idiom
 
SOLID & IoC Principles
SOLID & IoC PrinciplesSOLID & IoC Principles
SOLID & IoC Principles
 
Application Frameworks: The new kids on the block
Application Frameworks: The new kids on the blockApplication Frameworks: The new kids on the block
Application Frameworks: The new kids on the block
 
Android architecture
Android architecture Android architecture
Android architecture
 
Java design patterns
Java design patternsJava design patterns
Java design patterns
 
Building maintainable app #droidconzg
Building maintainable app #droidconzgBuilding maintainable app #droidconzg
Building maintainable app #droidconzg
 
Architecting ActionScript 3 applications using PureMVC
Architecting ActionScript 3 applications using PureMVCArchitecting ActionScript 3 applications using PureMVC
Architecting ActionScript 3 applications using PureMVC
 
Rcp by example
Rcp by exampleRcp by example
Rcp by example
 
Building maintainable app
Building maintainable appBuilding maintainable app
Building maintainable app
 
Design pattern proxy介紹 20130805
Design pattern proxy介紹 20130805Design pattern proxy介紹 20130805
Design pattern proxy介紹 20130805
 
Design pattern proxy介紹 20130805
Design pattern proxy介紹 20130805Design pattern proxy介紹 20130805
Design pattern proxy介紹 20130805
 
MicroProfile, Docker, Kubernetes, Istio and Open Shift lab @dev nexus
MicroProfile, Docker, Kubernetes, Istio and Open Shift lab @dev nexusMicroProfile, Docker, Kubernetes, Istio and Open Shift lab @dev nexus
MicroProfile, Docker, Kubernetes, Istio and Open Shift lab @dev nexus
 
WPF and Prism 4.1 Workshop at BASTA Austria
WPF and Prism 4.1 Workshop at BASTA AustriaWPF and Prism 4.1 Workshop at BASTA Austria
WPF and Prism 4.1 Workshop at BASTA Austria
 
Java programming concept
Java programming conceptJava programming concept
Java programming concept
 
OpenWebBeans and DeltaSpike at ApacheCon
OpenWebBeans and DeltaSpike at ApacheConOpenWebBeans and DeltaSpike at ApacheCon
OpenWebBeans and DeltaSpike at ApacheCon
 
Introduction to design_patterns
Introduction to design_patternsIntroduction to design_patterns
Introduction to design_patterns
 
Desiging for Modularity with Java 9
Desiging for Modularity with Java 9Desiging for Modularity with Java 9
Desiging for Modularity with Java 9
 
6976.ppt
6976.ppt6976.ppt
6976.ppt
 

Último

Dev Dives: Streamline document processing with UiPath Studio Web
Dev Dives: Streamline document processing with UiPath Studio WebDev Dives: Streamline document processing with UiPath Studio Web
Dev Dives: Streamline document processing with UiPath Studio WebUiPathCommunity
 
TeamStation AI System Report LATAM IT Salaries 2024
TeamStation AI System Report LATAM IT Salaries 2024TeamStation AI System Report LATAM IT Salaries 2024
TeamStation AI System Report LATAM IT Salaries 2024Lonnie McRorey
 
Training state-of-the-art general text embedding
Training state-of-the-art general text embeddingTraining state-of-the-art general text embedding
Training state-of-the-art general text embeddingZilliz
 
DevoxxFR 2024 Reproducible Builds with Apache Maven
DevoxxFR 2024 Reproducible Builds with Apache MavenDevoxxFR 2024 Reproducible Builds with Apache Maven
DevoxxFR 2024 Reproducible Builds with Apache MavenHervé Boutemy
 
Sample pptx for embedding into website for demo
Sample pptx for embedding into website for demoSample pptx for embedding into website for demo
Sample pptx for embedding into website for demoHarshalMandlekar2
 
Passkey Providers and Enabling Portability: FIDO Paris Seminar.pptx
Passkey Providers and Enabling Portability: FIDO Paris Seminar.pptxPasskey Providers and Enabling Portability: FIDO Paris Seminar.pptx
Passkey Providers and Enabling Portability: FIDO Paris Seminar.pptxLoriGlavin3
 
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptxThe Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptxLoriGlavin3
 
DevEX - reference for building teams, processes, and platforms
DevEX - reference for building teams, processes, and platformsDevEX - reference for building teams, processes, and platforms
DevEX - reference for building teams, processes, and platformsSergiu Bodiu
 
Take control of your SAP testing with UiPath Test Suite
Take control of your SAP testing with UiPath Test SuiteTake control of your SAP testing with UiPath Test Suite
Take control of your SAP testing with UiPath Test SuiteDianaGray10
 
Anypoint Exchange: It’s Not Just a Repo!
Anypoint Exchange: It’s Not Just a Repo!Anypoint Exchange: It’s Not Just a Repo!
Anypoint Exchange: It’s Not Just a Repo!Manik S Magar
 
Digital Identity is Under Attack: FIDO Paris Seminar.pptx
Digital Identity is Under Attack: FIDO Paris Seminar.pptxDigital Identity is Under Attack: FIDO Paris Seminar.pptx
Digital Identity is Under Attack: FIDO Paris Seminar.pptxLoriGlavin3
 
Advanced Computer Architecture – An Introduction
Advanced Computer Architecture – An IntroductionAdvanced Computer Architecture – An Introduction
Advanced Computer Architecture – An IntroductionDilum Bandara
 
Developer Data Modeling Mistakes: From Postgres to NoSQL
Developer Data Modeling Mistakes: From Postgres to NoSQLDeveloper Data Modeling Mistakes: From Postgres to NoSQL
Developer Data Modeling Mistakes: From Postgres to NoSQLScyllaDB
 
"Subclassing and Composition – A Pythonic Tour of Trade-Offs", Hynek Schlawack
"Subclassing and Composition – A Pythonic Tour of Trade-Offs", Hynek Schlawack"Subclassing and Composition – A Pythonic Tour of Trade-Offs", Hynek Schlawack
"Subclassing and Composition – A Pythonic Tour of Trade-Offs", Hynek SchlawackFwdays
 
WordPress Websites for Engineers: Elevate Your Brand
WordPress Websites for Engineers: Elevate Your BrandWordPress Websites for Engineers: Elevate Your Brand
WordPress Websites for Engineers: Elevate Your Brandgvaughan
 
Tampa BSides - Chef's Tour of Microsoft Security Adoption Framework (SAF)
Tampa BSides - Chef's Tour of Microsoft Security Adoption Framework (SAF)Tampa BSides - Chef's Tour of Microsoft Security Adoption Framework (SAF)
Tampa BSides - Chef's Tour of Microsoft Security Adoption Framework (SAF)Mark Simos
 
"ML in Production",Oleksandr Bagan
"ML in Production",Oleksandr Bagan"ML in Production",Oleksandr Bagan
"ML in Production",Oleksandr BaganFwdays
 
Nell’iperspazio con Rocket: il Framework Web di Rust!
Nell’iperspazio con Rocket: il Framework Web di Rust!Nell’iperspazio con Rocket: il Framework Web di Rust!
Nell’iperspazio con Rocket: il Framework Web di Rust!Commit University
 
Rise of the Machines: Known As Drones...
Rise of the Machines: Known As Drones...Rise of the Machines: Known As Drones...
Rise of the Machines: Known As Drones...Rick Flair
 
How to write a Business Continuity Plan
How to write a Business Continuity PlanHow to write a Business Continuity Plan
How to write a Business Continuity PlanDatabarracks
 

Último (20)

Dev Dives: Streamline document processing with UiPath Studio Web
Dev Dives: Streamline document processing with UiPath Studio WebDev Dives: Streamline document processing with UiPath Studio Web
Dev Dives: Streamline document processing with UiPath Studio Web
 
TeamStation AI System Report LATAM IT Salaries 2024
TeamStation AI System Report LATAM IT Salaries 2024TeamStation AI System Report LATAM IT Salaries 2024
TeamStation AI System Report LATAM IT Salaries 2024
 
Training state-of-the-art general text embedding
Training state-of-the-art general text embeddingTraining state-of-the-art general text embedding
Training state-of-the-art general text embedding
 
DevoxxFR 2024 Reproducible Builds with Apache Maven
DevoxxFR 2024 Reproducible Builds with Apache MavenDevoxxFR 2024 Reproducible Builds with Apache Maven
DevoxxFR 2024 Reproducible Builds with Apache Maven
 
Sample pptx for embedding into website for demo
Sample pptx for embedding into website for demoSample pptx for embedding into website for demo
Sample pptx for embedding into website for demo
 
Passkey Providers and Enabling Portability: FIDO Paris Seminar.pptx
Passkey Providers and Enabling Portability: FIDO Paris Seminar.pptxPasskey Providers and Enabling Portability: FIDO Paris Seminar.pptx
Passkey Providers and Enabling Portability: FIDO Paris Seminar.pptx
 
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptxThe Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
 
DevEX - reference for building teams, processes, and platforms
DevEX - reference for building teams, processes, and platformsDevEX - reference for building teams, processes, and platforms
DevEX - reference for building teams, processes, and platforms
 
Take control of your SAP testing with UiPath Test Suite
Take control of your SAP testing with UiPath Test SuiteTake control of your SAP testing with UiPath Test Suite
Take control of your SAP testing with UiPath Test Suite
 
Anypoint Exchange: It’s Not Just a Repo!
Anypoint Exchange: It’s Not Just a Repo!Anypoint Exchange: It’s Not Just a Repo!
Anypoint Exchange: It’s Not Just a Repo!
 
Digital Identity is Under Attack: FIDO Paris Seminar.pptx
Digital Identity is Under Attack: FIDO Paris Seminar.pptxDigital Identity is Under Attack: FIDO Paris Seminar.pptx
Digital Identity is Under Attack: FIDO Paris Seminar.pptx
 
Advanced Computer Architecture – An Introduction
Advanced Computer Architecture – An IntroductionAdvanced Computer Architecture – An Introduction
Advanced Computer Architecture – An Introduction
 
Developer Data Modeling Mistakes: From Postgres to NoSQL
Developer Data Modeling Mistakes: From Postgres to NoSQLDeveloper Data Modeling Mistakes: From Postgres to NoSQL
Developer Data Modeling Mistakes: From Postgres to NoSQL
 
"Subclassing and Composition – A Pythonic Tour of Trade-Offs", Hynek Schlawack
"Subclassing and Composition – A Pythonic Tour of Trade-Offs", Hynek Schlawack"Subclassing and Composition – A Pythonic Tour of Trade-Offs", Hynek Schlawack
"Subclassing and Composition – A Pythonic Tour of Trade-Offs", Hynek Schlawack
 
WordPress Websites for Engineers: Elevate Your Brand
WordPress Websites for Engineers: Elevate Your BrandWordPress Websites for Engineers: Elevate Your Brand
WordPress Websites for Engineers: Elevate Your Brand
 
Tampa BSides - Chef's Tour of Microsoft Security Adoption Framework (SAF)
Tampa BSides - Chef's Tour of Microsoft Security Adoption Framework (SAF)Tampa BSides - Chef's Tour of Microsoft Security Adoption Framework (SAF)
Tampa BSides - Chef's Tour of Microsoft Security Adoption Framework (SAF)
 
"ML in Production",Oleksandr Bagan
"ML in Production",Oleksandr Bagan"ML in Production",Oleksandr Bagan
"ML in Production",Oleksandr Bagan
 
Nell’iperspazio con Rocket: il Framework Web di Rust!
Nell’iperspazio con Rocket: il Framework Web di Rust!Nell’iperspazio con Rocket: il Framework Web di Rust!
Nell’iperspazio con Rocket: il Framework Web di Rust!
 
Rise of the Machines: Known As Drones...
Rise of the Machines: Known As Drones...Rise of the Machines: Known As Drones...
Rise of the Machines: Known As Drones...
 
How to write a Business Continuity Plan
How to write a Business Continuity PlanHow to write a Business Continuity Plan
How to write a Business Continuity Plan
 

Parsley & Flex

  • 1. Parsley & framework for Flex/Flash/AIR Alexander Budjakov Flex Developer prideconan@gmail.com
  • 2. Parsley is all about decoupling
  • 3. Overview Parsley is Open Source, licensed under the Apache License 2.0 Written by Jens Halm First version 1.0.RC1 (2007-12-09) Last version 3.0.0 (2012-02-06) > 4 years Parsley is an Application Framework for Flex and Flash Applications built upon an IOC Container and Messaging Framework that can be used to create highly decoupled architectures.
  • 4. Features Parsley Spicelib Flexible IOC Container Command Framework Dependency Injection XML-Mapper Decoupled Bindings Reflection API Messaging Framework Logging Managed Commands Dynamic View Wiring Advanced Modularity Object Lifecycle Localization Extensibility
  • 6. Inversion of Control (IoC) Hollywood Principle: Don't call us, we'll call you. Program logic runs against abstractions such as callbacks
  • 7. IoC Example Here is the simplest possible Here are a common smells that should lead IoC component you to refactor to IoC package com { package com { public interface IMap { public class GPSNavigator implements INavigator { //methods private var map:IMap; } public function GPSNavigator() { } this.map = new UkraineMapImpl(); } package com { //other methods public class GPSNavigator implements INavigator { } private var map:IMap; } public function GPSNavigator(map:IMap) { } this.map = map; Some other smells. //other methods package com { } public class GPSNavigator implements INavigator { } private static var map:IMap = MapFactory.getMap(); public function GPSNavigator() { } //other methods } } It is hard coded Not reusable.
  • 8. IOC Container We may ask for the object from the container and the container creates the object and its dependencies <interface> EBookReader File inject creates PDFFileImpl TXTFileImpl IoC Container Parsley is a classic IOC Container. It provides support for Dependency Injection, Object Lifecycle Management and Messaging
  • 10. Dependency Injection (DI) [Inject] The core feature of any IOC Container How objects obtain references to each other
  • 11. Dependency Injection (DI) You may have these different tools
  • 12. Dependency Injection (DI) You may have these different tools OR just one tool with attachments
  • 13. Dependency Injection (DI) You may have these different tools OR just one tool with attachments This brings us to the Design Principles - Program to an interface, not an implementation
  • 14. Dependency Injection (DI) Three ways of classic DI
  • 15. Dependency Injection (DI) public class Controller { private var model:Model; public function Controller(model:Model) { Constructor Injection this.model = model; } }
  • 16. Dependency Injection (DI) public class Controller { private var model:Model; public function Controller(model:Model) { Constructor Injection this.model = model; } } public class Controller { private var _model:Model; public function set model(value:Model):void { Setter Injection _model = value; } }
  • 17. Dependency Injection (DI) public class Controller { private var model:Model; public function Controller(model:Model) { Constructor Injection this.model = model; } } public class Controller { private var _model:Model; public function set model(value:Model):void { Setter Injection _model = value; } } public interface IController { function injectModel(model:Model):void } Interface Injection public class Controller implements IController { private var model:Model; public function injectModel(model:Model):void { this.model = model; } }
  • 18. NOT Dependency Injection public class Controller { private var model:Model; public function Controller() { model = new Model(); } } public class Controller { private var model:Model; public function Controller() { model = ModelFactory.create(Model); } } public class Controller { private var model:Model; public function Controller() { model = Model.getInstance(); } }
  • 19. IoC and DI Benefits • Dependency management • Simplify the reuse of classes or components • Offers configuration flexibility • Simplify unit-testing • The "cleaner" code
  • 21. Configuration and Initialization • Telling the IOC Container which classes it should manage 1 • MXML, XML, AS
  • 22. <?xml version="1.0" encoding="utf-8"?> UserConfig.mxml <parsley:Objects xmlns:fx="http://ns.adobe.com/mxml/2009" xmlns:s="library://ns.adobe.com/flex/spark" xmlns:mx="library://ns.adobe.com/flex/mx" xmlns:parsley="http://www.spicefactory.org/parsley"> // *hidden imports <fx:Declarations> <parsley:Object id="userModel" type="{Model}" lazy="true"/> <parsley:DynamicObject type="{Counter}"> <parsley:Property name="maxCount" value="100" /> </parsley:DynamicObject> <parsley:View type="{UsersView}"/> <service:MockUsersService /> <parsley:MapCommand type="{GetUsersCommand}" messageType="{GetUsersMessage}"/> </fx:Declarations> </parsley:Objects>
  • 23. Configuration and Initialization • Telling the IOC Container which classes it should manage 1 • MXML, XML, AS. • Configure DI or Messaging for each individual class 2 • MXML, XML, Metadata tags
  • 24. public class GetUsersCommand { GetUsersCommand.as [Inject] public var service:IUsersService; [Inject(id="userModel")] public var model:Model; public function execute():AsyncToken { return service.getUsers(); } public function result(users:ArrayCollection):void { model.users = users; } } public class UsersView extends SkinnableComponent { UserView.as [Inject] public var model:Model; [Publish(objectId="selectedUser")] [Bindable] public var seletedUser:User; [MessageHandler(selector="user")] public function externalUserSelection(msg:SelectMessage):void { //do something } }
  • 25. Configuration and Initialization • Telling the IOC Container which classes it should manage. 1 • MXML, XML, AS. • Configure DI or Messaging for each individual class 2 • MXML, XML, Metadata tags • Initialize IOC Container 3
  • 26. <s:Application xmlns:fx="http://ns.adobe.com/mxml/2009" You can use one big xmlns:s="library://ns.adobe.com/flex/spark" configuration file xmlns:mx="library://ns.adobe.com/flex/mx" xmlns:parsley="http://www.spicefactory.org/parsley" <fx:Declarations> <parsley:ContextBuilder config="{UserConfig}"/> </fx:Declarations> </s:Application> <s:Application xmlns:fx="http://ns.adobe.com/mxml/2009" Or several files with xmlns:s="library://ns.adobe.com/flex/spark" separated configuration xmlns:mx="library://ns.adobe.com/flex/mx" xmlns:parsley="http://www.spicefactory.org/parsley" <fx:Declarations> <parsley:ContextBuilder> <parsley:FlexConfig type="{UserConfig}"/> <parsley:FlexConfig type="{ServiceConfig}"/> <parsley:FlexConfig type="{MockServiceConfig}"/> </parsley:ContextBuilder </fx:Declarations> </s:Application> ContextBuilder.newBuilder() Configuration DSL .config(FlexConfig.forClass(UserConfig)) .config(FlexConfig.forClass(ServiceConfig)) .config(XmlConfig.forFile("logging.xml")) .build();
  • 27. Decoupled Bindings [Publish] [Subscribe] [PublishSubscribe] • This feature is much more dynamic than Dependency Injection. • It is really more the decoupled equivalent of the typical usage of Flex Bindings. • The published object does not even have to be a container managed object.
  • 28. Decoupled Bindings ActionScript Examples [Bindable] [Publish(objectId="selectedUser")] public var selectedUser:User; [Subscribe(scope="window")] public var selectedUser:User; uses Local [Bindable] SharedObjects [PublishSubscribe(persistent="true", objectId="selectedUserId")] public var selectedUserId:int; MXML Example <parsley:View type="{UsersView}"> <parsley:Publish property="selectedUser“ objectId="selectedUser"/> </parsley:View>
  • 29. Messaging [ManagedEvents] [MessageDispatcher] [MessageHandler] [MessageBinding] [MessageError] • The exchange messages between objects in a fully decoupled manner (sender and the receiver do not have to know each other) • Messaging Framework is generic, it does not impose a particular usage style
  • 30. ActionScript Examples [Event(name="userSelected",type="com.xyz.UserSelectedEvent")] UserSelectedEvent.as [ManagedEvents("userSelected, somethingSelected")] public class UsersView extends SkinnableComponent { Event based class private function handleUserSelect(user:User):void { dispatchEvent(new UserSelectedEvent("userSelected", user)); } } public class UsersView extends SkinnableComponent { UserSeletedMessage.as [MessageDispatcher] Simple class public var dispatcher:Function; private function handleUserSelect(user:User):void { dispatcher(new UserSeletedMessage(user)); } } [MessageHandler(type="com.xyz.UserSelectedEvent", messageProperties="user, role“)] public function handleUserSelect(user:User, role:String):void { } [MessageBinding(messageProperty="user", type="com.xyz.UserSelectedEvent")] public var user:User;
  • 31. Object Lifecycle [Init] [Destroy] Lifecycle phases preConfigure preInit postInit preDestroy postDestroy
  • 32. Object Lifecycle [Init] [Destroy] Lifecycle phases preConfigure preInit postInit preDestroy postDestroy The methods marked with [Init] get invoked after the object has been instantiated and all injections have been processed. [Init] public function init():void { // } The methods marked with [Destroy] get invoked after the Context instance they belong to has been destroyed with Context.destroy() or when the object was removed from the Context. [Destroy] public function destroy():void { // }
  • 33. Managed Commands • Dynamically add a command to a Context only for the time it executes • Declarative way to configure Commands • Grouping commands (parallel, sequence, flow) • Map command to message
  • 34. Managed Commands [CommandResult] <parsley:MapCommand type="{GetUserProfileCommand}"/> [CommandError] public class GetUserProfileCommand { [CommandComplete] [CommandStatus] [Inject("userService")] public var service:RemoteObject; public function execute(msg:GetUserMessage):AsyncToken { return service.getUserProfile(msg.userId); } public function result(profile:Profile):void { // } } [CommandResult] public function profileResult(profile:Profile, message:GetUserMessage):void { [CommandError] public function handleResult(fault:FaultEvent, trigger:GetUserMessage):void { [Bindable] [CommandStatus(type="com.xyz.GetUserMessage")] public var isGettingProfile:Boolean; <s:Button label="GetProfile" enabled="{isGettingProfile}" click="..." />
  • 35. Managed Commands Declaring Groups in MXML <parsley:MapCommand messageType="{FindUserMessage}"> <parsley:CommandSequence> <parsley:Command type="{GetUsersCommand}"/> <parsley:Command type="{FindUserCommand}"/> </parsley:CommandSequence> </parsley:MapCommand> <parsley:MapCommand messageType="{FindUserMessage}"> <parsley:ParallelCommands> <parsley:Command type="{FindUserCommand}"/> <parsley:Command type="{OutputDataComand}"/> </parsley:ParallelCommands> </parsley:MapCommand>
  • 38. Custom Scopes Default scope is global <parsley:ContextBuilder> Add new “window” scope <parsley:FlexConfig type="{UserConfig}"/> <parsley:FlexConfig type="{ServiceConfig}"/> <parsley:Scope name="window" inherited="true"/> Change default scope to local. <parsley:MessageSettings defaultReceiverScope="local"/> </parsley:ContextBuilder> Actionscript Examples [ManagedEvents("add, remove", scope=“global")] [MessageDispatcher(scope="local")] public var dispatcher:Function; [MessageHandler(selector="add", scope="local")] public function save (event:UdpateUser):void { [Subscribe(objectId="selectedUser", scope="window")] public var selectedUser:User;
  • 39. Localization Usual using with flex binding <s:Label text="{resourceManager.getString('resources', ‘user.profile')}"/> It is useful for properties of objects managed by the IOC Container [ResourceBinding(bundle="resources", key="user.profile")] public var message:String; MXML Example <parsley:View type="{ProfileView}"> <parsley:ResourceBinding property="header" bundle="resources" key="user.profile" /> </parsley:View>
  • 40. Configuration Properties project.properties dev_url = http://www.dev.xyz.com prod_url = http://www.prod.xyx.com version = 1.0.0 Property File compiled into the Application <fx:Declarations> <fx:String id="properties" source="project.properties" /> </fx:Declarations> <parsley:ContextBuilder <parsley:PropertiesString source="{properties}"/> </parsley:ContextBuilder> External Property File <parsley:ContextBuilder <parsley:PropertiesFile file="project.properties" /> </parsley:ContextBuilder> Using Properties in MXML Configuration <parsley:Object type="{Config}"> <parsley:Property name="dev" value="{properties.dev_url}" /> <parsley:Property name="prod" value="{properties.prod_url}" /> <parsley:Property name="version" value="{properties.version}" /> </parsley:Object>