100 lines
2.7 KiB
Go
100 lines
2.7 KiB
Go
package dynamo
|
|
|
|
import (
|
|
"context"
|
|
|
|
"github.com/aws/aws-sdk-go-v2/aws"
|
|
"github.com/aws/aws-sdk-go-v2/service/dynamodb"
|
|
"github.com/aws/aws-sdk-go-v2/service/dynamodb/types"
|
|
"github.com/lmika/awstools/internal/dynamo-browse/models"
|
|
"github.com/pkg/errors"
|
|
)
|
|
|
|
type Provider struct {
|
|
client *dynamodb.Client
|
|
}
|
|
|
|
func (p *Provider) ListTables(ctx context.Context) ([]string, error) {
|
|
out, err := p.client.ListTables(ctx, &dynamodb.ListTablesInput{})
|
|
if err != nil {
|
|
return nil, errors.Wrapf(err, "cannot list tables")
|
|
}
|
|
|
|
return out.TableNames, nil
|
|
}
|
|
|
|
func (p *Provider) DescribeTable(ctx context.Context, tableName string) (*models.TableInfo, error) {
|
|
out, err := p.client.DescribeTable(ctx, &dynamodb.DescribeTableInput{
|
|
TableName: aws.String(tableName),
|
|
})
|
|
if err != nil {
|
|
return nil, errors.Wrapf(err, "cannot describe table %v", tableName)
|
|
}
|
|
|
|
var tableInfo models.TableInfo
|
|
tableInfo.Name = aws.ToString(out.Table.TableName)
|
|
|
|
for _, keySchema := range out.Table.KeySchema {
|
|
if keySchema.KeyType == types.KeyTypeHash {
|
|
tableInfo.Keys.PartitionKey = aws.ToString(keySchema.AttributeName)
|
|
} else if keySchema.KeyType == types.KeyTypeRange {
|
|
tableInfo.Keys.SortKey = aws.ToString(keySchema.AttributeName)
|
|
}
|
|
}
|
|
|
|
for _, definedAttribute := range out.Table.AttributeDefinitions {
|
|
tableInfo.DefinedAttributes = append(tableInfo.DefinedAttributes, aws.ToString(definedAttribute.AttributeName))
|
|
}
|
|
|
|
return &tableInfo, nil
|
|
}
|
|
|
|
func (p *Provider) PutItem(ctx context.Context, name string, item models.Item) error {
|
|
_, err := p.client.PutItem(ctx, &dynamodb.PutItemInput{
|
|
TableName: aws.String(name),
|
|
Item: item,
|
|
})
|
|
if err != nil {
|
|
return errors.Wrapf(err, "cannot execute put on table %v", name)
|
|
}
|
|
return nil
|
|
}
|
|
|
|
func NewProvider(client *dynamodb.Client) *Provider {
|
|
return &Provider{client: client}
|
|
}
|
|
|
|
func (p *Provider) ScanItems(ctx context.Context, tableName string, maxItems int) ([]models.Item, error) {
|
|
paginator := dynamodb.NewScanPaginator(p.client, &dynamodb.ScanInput{
|
|
TableName: aws.String(tableName),
|
|
Limit: aws.Int32(int32(maxItems)),
|
|
})
|
|
|
|
items := make([]models.Item, 0)
|
|
|
|
outer:
|
|
for paginator.HasMorePages() {
|
|
res, err := paginator.NextPage(ctx)
|
|
if err != nil {
|
|
return nil, errors.Wrapf(err, "cannot execute scan on table %v", tableName)
|
|
}
|
|
|
|
for _, itm := range res.Items {
|
|
items = append(items, itm)
|
|
if len(items) >= maxItems {
|
|
break outer
|
|
}
|
|
}
|
|
}
|
|
|
|
return items, nil
|
|
}
|
|
|
|
func (p *Provider) DeleteItem(ctx context.Context, tableName string, key map[string]types.AttributeValue) error {
|
|
_, err := p.client.DeleteItem(ctx, &dynamodb.DeleteItemInput{
|
|
TableName: aws.String(tableName),
|
|
Key: key,
|
|
})
|
|
return errors.Wrap(err, "could not delete item")
|
|
}
|