suganya's Blog

Just another WordPress.com weblog

Sample program

<?xml version=”1.0″ encoding=”utf-8″?>
<mx:Application xmlns:mx=”http://www.adobe.com/2006/mxml” layout=”absolute”>
<mx:Script>
<![CDATA[
import mx.core.Application;
import mx.controls.SWFLoader;
private var gameswf:SWFLoader;
private var can:Canvas;
private var back_btn:Button;
public function onPlay_game(eve:MouseEvent):void
{
can=new Canvas();
back_btn=new Button();
gameswf=new SWFLoader();
gameswf.source="game.swf";
gameswf.width=500;
gameswf.height=400;
back_btn.width=70;
back_btn.height=30;
back_btn.x=175;
back_btn.y=330;
back_btn.label="Back";
back_btn.addEventListener(MouseEvent.CLICK,onPlay_back);
game_play.visible=false;
addChild(can);
can.addChild(gameswf);
can.addChild(back_btn);
}
public function onPlay_back(eve:MouseEvent):void

{
can.removeChild(gameswf);
can.removeChild(back_btn);
viewstack1.selectedChild=games;
}
]]>
</mx:Script>
<mx:ApplicationControlBar x=”93″ y=”59″ width=”411″ height=”5%”>
<mx:Button label=”Home” click=”viewstack1.selectedChild=home”/>
<mx:Button label=”About Us” click=”viewstack1.selectedChild=aboutus”/>
<mx:Button label=”Gallery” click=”viewstack1.selectedChild=gallery”/>
<mx:Button label=”Games” click=”viewstack1.selectedChild=games”/>
<mx:Button label=”ContactUs” click=”viewstack1.selectedChild=contactus”/>
</mx:ApplicationControlBar>
<mx:ViewStack x=”13″ y=”134″ id=”viewstack1″ width=”569″ height=”80%”>
<mx:Canvas label=”Home” width=”100%” height=”100%” id=”home” color=”#D9EDF1″>
<mx:ColorPicker x=”175″ y=”205″/>

</mx:Canvas>
<mx:Canvas label=”Aboutus” width=”100%” height=”100%” id=”aboutus” color=”#49CCE8″>
<mx:DataGrid x=”129″ y=”167″>
<mx:columns>
<mx:DataGridColumn headerText=”Column 1″ dataField=”col1″/>
<mx:DataGridColumn headerText=”Column 2″ dataField=”col2″/>
<mx:DataGridColumn headerText=”Column 3″ dataField=”col3″/>
</mx:columns>
</mx:DataGrid>

</mx:Canvas>
<mx:Canvas label=”Gallery” width=”100%” height=”100%” id=”gallery” color=”#BED32E”>
<mx:DateChooser x=”182″ y=”219″/>
</mx:Canvas>
<mx:Canvas label=”Games” width=”100%” height=”100%” id=”games” verticalScrollPolicy=”off”>
<mx:Image id=”game1″ x=”33″ y=”74″ width=”158″ height=”134″ source=”Images/image2.jpeg” click=”viewstack1.selectedChild=imagecan”/>
<mx:Image id=”game2″ x=”23″ y=”433″ width=”158″ height=”134″ source=”Images/image3.jpeg”/>
<mx:Image id=”game3″ x=”223.5″ y=”266″ width=”158″ height=”134″ source=”Images/image4.jpeg”/>
<mx:Image id=”game4″ x=”223.5″ y=”433″ width=”158″ height=”134″ source=”Images/image5.jpg”/>
<mx:Image id=”game5″ x=”23″ y=”255″ width=”158″ height=”134″ source=”Images/image6.jpg”/>
<mx:Image id=”game6″ x=”213″ y=”74″ width=”158″ height=”134″ source=”Images/image1.jpeg”/>
</mx:Canvas>
<mx:Canvas label=”ContactUs” width=”100%” height=”100%” id=”contactus” color=”#6E40B4″>
<mx:ProgressBar x=”212″ y=”198″/>
</mx:Canvas>
<mx:Canvas id=”imagecan” name=”imgcan” width=”700″ height=”500″
horizontalCenter=”0″ verticalCenter=”0″
verticalScrollPolicy=”off”>
<mx:Text x=”168″ y=”10″ text=”Gamedescription” width=”239″ height=”22″ fontWeight=”bold” fontSize=”14″/>
<mx:Button id=”game_play” x=”168″ y=”317″ label=”Play Game” click=”onPlay_game(event)” visible=”true”/>
<mx:Text x=”91″ y=”54″ text=”Identify the required color of the balloon correctly &#xa;and fill it with suitable color.To fill the color, select the color&#xa;from the palette and click on the balloon to fill color. You will &#xa;get bonus points by giving color to the parachute. &#xa;Reach the target  in each level within given duration&#xa;and play further levels.&#xa;&#xa;Game control.&#xa;Use mouse to interact.&#xa;To bring the game to pause, click on the pause button.&#xa;To mute the sound, click the mute button.” width=”348″ height=”177″ textAlign=”left” fontWeight=”bold” fontSize=”10″/>
</mx:Canvas>

</mx:ViewStack>
</mx:Application>

November 21, 2009 Posted by suganyakalaimani | Drupalwithflex | | No Comments Yet

Link to image

main application:

<?xml version=”1.0″ encoding=”utf-8″?>
<mx:Application xmlns:mx=”http://www.adobe.com/2006/mxml” layout=”absolute”
creationComplete=”init();”>

<mx:Script>
<![CDATA[
import mx.controls.Alert;
import mx.containers.Canvas;
import mx.controls.Image;
private var comp_img:imagecomp=new imagecomp();
private var img:Image;
private var can:Canvas;

public function init():void
{
img=new Image();
img.source="Images/helium_balloons.jpg";
img.x=50;
img.y=50;
img.addEventListener(MouseEvent.CLICK,onClick_show);
Application.application.addChild(img);

}
public function onClick_show(eve:MouseEvent):void
{
img.buttonMode=true;
img.useHandCursor=true;
Application.application.removeChild(img);
Application.application.addChild(comp_img);
}
]]>
</mx:Script>

</mx:Application>

imagecomp.mxml:

<?xml version=”1.0″ encoding=”utf-8″?>
<mx:Canvas name=”imgcan” xmlns:mx=”http://www.adobe.com/2006/mxml” width=”700″ height=”500″ horizontalCenter=”0″ verticalCenter=”0″
verticalScrollPolicy=”off”>
<mx:Text x=”168″ y=”10″ text=”Gamedescription” width=”239″ height=”22″ fontWeight=”bold” fontSize=”14″/>
<mx:Button id=”game_play” x=”168″ y=”317″ label=”Play Game” click=”onPlay_game(event)”/>
<mx:Text x=”91″ y=”54″ text=”Identify the required color of the balloon correctly &#xa;and fill it with suitable color.To fill the color, select the color&#xa;from the palette and click on the balloon to fill color. You will &#xa;get bonus points by giving color to the parachute. &#xa;Reach the target  in each level within given duration&#xa;and play further levels.&#xa;&#xa;Game control.&#xa;Use mouse to interact.&#xa;To bring the game to pause, click on the pause button.&#xa;To mute the sound, click the mute button.” width=”348″ height=”177″ textAlign=”left” fontWeight=”bold” fontSize=”10″/>

<mx:Script>
<![CDATA[
import mx.core.Application;
import mx.controls.SWFLoader;
private var gameswf:SWFLoader;
private var can:Canvas;
private var back_btn:Button;
public function onPlay_game(eve:MouseEvent):void
{
can=new Canvas();
back_btn=new Button();
gameswf=new SWFLoader();
gameswf.source="game.swf";
gameswf.width=500;
gameswf.height=400;
back_btn.width=70;
back_btn.height=30;
back_btn.x=175;
back_btn.y=330;
back_btn.label="Back";
addChild(can);
can.addChild(gameswf);
can.addChild(back_btn);
}

]]>
</mx:Script>

</mx:Canvas>

 

November 18, 2009 Posted by suganyakalaimani | Drupalwithflex | | No Comments Yet

Flex & Drupal login ( Actionscript remoteObjects )

Hello People!

It has been a long time since my last post so I’ve decided to post something found interesting. Long ago, seeking a faster way to create my websites I found CMS called Drupal, this CMS provides a lot of very important aspects of a web, such as content creation, scalability and robustness. But as you know this blog is basically based on the Flash platform technologies, not Drupal, But I was interested in joining the two sides and make a login.

To follow this tutorial is recommended that you have some knowledge of Drupal and Flex

Requirements

Have a server ( local or remote ) with Drupal

Note:

This tutorial was mad with Drupal 6.x but I think you can do it perfectly with the previous version 5.x

