Creare e gestire schemi protobuf

Questo documento descrive come creare ed eseguire operazioni sui bundle di schemi.

In Bigtable, puoi utilizzare gli schemi di buffer di protocollo (protobuf) per eseguire query su singoli campi all'interno dei messaggi protobuf archiviati come byte nelle colonne. Per farlo, carica gli schemi in un bundle di schemi, una risorsa a livello di tabella che contiene uno o più schemi protobuf.

L'utilizzo dei bundle di schemi offre i seguenti vantaggi:

  • Risparmio di tempo e fatica: con i buffer di protocollo, definisci la struttura dei dati una sola volta in un file proto e poi utilizzi il codice sorgente generato per scrivere e leggere i dati.
  • Miglioramento della coerenza dei dati: utilizzando un file proto come unica fonte di verità, puoi assicurarti che tutte le applicazioni e i servizi utilizzino lo stesso modello dei dati.
  • Eliminazione della duplicazione dei dati: puoi utilizzare i buffer di protocollo tra i progetti definendo i tipi di messaggio nei file proto che si trovano al di fuori della codebase di un progetto specifico.

La procedura di utilizzo degli schemi in Bigtable inizia con i file proto. Un file proto è un file di testo in cui definisci la struttura dei dati. Utilizzi lo strumento del compilatore protobuf, chiamato anche protoc, per generare un set di descrittori del file protobuf, ovvero uno schema leggibile da una macchina del file proto. Utilizzi quindi questo set di descrittori per creare un bundle di schemi.

Per esempi di file proto e dei relativi set di descrittori, consulta Dati di esempio.

Il seguente diagramma mostra la procedura di utilizzo degli schemi in Bigtable:

Il processo di utilizzo degli schemi protobuf in Bigtable.
Figura 1. La procedura di utilizzo degli schemi protobuf in Bigtable (fai clic per ingrandire).

Puoi creare bundle di schemi utilizzando Google Cloud CLI. Dopo aver caricato un bundle di schemi in Bigtable, puoi eseguire query sui dati utilizzando il generatore di query di Bigtable Studio, GoogleSQL per Bigtable o le tabelle esterne di Bigtable in BigQuery.

Prima di iniziare

Se prevedi di utilizzare gcloud CLI, segui questi passaggi:

  1. Installa la Google Cloud CLI.
  2. Inizializza gcloud CLI:

    gcloud init
    

Ruoli obbligatori

Per ottenere le autorizzazioni necessarie per creare e gestire i bundle di schemi, chiedi all'amministratore di concederti il ruolo IAM Bigtable Admin (roles/bigtable.admin) nella tabella.

Questo ruolo predefinito contiene le autorizzazioni richieste da Bigtable per lavorare con i bundle di schemi. Per visualizzare le autorizzazioni esatte richieste, espandi la sezione Autorizzazioni obbligatorie:

Autorizzazioni obbligatorie

  • bigtable.schemaBundles.create
  • bigtable.schemaBundles.update
  • bigtable.schemaBundles.delete
  • bigtable.schemaBundles.get
  • bigtable.schemaBundles.list

Potresti anche ottenere queste autorizzazioni con ruoli personalizzati o altri ruoli predefiniti.

Per saperne di più sui ruoli e sulle autorizzazioni di Bigtable, consulta Controllo dell'accesso con IAM.

Generare un set di descrittori di file protobuf

Prima di poter creare un bundle di schemi, devi generare un set di descrittori dai file proto con lo strumento del compilatore protobuf.

  1. Per installare il compilatore, scarica il pacchetto e segui le istruzioni nel file README.
  2. Esegui il compilatore:

    protoc --proto_path=IMPORT_PATH --include_imports \
       --descriptor_set_out=DESCRIPTOR_OUTPUT_LOCATION PATH_TO_PROTO
    

    Sostituisci quanto segue:

    • IMPORT_PATH: la directory in cui il compilatore protoc cerca i file proto.
    • DESCRIPTOR_OUTPUT_LOCATION: la directory in cui il compilatore protoc salva il set di descrittori generato.
    • PATH_TO_PROTO: il percorso del file proto.

Ad esempio, per creare un set di descrittori denominato library.pb per il file library.proto nella directory corrente, puoi utilizzare il seguente comando:

protoc --include_imports --descriptor_set_out=library.pb
library.proto

Creare un bundle di schemi

gcloud

Per creare un bundle di schemi, utilizza il gcloud bigtable schema-bundles create comando:

gcloud bigtable schema-bundles create SCHEMA_BUNDLE_ID \
    --instance=INSTANCE_ID \
    --table=TABLE_ID \
    --proto-descriptors-file=PROTO_DESCRIPTORS_FILE

Sostituisci quanto segue:

  • SCHEMA_BUNDLE_ID: un ID univoco per il nuovo bundle di schemi che non può contenere il carattere punto ('.').
  • INSTANCE_ID: l'ID dell'istanza in cui creare il bundle di schemi.
  • TABLE_ID: l'ID della tabella in cui creare il bundle di schemi.
  • PROTO_DESCRIPTORS_FILE: il percorso del set di descrittori generato nel passaggio precedente.

