Synchrone fouten in een toepassing afhandelen

Flash Player 9 of hoger, Adobe AIR 1.0 of hoger

Logica voor de afhandeling van synchrone fouten komt het meest voor. Dit houdt in dat u in uw code instructies gebruikt om synchrone fouten tijdens de uitvoering af te vangen. Door dit soort foutafhandeling weet de toepassing dat er iets mis is en kunnen uitvoeringsfouten worden hersteld. De logica voor het afvangen van een synchrone fout bevat instructies van het type try..catch..instructies van het type finally, die letterlijk een bewerking proberen, eventuele foutreacties van de Flash runtime afvangen en ten slotte een andere bewerking uitvoeren om de mislukte bewerking af te handelen.

Instructies van het type try..catch..finally gebruiken

Wanneer u met synchrone uitvoeringsfouten werkt, gebruikt u de instructies try..catch..finally om fouten af te vangen. Wanneer een uitvoeringsfout optreedt, genereert Flash runtime een uitzondering. Dit betekent dat Flash runtime de normale uitvoering opschort en een speciaal object van het type Error maakt. Dit object wordt vervolgens gegenereerd voor het eerste beschikbare blok catch.

De instructie try omsluit instructies die aanleiding kunnen geven tot fouten. U moet de instructie catch altijd gebruiken met een instructie van het type try. Als een fout wordt gevonden in een van de instructies in het blok van de instructie try, worden de catch-instructies die bij die try-instructie horen uitgevoerd.

De instructie finally omsluit instructies die hoe dan ook worden uitgevoerd, of er nu wel of niet een fout optreedt in het blok try. Als er geen fout optreedt, worden de instructies in het blok finally uitgevoerd na afloop van de instructies uit het blok try. Als er wel een fout optreedt, wordt eerst de desbetreffende catch-instructie uitgevoerd en daarna komen de instructies uit het blok finally.

In de volgende code ziet u de syntaxis voor het gebruik van de instructies try..catch..finally:

try 
{ 
    // some code that could throw an error 
} 
catch (err:Error) 
{ 
    // code to react to the error 
} 
finally 
{ 
    // Code that runs whether an error was thrown. This code can clean 
    // up after the error, or take steps to keep the application running. 
}

Elke instructie van het type catch identificeert een specifiek type uitzondering die de instructie afhandelt. Met catch kunnen alleen foutklassen worden opgegeven die een subklasse zijn van de klasse Error. Elke catch-instructie wordt in volgorde gecontroleerd. Alleen de eerste catch-instructie die met het type gegenereerde fout overeenkomt, wordt uitgevoerd. Met andere woorden: als u eerst de klasse Error van het hogere niveau controleert en vervolgens een subklasse van de klasse Error, komt alleen de klasse Error van het hogere niveau overeen. Dit wordt in de volgende code geïllustreerd:

try 
{ 
    throw new ArgumentError("I am an ArgumentError"); 
} 
catch (error:Error) 
{ 
    trace("<Error> " + error.message); 
} 
catch (error:ArgumentError) 
{ 
    trace("<ArgumentError> " + error.message); 
}

De vorige code geeft de volgende uitvoer weer:

<Error> I am an ArgumentError

Om de ArgumentError goed te kunnen afvangen moet u ervoor zorgen dat de meest specifieke fouttypen als eerste worden genoemd. De meer algemene fouttypen vermeldt u dan later, zoals in de volgende code wordt getoond:

try 
{ 
    throw new ArgumentError("I am an ArgumentError"); 
} 
catch (error:ArgumentError) 
{ 
    trace("<ArgumentError> " + error.message); 
} 
catch (error:Error) 
{ 
    trace("<Error> " + error.message); 
}

Diverse methoden en eigenschappen in de ActionScript-API genereren uitvoeringsfouten als ze fouten tegenkomen tijdens de uitvoering. Zo genereert de methode close() in de klasse Sound een IOError als de methode niet in staat is om de audiostream te sluiten. Dit wordt getoond in de volgende code:

var mySound:Sound = new Sound(); 
try 
{ 
    mySound.close(); 
} 
catch (error:IOError) 
{ 
    // Error #2029: This URLStream object does not have an open stream. 
}

Naarmate u vertrouwder raakt met de Naslaggids voor ActionScript 3.0 voor het Adobe Flash-platform, zult u merken welke methoden uitzonderingen genereren. Dit wordt in de beschrijving van de methoden uitgelegd.

De instructie throw

