Flex4数据库操作(服务器端使用PHP)是异步调用,也就意味着调用服务器端(PHP)函数操作数据库时客户端(Flex)不等待数据库操作完成就已经返回了。这样就会带来视图显示和数据库数据内容不一致的问题。
什么是“视图显示和数据库数据内容不一致?”简单点说,就是控件显示内容与数据库中的实际内容不相符。不过,似乎还是通过一个例子来描述会更为直观。实现仓库名称显示的Flex页面和仓库名称添加的页面:
第一个Flex页面实现仓库名称显示,并可通过“添加”和“删除”按钮对仓库名称进行管理。当点击“添加”按钮时弹出第二个页面,在第二个页面中输入新的仓库名称,并调用服务器端函数additem($item)实现仓库名称添加。虽然看起来很简单,但是实现的过程中需要特别注意两方面的问题:
1、事件监听——监听子对话框关闭事件。添加页面通过PopUpManage以对话框的方式弹出,在“添加”操作完成后仓库名称管理页面需要更新DataGrid的内容。也就是,仓库管理页面需要监听添加页面的关闭操作。
仓库管理页面“添加”按钮处理事件:
protected function btn_add_clickHandler(event:MouseEvent):void
{
var widget_storehouse_add:storehouse_add = new storehouse_add; // 构造添加页面对象
PopUpManager.addPopUp(widget_storehouse_add, this, true);// 通过PopUpManager弹出
PopUpManager.centerPopUp(widget_storehouse_add);// 居中显示
// 为添加页面添加事件监听器,当添加页面关闭后执行监听器函数addStroehouse_closed
widget_storehouse_add.addEventListener(CloseEvent.CLOSE, addStroehouse_closed);
}
仓库管理页面监听器函数:
private function addStroehouse_closed(evnet:CloseEvent):void
{
// 从数据库中重新读取数据,因为添加页面关闭时可能对数据库进行修改
getAllStorehouseResult.token = storehouseService.getAllStorehouse();
}
2、事件监听——监听服务器端函数调用结束(等待异步调用结束)。这个问题才是本文主要讨论的问题,我们先来看一下问题的起源。在添加页面中,调用服务器端函数对数据库进行添加操作:
protected function btn_add_clickHandler(event:MouseEvent):void
{
var data_add:DataStorehouse = new DataStorehouse; // 仓库数据对象
data_add.storehouse_name = textinput_name.text;
storehouseService.createItem(data_add);// 执行服务器端数据库操作
PopUpManager.removePopUp(this);// 关闭对话框返回仓库名称管理页面
}
添加操作函数没有问题,调用storehouseService.createItem(data_add);将数据写入数据库。问题在服务器端函数createItem(data_add)是异步执行的,换句话说btn_add_clickHandler不会阻塞等待createItem(data_add);执行结束再继续往下执行。这样就会导致,添加对话框被关闭了,仓库管理页面也触发了addStroehouse_closed事件,但是这个时候数据库的数据还是未添加的数据内容(createItem异步调用还未完成),从而导致addStroehouse_closed获取的还是原始数据,这样就产生了”视图显示和数据库数据内容不一致“的问题。
解决数据库异步操作所带来的问题的方法是——为数据库操作添加事件监听器。
在添加页面中为数据库操作添加事件监听器,当createItem调用完成后再关闭对话框。
// 定义数据库操作完成后触发事件storeUpdateEnd_resultHandler
<fx:Declarations>
<s:CallResponder id="storeUpdateEnd" result = "storeUpdateEnd_resultHandler"/>
</fx:Declarations>
// 数据库调用完成后处理事件函数storeUpdateEnd_resultHandler
protected function storeUpdateEnd_resultHandler(event:ResultEvent):void
{
PopUpManager.removePopUp(this);
}
// 修改添加按钮事件
protected function btn_add_clickHandler(event:MouseEvent):void
{
var data_add:DataStorehouse = new DataStorehouse; // 仓库数据对象
data_add.storehouse_name = textinput_name.text;
storeUpdateEnd.token = storehouseService.createItem(data_add);// 执行服务器端数据库操作
}
Q.P.K
2012年7月5日于北京邮电大学新科研楼302重新整理