Observação:
- Este tutorial requer acesso ao Oracle Cloud. Para se cadastrar em uma conta gratuita, consulte Conceitos básicos do Oracle Cloud Infrastructure Free Tier.
- Ele usa valores de exemplo para credenciais, tenancy e compartimentos do Oracle Cloud Infrastructure. Ao concluir seu laboratório, substitua esses valores por valores específicos do seu ambiente de nuvem.
Usar o Oracle Cloud Infrastructure Object Storage Service com a API Swift OpenStack
Introdução
O Oracle Cloud Infrastructure (OCI) Object Storage é uma arquitetura de armazenamento de dados que gerencia e organiza informações digitais como objetos, cada um compreendendo dados, metadados e um identificador exclusivo. Ao contrário do armazenamento tradicional de arquivos ou blocos, o OCI Object Storage não depende de uma estrutura hierárquica, permitindo um manuseio eficiente e escalável de grandes quantidades de dados não estruturados. Os objetos são armazenados em um espaço de endereço simples, simplificando a recuperação de dados e permitindo uma escalabilidade perfeita. Esta solução é ideal para diversos tipos de dados, como conteúdo multimídia e backups, tornando-a uma escolha robusta para ambientes de nuvem, armazenamento de arquivamento e sistemas distribuídos devido à sua flexibilidade, durabilidade e facilidade de acesso. Os usuários interagem com o serviço de armazenamento de objetos usando uma interface REST sobre o protocolo HTTP.
O serviço OCI Object Storage é uma solução de armazenamento baseada em nuvem na qual a Oracle lida com a complexidade de gerenciamento, garantindo durabilidade de dados confiável e econômica. A elasticidade da plataforma permite um início gradual com a capacidade de dimensionar sem problemas, tudo sem comprometer o desempenho ou a confiabilidade do serviço.
O OCI Object Storage fornece compatibilidade de API com a API OpenStack Swift e o Amazon Simple Storage Service (Amazon S3) por meio da API de Compatibilidade com Amazon S3. Isso permite que os clientes continuem usando suas ferramentas existentes (por exemplo, clientes SDK), minimizando a necessidade de fazer alterações em seus aplicativos. Para obter mais informações, consulte API de Compatibilidade com Amazon S3. Este tutorial se concentrará no consumo de API compatível com o OCI OpenStack Swift.
Antes de começarmos a discutir sobre a API Swift OpenStack, precisamos esclarecer algumas das construções usadas no OCI Object Storage.
-
Os Namespaces são empregados para fornecer isolamento no nível da conta no nível da região do OCI para buckets e objetos. Na criação de uma conta de tenant do Oracle Cloud Infrastructure, um nome de namespace exclusivo e imutável do OCI Object Storage é designado. Esses namespaces se estendem por todos os compartimentos em uma tenancy e permanecem os mesmos em todas as regiões.
-
Buckets são contêineres lógicos para armazenar objetos. O bucket é um recurso no nível da região.
-
Objeto: qualquer tipo de dados, independentemente do tipo de conteúdo, é armazenado como um objeto. Um objeto é composto do objeto em si e dos metadados sobre ele. Cada objeto é armazenado em um bucket.
-
Compartimentos são construções lógicas usadas para organizar seus recursos de nuvem. Um bucket do OCI Object Storage só pode existir em um compartimento. As políticas do OCI IAM (Oracle Cloud Infrastructure Identity and Access Management) que controlam o acesso aos recursos de armazenamento de objetos são aplicadas por compartimento.
O Swift OpenStack define três construções: Conta, Contêiner e Objeto.
-
Conta representa o nível superior da hierarquia e é sinônimo de um projeto ou tenant.
-
O container é usado como um namespace para objetos.
Agora podemos identificar recursos equivalentes entre o OCI Object Storage e a API Swift OpenStack.
- O namespace do OCI Object Storage é equivalente à conta Swift.
- O bucket do OCI Object Storage é equivalente ao contêiner Swift.
- O objeto do OCI Object Storage é equivalente ao objeto Swift.
Objetivos
- Ilustre várias maneiras de usar os serviços do OCI Object Storage com a API compatível com Swift OpenStack.
Pré-requisitos
-
Gerar Token de Autenticação do OCI: O consumo da API Swift do OCI requer autenticação usando tokens de autenticação do OCI. Para obter mais informações, consulte Criando um Token de Autenticação.
-
Crie políticas para conceder ao usuário acesso para consumir serviços do OCI Object Storage. Política do Oracle Cloud Infrastructure Identity and Access Management (OCI IAM) para permitir o acesso do usuário para gerenciar recursos da família de objetos em um compartimento. Os recursos do OCI são organizados em compartimentos e o acesso aos recursos é governado pelas políticas definidas para o compartimento. Para este tutorial, você precisa criar a política a seguir.
allow group <group-name> to manage object-family in tenancy
.
Usar API Swift do OCI
Os pontos finais regionais da API OCI Swift usam um formato de URL consistente de https://swiftobjectstorage.<region-identifier>.oraclecloud.com
. Por exemplo, o ponto final nativo da API OCI Swift na região Leste dos EUA (US-ashburn-1) é https://swiftobjectstorage.US-ashburn-1.oraclecloud.com
.
Considerando o isolamento no nível do tenant no nível da região, o ponto final da API Swift do OCI se torna: https://swiftobjectstorage.<region-identifier>.oraclecloud.com/<tenancy-namespace>
, em que <tenancy-namespace>
é a string de namespace do serviço Object Storage gerada automaticamente da tenancy na qual criar repositórios. Para obter mais informações, consulte a página Informações da Tenancy.
A API Swift da OCI não tem o conceito de compartimento. Por padrão, os buckets criados usando a API de Compatibilidade com Amazon S3 do OCI ou a API Swift do OCI são criados no compartimento root da tenancy do Oracle Cloud Infrastructure. Você pode designar outro compartimento para a API de Compatibilidade com Amazon S3 do OCI ou a API Swift do OCI para criar buckets. Para obter mais informações, consulte Editando Designações de Compartimento da API de Compatibilidade com o Amazon S3 e da API Swift da Tenancy.
A API OCI Swift suporta três abordagens para autenticar solicitações.
Abordagem 1: Usar Cabeçalho de Autorização Básica
O nome do usuário tem o formato <username>
. Por exemplo, john.doe@acme.com
. Se sua tenancy for federada com o Oracle Identity Cloud Service, use o formato oracleidentitycloudservice/<username>
.
A senha é o token de autenticação gerado para o usuário. Por exemplo, my-auth-token
. Para obter mais informações, consulte Como Obter um Token de Autenticação.
Cada solicitação para a API Swift do OCI deve incluir o cabeçalho a seguir.
- Autorização:
Basic <base64(username:password)>
.
Por exemplo, se o nome de usuário for oracleidentitycloudservice/john.doe@acme.com
e a senha for my-auth-token
, o cabeçalho terá a seguinte aparência:
- Autorização:
Basic b3JhY2xlaWRlbnRpdHljbG91ZHNlcnZpY2Uvam9obi5kb2VAYWNtZS5jb206b ktYXV0aC10b2tlbg==
.
Usaremos algumas das chamadas de API descritas na documentação oficial. Consulte OpenStack Swift API.
Exemplo:
-
Inicialize as variáveis de ambiente necessárias a seguir.
user='<username>' password='<password>' region='<oci-region>' tenancy_namespace='<tenancy-namespace>' bucket_name='tutorial-bucket' object_name='sample.txt'
-
Liste buckets na conta; somente buckets dos compartimentos selecionados da API Swift do OCI serão listados.
curl -sS -D /dev/stderr "https://swiftobjectstorage.${region}.oraclecloud.com/v1/${tenancy_namespace}" -u "${user}:${password}" | jq
-
Criar um bucket.
curl -sS -i "https://swiftobjectstorage.${region}.oraclecloud.com/v1/${tenancy_namespace}/${bucket_name}" -X PUT -u "${user}:${password}"
-
Faça upload de um arquivo para o bucket.
echo 'sample file' > ${object_name} curl -s -i "https://swiftobjectstorage.${region}.oraclecloud.com/v1/${tenancy_namespace}/${bucket_name}/${object_name}" -X PUT --data-binary "@${object_name}" -u "${user}:${password}"
-
Liste o conteúdo do bucket.
curl -sS -D /dev/stderr "https://swiftobjectstorage.${region}.oraclecloud.com/v1/${tenancy_namespace}/${bucket_name}" -u "${user}:${password}" | jq
-
Extraia um arquivo do bucket.
curl -s -D /dev/stderr "https://swiftobjectstorage.${region}.oraclecloud.com/v1/${tenancy_namespace}/${bucket_name}/${object_name}" -u "${user}:${password}" -o downloaded_file.txt cat downloaded_file.txt
-
Exclua o arquivo do bucket.
curl -sS -i "https://swiftobjectstorage.${region}.oraclecloud.com/v1/${tenancy_namespace}/${bucket_name}/${object_name}" -X DELETE -u "${user}:${password}"
-
Exclua o bucket.
curl -s -i "https://swiftobjectstorage.${region}.oraclecloud.com/v1/${tenancy_namespace}/${bucket_name}" -X DELETE -u "${user}:${password}"
Abordagem 2: Autenticação Baseada em Token usando a Autenticação v1
Você precisará chamar o ponto final de autorização da API Swift do OCI para a região e incluir os cabeçalhos X-Storage-User
e X-Storage-Pass
na solicitação. Se a solicitação de autenticação for bem-sucedida, você receberá uma resposta com o cabeçalho X-Storage-Token
que pode ser usado para autorização de solicitação e o cabeçalho X-Storage-Url
com o ponto final da API Swift do OCI para a conta.
O cabeçalho X-Storage-User
tem o formato <tenancy-namespace>:<username>
.
Por exemplo, se tenancy-namespace
for axaxnpcrorw5
e o nome de usuário for o mesmo da Abordagem 1, o valor do cabeçalho será axaxnpcrorw5:oracleidentitycloudservice/john.doe@acme.com
.
O X-Storage-Pass
é o token de autenticação gerado.
Exemplo:
-
Inicialize as variáveis de ambiente necessárias a seguir.
user='<username>' password='<password>' region='<oci-region>' tenancy_namespace='<tenancy-namespace>' bucket_name='tutorial-bucket' object_name='sample.txt'
-
Gerar um token.
curl -sS -D swift_headers.txt https://swiftobjectstorage.eu-frankfurt-1.oraclecloud.com/auth/v1.0 -H "X-Storage-User: ${tenancy_namespace}:${user}" -H "X-Storage-Pass: ${password}" X_Auth_Token=$(cat swift_headers.txt | grep X-Auth-Token | cut -d":" -f 2)
-
Liste buckets na conta; somente buckets dos compartimentos selecionados da API Swift do OCI serão listados.
curl -s -D /dev/stderr "https://swiftobjectstorage.${region}.oraclecloud.com/v1/${tenancy_namespace}" -H "X-Auth-Token: ${X_Auth_Token}" | jq
-
Criar um bucket.
curl -s -i "https://swiftobjectstorage.${region}.oraclecloud.com/v1/${tenancy_namespace}/${bucket_name}" -X PUT -H "X-Auth-Token: ${X_Auth_Token}"
-
Faça upload de um arquivo para o bucket.
echo 'sample file' > ${object_name} curl -s -i "https://swiftobjectstorage.${region}.oraclecloud.com/v1/${tenancy_namespace}/${bucket_name}/${object_name}" -X PUT --data-binary "@${object_name}" -H "X-Auth-Token: ${X_Auth_Token}"
-
Liste o conteúdo do bucket.
curl -s -D /dev/stderr "https://swiftobjectstorage.${region}.oraclecloud.com/v1/${tenancy_namespace}/${bucket_name}" -H "X-Auth-Token: ${X_Auth_Token}" | jq
-
Extraia um arquivo do bucket.
curl -s -D /dev/stderr "https://swiftobjectstorage.${region}.oraclecloud.com/v1/${tenancy_namespace}/${bucket_name}/${object_name}" -H "X-Auth-Token: ${X_Auth_Token}" -o downloaded_file.txt cat downloaded_file.txt
-
Exclua o arquivo do bucket.
curl -s -i "https://swiftobjectstorage.${region}.oraclecloud.com/v1/${tenancy_namespace}/${bucket_name}/${object_name}" -X DELETE -H "X-Auth-Token: ${X_Auth_Token}"
-
Exclua o bucket.
curl -s -i "https://swiftobjectstorage.${region}.oraclecloud.com/v1/${tenancy_namespace}/${bucket_name}" -X DELETE -H "X-Auth-Token: ${X_Auth_Token}"
Abordagem 3: Autenticação Baseada em Token usando a Autenticação v2
Para ilustrar o procedimento de autorização v2 da API OCI Swift, usaremos o pacote oficial OpenStack Swift API Python python-swiftclient 4.5.0 e as dependências necessárias para a autenticação v2 python-keystoneclient 5.4.0.
Exemplo:
-
Execute o comando a seguir para garantir que você tenha acesso a uma versão do Python acima de
3.6
. Para obter mais informações, consulte Download do Python.python3 --version
-
Instale os módulos Python obrigatórios.
python3 -m pip install python-swiftclient python-keystoneclient click
-
Você pode usar o código a seguir para interagir com a API Swift da OCI v2. Certifique-se de substituir os placeholders para
<user>
,<password>
,<region>
e<tenancy-namespace>
no código a seguir antes de executar.import click import os from swiftclient.client import Connection from swiftclient.exceptions import ClientException user='<username>' password='<password>' region='<oci-region>' tenancy_namespace='<tenancy-namespace>' bucket_name='tutorial-bucket' object_name='sample.txt' _authurl = f'https://swiftobjectstorage.{region}.oraclecloud.com/auth/v2.0/' _auth_version = '2' _user = f'{user}' _key = f'{password}' _tenant_name = f'{tenancy_namespace}' conn = Connection( authurl=_authurl, user=_user, key=_key, tenant_name=_tenant_name, auth_version=_auth_version ) @click.group(invoke_without_command=True) @click.pass_context def main(ctx): available_commands = { "a": ("List buckets in the account", get_account), "b": ("Create a new bucket", put_container), "c": ("Upload an object to the bucket", put_object), "d": ("List objects in the bucket", get_container), "e": ("Download object from the bucket", get_object), "f": ("Delete object from the bucket", delete_object), "g": ("Delete bucket from the account", delete_container) } while True: click.echo("Available actions") for index, command in available_commands.items(): click.echo(f"{index} - {command[0]}") action = click.prompt("Please select an option from the list") if action in available_commands.keys(): ctx.invoke(available_commands[action][1]) print("###"*10) @main.command() def get_account(conn=conn): print("Listing buckets in the account.") try: resp_headers = conn.get_account() for entry in resp_headers[1]: print(entry["name"]) except ClientException as e: print(f"Failed to get the buckets in the tenancy. Error: {e}") raise else: print(f"Successfuly listed bucket in the '{_tenant_name}' account.") @main.command() def put_container(conn=conn, bucket_name=bucket_name): print(f"Creating a new bucket named {bucket_name}.") try: resp_headers = conn.put_container(container=bucket_name) except ClientException as e: print(f"Failed to create the new bucket named {bucket_name} in the tenancy. Error: {e}") raise else: print(f"The '{bucket_name}' was successfuly created.") @main.command() def put_object(conn=conn, bucket_name=bucket_name, object_name=object_name): print(f"Uploading a new file, '{object_name}' to the new bucket '{bucket_name}'.") try: if not os.path.isfile(object_name): with open(object_name, "w") as f: f.write("sample file") with open(object_name) as f: resp_headers = conn.put_object(container=bucket_name, obj=object_name, contents=object_name) except ClientException as e: print(f"Failed to create a new object named '{object_name}' in the bucket '{bucket_name}'. Error: {e}") raise else: print(f"The '{object_name}' file was successfuly uploaded to '{bucket_name}' bucket.") @main.command() def get_container(conn=conn, bucket_name=bucket_name): print(f"List {bucket_name} bucket contents.") try: resp_headers = conn.get_container(container=bucket_name) for entry in resp_headers[1]: print(entry["name"]) except ClientException as e: print(f"Failed to list objects in the bucket {bucket_name}. Error: {e}") raise else: print(f"The '{bucket_name}' content was successfuly listed.") @main.command() def get_object(conn=conn, bucket_name=bucket_name, object_name=object_name, dest_file="downloaded_file.txt"): print(f"Fetch {object_name} object from the bucket {bucket_name}.") try: resp_headers = conn.get_object(container=bucket_name, obj=object_name) with open(dest_file, "wb") as f: f.write(resp_headers[1]) except ClientException as e: print(f"Failed to download {object_name} from {bucket_name} to local file named '{dest_file}'. Error: {e}") raise else: print(f"The '{object_name}' object was saved locally to '{dest_file}'.") @main.command() def delete_object(conn=conn, bucket_name=bucket_name, object_name=object_name): print(f"Deleting {object_name} object from the bucket {bucket_name}.") try: resp_headers = conn.delete_object(container=bucket_name, obj=object_name) except ClientException as e: print(f"Failed to delete {object_name} from {bucket_name}. Error: {e}") raise else: print(f"The '{object_name}' object was deleted.") @main.command() def delete_container(conn=conn, bucket_name=bucket_name): print(f"Deleting the bucket {bucket_name}.") try: resp_headers = conn.delete_container(container=bucket_name) except ClientException as e: print(f"Failed to delete {object_name} from {bucket_name}. Error: {e}") raise else: print(f"The '{bucket_name}' bucket was deleted.") if __name__ == "__main__": main()
Links Relacionados
Confirmações
- Autor - Andrei Ilas (Arquiteto de Nuvem Principal)
Mais Recursos de Aprendizagem
Explore outros laboratórios em docs.oracle.com/learn ou acesse mais conteúdo de aprendizado gratuito no canal Oracle Learning YouTube. Além disso, visite education.oracle.com/learning-explorer para se tornar um Oracle Learning Explorer.
Para obter a documentação do produto, visite o Oracle Help Center.
Use Oracle Cloud Infrastructure Object Storage Service with OpenStack Swift API
F95068-01
March 2024