Flash runtime genereert uitzonderingen wanneer deze fouten tijdens de uitvoering fouten in uw toepassing tegenkomen. Bovendien kunt u uitdrukkelijk zelf uitzonderingen genereren met behulp van de instructie throw. Wanneer u uitdrukkelijk zelf fouten genereert, raadt Adobe u aan om dit te doen met instanties van de klasse Error of een van de subklassen daarvan. De volgende code bevat een voorbeeld van een instructie van het type throw waarmee een instantie van de klasse Error wordt gegenereerd (MyErr) en waarmee uiteindelijk een functie wordt aangeroepen (myFunction()) als reactie na het genereren van de fout:

var MyError:Error = new Error("Encountered an error with the numUsers value", 99); 
var numUsers:uint = 0; 
try 
{ 
    if (numUsers == 0) 
    { 
        trace("numUsers equals 0"); 
    } 
} 
catch (error:uint) 
{ 
    throw MyError; // Catch unsigned integer errors. 
} 
catch (error:int) 
{ 
    throw MyError; // Catch integer errors. 
} 
catch (error:Number) 
{ 
    throw MyError; // Catch number errors. 
} 
catch (error:*) 
{ 
    throw MyError; // Catch any other error. 
} 
finally  
{ 
    myFunction(); // Perform any necessary cleanup here. 
}

De instructies catch zijn zo geordend dat de meest specifieke gegevenstypen als eerste komen. Als de instructie catch voor het gegevenstype Number als eerste voorkomt, wordt de instructie catch voor het gegevenstype uint noch de instructie catch voor het gegevenstype int ooit uitgevoerd.

Opmerking: In de programmeertaal Java moeten alle functies die een uitzondering kunnen genereren dit feit eerst declareren. Daarbij moeten de mogelijk gegenereerde uitzonderingsklassen worden vermeld in een clausule van het type throws die aan de functiedeclaratie is gekoppeld. Bij ActionScript is het niet verplicht om de uitzonderingen te declareren die door een functie worden gegenereerd.

Een eenvoudige foutmelding weergeven

Een van de grootste voordelen van het nieuwe model voor uitzonderingen en foutgebeurtenissen is dat het nu mogelijk is om de gebruikers te laten weten dat een actie is mislukt en waarom dat is gebeurd. Het is uw taak om code te schrijven voor het weergeven van de foutmelding en voor het aanbieden van opties in reactie daarop.

De volgende code bevat een enkelvoudige instructie try..catch om de fout in een tekstveld weer te geven:

package 
{ 
    import flash.display.Sprite; 
    import flash.text.TextField; 
     
    public class SimpleError extends Sprite 
    { 
        public var employee:XML =  
            <EmpCode> 
                <costCenter>1234</costCenter> 
                <costCenter>1-234</costCenter> 
            </EmpCode>; 
 
        public function SimpleError() 
        { 
            try 
            { 
                if (employee.costCenter.length() != 1) 
                { 
                    throw new Error("Error, employee must have exactly one cost center assigned."); 
                } 
            }  
            catch (error:Error) 
            { 
                var errorMessage:TextField = new TextField(); 
                errorMessage.autoSize = TextFieldAutoSize.LEFT; 
                errorMessage.textColor = 0xFF0000; 
                errorMessage.text = error.message; 
                addChild(errorMessage); 
            } 
        } 
    } 
}

Met een grotere verscheidenheid aan foutklassen en ingebouwde compilatiefouten verschaft ActionScript 3.0 meer informatie dan vorige versies van ActionScript over het waarom van een probleem. Met deze informatie kunt u stabielere toepassingen maken met een betere foutafhandeling.

Fouten opnieuw genereren

Bij het maken van toepassingen kan het gebeuren dat u een fout opnieuw moet genereren als het niet lukt om de fout goed af te handelen. De volgende code bevat bijvoorbeeld een genest blok try..catch, waarmee een aangepaste ApplicationError opnieuw wordt gegenereerd als het geneste blok catch de fout niet kan afhandelen:

try 
{ 
    try 
    { 
        trace("<< try >>"); 
        throw new ApplicationError("some error which will be rethrown"); 
    } 
    catch (error:ApplicationError) 
    { 
        trace("<< catch >> " + error); 
        trace("<< throw >>"); 
        throw error; 
    } 
    catch (error:Error) 
    { 
        trace("<< Error >> " + error); 
    } 
} 
catch (error:ApplicationError) 
{ 
    trace("<< catch >> " + error); 
}

De uitvoer van het vorige fragment wordt dan dit:

<< try >> 
<< catch >> ApplicationError: some error which will be rethrown 
<< throw >> 
<< catch >> ApplicationError: some error which will be rethrown

Het geneste blok try genereert een aangepaste ApplicationError die door het volgende blok catch wordt afgevangen. Dit geneste blok catch kan proberen de fout af te handelen en als dit niet lukt het ApplicationError-object genereren voor het omsluitende blok try..catch.