To complete this tutorial you will need some modules that do not come with the core ( amfphp and services ) as well as the amfphp server. To install the modules simply unzip them inside drupal_folder/modules but i recommend creating a folder drupal_folder/sites/all/modules and copy them inside. Then it¡s imperative you download the amfphp server and copy the the folder inside the amfphp. ( You should have something like this drupal_folder/modules/amfphp/amfphp, the first amfphp is the module logic and the second is the server.

Now we must activate some options of the modules we just install

- In Services activate Services ( it’s the only option, you can fail here xD )
- In Services – servers activate AMFPHP
- In Services – services activate System Service and User Service

You can go to the Drupal Services option and click on the AMFPHP server, you would see a default message from the server, if you can’t see it you may missed something.

One more thing before view the Actionscript code, in the Drupal Services menu, inside the Settings Tab, disable the “Use Keys” option which is used to provide security when we connect from external applications, and althought this tutorial might be used to create an external login too, we won’t use keys to simplify the tutorial ( maybe in a next post ) however we will leave the “Use sessid” active.

Once you have activate that options ( remember to save once you’ve activated ) we need to give permissions for anyone to access the services, if not an anonymous user couldn’t login because it couldn’t access them. Now we can begin to create our AS3

Before giving the Actionscript code I would like to discuss some aspects of the code:

While creating remoteObjects is easier in mxml I always prefer to avoid it using Actionscript but this meant more time until I found the way to communicate Flex with Drupal because I couldn’t how I could pass parameters to Drupal, if you’ve encountered the same problem, I hope this tutorial help.

Note:
Before communicating with any other service you must have your sessid, you’ll do that connecting with the system.connect service, which will return you an object containing the sessid. If you do not know if your services are working correctly because of your code or because of Drupal, you can execute them directly from the Drupal Services menu, there you can find all the parameters you need to execute any service.

Using MXML remoteObject is implemented like this ( using user.get as example ) :

sessid
1

This service is used to get the information about the user with a certain uid ( user id ). In order to do that you must be logged in.

In Actionscript should be something like this:

drupal.source = “user”
var params:Object = new Object();
params.sessid = sessid;
params.uid = 1
Operation(drupal.getOperation( “get” )).argumentNames = ["sessid","uid"]
drupal.getOperation( “get” ).arguments = params;
drupal.getOperation( “get” ).send();

The lined marked in bold is the one I was searching during hours, this is automatically implemented in the mxml component, if you don’t put it Drupal will always return “Missing Arguments”

Finally, the code:

<?xml version=”1.0″ encoding=”utf-8″?>
<mx:Application
layout=”absolute”
xmlns:mx=”http://www.adobe.com/2006/mxml”

applicationComplete=”init()”><mx:Script>
<![CDATA[
import mx.rpc.remoting.mxml.Operation;
import mx.messaging.channels.StreamingAMFChannel;
import mx.rpc.events.FaultEvent;
import mx.rpc.events.ResultEvent;
import mx.rpc.remoting.mxml.RemoteObject;

private var drupal:RemoteObject;
private var sessid:String = "";

private function init():void{
drupal = new RemoteObject();
drupal.endpoint = "http://localhost/drupal/services/amfphp"

drupal.destination = "amfphp";

drupal.addEventListener( ResultEvent.RESULT, handler_drupalResult );

drupal.addEventListener( FaultEvent.FAULT, handler_drupalFault );}

private function handler_drupalResult( event:ResultEvent ):void{
log( event.toString() )
log( event.result.toString() )
try{
sessid = event.result.sessid
LBL_sessid.text = event.result.sessid}
catch ( error:Error )

{}}

private function handler_drupalFault( event:FaultEvent ):void{
log( event.toString() )}

private function handler_systemConnect( event:Event ):void{
drupal.source = "system"
drupal.getOperation( "connect" ).send();}

private function handler_login( event:Event ):void{
drupal.source = "user"
var params:Object = new Object();
params.sessid = sessid;
params.username = TI_user.text;
params.password = TI_password.text
Operation(drupal.getOperation( "login" )).argumentNames = ["sessid","username","password"]
drupal.getOperation( “login” ).arguments = params
drupal.getOperation( “login” ).send();}

private function handler_logout( event:Event ):void{
drupal.source = “user”
drupal.getOperation( “logout” ).send( { sessid:sessid } ); }

private function handler_get( event:Event ):void
{
drupal.source = “user”

var params:Object = new Object();
params.sessid = sessid;
params.uid = 1
Operation(drupal.getOperation( “get” )).argumentNames = ["sessid","uid"]
drupal.getOperation( “get” ).arguments = params;

drupal.getOperation( “get” ).send();}

private function log( message:String ):void{
var d:Date = new Date();

TA_results.text += “[" + d.toLocaleTimeString() + "]\n” + message + “\n\n”;}]]>
</mx:Script>
<mx:TextArea x=”356″ y=”38″ width=”467″ height=”558″ id=”TA_results”/>
<mx:Panel x=”63″ y=”38″ width=”285″ height=”75″ layout=”absolute” title=”System”>
<mx:Button x=”15″ y=”10″ label=”connect” width=”235″ click=”handler_systemConnect( event )”/>
</mx:Panel>
<mx:Panel x=”831″ y=”38″ width=”285″ height=”558″ layout=”absolute” title=”Data”>
<mx:Label x=”10″ y=”10″ text=”sessid:”/>
<mx:Label x=”10″ y=”27″ width=”245″ fontWeight=”bold” id=”LBL_sessid”/>
</mx:Panel>
<mx:Panel x=”63″ y=”121″ width=”285″ height=”251″ layout=”absolute” title=”User”>
<mx:Button x=”15″ y=”88″ label=”logout” width=”235″ click=”handler_logout( event )”/>
<mx:Button x=”15″ y=”63″ label=”login” width=”235″ click=”handler_login( event )”/>
<mx:Button x=”15″ y=”145″ label=”get” width=”235″ click=”handler_get( event )”/>
<mx:Label x=”15″ y=”10″ text=”user:”/>
<mx:Label x=”15″ y=”121″ text=”user ID:”/>
<mx:Label x=”15″ y=”33″ text=”password:”/>
<mx:TextInput x=”86″ y=”8″ width=”164″ id=”TI_user” text=””/>
<mx:TextInput x=”86″ y=”119″ width=”164″ id=”TI_uid” text=”1″/>
<mx:TextInput x=”86″ y=”31″ width=”164″ id=”TI_password” text=””/>

</mx:Panel></mx:Application>

September 16, 2009 Posted by suganyakalaimani | Flex Java Integration | | No Comments Yet

Flex Automation

Flex Automation issue reporting – QTP log enabling

This section is for a user of flex automation with the following details.

1. You are a flex automaiton user .

2. You are using QTP as the testing tool

3. You are facing some issue with the automaiton and you would like to know the details of QTP calls or you would like take the help of Adobe Flex Automation team for resolving your issue.

If you like to inform Adobe about your issue – What you need to do?

1. File an issue in JIRA – the open Adobe bug base. http://bugs.adobe.com/jira Project FLEXENT

2. Have a log file related to QTP interaction and provide the log file also as a part of the bug details.

The steps below describes how to enabling the logging for QTP 9.2 (or lesser versions)

Steps to enable QTP logging.

1. Go to the mercury installation/bin directory say: “C:\Program Files\Mercury Interactive\QuickTest Professional\bin” and run MicLogSetting.exe


2. Select the log settings as:
Level: MicLogLevelDebug2
Folder:C:\Program Files\Mercury Interactive\QuickTest Professional\
Selected Categories:LogCatPackTEA

Ensure the max size of the file is reasonably high (else once the size reaches the maximum limit another file is created. So please ensure that all newly created files are identified)

Note: Please zip these files before uploading them to bug base.


3. Run QTP and repeat the operation which is found non functioning (please try to have minimum steps in your application recorded or executed and those are related to the issue. Else the log file can be huge )


4. A log file would have been generated like C:\Program Files\Mercury Interactive\QuickTest Professional\MicLogFile_QTPro_pid1912_11_32_32.html

Add comment September 29, 2008 <!–ranikumar–>

Automation Issues – controls non clickable

I am trying to cover the common issues faced by automation customers of Adobe Flex.

Issue Description :
When the application is compiled with  automation libraries some controls become non click-able. (Without automation libraries, the controls behaves perfectly fine).Please note that issue is different from controls not recording right events.

Reason:
In application layout, a container is overlapping the controls. Containers are invisible, and without automation, there are no event listeners to the containers. Hence all operation on the controls under the containers also work.
But when automation libraries are included, containers gets listeners registered, hence it will not pass to the containers physically present under them. (You can visualize the container as a transparent sheet kept on controls)
There are two samples below, working and no working case, when automation libraries are enabled.

Non working case:

<mx:Application xmlns:mx=”http://www.adobe.com/2006/mxml” layout=”absolute”>

<mx:Button label=”Hi” click=”{l1.text=’button clicked’}” />

<mx:VBox width=”100%” height=”100%” alpha=”0″  id=”vb1″>

<mx:Spacer height=”20″ />

<mx:Label id=”l1″ text=”button not clicked” />

</mx:VBox>

</mx:Application>

The application above does not allow the button to be clicked, if it is compiled with automation libraries. Without automation libraries it can be clicked.Reason is that, the invisible VBox overlaps this button. When we click on the button the following script gets recorded.Browser(”Browser”).FlexApplication(”temp”).FlexBox(”vb1″).Click

Working equivalent case:

If such a case exists it can be changed as follows.

<mx:Application xmlns:mx=”http://www.adobe.com/2006/mxml” layout=”absolute”><mx:VBox width=”100%” height=”100%”>

<mx:Button label=”Hi” click=”{l1.text=’button clicked’}” />

<mx:Spacer height=”20″ />

<mx:Label id=”l1″ text=”button not clicked” />

</mx:VBox>

</mx:Application>

Here button is inside the VBox. And hence the script gets recorded as

Browser(”Browser”).FlexApplication(”temp”).FlexButton(”Hi”).Click

Note from the script that , the user can find out what container is overlapping the control. And they can use the design view also to find this.

I.e. in short , in such scenario problem is with the application layout of components.

1 comment April 2, 2008 <!–ranikumar–>

Automation Of Flex Applications

Adobe provides the automation framework for the flex components. The plug-in for the QTP tool is also provided by Adobe.
Users of flex will be using either the 2.0.1 sdk or the latest 3.0 sdk.
With the Flex3 release, users of Flex 3.0 can try the automation support using the trail version or standard version of Flex Builder. But this will be restricted. i.e. the users can try only ~30 lines of user interaction recording and replay.
Once the user buys the professional version of Flex Builder, they can enable their 2.0.1 and 3.0 applications for automation.Old users (2.0.1) of automation was expected to have the LCDS license to use the automation. With flex3 this is not needed. However there is no trial version for 2.0.1 automation with the FlexBuilder.
The section below is for the users who already know how to use the Adobe Flex Automation and Flex Builder. It mentions how user can pick up the different components needed for automation.
2.0.1 User
 
 
 
 Libraries to be used (set the sdk to be used is 2.0. sdk)
 Automation Libraries – automation.swc and automation-charts.swc
Location – (C:Program FilesAdobeFlex Builder 3sdks2.0.1frameworkslibs)
 Automation Libraies – automation-agent_rb.swc automation_agent.swc and qtp.swc (user should move the _rb.swc to the locale folder of 2.0.1frameworks)
Location – C:Program FilesAdobeFlex Builder 3sdks3.0.0frameworkslibs2.0.1.automation_swcs (this directory will be present only when they enter the valid flex builder professional license key
 
 
 Plugin to be used – QTP_Plugin_Installer
Location- C:Program FilesAdobeFlex Builder 3InstallersQTP_Plugin_Installer.exe
 
 
 How to run the application without recompiling.
 Use the runtime loading swf. How to create the runtime loading swf.
Point to the location of the 2.0.1 swc’s mentioned above in the build.bat which is available under C:Program FilesAdobeFlex Builder 3sdks3.0.0templatesautomation-runtimeloading-files and compile the runtimeloading.swf from the runtimeloading.mxml
 
 
 3.0 User  
 
 
 
Libraries to be used (set the sdk to be used is 3.0. sdk)
AutomationLibraries – automation.swc and automation_agent.swc,automation_dmv.swc automation_flashflexkit.swc qtp.swc
Location – (C:Program FilesAdobeFlex Builder 3sdks2.0.1frameworkslibs)
Plug-in to be used -QTP_Plugin_Installer.exe
Location – C:Program FilesAdobeFlex Builder 3InstallersQTP_Plugin_Installer.exe
How to run the application without recompiling.
Run the build.bat which is available under C:Program FilesAdobeFlex Builder 3sdks3.0.0templatesautomation-runtimeloading-files use that runtimeloading.swf
(The users who are not familiar with the flex automation can get the details of the same from http://www.adobe.com/support/documentation/en/flex/3/releasenotes_flex3_fb.html#install_automated_testing and from the Help of FlexBuilder AdobeFlex3Help -> Flex Data visualization developer’s Guide -> Advanced Data Grid Controls and Automation Tools -> Creating Applications For testing)

September 15, 2009 Posted by suganyakalaimani | Flex Java Integration | | 2 Comments

Developing Flex Applications in Liferay Portals

The Relationship of Rich Internet Applications and JSR-1/268 Portals Rich internet applications, or RIAs for short, are self-contained applications. In contrast, the “traditional” web applications are HTML-page-based UI. The JSR-168 portal specification marks one of the highest points of this page-based UI, allowing disparate logical pieces to be displayed on a single page in customizable ways.

 On the flip side, JSR-168 portal technology is also the hardest web technology to evolve into using RIAs. Flex, Flash, rich AJAX applications and Java applets are all self-contained programs that maintain their own states.

In a browser, they are susceptible to page navigation and refreshes. Unfortunately, this is how JSR-168 portals work. A portal page is comprised of portlets, each occupying a section of the screen.

When the user clicks on something in a portlet, most likely the whole page is refreshed with the new states of each portlets; this causes every Flash movie on the page to restart. Theoretically, it is possible for a Flex program to save all its states and recover them during each restart; but for rich UI programs, this is never practical.

Why, then, are we even concerned about embedding Flex, Flash, rich AJAX or Java applets in Liferay, if the JSR-168 portal idea is indeed that insane? Why can’t we build a Flex portal container, and implement Flex portlets using dynamic modules? Answer: a Flex portal is certainly possible, and even technically desirable; but the reality tells otherwise, at least for a while. Internet will remain the way it has been; JSR-168, being a HTML-page-based solution, works with existing paradigms well.

Portal products like Liferay have packed more than enough useful features; this is where their values lie. At the same time, there will be situations where Flex and the like are desirable. For instance, your portal site may host Flash games; more and more reporting tools are using Flex charting and grids; you may have sophisticated operations implemented by Flex.

 Bottom line: to use Flex with Liferay, compromises have to be made. You can not expect your Flex applications work seamlessly like normal JSR-168 portlets, and your design has to cope with this natural discrepancy between JSR-168 portals and RIAs. Flex Applications In Liferay Portals Housing Flex and Flash Applications in Portlets and Pages Flex internet applications are Flash movies.

While Flex and Flash applications are developed in very different ways, their deployment and runtime are the same. Flex internet applications are usually used in wrapper HTML files. It is possible to turn the main wrapper HTML file into the source of a portlet, but resizing is a major issue.

The normal Flex wrapper can specify relative width and height of the embedded Flash player, but they are relative to the browser window. A maximized portlet most likely just occupies a part of the window. The best option is probably to use the Liferay embedded page or the IFrame portlet to house Flex, Flash, rich AJAX UI, or Java applets.

Within such a page or portlet, the content is displayed in an IFrame control. The Flash player can be sized to 100% of the wrapper HTML within the IFrame control, which can be arbitrarily positioned and sized by the portal. Flex wrappers are not limited to static HTML pages; they can be dynamic JSPs as well. Developing a Sample Flex Applications to Run On Liferay Now that we understand the options of embedding Flex applications in portal pages, it is time to develop a demo.

 We will develop a simple Flex application that uses BlazeDS to call server-side Java, to list user information with the Liferay API. It will use the current user’s authentication for security checks and permission enforcement on the server side. The Flex application will be embedded in its own portal page. We will develop our Flex-Liferay demo with the Liferay Extension framework. We will use Eclipse to debug our Java code in Liferay, and use Flex Builder to debug our Flex application on Liferay.

Setting Up the Development Environment for Liferay, BlazeDS, and Flex Let’s use Liferay 5.2.2 and Tomcat 5.5.27 for our Flex-Liferay development experience. We will not detail on each step. Windows convention is used in this article; please adapt for your OS for the path names.

 Our final directory structure for our project will look like this: C:\MyPortalDev\ext\ C:\MyPortalDev\flex_projects \ C:\MyPortalDev\portal\If you have your Ext development environment set up already, just do the last step of adding BlazeDS library files. Otherwise, follow these steps: Have JDK (1.5 or 1.6) and Ant (1.7 or higher) installed, with JAVA_HOME and ANT_HOME set appropriately. Install the Liferay with Tomcat.

Create directory: C:\MyPortalDev\. Unzip liferay-portal-tomcat-5.5-5.2.2.zip into C:\MyPortalDev\, and rename lifera-portal-5.2.2\ to portal\. In that directory, you will find a tomcat-5.5.27\ directory and some others. More directories may be created there by the Liferay portal at runtime. Remove the sample Liferay webapp, 7-Cogs.

 To do that, go to C:\MyPortalDev\portal\tomcat-5.5.27\webapps\, and delete these directories: sevencogs-hook\, sevencogs-theme\, and wol-portlet\. Install the Liferay Ext environment. Unzip liferay-portal-ext-5.2.2.zip into C:\MyPortalDev\, and rename liferay-portal-ext-5.2.2\ to ext\. Check everything inside ext\ into the source control system such as a Subversion or Perforce repository, with a note similar to “Initial Liferay Ext 5.2.2 install”.

This is very important to maintain visibility of your own files and changes, given that there are so many files involved. You may choose to clean up some unwanted pieces, such as never-used SQL scripts and data. Configure the Ext environment in preparation of building. Copy from build.properties to build.${username}.properties, and clean up unwanted parts and set up your preferences. Copy from app.server.properties to app.server.${username}.properties. Make sure app.server.type is set to tomcat and app.server.tomcat.dir to ${project.dir}/../portal/tomcat-5.5.27.

Add all the BlazeDS jar files (flex-messaging-*.jar) into the Ext environment under ext\ext-lib\portal\. Use MySQL as database. Make sure MySQL is running and has a database called lportal, accessible by user liferay with password liferay. There is no need to create schema yourself. Set the JDBC options in ext\ext-impl\src\portal-ext.properties with lines like these: # # MySQL # jdbc.default.driverClassName=com.mysql.jdbc.Driver jdbc.default.url=jdbc:mysql://localhost/lportal?useUnicode=true&characterEncoding=UTF-8&useFastDateParsing=false jdbc.default.username=liferay jdbc.default.password=liferayNow, go to C:\MyPortalDev\ext\, and run ant deploy.

It will build and deploy the Liferay webapp to C:\MyPortalDev\portal\tomcat-5.5.27\webapps\ROOT\. When this is done, go to tomcat-5.5.27\bin\, and run startup.bat. Liferay server will start, and a browser window will be launched. Login as test@liferay.com with password test. If you can go this far, you have successfully set up your development environment, and ready for Flex-Liferay development.

Developing Flex Application on Liferay “Hello, Flex Life!” Let’s create our first Flex application that runs on Liferay. In your Flex Builder, create a Flex project called flexlife in C:\MyPortalDev\flex_project\, and set its output directory to C:\MyPortalDev\porta\tomcat-5.5.27\webapps\ROOT\flexlife\. Write a simple Flex screen, like:

This will build into a Flex application on the Tomcat server; the wrapper HTML file is webapps\ROOT\flexlife\flexlife.html. Log on to Liferay, add a page named Flex Life. Select Manage Pages, and set its type to be Embedded and URL to be /flexlife/flexlife.html. Go back to portal mode, and you will see this: Flex Call Server-Side Java via BlazeDS In ext\ext-impl\src\, create a Java file as test\flexlife\FlexLifeFacade.java like so: package test.flexlife; public class FlexLifeFacade { public String echo(String msg) { return “Message received at ” + new java.util.Date() + “: ” + msg; } }

 Create a BlazeDS configuration file, services-config.xml, in C:\MyPortalDev\ext\ext-web\docroot\WEB-INF\flex\:

test.flexlife.FlexLifeFacade application false false

[BlazeDS] false false true false Endpoint.* Service.* Configuration In C:\MyPortalDev\ext\ext-web\docroot\WEB-INF\web.xml, add a servlet and its mapping: MessageBrokerServlet MessageBrokerServlet flex.messaging.MessageBrokerServlet  services.configuration.file /WEB-INF/flex/services-config.xml 1 MessageBrokerServlet /messagebroker/*

 We have just coded and configured a server-side Java class callable by remote clients via BlazeDS. Shut down Liferay server if it is running, go to C:\MyPortalDev\ext\ and run ant deploy. Now it is time to extend our Flex application to call the server-side Java. The application will take user’s input, call the server and append the result in a TextArea.

After building it in Flex Builder, go to the Liferay page and refresh to see the new Flex application. (You may need to clear browser cache first to see the new Flex application, since many browsers cache Flash movies aggressively.) Type in something in the text input box and hit enter. If you see an echoed message, that is return from server-side!

If you are familiar with Flex and BlazeDS, you will quickly realize this is just the normal way of using Flex and BlazeDS, except that the Flex application is displayed in a portal page.

We have learned the basics of Flex-Liferay programming. In the rest of this article, we will discuss Liferay-specific Flex development topics.

Calling Liferay APIs for the Flex Client
Liferay API exposes all its internals through Java. You can programmatically do anything that the portal UI does.

We will create a Flex program to list all the Liferay users. We will write a Java method (in FlexLifeFacade.java) to get all the Liferay users, pack the information in an array of UserVO objects. On the Flex side, an array of objects will be received and turned into client-side UserVO objects, and displayed in a DataGrid.

The new FlexLifeFacade.java class looks like this:

package test.flexlife;

import com.liferay.portal.model.User;
import com.liferay.portal.service.persistence.UserUtil;

import java.util.List;

public class FlexLifeFacade
{
public UserVO[] getAllUsers() throws Exception {
List users = UserUtil.findAll();
UserVO[] ret = new UserVO[users.size()];
int i = 0;
for (User user : users)
ret[i++] = new UserVO(user);
return ret;
}
} UserVO.java:
package test.flexlife;

import com.liferay.portal.model.User;

public class UserVO
{
public long userId;
public String screenName;
public String fullName;
public String emailAddress;

public UserVO() {}

public UserVO(User user) {
this.userId = user.getUserId();
this.screenName = user.getScreenName();
this.fullName = user.getFullName();
this.emailAddress = user.getEmailAddress();
}
} On the client side, we have a counterpart UserVO class:

package test.flexlife
{
[RemoteClass(alias="test.flexlif.UserVO")]
public class UserVO
{
public var userId:uint;
public var screenName:String;
public var fullName:String;
public var emailAddress:String;
}
} And the Flex UI becomes:

Build and run. It looks like this: Debugging Flex Applications In Liferay with HTTPS and Single Sign-On Normally, Flex programs deployed to a server and are self contained with their own login screens. They do call the server-side, so the Flex executable must be downloaded from the server. To debug such Flex programs, in the Flex Builder, select Run|Debug|Other menu options, and set the URLs like so: When debugging Flex applications running on Liferay, it can be tricky. Most likely your Flex program will call the server-side, and user authentication is required.

In a normal flow of usage, a user logs onto Liferay, then the Flex application is launched; naturally, the user would not expect to login again into the Flex application. But this poses a dilemma for our debugging. If we still use the normal remote debugging of Flex, the “user” is not logged in, thus, many calls will fail; if we login to Liferay and navigate to the Flex wrapper HTML, how to attach the Flex debugger?

 The solution for this dilemma is to silently fake a login user for the URLs of the Flex resources. Of course, this can only happen in the development environment. We will create a filter, which always sticks in the same user information into the session, so no explicit login is needed.

package test.flexlife; import java.io.IOException;

 import javax.servlet.*;

import javax.servlet.http.*;

 import com.liferay.portal.util.WebKeys;

 public class MyDebugFilter implements Filter { private String screenName = “”; private Long userId = null; public void init(FilterConfig fc) { super.init(fc); screenName = fc.getInitParameter(“screenName”);

userId = Long.valueOf(fc.getInitParameter(“userId”)); } public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain) throws IOException, ServletException { HttpServletRequest httpreq = (HttpServletRequest) req;

HttpSession session = httpreq.getSession(); session.setAttribute(WebKeys.USER_ID, userId); filterChain.doFilter(req, res); } } In your environment, your custom login handler may put more values into the session. You can fake them here as well just like we fake the userId. Let’s install this filter.

In ext\ext-web\docroot\WEB-INF\web.xml, add these lines: My Debug Filter test.flexlife.MyDebugFilter screenName test userId 10134 My Debug Filter /flexlife/*

 How do you figure out the user information?

Run this query against the Liferay database:

 SELECT userid, screenname from User_; Ok, you get the idea, and the code… Security Considerations of Flex Applications in Liferay Security Concerns It is a good practice to put security checks in the wrapper HTMLs and links. For instance, based on the role of the user, you may not even display the link leading to your Flex service.

 Or the Flex wrapper JSP pages checks the user role and optionally display a message rather than the Flash player. But to hackers, the URL to the Flex executable SWF file is readily available. Your Flex program on Liferay needs to implement security checks.

 Enforcing Security Check in Flex and Server Calls Some high-level mission-critical Liferay APIs do check on the user permissions before carrying out the operations. In Liferay, when a user is logged in, a user-id is stored in the HTTP session.

 By getting this user and setting its permission checkers, you can use many of the Liferay APIs. The following is a useful helper method to invoke before calling such Liferay APIs:

import com.liferay.portal.model.User;

import com.liferay.portal.service.UserLocalServiceUtil;

 import com.liferay.portal.security.auth.PrincipalThreadLocal;

 import com.liferay.portal.security.permission.PermissionChecker;

import com.liferay.portal.security.permission.PermissionThreadLocal;

 import com.liferay.portal.security.permission.PermissionCheckerFactory;

import com.liferay.portal.util.WebKeys;

 import flex.messaging.FlexContext;

 import javax.servlet.http.HttpServletRequest;

 import javax.servlet.http.HttpSession;

 /** * @return the login user of the session. Sets the permission checker if need to. */

 protected User getCurrentUser() throws Exception

 { HttpServletRequest request = FlexContext.getHttpRequest(); HttpSession session = request.getSession();

 Number userId = (Number)session.getAttribute(WebKeys.USER_ID);

 User user = UserLocalServiceUtil.getUserById(userId.longValue());

if (PrincipalThreadLocal.getName() == null) { String name = String.valueOf(userId);

PrincipalThreadLocal.setName(name);

PermissionChecker pc = PermissionCheckerFactory.create(user, true);

PermissionThreadLocal.setPermissionChecker(pc); } return user; }

 Lower-level Liferay APIs may not enforce user permission checks. When you make such calls, you need to programmatically enforce the user permissions. Cross-Domain Flex Applications Flex applications in Liferay portal pages can be served from other domains as well.

 These Flex applications should not require users to log in again, so a single-sign-on infrastructure must exist across the Liferay server and the server servicing Flex applications. This is beyond the scope of this article. Conclusions This article explains the discrepancy of RIAs technologies and JSR-168 portals, and why special care must be given to accommodate Flex applications in Liferay portal pages.

 It shows how to use and develop Flex applications on Liferay, and gives detailed steps to develop, debug, and host Flex applications in Liferay portal pages. If you have successfully done all these steps, you are well equipped for full-blown Flex development with Liferay. Congratulations and have fun!

Go through this link:

http://www.liferay.com/web/guest/community/wiki/-/wiki/Main/Developing+Flex+Applications+in+Liferay+Portals;jsessionid=79BFE86237B03060FF0EFBBFF6DF5308

September 15, 2009 Posted by suganyakalaimani | Flex Java Integration | | No Comments Yet

Accessing xml data

Many server-side applications use XML to structure data, so you can use the XML classes in ActionScript to create sophisticated rich Internet applications, such as those that connect to web services. A web service is a means to connect applications—for example, an Adobe Flash Player 9 application and an application on a web server—through a common standard such as the Simple Object Access Protocol (SOAP).

The ECMAScript for XML specification in Adobe Flex defines a set of classes and functionality for working with XML data. These classes and functionality are known collectively as E4X. The two main classes you use in Flex are the XML and XMLList classes.

Note: There was an XML class in ActionScript 2.0. In ActionScript 3.0, it is renamed XMLDocument so that it does not conflict with the new XML class that is part of E4X. In ActionScript 3.0, the legacy classes — XMLDocument, XMLNode, XMLParser, and XMLTag — are included in the flash.xml package primarily for legacy support. The E4X classes are core classes; you need not import a package to use them. This Quick Start does not go into detail about the legacy ActionScript 2.0 XML classes. For details on these, see the flash.xml package in the Flex 3 Language Reference.

In the following example, you create an XML literal called myBooks by using ActionScript. You can create XML literals in ActionScript by writing XML in an ActionScript block and assigning it to a variable, because XML is a native data type in Flex, just like Number or Boolean.

The myBooks XML literal in the following example contains two book elements (also known as nodes). The first book element has four child elements, with the names title, author, amazonUrl, and pageCount.

To access the elements in an XML instance, you use dot notation (.), just like you do when accessing the property of an object. So, for example, to get a reference to the list of book nodes, you write myBooks.book. This returns an XMLList instance that contains the two book nodes in the myBooks XML. To access a specific node in a list of identical nodes, you use array notation. To get a reference to the first book node, for example, you write myBooks.book[0]. You should already be familiar with this use of the dot operator and array-style syntax if you have worked previously with Objects and Arrays in ActionScript. E4X, however, goes further than this and enables you to search the XML for a node with a specific attribute value.

In the following example, you get a reference to the first book by searching for the value of its ISBN attribute. Attributes in E4X are referenced by prefixing them with the at-sign, as in @ISBN. The statement myBooks.book.(@ISBN=="1590595181") translates to “find the book node where the ISBN attribute has a value of 1590595181.” The other examples describe more advanced, query techniques.

Example

<?xml version="1.0" encoding="utf-8"?>
<mx:Application
    xmlns:mx="http://www.adobe.com/2006/mxml"
    width="440" height="400"
    initialize="initializeHandler();"
>

    <mx:Script>
        <![CDATA[

            [Bindable] public var a:XMLList;
            [Bindable] public var b:XMLList;
            [Bindable] public var c:XMLList;
            [Bindable] public var d:XMLList;

            // Model: XML structure describing
            // some of the books in my collection.
            [Bindable]
            private var myBooks:XML =
                <books>

                    <book ISBN="1590595181">
                        <title>Foundation ActionScript Animation: Making Things Move</title>
                        <author>Keith Peters</author>

                        <amazonUrl>http://tinyurl.com/npuxt</amazonUrl>
                        <pageCount>470</pageCount>
                    </book>

                    <book ISBN="1582346194">
                        <title>Send in the Idiots: Stories from the Other Side of Autism</title>

                        <author>Kamran Nazeer</author>
                        <amazonUrl>http://tinyurl.com/lo5ts</amazonUrl>
                        <pageCount>500</pageCount>

                    </book>
                </books>

            private function initializeHandler():void

            {
                // An XML list that contains both book nodes.
                a = myBooks.book;  

                // Keith Peters
                b = myBooks.book[0].author;

                // 470

                c = myBooks.book.(@ISBN=="1590595181").pageCount;

                // Delete the first book node.
                delete myBooks.book[0];

                // Send in the Idiots...
                d = myBooks.book[0].title;
            }
        ]]>
    </mx:Script>

    <!-- User interface -->
    <mx:Panel
        title="XML lookup results"
        paddingBottom="10" paddingLeft="10" paddingRight="10" paddingTop="10">

        <mx:Text text="{'a: ' + a}" width="300"/>
        <mx:Label text="{'b: ' + b}"/>
        <mx:Label text="{'c: ' + c}"/>

        <mx:Label text="{'d: ' + d}"/>
    </mx:Panel>

</mx:Application>

Result

September 7, 2009 Posted by suganyakalaimani | Simple programs with actionscript | | No Comments Yet

Automatically generating web service proxies

You can use the Flex Builder Import Web Service feature to automatically generate connection code for invoking SOAP-based web service operations. The generated code includes client-side (ActionScript) web service proxy classes that return strongly typed objects. You can use the generated code to call web service operations directly and to pass strongly typed objects as operation parameters.

Generate client code for a WSDL document

  1. Select Data > Import Web Services (WSDL).
  2. Select the project source folder in which to save the generated code.
  3. Click Next.
  4. Specify the URI of the WSDL to use. If your project uses LiveCycle Data Services ES, you can optionally select a LiveCycle Data Services ES web service destination. For a LiveCycle Data Services ES destination to appear in the Import Web Service menu, it must be defined in the proxy-config.xml file and be configured in the following way:
    • The adapter=”soap-proxy” attribute must be specified on the destination element. This implies that you have an adapter definition with the id=”soap-proxy” attribute defined somewhere else in your configuration files.
    • The destination must also have an id attribute (the value of the id attribute is displayed in the pop-up menu).
    • The destination must have a wsdl child element. Its text value is prefilled in the WSDL URI text box in the wizard.
  5. Click Next.
  6. Deselect any of the listed web service operations for which you do not want to generate code.
  7. (Optional) Select a different service and or port from the Service and Port pop-up menus.
  8. (Optional) Change the default package name and the main class name.
  9. Click Finish to generate the ActionScript proxy classes.

Generated web service proxy files

The Import Web Service feature introspects a WSDL file and generates the following types of ActionScript class files:

Generated file Description
BaseServiceName.as A base implementation of the web service. This class contains the internal code that maps the operations from the WSDL file to Flex WSDLOperation instances and sets the corresponding parameters.
IServicename.as The service interface that defines all of the methods that users can access.
Servicename.as The concrete web service implementation.
BaseServicenameSchema.as A file containing the XSD schema of the web service as an ActionScript custom type.
OperationnameResultEvent.as For each web service operation, Flex Builder generates a strongly typed event type class. You can use these classes to benefit from strongly typed results.
Operationname_request.as For each web service operation that passes parameters to the server operation, Flex Builder generates a request wrapper class with the parameters as members. The request object is intended for use with the MXML tag syntax.
Type.as For each complex type defined in the WSDL file, Flex Builder generates a class with the same name as the complex type or with the same name as the enclosing element.

Managing generated web service code

The Manage Web Services feature lets you add, update, or delete generated web service proxy code.

Generate web service code

  1. Select Data > Manage Web Services.
  2. Select a project from the tree of projects.
  3. Click Add.
  4. Click Next.
  5. Enter a new WSDL URI or select an existing one from the pop-up menu. Optionally, if you have a LiveCycle Data Services ES installation, you can use a LiveCycle Data Services ES destination.
  6. Complete the Configure Code Generation text boxes and click Finish.

Update generated web service code

  1. Select Data > Manage Web Services.
  2. Within a project, select the WSDL URI for which you want to update generated code.
  3. Click Update.
  4. Click Refresh to find out if the WSDL document has changed since you imported it.
  5. If the WSDL document has changed, select the operations to update (if different from the default selections).
  6. Click Finish to regenerate code based on the current version of the WSDL document.

Delete generated web service code

  1. Select Data > Manage Web Services.
  2. Within a project, select the WSDL URI for the generated code to delete.
  3. Click Delete and then click Yes in the Confirm Imported WSDL Deletion dialog box.

Creating an application that uses the generated proxy code

You can use MXML tags or ActionScript to call a web service. Equivalent MXML-centric and ActionScript-centric applications use an address book web service that exposes the following operations:

  • AddEntry lets you store someone’s address.
  • FindEntry lets you retrieve the address when you provide the person’s name.

The AddEntry operation takes an Entry object as input and returns nothing. The FindEntry operation takes a string as input and returns an Entry object.

These sample applications demonstrate the following concepts for working with the code that Flex Builder generated from the WSDL document:

  • You can call a web service operation directly, as the following example shows:
    myWebService.callOperation(parameters)
  • The parameters passed to the web service operations are strongly typed and reflect the types that are described in the WSDL document.
  • The generated code includes event listeners that are specific to each operation; these listeners return strongly typed results.

The MXML and ActionScript address book applications both use the following generated ActionScript classes:

Generated file Description
BaseAddressBookService.as A base implementation of the web service. This class contains the internal code that maps the operations from the WSDL file to Flex WSDLOperation instances and sets the corresponding parameters.
IAddressBookService.as The service interface that defines all of the methods that users can access.
AddressBookService.as The concrete web service implementation.
BaseAddressBookServiceSchema.as The XSD schema of the web service as an ActionScript custom type.
FindEntryResultEvent.as A strongly typed event type object for the FindEntry operation. For each web service operation, Flex Builder generates a strongly typed event type class. You can use these classes to benefit from strongly typed results.
AddEntry_request.as A request wrapper class for the AddEntry operation with the parameters as members. The request object is intended for use with the MXML tag syntax.
FindEntry_request.as A request wrapper class for the FindEntry operation with the parameters as members. The request object is intended for use with the MXML tag syntax.
Entry.as For each complex type defined in the WSDL file, Flex Builder generates a class with the same name as the complex type or with the same name as the enclosing element.

Calling a service with MXML

For an MXML-centric application, you create an instance of the web service in an MXML tag, as the following code snippet shows. Note that the application uses a custom namespace, ws; this namespace is declared as xmlns:ws=”com.adobe.*” in the <mx:Application> tag.

<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute" xmlns:ws="com.adobe.*">
...
    <!-- This is how we create an instance of the AddressBookService generated class.-->
    <ws:AddressBookService id="myWebService">
        <!-- We need to specify the request variables that are passed to the corresponding operations. -->
        <ws:addEntry_request_var>
            <!-- The addEntry operation has one input parameter. This parameter's type is Entry. -->
            <ws:AddEntry_request>
                <ws:param0>
                    <ws:Entry>
                        <!-- We bind each of the members of an Entry object to the corresponding text input field.-->
                        <ws:name>{tiNameInput.text}</ws:name>
                        <ws:city>{tiCityInput.text}</ws:city>
                        <ws:street>{tiStreetInput.text}</ws:street>
                        <ws:state>{tiStateInput.text}</ws:state>
                        <ws:postalCode>{tiPostalCodeInput.text}</ws:postalCode>
                    </ws:Entry>
                </ws:param0>
            </ws:AddEntry_request>
        </ws:addEntry_request_var>

        <!-- The findEntry operation has one input parameter of the String type. -->
        <ws:findEntry_request_var>
            <!-- We bind the corresponding text input field to the operation's input parameter.
              Since the operation's input parameter has a simple type, you can use the following syntax to do the data binding.
              Alternatively you could do:
              <ws:FindEntry_request>
                <ws:param0>{tiSearch.text}</ws:param0>
              </ws:FindEntry_request>
              -->
            <ws:FindEntry_request param0="{tiSearch.text}">
            </ws:FindEntry_request>
        </ws:findEntry_request_var>
    </ws:AddressBookService>
...

On the click event for the Add entry button, call the addEntry_send() method to pass the request to the service, as the following code snippet shows:

...
<mx:Button label="Add entry" labelPlacement="top" click="myWebService.addEntry_send(); clearInputFields()"/>
...

On the click event for the Find entry button, call the findEntry_send() method to pass the request to the service, as the following code snippet shows:

...
<mx:Button label="Add entry" labelPlacement="top" click="myWebService.addEntry_send(); clearInputFields()"/>
...

In a Form control, bind the results of the findEntry operation to Form fields:

...
                <mx:HBox id="hbResults" x="10" y="70" width="100%" verticalAlign="middle" borderStyle="solid" visible="true">
                    <mx:Label text="Results:"/>
                    <!-- In the form that we use to display the data that is returned by the web service, we bind each
                        member of the last result returned for the findEntry operation to its corresponding text control. -->
                    <mx:Form width="293" height="181" borderStyle="solid">
                        <mx:FormItem label="Name">
                            <mx:Text id="txNameOutput" text="{myWebService.findEntry_lastResult.name}"/>
...
                    </mx:Form>
                </mx:HBox>
...

The following example shows the complete MXML-centric address book application:

<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute" xmlns:ws="com.adobe.*">
    <mx:Script>
        <![CDATA[
            /**
                @private

                This method clears the input fields from the Add Entry view.
            */
            private function clearInputFields():void {
                tiNameInput.text = "";
                tiCityInput.text = "";
                tiStreetInput.text = "";
                tiStateInput.text = "";
                tiPostalCodeInput.text = "";
            }

        ]]>
    </mx:Script>

    <!-- This is how we create an instance of the AddressBookService generated class.-->
    <ws:AddressBookService id="myWebService">
        <!-- We need to specify the request variables that are passed to the corresponding operations. -->
        <ws:addEntry_request_var>
            <!-- The addEntry operation has one input parameter. This parameter's type is Entry. -->
            <ws:AddEntry_request>
                <ws:param0>
                    <ws:Entry>
                        <!-- We bind each of the members of an Entry object to the corresponding text input field. -->
                        <ws:name>{tiNameInput.text}</ws:name>
                        <ws:city>{tiCityInput.text}</ws:city>
                        <ws:street>{tiStreetInput.text}</ws:street>
                        <ws:state>{tiStateInput.text}</ws:state>
                        <ws:postalCode>{tiPostalCodeInput.text}</ws:postalCode>
                    </ws:Entry>
                </ws:param0>
            </ws:AddEntry_request>
        </ws:addEntry_request_var>

        <!-- The findEntry operation has one input parameter of the String type. -->
        <ws:findEntry_request_var>
            <!-- We bind the corresponding text input field to the operation's input parameter.
              Since the operation's input parameter has a simple type, you can use the following syntax to do the data binding.
              Alternatively you could do:
              <ws:FindEntry_request>
                <ws:param0>{tiSearch.text}</ws:param0>
              </ws:FindEntry_request>
              -->
            <ws:FindEntry_request param0="{tiSearch.text}">
            </ws:FindEntry_request>

        </ws:findEntry_request_var>
    </ws:AddressBookService>

    <mx:Panel width="640" height="480" layout="absolute" verticalCenter="0" horizontalCenter="0" title="AddressBook Client App">
        <mx:TabNavigator x="10" y="10" width="100%" height="100%">
            <mx:Canvas label="Add" width="100%" height="100%" id="tabAdd">
                <mx:HBox x="10" y="10" width="100%" verticalAlign="middle" borderStyle="solid">
                    <mx:Label text="New entry details:"/>
                    <mx:Form width="293" height="181" borderStyle="solid">
                        <mx:FormItem label="Name">
                            <mx:TextInput id="tiNameInput"/>
                        </mx:FormItem>
                        <mx:FormItem label="City">
                            <mx:TextInput id="tiCityInput"/>
                        </mx:FormItem>
                        <mx:FormItem label="Street">
                            <mx:TextInput id="tiStreetInput"/>
                        </mx:FormItem>
                        <mx:FormItem label="State">
                            <mx:TextInput id="tiStateInput"/>
                        </mx:FormItem>
                        <mx:FormItem label="Postal Code">
                            <mx:TextInput id="tiPostalCodeInput"/>
                        </mx:FormItem>
                    </mx:Form>
                    <!-- On the click event for the Add entry button, we call the addEntry_send() method of the web service that we defined earlier. -->
                    <mx:Button label="Add entry" labelPlacement="top" click="myWebService.addEntry_send(); clearInputFields()"/>
                </mx:HBox>
            </mx:Canvas>
            <mx:Canvas label="Search" width="100%" height="100%" id="tabSearch">
                <mx:HBox x="10" y="10" width="100%">
                    <mx:Label text="Name"/>
                    <mx:TextInput id="tiSearch"/>
                    <!-- On the click event for the 'Find entry' button we call the 'findEntry_send()' method of the web service we defined earlier. -->
                    <mx:Button label="Find entry" click="myWebService.findEntry_send()"/>
                </mx:HBox>
                <mx:HBox id="hbNoResults" x="10" y="40" height="22" visible="false">
                    <mx:Text text="'No entry was found!"/>
                </mx:HBox>
                <mx:HBox id="hbResults" x="10" y="70" width="100%" verticalAlign="middle" borderStyle="solid" visible="true">
                    <mx:Label text="Results:"/>
                    <!-- In the form that we use to display the data that is returned by the web service, we bind each
                        member of the last result returned for the findEntry operation to its corresponding text control. -->
                    <mx:Form width="293" height="181" borderStyle="solid">
                        <mx:FormItem label="Name">
                            <mx:Text id="txNameOutput" text="{myWebService.findEntry_lastResult.name}"/>
                        </mx:FormItem>
                        <mx:FormItem label="City">
                            <mx:Text id="txCityOutput" text="{myWebService.findEntry_lastResult.city}"/>
                        </mx:FormItem>
                        <mx:FormItem label="Street">
                            <mx:Text id="txStreetOutput" text="{myWebService.findEntry_lastResult.street}"/>
                        </mx:FormItem>
                        <mx:FormItem label="State">
                            <mx:Text id="txStateOutput" text="{myWebService.findEntry_lastResult.state}"/>
                        </mx:FormItem>
                        <mx:FormItem label="Postal Code">
                            <mx:Text id="txPostalCodeOutput" text="{myWebService.findEntry_lastResult.postalCode}"/>
                        </mx:FormItem>
                    </mx:Form>
                </mx:HBox>
            </mx:Canvas>
        </mx:TabNavigator>
    </mx:Panel>
</mx:Application>

Calling a service with ActionScript

For an ActionScript-centric application, you create an instance of the web service in ActionScript, as the following code snippet shows:

...
<mx:Script>
    <![CDATA[
        import com.adobe.*;
        import mx.rpc.events.FaultEvent;
        import mx.controls.Alert;

        // Declare an instance of the generated web service class.
        public var agenda:AddressBookService;
        public function initApp():void
        {
            // Instantiate the new object.
            agenda = new AddressBookService();

...
        }
...

If you are using a LiveCycle Data Services ES destination, you pass the destination name to the service as a parameter of the constructor.

Add a result event listener (a function that you have previously defined) for the operation to call, as the following code snippet shows:

agenda.addEntryEventListener(myResultHandlingFunction);

In the addEntry() method, call the addEntry operation of the service and pass the correct values as arguments, as the following example shows:

agenda.addEntry(myparam0);

In the searchEntry() method, call the findEntry operation of the service and bind the results of the findEntry operation to Form fields:

...
        /**
        * The handleSearchResult() method is the result event handler for the
        * findEntry operation.
        * It displays the address of a given person by populating the corresponding
        * Form fields with the members of the strongly typed Entry result that
        * you get when the call to the operation succeeds. Or, if we have no record of the person's address, a message is displayed that
        * no entry was found.
        */
        public function handleSearchResult(event:FindEntryResultEvent):void
        {
            if(event.result != null) {
                // Instantiate a new Entry object with the result that we got from the call.
                var res:Entry = event.result;

                // Populate the result Form fields with the corresponding data.
                txNameOutput.text = res.name;
                txCityOutput.text = res.city;
                txStreetOutput.text = res.street;
                txStateOutput.text = res.state;
                txPostalCodeOutput.text = res.postalCode;

                // Make sure that the no entry found message is not displayed.
                hbNoResults.visible = false;

                // Show the results.
                hbResults.visible = true;

                // Clear the search name field
                tiSearch.text = "";
            }
            else {
                // Display the no entry found message.
                hbNoResults.visible = true;

                // Hide any previous results.
                hbResults.visible = false;
            }
        }
...

The following example shows the complete ActionScript-centric address book application:

<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute" creationComplete="initApp()">
<mx:Script>
    <![CDATA[
        import com.adobe.*;
        import mx.rpc.events.FaultEvent;
        import mx.controls.Alert;

        // Declare an instance of the generated web service class.
        public var agenda:AddressBookService;

        /**
        * In the initApp() method we will create a new web service object and
        * add the fault event listener for that web service.
        * Unlike the event listeners, we get only one fault event listener per
        * web service class, as opposed to the event listeners that we get for each
        * operation that returns something.
        */
        public function initApp():void
        {
            // Instantiate the new object.
            agenda = new AddressBookService();

            // Register the fault event listener method.
            agenda.addAddressBookServiceFaultEventListener(handleFaults);
        }

        /**
        * The addEntry() method is used to call the addEntry web service operation.
        * The method gets called when the user clicks the Add Entry button.
        * It builds an Entry object by using the data that the user has provided, calls the
        * web service operation and passes along the strong typed parameter, and then
        * clears the user input fields to provide the visual hint that an action has been taken.
        */
        public function addEntry():void
        {
            // Instantiate a new Entry object.
            var newEntry:Entry = new Entry();

            // Use the data that the user has provided to populate the Entry object.
            newEntry.name = tiNameInput.text;
            newEntry.city = tiCityInput.text;
            newEntry.street = tiStreetInput.text;
            newEntry.state = tiStateInput.text;
            newEntry.postalCode = tiPostalCodeInput.text; 

            // Call the addEntry operation directly from the web service class instance and
            // pass along the required parameter.
            agenda.addEntry(newEntry);

            // Clear the user input fields.
            clearInputFields();
        }

        private function clearInputFields():void {
            tiNameInput.text = "";
            tiCityInput.text = "";
            tiStreetInput.text = "";
            tiStateInput.text = "";
            tiPostalCodeInput.text = "";
        }

        /**
        * The handleFaults() method is a very basic fault event handler method that
        * displays an Alert with the error message.
        */
        public function handleFaults(event:FaultEvent):void
        {
            Alert.show("A fault occured contacting the server. Fault message is: " + event.fault.faultString);
        }

        /**
        * The searchEntry() method is used to call the findEntry web service operation.
        * It gets called when the user clicks the Find Entry button.
        * It adds the specific findEntry event listener, and if the user has provided a name
        * it makes a call to the web service operation with the provided name.
        */
        public function searchEntry(name:String):void
        {
            // Register the event listener for the findEntry operation.
            agenda.addfindEntryEventListener(handleSearchResult);

            // Call the operation if we have a valid name.
            if(name!= null && name.length > 0)
                agenda.findEntry(name);
        }

        /**
        * The handleSearchResult() method is the result event handler for the
        * findEntry operation.
        * It displays the address of a given person by populating the corresponding
        * form fields with the members of the strongly typed Entry result that
        * you get when the call to the operation succeeds. Or, if we have no record of a person's address, a message is displayed that
        * no entry was found.the
        */
        public function handleSearchResult(event:FindEntryResultEvent):void
        {
            if(event.result != null) {
                // Instantiate a new Entry object with result that we got from the call.
                var res:Entry = event.result;

                // Populate the result form fields with the corresponding data.
                txNameOutput.text = res.name;
                txCityOutput.text = res.city;
                txStreetOutput.text = res.street;
                txStateOutput.text = res.state;
                txPostalCodeOutput.text = res.postalCode;

                // Make sure that the no entry found message is not displayed.
                hbNoResults.visible = false;

                // Show the results.
                hbResults.visible = true;

                // Clear the search name field.
                tiSearch.text = "";
            }
            else {
                // Display the no entry found message.
                hbNoResults.visible = true;

                // Hide any previous results.
                hbResults.visible = false;
            }
        }
    ]]>
</mx:Script>
    <mx:Panel width="640" height="480" layout="absolute" verticalCenter="0" horizontalCenter="0" title="AddressBook Client App">
        <mx:TabNavigator x="10" y="10" width="100%" height="100%">
            <mx:Canvas label="Add" width="100%" height="100%" id="tabAdd">
                <mx:HBox x="10" y="10" width="100%" verticalAlign="middle" borderStyle="solid">
                    <mx:Label text="New entry details:"/>
                    <mx:Form width="293" height="181" borderStyle="solid">
                        <mx:FormItem label="Name">
                            <mx:TextInput id="tiNameInput"/>
                        </mx:FormItem>
                        <mx:FormItem label="City">
                            <mx:TextInput id="tiCityInput"/>
                        </mx:FormItem>
                        <mx:FormItem label="Street">
                            <mx:TextInput id="tiStreetInput"/>
                        </mx:FormItem>
                        <mx:FormItem label="State">
                            <mx:TextInput id="tiStateInput"/>
                        </mx:FormItem>
                        <mx:FormItem label="Postal Code">
                            <mx:TextInput id="tiPostalCodeInput"/>
                        </mx:FormItem>
                    </mx:Form>
                    <mx:Button label="Add entry" labelPlacement="top" click="addEntry()"/>
                </mx:HBox>
            </mx:Canvas>
            <mx:Canvas label="Search" width="100%" height="100%" id="tabSearch">
                <mx:HBox x="10" y="10" width="100%">
                    <mx:Label text="Name"/>
                    <mx:TextInput id="tiSearch"/>
                    <mx:Button label="Find entry" click="searchEntry(tiSearch.text);"/>
                </mx:HBox>
                <mx:HBox id="hbNoResults" x="10" y="40" height="22" visible="false">
                    <mx:Text text="'No entry was found!"/>
                </mx:HBox>
                <mx:HBox id="hbResults" x="10" y="70" width="100%" verticalAlign="middle" borderStyle="solid" visible="false">
                    <mx:Label text="Results:"/>
                    <mx:Form width="293" height="181" borderStyle="solid">
                        <mx:FormItem label="Name">
                            <mx:Text id="txNameOutput"/>
                        </mx:FormItem>
                        <mx:FormItem label="City">
                            <mx:Text id="txCityOutput"/>
                        </mx:FormItem>
                        <mx:FormItem label="Street">
                            <mx:Text id="txStreetOutput"/>
                        </mx:FormItem>
                        <mx:FormItem label="State">
                            <mx:Text id="txStateOutput"/>
                        </mx:FormItem>
                        <mx:FormItem label="Postal Code">
                            <mx:Text id="txPostalCodeOutput"/>
                        </mx:FormItem>
                    </mx:Form>
                </mx:HBox>
            </mx:Canvas>
        </mx:TabNavigator>
    </mx:Panel>
</mx:Application>

Working with special types

In addition to the simple classes that the code generator creates for WSDL-defined complex types and request and result event wrappers, special classes are generated for the following types:

  • Simple types that enumerate accepted values
  • Array types

Generated code for simple types, enumerations, and restrictions

When the code generator introspects a WSDL document and encounters the definition of a simple type that is a restriction of a certain type, and the WSDL provides a list of accepted values, the generated ActionScript model exposes the acceptable values. To do so, the actual value has [Inspectable] metadata attached to it. When using MXML syntax, the values read from the WSDL document are proposed as hints, and any other values are rejected by the compiler.

As an example, consider the definition of a simple type that is a string with possible length unit values. Its definition inside the WSDL document is:

<s:simpleType name="Lengths">
    <s:restriction base="s:string">
        <s:enumeration value="Angstroms"/>
        <s:enumeration value="Nanometers"/>
        <s:enumeration value="Microinch"/>
        <s:enumeration value="Microns"/>
        <s:enumeration value="Mils"/>
</s:restriction>
</s:simpleType>

The code generator translates this into an ActionScript class called Lengths.as with a single member (_Lengths), of type String. Inside the generated class, it also adds the[Inspectable] metadata with the values it read from the WSDL document, as the following example shows:

public class Lengths
{
    /**
    * Constructor, initializes the type class.
    */
    public function Lengths() {}
        [Inspectable(category="Generated values",
        enumeration="Angstroms,Nanometers,Microinch,Microns,Mils", type="String")]
        public var _Lengths:String;
        public function toString():String {
        return _Lengths.toString();
    }
)

Generated code for array types

When an operation must return an array of a specific type and it is defined as a complex type inside the WSDL document, a class is generated for it. This class extends mx.collections.ArrayCollection and implements all of the utility methods that are defined in the base class. To make it easier to see what the underlying type of the array is, all of the methods are slightly modified from their original. For example, getItemAt(index:int) becomes getBaseTypeAt(index:int), getItemIndex(item:Object) becomes getBaseTypeIndex(item:BaseType), and so on.

Consider the following structure:

<s:complexType name="ArrayOfAlert">
    <s:sequence>
        <s:element minOccurs="0" maxOccurs="unbounded" name="Alert" type="tns:Alert" />
    </s:sequence>
</s:complexType>

This structure results in the following generated class:

public class ArrayOfAlert extends ArrayCollection {
/**
    * Constructor - initializes the array collection based on a source array
    */
    public function ArrayOfAlert(source:Array = null) {
        super(source);
    }
    public function addAlertAt(item:Alert,index:int):void {
        addItemAt(item,index);
    }
    public function addAlert(item:Alert):void {
        addItem(item);
    }
    public function getAlertAt(index:int):Alert {
        return getItemAt(index) as Alert;
    }
    public function getAlertIndex(item:Alert):int {
        return getItemIndex(item);
    }
    public function setAlertAt(item:Alert,index:int):void {
        setItemAt(item,index);
    }
    public function asIList():IList {
        return this as IList;
    }
    public function asICollectionView():ICollectionView {
        return this as ICollectionView;
    }
}

One exception to this naming rule happens when the base type is another complex type named Item. This causes the generation of methods that override the ones implemented in the base class, but without actually specifying it. In this case, the base type is renamed to MyItem, inside method names. When used as actual argument type, the base type name is left unchanged.

Adding a header to an operation call and getting the header from an operation result

Operations defined in a WSDL document can optionally have headers attached to them, either when calling an operation or when returning the result. The code that Flex Builder generates lets the user handle both the request headers and the result headers.

Request headers

If the WSDL document defines request headers for an operation, the generated code has the following extra methods for each operation:

setOperationName_header() Sets the operation’s request header. You must pass it the exact header object that the operation expects.

getOperationName_header() Gets the object that was previously passed as the operation header.

addOperationName_header(header_arguments:headerType) Adds a new header item for the operation. This is the preferred way of adding headers becaue it automatically takes care of encoding the header and you need to provide only a strong typed object, the method argument.

You can add a request header to an operation call, as the following example shows:

...
public function doCall():void {
    var myHeader:LicenseInfo = new LicenseInfo()
    //Or use the keywordSearchRequest_header property to set the value.
    myService.addkeywordSearchRequest_header(myHeader);
    myService.addkeywordSearchRequestEventListener(handleResults);
    myService.keywordSearchRequest(inputParams);
}
...

Result headers

Some operations also return information in headers along with the actual result. You can retrieve the array of headers by accessing the headers property on the typed result event, inside the operation’s result event handler, as the following example shows:

...
public function doCall():void {
    myService.addkeywordSearchRequestEventListener(handleResults);
    myService.keywordSearchRequest(inputParams);
}
public function handleResult(event:KeywordSearchRequestResultEvent):void {
    trace(event.result.TotalResults); //do something with the result
    trace(event.headers); //do something with the result headers
}

Handling the result of an operation call

After calling a web service operation, you must retrieve the result and manipulate it. The result of a web service call can be either a SOAP-encoded response or a SOAP fault that contains an error.

To facilitate access to the response of a web service operation call, the code generator also creates some typed event classes. Because Flex operates asynchronously, you must use events to be notified of the result or fault. You can do this in any of the following ways:

  • By using the token returned when the operation call is placed
  • By using the utility methods defined on the typed service
  • By binding elements via MXML to the service’s lastResult property

Using a return token

When the call to the operation is made, the user gets an AsyncToken object returned immediately. This can be used to attach event listeners (methods that are executed when a specific event occurs), by using syntax like the following example:

...
private function doCall():void {
    var ret:AsyncToken;
    ret = myService.keywordSearchRequest(input);
    ret.addEventListener
        (KeywordSearchRequestResultEvent.KeywordSearchRequest_RESULT,handleResult);
    ret.addEventListener(FaultEvent.FAULT,handleFaults);
}
...

In this example, the handleResult() and handleFaults() methods are user-defined methods. When using this approach, the result handling method has an argument of type ResultEvent, instead of a strongly typed, operation-specific event, as in the following example:

public function handleResults(event:ResultEvent):void {
    trace(event.result); //do something with the result
}

Using utility methods

Through metadata, the service provides a list of events to which the user can listen. There is a single unified fault event, and one result event for each operation. This is because each operation returns a different type of result, but the fault is the same for all. The service provides the following utility methods for attaching event listeners to an operation call:

  • The method to add the fault event listener for the service, as the following example shows:
    public function addSearchServiceFaultEventListener(listener:Function):void
  • The method on each operation to add the listener to process the result, as the following example shows:
    public function addkeywordSearchRequestEventListener(listener:Function):void

The types of events that the service exposes are available via code hints and as metadata on the service. Each event metadata is commented and exposes the method that dispatches it, as the following example shows:

/**
 * Dispatched when a call to the operation KeywordSearchRequest completes successfully
 * and returns some data.
 * @eventType KeywordSearchRequestResultEvent
 */
[Event(name="KeywordSearchRequest_result", type="KeywordSearchRequestResultEvent")]

When using this approach, the result handling method takes the strongly typed, operation-specific event, as the following example shows:

public function handleResults(event:KeywordSearchRequestResultEvent):void
{
      trace(event.result);    //do something with the result
}

Using MXML binding

The generated service class exposes for each operation a specific property, operationName_lastResult, which is populated each time the result of the operation call is returned. You can bind this property through MXML, and when the operation returns a value, it automatically populates all bound items. The following example shows a binding to operationName_lastResult in an MXML tag:

<mx:Text text={myService.keywordSearchRequest_lastResult} />

September 7, 2009 Posted by suganyakalaimani | Flex Java Integration | | No Comments Yet

Generating a PHP database application

You can generate an application that uses PHP and a MySQL database. To generate this type of application, you must have a local PHP server and access to a target MySQL database table.

Generate PHP application code

  1. If you have not already done so, create a Flex project that specifies PHP as its application server type.
  2. Select Data > Create Application from Database.
  3. From the Project list, select the PHP project to use.
  4. From the Connection list, select a database connection profile. To create and use a new connection profile, click the New button and complete the text boxes. For more information, see Directory structure and deployment considerations for PHP.
  5. From the Table list, select the database table to use.
  6. From the Primary Key list, select the primary key of the database table if it is not already selected.
  7. Click Next.
  8. Specify a Main Source Folder and a Main Application File, or accept the default values. You can generate the PHP files in the bin-debug folder, which is the default location, or in the src folder. If you want to export the project after using the data wizard, you must generate the PHP files in the src folder; otherwise, the project is exported without the PHP files and does not function.
  9. Click Next.
  10. Deselect any database columns that you do not want to appear in the DataGrid that the wizard generates.
  11. Choose a database filter column, or accept the default value.
  12. Click Finish.
  13. Select Run > External Tools > Run As > Run on Server.
  14. Select Run > Run to run the application on the server.

Directory structure and deployment considerations for PHP

When you use the data wizard to generate a PHP application, the default location of the generated files is the [web_server_root]\[project_name]_debug directory. The directory includes a PEAR subdirectory that contains the PEAR XML parsing utility, and a history subdirectory that contains files for Flex history management.

The main deployment directory contains tablename.php, databasenameconn.php, functionsinc.php, and XmlSerializer.class.php PHP files. It also contains a SWF file named tablename.swf and an HTML wrapper named tablename.html.

The project src directory contains the following files: tablename.mxml, tablenameconfig.as, and tablenamescript.as.

Deploy an application to a remote server

  1. Set up the host:
    1. Create a new database. Typically, the host has a naming convention like sitename_dbname.
    2. Create a web user with a password (for example, name: bigryans_webuser, pw: webuser). Give the web user the following privileges: insert, update, delete, and select.
    3. Create the database table or tables (you can export the SQL and run it in your MySQL administrator application, or you can create it manually); for example:
      CREATE TABLE users (
      userid int(10) unsigned NOT NULL auto_increment,
      username varchar(255) collate latin1_general_ci NOT NULL,
      emailaddress varchar(255) collate latin1_general_ci NOT NULL,
      PRIMARY KEY (userid)
      ) ENGINE=MyISAM DEFAULT CHARSET=latin1 COLLATE=latin1_general_ci;
  2. Edit the Flexphpconn.php file. This file creates the connection to the database for your Flex application users:
    $hostname_conn = "localhost"; // If your database and Flex app are on the same server $database_conn = "bigryans_flexphp"; // name you gave it in step 1 $username_conn = "bigryans_webuser"; // name you created in step 1 $password_conn = "webuser"; // password you gave it in step 1
  3. Upload the files. You need the following subset of the files that the wizard outputs:
    • /history directory (if you want to support history management/deep linking)
    • /PEAR directory
    • AC_OETags.js
    • Flexphpconn.php
    • functions.inc.php
    • playerProdInstall.swf (if you want to support express installation)
    • Flex application files:
      • users.html (HTML wrapper)
      • users.swf (Flex application)
      • users.php (PHP functions for the Flex application)
      • XMLSerializer.class.php

You do not need to upload the xxx-profile.swf files, the projectname.swf file, or the projectname.html file.

Generating a J2EE database application

You can generate an application that uses Java and a SQL database. To generate this type of application, you must have a local Java application server and access to a target SQL database table. You can generate an application that uses a Java servlet to access a database and return data to the Flex application; or if you have LiveCycle Data Services ES, you can choose to generate an application that uses the data management service to access a database and dynamically distribute data to and from clients.

Generate J2EE application code

  1. If you have not already done so, create a new Flex project that specifies Java 2 Enterprise Edition (J2EE) as the application server type.
  2. Select Data > Create Application from Database.
  3. From the Project list, select the J2EE project to use.
  4. From the Connection list, select a database connection profile. To create and use a new connection profile, click the New button and complete the text boxes.
  5. From the Table list, select the database table to use.
  6. From the Primary Key list, select the primary key of the database table.
  7. Click Next.
  8. To use a specific Java package for the Java classes that will be generated, enter the package name in the Java Package text box.
  9. By default, the names of the generated Java classes are prefixed with the name of the selected database table. To use a different prefix, enter it in the Class Name Prefix text box.
  10. If your project uses LiveCycle Data Services ES, select whether to use LiveCycle Data Services ES or XML over HTTP for communication between the client and the server. If you select LiveCycle Data Services ES, the Data Management Service is used. If you select XML over HTTP, a servlet passes XML between the client and the server.
  11. Click Next.
  12. (Optional) Deselect any of the listed table fields to exclude them from the generated Flex DataGrid control.
  13. Click Finish.
  14. Select Run > External Tools > Run As > Run on Server.
  15. Select Run > Run to run the application on the server.

Directory structure and deployment considerations for J2EE

The Flex Builder project’s WebContent directory contains directories to be deployed into the root directory of the web application. Depending on the type of Java application server, the web application is deployed as a WAR file or, as is the case with Tomcat, as a linked web application directory. The Flex Builder project’s src directory contains Java source files for classes that are deployed to the WEB-INF/classes directory of the web application. For projects that are compiled with Flex Builder, the contents of the Flex Builder project’s bin and flex_src directories are included in the list of files that are deployed to the web application; however, the compiled SWF files are deployed rather than the corresponding MXML files that are in the flex_src directory. All of the files in those folders are deployed to the root of the web application.

Generating an ASP .NET database application

You can generate an application that uses ASP .NET and a Microsoft SQL Server database. To generate this type of application, you must have a local .NET installation and access to a target Microsoft SQL Server database table. You can generate an application that uses an ASP .NET page to access a database and return data to the Flex application.

Generate ASP .NET application code

  1. If you have not already done so, create a new Flex project that specifies ASP .NET as the application server type. You can deploy the application to the Visual Studio Development Server or the Internet Information Server (IIS) web server that comes with Windows. If you use IIS, the deployment directory specified in the New Flex Project wizard must be defined in the IIS administration console as an ASP Application.
  2. Select Data > Create Application from Database.
  3. From the Project list, select the ASP .NET project to use.
  4. From the Connection list, select a database connection profile. To create and use a new connection profile, click the New button and complete the text boxes.
  5. From the Table list, select the database table to use.
  6. From the Primary Key list, select the primary key of the database table.
  7. Click Next.
  8. Specify a .NET class name, or accept the default value.
  9. Choose either C# with Web Services or VB with Web Services as the server language.
  10. Click Next.
  11. (Optional) Deselect any of the listed table fields to exclude them from the generated Flex DataGrid control.
  12. Click Finish.
  13. Select Run > External Tools > Run As > Run on Server.
  14. Select Run > Run to run the application on the server.

Directory structure and deployment considerations for ASP .NET

When you run Project > Export Release Build, files are saved in the project bin_release directory and the optimized application runs from that location.

Creating a database connection profile

To generate a database application, you must have a database connection profile that provides information about the database that you want to use.

Create a connection profile

  1. If the Create Application from Database dialog box is not already open, select Data > Create Application from Database.
  2. Click the New button to the right of the Connection text box.
  3. In the Create Connection Profile dialog box, enter a connection name in the Name text box. You can also complete the optional Description text box.
  4. (Optional) When the wizard is finished or when the Data Source Explorer is opened, select the Autoconnect option to connect to the database.
  5. Click New.
  6. Complete the database connection text boxes. The fields vary depending on the type of database connection you choose. For PHP projects, you use MySQL. For ASP.NET projects, you use Microsoft SQL Server. For J2EE projects, you can select from a list of choices, but MySQL and Microsoft SQL Server are supported.
  7. Click Test Connection to make sure that the connection is valid.
  8. Click Next.
  9. Click Finish.

 

September 7, 2009 Posted by suganyakalaimani | Flex Java Integration | | No Comments Yet

Connect Flex Applications with your Database

 

Introduction

Flex was developed by Adobe to allow users to create rich internet applications that Flash was not built to be used for. Flex is an amazing technology in that it combines a well structured interface with the ability to build dynamic web applications. One of the main reasons for choosing Flex for your RIA is it’s ability to seamlessly connect and work with your MySQL database. This makes building online applications very easy and much more structured than Flash currently allows. If after connecting your flex application to your MySQl database, you are still not convinced that Flex is awesome, you may not be human.

So sit back and and lets dive into building a Flex and MySQL Application.

What you’ll need

1.) Adobe Flex – Can be downloaded free for 60 days.

Download Flex

 

2.) MAMP, WAMP or LAMP – Can be downloaded for free.

  1. MAMP – Download MAMP
  2. LAMP – Setup LAMP
  3. WAMP – Download WAMP

3.) Ability to follow directions and show off your skills to Flash Developers.

Steps

Now that you have installed both Flex and an AMP technology stack lets get to the fun part!

For the sake of simplicity and the fact that I own two Macs, I will be walking us through these steps using MAMP. Sorry but they just work…

1.) Database Setup
Lets first go ahead and open up our AMP stack and create a new database with some user information. First we are going to need to create a new database. Go ahead and use this SQL statement to expedite the process.

 

CREATE TABLE `users` (
  `id` int(11) NOT NULL auto_increment,
  `user_name` varchar(20) NOT NULL,
  `user_pass` varchar(20) NOT NULL,
  PRIMARY KEY  (`id`)
) ENGINE=MyISAM  DEFAULT CHARSET=latin1 AUTO_INCREMENT=30 ;

INSERT INTO `users` VALUES(1, 'blakeman', 'pizza132');
INSERT INTO `users` VALUES(2, 'shitfter', 'aspenishome');
INSERT INTO `users` VALUES(3, 'dynamiteman', '101party');
INSERT INTO `users` VALUES(4, 'ilovecats', 'purr342');
INSERT INTO `users` VALUES(5, 'eatallday', 'fajita98p');
INSERT INTO `users` VALUES(6, 'flexbuilder', 'flashsucks101');
INSERT INTO `users` VALUES(7, 'gregnorman', 'mygolfhero');
INSERT INTO `users` VALUES(8, 'macuser301', 'ilovemacs1');
INSERT INTO `users` VALUES(9, 'winnerMan', '092817yes');
INSERT INTO `users` VALUES(10, 'beattheheat', 'golf1234');
INSERT INTO `users` VALUES(11, 'sumemerChill', 'feeezerburn101');
INSERT INTO `users` VALUES(12, 'lp4Life', 'laspalomas101');
INSERT INTO `users` VALUES(13, 'johhnyapp', 'makemehero1');
INSERT INTO `users` VALUES(14, 'tennisplayers', 'tennis4life');
INSERT INTO `users` VALUES(15, 'eatmoregreens', 'benchpress100');
INSERT INTO `users` VALUES(16, 'collegehero', 'makebelieve');
INSERT INTO `users` VALUES(17, 'asprinhelps', 'headacheman1');
INSERT INTO `users` VALUES(18, 'diabloNXE', 'ilovepaintball');
INSERT INTO `users` VALUES(19, 'PHPman', 'aspNeverWorks');
INSERT INTO `users` VALUES(20, 'WindowsUser', 'iliedionlyusemacs');
INSERT INTO `users` VALUES(21, 'MakeFunofVista', 'everyoneelsedoes');
INSERT INTO `users` VALUES(22, 'MacRock', 'ionlyuseaPC101');
INSERT INTO `users` VALUES(23, 'unbuntuUSER', 'iActuallyDo');
INSERT INTO `users` VALUES(24, 'LinuxRocks', 'IonlyUseLinx222');
INSERT INTO `users` VALUES(25, 'ChipsandDip', 'makus101');
INSERT INTO `users` VALUES(26, 'makeitsimple', 'neverusetextmate');
INSERT INTO `users` VALUES(27, 'JonnyAppleSeed', '123Apples');
INSERT INTO `users` VALUES(28, 'LinuxFan', '123Unbuntu');
INSERT INTO `users` VALUES(29, 'SuperiorMan', '123Iwin');

 

3.) AMP Port Setup
Once you have your database set up we are going to need to make some changes to the default setting of our AMP stack. To do this you are going to need to open up your AMP application. Go to “Preferences” > “Ports” and click the button labeled “Set to default Apache and MySql ports”. This should change the port numbers to:

  1. Apache Port: 80
  2. MySQL Port: 3306

