ownerAccountID

This commit is contained in:
Chris Lu
2026-01-28 13:54:49 -08:00
parent 1fdd9c3372
commit 1697ec862f
7 changed files with 57 additions and 58 deletions

View File

@@ -76,9 +76,9 @@ func (h *S3TablesHandler) handleCreateTableBucket(w http.ResponseWriter, r *http
// Create the bucket directory and set metadata as extended attributes // Create the bucket directory and set metadata as extended attributes
now := time.Now() now := time.Now()
metadata := &tableBucketMetadata{ metadata := &tableBucketMetadata{
Name: req.Name, Name: req.Name,
CreatedAt: now, CreatedAt: now,
OwnerID: h.getAccountID(r), OwnerAccountID: h.getAccountID(r),
} }
metadataBytes, err := json.Marshal(metadata) metadataBytes, err := json.Marshal(metadata)

View File

@@ -57,7 +57,7 @@ func (h *S3TablesHandler) handleGetTableBucket(w http.ResponseWriter, r *http.Re
// Check permission // Check permission
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanGetTableBucket(principal, metadata.OwnerID) { if !CanGetTableBucket(principal, metadata.OwnerAccountID) {
h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to get table bucket details") h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to get table bucket details")
return NewAuthError("GetTableBucket", principal, "not authorized to get table bucket details") return NewAuthError("GetTableBucket", principal, "not authorized to get table bucket details")
} }
@@ -65,7 +65,7 @@ func (h *S3TablesHandler) handleGetTableBucket(w http.ResponseWriter, r *http.Re
resp := &GetTableBucketResponse{ resp := &GetTableBucketResponse{
ARN: h.generateTableBucketARN(r, bucketName), ARN: h.generateTableBucketARN(r, bucketName),
Name: metadata.Name, Name: metadata.Name,
OwnerAccountID: metadata.OwnerID, OwnerAccountID: metadata.OwnerAccountID,
CreatedAt: metadata.CreatedAt, CreatedAt: metadata.CreatedAt,
} }
@@ -245,7 +245,7 @@ func (h *S3TablesHandler) handleDeleteTableBucket(w http.ResponseWriter, r *http
// Check permission // Check permission
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanDeleteTableBucket(principal, metadata.OwnerID) { if !CanDeleteTableBucket(principal, metadata.OwnerAccountID) {
h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to delete table bucket") h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to delete table bucket")
return NewAuthError("DeleteTableBucket", principal, "not authorized to delete table bucket") return NewAuthError("DeleteTableBucket", principal, "not authorized to delete table bucket")
} }

View File

@@ -67,7 +67,7 @@ func (h *S3TablesHandler) handleCreateNamespace(w http.ResponseWriter, r *http.R
// Check permission // Check permission
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanCreateNamespace(principal, bucketMetadata.OwnerID) { if !CanCreateNamespace(principal, bucketMetadata.OwnerAccountID) {
h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to create namespace") h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to create namespace")
return NewAuthError("CreateNamespace", principal, "not authorized to create namespace") return NewAuthError("CreateNamespace", principal, "not authorized to create namespace")
} }
@@ -91,9 +91,9 @@ func (h *S3TablesHandler) handleCreateNamespace(w http.ResponseWriter, r *http.R
// Create the namespace // Create the namespace
now := time.Now() now := time.Now()
metadata := &namespaceMetadata{ metadata := &namespaceMetadata{
Namespace: req.Namespace, Namespace: req.Namespace,
CreatedAt: now, CreatedAt: now,
OwnerID: h.getAccountID(r), OwnerAccountID: h.getAccountID(r),
} }
metadataBytes, err := json.Marshal(metadata) metadataBytes, err := json.Marshal(metadata)
@@ -178,7 +178,7 @@ func (h *S3TablesHandler) handleGetNamespace(w http.ResponseWriter, r *http.Requ
// Check permission // Check permission
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanGetNamespace(principal, metadata.OwnerID) { if !CanGetNamespace(principal, metadata.OwnerAccountID) {
h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to get namespace details") h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to get namespace details")
return NewAuthError("GetNamespace", principal, "not authorized to get namespace details") return NewAuthError("GetNamespace", principal, "not authorized to get namespace details")
} }
@@ -186,7 +186,7 @@ func (h *S3TablesHandler) handleGetNamespace(w http.ResponseWriter, r *http.Requ
resp := &GetNamespaceResponse{ resp := &GetNamespaceResponse{
Namespace: metadata.Namespace, Namespace: metadata.Namespace,
CreatedAt: metadata.CreatedAt, CreatedAt: metadata.CreatedAt,
OwnerAccountID: metadata.OwnerID, OwnerAccountID: metadata.OwnerAccountID,
} }
h.writeJSON(w, http.StatusOK, resp) h.writeJSON(w, http.StatusOK, resp)
@@ -242,7 +242,7 @@ func (h *S3TablesHandler) handleListNamespaces(w http.ResponseWriter, r *http.Re
} }
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanListNamespaces(principal, bucketMetadata.OwnerID) { if !CanListNamespaces(principal, bucketMetadata.OwnerAccountID) {
h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to list namespaces") h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to list namespaces")
return NewAuthError("ListNamespaces", principal, "not authorized to list namespaces") return NewAuthError("ListNamespaces", principal, "not authorized to list namespaces")
} }
@@ -400,7 +400,7 @@ func (h *S3TablesHandler) handleDeleteNamespace(w http.ResponseWriter, r *http.R
// Check permission // Check permission
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanDeleteNamespace(principal, metadata.OwnerID) { if !CanDeleteNamespace(principal, metadata.OwnerAccountID) {
h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to delete namespace") h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to delete namespace")
return NewAuthError("DeleteNamespace", principal, "not authorized to delete namespace") return NewAuthError("DeleteNamespace", principal, "not authorized to delete namespace")
} }

View File

@@ -59,7 +59,7 @@ func (h *S3TablesHandler) handlePutTableBucketPolicy(w http.ResponseWriter, r *h
// Check permission // Check permission
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanPutTableBucketPolicy(principal, bucketMetadata.OwnerID) { if !CanPutTableBucketPolicy(principal, bucketMetadata.OwnerAccountID) {
h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to put table bucket policy") h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to put table bucket policy")
return NewAuthError("PutTableBucketPolicy", principal, "not authorized to put table bucket policy") return NewAuthError("PutTableBucketPolicy", principal, "not authorized to put table bucket policy")
} }
@@ -132,7 +132,7 @@ func (h *S3TablesHandler) handleGetTableBucketPolicy(w http.ResponseWriter, r *h
// Check permission // Check permission
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanGetTableBucketPolicy(principal, bucketMetadata.OwnerID) { if !CanGetTableBucketPolicy(principal, bucketMetadata.OwnerAccountID) {
h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to get table bucket policy") h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to get table bucket policy")
return NewAuthError("GetTableBucketPolicy", principal, "not authorized to get table bucket policy") return NewAuthError("GetTableBucketPolicy", principal, "not authorized to get table bucket policy")
} }
@@ -190,7 +190,7 @@ func (h *S3TablesHandler) handleDeleteTableBucketPolicy(w http.ResponseWriter, r
// Check permission // Check permission
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanDeleteTableBucketPolicy(principal, bucketMetadata.OwnerID) { if !CanDeleteTableBucketPolicy(principal, bucketMetadata.OwnerAccountID) {
h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to delete table bucket policy") h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to delete table bucket policy")
return NewAuthError("DeleteTableBucketPolicy", principal, "not authorized to delete table bucket policy") return NewAuthError("DeleteTableBucketPolicy", principal, "not authorized to delete table bucket policy")
} }
@@ -270,7 +270,7 @@ func (h *S3TablesHandler) handlePutTablePolicy(w http.ResponseWriter, r *http.Re
// Check permission // Check permission
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanPutTablePolicy(principal, metadata.OwnerID) { if !CanPutTablePolicy(principal, metadata.OwnerAccountID) {
h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to put table policy") h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to put table policy")
return NewAuthError("PutTablePolicy", principal, "not authorized to put table policy") return NewAuthError("PutTablePolicy", principal, "not authorized to put table policy")
} }
@@ -354,7 +354,7 @@ func (h *S3TablesHandler) handleGetTablePolicy(w http.ResponseWriter, r *http.Re
// Check permission // Check permission
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanGetTablePolicy(principal, metadata.OwnerID) { if !CanGetTablePolicy(principal, metadata.OwnerAccountID) {
h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to get table policy") h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to get table policy")
return NewAuthError("GetTablePolicy", principal, "not authorized to get table policy") return NewAuthError("GetTablePolicy", principal, "not authorized to get table policy")
} }
@@ -423,7 +423,7 @@ func (h *S3TablesHandler) handleDeleteTablePolicy(w http.ResponseWriter, r *http
// Check permission // Check permission
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanDeleteTablePolicy(principal, metadata.OwnerID) { if !CanDeleteTablePolicy(principal, metadata.OwnerAccountID) {
h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to delete table policy") h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to delete table policy")
return NewAuthError("DeleteTablePolicy", principal, "not authorized to delete table policy") return NewAuthError("DeleteTablePolicy", principal, "not authorized to delete table policy")
} }
@@ -475,24 +475,24 @@ func (h *S3TablesHandler) handleTagResource(w http.ResponseWriter, r *http.Reque
return err return err
} }
var ownerID string var ownerAccountID string
if rType == ResourceTypeTable { if rType == ResourceTypeTable {
var meta tableMetadataInternal var meta tableMetadataInternal
if err := json.Unmarshal(data, &meta); err != nil { if err := json.Unmarshal(data, &meta); err != nil {
return err return err
} }
ownerID = meta.OwnerID ownerAccountID = meta.OwnerAccountID
} else { } else {
var meta tableBucketMetadata var meta tableBucketMetadata
if err := json.Unmarshal(data, &meta); err != nil { if err := json.Unmarshal(data, &meta); err != nil {
return err return err
} }
ownerID = meta.OwnerID ownerAccountID = meta.OwnerAccountID
} }
// Check Permission inside the closure because we just got the ID // Check Permission inside the closure because we just got the ID
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanManageTags(principal, ownerID) { if !CanManageTags(principal, ownerAccountID) {
return NewAuthError("TagResource", principal, "not authorized to tag resource") return NewAuthError("TagResource", principal, "not authorized to tag resource")
} }
@@ -574,24 +574,24 @@ func (h *S3TablesHandler) handleListTagsForResource(w http.ResponseWriter, r *ht
return err return err
} }
var ownerID string var ownerAccountID string
if rType == ResourceTypeTable { if rType == ResourceTypeTable {
var meta tableMetadataInternal var meta tableMetadataInternal
if err := json.Unmarshal(data, &meta); err != nil { if err := json.Unmarshal(data, &meta); err != nil {
return err return err
} }
ownerID = meta.OwnerID ownerAccountID = meta.OwnerAccountID
} else { } else {
var meta tableBucketMetadata var meta tableBucketMetadata
if err := json.Unmarshal(data, &meta); err != nil { if err := json.Unmarshal(data, &meta); err != nil {
return err return err
} }
ownerID = meta.OwnerID ownerAccountID = meta.OwnerAccountID
} }
// Check Permission // Check Permission
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CheckPermission("ListTagsForResource", principal, ownerID) { if !CheckPermission("ListTagsForResource", principal, ownerAccountID) {
return NewAuthError("ListTagsForResource", principal, "not authorized to list tags for resource") return NewAuthError("ListTagsForResource", principal, "not authorized to list tags for resource")
} }
@@ -661,24 +661,24 @@ func (h *S3TablesHandler) handleUntagResource(w http.ResponseWriter, r *http.Req
return err return err
} }
var ownerID string var ownerAccountID string
if rType == ResourceTypeTable { if rType == ResourceTypeTable {
var meta tableMetadataInternal var meta tableMetadataInternal
if err := json.Unmarshal(data, &meta); err != nil { if err := json.Unmarshal(data, &meta); err != nil {
return err return err
} }
ownerID = meta.OwnerID ownerAccountID = meta.OwnerAccountID
} else { } else {
var meta tableBucketMetadata var meta tableBucketMetadata
if err := json.Unmarshal(data, &meta); err != nil { if err := json.Unmarshal(data, &meta); err != nil {
return err return err
} }
ownerID = meta.OwnerID ownerAccountID = meta.OwnerAccountID
} }
// Check Permission // Check Permission
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanManageTags(principal, ownerID) { if !CanManageTags(principal, ownerAccountID) {
return NewAuthError("UntagResource", principal, "not authorized to untag resource") return NewAuthError("UntagResource", principal, "not authorized to untag resource")
} }

