Patroon Voor opnieuw proberen
In sommige situaties komt het gedrag van een gegevensbron niet overeen met de standaardverwerking van HTTP-code van Power Query. In de onderstaande voorbeelden ziet u hoe u deze situatie kunt omzeilen.
In dit scenario werkt u met een REST API die af en toe een statuscode van 500 retourneert, wat een interne serverfout aangeeft. In deze gevallen kunt u een paar seconden wachten en het opnieuw proberen, mogelijk een paar keer voordat u het opgeeft.
Als Web.Contents
er een antwoord van 500 statuscode wordt ontvangen, wordt er standaard een DataSource.Error
gegenereerd. U kunt dit gedrag overschrijven door een lijst met codes op te geven als een optioneel argument voor Web.Contents
:
response = Web.Contents(url, [ManualStatusHandling={404, 500}])
Door de statuscodes op deze manier op te geven, blijft Power Query het webantwoord gewoon verwerken. Normale reactieverwerking is echter vaak niet geschikt in deze gevallen. U moet begrijpen dat er een abnormale responscode is ontvangen en speciale logica is uitgevoerd om deze te verwerken. Als u de antwoordcode wilt bepalen die is geretourneerd vanuit de webservice, kunt u deze openen vanuit de meta
record die bij het antwoord hoort:
responseCode = Value.Metadata(response)[Response.Status]
Op basis van of responseCode
het 200 of 500 is, kunt u het resultaat als normaal verwerken of de logica voor het opnieuw proberen volgen die u in de volgende sectie gaat invullen.
Power Query heeft een lokale cache waarin de resultaten van eerdere aanroepen naar Web.Contents worden opgeslagen. Wanneer u dezelfde URL voor een nieuw antwoord peilt of wanneer u het opnieuw probeert na een foutstatus, moet u ervoor zorgen dat de query alle resultaten in de cache negeert. U kunt dit doen door de IsRetry
optie in de aanroep van de Web.Contents
functie op te geven. In dit voorbeeld wordt dit ingesteld IsRetry
true
op na de eerste iteratie van de Value.WaitFor
lus.
Value.WaitFor()
is een standaardhulpfunctie die meestal zonder aanpassingen kan worden gebruikt. Het werkt door een lijst met nieuwe pogingen te maken.
Dit bevat de taak die (mogelijk) opnieuw moet worden geprobeerd. Het wordt weergegeven als een functie, zodat het iteratienummer kan worden gebruikt in de producer
logica. Het verwachte gedrag is dat producer
wordt geretourneerd null
als een nieuwe poging noodzakelijk is. Als iets anders dan null
wordt geretourneerd door producer
, wordt die waarde op zijn beurt geretourneerd door Value.WaitFor
.
Dit bevat de logica die moet worden uitgevoerd tussen nieuwe pogingen. Het wordt weergegeven als een functie, zodat het iteratienummer kan worden gebruikt in de delay
logica. Het verwachte gedrag is dat delay
een duur retourneert.
Een maximum aantal nieuwe pogingen kan worden ingesteld door een getal op te geven voor het count
argument.
In het volgende voorbeeld ziet u hoe ManualStatusHandling
en Value.WaitFor
kan worden gebruikt om een vertraagde nieuwe poging te implementeren in het geval van een 500-reactie. Wachttijd tussen nieuwe pogingen verdubbelt bij elke poging, met maximaal vijf nieuwe pogingen.
let
waitForResult = Value.WaitFor(
(iteration) =>
let
result = Web.Contents(url, [ManualStatusHandling = {500}, IsRetry = iteration > 0]),
status = Value.Metadata(result)[Response.Status],
actualResult = if status = 500 then null else result
in
actualResult,
(iteration) => #duration(0, 0, 0, Number.Power(2, iteration)),
5)
in
if waitForResult = null then
error "Value.WaitFor() Failed after multiple retry attempts"
else
waitForResult