Utilizzo di Python
Il supporto Python viene fornito tramite un duplicato della libreria boto3 con funzioni che utilizzano in modo ottimale IBM Cloud® Object Storage.
Può essere installato dal Python Package Index tramite pip install ibm-cos-sdk.
Il codice sorgente è disponibile all'indirizzo GitHub.
La libreria ibm_boto3 fornisce l'accesso completo all'API IBM Cloud® Object Storage. Devono essere specificati gli endpoint, una chiave API e l'ID istanza durante la creazione di una risorsa del servizio o del client di basso livello
come mostrato nei seguenti esempi di base.
L'ID dell'istanza di servizio viene anche chiamato ID dell'istanza di risorsa. Il valore può essere trovato creando una credenziale di servizio o tramite la CLI.
La documentazione dettagliata è disponibile qui.
Creazione di un client e derivazione delle credenziali
Per stabilire una connessione a COS, un client viene creato e configurato utilizzando le informazioni delle credenziali (chiave API e ID istanza del servizio). Questi valori possono anche essere derivati automaticamente da un file di credenziali o dalle variabili di ambiente.
Dopo aver generato una credenziale del servizio, il documento JSON risultante può essere salvato in ~/.bluemix/cos_credentials. L'SDK deriverà
automaticamente le credenziali da questo file a meno che non vengano esplicitamente impostate altre credenziali durante la creazione del client. Se il file cos_credentials contiene chiavi HMAC che il client autentica con una firma,
altrimenti il client utilizza la chiave API fornita per eseguire l'autenticazione utilizzando un token di connessione (l'uso di una chiave API richiede ancora che config=Config(signature_version="oauth") sia incluso
durante la creazione del client).
Se si esegue la migrazione da AWS S3, puoi anche derivare i dati delle credenziali da ~/.aws/credentials nel formato:
[default]
aws_access_key_id = {API_KEY}
aws_secret_access_key = {SERVICE_INSTANCE_ID}
Nota: Se esistono sia ~/.bluemix/cos_credentials che ~/.aws/credentials, cos_credentials ha la precedenza.
Raccogli le informazioni richieste
Le seguenti variabili vengono visualizzate negli esempi:
bucket_namedeve essere una stringa univoca e indipendente da DNS. Poiché i nomi dei bucket sono univoci nell'intero sistema, questi valori devono essere modificati se questo esempio viene eseguito più volte. Tieni presente che i nomi sono riservati per 10 - 15 minuti dopo l'eliminazione.ibm_api_key_idè il valore trovato nella credenziale del servizio comeapikey.ibm_service_instance_idè il valore trovato nella credenziale del servizio comeresource_instance_id.endpoint_urlè un URL di endpoint del servizio, inclusivo del protocollohttps://. Questo valore non è il valoreendpointsdisponibile nella credenziale del servizio. Per ulteriori informazioni sugli endpoint, vedi Endpoint e ubicazioni di archiviazione.LocationConstraintè un codice di provisioning valido che corrisponde al valoreendpoint.
Esempi di codici
Gli esempi di codice vengono verificati sulle versioni di release supportate di Python.
Nel codice, è necessario rimuovere le parentesi angolari o qualsiasi altro carattere in eccesso fornito qui come illustrazione.
Inizializzazione della configurazione
Questo esempio crea un oggetto resource. Una risorsa fornisce un'interfaccia orientata agli oggetti a COS. Ciò consente un livello di astrazione superiore rispetto alle chiamate di livello inferiore fornite da un oggetto client.
Si noti che alcune operazioni (come il trasferimento ad alta velocità dell' Aspera ) richiedono un client oggetto. Aspera richiede una version Python e di 3.6.
Avviso relativo alle versioni precedenti: il supporto per Aspera è considerato obsoleto. Utilizza invece il Aspera Transfer SDK.
import ibm_boto3
from ibm_botocore.client import Config, ClientError
# Constants for IBM COS values
COS_ENDPOINT = "<endpoint>" # Current list avaiable at https://control.cloud-object-storage.cloud.ibm.com/v2/endpoints
COS_API_KEY_ID = "<api-key>" # eg "W00YixxxxxxxxxxMB-odB-2ySfTrFBIQQWanc--P3byk"
COS_INSTANCE_CRN = "<service-instance-id>" # eg "crn:v1:bluemix:public:cloud-object-storage:global:a/3bf0d9003xxxxxxxxxx1c3e97696b71c:d6f04d83-6c4f-4a62-a165-696756d63903::"
# Create resource
cos_resource = ibm_boto3.resource("s3",
ibm_api_key_id=COS_API_KEY_ID,
ibm_service_instance_id=COS_INSTANCE_CRN,
config=Config(signature_version="oauth"),
endpoint_url=COS_ENDPOINT
)
Un client fornisce un'interfaccia di basso livello all'API COS S3. Ciò consente di elaborare direttamente le risposte di HTTP, anziché utilizzare i metodi e gli attributi astratti forniti da una risorsa per accedere alle informazioni contenute nelle intestazioni o nei payload delle risposte XML.
import ibm_boto3
from ibm_botocore.client import Config, ClientError
# Constants for IBM COS values
COS_ENDPOINT = "<endpoint>" # Current list avaiable at https://control.cloud-object-storage.cloud.ibm.com/v2/endpoints
COS_API_KEY_ID = "<api-key>" # eg "W00YixxxxxxxxxxMB-odB-2ySfTrFBIQQWanc--P3byk"
COS_INSTANCE_CRN = "<service-instance-id>" # eg "crn:v1:bluemix:public:cloud-object-storage:global:a/3bf0d9003xxxxxxxxxx1c3e97696b71c:d6f04d83-6c4f-4a62-a165-696756d63903::"
# Create client
cos_client = ibm_boto3.client("s3",
ibm_api_key_id=COS_API_KEY_ID,
ibm_service_instance_id=COS_INSTANCE_CRN,
config=Config(signature_version="oauth"),
endpoint_url=COS_ENDPOINT
)
Valori chiave
<endpoint>- endpoint pubblico per il vostro cloud Object Storage con schema preceduto da (' https:// ') (disponibile nella Dashboard di IBM Cloud ). Per ulteriori informazioni sugli endpoint, vedi Endpoint e ubicazioni di archiviazione.<api-key>- chiave api generata durante la creazione delle credenziali del servizio (è richiesto l'accesso in scrittura per gli esempi di creazione e cancellazione)<service-instance-id>- ID risorsa per il cloud Object Storage (disponibile tramite IBM Cloud CLI o IBM Cloud Dashboard )<location>- posizione predefinita per il cloud Object Storage (deve corrispondere alla regione utilizzata per<endpoint>)
Riferimenti SDK
Creazione di un nuovo bucket
Gli esempi seguenti utilizzano il client che è un'interfaccia di basso livello.
È possibile che si faccia riferimento a un elenco di codici di provisioning validi per LocationConstraint nella guida alle classi di archiviazione.
def create_bucket(bucket_name):
print("Creating new bucket: {0}".format(bucket_name))
try:
cos_client.create_bucket(
Bucket=bucket_name,
CreateBucketConfiguration={
"LocationConstraint":COS_BUCKET_LOCATION
}
)
print("Bucket: {0} created!".format(bucket_name))
except ClientError as be:
print("CLIENT ERROR: {0}\n".format(be))
except Exception as e:
print("Unable to create bucket: {0}".format(e))
Riferimenti SDK
Metodi
Creazione di un nuovo file di testo
def create_text_file(bucket_name, item_name, file_text):
print("Creating new item: {0}".format(item_name))
try:
cos_client.put_object(
Bucket=bucket_name,
Key=item_name,
Body=file_text
)
print("Item: {0} created!".format(item_name))
except ClientError as be:
print("CLIENT ERROR: {0}\n".format(be))
except Exception as e:
print("Unable to create text file: {0}".format(e))
Riferimenti SDK
Metodi
Elenca i bucket disponibili
def get_buckets():
print("Retrieving list of buckets")
try:
buckets = cos_client.list_buckets()
for bucket in buckets["Buckets"]:
print("Bucket Name: {0}".format(bucket["Name"]))
except ClientError as be:
print("CLIENT ERROR: {0}\n".format(be))
except Exception as e:
print("Unable to retrieve list buckets: {0}".format(e))
Riferimenti SDK
Metodi
Elenca gli elementi in un bucket
def get_bucket_contents(bucket_name):
print("Retrieving bucket contents from: {0}".format(bucket_name))
try:
files = cos_client.list_objects(Bucket=bucket_name)
for file in files.get("Contents", []):
print("Item: {0} ({1} bytes).".format(file["Key"], file["Size"]))
except ClientError as be:
print("CLIENT ERROR: {0}\n".format(be))
except Exception as e:
print("Unable to retrieve bucket contents: {0}".format(e))
Riferimenti SDK
Metodi
Ottieni il contenuto del file di uno specifico elemento
def get_item(bucket_name, item_name):
print("Retrieving item from bucket: {0}, key: {1}".format(bucket_name, item_name))
try:
file = cos_client.get_object(Bucket=bucket_name, Key=item_name)
print("File Contents: {0}".format(file["Body"].read()))
except ClientError as be:
print("CLIENT ERROR: {0}\n".format(be))
except Exception as e:
print("Unable to retrieve file contents: {0}".format(e))
Riferimenti SDK
Metodi
Elimina un elemento da un bucket
def delete_item(bucket_name, object_name):
try:
cos_client.delete_object(Bucket=bucket_name, Key=object_name)
print("Item: {0} deleted!\n".format(object_name))
except ClientError as be:
print("CLIENT ERROR: {0}\n".format(be))
except Exception as e:
print("Unable to delete object: {0}".format(e))
Riferimenti SDK
Metodi
Elimina più elementi da un bucket
La richiesta di eliminazione può contenere un massimo di 1000 chiavi che vuoi eliminare. Sebbene sia utile per ridurre le prestazioni per richiesta, occorre prestare attenzione quando si eliminano molte chiavi. Inoltre, prendi in considerazione anche le dimensioni degli oggetti per garantire delle prestazioni adeguate.
def delete_items(bucket_name):
try:
delete_request = {
"Objects": [
{ "Key": "deletetest/testfile1.txt" },
{ "Key": "deletetest/testfile2.txt" },
{ "Key": "deletetest/testfile3.txt" },
{ "Key": "deletetest/testfile4.txt" },
{ "Key": "deletetest/testfile5.txt" }
]
}
response = cos_client.delete_objects(
Bucket=bucket_name,
Delete=delete_request
)
print("Deleted items for {0}\n".format(bucket_name))
print(json.dumps(response.get("Deleted"), indent=4))
except ClientError as be:
print("CLIENT ERROR: {0}\n".format(be))
except Exception as e:
print("Unable to copy item: {0}".format(e))
Riferimenti SDK
Metodi
Elimina un bucket
def delete_bucket(bucket_name):
print("Deleting bucket: {0}".format(bucket_name))
try:
cos_client.delete_bucket(Bucket=bucket_name)
print("Bucket: {0} deleted!".format(bucket_name))
except ClientError as be:
print("CLIENT ERROR: {0}\n".format(be))
except Exception as e:
print("Unable to delete bucket: {0}".format(e))
Riferimenti SDK
Metodi
I nomi dei bucket sono riservati per 10-15 minuti dopo l'eliminazione.
Esegui un caricamento in più parti
Carica un file binario (metodo preferito)
Il metodo upload_fileobj dell'oggetto S3 esegue automaticamente un caricamento in più
parti, se necessario. La classe TransferConfig viene utilizzata per determinare la soglia di utilizzo
del caricamento in più parti.
def multi_part_upload(bucket_name, item_name, file_path):
try:
print("Starting file transfer for {0} to bucket: {1}\n".format(item_name, bucket_name))
# set 5 MB chunks
part_size = 1024 * 1024 * 5
# set threadhold to 15 MB
file_threshold = 1024 * 1024 * 15
# set the transfer threshold and chunk size
transfer_config = ibm_boto3.s3.transfer.TransferConfig(
multipart_threshold=file_threshold,
multipart_chunksize=part_size
)
# the upload_fileobj method will automatically execute a multi-part upload
# in 5 MB chunks for all files over 15 MB
with open(file_path, "rb") as file_data:
cos_client.upload_fileobj(
Bucket=bucket_name,
Key=item_name,
Fileobj=file_data,
Config=transfer_config
)
print("Transfer for {0} Complete!\n".format(item_name))
except ClientError as be:
print("CLIENT ERROR: {0}\n".format(be))
except Exception as e:
print("Unable to complete multi-part upload: {0}".format(e))
Riferimenti SDK
Metodi
Esegui manualmente un caricamento in più parti
Se si desidera, la classe S3.Client può essere usata per eseguire un caricamento in più parti. Questo può essere utile se è necessario maggiore controllo sul processo di caricamento.
def multi_part_upload_manual(bucket_name, item_name, file_path):
try:
# create client object
cos_client = ibm_boto3.client("s3",
ibm_api_key_id=COS_API_KEY_ID,
ibm_service_instance_id=COS_SERVICE_CRN,
config=Config(signature_version="oauth"),
endpoint_url=COS_ENDPOINT
)
print("Starting multi-part upload for {0} to bucket: {1}\n".format(item_name, bucket_name))
# initiate the multi-part upload
mp = cos_client.create_multipart_upload(
Bucket=bucket_name,
Key=item_name
)
upload_id = mp["UploadId"]
# min 20MB part size
part_size = 1024 * 1024 * 20
file_size = os.stat(file_path).st_size
part_count = int(math.ceil(file_size / float(part_size)))
data_packs = []
position = 0
part_num = 0
# begin uploading the parts
with open(file_path, "rb") as file:
for i in range(part_count):
part_num = i + 1
part_size = min(part_size, (file_size - position))
print("Uploading to {0} (part {1} of {2})".format(item_name, part_num, part_count))
file_data = file.read(part_size)
mp_part = cos_client.upload_part(
Bucket=bucket_name,
Key=item_name,
PartNumber=part_num,
Body=file_data,
ContentLength=part_size,
UploadId=upload_id
)
data_packs.append({
"ETag":mp_part["ETag"],
"PartNumber":part_num
})
position += part_size
# complete upload
cos_client.complete_multipart_upload(
Bucket=bucket_name,
Key=item_name,
UploadId=upload_id,
MultipartUpload={
"Parts": data_packs
}
)
print("Upload for {0} Complete!\n".format(item_name))
except ClientError as be:
# abort the upload
cos_client.abort_multipart_upload(
Bucket=bucket_name,
Key=item_name,
UploadId=upload_id
)
print("Multi-part upload aborted for {0}\n".format(item_name))
print("CLIENT ERROR: {0}\n".format(be))
except Exception as e:
print("Unable to complete multi-part upload: {0}".format(e))
Riferimenti SDK continuati
Classi
Metodi
Caricamento di grandi oggetti tramite TransferManager
TransferManager fornisce un altro modo di eseguire trasferimenti di grandi file incorporando automaticamente i caricamenti in più parti quando necessario impostando dei parametri di configurazione.
def upload_large_file(bucket_name, item_name, file_path):
print("Starting large file upload for {0} to bucket: {1}".format(item_name, bucket_name))
# set the chunk size to 5 MB
part_size = 1024 * 1024 * 5
# set threadhold to 5 MB
file_threshold = 1024 * 1024 * 5
# Create client connection
cos_client = ibm_boto3.client("s3",
ibm_api_key_id=COS_API_KEY_ID,
ibm_service_instance_id=COS_SERVICE_CRN,
config=Config(signature_version="oauth"),
endpoint_url=COS_ENDPOINT
)
# set the transfer threshold and chunk size in config settings
transfer_config = ibm_boto3.s3.transfer.TransferConfig(
multipart_threshold=file_threshold,
multipart_chunksize=part_size
)
# create transfer manager
transfer_mgr = ibm_boto3.s3.transfer.TransferManager(cos_client, config=transfer_config)
try:
# initiate file upload
future = transfer_mgr.upload(file_path, bucket_name, item_name)
# wait for upload to complete
future.result()
print ("Large file upload complete!")
except Exception as e:
print("Unable to complete large file upload: {0}".format(e))
finally:
transfer_mgr.shutdown()
Elenca gli elementi in un bucket (v2)
S3.Client client ha un metodo aggiornato per elencare il contenuto (list_objects_v2). Questo metodo ti consente di limitare il numero di record restituiti e di richiamare i record in batch. Questo potrebbe essere utile per la paginazione dei tuoi risultati all'interno di un'applicazione e per migliorare le prestazioni.
def get_bucket_contents_v2(bucket_name, max_keys):
print("Retrieving bucket contents from: {0}".format(bucket_name))
try:
# create client object
cos_client = ibm_boto3.client("s3",
ibm_api_key_id=COS_API_KEY_ID,
ibm_service_instance_id=COS_SERVICE_CRN,
config=Config(signature_version="oauth"),
endpoint_url=COS_ENDPOINT)
more_results = True
next_token = ""
while (more_results):
response = cos_client.list_objects_v2(Bucket=bucket_name, MaxKeys=max_keys, ContinuationToken=next_token)
files = response["Contents"]
for file in files:
print("Item: {0} ({1} bytes).".format(file["Key"], file["Size"]))
if (response["IsTruncated"]):
next_token = response["NextContinuationToken"]
print("...More results in next batch!\n")
else:
more_results = False
next_token = ""
except ClientError as be:
print("CLIENT ERROR: {0}\n".format(be))
except Exception as e:
print("Unable to retrieve bucket contents: {0}".format(e))
Riferimenti SDK
Metodi
Creazione di un criterio di backup
# Config values
api_key = "<API_KEY>"
vault_crn = "<SERVICE_INSTANCE_ID>"
source_bucket_name = "<BACKUP_VAULT_NAME>"
policy_name = "<POLICY_NAME>"
# Authenticator and client setup
authenticator = IAMAuthenticator(apikey=api_key)
rc_client = ResourceConfigurationV1(authenticator=authenticator)
# Create policy
create_backup_policy = rc_client.create_backup_policy(
bucket=source_bucket_name,
policy_name=policy_name,
target_backup_vault_crn=vault_crn,
backup_type="continuous",
initial_retention={"delete_after_days": 1}
)
# Print response
print(f" Policy created: { create_backup_policy }")
Elencare un criterio di backup
# Config values
api_key = "<API_KEY>"
source_bucket_name = "<BACKUP_VAULT_NAME>"
# Authenticator and client setup
authenticator = IAMAuthenticator(apikey=api_key)
rc_client = ResourceConfigurationV1(authenticator=authenticator)
# List all backup policies
list_response = rc_client.list_backup_policies(bucket=source_bucket_name)
print("\nList of backup policies:")
for policy in list_response.result.get("backup_policies", []):
print(policy)
Ottenere una politica di backup
# Config
api_key = "<API_KEY>"
source_bucket_name = "<SOURCE_BUCKET_NAME>"
backup_vault_crn = "<BACKUP_VAULT_CRN>"
policy_name = "<POLICY_NAME>"
# Setup authenticator and client
authenticator = IAMAuthenticator(apikey=api_key)
rc_client = ResourceConfigurationV1(authenticator=authenticator)
# Create backup policy
create_backup_policy_response = rc_client.create_backup_policy(
bucket=source_bucket_name,
policy_name=policy_name,
target_backup_vault_crn=backup_vault_crn,
backup_type="continuous",
initial_retention={"delete_after_days": 1}
)
# Extract policy ID
policy_id = create_backup_policy_response.result.get("policy_id")
get_backup_policy_response = rc_client.get_backup_policy(
bucket=source_bucket_name,
policy_id=policy_id
)
print("\nFetched Backup Policy Details:")
print(get_backup_policy_response.result)
Eliminare un criterio di backup
# Config
api_key = "<API_KEY>"
source_bucket_name = "<SOURCE_BUCKET_NAME>"
policy_id = "<POLICY_ID>"
# Setup authenticator and client
authenticator = IAMAuthenticator(apikey=api_key)
rc_client = ResourceConfigurationV1(authenticator=authenticator)
# Delete the backup policy
delete_backup_policy_response = rc_client.delete_backup_policy(
bucket=source_bucket_name,
policy_id=policy_id
)
print(f"Backup policy '{policy_id}' deleted successfully.")
Creazione di un vault di backup
# Config
api_key = "<API_KEY>"
service_instance_id = "<SERVICE_INSTANCE_ID>"
backup_vault_name = "<BACKUP_VAULT_NAME>"
region = "<REGION>"
# Setup authenticator and client
authenticator = IAMAuthenticator(apikey=api_key)
rc_client = ResourceConfigurationV1(authenticator=authenticator)
# Create a backup vault
create_backup_vault_response = rc_client.create_backup_vault(
service_instance_id=service_instance_id,
backup_vault_name=backup_vault_name,
region=region
)
# Output result
print("Backup vault created:")
print(create_backup_vault_response.result)
Elenco delle camere blindate di backup
# Config
api_key = "<API_KEY>"
service_instance_id = "<SERVICE_INSTANCE_ID>"
# Setup authenticator and client
authenticator = IAMAuthenticator(apikey=api_key)
rc_client = ResourceConfigurationV1(authenticator=authenticator)
# List backup vaults
list_backup_vaults_response = rc_client.list_backup_vaults(
service_instance_id=service_instance_id
)
print("List of backup vaults:")
print(list_backup_vaults_response.result)
Ottenere i vault di backup
# Config
api_key = "<API_KEY>"
backup_vault_name = "<BACKUP_VAULT_NAME>"
# Setup authenticator and client
authenticator = IAMAuthenticator(apikey=api_key)
rc_client = ResourceConfigurationV1(authenticator=authenticator)
# Get backup vault
get_backup_vault = rc_client.get_backup_vault(
backup_vault_name=backup_vault_name
)
# Output result
print("Backup vault details:")
print(get_backup_vault.result)
Aggiornare i vault di backup
# Config
api_key = "<API_KEY>"
backup_vault_name = "<BACKUP_VAULT_NAME>"
# Setup authenticator and client
authenticator = IAMAuthenticator(apikey=api_key)
rc_client = ResourceConfigurationV1(authenticator=authenticator)
# Update backup vault settings (disable activity tracking and metrics monitoring)
backup_vault_patch = {
"activity_tracking": {"management_events": True},
"metrics_monitoring": {"usage_metrics_enabled": True},
}
update_backup_vault_response = rc_client.update_backup_vault(
backup_vault_name=backup_vault_name,
backup_vault_patch=backup_vault_patch
)
# Output result
print("Backup vault updated successfully.")
print(update_backup_vault_response)
Eliminare un vault di backup
# Config
api_key = "<API_KEY>"
backup_vault_name = "<BACKUP_VAULT_NAME>"
# Setup authenticator and client
authenticator = IAMAuthenticator(apikey=api_key)
rc_client = ResourceConfigurationV1(authenticator=authenticator)
# Delete the backup vault
delete_vault_response = rc_client.delete_backup_vault(
backup_vault_name=backup_vault_name
)
# Output result
print(f"Successfully deleted backup vault '{delete_vault_response}'.")
Elenco Gamme di recupero
# Config
api_key = "<API_KEY>"
backup_vault_name = "<BACKUP_VAULT_NAME>"
# Setup authenticator and client
authenticator = IAMAuthenticator(apikey=api_key)
rc_client = ResourceConfigurationV1(authenticator=authenticator)
# List recovery ranges
recovery_ranges_response = rc_client.list_recovery_ranges(
backup_vault_name=backup_vault_name
)
# Output recovery range results
print("Recovery Ranges:")
print(recovery_ranges_response.result)
Ottenere l'intervallo di recupero
# Config
api_key = "<API_KEY>"
backup_vault_name = "<BACKUP_VAULT_NAME>"
recovery_range_id = "<RECOVERY_RANGE_ID>"
# Setup authenticator and client
authenticator = IAMAuthenticator(apikey=api_key)
rc_client = ResourceConfigurationV1(authenticator=authenticator)
get_recovery_range_response = rc_client.get_source_resource_recovery_range(
backup_vault_name=backup_vault_name,
recovery_range_id=recovery_range_id
)
print("Recovery Range Details:")
print(get_recovery_range_response.result)
Aggiornamento dell'intervallo di recupero
# Config
api_key = "<API_KEY>"
backup_vault_name = "<BACKUP_VAULT_NAME>"
recovery_range_id = "<RECOVERY_RANGE_ID>"
# Setup authenticator and client
authenticator = IAMAuthenticator(apikey=api_key)
rc_client = ResourceConfigurationV1(authenticator=authenticator)
recovery_range_patch_model = {}
recovery_range_patch_model['retention'] = {"delete_after_days": 99}
patch_response = rc_client.patch_source_resource_recovery_range(
backup_vault_name=backup_vault_name,
recovery_range_id=recovery_range_id,
recovery_range_patch=recovery_range_patch_model
)
print("Patch Response Details:")
print(patch_response)
Avvio di un ripristino
# Configuration
api_key = "<API_KEY>"
backup_vault_name = "<BACKUP_VAULT_NAME>"
target_bucket_crn = "<TARGET_BUCKET_CRN>"
recovery_range_id = "<RECOVERY_RANGE_ID>"
restore_point_in_time = "<RESTORE_POINT_IN_TIME>"
# Setup authenticator and clients
authenticator = IAMAuthenticator(apikey=api_key)
rc_client = ResourceConfigurationV1(authenticator=authenticator)
# Initiate restore
create_restore = rc_client.create_restore(
backup_vault_name=backup_vault_name,
recovery_range_id=recovery_range_id,
restore_type="in_place",
restore_point_in_time=restore_point_in_time,
target_resource_crn=target_bucket_crn
)
print(f"Restore initiated : {create_restore}")
Ripristino dell'elenco
# Config
api_key = "<API_KEY>"
backup_vault_name = "<BACKUP_VAULT_NAME>"
# Setup authenticator and clients
authenticator = IAMAuthenticator(apikey=api_key)
rc_client = ResourceConfigurationV1(authenticator=authenticator)
# List restore operations
get_store = rc_client.get_restore(
backup_vault_name=backup_vault_name)
print("Restore response:")
print(get_store.result)
Ottenere i dettagli del ripristino
# Config
api_key = "<API_KEY>"
source_bucket_name = "<SOURCE_BUCKET_NAME>"
backup_vault_crn = "<BACKUP_VAULT_CRN>"
backup_vault_name = "<BACKUP_VAULT_NAME>"
target_bucket_crn = "<TARGET_BUCKET_CRN>"
recovery_range_id = "<RECOVERY_RANGE_ID>"
restore_point_in_time = "<RESTORE_POINT_IN_TIME>"
# Setup authenticator and clients
authenticator = IAMAuthenticator(apikey=api_key)
rc_client = ResourceConfigurationV1(authenticator=authenticator)
# Create restore
create_restore = rc_client.create_restore(
backup_vault_name=backup_vault_name,
recovery_range_id=recovery_range_id,
restore_type="in_place",
restore_point_in_time=restore_point_in_time,
target_resource_crn=target_bucket_crn
)
restore_id = create_restore.result["restore_id"]
# List restore operations
get_store = rc_client.get_restore(
backup_vault_name=backup_vault_name, restore_id=restore_id)
print("Restore response:")
print(get_store.result)
Crea un nuovo bucket COS con blocco oggetti abilitato
def create_bucket_with_objectlock(bucket_name):
cos_cli.create_bucket(
Bucket=bucket_name,
ObjectLockEnabledForBucket=True,
)
print("Bucket: {0} created with objectlock enabled".format(bucket_name))
Imposta la configurazione del blocco oggetti con modalità di conformità sul bucket COS
def objectlock_configuration_on_bucket(bucket_name):
# Putting default retenion on the COS bucket.
default_retention_rule = {'DefaultRetention': {'Mode': 'COMPLIANCE', 'Years': 1}}
object_lock_config = {'ObjectLockEnabled': 'Enabled', 'Rule': default_retention_rule}
cos_cli.put_object_lock_configuration(Bucket=bucket_name, ObjectLockConfiguration=object_lock_config)
Imposta la configurazione del blocco degli oggetti con modalità di governance sul bucket COS
def objectlock_configuration_with_governance_mode_on_bucket(bucket_name):
# Putting default retenion on the COS bucket with governance mode.
default_retention_rule = {'DefaultRetention': {'Mode': 'GOVERNANCE', 'Years': 1}}
object_lock_config = {'ObjectLockEnabled': 'Enabled', 'Rule': default_retention_rule}
cos_cli.put_object_lock_configuration(Bucket=bucket_name, ObjectLockConfiguration=object_lock_config)
Ottieni la configurazione del blocco oggetti sul bucket COS
def objectlock_configuration_with_governance_mode_on_bucket(bucket_name):
# Reading the objectlock configuration set on the bucket.
response = cos_cli.get_object_lock_configuration(Bucket=bucket_name)
print("Objectlock Configuration for {0} =>".format(bucket_name))
print(response.ObjectLockConfiguration)
Carica un oggetto con modalità di governance nel bucket COS
def upload_object_with_governance_mode(bucket_name,object_name,object_content):
cos_cli.put_object(
Bucket=bucket_name,
Key=object_name,
Body=object_content,
ObjectLockMode='GOVERNANCE',
ObjectLockRetainUntilDate=datetime(2025, 11, 15)
)
print("Object: {0} uploaded!".format(object_name))
Attiva la conservazione del blocco dell'oggetto con modalità di conformità sull'oggetto
def objectlock_retention(bucket_name,object_name):
# Put objectlock retenion on the object uploaded to the bucket.
date = datetime.now()+timedelta(seconds=5)
retention_rule = {'Mode': 'COMPLIANCE', 'RetainUntilDate': date}
cos_cli.put_object_retention(Bucket=bucket_name, Key=object_name, Retention=retention_rule)
Attiva la conservazione del blocco dell'oggetto con modalità di governance sull'oggetto
def objectlock_retention_with_governance_mode(bucket_name,object_name):
# Put objectlock retenion with governance mode on the object uploaded to the bucket.
date = datetime.now()+timedelta(seconds=5)
retention_rule = {'Mode': 'GOVERNANCE', 'RetainUntilDate': date}
cos_cli.put_object_retention(Bucket=bucket_name, Key=object_name, Retention=retention_rule)
Ottieni il mantenimento del blocco dell'oggetto
def objectlock_retention_with_governance_mode(bucket_name,object_name):
# Get objectlock retention of the above object.
response = cos_cli.get_object_retention(Bucket=bucket_name, Key=object_name)
print("Objectlock Retention for {0}=>".format(object_name))
print(response.Retention)
Applicare il blocco legale all'oggetto
def objectlock_legal_hold(bucket_name,object_name):
# Setting the objectlock legal-hold status to ON.
cos_cli.put_object_legal_hold(Bucket=bucket_name, Key=object_name, legal_hold={'Status': 'ON'})
Ottieni il blocco dell'oggetto legalhold
def objectlock_legal_hold(bucket_name,object_name):
# Get objectlock retention of the above object.
response = cos_cli.get_object_legal_hold(Bucket=bucket_name, Key=object_name)
print("Objectlock legal-hold for {0}=>".format(object_name))
print(response.legal_hold)
Eliminazione di un oggetto con modalità di governance del blocco oggetti utilizzando la governance di bypass
def delete_object_with_bypass_governance(bucket_name,object_name):
# Deleting an object with retention using bypass governance
cos_cli.delete_object(Bucket=bucket_name, Key=object_name, BypassGovernanceRetention=True)
Utilizzo di Key Protect
Key Protect può essere aggiunto a un bucket di archiviazione per crittografare dati sensibili inattivi nel cloud.
Prima di cominciare
I seguenti elementi sono necessari per creare un bucket con Key-Protect abilitato:
- Un servizio Key Protect di cui è stato eseguito il provisioning
- Una chiave root disponibile (generata o importata)
Richiamo del CRN di chiave root
- Richiama l'ID istanza per il tuo servizio Key Protect
- Utilizza l'API Key Protect per richiamare tutte le tue chiavi disponibili
- Puoi utilizzare i comandi
curlo un client REST API come Postman per accedere all'API Key Protect.
- Puoi utilizzare i comandi
- Richiama il CRN della chiave root che utilizzi per abilitare Key Protect sul tuo bucket. Il CRN è simile al seguente:
crn:v1:bluemix:public:kms:us-south:a/3d624cd74a0dea86ed8efe3101341742:90b6a1db-0fe1-4fe9-b91e-962c327df531:key:0bg3e33e-a866-50f2-b715-5cba2bc93234
Creazione di un bucket con Key Protect abilitato
COS_KP_ALGORITHM = "<algorithm>"
COS_KP_ROOTKEY_CRN = "<root-key-crn>"
# Create a new bucket with key protect (encryption)
def create_bucket_kp(bucket_name):
print("Creating new encrypted bucket: {0}".format(bucket_name))
try:
cos_client.create_bucket(
Bucket=bucket_name,
CreateBucketConfiguration={
"LocationConstraint":COS_BUCKET_LOCATION
},
IBMSSEKPEncryptionAlgorithm=COS_KP_ALGORITHM,
IBMSSEKPCustomerRootKeyCrn=COS_KP_ROOTKEY_CRN
)
print("Encrypted Bucket: {0} created!".format(bucket_name))
except ClientError as be:
print("CLIENT ERROR: {0}\n".format(be))
except Exception as e:
print("Unable to create encrypted bucket: {0}".format(e))
Valori chiave
<algorithm>- L'algoritmo di crittografia utilizzato per i nuovi oggetti aggiunti al bucket (l'impostazione predefinita è AES256 ).<root-key-crn>- CRN della Root Key ottenuta dal servizio Key Protect.
Riferimenti SDK
Metodi
Utilizzo del trasferimento ad alta velocità Aspera
Avviso relativo alle versioni precedenti: il supporto per Aspera è considerato obsoleto. Si consiglia agli utenti di utilizzare Aspera Transfer SDK[https://developer.ibm.com/apis/catalog/aspera--aspera-transfer-sdk/API Reference].
Avviso relativo alle versioni precedenti: il supporto per Aspera è considerato obsoleto. Si consiglia agli utenti di utilizzare Aspera Transfer SDK.
Installando la Libreria del trasferimento ad alta velocità Aspera, puoi utilizzare trasferimenti file ad alta velocità all'interno della tua applicazione. La libreria Aspera è closed-source e, pertanto, una dipendenza facoltativa per l'SDK COS (che utilizza una licenza Apache).
Ogni sessione Aspera crea un singolo processo ascp eseguito sulla macchina client per eseguire il trasferimento. Assicurati che il tuo ambiente di calcolo possa consentire l'esecuzione di questo processo.
Inizializzazione di AsperaTransferManager
Prima di inizializzare AsperaTransferManager, assicurarsi di avere un oggetto funzionante (non un oggetto o ). client (non un oggetto resource o session).
import ibm_boto3
from ibm_botocore.client import Config
from ibm_s3transfer.aspera.manager import AsperaTransferManager
COS_ENDPOINT = "<endpoint>" # Current list avaiable at https://control.cloud-object-storage.cloud.ibm.com/v2/endpoints
COS_API_KEY_ID = "<api-key>"
COS_RESOURCE_CRN = "<resource-instance-id>"
COS_BUCKET_LOCATION = "<location>"
# Create resource
cos_client = ibm_boto3.client("s3",
ibm_api_key_id=COS_API_KEY_ID,
ibm_service_instance_id=COS_RESOURCE_CRN,
config=Config(signature_version="oauth"),
endpoint_url=COS_ENDPOINT
)
transfer_manager = AsperaTransferManager(cos)
Devi fornire una chiave API IAM per i trasferimenti ad alta velocità Aspera. Le credenziali HMAC NON sono attualmente supportate. Per ulteriori informazioni su IAM, fai clic qui.
Per ottenere una velocità effettiva più elevata, suddividi il trasferimento in un numero specificato di sessioni parallele che inviano blocchi di dati la cui dimensione è definita dal valore threshold.
La tipica configurazione per l'utilizzo di più sessioni dovrebbe essere:
- Velocità di destinazione di 2500 MBps
- Soglia di 100 MB (questo è il valore consigliato per la maggior parte delle applicazioni)
ms_transfer_config = AsperaConfig(multi_session="all",
target_rate_mbps=2500,
multi_session_threshold_mb=100)
Nell'esempio sopra riportato, l'SDK genera un numero sufficiente di sessioni per provare a raggiungere la velocità di destinazione di 2500 MBps.
La gestione delle sessioni può anche essere configurata esplicitamente nell'SDK. Ciò è utile nei casi in cui si voglia un controllo più preciso sull'utilizzo della rete.
La tipica configurazione per l'utilizzo di più sessioni esplicito dovrebbe essere:
- 2 o 10 sessioni
- Soglia di 100 MB (questo è il valore consigliato per la maggior parte delle applicazioni)
from ibm_s3transfer.aspera.manager import AsperaConfig
# Configure 2 sessions for transfer
ms_transfer_config = AsperaConfig(multi_session=2,
multi_session_threshold_mb=100)
# Create the Aspera Transfer Manager
transfer_manager = AsperaTransferManager(client=client,
transfer_config=ms_transfer_config)
Per ottenere le migliori prestazioni nella maggior parte degli scenari, utilizzare sempre sessioni multiple per ridurre al minimo l'elaborazione associata all'istanziazione di un trasferimento ad alta velocità Aspera. Se la tua capacità di rete è di almeno 1 Gbps, devi utilizzare 10 sessioni. Reti con una larghezza di banda inferiore devono utilizzare due sessioni.
Caricamento file
bucket_name = "<bucket-name>"
upload_filename = "<absolute-path-to-file>"
object_name = "<item-name>"
# Create Transfer manager
with AsperaTransferManager(client) as transfer_manager:
# Perform upload
future = transfer_manager.upload(upload_filename, bucket_name, object_name)
# Wait for upload to complete
future.result()
Valori chiave
<bucket-name>- nome del bucket di destinazione<absolute-path-to-file>- percorso della directory e nome del file da caricare<item-name>- nome del nuovo file aggiunto al bucket
Scarica file
bucket_name = "<bucket-name>"
download_filename = "<absolute-path-to-file>"
object_name = "<object-to-download>"
# Create Transfer manager
with AsperaTransferManager(client) as transfer_manager:
# Get object with Aspera
future = transfer_manager.download(bucket_name, object_name, download_filename)
# Wait for download to complete
future.result()
Valori chiave
<bucket-name>- nome del bucket nell'istanza del servizio Object Storage che ha abilitato Aspera.<absolute-path-to-file>- e il nome del file in cui salvare il file nel sistema locale.<object-to-download>- nome del file nel bucket da scaricare.
Caricamento directory
bucket_name = "<bucket-name>"
# THIS DIRECTORY MUST EXIST LOCALLY, and have objects in it.
local_upload_directory = "<absolute-path-to-directory>"
# THIS SHOULD NOT HAVE A LEADING "/"
remote_directory = "<object prefix>"
# Create Transfer manager
with AsperaTransferManager(client) as transfer_manager:
# Perform upload
future = transfer_manager.upload_directory(local_upload_directory, bucket_name, remote_directory)
# Wait for upload to complete
future.result()
Valori chiave
<bucket-name>- nome del bucket nell'istanza del servizio Object Storage che ha abilitato Aspera<absolute-path-to-directory>- directory locale che contiene i file da caricare. Deve avere una/di inizio e di fine (ossia/Users/testuser/Documents/Upload/)<object prefix>- nome della directory nel bucket in cui memorizzare i file. Non deve avere una barra/iniziale (ossianewuploads/)
Scaricamento directory
bucket_name = "<bucket-name>"
# THIS DIRECTORY MUST EXIST LOCALLY
local_download_directory = "<absolute-path-to-directory>"
remote_directory = "<object prefix>"
# Create Transfer manager
with AsperaTransferManager(client) as transfer_manager:
# Get object with Aspera
future = transfer_manager.download_directory(bucket_name, remote_directory, local_download_directory)
# Wait for download to complete
future.result()
Valori chiave
<bucket-name>- nome del bucket nell'istanza del servizio Object Storage che ha abilitato Aspera<absolute-path-to-directory>- directory locale in cui salvare i file scaricati. Deve avere una barra di separazione e un'altra di separazione/(cioè/Users/testuser/Downloads/)<object prefix>- nome della directory nel bucket in cui memorizzare i file. Non deve avere una barra/iniziale (ossiatodownload/)
Utilizzo dei sottoscrittori
I sottoscrittori forniscono l'osservabilità nei trasferimenti collegando dei metodi di callback personalizzati. Tutte le transizioni dei trasferimenti tra le seguenti fasi:
Queued - In Progress - Done
Esistono tre sottoscrittori disponibili per ogni fase:
CallbackOnQueued()- richiamato quando è stato aggiunto un nuovo trasferimento aAsperaTransferManagerCallbackOnProgress()- richiamato quando un trasferimento ha trasmesso i dati (attivato ripetutamente mentre il trasferimento è in corso).CallbackOnDone()- richiamato quando il trasferimento è stato completato
bucket_name = "<bucket-name>"
local_download_directory = "<absolute-path-to-directory>"
remote_directory = "<object prefix>"
# Subscriber callbacks
class CallbackOnQueued(AsperaBaseSubscriber):
def __init__(self):
pass
def on_queued(self, future, **kwargs):
print("Directory download queued.")
class CallbackOnProgress(AsperaBaseSubscriber):
def __init__(self):
pass
def on_progress(self, future, bytes_transferred, **kwargs):
print("Directory download in progress: %s bytes transferred" % bytes_transferred)
class CallbackOnDone(AsperaBaseSubscriber):
def __init__(self):
pass
def on_done(self, future, **kwargs):
print("Downloads complete!")
# Create Transfer manager
transfer_manager = AsperaTransferManager(client)
# Attach subscribers
subscribers = [CallbackOnQueued(), CallbackOnProgress(), CallbackOnDone()]
# Get object with Aspera
future = transfer_manager.download_directory(bucket_name, remote_directory, local_download_directory, None, subscribers)
# Wait for download to complete
future.result()
Valori chiave
<bucket-name>- nome del bucket nell'istanza del servizio Object Storage che ha abilitato Aspera<absolute-path-to-directory>- directory locale in cui salvare i file scaricati. Deve avere una barra/di inizio e di fine (ossia/Users/testuser/Downloads/)<object prefix>- nome della directory nel bucket in cui memorizzare i file. Non deve avere una barra/iniziale (ossiatodownload/)
Il codice di esempio produce il seguente output:
Directory download queued.
Directory download in progress: 5632 bytes transferred
Directory download in progress: 1047552 bytes transferred
...
Directory download in progress: 53295130 bytes transferred
Directory download in progress: 62106855 bytes transferred
Download complete!
Metti in pausa/Riprendi/Annulla
L'SDK consente di gestire l'avanzamento dei trasferimenti di file/directory mediante i seguenti metodi dell'oggetto AsperaTransferFuture:
pause()resume()cancel()
Il richiamo dei metodi sopra indicati non ha alcun effetto collaterale. Adeguate attività di ripulitura e manutenzione sono gestite dall'SDK.
# Create Transfer manager
bucket_name = "<bucket-name>"
local_download_directory = "<absolute-path-to-directory>"
remote_directory = "<object prefix>"
with AsperaTransferManager(client) as transfer_manager:
# download a directory with Aspera
future = transfer_manager.download_directory(bucket_name, remote_directory, local_download_directory, None, None)
# pause the transfer
future.pause()
# resume the transfer
future.resume()
# cancel the transfer
future.cancel()
Risoluzione dei problemi di Aspera
Problema: gli sviluppatori che utilizzano qualsiasi versione di Python oltre a 3.6 potrebbero riscontrare degli errori durante l'installazione o l'utilizzo di Aspera SDK.
Causa: Se nel vostro ambiente sono installate diverse versioni di Python, è possibile che si verifichino errori di installazione quando si tenta di installare Aspera SDK. Questo può essere causato dalla mancanza di file DLL o di una DLL non corretta nel percorso.
Soluzione: il primo passo nella risoluzione di questo problema consiste nel reinstallare le librerie Aspera. Potrebbe essersi verificato un errore durante l'installazione. Di conseguenza, questo errore potrebbe avere interessato i file DLL. Se questo non risolve i problemi, ti verrà richiesto di aggiornare la tua versione di Python. Se non è possibile farlo, è possibile utilizzare l'installazione di Intel® Distribution per Python *. Ciò ti dovrebbe consentire di installare Aspera SDK su Python 3.6.x senza alcun problema.
Aggiornamento dei metadati
Esistono due modi per aggiornare i metadati in un oggetto esistente:
- Una richiesta
PUTcon i nuovi metadati e il contenuto dell'oggetto originale - L'esecuzione di una richiesta
COPYcon i nuovi metadati che specifica l'oggetto originale come origine della copia
Utilizzo di PUT per aggiornare i metadati
Nota: la richiesta di PUT sovrascrive il contenuto esistente dell'oggetto, che deve quindi essere prima scaricato e ricaricato con i nuovi metadati.
def update_metadata_put(bucket_name, item_name, key, value):
try:
# retrieve the existing item to reload the contents
response = cos_client.get_object(Bucket=bucket_name, Key=item_name)
existing_body = response.get("Body").read()
# set the new metadata
new_metadata = {
key: value
}
cos_client.put_object(Bucket=bucket_name, Key=item_name, Body=existing_body, Metadata=new_metadata)
print("Metadata update (PUT) for {0} Complete!\n".format(item_name))
except ClientError as be:
print("CLIENT ERROR: {0}\n".format(be))
except Exception as e:
log_error("Unable to update metadata: {0}".format(e))
Utilizzo di COPY per aggiornare i metadati
def update_metadata_copy(bucket_name, item_name, key, value):
try:
# set the new metadata
new_metadata = {
key: value
}
# set the copy source to itself
copy_source = {
"Bucket": bucket_name,
"Key": item_name
}
cos_client.copy_object(Bucket=bucket_name, Key=item_name, CopySource=copy_source, Metadata=new_metadata, MetadataDirective="REPLACE")
print("Metadata update (COPY) for {0} Complete!\n".format(item_name))
except ClientError as be:
print("CLIENT ERROR: {0}\n".format(be))
except Exception as e:
log_error("Unable to update metadata: {0}".format(e))
Utilizzo di Immutable Object Storage
Aggiunta di una configurazione di protezione ad un bucket esistente
Gli oggetti scritti in un bucket protetto non possono essere eliminati fino a quando il periodo di protezione non è scaduto e tutte le conservazioni a fini legali sull'oggetto non sono stati rimosse. A un oggetto viene dato il valore di conservazione predefinito del bucket, a meno che non venga fornito un valore specifico per l'oggetto quando l'oggetto viene creato. Gli oggetti nei bucket protetti che non sono più sottoposti a conservazione (il periodo di conservazione è scaduto e l'oggetto non ha alcuna conservazione a fini legali), quando vengono sovrascritti sono di nuovo sottoposti a conservazione. Il nuovo periodo di conservazione può essere fornito come parte della richiesta di sovrascrittura dell'oggetto, altrimenti all'oggetto verrà assegnato il tempo di conservazione predefinito del bucket.
I valori minimi e massimi supportati per le impostazioni del periodo di conservazione MinimumRetention, DefaultRetention e MaximumRetention sono un minimo di 0 giorni e un massimo di 365243 giorni (1000
anni).
def add_protection_configuration_to_bucket(bucket_name):
try:
new_protection_config = {
"Status": "Retention",
"MinimumRetention": {"Days": 10},
"DefaultRetention": {"Days": 100},
"MaximumRetention": {"Days": 1000}
}
cos_client.put_bucket_protection_configuration(Bucket=bucket_name, ProtectionConfiguration=new_protection_config)
print("Protection added to bucket {0}\n".format(bucket_name))
except ClientError as be:
print("CLIENT ERROR: {0}\n".format(be))
except Exception as e:
print("Unable to set bucket protection config: {0}".format(e))
Controlla la protezione su un bucket
def get_protection_configuration_on_bucket(bucket_name):
try:
response = cos_client.get_bucket_protection_configuration(Bucket=bucket_name)
protection_config = response.get("ProtectionConfiguration")
print("Bucket protection config for {0}\n".format(bucket_name))
print(protection_config)
print("\n")
except ClientError as be:
print("CLIENT ERROR: {0}\n".format(be))
except Exception as e:
print("Unable to get bucket protection config: {0}".format(e))
Carica un oggetto protetto
Gli oggetti nei bucket protetti che non sono più sottoposti a conservazione (il periodo di conservazione è scaduto e l'oggetto non ha alcuna conservazione a fini legali), quando vengono sovrascritti sono di nuovo sottoposti a conservazione. Il nuovo periodo di conservazione può essere fornito come parte della richiesta di sovrascrittura dell'oggetto, altrimenti all'oggetto verrà assegnato il tempo di conservazione predefinito del bucket.
| Valore | Immettere | Descrizione |
|---|---|---|
Retention-Period |
Numero intero non negativo (secondi) | Il periodo di conservazione da memorizzare sull'oggetto, in secondi. L'oggetto non può essere sovrascritto o eliminato finché l'intervallo di tempo specificato nel periodo di conservazione non è trascorso. Se vengono specificati questi
campo e Retention-Expiration-Date, viene restituito un errore 400. Se non viene specificato nessuno di questi due valori, verrà utilizzato il periodo DefaultRetention del bucket. Zero (0)
è un valore consentito, presumendo che il periodo di conservazione minimo del bucket sia anch'esso 0. |
Retention-expiration-date |
Data (formato ISO 8601) | Data in cui sarà consentito eliminare o modificare l'oggetto. Puoi specificare solo questo valore oppure l'intestazione Retention-Period. Se vengono specificati entrambi, verrà restituito un errore 400. Se non viene specificato
nessuno di questi due valori, verrà utilizzato il periodo DefaultRetention del bucket. |
Retention-legal-hold-id |
stringa | Una singola conservazione a fini legali da applicare all'oggetto. Una conservazione a fini legali è una stringa di caratteri di lunghezza Y. L'oggetto non può essere sovrascritto o eliminato finché non sono state rimosse tutte le conservazioni a fini legali a esso associate. |
def put_object_add_legal_hold(bucket_name, object_name, file_text, legal_hold_id):
print("Add legal hold {0} to {1} in bucket {2} with a putObject operation.\n".format(legal_hold_id, object_name, bucket_name))
cos_client.put_object(
Bucket=bucket_name,
Key=object_name,
Body=file_text,
RetentionLegalHoldId=legal_hold_id)
print("Legal hold {0} added to object {1} in bucket {2}\n".format(legal_hold_id, object_name, bucket_name))
def copy_protected_object(source_bucket_name, source_object_name, destination_bucket_name, new_object_name):
print("Copy protected object {0} from bucket {1} to {2}/{3}.\n".format(source_object_name, source_bucket_name, destination_bucket_name, new_object_name))
copy_source = {
"Bucket": source_bucket_name,
"Key": source_object_name
}
cos_client.copy_object(
Bucket=destination_bucket_name,
Key=new_object_name,
CopySource=copy_source,
RetentionDirective="Copy"
)
print("Protected object copied from {0}/{1} to {2}/{3}\n".format(source_bucket_name, source_object_name, destination_bucket_name, new_object_name));
def complete_multipart_upload_with_retention(bucket_name, object_name, upload_id, retention_period):
print("Completing multi-part upload for object {0} in bucket {1}\n".format(object_name, bucket_name))
cos_client.complete_multipart_upload(
Bucket=bucket_name,
Key=object_name,
MultipartUpload={
"Parts":[{
"ETag": part["ETag"],
"PartNumber": 1
}]
},
UploadId=upload_id,
RetentionPeriod=retention_period
)
print("Multi-part upload completed for object {0} in bucket {1}\n".format(object_name, bucket_name))
def upload_file_with_retention(bucket_name, object_name, path_to_file, retention_period):
print("Uploading file {0} to object {1} in bucket {2}\n".format(path_to_file, object_name, bucket_name))
args = {
"RetentionPeriod": retention_period
}
cos_client.upload_file(
Filename=path_to_file,
Bucket=bucket_name,
Key=object_name,
ExtraArgs=args
)
print("File upload complete to object {0} in bucket {1}\n".format(object_name, bucket_name))
Aggiungi/rimuovi una conservazione a fini legali a/da un oggetto protetto
L'oggetto può supportare 100 conservazioni a fini legali:
- Un identificativo di conservazione a fini legali è una stringa di una lunghezza massima di 64 caratteri e una lunghezza minima di 1 carattere. I caratteri validi sono lettere, numeri e simboli
!,_,.,*,(,)e-. - Se l'aggiunta di una specifica conservazione a fini legali comporta il superamento di un totale di 100 conservazioni a fini legali sull'oggetto, la nuova conservazione a fini legali non viene aggiunta e viene restituito un errore
400. - Se un identificativo è troppo lungo, non viene aggiunto all'oggetto e viene restituito un errore
400. - Se un identificativo contiene caratteri non validi, non viene aggiunto all'oggetto e viene restituito un errore
400. - Se un identificativo è già in uso su un oggetto, la conservazione a fini legali esistente non viene modificata e la risposta indica che l'identificativo era già in uso con un errore
409. - Se un oggetto non ha metadati del periodo di conservazione, viene restituito un errore
400e l'aggiunta o la rimozione di una conservazione a fini legali non è consentita.
Per aggiungere o rimuovere un blocco legale, devi disporre delle autorizzazioni Manager per questo bucket.
def add_legal_hold_to_object(bucket_name, object_name, legal_hold_id):
print("Adding legal hold {0} to object {1} in bucket {2}\n".format(legal_hold_id, object_name, bucket_name))
cos_client.add_legal_hold(
Bucket=bucket_name,
Key=object_name,
RetentionLegalHoldId=legal_hold_id
)
print("Legal hold {0} added to object {1} in bucket {2}!\n".format(legal_hold_id, object_name, bucket_name))
def delete_legal_hold_from_object(bucket_name, object_name, legal_hold_id):
print("Deleting legal hold {0} from object {1} in bucket {2}\n".format(legal_hold_id, object_name, bucket_name))
cos_client.delete_legal_hold(
Bucket=bucket_name,
Key=object_name,
RetentionLegalHoldId=legal_hold_id
)
print("Legal hold {0} deleted from object {1} in bucket {2}!\n".format(legal_hold_id, object_name, bucket_name))
Estendi il periodo di conservazione di un oggetto protetto
Il periodo di conservazione di un oggetto può solo essere esteso. Non può essere ridotto rispetto al valore attualmente configurato.
Il valore di espansione della conservazione è impostato in uno di tre possibili modi:
- ulteriore tempo dal valore corrente (
Additional-Retention-Periodo metodo simile) - nuovo periodo di estensione in secondi (
Extend-Retention-From-Current-Timeo metodo simile) - nuova data di scadenza della conservazione dell'oggetto (
New-Retention-Expiration-Dateo metodo simile)
Il periodo di conservazione attuale memorizzato nei metadati dell'oggetto viene aumentato in misura equivalente al tempo aggiuntivo indicato oppure sostituito con il nuovo valore, a seconda del parametro impostato nella richiesta extendRetention.
In tutti i casi, il parametro di estensione della conservazione viene controllato rispetto al periodo di conservazione attuale e il parametro esteso viene accettato solo se il periodo di conservazione aggiornato è più grande del periodo
di conservazione attuale.
Gli oggetti nei bucket protetti che non sono più sottoposti a conservazione (il periodo di conservazione è scaduto e l'oggetto non ha alcuna conservazione a fini legali), quando vengono sovrascritti sono di nuovo sottoposti a conservazione. Il nuovo periodo di conservazione può essere fornito come parte della richiesta di sovrascrittura dell'oggetto, altrimenti all'oggetto verrà assegnato il tempo di conservazione predefinito del bucket.
def extend_retention_period_on_object(bucket_name, object_name, additional_seconds):
print("Extend the retention period on {0} in bucket {1} by {2} seconds.\n".format(object_name, bucket_name, additional_seconds))
cos_client.extend_object_retention(
Bucket=bucket_ame,
Key=object_name,
AdditionalRetentionPeriod=additional_seconds
)
print("New retention period on {0} is {1}\n".format(object_name, additional_seconds))
Elenca le conservazioni a fini legali su un oggetto protetto
Questa operazione restituisce:
- La data di creazione dell'oggetto
- Il periodo di conservazione dell'oggetto in secondi
- Data di scadenza della conservazione calcolata sulla base del periodo e della data di creazione
- Elenco delle conservazioni a fini legali
- Identificativo della conservazione a fini legali
- Data/ora di quando è stata applicata la conservazione a fini legali
Se non ci sono conservazioni a fini legali sull'oggetto, viene restituito un LegalHoldSet vuoto. Se non c'è alcun periodo di conservazione specificato sull'oggetto, viene restituito un errore 404.
def list_legal_holds_on_object(bucket_name, object_name):
print("List all legal holds on object {0} in bucket {1}\n".format(object_name, bucket_name));
response = cos_client.list_legal_holds(
Bucket=bucket_name,
Key=object_name
)
print("Legal holds on bucket {0}: {1}\n".format(bucket_name, response))
Crea un sito web statico ospitato
Questa operazione richiede le autorizzazioni, poiché solo al proprietario del bucket è generalmente consentito configurare un bucket per ospitare un sito web statico. I parametri determinano il suffisso predefinito per i visitatori del sito e un documento di errore facoltativo.
def putBucketWebsiteConfiguration(bucket_name):
website_defaults = {
'ErrorDocument': {'Key': 'error.html'},
'IndexDocument': {'Suffix': 'index.html'},
}
cos_client.put_bucket_website(Bucket=bucket_name, WebsiteConfiguration=website_defaults)
print("Website configuration set on bucket {0}\n".format(bucket_name))
Passi successivi
Per ulteriori informazioni, il codice sorgente può essere trovato all'indirizzo GitHub.