Gemini API を使用して構造化出力(JSON や列挙型など)を生成する

Gemini API はデフォルトで非構造化テキストとしてレスポンスを返します。ただし、JSON などの構造化テキストが必要なユースケースもあります。たとえば、確立されたデータ スキーマを必要とする他のダウンストリーム タスクでレスポンスを使用している場合があります。

モデルの生成済み出力が常に特定のスキーマに準拠するようにするには、レスポンス スキーマを定義します。これは、モデルのレスポンスのブループリントのように機能します。その後、後処理を減らしてモデルの出力からデータを直接抽出できます。

次に例を示します。

  • モデルのレスポンスが有効な JSON を生成し、指定されたスキーマに準拠していることを確認します。
    たとえば、このモデルは、レシピ名、材料のリスト、手順が常に含まれるレシピの構造化エントリを生成できます。これにより、この情報をより簡単に解析してアプリの UI に表示できます。

  • 分類タスク中にモデルが応答できる方法を制限する。
    たとえば、モデルが生成したラベル(goodpositivenegativebad など、ある程度のばらつきがある可能性がある)ではなく、特定のラベルセット(positivenegative などの特定の列挙型セットなど)でテキストにアノテーションを付けるようにモデルに指示できます。

このガイドでは、generateContent の呼び出しで responseSchema を指定して JSON 出力を生成する方法について説明します。テキストのみの入力に重点を置いていますが、Gemini は、画像、動画、音声を入力として含むマルチモーダル リクエストに対して構造化レスポンスを生成することもできます。

このページの下部には、列挙型の値を出力として生成する方法など、その他の例があります。構造化出力を生成する方法の追加例については、Google Cloud ドキュメントのスキーマとモデル レスポンスの例のリストをご覧ください。

始める前に

まだ行っていない場合は、スタートガイドを完了してください。Firebase プロジェクトの設定、アプリの Firebase への接続、SDK の追加、Vertex AI サービスの初期化、GenerativeModel インスタンスの作成方法が記載されています。

ステップ 1: レスポンス スキーマを定義する

レスポンス スキーマを定義して、モデルの出力の構造、フィールド名、各フィールドの想定されるデータ型を指定します。

モデルがレスポンスを生成するときは、プロンプトからフィールド名とコンテキストを使用します。意図が明確になるように、明確な構造、曖昧さのないフィールド名、必要に応じて説明を使用することをおすすめします。

レスポンス スキーマに関する考慮事項

レスポンス スキーマを作成する際は、次の点に注意してください。

  • レスポンス スキーマのサイズは、入力トークン制限にカウントされます。

  • レスポンス スキーマ機能は、次のレスポンス MIME タイプをサポートしています。

    • application/json: レスポンス スキーマで定義されている JSON を出力します(構造化出力要件に役立ちます)。

    • text/x.enum: レスポンス スキーマで定義されている列挙型の値を出力します(分類タスクに役立ちます)。

  • レスポンス スキーマ機能は、次のスキーマ フィールドをサポートしています。

    enum
    items
    maxItems
    nullable
    properties
    required

    サポートされていないフィールドを使用した場合でも、モデルはリクエストを処理できますが、そのフィールドは無視されます。上記のリストは、OpenAPI 3.0 スキーマ オブジェクトのサブセットです(Vertex AI スキーマ リファレンスをご覧ください)。

  • デフォルトでは、Vertex AI in Firebase SDK では、optionalProperties 配列で省略可能として指定しない限り、すべてのフィールドが必須と見なされます。これらの省略可能なフィールドの場合、モデルはフィールドにデータを入力することも、フィールドをスキップすることもできます。

    これは、Vertex AI Gemini API のデフォルトの動作とは逆です。

ステップ 2: レスポンス スキーマを含むプロンプトを送信して JSON を生成する

次の例は、構造化 JSON 出力を生成する方法を示しています。

GenerativeModel インスタンスを作成するときに、適切な responseMimeType(この例では application/json)と、モデルで使用する responseSchema を指定します。

Swift

import FirebaseVertexAI

// Provide a JSON schema object using a standard format.
// Later, pass this schema object into `responseSchema` in the generation config.
let jsonSchema = Schema.object(
  properties: [
    "characters": Schema.array(
      items: .object(
        properties: [
          "name": .string(),
          "age": .integer(),
          "species": .string(),
          "accessory": .enumeration(values: ["hat", "belt", "shoes"]),
        ],
        optionalProperties: ["accessory"]
      )
    ),
  ]
)

// Initialize the Vertex AI service and the generative model.
let model = VertexAI.vertexAI().generativeModel(
  modelName: "gemini-2.0-flash",
  // In the generation config, set the `responseMimeType` to `application/json`
  // and pass the JSON schema object into `responseSchema`.
  generationConfig: GenerationConfig(
    responseMIMEType: "application/json",
    responseSchema: jsonSchema
  )
)

