April 30, 2009
Security Bulletin
Security Bulletin for Flash Media Server:
APSB09-05 – Updates available to address Flash Media Server privilege escalation issue
http://www.adobe.com/support/security/bulletins/apsb09-05.html
Release date: April 30, 2009
Overview of the Flash Player February 2009 Security Update
http://www.adobe.com/devnet/flashplayer/articles/flash_player10.0.22_security_update.html
Update to Flex 3 to address potential cross-site scripting vulnerability
http://www.adobe.com/support/security/bulletins/apsb08-14.html
Release date: June 17, 2008
Posted by lin at 6:17 PM
RTMFP -- Real-Time Media Flow Protocol
A great new article about RTMFP
http://broadcast.oreilly.com/2009/04/adobes-real-time-media-flow-pr.html
Posted by lin at 5:47 PM
September 18, 2008
Working with Flex Builder 3
When you have problem installing/running FB3:
1. FB 3 does not work with firefox 3. See http://bugs.adobe.com/jira/browse/FB-13064 for details.
2. FB3 does not run in 64-bit eclipse, or a 64 bit JDK (JDK 1.6 on Mac is 64-bit) FB-10052
Workaround: use 32-bit eclipse or JDK.
3. UNC homedrive and homepath leads to win install failure. FB-9038
Workaround: Use a local user account.
When you have problem with FB 3 debugging/tracing:
1. Make sure you have the debug version of flash play 9 installed on the browser. You will not see trace statment if debug player is not installed crrectly.
To do that, request http://kb.adobe.com/selfservice/viewContent.do?externalId=tn_15507&sliceId=2 from the browser you use as default browser. (Ie. In the FB, if you have IE set as default browser, then run the url from IE. If the default browser for FB is set to IE, but you request that url from FireFox, that doesn’t help.) Make sure you have “Debug Player: Yes” is displayed.
2. Double check the mm.cfg and make sure it is set correctly. mm.cfg is in different location on different OS. Follow the doc here to config it.
Posted by lin at 6:07 PM | Comments (16)
using webtier compiler with flex 3
In flex 2, the webtier compiler is included in the SDK. But in flex 3, it is no longer included in the flex 3sdk install. You have to install and configure it separately. The following links will show you how to install and configure it.
http://labs.adobe.com/wiki/index.php/Flex_Module_for_Apache_and_IIS
http://livedocs.adobe.com/flex/3/html/help.html?content=apache_3.html
http://opensource.adobe.com/wiki/display/flexsdk/Downloads
There are two type of configuration:
1. config with Apache or IIS connector. If you are using Apache or IIS as your web server, then this may be the approach you want to take.
2. install as a J2EE app. This approach will install a webtier.war to your machine. Then you can deploy this war file to the app server you are using. You should deploy it as extracted app, and put your flex app page under the web root.
Problem:
When you run a flex app page with the webtier compiler, it runs fine the first time you request it. If you modify anything in the code and recompile that page, then you may see the following Error:
TypeError: Error #1010: A term is undefined and has no properties.
at mx.styles::StyleManagerImpl/initProtoChainRoots()
at mx.styles::StyleManager$/http://www.adobe.com/2006/flex/mx/internal::initProtoChainRoots()
See bug http://bugs.adobe.com/jira/browse/LCDS-387 for details.
Workaround:
By default, we are using incremental compile to do the compiling, but the incremental compile has some issues. The workaround is to not use the incremental compile.
in flex-webtier-config.xml; set the incremental-compile to false:
<incremental-compile>false</incremental-compile>
Once the change is made, the webtier compiler will work properly.
Posted by lin at 4:42 PM | Comments (17)
August 12, 2008
How to turn on debug trace in Flex
When you encounter issue wit your flex app, one useful tool for troubleshooting is to turn on debug in flex to get some output that will provide some clue of the cause of he problem. Here is how to turn it on from server-side as well as from client-side:
1. From server side:
In the services-config.xml, set the logging level to debug, and set filters to include the service you need:
<target class="flex.messaging.log.ConsoleTarget" level="debug">
<properties>
<prefix>[Flex hotfix2] </prefix>
<includeDate>true</includeDate>
<includeTime>true</includeTime>
<includeLevel>true</includeLevel>
<includeCategory>true</includeCategory>
</properties>
<filters>
<pattern>Endpoint.*</pattern>
<pattern>Service.*</pattern>
<pattern>Protocol.*</pattern>
<pattern>Message.*</pattern>
<pattern>DataService.*</pattern>
<pattern>Configuration</pattern>
</filters>
</target>
See available pattern in doc:
http://livedocs.adobe.com/livecycle/8.2/programLC/programmer/lcds/help.html?content=services_logging_3.html
2. To turn on trace in JGroup:
in jgroups-tcp.xml, add <TRACE/> tag just before the </config> line :
<config>
....
<TRACE/>
</config>
3. To turn on from client-side:
Make sure flashlog.txt is enabled, i.e, have the following setting in mm.cfg
TraceOutputFileEnable=1
ErrorReportingEnable=1
See more details in the doc here
There is a good blog regarding mm.cfg here as well.
Then in your flex app, add the following tag:
<mx:TraceTarget/>
4. To turn on the flash player policy logging
see http://www.adobe.com/devnet/flashplayer/articles/fplayer9_security_05.html
Posted by lin at 4:38 PM | Comments (48)
April 4, 2008
Tips for working with time zone in flex app
1. Understand how date and time are determined by flex (player on the client machine)
From flex doc we can see:
"The Date class lets you retrieve date and time values relative to universal time (Greenwich mean time, now called universal time or UTC) or relative to local time, which is determined by the local time zone setting on the operating system that is running Flash Player. "
This mean if one user's machine is using "Automatically adjust clock for daylight saving changes", the time displaied in flex app may be different with another user who is running the same flex app without “Automatically adjust clock for daylight saving changes” on his machine.
"Automatically adjust clock for daylight saving changes" can be checked from
Control Panel --> Date and time -->Time Zone.
2. Understand how date and time are determined by Java ( On server machine)
1). The JVM determines the correct Coordinated Universal Time (UTC) by comparing the QUTCOFFSET value to the local time for the system
The JVM returns the correct local time to the system by using the Java system property user.timezone.
The default value for QUTCOFFSET is zero (+00:00).
The QUTCOFFSET value allows the JVM to determine the correct value for the local time. For example, the value for QUTCOFFSET to specify central standard time (CST) is -6:00. To specify central daylight time (CDT), QUTCOFFSET has a value of -5:00.
The user.timezone Java system property uses UTC time as the default value. Unless you specify a different value, the JVM recognizes UTC time as the current time.
See more details in here
2). you need correct patches for Java to get correc date and time.
-- There is a patch for jdk you may want to double check:
http://sunsolve.sun.com/search/document.do?assetkey=1-26-102836-1
-- if you are using Solaris, you may need this patch
http://sunsolve.sun.com/search/document.do?assetkey=1-26-103044-1
-- if you are using 1.4.2_10 or lower version of JDK, you need this patch
http://kb.adobe.com/selfservice/viewContent.do?externalId=kb400722
3). To verify your time zone setting in JDK, read this
http://publib.boulder.ibm.com/infocenter/wasinfo/v4r0/index.jsp?topic=/com.ibm.support.was.doc/html/WebSphere_Application_Server/1173447.html
Download time.jsp from there, and run it on your server.
To change timezone setting in Java, you can use java arg:
-Duser.timezone=America/Los_Angeles
If you are using Jrun as app sever, this can be change in JRun_install/bin/jvm.config file:
java.args=-Xms32m -Xmx384m -Dsun.io.useCanonCaches=false -Duser.timezone=Etc/UCT
3. synchronize time znoe on client and server
If you want to enter time in the client’s local time - regardless of the timezone your in at the time of data entry, and keep the date in UTC zone on both server and client side, see example
Note, don’t forget you also need to set JAVA VM timezone to UTC for this example.
Posted by lin at 4:49 PM | Comments (124)
April 3, 2008
How to access flex app over https but connect to backend using http
Many application needs to be accessed over secure connection, but only need to connect to the backend using non-secure connection, or vice versa. How do we accomplish that?
Secure connections can talk to secure and non-secure endpoints. Non-secure connections can only talk to non-secure endpoints. So you will need to configure your channel differently.
1. If the app is requested over https and then use http to connect to backend:
<channel-definition id="my-amf-secure" class="mx.messaging.channels.SecureAMFChannel">
<endpoint uri="https://{server.name}:{server.port}{context.root}/flex2gateway/" class="flex.messaging.endpoints.AMFEndpoint "/>
<properties>
<add-no-cache-headers>false</add-no-cache-headers>
</properties>
</channel-definition>
2. If the flex app is requested over http, then using https to connect backend:
<channel-definition id="my-amf" class="mx.messaging.channels.SecureAMFChannel">
<endpoint uri="https://{server.name}:{server.port}{context.root}/flex2gateway/" class="flex.messaging.endpoints.SecureAMFEndpoint"/>
<properties>
<add-no-cache-headers>false</add-no-cache-headers>
</properties>
</channel-definition>
3. For LCDS 2.5 and 2.5.1, the configuration would be enough.
For FDS 201, you need to apply the hotfix build 168076 as well. You can get the build 168076 from flex Tech support.
Posted by lin at 2:08 PM | Comments (123)
March 12, 2008
How to apply chart license to flex 3
Some user found that after upgrade from FB2/Flex2 to FB3/Flex3, the chart watermark appears in the app. This is because the license has not applied correctly. There are certain changes regarding how we get license info, and they are described in the doc http://livedocs.adobe.com/flex/3/html/help.html?content=configuring_environment_2.html
Also see Blog entries:
http://raghuonflex.wordpress.com/2008/02/19/changes-in-flex-beta-3-licensing-model/
http://raghuonflex.wordpress.com/2008/02/20/how-to-apply-the-data-visualization-license-on-command-line-in-flex-3/
Basically, here are the things you need to know:
1. If you want to compile with flex 3 SDK, you will need a new license for flex 3. The license for flex 2 sdk would not work.
2. To apply the license from FB3, go to Help --> Manage flex license, then type in the license key. It should look like this: 1377-xxxx-xxxx-xxxx-xxxx-xxxx.
3. To apply the license in flex-config.xml:
<flex-config>
<licenses>
<license>
<product>flexbuilder3</product>
<serial-number>1377-xxxx-xxxx-xxxx-xxxx-xxxx</serial-number>
</license>
</licenses>
<compiler>
...
</compiler>
</flex-config>
4. To apply the license in license.properties file:
The path to the license.properties file for various OS are changes for flex 3, they are now at:
1)."../Documents and Settings/All Users/Application Data/Adobe/Flex" directory on Windows
2)."Library/Application Support/Adobe/Flex" directory on MAC
3)."$HOME/.adobe/Flex" on Linux
Posted by lin at 6:12 PM | Comments (132)
February 22, 2007
Accessing Spring beans from flex (FDS)
1. What is Spring? Why do we care about Spring?
Christophe Coenraets ‘ s 30 minute test drive provides good answer to these questions. See details here.
2. Spring Configuration
You can follow the steps described by Christophe or Jeff Vroom, or you can follow the steps below which provide easier access to the required jars.
1). Download spring.jar and flex-spring-factory.jar to your machine, and put them into your flex app’s WEB-INF/lib directory.
2). Add the following into your flex app’s WEB-INF/web.xml file, inside <web-app> tag.
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/applicationContext.xml</param-value>
</context-param>
<listener>
<listener-class> org.springframework.web.context.ContextLoaderListener </listener-class>
</listener>
3). Add the following into to WEB-INF\flex\services-config.xml inside <services-config> tag:
<factories>
<factory id="spring" class="flex.samples.factories.SpringFactory"/>
</factories>
4). If you are using JRun as app server, set the following in WEB-INF\jrun-web.xml to avoid parser conflicting:
<jrun-web-app>
<load-system-classes-first>
true</load-system-classes-first>
</jrun-web-app>
Now you are ready to use flex to access Spring beans.
3. Create Spring beans
We are going to use the sample code in singleManagedObject.zip. To understand the code and configuration, see ""How to get Single Managed Objects from a specified remote destination". In that example, we access data from DataService using an Assembler MyAssembler.java. With the Assembler, we should be able to access Spring beans, right? Well, we are just a couple of steps away.
1). Create an interface (MyDAO.java)
Because we are trying to access Spring beans, we need to add an interface that represents all the methods we are going to use. From MyService.java we can see that there are only two methods for this sample, so MyDAO.java is going to be very simple:
package myfds;
import java.util.Collection;
import java.util.List;
import org.springframework.dao.DataAccessException;
public interface MyDAO {
public List getProducts() throws DataAccessException ;
public MyBean getProduct(int myid) throws DataAccessException ;
}
2). Modify MyService.java and MyAssembler.java
--- copy MyService.java and save it as MyServiceSpring.java
Change the class to extends JdbcDaoSupport and implements the interface:
import org.springframework.dao.DataAccessException;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.jdbc.core.RowMapper;
import org.springframework.jdbc.core.namedparam.BeanPropertySqlParameterSource;
import org.springframework.jdbc.core.namedparam.NamedParameterJdbcTemplate;
import org.springframework.jdbc.core.namedparam.SqlParameterSource;
import org.springframework.jdbc.core.support.JdbcDaoSupport;
public class MyServiceSpring extends JdbcDaoSupport implements MyDAO {
......
--- copy MyAssembler.java and save it as MyAssemblerSpring.java
Change the class with setMyDAO():
import flex.data.assemblers.AbstractAssembler;
public class MyAssemblerSpring extends AbstractAssembler {
private MyDAO myDAO;
public void setMyDAO(MyDAO myDAO) {
this.myDAO = myDAO;
}
........
3). Compile your java code
Remember to include spring.jar and flex-messaging.jar in the classpath,
C:\flex\jrun4\servers\default\samples2\WEB-INF\classes>javac -classpath ./;C:\fl
ex\jrun4\servers\default\samples2\WEB-INF\lib\spring.jar;C:\flex\jrun4\servers\d
efault\samples2\WEB-INF\lib\flex-messaging.jar -Xlint myfds/*.java
Now we have the spring bean that we can access from flex, we need to register it with our flex app, and configure flex destination to point to the Spring factory.
4. Spring beans registration and flex destination configuration
1). Create applicationContext.xml and put it under your flex app’s WEB-INF directory. Here is the applicationContext.xml for this example:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN" "http://www.springframework.org/dtd/spring-beans.dtd">
<beans>
<!--define a data source to connect to your database -->
<bean id="dataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<property name="driverClassName" value="org.hsqldb.jdbcDriver"/>
<property name="url" value="jdbc:hsqldb:hsql://localhost/flexdemodb"/>
<property name="username" value="sa"/>
<property name="password" value=""/>
</bean>
<!-- define your service (methods) with a reference to dataSource -->
<bean id="myServiceSpring" class="myfds.MyServiceSpring">
<property name="dataSource" ref="dataSource"/>
</bean>
<!-- define assembler with reference (dependency) to myServiceSpring -->
<bean id="myAssemblerSpring" class="myfds.MyAssemblerSpring" singleton="true">
<!--the property name myDAO should match the variable for interface MyDAO defined in MyAssemblerSpring-->
<property name="myDAO" ref="myServiceSpring"/>
</bean>
</beans>
Note, myServiceSpring will be the soruce name you use in the destination you define below.
2). Configure destination
We have registered Spring factory in WEB-INF\flex\services-config.xml in step 2 #3).
<factory id="spring" class="flex.samples.factories.SpringFactory"/>
Therefore we need to point the destination to spring factory. Add the following into WEF-INF\flex\Data-management-config.xml:
<destination id="myfds-spring">
<adapter ref="java-dao" />
<properties>
<factory>spring</factory>
<source>myAssemblerSpring</source>
<metadata>
<identity property="myid"/>
</metadata>
</properties>
</destination>
Now, in flex mxml page, you can access the destination myfds-spring by doing something like this:
<mx:DataService id="ds" destination="myfds-spring" result="getData1(event)"/>
And call the methods in the Spring beans by using ds.getItem({myid:2})
If you run myDataServiceSpring.mxml, you can get data from different method by click on different button.
Here is the simpleSpring.zip which incdules all the code.
Posted by lin at 7:04 PM | Comments (187)
February 21, 2007
How to get Single Managed Objects from a specified remote destination
Flex Campaign for Java Developers has launched on Monday, Feb. 13. This is good news for java developer who would like to make Flex app work with backend database.Christophe Coenraets 's 30 minute test drive provides many examples about how to manipulate data with FDS. You can download the test drive server here.
Once you extracted fds-tomcat.zip , you can see flex samples that integrate with ActiveMQ , Spring 2 , Hibernate 3.2 , and HSQLDB 1.8 . Sample 8 under testdrive folder demonstrated how to retrieve/create/update/delete data using FDS. The flex client code displays the collection managed objects retrieved from backend. However, users may have difficulty to get Single Managed Objects from flex app. It may not be clear how the identity is passed to the method. I was asked to create a sample to get Single Managed Objects from a specified remote destination. I am putting a simplified version of the example here to demonstrate how to do that.
1. Create java Assembler
1). Create your bean (MyBean.java)
First you create your bean with the data field you needed, and set/get method for each of them.
2). Create MyService.java for your methods
For simplicity, I have only defined two methods:
getProducts() -- retrieve all data, returns a list
getProduct(int myid) --- retrieve data with myid as identity, returns a single Object.
3). Create an Assembler (MyAssembler.java)
MyService service = new MyService();
return service.getProducts();
}
public Object getItem(Map identity) {
MyService service = new MyService();
MyBean mybean = service.getProduct(((Integer) identity.get("myid")).intValue());
System.out.println("mybean.myid="+mybean.myid);
return mybean;
}
As we can see, fill() method calls getProducts(), and getItem() calls getProduct() from MyService.
Note, MyBean mybean = service.getProduct(((Integer) identity.get("myid")).intValue());
Here myid is the identity field. It must match the identity property in your destination configuration:
<identity property="myid"/>
2. Compile your java code.
As we mentioned before, MyAssembler extends AbstractAssembler which is defined in flex-messaging.jar. So when you compile the java code, you must include flex-messaging.jar in your classpath. This jar is included in your fds flex app’s \WEB-INF\lib directory. For example:
C:\flex\jrun4\servers\default\samples2\WEB-INF\classes>javac -classpath ./;C:\fds-tomcat\webapps\ROOT\WEB-INF\lib\flex-messaging.jar -Xlint myfds/*.java
3. Mapping client-side objects to Java objects
This is a very important step, but easy to forget. Here are some key points from doc:
1). To represent a server-side Java object in a client application, you use the [RemoteClass(alias=" ")] metadata tag to create an ActionScript object that maps directly to the Java object. You specify the fully qualified class name of the Java class as the value of alias. This is the same technique that you use to map to Java objects when using RemoteObject components.
2).You can use the [RemoteClass] metadata tag without an alias if you do not map to a Java object on the server, but you do send back your object type from the server. Your ActionScript object is serialized to a Map object when it is sent to the server, but the object returned from the server to the clients is your original ActionScript type.
3). To create a managed association between client-side and server-side objects, you also use the [Managed] metadata tag or explicitly implement the mx.data.IManaged interface. The [Managed] metadata tag ensures that the managed Contact object supports the proper change events to propagate changes between the client-based object and the server-based object.
See MyBeam.as for code details.
4. configure destination in data-management-config.xml
add the following into your data-management-config.xml, parallel to other destination definition.
<destination id="myfds">
<adapter ref="java-dao" />
<properties>
<source>myfds.MyAssembler</source>
<scope>application</scope>
<metadata>
<identity property="myid"/>
</metadata>
<network>
<session-timeout>20</session-timeout>
<paging enabled="false" pageSize="10" />
<throttle-inbound policy="ERROR" max-frequency="500"/>
<throttle-outbound policy="REPLACE" max-frequency="500"/>
</network>
</properties>
</destination>
Note: source should point to the full qualified class name of your assembler.
Identity should match the identity you are passing in Assembler:
MyBean mybean = service.getProduct(((Integer) identity.get("myid")).intValue());
5. create flex page to display the data (myDataSerivce.mxml)
1). Retrieve data
<mx:ArrayCollection id="mydata1"/>
<mx:DataService id="ds1" destination="myfds" result="getData(event)"/>
<mx:Button id="bt1" label="Get data from fill method" click="ds1.fill(mydata1)"/>
<mx:Button id="bt2" label="Get data from getItem method" click="ds1.getItem({myid:2})"/>
--- We first define a DataService ds1 which is mapped to destination named myfds. This should match <destination id="myfds"> in data-management-config.xml.
---We call ds1.fill(mydata1) to populates an ArrayCollection mydata1, and use it as dataProvider of the datagrid.
<mx:DataGrid dataProvider="{mydata1}" width="300" height="100%" >
---We use ds1.getItem({myid:2}) to get single Object based on the dentity myid we passed into getItem.
2). We use a result handler getData(event) to handle the data we retrieved from DataService. This will make sure that your event is trigged after the data has returned.
Now let’s look at resulte handler getData():
private function getData(event:ResultEvent):void{
if(myButton == "bt1"){
prodId.text = event.result[1].prodID;
firstName.text = event.result[1].firstName;
lastName.text = event.result[1].lastName;
}else{
prodId.text = event.result.prodID;
firstName.text = event.result.firstName;
lastName.text = event.result.lastName;
}
}
Because fill() method returns an ArrayCollection, getItem() returns a single object, so we have to treat it differently. To figure out which method is called by the user, we add EventListener to the button, and record the button id.
private function init():void{
bt1.addEventListener(MouseEvent.CLICK,clickHandler);
bt2.addEventListener(MouseEvent.CLICK,clickHandler);
}
private function clickHandler(event:MouseEvent):void{
myButton = event.currentTarget.id;
}
Now, when you click different button, different data will be displayed in "User Details" TitleWindow.
6. To test the sample:
1). Unzip singleManagedObject.zip to your machine . Put myfds folder under your flex app’s WEB-INF/classes directory. Put myDataService.mxml and MyBean.as under you flex app’s root directory.
2). Double check the step 4 mentioned above. Restart your flex app server if needed.
3). Run myDataService.mxml, click on the two buttons and see different data displayed.
7. Troubleshooting
If there are no erros client side, but can't get data to retrun from the server side, check the following:
1). double check step 4 mentioned above, make sure your destinatio id, sourceand identity property are defined correctly. Also, make sure your database connection is valid and qurey statement are correctly retrieving data.
2). Trun on server side debug bysetting log level to debug in services-config.xml:
<target class="flex.messaging.log.ConsoleTarget" level="Debug">
Posted by lin at 5:50 PM | Comments (270)