These port numbers are the default port numbers you would find when working on a non-local server.

 

4.) Open Flex Builder
Once you have made the appropriate changes to you AMP ports, lets go ahead and open up Flex builder.

 

5.) Create A New Flex Project
In your navigator start a new Flex Project titled “flex_database”. At the bottom of “Create a Flex Project” page you will see “Server Technology”. From the dropdown menu select the “PHP” option.

Once you click next you will be prompted to enter in your “Server Location” Information.

If you are using MAMP on the Mac, your information should be as follows:

 

  1. Web root: /Applications/MAMP/htdocs
  2. Root URL: http://localhost

After you have entered this information, click on “Validate Configuration”. You will see a small alert at the top stating: “The web root folder and root URL are valid.”

The following windows you can leave with all default settings and simply hit next until you finish the process. Once you are back to the main flex interface you should see your new application in the left navigator window.
6.) Creating a Flex Database Application
From the main Flex interface window we will see an option in the menu bar titled “Data” with the first option being “Create Application From Database”. Go ahead a select that option.

 

7.) Flex Database Application Connection
A new window will pop-up asking us to enter in the project that we wish to use for this Database Application. Select “flex_database” and than click “New..”.

We will be prompted to enter in information for our Connection Profile. This information can be whatever you wish to use. For this example I will use the following information:

  1. Name: “flex_database_connection”
  2. Description: “Connection to test database Application”