let prompt = "For use in a children's card game, generate 10 animal-based characters."

let response = try await model.generateContent(prompt)
print(response.text ?? "No text in response.")

Kotlin

Kotlin の場合、この SDK のメソッドは suspend 関数であり、Coroutine スコープから呼び出す必要があります。
// Provide a JSON schema object using a standard format.
// Later, pass this schema object into `responseSchema` in the generation config.
val jsonSchema = Schema.obj(
    mapOf("characters" to Schema.array(
        Schema.obj(
            mapOf(
                "name" to Schema.string(),
                "age" to Schema.integer(),
                "species" to Schema.string(),
                "accessory" to Schema.enumeration(listOf("hat", "belt", "shoes")),
            ),
            optionalProperties = listOf("accessory")
        )
    ))
)

// Initialize the Vertex AI service and the generative model.
val generativeModel = Firebase.vertexAI.generativeModel(
    modelName = "gemini-2.0-flash",
    // In the generation config, set the `responseMimeType` to `application/json`
    // and pass the JSON schema object into `responseSchema`.
    generationConfig = generationConfig {
        responseMimeType = "application/json"
        responseSchema = jsonSchema
    })

val prompt = "For use in a children's card game, generate 10 animal-based characters."
val response = generativeModel.generateContent(prompt)
print(response.text)

Java

Java の場合、この SDK のストリーミング メソッドは Reactive Streams ライブラリPublisher 型を返します。
// Provide a JSON schema object using a standard format.
// Later, pass this schema object into `responseSchema` in the generation config.
Schema jsonSchema = Schema.obj(
        /* properties */
        Map.of(
                "characters", Schema.array(
                        /* items */ Schema.obj(
                                /* properties */
                                Map.of("name", Schema.str(),
                                        "age", Schema.numInt(),
                                        "species", Schema.str(),
                                        "accessory",
                                        Schema.enumeration(
                                                List.of("hat", "belt", "shoes")))
                        ))),
        List.of("accessory"));

// In the generation config, set the `responseMimeType` to `application/json`
// and pass the JSON schema object into `responseSchema`.
GenerationConfig.Builder configBuilder = new GenerationConfig.Builder();
configBuilder.responseMimeType = "application/json";
configBuilder.responseSchema = jsonSchema;

GenerationConfig generationConfig = configBuilder.build();

// Initialize the Vertex AI service and the generative model.
GenerativeModel gm = FirebaseVertexAI.getInstance().generativeModel(
  /* modelName */ "gemini-2.0-flash",
  /* generationConfig */ generationConfig);
GenerativeModelFutures model = GenerativeModelFutures.from(gm);

Content content = new Content.Builder()
    .addText("For use in a children's card game, generate 10 animal-based characters.")
    .build();

// For illustrative purposes only. You should use an executor that fits your needs.
Executor executor = Executors.newSingleThreadExecutor();

ListenableFuture<GenerateContentResponse> response = model.generateContent(content);
Futures.addCallback(
    response,
    new FutureCallback<GenerateContentResponse>() {
      @Override
      public void onSuccess(GenerateContentResponse result) {
        String resultText = result.getText();
        System.out.println(resultText);
      }

      @Override
      public void onFailure(Throwable t) {
        t.printStackTrace();
      }
    },
    executor);

Web

import { initializeApp } from "firebase/app";
import { getVertexAI, getGenerativeModel, Schema } from "firebase/vertexai";

// TODO(developer) Replace the following with your app's Firebase configuration.
// See: https://firebase.google.com/docs/web/learn-more#config-object
const firebaseConfig = {
  // ...
};

// Initialize FirebaseApp
const firebaseApp = initializeApp(firebaseConfig);

// Initialize the Vertex AI service.
const vertexAI = getVertexAI(firebaseApp);

// Provide a JSON schema object using a standard format.
// Later, pass this schema object into `responseSchema` in the generation config.
const jsonSchema = Schema.object({
 properties: {
    characters: Schema.array({
      items: Schema.object({
        properties: {
          name: Schema.string(),
          accessory: Schema.string(),
          age: Schema.number(),
          species: Schema.string(),
        },
        optionalProperties: ["accessory"],
      }),
    }),
  }
});

// Initialize the generative model.
const model = getGenerativeModel(vertexAI, {
  model: "gemini-2.0-flash",
  // In the generation config, set the `responseMimeType` to `application/json`
  // and pass the JSON schema object into `responseSchema`.
  generationConfig: {
    responseMimeType: "application/json",
    responseSchema: jsonSchema
  },
});


