Go'da DynamoDB PutItem (AWS SDK v2)
PutItem bir öğenin tamamını yazar ve aynı birincil anahtara sahip mevcut her öğeyi değiştirir (öğe tabanlı eylemler bunun UpdateItem'dan nasıl farklı olduğunu ele alır). AWS SDK for Go v2'de ilginç kısım çağrının kendisi değil, Go değerlerinizin dışarı çıkarken neye dönüştüğüdür.
Kod
package main
import (
"context"
"errors"
"fmt"
"log"
"github.com/aws/aws-sdk-go-v2/aws"
"github.com/aws/aws-sdk-go-v2/config"
"github.com/aws/aws-sdk-go-v2/service/dynamodb"
"github.com/aws/aws-sdk-go-v2/service/dynamodb/types"
)
func main() {
ctx := context.TODO()
cfg, err := config.LoadDefaultConfig(ctx, config.WithRegion("us-east-1"))
if err != nil {
log.Fatalf("load config: %v", err)
}
client := dynamodb.NewFromConfig(cfg)
_, err = client.PutItem(ctx, &dynamodb.PutItemInput{
TableName: aws.String("Music"),
Item: map[string]types.AttributeValue{
"Artist": &types.AttributeValueMemberS{Value: "Arturo Sandoval"},
"SongTitle": &types.AttributeValueMemberS{Value: "Cubano Chant"},
"AlbumTitle": &types.AttributeValueMemberS{Value: "Danzon"},
"Year": &types.AttributeValueMemberN{Value: "1994"},
"Awards": &types.AttributeValueMemberN{Value: "0"},
},
ConditionExpression: aws.String("attribute_not_exists(#cond0) AND attribute_not_exists(#cond1)"),
ExpressionAttributeNames: map[string]string{
"#cond0": "Artist",
"#cond1": "SongTitle",
},
})
if err != nil {
var ccf *types.ConditionalCheckFailedException
if errors.As(err, &ccf) {
fmt.Println("A song with that key already exists — not overwritten")
return
}
log.Fatalf("put item: %v", err)
}
fmt.Println("Song written")
}Açıklama
attributevalue.MarshalMap kısayoldur ve fikirleri vardır. Yukarıdaki map[string]types.AttributeValue'yu elle kurmak yerine bir struct'ı github.com/aws/aws-sdk-go-v2/feature/dynamodb/attributevalue'ye vermek olağan hamledir. Bir time.Time, dokunulmamış bir string alanı ve nil bir *int içeren bir struct için gerçekte ürettiği şu:
Artist => &types.AttributeValueMemberS{Value:"Arturo Sandoval"}
SongTitle => &types.AttributeValueMemberS{Value:"Cubano Chant"}
Released => &types.AttributeValueMemberS{Value:"1994-01-01T00:00:00Z"}
Notes => &types.AttributeValueMemberS{Value:""}
Rating => &types.AttributeValueMemberNULL{Value:true}Bundan çıkarılacak üç şey var. time.Time bir Unix sayısına değil, RFC 3339 biçiminde bir dizeye dönüşür; dolayısıyla bir zaman damgası sıralama anahtarı sözlüksel olarak sıralanır ve ancak her değer sıfırla doldurulmuşsa ve aynı saat diliminde ise beklendiği gibi davranır. Dokunulmamış bir dize, dışarıda bırakılmak yerine gerçek bir boş dize özniteliğine dönüşür. Ve nil bir işaretçi NULL'a dönüşür — ki bu var olan bir özniteliktir.
Bir NULL özniteliği attribute_not_exists'i etkisiz kılar. İnsana bir öğleden sonrasına mal olan da budur. Rating'i nil bir *int'ten gelen bir öğe yazın, sonra bir sonraki yazmayı attribute_not_exists(Rating) ile koruyun; başarısız olur:
ConditionalCheckFailedException: The conditional request failedDynamoDB haklıdır: öznitelik oradadır, NULL tutmaktadır. Çözüm, alanı null yapmak yerine düşüren dynamodbav:"Rating,omitempty" struct etiketidir. Aynı etiket boş dize özniteliğini de engeller — ki bu önemlidir, çünkü onlar seyrek indeksleri bozar ve bir anahtar özniteliğinde doğrudan reddedilir:
ValidationException: One or more parameter values are not valid. The AttributeValue for a key attribute cannot contain an empty string value. Key: Artisterrors.As, asla dize eşleştirme. Go SDK'sı her hizmet hatasını smithy'nin işlem hatasına sarar; dolayısıyla err.Error()'dan aldığınız dize DynamoDB'nin gönderdiği mesaj değildir:
operation error DynamoDB: PutItem, https response error StatusCode: 400, RequestID: 6886fce0-b246-4762-8a8b-0c6dab813040, ConditionalCheckFailedException: The conditional request failederrors.As(err, &ccf) onu açar ve yukarıda true döndürdü; ccf.ErrorMessage() sonra çıplak The conditional request failed mesajını verir. Dış dize üzerinde bir strings.Contains denetimi bugün çalışır ve SDK sarmalayıcı biçimini değiştirdiği gün bozulur.
Tipli hata sizi engelleyen öğeyi taşıyabilir. Girdide ReturnValuesOnConditionCheckFailure: types.ReturnValuesOnConditionCheckFailureAllOld ayarlayın; ccf.Item dolu olarak geri gelir: yukarıdaki çalıştırmada beş öznitelik, Year dahil, &types.AttributeValueMemberN{Value:"1994"} olarak. Bu, çoğu yeniden deneme döngüsünün elle yaptığı başarısızlık-sonrası-okuma gidiş-dönüşünü ortadan kaldırır. ReturnValues: types.ReturnValueAllOld bunun başarı yolundaki karşılığıdır (ReturnValues).
Sayılar dizedir ve bu bir Go tuhaflığı değildir. AttributeValueMemberN{Value: "1994"} tipli bir dilden gelen herkese yanlış görünür, ama DynamoDB'nin N türü tam da hiçbir şeyin bir float64 üzerinden gidip gelmek zorunda kalmaması için metin olarak taşınan bir ondalıktır. Dönüşüm strconv.FormatInt ve strconv.FormatFloat'tır; attributevalue bunu sizin yerinize yapar.
Ne marshal ederseniz onun bedelini ödersiniz. ~15 KB'lık bir öğenin put'u, ReturnConsumedCapacity ile "CapacityUnits": 15 bildirdi. Yazmalar 1 KB başına yukarı yuvarlanır; dolayısıyla kazara eklenmiş bir blob alanı ya da düşürmek istediğiniz öznitelikleri yayan bir MarshalMap doğrudan faturada görünür.
Görsel olarak yapın
Öğeye gerçekte neyin ineceğine MarshalMap karar verdiğine göre, o öğenin ne kadar ağır olduğunu bilmeye değer. Ücretsiz DynamoDB öğe boyutu hesaplayıcısı, marshal edilmiş JSON'u alır ve bayt boyutunu ve yukarı yuvarlandığı yazma birimlerini döndürür.
Kendi tablolarınıza karşı öğe yazmak ve düzenlemek için — öznitelik başına bir form, tür seçiciler, sonucu Go olarak geri kopyalama — DynoTable'ı indirin.
İlgili örnekler
- Java'da DynamoDB PutItem — AWS SDK for Java 2.x ile aynı koşullu yazma, ki orada ayarlanmamış bir değer tam ters yönde başarısız olur.
- Go'da DynamoDB UpdateItem — öğeyi değiştirmek yerine belirli öznitelikleri değiştirin.
- DynamoDB koşul ifadeleri —
attribute_not_exists, iyimser kilitleme ve dahası. - DynamoDB ConditionalCheckFailedException — öğe zaten varken yalnızca-oluştur koşulunun fırlattığı şey.
- DynamoDB ValidationException — hatalı biçimlendirilmiş bir öğe ya da ifade için genel karşılayıcı.
Kaynaklar
- PutItem — Amazon DynamoDB API Reference
- Use PutItem with an AWS SDK or CLI — Amazon DynamoDB Developer Guide
- dynamodb package — AWS SDK for Go v2 (pkg.go.dev)
- attributevalue package — AWS SDK for Go v2 (pkg.go.dev)
- Handling errors — AWS SDK for Go v2 Developer Guide
- Condition expressions — Amazon DynamoDB Developer Guide
2026-07-28 tarihinde go1.26.5 üzerinde aws-sdk-go-v2/service/dynamodb v1.62.1 ve feature/dynamodb/attributevalue v1.20.55 ile, 9000 numaralı bağlantı noktasındaki DynamoDB Local'e (amazon/dynamodb-local) karşı yeniden üretildi. Marshal edilmiş değerler, hata dizeleri ve kapasite okuması yakalanmış çıktıdır, birebir kopyalanmıştır.