4

我正在尝试使用 UrlLoader 模拟“HEAD”方法;本质上,我只想检查文件是否存在而不下载整个文件。我想我只会使用 HttpStatusEvent,但是当您在调试模式下运行时,以下代码会引发异常(我无法将其包装在 try/catch 块中)。

<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute" initialize="init()">
<mx:Script>
    <![CDATA[

       private static const BIG_FILE:String = "http://www.archive.org/download/gspmovvideotestIMG0021mov/IMG_0021.mov";

       private var _loader:URLLoader;

       private function init():void {
            _loader = new URLLoader();
            _loader.addEventListener(HTTPStatusEvent.HTTP_STATUS, statusHandler);
            _loader.addEventListener(IOErrorEvent.IO_ERROR, errorHandler);
            _loader.addEventListener(SecurityErrorEvent.SECURITY_ERROR, errorHandler);
            _loader.load(new URLRequest(BIG_FILE));   
       }

       public function unload():void { 
            try {
                _loader.close();
                _loader.removeEventListener(HTTPStatusEvent.HTTP_STATUS, statusHandler);
                _loader.removeEventListener(IOErrorEvent.IO_ERROR, errorHandler);
                _loader.removeEventListener(SecurityErrorEvent.SECURITY_ERROR, errorHandler);
            }
            catch(error:Error) {
                status.text = error.message;
            }
        }

        private function errorHandler(event:Event):void {
            status.text = "error";
            unload();
        }

        private function statusHandler(event:HTTPStatusEvent):void {
            if(event.status.toString().match(/^2/)) {
                status.text = "success";
                unload();
            }
            else {
                errorHandler(event);
            }
        }   
    ]]>
</mx:Script>

<mx:Label id="status" />

我尝试改用 ProgressEvents,但似乎有些 404 页面返回内容,因此状态事件将正确识别页面是否存在。

有人有想法么?

4

2 回答 2

6

我认为这是 URLLoader 类中的一个错误。

如果您阅读了错误消息(至少是我收到的错误消息,您还没有粘贴 yorrs!),您将看到它:

错误:错误 #2029:此 URLStream 对象没有在 flash.net::URLStream/readBytes() 在 flash.net::URLLoader/onComplete() 处打开的流

这让您对正在发生的事情有所了解。URLLoader 类在内部使用URLStream对象,该对象提供对下载数据的低级访问。

错误消息表明在 URLLoader 上调用了 onComplete 处理程序。该文件很大,但可能已缓存,因此加载速度相当快。现在,如果您为进度和完成事件添加侦听器,您将看到触发事件的顺序如下:

  • 进步
  • 地位
  • 完全的

文档证实了这一点:

请注意,httpStatus 事件(如果有)是在任何完成或错误事件之前(以及除此之外)发送的。

现在,您可以看到问题在于您正在调用 close() 的状态处理程序。这将关闭流。但显然(我认为这是错误),URLLoader 类中的 onComplete 处理程序不会检查流是否打开。(从 Actionscript 无法检查这一点,因此您必须将代码包装在 try/catch 中)。您无法从封闭的流中读取数据,所以这就是它爆炸的原因。

我可以看到两种方法来解决这个问题:

1)延迟调用close()的函数(你的unload方法)的执行,所以close()在URLLoader内部的onComplete方法被调用之后被调用。

也就是说,这样做:

setTimeout(unload,1);

而不是这个:

unload();

2) 使用 URLStream 而不是 URLLoader。第一个选项让我觉得有点骇人听闻的解决方法,所以在你的情况下,我会选择最后一个。通常,使用 URLStream 意味着您需要做更多的工作,但在这种情况下,您实际上对读取任何数据并不感兴趣,因此它没有太大区别。另外,您只需要更改当前代码中的两行:

这个:

private var _loader:URLStream;

和这个:

_loader = new URLStream(); 

你都准备好了。

于 2010-05-30T01:52:37.657 回答
1

我遇到了类似的问题。
我发现问题是这个电话:

_loader.close();

当我试图关闭一个我什至没有打开的文件时发生了错误。因此,在“try”子句中,在尝试关闭文件之前检查文件是否已打开。

麦克风

于 2011-01-10T15:34:17.520 回答