let prompt = "For use in a children's card game, generate 10 animal-based characters.";

let result = await model.generateContent(prompt)
console.log(result.response.text());

Dart

import 'package:firebase_vertexai/firebase_vertexai.dart';
import 'package:firebase_core/firebase_core.dart';

// Provide a JSON schema object using a standard format.
// Later, pass this schema object into `responseSchema` in the generation config.
final jsonSchema = Schema.object(
        properties: {
          'characters': Schema.array(
            items: Schema.object(
              properties: {
                'name': Schema.string(),
                'age': Schema.integer(),
                'species': Schema.string(),
                'accessory':
                    Schema.enumString(enumValues: ['hat', 'belt', 'shoes']),
              },
            ),
          ),
        },
        optionalProperties: ['accessory'],
      );

await Firebase.initializeApp();
// Initialize the Vertex AI service and the generative model.
final model =
      FirebaseVertexAI.instance.generativeModel(
        model: 'gemini-2.0-flash',
        // In the generation config, set the `responseMimeType` to `application/json`
        // and pass the JSON schema object into `responseSchema`.
        generationConfig: GenerationConfig(
            responseMimeType: 'application/json', responseSchema: jsonSchema));

final prompt = "For use in a children's card game, generate 10 animal-based characters.";
final response = await model.generateContent([Content.text(prompt)]);
print(response.text);

ユースケースとアプリに適したモデルと、必要に応じてロケーションを選択する方法を学びます。

その他の例

構造化出力の使用方法と生成方法のその他の例については、Google Cloud ドキュメントのスキーマとモデル レスポンスの例をご覧ください。

列挙型の値を出力として生成する

次の例は、分類タスクにレスポンス スキーマを使用する方法を示しています。モデルは、説明に基づいて映画のジャンルを特定するように求められます。出力は、指定されたレスポンス スキーマで定義された値のリストからモデルが選択した書式なしテキストの列挙型値です。

この構造化分類タスクを実行するには、モデルの初期化時に適切な responseMimeType(この例では text/x.enum)と、モデルで使用する responseSchema を指定する必要があります。

Swift

import FirebaseVertexAI

// Provide an enum schema object using a standard format.
// Later, pass this schema object into `responseSchema` in the generation config.
let enumSchema = Schema.enumeration(values: ["drama", "comedy", "documentary"])

// Initialize the Vertex AI service and the generative model.
let model = VertexAI.vertexAI().generativeModel(
  modelName: "gemini-2.0-flash",
  // In the generation config, set the `responseMimeType` to `text/x.enum`
  // and pass the enum schema object into `responseSchema`.
  generationConfig: GenerationConfig(
    responseMIMEType: "text/x.enum",
    responseSchema: enumSchema
  )
)

let prompt = """
The film aims to educate and inform viewers about real-life subjects, events, or people.
It offers a factual record of a particular topic by combining interviews, historical footage,
and narration. The primary purpose of a film is to present information and provide insights
into various aspects of reality.
"""

let response = try await model.generateContent(prompt)
print(response.text ?? "No text in response.")

Kotlin

Kotlin の場合、この SDK のメソッドは suspend 関数であり、Coroutine スコープから呼び出す必要があります。
// Provide an enum schema object using a standard format.
// Later, pass this schema object into `responseSchema` in the generation config.
val enumSchema = Schema.enumeration(listOf("drama", "comedy", "documentary"))

// Initialize the Vertex AI service and the generative model.
val generativeModel = Firebase.vertexAI.generativeModel(
    modelName = "gemini-2.0-flash",
    // In the generation config, set the `responseMimeType` to `text/x.enum`
    // and pass the enum schema object into `responseSchema`.
    generationConfig = generationConfig {
        responseMimeType = "text/x.enum"
        responseSchema = enumSchema
    })

val prompt = """
    The film aims to educate and inform viewers about real-life subjects, events, or people.
    It offers a factual record of a particular topic by combining interviews, historical footage, 
    and narration. The primary purpose of a film is to present information and provide insights 
    into various aspects of reality.
    """
val response = generativeModel.generateContent(prompt)
print(response.text)

Java

Java の場合、この SDK のストリーミング メソッドは Reactive Streams ライブラリPublisher 型を返します。
// Provide an enum schema object using a standard format.
// Later, pass this schema object into `responseSchema` in the generation config.
Schema enumSchema = Schema.enumeration(List.of("drama", "comedy", "documentary"));

// In the generation config, set the `responseMimeType` to `text/x.enum`
// and pass the enum schema object into `responseSchema`.
GenerationConfig.Builder configBuilder = new GenerationConfig.Builder();
configBuilder.responseMimeType = "text/x.enum";
configBuilder.responseSchema = enumSchema;