View File

@@ -87,7 +87,7 @@ func (h *S3TablesHandler) handleCreateTable(w http.ResponseWriter, r *http.Reque
// Check permission // Check permission
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanCreateTable(principal, namespaceMetadata.OwnerID) { if !CanCreateTable(principal, namespaceMetadata.OwnerAccountID) {
h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to create table") h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to create table")
return NewAuthError("CreateTable", principal, "not authorized to create table") return NewAuthError("CreateTable", principal, "not authorized to create table")
} }
@@ -113,14 +113,14 @@ func (h *S3TablesHandler) handleCreateTable(w http.ResponseWriter, r *http.Reque
versionToken := generateVersionToken() versionToken := generateVersionToken()
metadata := &tableMetadataInternal{ metadata := &tableMetadataInternal{
Name: tableName, Name: tableName,
Namespace: namespaceName, Namespace: namespaceName,
Format: req.Format, Format: req.Format,
CreatedAt: now, CreatedAt: now,
ModifiedAt: now, ModifiedAt: now,
OwnerID: h.getAccountID(r), OwnerAccountID: h.getAccountID(r),
VersionToken: versionToken, VersionToken: versionToken,
Schema: req.Metadata, Schema: req.Metadata,
} }
metadataBytes, err := json.Marshal(metadata) metadataBytes, err := json.Marshal(metadata)
@@ -241,7 +241,7 @@ func (h *S3TablesHandler) handleGetTable(w http.ResponseWriter, r *http.Request,
// Check permission // Check permission
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanGetTable(principal, metadata.OwnerID) { if !CanGetTable(principal, metadata.OwnerAccountID) {
h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to get table") h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to get table")
return NewAuthError("GetTable", principal, "not authorized to get table") return NewAuthError("GetTable", principal, "not authorized to get table")
} }
@@ -255,7 +255,7 @@ func (h *S3TablesHandler) handleGetTable(w http.ResponseWriter, r *http.Request,
Format: metadata.Format, Format: metadata.Format,
CreatedAt: metadata.CreatedAt, CreatedAt: metadata.CreatedAt,
ModifiedAt: metadata.ModifiedAt, ModifiedAt: metadata.ModifiedAt,
OwnerAccountID: metadata.OwnerID, OwnerAccountID: metadata.OwnerAccountID,
MetadataLocation: metadata.MetadataLocation, MetadataLocation: metadata.MetadataLocation,
VersionToken: metadata.VersionToken, VersionToken: metadata.VersionToken,
} }
@@ -311,7 +311,7 @@ func (h *S3TablesHandler) handleListTables(w http.ResponseWriter, r *http.Reques
return err return err
} }
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanListTables(principal, nsMeta.OwnerID) { if !CanListTables(principal, nsMeta.OwnerAccountID) {
return NewAuthError("ListTables", principal, "not authorized to list tables") return NewAuthError("ListTables", principal, "not authorized to list tables")
} }
@@ -328,7 +328,7 @@ func (h *S3TablesHandler) handleListTables(w http.ResponseWriter, r *http.Reques
return err return err
} }
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanListTables(principal, bucketMeta.OwnerID) { if !CanListTables(principal, bucketMeta.OwnerAccountID) {
return NewAuthError("ListTables", principal, "not authorized to list tables") return NewAuthError("ListTables", principal, "not authorized to list tables")
} }
@@ -603,7 +603,7 @@ func (h *S3TablesHandler) handleDeleteTable(w http.ResponseWriter, r *http.Reque
// Check permission // Check permission
principal := h.getPrincipalFromRequest(r) principal := h.getPrincipalFromRequest(r)
if !CanDeleteTable(principal, metadata.OwnerID) { if !CanDeleteTable(principal, metadata.OwnerAccountID) {
h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to delete table") h.writeError(w, http.StatusForbidden, ErrCodeAccessDenied, "not authorized to delete table")
return NewAuthError("DeleteTable", principal, "not authorized to delete table") return NewAuthError("DeleteTable", principal, "not authorized to delete table")
} }

View File

@@ -5,10 +5,10 @@ import "time"
// Table bucket types // Table bucket types
type TableBucket struct { type TableBucket struct {
ARN string `json:"arn"` ARN string `json:"arn"`
Name string `json:"name"` Name string `json:"name"`
OwnerID string `json:"ownerAccountId"` OwnerAccountID string `json:"ownerAccountId"`
CreatedAt time.Time `json:"createdAt"` CreatedAt time.Time `json:"createdAt"`
} }
type CreateTableBucketRequest struct { type CreateTableBucketRequest struct {

View File

@@ -71,18 +71,17 @@ func getTablePath(bucketName, namespace, tableName string) string {
// Metadata structures // Metadata structures
// tableBucketMetadata stores metadata for a table bucket
type tableBucketMetadata struct { type tableBucketMetadata struct {
Name string `json:"name"` Name string `json:"name"`
CreatedAt time.Time `json:"createdAt"` CreatedAt time.Time `json:"createdAt"`
OwnerID string `json:"ownerAccountId"` OwnerAccountID string `json:"ownerAccountId"`
} }
// namespaceMetadata stores metadata for a namespace // namespaceMetadata stores metadata for a namespace
type namespaceMetadata struct { type namespaceMetadata struct {
Namespace []string `json:"namespace"` Namespace []string `json:"namespace"`
CreatedAt time.Time `json:"createdAt"` CreatedAt time.Time `json:"createdAt"`
OwnerID string `json:"ownerAccountId"` OwnerAccountID string `json:"ownerAccountId"`
} }
// tableMetadataInternal stores metadata for a table // tableMetadataInternal stores metadata for a table
@@ -92,7 +91,7 @@ type tableMetadataInternal struct {
Format string `json:"format"` Format string `json:"format"`
CreatedAt time.Time `json:"createdAt"` CreatedAt time.Time `json:"createdAt"`
ModifiedAt time.Time `json:"modifiedAt"` ModifiedAt time.Time `json:"modifiedAt"`
OwnerID string `json:"ownerAccountId"` OwnerAccountID string `json:"ownerAccountId"`
VersionToken string `json:"versionToken"` VersionToken string `json:"versionToken"`
MetadataLocation string `json:"metadataLocation,omitempty"` MetadataLocation string `json:"metadataLocation,omitempty"`
Schema *TableMetadata `json:"metadata,omitempty"` Schema *TableMetadata `json:"metadata,omitempty"`