Select Next

 

8.) Flex Database Application Connection II
On the next window titled “Simple MySQL Connection” you will be prompted to enter in: Host URL, Database Name, User Name, and Password. The information for this example should be as follows:

  1. Host URL: localhost
  2. Database Name: flex_testing
  3. User Name: root (Enter in your User Name if not root)
  4. Password: root (Enter in your Password if not root)

After you have entered in your information, click “Test Connection”. If everything was entered correctly, you will receive a pop-up stating “The connection was successful”. If you did not go back and start again.

After this click Next followed by Finish.

 

9.) Choose Connection Data
Once you are back to the “Choose data source” page select the following options from the drop down.

  1. Connection: flex_database_connection
  2. Table: users
  3. Primary Key: id

Click Finished.

 

10.) The Final Product
At this point Flex is creating all of the files necessary to create a working Database Application. Once the files are created run the application. At this point if you are not screaming in joy I truly feel sorry for you.

Flex has just built you a Database Management Application in less than five minutes. You are able to Search, Add, Delete, and Inline Edit your database in real time.

So go ahead and play around a bit. Switch back to your database to see that the changes are in fact being made in real time. Have fun and enjoy Flex!

Alternate methods

The following steps can be followed even if you are not using an AMP stack. As long as you are using a MySQL database on an Apache Server, you can follow the same steps only replacing the information with your live server information.

September 7, 2009 Posted by suganyakalaimani | Flex Java Integration | | No Comments Yet

Connect java method From Flex

If you are looking to develop an Flex application with Java as backend(J2ee) ,then You can use either LCDS or BlazeDS for making communication between those.

BlazeDS

BlazeDS is the Java remoting and web messaging technology,By using this the developers can easily make communications between Java and Flex.

BlazeDS is an Opensource project,BlazeDS and its source code can be downloaded from

http://opensource.adobe.com/wiki/display/blazeds/Downloads

It is distibuted by GNU Lesser General Public License

You can download the integrated Tomcat with various samples to use Flex-BlazeDS-Java from

http://flexorg.wip3.adobe.com/blazeds/3.0.x/milestone/3978/blazeds-turnkey-3.2.0.3978.zip

as single download.

This download inclues Tomcat 6.0 wih various samples for using HTTPService,Remoteservice and Webservice call with Flex using blazeDs

We can use this BlazeDS for AIR clients also.

September 6, 2009 Posted by suganyakalaimani | Flex Java Integration | | No Comments Yet