Skip to content

[Bug]: websearch enterprise setting defaults to false and cannot be changed #2520

@Maimikuru

Description

@Maimikuru

What happened?

When creating a websearch engine, if the enterprise setting is not explicitly specified, it defaults to false. I believe this is a bug. There is no way for applications to change the enterprise setting.
Expected behavior: Either make the default configurable or provide an API/interface for applications to change this setting.
Reproduction steps: When creating a new websearch engine, the enterprise setting is observed to be fixed to false. Attempts to change it from the application side fail because there is no settings UI.

 /**
 * Google Cloud Discovery Engine - Bug Reproduction Code (Without Enterprise Edition Setting)
 *
 * Issue: When searchTier is not set during engine creation, the engine is created as Standard Edition,
 * but when trying to use Enterprise Edition features (extractiveContentSpec, returnSnippet),
 * an error occurs. However, the behavior when searchTier is not explicitly set during engine creation
 * may be inconsistent.
 */

import { DataStoreServiceClient, EngineServiceClient, protos } from '@google-cloud/discoveryengine'
import { GoogleAuth } from 'google-auth-library'

// Configuration
const PROJECT_ID = 'your-project-id'
const LOCATION = 'global'
const COLLECTION_ID = 'default_collection'
const DATA_STORE_ID = 'test-datastore-bug-reproduction'
const ENGINE_ID = 'test-engine-bug-reproduction'

async function reproduceBug() {
  const auth = new GoogleAuth({
    scopes: 'https://www.googleapis.com/auth/cloud-platform',
  })

  const client = await auth.getClient()
  const credentials = await auth.getCredentials()

  const dataStoreClient = new DataStoreServiceClient({
    credentials: credentials as any,
  })

  const engineClient = new EngineServiceClient({
    credentials: credentials as any,
  })

  const parentCollection = `projects/${PROJECT_ID}/locations/${LOCATION}/collections/${COLLECTION_ID}`
  const parentDataStores = `${parentCollection}/dataStores`
  const dataStoreName = `${parentDataStores}/${DATA_STORE_ID}`
  const engineName = `${parentCollection}/engines/${ENGINE_ID}`

  try {
    // Step 1: Create DataStore
    try {
      const [op] = await dataStoreClient.createDataStore({
        dataStore: {
          contentConfig:
            protos.google.cloud.discoveryengine.v1.DataStore.ContentConfig.PUBLIC_WEBSITE,
          displayName: 'Bug Reproduction DataStore',
          industryVertical: protos.google.cloud.discoveryengine.v1.IndustryVertical.GENERIC,
          solutionTypes: [protos.google.cloud.discoveryengine.v1.SolutionType.SOLUTION_TYPE_SEARCH],
        },
        dataStoreId: DATA_STORE_ID,
        parent: parentCollection,
      })
      await op.promise()
    } catch (error: any) {
      if (error.code !== 6) {
        throw error
      }
    }

    // Step 2: Create Engine without searchTier (should default to Standard Edition)
    try {
      const [op] = await engineClient.createEngine({
        engine: {
          dataStoreIds: [DATA_STORE_ID],
          displayName: 'Bug Reproduction Engine (No Enterprise Setting)',
          // Do not explicitly set searchTier (default should be Standard Edition)
          searchEngineConfig: {},
          solutionType: protos.google.cloud.discoveryengine.v1.SolutionType.SOLUTION_TYPE_SEARCH,
        },
        engineId: ENGINE_ID,
        parent: parentCollection,
      })
      await op.promise()
    } catch (error: any) {
      if (error.code !== 6) {
        throw error
      }
    }

    // Step 3: Verify Engine Configuration
    const [engine] = await engineClient.getEngine({ name: engineName })
    const searchTier = engine.searchEngineConfig?.searchTier
    console.log('Engine searchTier:', searchTier)
    console.log('Expected: SEARCH_TIER_STANDARD (1) or SEARCH_TIER_UNSPECIFIED (0)')

    // Step 4: Execute Search with Enterprise Edition Features
    const token = await client.getAccessToken()

    // Request including Enterprise Edition features
    const searchRequest = {
      contentSearchSpec: {
        extractiveContentSpec: {
          maxExtractiveAnswerCount: 1,
        },
        snippetSpec: {
          returnSnippet: true,
        },
      },
      pageSize: 10,
      query: 'test query',
      queryExpansionSpec: {
        condition: 'AUTO',
      },
      spellCorrectionSpec: {
        mode: 'AUTO',
      },
    }

    const searchUrl = `https://discoveryengine.googleapis.com/v1alpha/projects/${PROJECT_ID}/locations/${LOCATION}/collections/${COLLECTION_ID}/engines/${ENGINE_ID}/servingConfigs/default_search:search`

    const response = await fetch(searchUrl, {
      body: JSON.stringify(searchRequest),
      headers: {
        Authorization: `Bearer ${token.token}`,
        'Content-Type': 'application/json',
      },
      method: 'POST',
    })

    const responseText = await response.text()

    if (response.ok) {
      console.log('\n=== Unexpected Behavior ===')
      console.log(
        'Enterprise Edition features were usable on an engine created as Standard Edition.',
      )
    } else {
      const errorData = JSON.parse(responseText)
      console.log('\n=== Error Occurred ===')
      console.log('Error code:', errorData.error?.code)
      console.log('Error message:', errorData.error?.message)

      if (
        errorData.error?.message?.includes('enterprise edition features') ||
        errorData.error?.message?.includes('standard edition')
      ) {
        console.log('\n=== Bug Confirmed ===')
        console.log('Issue: When searchTier is not set, the engine is created as Standard Edition,')
        console.log('but when trying to use Enterprise Edition features, an error occurs.')
      }
    }
  } catch (error) {
    console.error('Error during bug reproduction:', error)

    throw error
  }
}

// Execute
try {
  await reproduceBug()
} catch (error) {
  console.error('Failed to reproduce bug:', error)
  process.exit(1)
}

Relevant log output

Error: Vertex AI Search: Search API request failed: Vertex AI Search: Search API request failed: HTTP error! status: 400, response: {
[chatbot]   "error": {
[chatbot]     "code": 400,
[chatbot]     "message": "Cannot use enterprise edition features (website search, multi-modal search, extractive answers/segments, etc.) in a standard edition search engine. Please follow https://cloud.google.com/generative-ai-app-builder/docs/enterprise-edition#toggle-enterprise to enable Enterprise edition. Enterprise edition can be only enabled at the engine / app level. If the search request is against a data store, please update the serving config in the search request to use the engine/app ID instead, in the format of: \"projects/*/locations/*/collections/*/engines/*/servingConfigs/*\".",
[chatbot]     "status": "FAILED_PRECONDITION"
[chatbot]   }
[chatbot] }

Code of Conduct

  • I agree to follow this project's Code of Conduct

Metadata

Metadata

Assignees

Labels

No labels
No labels

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions