web-dev-qa-db-fra.com

Comment utiliser la pagination Boto3

CONTEXTE:

L'opération AWS pour répertorier les utilisateurs IAM renvoie un maximum de 50 par défaut.

En lisant les documents (liens) ci-dessous, j'ai exécuté le code suivant et renvoyé un ensemble de données complet en définissant les "MaxItems" à 1000.

paginator = client.get_paginator('list_users')
response_iterator = paginator.paginate(
 PaginationConfig={
     'MaxItems': 1000,
     'PageSize': 123})
for page in response_iterator:
    u = page['Users']
    for user in u:
        print(user['UserName'])

http://boto3.readthedocs.io/en/latest/guide/paginators.htmlhttps://boto3.readthedocs.io/en/latest/reference/services/iam. html # IAM.Paginator.ListUsers

QUESTION:

Si "MaxItems" a été défini sur 10, par exemple, quelle serait la meilleure méthode pour parcourir les résultats? les

J'ai testé avec ce qui suit mais il ne boucle que 2 itérations avant 'IsTruncated' == False et résulte en "KeyError: 'Marker'". Je ne sais pas pourquoi cela se produit, car je sais qu'il y a plus de 200 résultats.

marker = None

while True:
    paginator = client.get_paginator('list_users')
    response_iterator = paginator.paginate( 
        PaginationConfig={
            'MaxItems': 10,
            'StartingToken': marker})
    #print(response_iterator)
    for page in response_iterator:
        u = page['Users']
        for user in u:
            print(user['UserName'])
            print(page['IsTruncated'])
            marker = page['Marker']
            print(marker)
        else:
            break

Merci.

9
user45097

(Réponse réécriture) ** REMARQUE **, le paginateur contient un bogue qui ne correspond pas à la documentation (ou vice versa). MaxItems ne renvoie pas le marqueur ou le NextToken lorsque le nombre total d'éléments dépasse le nombre MaxItems. En effet PageSize est celui qui contrôle le retour de l'indicateur Marker/NextToken.

import sys
import boto3
iam = boto3.client("iam")
marker = None
while True:
    paginator = iam.get_paginator('list_users')
    response_iterator = paginator.paginate( 
        PaginationConfig={
            'PageSize': 10,
            'StartingToken': marker})
    for page in response_iterator:
        print("Next Page : {} ".format(page['IsTruncated']))
        u = page['Users']
        for user in u:
            print(user['UserName'])
    try:
        marker = page['Marker']
        print(marker)
    except KeyError:
        sys.exit()

Ce n'est pas votre erreur si votre code ne fonctionne pas. MaxItems dans le paginateur semble devenir un indicateur "seuil". Ironiquement, le MaxItems à l'intérieur de boto3.iam.list_users d'origine fonctionne toujours comme mentionné.

Si vous cochez boto3.iam.list_users, vous remarquerez que vous omettez Marker, sinon vous devez mettre une valeur. Apparemment, paginator n'est PAS un wrapper pour toutes les méthodes list_ * de la classe boto3.

import sys
import boto3
iam = boto3.client("iam")
marker = None
while True:
    if marker:
        response_iterator = iam.list_users(
            MaxItems=10,
            Marker=marker
        )
    else:
        response_iterator = iam.list_users(
            MaxItems=10
        )
    print("Next Page : {} ".format(response_iterator['IsTruncated']))
    for user in response_iterator['Users']:
        print(user['UserName'])

    try:
        marker = response_iterator['Marker']
        print(marker)
    except KeyError:
        sys.exit()

Vous pouvez suivre le problème que j'ai déposé dans boto3 github . Selon le membre, vous pouvez appeler build_full_result après paginate (), qui montrera le comportement souhaité.

10
mootmoot