GenerationConfig generationConfig = configBuilder.build();

// Initialize the Vertex AI service and the generative model.
GenerativeModel gm = FirebaseVertexAI.getInstance().generativeModel(
  /* modelName */ "gemini-2.0-flash",
  /* generationConfig */ generationConfig);
GenerativeModelFutures model = GenerativeModelFutures.from(gm);

String prompt = "The film aims to educate and inform viewers about real-life subjects," +
                " events, or people. It offers a factual record of a particular topic by" +
                " combining interviews, historical footage, and narration. The primary purpose" +
                " of a film is to present information and provide insights into various aspects" +
                " of reality.";

Content content = new Content.Builder().addText(prompt).build();

// For illustrative purposes only. You should use an executor that fits your needs.
Executor executor = Executors.newSingleThreadExecutor();

ListenableFuture<GenerateContentResponse> response = model.generateContent(content);
Futures.addCallback(
    response,
    new FutureCallback<GenerateContentResponse>() {
      @Override
      public void onSuccess(GenerateContentResponse result) {
        String resultText = result.getText();
        System.out.println(resultText);
      }

      @Override
      public void onFailure(Throwable t) {
        t.printStackTrace();
      }
    },
    executor);

Web

import { initializeApp } from "firebase/app";
import { getVertexAI, getGenerativeModel, Schema } from "firebase/vertexai";

// TODO(developer) Replace the following with your app's Firebase configuration.
// See: https://firebase.google.com/docs/web/learn-more#config-object
const firebaseConfig = {
 // ...
};

// Initialize FirebaseApp
const firebaseApp = initializeApp(firebaseConfig);

// Initialize the Vertex AI service.
const vertexAI = getVertexAI(firebaseApp);

// Provide an enum schema object using a standard format.
// Later, pass this schema object into `responseSchema` in the generation config.
const enumSchema = Schema.enumString({
  enum: ["drama", "comedy", "documentary"],
});

// Initialize the generative model.
const model = getGenerativeModel(vertexAI, {
  model: "gemini-2.0-flash",
  // In the generation config, set the `responseMimeType` to `text/x.enum`
  // and pass the JSON schema object into `responseSchema`.
  generationConfig: {
    responseMimeType: "text/x.enum",
    responseSchema: enumSchema,
  },
});

let prompt = `The film aims to educate and inform viewers about real-life
subjects, events, or people. It offers a factual record of a particular topic
by combining interviews, historical footage, and narration. The primary purpose
of a film is to present information and provide insights into various aspects
of reality.`;

let result = await model.generateContent(prompt);
console.log(result.response.text());

Dart

import 'package:firebase_vertexai/firebase_vertexai.dart';
import 'package:firebase_core/firebase_core.dart';

// Provide an enum schema object using a standard format.
// Later, pass this schema object into `responseSchema` in the generation config.
final enumSchema = Schema.enumString(enumValues: ['drama', 'comedy', 'documentary']);

await Firebase.initializeApp();
// Initialize the Vertex AI service and the generative model.
final model =
      FirebaseVertexAI.instance.generativeModel(
        model: 'gemini-2.0-flash',
        // In the generation config, set the `responseMimeType` to `text/x.enum`
        // and pass the enum schema object into `responseSchema`.
        generationConfig: GenerationConfig(
            responseMimeType: 'text/x.enum', responseSchema: enumSchema));

final prompt = """
      The film aims to educate and inform viewers about real-life subjects, events, or people.
      It offers a factual record of a particular topic by combining interviews, historical footage, 
      and narration. The primary purpose of a film is to present information and provide insights
      into various aspects of reality.
      """;
final response = await model.generateContent([Content.text(prompt)]);
print(response.text);

ユースケースとアプリに適したモデルと、必要に応じてロケーションを選択する方法を学びます。

コンテンツ生成を制御するためのその他のオプション

  • プロンプトの設計について学び、ニーズに固有の出力を生成するようにモデルに影響を与えましょう。
  • モデル パラメータを構成して、モデルがどのようにレスポンスを生成するかを制御します。Gemini モデルの場合、これらのパラメータには、最大出力トークン、温度、topK、topP が含まれます。Imagen モデルの場合、アスペクト比、人物の生成、ウォーターマークなどがあります。
  • 安全性設定を使用して、ヘイトスピーチや性的描写が露骨なコンテンツなど、有害と見なされる回答が生成される可能性を調整します。
  • システム指示を設定して、モデルの動作を制御します。この機能は、エンドユーザーからの詳細な手順を示すためにモデルが公開される前に追加する「プリアンブル」のようなものです。


Vertex AI in Firebase の使用感に関するフィードバックを送信する