Classe DynamoDBMapper - Amazon DynamoDB

Le traduzioni sono generate tramite traduzione automatica. In caso di conflitto tra il contenuto di una traduzione e la versione originale in Inglese, quest'ultima prevarrà.

Classe DynamoDBMapper

La classe DynamoDBMapper è il punto di ingresso al database Amazon DynamoDB. Fornisce l'accesso a un endpoint DynamoDB e consente di accedere ai dati in diverse tabelle. Consente anche di eseguire diverse operazioni di creazione, lettura, aggiornamento ed eliminazione (CRUD) sugli elementi e di eseguire query e scansioni sulle tabelle. Questa classe fornisce i metodi seguenti per lavorare con DynamoDB.

Per la documentazione Javadoc corrispondente, consulta DynamoDBMapper nella Documentazione di riferimento delle API di AWS SDK for Java .

save

Salva l'oggetto specificato nella tabella. L'oggetto che intendi salvare è l'unico parametro obbligatorio di questo metodo. Puoi fornire parametri di configurazione opzionali utilizzando l'oggetto DynamoDBMapperConfig.

Se non esiste un item avente la stessa chiave primaria, questo metodo crea un nuovo item nella tabella. Se esiste un item avente la stessa chiave primaria, esso aggiorna l'item esistente. Se la chiave di partizione e la chiave di ordinamento sono del tipo String e sono annotate con @DynamoDBAutoGeneratedKey, viene loro assegnato un identificatore unico universale casuale (UUID) in caso di mancata inizializzazione. I campi di versione annotati con @DynamoDBVersionAttribute vengono incrementati di una unità. Inoltre, se viene aggiornato un campo di versione o viene generata una chiave, l'oggetto passato si aggiornerà a seguito dell'operazione.

Per impostazione predefinita, solo gli attributi corrispondenti alle proprietà della classe mappate vengono aggiornati. Glie eventuali attributi esistenti aggiuntivi su un item non sono interessati. Tuttavia, se specifichi SaveBehavior.CLOBBER, puoi forzare la sovrascrittura completa dell'item.

DynamoDBMapperConfig config = DynamoDBMapperConfig.builder() .withSaveBehavior(DynamoDBMapperConfig.SaveBehavior.CLOBBER).build(); mapper.save(item, config);

Se la funzione Versioni multiple è abilitata, le versioni dell'item lato client e lato server devono corrispondere. Tuttavia, non è necessario che la versione corrisponda se viene utilizzata l'opzione SaveBehavior.CLOBBER. Per ulteriori informazioni sulla funzione Controllo delle versioni, consulta Blocco ottimistico con il numero di versione.

caricare

Recupera un item da una tabella. È necessario fornire la chiave primaria dell'item che intendi recuperare. Puoi fornire parametri di configurazione opzionali utilizzando l'oggetto DynamoDBMapperConfig. Ad esempio, puoi richiedere facoltativamente letture fortemente consistenti per garantire che questo metodo recuperi solo i valori di item più recenti, come riportato nella seguente dichiarazione Java.

DynamoDBMapperConfig config = DynamoDBMapperConfig.builder() .withConsistentReads(DynamoDBMapperConfig.ConsistentReads.CONSISTENT).build(); CatalogItem item = mapper.load(CatalogItem.class, item.getId(), config);

Per impostazione predefinita, DynamoDB restituisce l'elemento che dispone di valori con consistenza finale. Per informazioni sul modello di consistenza finale di DynamoDB, consulta Consistenza di lettura.

Elimina

Elimina un item dalla tabella. È necessario passare un'istanza di oggetto della classe mappata.

Se la funzione Versioni multiple è abilitata, le versioni dell'item lato client e lato server devono corrispondere. Tuttavia, non è necessario che la versione corrisponda se viene utilizzata l'opzione SaveBehavior.CLOBBER. Per ulteriori informazioni sulla funzione Controllo delle versioni, consulta Blocco ottimistico con il numero di versione.

query

Esegue una query su una tabella o un indice secondario.