Java

Per creare un bundle di schemi, utilizza il metodo createSchemaBundle:

Per scoprire come installare e utilizzare la libreria client per Bigtable, consulta Librerie client di Bigtable.

Per eseguire l'autenticazione in Bigtable, configura le Credenziali predefinite dell'applicazione. Per saperne di più, consulta Configura l'autenticazione per un ambiente di sviluppo locale.

try {
  InputStream in = getClass().getClassLoader().getResourceAsStream(PROTO_FILE_PATH);
  CreateSchemaBundleRequest request =
      CreateSchemaBundleRequest.of(tableId, schemaBundleId)
          .setProtoSchema(ByteString.readFrom(in));
  SchemaBundle schemaBundle = adminClient.createSchemaBundle(request);
  System.out.printf("Schema bundle: %s created successfully%n", schemaBundle.getId());
} catch (NotFoundException e) {
  System.err.println(
      "Failed to create a schema bundle from a non-existent table: " + e.getMessage());
} catch (IOException e) {
  throw new RuntimeException(e);
}

Visualizzare informazioni sui bundle di schemi

Prima di poter visualizzare le informazioni sui bundle di schemi, devi avere una tabella Bigtable con almeno un bundle di schemi. Puoi ottenere informazioni sui bundle di schemi in una tabella recuperando la definizione di un singolo bundle di schemi o elencando tutti i bundle di schemi in una tabella.

Recuperare la definizione del bundle di schemi

gcloud

Per ottenere i dettagli di un bundle di schemi, utilizza il gcloud bigtable schema-bundles describe comando:

gcloud bigtable schema-bundles describe SCHEMA_BUNDLE_ID \
    --instance=INSTANCE_ID \
    --table=TABLE_ID

Sostituisci quanto segue:

  • SCHEMA_BUNDLE_ID: l'ID del bundle di schemi.
  • INSTANCE_ID: l'ID dell'istanza.
  • TABLE_ID: l'ID della tabella.

Java

Per ottenere la definizione di un bundle di schemi, utilizza il metodo getSchemaBundle. Questo metodo restituisce un oggetto SchemaBundle che contiene la definizione dello schema.

L'esempio seguente mostra come ottenere un bundle di schemi e deserializzare il set di descrittori per stampare i contenuti dello schema:

Per scoprire come installare e utilizzare la libreria client per Bigtable, consulta Librerie client di Bigtable.

Per eseguire l'autenticazione in Bigtable, configura le Credenziali predefinite dell'applicazione. Per saperne di più, consulta Configura l'autenticazione per un ambiente di sviluppo locale.

SchemaBundle schemaBundle = null;
try {
  schemaBundle = adminClient.getSchemaBundle(tableId, schemaBundleId);
  // Deserialize and print the FileDescriptorSet
  DescriptorProtos.FileDescriptorSet fileDescriptorSet =
      DescriptorProtos.FileDescriptorSet.parseFrom(schemaBundle.getProtoSchema());

  System.out.println("--------- Deserialized FileDescriptorSet ---------");
  for (DescriptorProtos.FileDescriptorProto fileDescriptorProto :
      fileDescriptorSet.getFileList()) {
    System.out.println("File: " + fileDescriptorProto.getName());
    System.out.println("  Package: " + fileDescriptorProto.getPackage());
    for (DescriptorProtos.DescriptorProto messageType :
        fileDescriptorProto.getMessageTypeList()) {
      System.out.println("  Message: " + messageType.getName());
    }
  }
  System.out.println("--------------------------------------------------");
} catch (InvalidProtocolBufferException e) {
  System.err.println("Failed to parse FileDescriptorSet: " + e.getMessage());
} catch (NotFoundException e) {
  System.err.println(
      "Failed to retrieve metadata from a non-existent schema bundle: " + e.getMessage());
}

L'output è simile al seguente:

--------- Deserialized FileDescriptorSet ---------
File: my_schema.proto
Package: my_package
Message: MyMessage
--------------------------------------------------

Elencare i bundle di schemi in una tabella

gcloud

Per visualizzare un elenco dei bundle di schemi per una tabella, utilizza il gcloud bigtable schema-bundles list comando:

gcloud bigtable schema-bundles list \
    --instance=INSTANCE_ID \
    --table=TABLE_ID

Sostituisci quanto segue:

  • INSTANCE_ID: l'ID dell'istanza.
  • TABLE_ID: l'ID della tabella.

Java

Per visualizzare un elenco di tutti i bundle di schemi in una tabella, utilizza il metodo listSchemaBundles. Questo metodo restituisce un elenco di ID dei bundle di schemi.

L'esempio seguente mostra come elencare i bundle di schemi in una tabella:

Per scoprire come installare e utilizzare la libreria client per Bigtable, consulta Librerie client di Bigtable.

Per eseguire l'autenticazione in Bigtable, configura le Credenziali predefinite dell'applicazione. Per saperne di più, consulta Configura l'autenticazione per un ambiente di sviluppo locale.

