Padrão de espera-repetição
Em algumas situações, o comportamento de uma fonte de dados não corresponde ao esperado pela manipulação de código HTTP padrão do Power Query. Os exemplos abaixo mostram como contornar essa situação.
Nesse cenário, você estará trabalhando com uma API REST que ocasionalmente retorna um código de status 500, indicando um erro interno do servidor. Nesses casos, você pode esperar alguns segundos e tentar novamente, potencialmente algumas vezes antes de desistir.
Se Web.Contents
obtiver uma resposta de código de status 500, ele lançará um DataSource.Error
por padrão. Você pode substituir esse comportamento fornecendo uma lista de códigos como um argumento opcional para Web.Contents
:
response = Web.Contents(url, [ManualStatusHandling={404, 500}])
Ao especificar os códigos de estado desta forma, o Power Query continuará a processar a resposta Web normalmente. No entanto, o processamento normal da resposta muitas vezes não é apropriado nesses casos. Você precisará entender que um código de resposta anormal foi recebido e executar uma lógica especial para lidar com ele. Para determinar o código de resposta que foi retornado do serviço Web, você pode acessá-lo a meta
partir do Registro que acompanha a resposta:
responseCode = Value.Metadata(response)[Response.Status]
Com base em 200 responseCode
ou 500, você pode processar o resultado normalmente ou seguir sua lógica de espera e repetição que você detalhará na próxima seção.
O Power Query tem uma cache local que armazena os resultados de chamadas anteriores para Web.Contents. Ao sondar o mesmo URL para obter uma nova resposta ou ao tentar novamente após um status de erro, você precisará garantir que a consulta ignore todos os resultados armazenados em cache. Você pode fazer isso incluindo a opção na chamada para a IsRetry
Web.Contents
função. Neste exemplo, definiremos IsRetry
como true
após a primeira iteração do Value.WaitFor
loop.
Value.WaitFor()
é uma função auxiliar padrão que geralmente pode ser usada sem modificações. Ele funciona construindo uma lista de tentativas de repetição.
Isso contém a tarefa a ser (possivelmente) repetida. É representado como uma função para que o número de iteração possa ser usado na producer
lógica. O comportamento esperado é que producer
retornará null
se uma nova tentativa for determinada como necessária. Se algo diferente for null
retornado por , esse valor é, por sua vez, retornado por producer
Value.WaitFor
.
Isso contém a lógica a ser executada entre tentativas. É representado como uma função para que o número de iteração possa ser usado na delay
lógica. O comportamento esperado é que delay
retorna uma duração.
Um número máximo de novas tentativas pode ser definido fornecendo um número para o count
argumento.
O exemplo a seguir mostra como ManualStatusHandling
e Value.WaitFor
pode ser usado para implementar uma nova tentativa atrasada no caso de uma resposta 500. O tempo de espera entre novas tentativas dobra a cada tentativa, com um máximo de cinco tentativas.
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