Supponiamo che tu abbia una tabella, Reply, in cui vengono memorizzate le risposte dei thread di un forum. Ogni tema del thread può contenere 0 o più risposte. La chiave primaria della tabella Reply è costituita dai campi Id e ReplyDateTime, in cui l'Id è la chiave di partizione, mentre ReplyDateTime è la chiave di ordinamento della chiave primaria.

Reply ( Id, ReplyDateTime, ... )

Si supponga ora di aver creato una mappatura tra la classe Reply e la tabella Reply corrispondente in DynamoDB. Il seguente codice Java utilizza DynamoDBMapper per trovare tutte le risposte delle due settimane precedenti di uno specifico tema di un thread.

Esempio
String forumName = "&DDB;"; String forumSubject = "&DDB; Thread 1"; String partitionKey = forumName + "#" + forumSubject; long twoWeeksAgoMilli = (new Date()).getTime() - (14L*24L*60L*60L*1000L); Date twoWeeksAgo = new Date(); twoWeeksAgo.setTime(twoWeeksAgoMilli); SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSS'Z'"); String twoWeeksAgoStr = df.format(twoWeeksAgo); Map<String, AttributeValue> eav = new HashMap<String, AttributeValue>(); eav.put(":v1", new AttributeValue().withS(partitionKey)); eav.put(":v2",new AttributeValue().withS(twoWeeksAgoStr.toString())); DynamoDBQueryExpression<Reply> queryExpression = new DynamoDBQueryExpression<Reply>() .withKeyConditionExpression("Id = :v1 and ReplyDateTime > :v2") .withExpressionAttributeValues(eav); List<Reply> latestReplies = mapper.query(Reply.class, queryExpression);

La query restituisce una raccolta di oggetti Reply.

Per impostazione predefinita, il metodo query restituisce una raccolta a "caricamento differito". Inizialmente restituisce solo una pagina di risultati e in seguito effettua una chiamata di assistenza per la pagina successiva, se necessario. Per ottenere tutti gli elementi corrispondenti, eseguire iterazioni sulla raccolta latestReplies.

Tieni presente che la chiamata del metodo size() sulla raccolta carica tutti i risultati al fine di fornire un conteggio accurato. Di conseguenza si potrebbe verificare un consumo eccessivo di throughput assegnato e nel caso di una tabella molto grande potrebbe persino esaurirsi tutta la memoria nella JVM.

Per eseguire query a un indice, è necessario in primo luogo modellarlo come classe di mappatore. Supponiamo che la Reply tabella abbia un indice secondario globale denominato -Message-Index. PostedBy La chiave di partizione di quest'indice è PostedBy, mentre la chiave di ordinamento è Message. La definizione di classe di un item dell'indice dovrebbe avere un aspetto simile al seguente:

@DynamoDBTable(tableName="Reply") public class PostedByMessage { private String postedBy; private String message; @DynamoDBIndexHashKey(globalSecondaryIndexName = "PostedBy-Message-Index", attributeName = "PostedBy") public String getPostedBy() { return postedBy; } public void setPostedBy(String postedBy) { this.postedBy = postedBy; } @DynamoDBIndexRangeKey(globalSecondaryIndexName = "PostedBy-Message-Index", attributeName = "Message") public String getMessage() { return message; } public void setMessage(String message) { this.message = message; } // Additional properties go here. }

L'annotazione @DynamoDBTable indica che questo indice è associato alla tabella Reply. L'@DynamoDBIndexHashKeyannotazione indica la chiave di partizione (PostedBy) dell'indice e @DynamoDBIndexRangeKey indica la chiave di ordinamento (Message) dell'indice.

Puoi ora utilizzare DynamoDBMapper per eseguire query all'indice, recuperando un sottoinsieme di messaggi pubblicati da un determinato utente. Non è necessario specificare il nome dell'indice se non sono presenti mappature in conflitto tra tabelle e indici e le mappature sono già state eseguite nel mappatore. Il mappatore deciderà in base alla chiave primaria e alla chiave di ordinamento. Il codice seguente esegue una query su un indice secondario globale. Poiché gli indici secondari globali supportano letture consistenti finali, ma non letture consistenti, è necessario specificare withConsistentRead(false).

HashMap<String, AttributeValue> eav = new HashMap<String, AttributeValue>(); eav.put(":v1", new AttributeValue().withS("User A")); eav.put(":v2", new AttributeValue().withS("DynamoDB")); DynamoDBQueryExpression<PostedByMessage> queryExpression = new DynamoDBQueryExpression<PostedByMessage>() .withIndexName("PostedBy-Message-Index") .withConsistentRead(false) .withKeyConditionExpression("PostedBy = :v1 and begins_with(Message, :v2)") .withExpressionAttributeValues(eav); List<PostedByMessage> iList = mapper.query(PostedByMessage.class, queryExpression);

La query restituisce una raccolta di oggetti PostedByMessage.

queryPage

Esegue query su una tabella o un indice secondario e restituisce una singola pagina di risultati corrispondenti. Come per il metodo query, è necessario specificare il valore di una chiave di partizione e un filtro query applicato all'attributo della chiave di ordinamento. Tuttavia, queryPage restituisce solo la prima "pagina" di dati, ovvero la quantità di dati che rientra in 1 MB.

scan

Esegue la scansione di un'intera tabella o di un indice secondario. Puoi specificare facoltativamente FilterExpression per filtrare il set di risultati.

Supponiamo che tu abbia una tabella, Reply, in cui vengono memorizzate le risposte dei thread di un forum. Ogni tema del thread può contenere 0 o più risposte. La chiave primaria della tabella Reply è costituita dai campi Id e ReplyDateTime, in cui l'Id è la chiave di partizione, mentre ReplyDateTime è la chiave di ordinamento della chiave primaria.

Reply ( Id, ReplyDateTime, ... )

Se hai mappato una classe Java alla tabella Reply, puoi utilizzare la DynamoDBMapper per eseguire la scansione della tabella. Ad esempio, il seguente codice Java esegue la scansione dell'intera tabella Reply, restituendo solo le risposte di un determinato anno.

Esempio
HashMap<String, AttributeValue> eav = new HashMap<String, AttributeValue>(); eav.put(":v1", new AttributeValue().withS("2015")); DynamoDBScanExpression scanExpression = new DynamoDBScanExpression() .withFilterExpression("begins_with(ReplyDateTime,:v1)") .withExpressionAttributeValues(eav); List<Reply> replies = mapper.scan(Reply.class, scanExpression);

Per impostazione predefinita, il metodo scan restituisce una raccolta a "caricamento differito". Inizialmente restituisce solo una pagina di risultati e in seguito effettua una chiamata di assistenza per la pagina successiva, se necessario. Per ottenere tutti gli elementi corrispondenti, eseguire iterazioni sulla raccolta replies.

Tieni presente che la chiamata del metodo size() sulla raccolta carica tutti i risultati al fine di fornire un conteggio accurato. Di conseguenza si potrebbe verificare un consumo eccessivo di throughput assegnato e nel caso di una tabella molto grande potrebbe persino esaurirsi tutta la memoria nella JVM.

Per eseguire la scansione di un indice, è necessario in primo luogo modellarlo come classe di mappatore. Supponiamo che la tabella Reply abbia un indice secondario globale denominato PostedBy-Message-Index. La chiave di partizione di quest'indice è PostedBy, mentre la chiave di ordinamento è Message. Una classe di mappatore per questo indice viene mostrata nella sezione query. Utilizza le annotazioni @DynamoDBIndexHashKey e @DynamoDBIndexRangeKey per specificare la chiave di partizione e la chiave di ordinamento dell'indice.

L'esempio di codice seguente esegue la scansione di PostedBy-Message-Index. Esso non utilizza un filtro di scansione, così che ti vengano restituiti tutti gli elementi dell'indice.

DynamoDBScanExpression scanExpression = new DynamoDBScanExpression() .withIndexName("PostedBy-Message-Index") .withConsistentRead(false); List<PostedByMessage> iList = mapper.scan(PostedByMessage.class, scanExpression); Iterator<PostedByMessage> indexItems = iList.iterator();

scanPage

Esegue una scansione su una tabella o un indice secondario e restituisce una singola pagina di risultati corrispondenti. Come per il metodo scan, puoi specificare facoltativamente FilterExpression per filtrare il set di risultati. Tuttavia, scanPage restituisce solo la prima "pagina" di dati, ovvero la quantità di dati che rientra in 1 MB.

parallelScan

Esegue una scansione parallela di un'intera tabella o di un indice secondario. Puoi specificare una serie di segmenti logici della tabella e un'espressione scan per filtrare i risultati. parallelScan divide l'attività di scansione tra più dipendenti, uno per ogni segmento logico; i dipendenti elaborano i dati in parallelo e restituiscono i risultati.

L'esempio di codice Java seguente esegue una scansione parallela sulla tabella Product.

int numberOfThreads = 4; Map<String, AttributeValue> eav = new HashMap<String, AttributeValue>(); eav.put(":n", new AttributeValue().withN("100")); DynamoDBScanExpression scanExpression = new DynamoDBScanExpression() .withFilterExpression("Price <= :n") .withExpressionAttributeValues(eav); List<Product> scanResult = mapper.parallelScan(Product.class, scanExpression, numberOfThreads);

Per un esempio di codice Java che illustra l'utilizzo di parallelScan, consulta Operazioni di query e analisi per la classe DynamoDBMapper.

batchSave

Salva gli oggetti in una o più tabelle tramite una o più chiamate al metodo AmazonDynamoDB.batchWriteItem. Questo metodo non fornisce garanzie sulle transazioni.

Il codice Java seguente salva due item (libri) nella tabella ProductCatalog.

Book book1 = new Book(); book1.setId(901); book1.setProductCategory("Book"); book1.setTitle("Book 901 Title"); Book book2 = new Book(); book2.setId(902); book2.setProductCategory("Book"); book2.setTitle("Book 902 Title"); mapper.batchSave(Arrays.asList(book1, book2));

batchLoad

Recupera più item da una o più tabelle utilizzando la loro chiave primaria.

Il seguente codice Java recupera due item da due tabelle differenti.

ArrayList<Object> itemsToGet = new ArrayList<Object>(); ForumItem forumItem = new ForumItem(); forumItem.setForumName("Amazon DynamoDB"); itemsToGet.add(forumItem); ThreadItem threadItem = new ThreadItem(); threadItem.setForumName("Amazon DynamoDB"); threadItem.setSubject("Amazon DynamoDB thread 1 message text"); itemsToGet.add(threadItem); Map<String, List<Object>> items = mapper.batchLoad(itemsToGet);

batchDelete

Elimina gli oggetti da una o più tabelle tramite una o più chiamate al metodo AmazonDynamoDB.batchWriteItem. Questo metodo non fornisce garanzie sulle transazioni.

Il seguente codice Java elimina due item (libri) dalla tabella ProductCatalog.

Book book1 = mapper.load(Book.class, 901); Book book2 = mapper.load(Book.class, 902); mapper.batchDelete(Arrays.asList(book1, book2));

BatchWrite

Salva gli oggetti o li elimina da una o più tabelle tramite una o più chiamate al metodo AmazonDynamoDB.batchWriteItem. Questo metodo non fornisce garanzie sulle transazioni né supporta la funzione Versioni multiple (inserimenti o eliminazioni condizionali).

Il seguente frammento di codice Java scrive un nuovo item nella tabella Forum, scrive un nuovo item nella tabella Thread ed elimina un item dalla tabella ProductCatalog.

// Create a Forum item to save Forum forumItem = new Forum(); forumItem.setName("Test BatchWrite Forum"); // Create a Thread item to save Thread threadItem = new Thread(); threadItem.setForumName("AmazonDynamoDB"); threadItem.setSubject("My sample question"); // Load a ProductCatalog item to delete Book book3 = mapper.load(Book.class, 903); List<Object> objectsToWrite = Arrays.asList(forumItem, threadItem); List<Book> objectsToDelete = Arrays.asList(book3); mapper.batchWrite(objectsToWrite, objectsToDelete);

transactionWrite

Salva gli oggetti o li elimina da una o più tabelle tramite una o più chiamate al metodo AmazonDynamoDB.transactWriteItems.

Per un elenco delle eccezioni specifiche delle transazioni, consulta errori. TransactWriteItems

Per ulteriori informazioni sulle transazioni DynamoDB e le garanzie ACID (Atomicity, Consistency, Isolation and Durability) fornite, consulta Amazon DynamoDB Transactions.

Nota

Questo metodo non supporta i seguenti metodi:

Il seguente codice Java scrive un nuovo item in ogni tabella Forum e Thread, a livello di transazione.

Thread s3ForumThread = new Thread(); s3ForumThread.setForumName("S3 Forum"); s3ForumThread.setSubject("Sample Subject 1"); s3ForumThread.setMessage("Sample Question 1"); Forum s3Forum = new Forum(); s3Forum.setName("S3 Forum"); s3Forum.setCategory("Amazon Web Services"); s3Forum.setThreads(1); TransactionWriteRequest transactionWriteRequest = new TransactionWriteRequest(); transactionWriteRequest.addPut(s3Forum); transactionWriteRequest.addPut(s3ForumThread); mapper.transactionWrite(transactionWriteRequest);

transactionLoad

Carica gli oggetti da una o più tabelle tramite una chiamata al metodo AmazonDynamoDB.transactGetItems.

Per un elenco delle eccezioni specifiche delle transazioni, consulta errori. TransactGetItems

Per ulteriori informazioni sulle transazioni DynamoDB e le garanzie ACID (Atomicity, Consistency, Isolation and Durability) fornite, consulta Amazon DynamoDB Transactions.

Il seguente codice Java carica un elemento da ciascuna delle tabelle Forum e Thread, a livello di transazione.

Forum dynamodbForum = new Forum(); dynamodbForum.setName("DynamoDB Forum"); Thread dynamodbForumThread = new Thread(); dynamodbForumThread.setForumName("DynamoDB Forum"); TransactionLoadRequest transactionLoadRequest = new TransactionLoadRequest(); transactionLoadRequest.addLoad(dynamodbForum); transactionLoadRequest.addLoad(dynamodbForumThread); mapper.transactionLoad(transactionLoadRequest);

count

Valuta l'espressione scan specificata e restituisce il numero di item corrispondenti. Non viene restituito alcun dato di item.

generateCreateTableRichiesta

Analizza una classe POJO che rappresenta una tabella DynamoDB e restituisce un CreateTableRequest per tale tabella.

Crea un collegamento a un oggetto in Amazon S3. È necessario specificare un nome del bucket e un nome della chiave, il quale identifica l'oggetto nel bucket in modo univoco.

Per utilizzare createS3Link, la classe di mappatore deve definire metodi getter e setter. Ciò viene illustrato nel seguente codice, nel quale si aggiunge alla classe CatalogItem un nuovo attributo e metodi getter/setter:

@DynamoDBTable(tableName="ProductCatalog") public class CatalogItem { ... public S3Link productImage; .... @DynamoDBAttribute(attributeName = "ProductImage") public S3Link getProductImage() { return productImage; } public void setProductImage(S3Link productImage) { this.productImage = productImage; } ... }

Il seguente frammento di codice Java definisce un nuovo item da scrivere nella tabella Product. Questo elemento include un collegamento all'immagine del prodotto; i dati relativi all'immagine vengono caricati in Amazon S3.

CatalogItem item = new CatalogItem(); item.setId(150); item.setTitle("Book 150 Title"); String myS3Bucket = "myS3bucket"; String myS3Key = "productImages/book_150_cover.jpg"; item.setProductImage(mapper.createS3Link(myS3Bucket, myS3Key)); item.getProductImage().uploadFrom(new File("/file/path/book_150_cover.jpg")); mapper.save(item);

La classe S3Link fornisce molti altri metodi per manipolare gli oggetti in Amazon S3. Per ulteriori informazioni, vedi la sezione relativa a Javadocs per S3Link.

GetS3 ClientCache

Restituisce S3ClientCache sottostante per accedere ad Amazon S3. Una S3ClientCache è una mappa intelligente per gli oggetti AmazonS3Client. Se hai più clienti, An S3ClientCache può aiutarti a mantenere i clienti organizzati per AWS regione e può creare nuovi client Amazon S3 su richiesta.