List<String> schemaBundleIds = new ArrayList<>();
try {
  schemaBundleIds = adminClient.listSchemaBundles(tableId);
  for (String schemaBundleId : schemaBundleIds) {
    System.out.println(schemaBundleId);
  }
} catch (NotFoundException e) {
  System.err.println(
      "Failed to list schema bundles from a non-existent table: " + e.getMessage());
}

L'output è simile al seguente:

my-schema-bundle-1
my-schema-bundle-2

Aggiornare un bundle di schemi

Quando aggiorni un bundle di schemi, Bigtable verifica se il nuovo set di descrittori è compatibile con il precedente. Se non è compatibile, l'aggiornamento non riesce e viene visualizzato un errore FailedPrecondition. Ti consigliamo di riservare i numeri dei campi eliminati per impedirne il riutilizzo. Per saperne di più, consulta le best practice per i file proto nella documentazione di protobuf.

Se hai la certezza che le modifiche incompatibili siano sicure e vuoi forzare un aggiornamento, puoi utilizzare il flag --ignore-warnings con gcloud CLI.

gcloud

Per aggiornare un bundle di schemi in modo che utilizzi un set di descrittori diverso, utilizza il gcloud bigtable schema-bundles update comando:

gcloud bigtable schema-bundles update SCHEMA_BUNDLE_ID \
    --instance=INSTANCE_ID \
    --table=TABLE_ID \
    --proto-descriptors-file=PROTO_DESCRIPTORS_FILE

Sostituisci quanto segue:

  • SCHEMA_BUNDLE_ID: l'ID del bundle di schemi da aggiornare.
  • INSTANCE_ID: l'ID dell'istanza che contiene il bundle di schemi.
  • TABLE_ID: l'ID della tabella che contiene il bundle di schemi.
  • PROTO_DESCRIPTORS_FILE: il percorso del nuovo file del set di descrittori.

(Facoltativo) Per forzare l'aggiornamento anche se sono presenti modifiche incompatibili, aggiungi il flag --ignore-warnings al comando. Se una vista materializzata continua o una vista logica utilizza il bundle di schemi, non devi forzare le modifiche incompatibili.

Java

Per scoprire come installare e utilizzare la libreria client per Bigtable, consulta Librerie client di Bigtable.

Per eseguire l'autenticazione in Bigtable, configura le Credenziali predefinite dell'applicazione. Per saperne di più, consulta Configura l'autenticazione per un ambiente di sviluppo locale.

try {
  InputStream in = getClass().getClassLoader().getResourceAsStream(PROTO_FILE_PATH);
  UpdateSchemaBundleRequest request =
      UpdateSchemaBundleRequest.of(tableId, schemaBundleId)
          .setProtoSchema(ByteString.readFrom(in));
  SchemaBundle schemaBundle = adminClient.updateSchemaBundle(request);
  System.out.printf("Schema bundle: %s updated successfully%n", schemaBundle.getId());
} catch (NotFoundException e) {
  System.err.println("Failed to modify a non-existent schema bundle: " + e.getMessage());
} catch (IOException e) {
  throw new RuntimeException(e);
}

Eliminare un bundle di schemi

gcloud

Per eliminare un bundle di schemi, utilizza il gcloud bigtable schema-bundles delete comando:

gcloud bigtable schema-bundles delete SCHEMA_BUNDLE_ID \
    --instance=INSTANCE_ID \
    --table=TABLE_ID

Sostituisci quanto segue:

  • SCHEMA_BUNDLE_ID: l'ID del bundle di schemi da eliminare.
  • INSTANCE_ID: l'ID dell'istanza che contiene il bundle di schemi.
  • TABLE_ID: l'ID della tabella che contiene il bundle di schemi.

Se una vista materializzata continua o una vista logica utilizza il bundle di schemi, non eliminare il bundle.

Java

Per scoprire come installare e utilizzare la libreria client per Bigtable, consulta Librerie client di Bigtable.

Per eseguire l'autenticazione in Bigtable, configura le Credenziali predefinite dell'applicazione. Per saperne di più, consulta Configura l'autenticazione per un ambiente di sviluppo locale.

try {
  adminClient.deleteSchemaBundle(tableId, schemaBundleId);
  System.out.printf("SchemaBundle: %s deleted successfully%n", schemaBundleId);
} catch (NotFoundException e) {
  System.err.println("Failed to delete a non-existent schema bundle: " + e.getMessage());
}

Limitazioni

I bundle di schemi presentano le seguenti limitazioni:

  • Puoi creare un massimo di 10 bundle di schemi per tabella.
  • Le dimensioni totali dei descrittori di buffer di protocollo serializzati all'interno di un bundle di schemi non possono superare i 4 MB. Non esiste un limite diretto al numero di singoli schemi che puoi includere in un bundle, a condizione che le dimensioni totali del bundle non superino questo limite.
  • Se una vista materializzata continua o una vista logica utilizza il bundle di schemi, non devi forzare le modifiche incompatibili o eliminare il bundle.

Passaggi successivi