// Copyright 2024 Google LLC
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     https://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

// Code generated by protoc-gen-go_gapic. DO NOT EDIT.

package dataplex

import (
	"context"
	"fmt"
	"math"
	"net/url"
	"time"

	dataplexpb "cloud.google.com/go/dataplex/apiv1/dataplexpb"
	"cloud.google.com/go/longrunning"
	lroauto "cloud.google.com/go/longrunning/autogen"
	longrunningpb "cloud.google.com/go/longrunning/autogen/longrunningpb"
	gax "github.com/googleapis/gax-go/v2"
	"google.golang.org/api/iterator"
	"google.golang.org/api/option"
	"google.golang.org/api/option/internaloption"
	gtransport "google.golang.org/api/transport/grpc"
	locationpb "google.golang.org/genproto/googleapis/cloud/location"
	"google.golang.org/grpc"
	"google.golang.org/grpc/codes"
	"google.golang.org/protobuf/proto"
)

var newCatalogClientHook clientHook

// CatalogCallOptions contains the retry settings for each method of CatalogClient.
type CatalogCallOptions struct {
	CreateEntryType  []gax.CallOption
	UpdateEntryType  []gax.CallOption
	DeleteEntryType  []gax.CallOption
	ListEntryTypes   []gax.CallOption
	GetEntryType     []gax.CallOption
	CreateAspectType []gax.CallOption
	UpdateAspectType []gax.CallOption
	DeleteAspectType []gax.CallOption
	ListAspectTypes  []gax.CallOption
	GetAspectType    []gax.CallOption
	CreateEntryGroup []gax.CallOption
	UpdateEntryGroup []gax.CallOption
	DeleteEntryGroup []gax.CallOption
	ListEntryGroups  []gax.CallOption
	GetEntryGroup    []gax.CallOption
	CreateEntry      []gax.CallOption
	UpdateEntry      []gax.CallOption
	DeleteEntry      []gax.CallOption
	ListEntries      []gax.CallOption
	GetEntry         []gax.CallOption
	LookupEntry      []gax.CallOption
	SearchEntries    []gax.CallOption
	GetLocation      []gax.CallOption
	ListLocations    []gax.CallOption
	CancelOperation  []gax.CallOption
	DeleteOperation  []gax.CallOption
	GetOperation     []gax.CallOption
	ListOperations   []gax.CallOption
}

func defaultCatalogGRPCClientOptions() []option.ClientOption {
	return []option.ClientOption{
		internaloption.WithDefaultEndpoint("dataplex.googleapis.com:443"),
		internaloption.WithDefaultEndpointTemplate("dataplex.UNIVERSE_DOMAIN:443"),
		internaloption.WithDefaultMTLSEndpoint("dataplex.mtls.googleapis.com:443"),
		internaloption.WithDefaultUniverseDomain("googleapis.com"),
		internaloption.WithDefaultAudience("https://dataplex.googleapis.com/"),
		internaloption.WithDefaultScopes(DefaultAuthScopes()...),
		internaloption.EnableJwtWithScope(),
		option.WithGRPCDialOption(grpc.WithDefaultCallOptions(
			grpc.MaxCallRecvMsgSize(math.MaxInt32))),
	}
}

func defaultCatalogCallOptions() *CatalogCallOptions {
	return &CatalogCallOptions{
		CreateEntryType: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
		},
		UpdateEntryType: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
		},
		DeleteEntryType: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
		},
		ListEntryTypes: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
			gax.WithRetry(func() gax.Retryer {
				return gax.OnCodes([]codes.Code{
					codes.Unavailable,
					codes.ResourceExhausted,
				}, gax.Backoff{
					Initial:    1000 * time.Millisecond,
					Max:        10000 * time.Millisecond,
					Multiplier: 1.30,
				})
			}),
		},
		GetEntryType: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
			gax.WithRetry(func() gax.Retryer {
				return gax.OnCodes([]codes.Code{
					codes.Unavailable,
					codes.ResourceExhausted,
				}, gax.Backoff{
					Initial:    1000 * time.Millisecond,
					Max:        10000 * time.Millisecond,
					Multiplier: 1.30,
				})
			}),
		},
		CreateAspectType: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
		},
		UpdateAspectType: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
		},
		DeleteAspectType: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
		},
		ListAspectTypes: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
			gax.WithRetry(func() gax.Retryer {
				return gax.OnCodes([]codes.Code{
					codes.Unavailable,
					codes.ResourceExhausted,
				}, gax.Backoff{
					Initial:    1000 * time.Millisecond,
					Max:        10000 * time.Millisecond,
					Multiplier: 1.30,
				})
			}),
		},
		GetAspectType: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
			gax.WithRetry(func() gax.Retryer {
				return gax.OnCodes([]codes.Code{
					codes.Unavailable,
					codes.ResourceExhausted,
				}, gax.Backoff{
					Initial:    1000 * time.Millisecond,
					Max:        10000 * time.Millisecond,
					Multiplier: 1.30,
				})
			}),
		},
		CreateEntryGroup: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
		},
		UpdateEntryGroup: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
		},
		DeleteEntryGroup: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
		},
		ListEntryGroups: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
			gax.WithRetry(func() gax.Retryer {
				return gax.OnCodes([]codes.Code{
					codes.Unavailable,
					codes.ResourceExhausted,
				}, gax.Backoff{
					Initial:    1000 * time.Millisecond,
					Max:        10000 * time.Millisecond,
					Multiplier: 1.30,
				})
			}),
		},
		GetEntryGroup: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
			gax.WithRetry(func() gax.Retryer {
				return gax.OnCodes([]codes.Code{
					codes.Unavailable,
					codes.ResourceExhausted,
				}, gax.Backoff{
					Initial:    1000 * time.Millisecond,
					Max:        10000 * time.Millisecond,
					Multiplier: 1.30,
				})
			}),
		},
		CreateEntry: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
		},
		UpdateEntry: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
			gax.WithRetry(func() gax.Retryer {
				return gax.OnCodes([]codes.Code{
					codes.Unavailable,
					codes.ResourceExhausted,
				}, gax.Backoff{
					Initial:    1000 * time.Millisecond,
					Max:        10000 * time.Millisecond,
					Multiplier: 1.30,
				})
			}),
		},
		DeleteEntry: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
		},
		ListEntries: []gax.CallOption{
			gax.WithTimeout(20000 * time.Millisecond),
			gax.WithRetry(func() gax.Retryer {
				return gax.OnCodes([]codes.Code{
					codes.Unavailable,
					codes.ResourceExhausted,
				}, gax.Backoff{
					Initial:    1000 * time.Millisecond,
					Max:        10000 * time.Millisecond,
					Multiplier: 1.30,
				})
			}),
		},
		GetEntry: []gax.CallOption{
			gax.WithTimeout(20000 * time.Millisecond),
			gax.WithRetry(func() gax.Retryer {
				return gax.OnCodes([]codes.Code{
					codes.Unavailable,
					codes.ResourceExhausted,
				}, gax.Backoff{
					Initial:    1000 * time.Millisecond,
					Max:        10000 * time.Millisecond,
					Multiplier: 1.30,
				})
			}),
		},
		LookupEntry: []gax.CallOption{
			gax.WithTimeout(20000 * time.Millisecond),
			gax.WithRetry(func() gax.Retryer {
				return gax.OnCodes([]codes.Code{
					codes.Unavailable,
					codes.ResourceExhausted,
				}, gax.Backoff{
					Initial:    1000 * time.Millisecond,
					Max:        10000 * time.Millisecond,
					Multiplier: 1.30,
				})
			}),
		},
		SearchEntries: []gax.CallOption{
			gax.WithTimeout(60000 * time.Millisecond),
			gax.WithRetry(func() gax.Retryer {
				return gax.OnCodes([]codes.Code{
					codes.Unavailable,
					codes.ResourceExhausted,
				}, gax.Backoff{
					Initial:    1000 * time.Millisecond,
					Max:        10000 * time.Millisecond,
					Multiplier: 1.30,
				})
			}),
		},
		GetLocation:     []gax.CallOption{},
		ListLocations:   []gax.CallOption{},
		CancelOperation: []gax.CallOption{},
		DeleteOperation: []gax.CallOption{},
		GetOperation:    []gax.CallOption{},
		ListOperations:  []gax.CallOption{},
	}
}

// internalCatalogClient is an interface that defines the methods available from Cloud Dataplex API.
type internalCatalogClient interface {
	Close() error
	setGoogleClientInfo(...string)
	Connection() *grpc.ClientConn
	CreateEntryType(context.Context, *dataplexpb.CreateEntryTypeRequest, ...gax.CallOption) (*CreateEntryTypeOperation, error)
	CreateEntryTypeOperation(name string) *CreateEntryTypeOperation
	UpdateEntryType(context.Context, *dataplexpb.UpdateEntryTypeRequest, ...gax.CallOption) (*UpdateEntryTypeOperation, error)
	UpdateEntryTypeOperation(name string) *UpdateEntryTypeOperation
	DeleteEntryType(context.Context, *dataplexpb.DeleteEntryTypeRequest, ...gax.CallOption) (*DeleteEntryTypeOperation, error)
	DeleteEntryTypeOperation(name string) *DeleteEntryTypeOperation
	ListEntryTypes(context.Context, *dataplexpb.ListEntryTypesRequest, ...gax.CallOption) *EntryTypeIterator
	GetEntryType(context.Context, *dataplexpb.GetEntryTypeRequest, ...gax.CallOption) (*dataplexpb.EntryType, error)
	CreateAspectType(context.Context, *dataplexpb.CreateAspectTypeRequest, ...gax.CallOption) (*CreateAspectTypeOperation, error)
	CreateAspectTypeOperation(name string) *CreateAspectTypeOperation
	UpdateAspectType(context.Context, *dataplexpb.UpdateAspectTypeRequest, ...gax.CallOption) (*UpdateAspectTypeOperation, error)
	UpdateAspectTypeOperation(name string) *UpdateAspectTypeOperation
	DeleteAspectType(context.Context, *dataplexpb.DeleteAspectTypeRequest, ...gax.CallOption) (*DeleteAspectTypeOperation, error)
	DeleteAspectTypeOperation(name string) *DeleteAspectTypeOperation
	ListAspectTypes(context.Context, *dataplexpb.ListAspectTypesRequest, ...gax.CallOption) *AspectTypeIterator
	GetAspectType(context.Context, *dataplexpb.GetAspectTypeRequest, ...gax.CallOption) (*dataplexpb.AspectType, error)
	CreateEntryGroup(context.Context, *dataplexpb.CreateEntryGroupRequest, ...gax.CallOption) (*CreateEntryGroupOperation, error)
	CreateEntryGroupOperation(name string) *CreateEntryGroupOperation
	UpdateEntryGroup(context.Context, *dataplexpb.UpdateEntryGroupRequest, ...gax.CallOption) (*UpdateEntryGroupOperation, error)
	UpdateEntryGroupOperation(name string) *UpdateEntryGroupOperation
	DeleteEntryGroup(context.Context, *dataplexpb.DeleteEntryGroupRequest, ...gax.CallOption) (*DeleteEntryGroupOperation, error)
	DeleteEntryGroupOperation(name string) *DeleteEntryGroupOperation
	ListEntryGroups(context.Context, *dataplexpb.ListEntryGroupsRequest, ...gax.CallOption) *EntryGroupIterator
	GetEntryGroup(context.Context, *dataplexpb.GetEntryGroupRequest, ...gax.CallOption) (*dataplexpb.EntryGroup, error)
	CreateEntry(context.Context, *dataplexpb.CreateEntryRequest, ...gax.CallOption) (*dataplexpb.Entry, error)
	UpdateEntry(context.Context, *dataplexpb.UpdateEntryRequest, ...gax.CallOption) (*dataplexpb.Entry, error)
	DeleteEntry(context.Context, *dataplexpb.DeleteEntryRequest, ...gax.CallOption) (*dataplexpb.Entry, error)
	ListEntries(context.Context, *dataplexpb.ListEntriesRequest, ...gax.CallOption) *EntryIterator
	GetEntry(context.Context, *dataplexpb.GetEntryRequest, ...gax.CallOption) (*dataplexpb.Entry, error)
	LookupEntry(context.Context, *dataplexpb.LookupEntryRequest, ...gax.CallOption) (*dataplexpb.Entry, error)
	SearchEntries(context.Context, *dataplexpb.SearchEntriesRequest, ...gax.CallOption) *SearchEntriesResultIterator
	GetLocation(context.Context, *locationpb.GetLocationRequest, ...gax.CallOption) (*locationpb.Location, error)
	ListLocations(context.Context, *locationpb.ListLocationsRequest, ...gax.CallOption) *LocationIterator
	CancelOperation(context.Context, *longrunningpb.CancelOperationRequest, ...gax.CallOption) error
	DeleteOperation(context.Context, *longrunningpb.DeleteOperationRequest, ...gax.CallOption) error
	GetOperation(context.Context, *longrunningpb.GetOperationRequest, ...gax.CallOption) (*longrunningpb.Operation, error)
	ListOperations(context.Context, *longrunningpb.ListOperationsRequest, ...gax.CallOption) *OperationIterator
}

// CatalogClient is a client for interacting with Cloud Dataplex API.
// Methods, except Close, may be called concurrently. However, fields must not be modified concurrently with method calls.
//
// The primary resources offered by this service are EntryGroups, EntryTypes,
// AspectTypes, Entry and Aspect which collectively allow a data administrator
// to organize, manage, secure and catalog data across their organization
// located across cloud projects in a variety of storage systems including Cloud
// Storage and BigQuery.
type CatalogClient struct {
	// The internal transport-dependent client.
	internalClient internalCatalogClient

	// The call options for this service.
	CallOptions *CatalogCallOptions

	// LROClient is used internally to handle long-running operations.
	// It is exposed so that its CallOptions can be modified if required.
	// Users should not Close this client.
	LROClient *lroauto.OperationsClient
}

// Wrapper methods routed to the internal client.

// Close closes the connection to the API service. The user should invoke this when
// the client is no longer required.
func (c *CatalogClient) Close() error {
	return c.internalClient.Close()
}

// setGoogleClientInfo sets the name and version of the application in
// the `x-goog-api-client` header passed on each request. Intended for
// use by Google-written clients.
func (c *CatalogClient) setGoogleClientInfo(keyval ...string) {
	c.internalClient.setGoogleClientInfo(keyval...)
}

// Connection returns a connection to the API service.
//
// Deprecated: Connections are now pooled so this method does not always
// return the same resource.
func (c *CatalogClient) Connection() *grpc.ClientConn {
	return c.internalClient.Connection()
}

// CreateEntryType creates an EntryType
func (c *CatalogClient) CreateEntryType(ctx context.Context, req *dataplexpb.CreateEntryTypeRequest, opts ...gax.CallOption) (*CreateEntryTypeOperation, error) {
	return c.internalClient.CreateEntryType(ctx, req, opts...)
}

// CreateEntryTypeOperation returns a new CreateEntryTypeOperation from a given name.
// The name must be that of a previously created CreateEntryTypeOperation, possibly from a different process.
func (c *CatalogClient) CreateEntryTypeOperation(name string) *CreateEntryTypeOperation {
	return c.internalClient.CreateEntryTypeOperation(name)
}

// UpdateEntryType updates a EntryType resource.
func (c *CatalogClient) UpdateEntryType(ctx context.Context, req *dataplexpb.UpdateEntryTypeRequest, opts ...gax.CallOption) (*UpdateEntryTypeOperation, error) {
	return c.internalClient.UpdateEntryType(ctx, req, opts...)
}

// UpdateEntryTypeOperation returns a new UpdateEntryTypeOperation from a given name.
// The name must be that of a previously created UpdateEntryTypeOperation, possibly from a different process.
func (c *CatalogClient) UpdateEntryTypeOperation(name string) *UpdateEntryTypeOperation {
	return c.internalClient.UpdateEntryTypeOperation(name)
}

// DeleteEntryType deletes a EntryType resource.
func (c *CatalogClient) DeleteEntryType(ctx context.Context, req *dataplexpb.DeleteEntryTypeRequest, opts ...gax.CallOption) (*DeleteEntryTypeOperation, error) {
	return c.internalClient.DeleteEntryType(ctx, req, opts...)
}

// DeleteEntryTypeOperation returns a new DeleteEntryTypeOperation from a given name.
// The name must be that of a previously created DeleteEntryTypeOperation, possibly from a different process.
func (c *CatalogClient) DeleteEntryTypeOperation(name string) *DeleteEntryTypeOperation {
	return c.internalClient.DeleteEntryTypeOperation(name)
}

// ListEntryTypes lists EntryType resources in a project and location.
func (c *CatalogClient) ListEntryTypes(ctx context.Context, req *dataplexpb.ListEntryTypesRequest, opts ...gax.CallOption) *EntryTypeIterator {
	return c.internalClient.ListEntryTypes(ctx, req, opts...)
}

// GetEntryType retrieves a EntryType resource.
func (c *CatalogClient) GetEntryType(ctx context.Context, req *dataplexpb.GetEntryTypeRequest, opts ...gax.CallOption) (*dataplexpb.EntryType, error) {
	return c.internalClient.GetEntryType(ctx, req, opts...)
}

// CreateAspectType creates an AspectType
func (c *CatalogClient) CreateAspectType(ctx context.Context, req *dataplexpb.CreateAspectTypeRequest, opts ...gax.CallOption) (*CreateAspectTypeOperation, error) {
	return c.internalClient.CreateAspectType(ctx, req, opts...)
}

// CreateAspectTypeOperation returns a new CreateAspectTypeOperation from a given name.
// The name must be that of a previously created CreateAspectTypeOperation, possibly from a different process.
func (c *CatalogClient) CreateAspectTypeOperation(name string) *CreateAspectTypeOperation {
	return c.internalClient.CreateAspectTypeOperation(name)
}

// UpdateAspectType updates a AspectType resource.
func (c *CatalogClient) UpdateAspectType(ctx context.Context, req *dataplexpb.UpdateAspectTypeRequest, opts ...gax.CallOption) (*UpdateAspectTypeOperation, error) {
	return c.internalClient.UpdateAspectType(ctx, req, opts...)
}

// UpdateAspectTypeOperation returns a new UpdateAspectTypeOperation from a given name.
// The name must be that of a previously created UpdateAspectTypeOperation, possibly from a different process.
func (c *CatalogClient) UpdateAspectTypeOperation(name string) *UpdateAspectTypeOperation {
	return c.internalClient.UpdateAspectTypeOperation(name)
}

// DeleteAspectType deletes a AspectType resource.
func (c *CatalogClient) DeleteAspectType(ctx context.Context, req *dataplexpb.DeleteAspectTypeRequest, opts ...gax.CallOption) (*DeleteAspectTypeOperation, error) {
	return c.internalClient.DeleteAspectType(ctx, req, opts...)
}

// DeleteAspectTypeOperation returns a new DeleteAspectTypeOperation from a given name.
// The name must be that of a previously created DeleteAspectTypeOperation, possibly from a different process.
func (c *CatalogClient) DeleteAspectTypeOperation(name string) *DeleteAspectTypeOperation {
	return c.internalClient.DeleteAspectTypeOperation(name)
}

// ListAspectTypes lists AspectType resources in a project and location.
func (c *CatalogClient) ListAspectTypes(ctx context.Context, req *dataplexpb.ListAspectTypesRequest, opts ...gax.CallOption) *AspectTypeIterator {
	return c.internalClient.ListAspectTypes(ctx, req, opts...)
}

// GetAspectType retrieves a AspectType resource.
func (c *CatalogClient) GetAspectType(ctx context.Context, req *dataplexpb.GetAspectTypeRequest, opts ...gax.CallOption) (*dataplexpb.AspectType, error) {
	return c.internalClient.GetAspectType(ctx, req, opts...)
}

// CreateEntryGroup creates an EntryGroup
func (c *CatalogClient) CreateEntryGroup(ctx context.Context, req *dataplexpb.CreateEntryGroupRequest, opts ...gax.CallOption) (*CreateEntryGroupOperation, error) {
	return c.internalClient.CreateEntryGroup(ctx, req, opts...)
}

// CreateEntryGroupOperation returns a new CreateEntryGroupOperation from a given name.
// The name must be that of a previously created CreateEntryGroupOperation, possibly from a different process.
func (c *CatalogClient) CreateEntryGroupOperation(name string) *CreateEntryGroupOperation {
	return c.internalClient.CreateEntryGroupOperation(name)
}

// UpdateEntryGroup updates a EntryGroup resource.
func (c *CatalogClient) UpdateEntryGroup(ctx context.Context, req *dataplexpb.UpdateEntryGroupRequest, opts ...gax.CallOption) (*UpdateEntryGroupOperation, error) {
	return c.internalClient.UpdateEntryGroup(ctx, req, opts...)
}

// UpdateEntryGroupOperation returns a new UpdateEntryGroupOperation from a given name.
// The name must be that of a previously created UpdateEntryGroupOperation, possibly from a different process.
func (c *CatalogClient) UpdateEntryGroupOperation(name string) *UpdateEntryGroupOperation {
	return c.internalClient.UpdateEntryGroupOperation(name)
}

// DeleteEntryGroup deletes a EntryGroup resource.
func (c *CatalogClient) DeleteEntryGroup(ctx context.Context, req *dataplexpb.DeleteEntryGroupRequest, opts ...gax.CallOption) (*DeleteEntryGroupOperation, error) {
	return c.internalClient.DeleteEntryGroup(ctx, req, opts...)
}

// DeleteEntryGroupOperation returns a new DeleteEntryGroupOperation from a given name.
// The name must be that of a previously created DeleteEntryGroupOperation, possibly from a different process.
func (c *CatalogClient) DeleteEntryGroupOperation(name string) *DeleteEntryGroupOperation {
	return c.internalClient.DeleteEntryGroupOperation(name)
}

// ListEntryGroups lists EntryGroup resources in a project and location.
func (c *CatalogClient) ListEntryGroups(ctx context.Context, req *dataplexpb.ListEntryGroupsRequest, opts ...gax.CallOption) *EntryGroupIterator {
	return c.internalClient.ListEntryGroups(ctx, req, opts...)
}

// GetEntryGroup retrieves a EntryGroup resource.
func (c *CatalogClient) GetEntryGroup(ctx context.Context, req *dataplexpb.GetEntryGroupRequest, opts ...gax.CallOption) (*dataplexpb.EntryGroup, error) {
	return c.internalClient.GetEntryGroup(ctx, req, opts...)
}

// CreateEntry creates an Entry.
func (c *CatalogClient) CreateEntry(ctx context.Context, req *dataplexpb.CreateEntryRequest, opts ...gax.CallOption) (*dataplexpb.Entry, error) {
	return c.internalClient.CreateEntry(ctx, req, opts...)
}

// UpdateEntry updates an Entry.
func (c *CatalogClient) UpdateEntry(ctx context.Context, req *dataplexpb.UpdateEntryRequest, opts ...gax.CallOption) (*dataplexpb.Entry, error) {
	return c.internalClient.UpdateEntry(ctx, req, opts...)
}

// DeleteEntry deletes an Entry.
func (c *CatalogClient) DeleteEntry(ctx context.Context, req *dataplexpb.DeleteEntryRequest, opts ...gax.CallOption) (*dataplexpb.Entry, error) {
	return c.internalClient.DeleteEntry(ctx, req, opts...)
}

// ListEntries lists entries within an entry group.
func (c *CatalogClient) ListEntries(ctx context.Context, req *dataplexpb.ListEntriesRequest, opts ...gax.CallOption) *EntryIterator {
	return c.internalClient.ListEntries(ctx, req, opts...)
}

// GetEntry gets a single entry.
func (c *CatalogClient) GetEntry(ctx context.Context, req *dataplexpb.GetEntryRequest, opts ...gax.CallOption) (*dataplexpb.Entry, error) {
	return c.internalClient.GetEntry(ctx, req, opts...)
}

// LookupEntry looks up a single entry.
func (c *CatalogClient) LookupEntry(ctx context.Context, req *dataplexpb.LookupEntryRequest, opts ...gax.CallOption) (*dataplexpb.Entry, error) {
	return c.internalClient.LookupEntry(ctx, req, opts...)
}

// SearchEntries searches for entries matching given query and scope.
func (c *CatalogClient) SearchEntries(ctx context.Context, req *dataplexpb.SearchEntriesRequest, opts ...gax.CallOption) *SearchEntriesResultIterator {
	return c.internalClient.SearchEntries(ctx, req, opts...)
}

// GetLocation gets information about a location.
func (c *CatalogClient) GetLocation(ctx context.Context, req *locationpb.GetLocationRequest, opts ...gax.CallOption) (*locationpb.Location, error) {
	return c.internalClient.GetLocation(ctx, req, opts...)
}

// ListLocations lists information about the supported locations for this service.
func (c *CatalogClient) ListLocations(ctx context.Context, req *locationpb.ListLocationsRequest, opts ...gax.CallOption) *LocationIterator {
	return c.internalClient.ListLocations(ctx, req, opts...)
}

// CancelOperation is a utility method from google.longrunning.Operations.
func (c *CatalogClient) CancelOperation(ctx context.Context, req *longrunningpb.CancelOperationRequest, opts ...gax.CallOption) error {
	return c.internalClient.CancelOperation(ctx, req, opts...)
}

// DeleteOperation is a utility method from google.longrunning.Operations.
func (c *CatalogClient) DeleteOperation(ctx context.Context, req *longrunningpb.DeleteOperationRequest, opts ...gax.CallOption) error {
	return c.internalClient.DeleteOperation(ctx, req, opts...)
}

// GetOperation is a utility method from google.longrunning.Operations.
func (c *CatalogClient) GetOperation(ctx context.Context, req *longrunningpb.GetOperationRequest, opts ...gax.CallOption) (*longrunningpb.Operation, error) {
	return c.internalClient.GetOperation(ctx, req, opts...)
}

// ListOperations is a utility method from google.longrunning.Operations.
func (c *CatalogClient) ListOperations(ctx context.Context, req *longrunningpb.ListOperationsRequest, opts ...gax.CallOption) *OperationIterator {
	return c.internalClient.ListOperations(ctx, req, opts...)
}

// catalogGRPCClient is a client for interacting with Cloud Dataplex API over gRPC transport.
//
// Methods, except Close, may be called concurrently. However, fields must not be modified concurrently with method calls.
type catalogGRPCClient struct {
	// Connection pool of gRPC connections to the service.
	connPool gtransport.ConnPool

	// Points back to the CallOptions field of the containing CatalogClient
	CallOptions **CatalogCallOptions

	// The gRPC API client.
	catalogClient dataplexpb.CatalogServiceClient

	// LROClient is used internally to handle long-running operations.
	// It is exposed so that its CallOptions can be modified if required.
	// Users should not Close this client.
	LROClient **lroauto.OperationsClient

	operationsClient longrunningpb.OperationsClient

	locationsClient locationpb.LocationsClient

	// The x-goog-* metadata to be sent with each request.
	xGoogHeaders []string
}

// NewCatalogClient creates a new catalog service client based on gRPC.
// The returned client must be Closed when it is done being used to clean up its underlying connections.
//
// The primary resources offered by this service are EntryGroups, EntryTypes,
// AspectTypes, Entry and Aspect which collectively allow a data administrator
// to organize, manage, secure and catalog data across their organization
// located across cloud projects in a variety of storage systems including Cloud
// Storage and BigQuery.
func NewCatalogClient(ctx context.Context, opts ...option.ClientOption) (*CatalogClient, error) {
	clientOpts := defaultCatalogGRPCClientOptions()
	if newCatalogClientHook != nil {
		hookOpts, err := newCatalogClientHook(ctx, clientHookParams{})
		if err != nil {
			return nil, err
		}
		clientOpts = append(clientOpts, hookOpts...)
	}

	connPool, err := gtransport.DialPool(ctx, append(clientOpts, opts...)...)
	if err != nil {
		return nil, err
	}
	client := CatalogClient{CallOptions: defaultCatalogCallOptions()}

	c := &catalogGRPCClient{
		connPool:         connPool,
		catalogClient:    dataplexpb.NewCatalogServiceClient(connPool),
		CallOptions:      &client.CallOptions,
		operationsClient: longrunningpb.NewOperationsClient(connPool),
		locationsClient:  locationpb.NewLocationsClient(connPool),
	}
	c.setGoogleClientInfo()

	client.internalClient = c

	client.LROClient, err = lroauto.NewOperationsClient(ctx, gtransport.WithConnPool(connPool))
	if err != nil {
		// This error "should not happen", since we are just reusing old connection pool
		// and never actually need to dial.
		// If this does happen, we could leak connp. However, we cannot close conn:
		// If the user invoked the constructor with option.WithGRPCConn,
		// we would close a connection that's still in use.
		// TODO: investigate error conditions.
		return nil, err
	}
	c.LROClient = &client.LROClient
	return &client, nil
}

// Connection returns a connection to the API service.
//
// Deprecated: Connections are now pooled so this method does not always
// return the same resource.
func (c *catalogGRPCClient) Connection() *grpc.ClientConn {
	return c.connPool.Conn()
}

// setGoogleClientInfo sets the name and version of the application in
// the `x-goog-api-client` header passed on each request. Intended for
// use by Google-written clients.
func (c *catalogGRPCClient) setGoogleClientInfo(keyval ...string) {
	kv := append([]string{"gl-go", gax.GoVersion}, keyval...)
	kv = append(kv, "gapic", getVersionClient(), "gax", gax.Version, "grpc", grpc.Version)
	c.xGoogHeaders = []string{"x-goog-api-client", gax.XGoogHeader(kv...)}
}

// Close closes the connection to the API service. The user should invoke this when
// the client is no longer required.
func (c *catalogGRPCClient) Close() error {
	return c.connPool.Close()
}

func (c *catalogGRPCClient) CreateEntryType(ctx context.Context, req *dataplexpb.CreateEntryTypeRequest, opts ...gax.CallOption) (*CreateEntryTypeOperation, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).CreateEntryType[0:len((*c.CallOptions).CreateEntryType):len((*c.CallOptions).CreateEntryType)], opts...)
	var resp *longrunningpb.Operation
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.catalogClient.CreateEntryType(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return &CreateEntryTypeOperation{
		lro: longrunning.InternalNewOperation(*c.LROClient, resp),
	}, nil
}

func (c *catalogGRPCClient) UpdateEntryType(ctx context.Context, req *dataplexpb.UpdateEntryTypeRequest, opts ...gax.CallOption) (*UpdateEntryTypeOperation, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "entry_type.name", url.QueryEscape(req.GetEntryType().GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).UpdateEntryType[0:len((*c.CallOptions).UpdateEntryType):len((*c.CallOptions).UpdateEntryType)], opts...)
	var resp *longrunningpb.Operation
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.catalogClient.UpdateEntryType(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return &UpdateEntryTypeOperation{
		lro: longrunning.InternalNewOperation(*c.LROClient, resp),
	}, nil
}

func (c *catalogGRPCClient) DeleteEntryType(ctx context.Context, req *dataplexpb.DeleteEntryTypeRequest, opts ...gax.CallOption) (*DeleteEntryTypeOperation, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).DeleteEntryType[0:len((*c.CallOptions).DeleteEntryType):len((*c.CallOptions).DeleteEntryType)], opts...)
	var resp *longrunningpb.Operation
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.catalogClient.DeleteEntryType(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return &DeleteEntryTypeOperation{
		lro: longrunning.InternalNewOperation(*c.LROClient, resp),
	}, nil
}

func (c *catalogGRPCClient) ListEntryTypes(ctx context.Context, req *dataplexpb.ListEntryTypesRequest, opts ...gax.CallOption) *EntryTypeIterator {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).ListEntryTypes[0:len((*c.CallOptions).ListEntryTypes):len((*c.CallOptions).ListEntryTypes)], opts...)
	it := &EntryTypeIterator{}
	req = proto.Clone(req).(*dataplexpb.ListEntryTypesRequest)
	it.InternalFetch = func(pageSize int, pageToken string) ([]*dataplexpb.EntryType, string, error) {
		resp := &dataplexpb.ListEntryTypesResponse{}
		if pageToken != "" {
			req.PageToken = pageToken
		}
		if pageSize > math.MaxInt32 {
			req.PageSize = math.MaxInt32
		} else if pageSize != 0 {
			req.PageSize = int32(pageSize)
		}
		err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
			var err error
			resp, err = c.catalogClient.ListEntryTypes(ctx, req, settings.GRPC...)
			return err
		}, opts...)
		if err != nil {
			return nil, "", err
		}

		it.Response = resp
		return resp.GetEntryTypes(), resp.GetNextPageToken(), nil
	}
	fetch := func(pageSize int, pageToken string) (string, error) {
		items, nextPageToken, err := it.InternalFetch(pageSize, pageToken)
		if err != nil {
			return "", err
		}
		it.items = append(it.items, items...)
		return nextPageToken, nil
	}

	it.pageInfo, it.nextFunc = iterator.NewPageInfo(fetch, it.bufLen, it.takeBuf)
	it.pageInfo.MaxSize = int(req.GetPageSize())
	it.pageInfo.Token = req.GetPageToken()

	return it
}

func (c *catalogGRPCClient) GetEntryType(ctx context.Context, req *dataplexpb.GetEntryTypeRequest, opts ...gax.CallOption) (*dataplexpb.EntryType, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).GetEntryType[0:len((*c.CallOptions).GetEntryType):len((*c.CallOptions).GetEntryType)], opts...)
	var resp *dataplexpb.EntryType
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.catalogClient.GetEntryType(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return resp, nil
}

func (c *catalogGRPCClient) CreateAspectType(ctx context.Context, req *dataplexpb.CreateAspectTypeRequest, opts ...gax.CallOption) (*CreateAspectTypeOperation, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).CreateAspectType[0:len((*c.CallOptions).CreateAspectType):len((*c.CallOptions).CreateAspectType)], opts...)
	var resp *longrunningpb.Operation
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.catalogClient.CreateAspectType(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return &CreateAspectTypeOperation{
		lro: longrunning.InternalNewOperation(*c.LROClient, resp),
	}, nil
}

func (c *catalogGRPCClient) UpdateAspectType(ctx context.Context, req *dataplexpb.UpdateAspectTypeRequest, opts ...gax.CallOption) (*UpdateAspectTypeOperation, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "aspect_type.name", url.QueryEscape(req.GetAspectType().GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).UpdateAspectType[0:len((*c.CallOptions).UpdateAspectType):len((*c.CallOptions).UpdateAspectType)], opts...)
	var resp *longrunningpb.Operation
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.catalogClient.UpdateAspectType(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return &UpdateAspectTypeOperation{
		lro: longrunning.InternalNewOperation(*c.LROClient, resp),
	}, nil
}

func (c *catalogGRPCClient) DeleteAspectType(ctx context.Context, req *dataplexpb.DeleteAspectTypeRequest, opts ...gax.CallOption) (*DeleteAspectTypeOperation, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).DeleteAspectType[0:len((*c.CallOptions).DeleteAspectType):len((*c.CallOptions).DeleteAspectType)], opts...)
	var resp *longrunningpb.Operation
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.catalogClient.DeleteAspectType(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return &DeleteAspectTypeOperation{
		lro: longrunning.InternalNewOperation(*c.LROClient, resp),
	}, nil
}

func (c *catalogGRPCClient) ListAspectTypes(ctx context.Context, req *dataplexpb.ListAspectTypesRequest, opts ...gax.CallOption) *AspectTypeIterator {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).ListAspectTypes[0:len((*c.CallOptions).ListAspectTypes):len((*c.CallOptions).ListAspectTypes)], opts...)
	it := &AspectTypeIterator{}
	req = proto.Clone(req).(*dataplexpb.ListAspectTypesRequest)
	it.InternalFetch = func(pageSize int, pageToken string) ([]*dataplexpb.AspectType, string, error) {
		resp := &dataplexpb.ListAspectTypesResponse{}
		if pageToken != "" {
			req.PageToken = pageToken
		}
		if pageSize > math.MaxInt32 {
			req.PageSize = math.MaxInt32
		} else if pageSize != 0 {
			req.PageSize = int32(pageSize)
		}
		err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
			var err error
			resp, err = c.catalogClient.ListAspectTypes(ctx, req, settings.GRPC...)
			return err
		}, opts...)
		if err != nil {
			return nil, "", err
		}

		it.Response = resp
		return resp.GetAspectTypes(), resp.GetNextPageToken(), nil
	}
	fetch := func(pageSize int, pageToken string) (string, error) {
		items, nextPageToken, err := it.InternalFetch(pageSize, pageToken)
		if err != nil {
			return "", err
		}
		it.items = append(it.items, items...)
		return nextPageToken, nil
	}

	it.pageInfo, it.nextFunc = iterator.NewPageInfo(fetch, it.bufLen, it.takeBuf)
	it.pageInfo.MaxSize = int(req.GetPageSize())
	it.pageInfo.Token = req.GetPageToken()

	return it
}

func (c *catalogGRPCClient) GetAspectType(ctx context.Context, req *dataplexpb.GetAspectTypeRequest, opts ...gax.CallOption) (*dataplexpb.AspectType, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).GetAspectType[0:len((*c.CallOptions).GetAspectType):len((*c.CallOptions).GetAspectType)], opts...)
	var resp *dataplexpb.AspectType
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.catalogClient.GetAspectType(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return resp, nil
}

func (c *catalogGRPCClient) CreateEntryGroup(ctx context.Context, req *dataplexpb.CreateEntryGroupRequest, opts ...gax.CallOption) (*CreateEntryGroupOperation, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).CreateEntryGroup[0:len((*c.CallOptions).CreateEntryGroup):len((*c.CallOptions).CreateEntryGroup)], opts...)
	var resp *longrunningpb.Operation
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.catalogClient.CreateEntryGroup(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return &CreateEntryGroupOperation{
		lro: longrunning.InternalNewOperation(*c.LROClient, resp),
	}, nil
}

func (c *catalogGRPCClient) UpdateEntryGroup(ctx context.Context, req *dataplexpb.UpdateEntryGroupRequest, opts ...gax.CallOption) (*UpdateEntryGroupOperation, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "entry_group.name", url.QueryEscape(req.GetEntryGroup().GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).UpdateEntryGroup[0:len((*c.CallOptions).UpdateEntryGroup):len((*c.CallOptions).UpdateEntryGroup)], opts...)
	var resp *longrunningpb.Operation
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.catalogClient.UpdateEntryGroup(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return &UpdateEntryGroupOperation{
		lro: longrunning.InternalNewOperation(*c.LROClient, resp),
	}, nil
}

func (c *catalogGRPCClient) DeleteEntryGroup(ctx context.Context, req *dataplexpb.DeleteEntryGroupRequest, opts ...gax.CallOption) (*DeleteEntryGroupOperation, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).DeleteEntryGroup[0:len((*c.CallOptions).DeleteEntryGroup):len((*c.CallOptions).DeleteEntryGroup)], opts...)
	var resp *longrunningpb.Operation
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.catalogClient.DeleteEntryGroup(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return &DeleteEntryGroupOperation{
		lro: longrunning.InternalNewOperation(*c.LROClient, resp),
	}, nil
}

func (c *catalogGRPCClient) ListEntryGroups(ctx context.Context, req *dataplexpb.ListEntryGroupsRequest, opts ...gax.CallOption) *EntryGroupIterator {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).ListEntryGroups[0:len((*c.CallOptions).ListEntryGroups):len((*c.CallOptions).ListEntryGroups)], opts...)
	it := &EntryGroupIterator{}
	req = proto.Clone(req).(*dataplexpb.ListEntryGroupsRequest)
	it.InternalFetch = func(pageSize int, pageToken string) ([]*dataplexpb.EntryGroup, string, error) {
		resp := &dataplexpb.ListEntryGroupsResponse{}
		if pageToken != "" {
			req.PageToken = pageToken
		}
		if pageSize > math.MaxInt32 {
			req.PageSize = math.MaxInt32
		} else if pageSize != 0 {
			req.PageSize = int32(pageSize)
		}
		err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
			var err error
			resp, err = c.catalogClient.ListEntryGroups(ctx, req, settings.GRPC...)
			return err
		}, opts...)
		if err != nil {
			return nil, "", err
		}

		it.Response = resp
		return resp.GetEntryGroups(), resp.GetNextPageToken(), nil
	}
	fetch := func(pageSize int, pageToken string) (string, error) {
		items, nextPageToken, err := it.InternalFetch(pageSize, pageToken)
		if err != nil {
			return "", err
		}
		it.items = append(it.items, items...)
		return nextPageToken, nil
	}

	it.pageInfo, it.nextFunc = iterator.NewPageInfo(fetch, it.bufLen, it.takeBuf)
	it.pageInfo.MaxSize = int(req.GetPageSize())
	it.pageInfo.Token = req.GetPageToken()

	return it
}

func (c *catalogGRPCClient) GetEntryGroup(ctx context.Context, req *dataplexpb.GetEntryGroupRequest, opts ...gax.CallOption) (*dataplexpb.EntryGroup, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).GetEntryGroup[0:len((*c.CallOptions).GetEntryGroup):len((*c.CallOptions).GetEntryGroup)], opts...)
	var resp *dataplexpb.EntryGroup
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.catalogClient.GetEntryGroup(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return resp, nil
}

func (c *catalogGRPCClient) CreateEntry(ctx context.Context, req *dataplexpb.CreateEntryRequest, opts ...gax.CallOption) (*dataplexpb.Entry, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).CreateEntry[0:len((*c.CallOptions).CreateEntry):len((*c.CallOptions).CreateEntry)], opts...)
	var resp *dataplexpb.Entry
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.catalogClient.CreateEntry(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return resp, nil
}

func (c *catalogGRPCClient) UpdateEntry(ctx context.Context, req *dataplexpb.UpdateEntryRequest, opts ...gax.CallOption) (*dataplexpb.Entry, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "entry.name", url.QueryEscape(req.GetEntry().GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).UpdateEntry[0:len((*c.CallOptions).UpdateEntry):len((*c.CallOptions).UpdateEntry)], opts...)
	var resp *dataplexpb.Entry
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.catalogClient.UpdateEntry(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return resp, nil
}

func (c *catalogGRPCClient) DeleteEntry(ctx context.Context, req *dataplexpb.DeleteEntryRequest, opts ...gax.CallOption) (*dataplexpb.Entry, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).DeleteEntry[0:len((*c.CallOptions).DeleteEntry):len((*c.CallOptions).DeleteEntry)], opts...)
	var resp *dataplexpb.Entry
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.catalogClient.DeleteEntry(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return resp, nil
}

func (c *catalogGRPCClient) ListEntries(ctx context.Context, req *dataplexpb.ListEntriesRequest, opts ...gax.CallOption) *EntryIterator {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).ListEntries[0:len((*c.CallOptions).ListEntries):len((*c.CallOptions).ListEntries)], opts...)
	it := &EntryIterator{}
	req = proto.Clone(req).(*dataplexpb.ListEntriesRequest)
	it.InternalFetch = func(pageSize int, pageToken string) ([]*dataplexpb.Entry, string, error) {
		resp := &dataplexpb.ListEntriesResponse{}
		if pageToken != "" {
			req.PageToken = pageToken
		}
		if pageSize > math.MaxInt32 {
			req.PageSize = math.MaxInt32
		} else if pageSize != 0 {
			req.PageSize = int32(pageSize)
		}
		err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
			var err error
			resp, err = c.catalogClient.ListEntries(ctx, req, settings.GRPC...)
			return err
		}, opts...)
		if err != nil {
			return nil, "", err
		}

		it.Response = resp
		return resp.GetEntries(), resp.GetNextPageToken(), nil
	}
	fetch := func(pageSize int, pageToken string) (string, error) {
		items, nextPageToken, err := it.InternalFetch(pageSize, pageToken)
		if err != nil {
			return "", err
		}
		it.items = append(it.items, items...)
		return nextPageToken, nil
	}

	it.pageInfo, it.nextFunc = iterator.NewPageInfo(fetch, it.bufLen, it.takeBuf)
	it.pageInfo.MaxSize = int(req.GetPageSize())
	it.pageInfo.Token = req.GetPageToken()

	return it
}

func (c *catalogGRPCClient) GetEntry(ctx context.Context, req *dataplexpb.GetEntryRequest, opts ...gax.CallOption) (*dataplexpb.Entry, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).GetEntry[0:len((*c.CallOptions).GetEntry):len((*c.CallOptions).GetEntry)], opts...)
	var resp *dataplexpb.Entry
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.catalogClient.GetEntry(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return resp, nil
}

func (c *catalogGRPCClient) LookupEntry(ctx context.Context, req *dataplexpb.LookupEntryRequest, opts ...gax.CallOption) (*dataplexpb.Entry, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).LookupEntry[0:len((*c.CallOptions).LookupEntry):len((*c.CallOptions).LookupEntry)], opts...)
	var resp *dataplexpb.Entry
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.catalogClient.LookupEntry(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return resp, nil
}

func (c *catalogGRPCClient) SearchEntries(ctx context.Context, req *dataplexpb.SearchEntriesRequest, opts ...gax.CallOption) *SearchEntriesResultIterator {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).SearchEntries[0:len((*c.CallOptions).SearchEntries):len((*c.CallOptions).SearchEntries)], opts...)
	it := &SearchEntriesResultIterator{}
	req = proto.Clone(req).(*dataplexpb.SearchEntriesRequest)
	it.InternalFetch = func(pageSize int, pageToken string) ([]*dataplexpb.SearchEntriesResult, string, error) {
		resp := &dataplexpb.SearchEntriesResponse{}
		if pageToken != "" {
			req.PageToken = pageToken
		}
		if pageSize > math.MaxInt32 {
			req.PageSize = math.MaxInt32
		} else if pageSize != 0 {
			req.PageSize = int32(pageSize)
		}
		err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
			var err error
			resp, err = c.catalogClient.SearchEntries(ctx, req, settings.GRPC...)
			return err
		}, opts...)
		if err != nil {
			return nil, "", err
		}

		it.Response = resp
		return resp.GetResults(), resp.GetNextPageToken(), nil
	}
	fetch := func(pageSize int, pageToken string) (string, error) {
		items, nextPageToken, err := it.InternalFetch(pageSize, pageToken)
		if err != nil {
			return "", err
		}
		it.items = append(it.items, items...)
		return nextPageToken, nil
	}

	it.pageInfo, it.nextFunc = iterator.NewPageInfo(fetch, it.bufLen, it.takeBuf)
	it.pageInfo.MaxSize = int(req.GetPageSize())
	it.pageInfo.Token = req.GetPageToken()

	return it
}

func (c *catalogGRPCClient) GetLocation(ctx context.Context, req *locationpb.GetLocationRequest, opts ...gax.CallOption) (*locationpb.Location, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).GetLocation[0:len((*c.CallOptions).GetLocation):len((*c.CallOptions).GetLocation)], opts...)
	var resp *locationpb.Location
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.locationsClient.GetLocation(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return resp, nil
}

func (c *catalogGRPCClient) ListLocations(ctx context.Context, req *locationpb.ListLocationsRequest, opts ...gax.CallOption) *LocationIterator {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).ListLocations[0:len((*c.CallOptions).ListLocations):len((*c.CallOptions).ListLocations)], opts...)
	it := &LocationIterator{}
	req = proto.Clone(req).(*locationpb.ListLocationsRequest)
	it.InternalFetch = func(pageSize int, pageToken string) ([]*locationpb.Location, string, error) {
		resp := &locationpb.ListLocationsResponse{}
		if pageToken != "" {
			req.PageToken = pageToken
		}
		if pageSize > math.MaxInt32 {
			req.PageSize = math.MaxInt32
		} else if pageSize != 0 {
			req.PageSize = int32(pageSize)
		}
		err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
			var err error
			resp, err = c.locationsClient.ListLocations(ctx, req, settings.GRPC...)
			return err
		}, opts...)
		if err != nil {
			return nil, "", err
		}

		it.Response = resp
		return resp.GetLocations(), resp.GetNextPageToken(), nil
	}
	fetch := func(pageSize int, pageToken string) (string, error) {
		items, nextPageToken, err := it.InternalFetch(pageSize, pageToken)
		if err != nil {
			return "", err
		}
		it.items = append(it.items, items...)
		return nextPageToken, nil
	}

	it.pageInfo, it.nextFunc = iterator.NewPageInfo(fetch, it.bufLen, it.takeBuf)
	it.pageInfo.MaxSize = int(req.GetPageSize())
	it.pageInfo.Token = req.GetPageToken()

	return it
}

func (c *catalogGRPCClient) CancelOperation(ctx context.Context, req *longrunningpb.CancelOperationRequest, opts ...gax.CallOption) error {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).CancelOperation[0:len((*c.CallOptions).CancelOperation):len((*c.CallOptions).CancelOperation)], opts...)
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		_, err = c.operationsClient.CancelOperation(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	return err
}

func (c *catalogGRPCClient) DeleteOperation(ctx context.Context, req *longrunningpb.DeleteOperationRequest, opts ...gax.CallOption) error {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).DeleteOperation[0:len((*c.CallOptions).DeleteOperation):len((*c.CallOptions).DeleteOperation)], opts...)
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		_, err = c.operationsClient.DeleteOperation(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	return err
}

func (c *catalogGRPCClient) GetOperation(ctx context.Context, req *longrunningpb.GetOperationRequest, opts ...gax.CallOption) (*longrunningpb.Operation, error) {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).GetOperation[0:len((*c.CallOptions).GetOperation):len((*c.CallOptions).GetOperation)], opts...)
	var resp *longrunningpb.Operation
	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
		var err error
		resp, err = c.operationsClient.GetOperation(ctx, req, settings.GRPC...)
		return err
	}, opts...)
	if err != nil {
		return nil, err
	}
	return resp, nil
}

func (c *catalogGRPCClient) ListOperations(ctx context.Context, req *longrunningpb.ListOperationsRequest, opts ...gax.CallOption) *OperationIterator {
	hds := []string{"x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName()))}

	hds = append(c.xGoogHeaders, hds...)
	ctx = gax.InsertMetadataIntoOutgoingContext(ctx, hds...)
	opts = append((*c.CallOptions).ListOperations[0:len((*c.CallOptions).ListOperations):len((*c.CallOptions).ListOperations)], opts...)
	it := &OperationIterator{}
	req = proto.Clone(req).(*longrunningpb.ListOperationsRequest)
	it.InternalFetch = func(pageSize int, pageToken string) ([]*longrunningpb.Operation, string, error) {
		resp := &longrunningpb.ListOperationsResponse{}
		if pageToken != "" {
			req.PageToken = pageToken
		}
		if pageSize > math.MaxInt32 {
			req.PageSize = math.MaxInt32
		} else if pageSize != 0 {
			req.PageSize = int32(pageSize)
		}
		err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
			var err error
			resp, err = c.operationsClient.ListOperations(ctx, req, settings.GRPC...)
			return err
		}, opts...)
		if err != nil {
			return nil, "", err
		}

		it.Response = resp
		return resp.GetOperations(), resp.GetNextPageToken(), nil
	}
	fetch := func(pageSize int, pageToken string) (string, error) {
		items, nextPageToken, err := it.InternalFetch(pageSize, pageToken)
		if err != nil {
			return "", err
		}
		it.items = append(it.items, items...)
		return nextPageToken, nil
	}

	it.pageInfo, it.nextFunc = iterator.NewPageInfo(fetch, it.bufLen, it.takeBuf)
	it.pageInfo.MaxSize = int(req.GetPageSize())
	it.pageInfo.Token = req.GetPageToken()

	return it
}

// CreateAspectTypeOperation returns a new CreateAspectTypeOperation from a given name.
// The name must be that of a previously created CreateAspectTypeOperation, possibly from a different process.
func (c *catalogGRPCClient) CreateAspectTypeOperation(name string) *CreateAspectTypeOperation {
	return &CreateAspectTypeOperation{
		lro: longrunning.InternalNewOperation(*c.LROClient, &longrunningpb.Operation{Name: name}),
	}
}

// CreateEntryGroupOperation returns a new CreateEntryGroupOperation from a given name.
// The name must be that of a previously created CreateEntryGroupOperation, possibly from a different process.
func (c *catalogGRPCClient) CreateEntryGroupOperation(name string) *CreateEntryGroupOperation {
	return &CreateEntryGroupOperation{
		lro: longrunning.InternalNewOperation(*c.LROClient, &longrunningpb.Operation{Name: name}),
	}
}

// CreateEntryTypeOperation returns a new CreateEntryTypeOperation from a given name.
// The name must be that of a previously created CreateEntryTypeOperation, possibly from a different process.
func (c *catalogGRPCClient) CreateEntryTypeOperation(name string) *CreateEntryTypeOperation {
	return &CreateEntryTypeOperation{
		lro: longrunning.InternalNewOperation(*c.LROClient, &longrunningpb.Operation{Name: name}),
	}
}

// DeleteAspectTypeOperation returns a new DeleteAspectTypeOperation from a given name.
// The name must be that of a previously created DeleteAspectTypeOperation, possibly from a different process.
func (c *catalogGRPCClient) DeleteAspectTypeOperation(name string) *DeleteAspectTypeOperation {
	return &DeleteAspectTypeOperation{
		lro: longrunning.InternalNewOperation(*c.LROClient, &longrunningpb.Operation{Name: name}),
	}
}

// DeleteEntryGroupOperation returns a new DeleteEntryGroupOperation from a given name.
// The name must be that of a previously created DeleteEntryGroupOperation, possibly from a different process.
func (c *catalogGRPCClient) DeleteEntryGroupOperation(name string) *DeleteEntryGroupOperation {
	return &DeleteEntryGroupOperation{
		lro: longrunning.InternalNewOperation(*c.LROClient, &longrunningpb.Operation{Name: name}),
	}
}

// DeleteEntryTypeOperation returns a new DeleteEntryTypeOperation from a given name.
// The name must be that of a previously created DeleteEntryTypeOperation, possibly from a different process.
func (c *catalogGRPCClient) DeleteEntryTypeOperation(name string) *DeleteEntryTypeOperation {
	return &DeleteEntryTypeOperation{
		lro: longrunning.InternalNewOperation(*c.LROClient, &longrunningpb.Operation{Name: name}),
	}
}

// UpdateAspectTypeOperation returns a new UpdateAspectTypeOperation from a given name.
// The name must be that of a previously created UpdateAspectTypeOperation, possibly from a different process.
func (c *catalogGRPCClient) UpdateAspectTypeOperation(name string) *UpdateAspectTypeOperation {
	return &UpdateAspectTypeOperation{
		lro: longrunning.InternalNewOperation(*c.LROClient, &longrunningpb.Operation{Name: name}),
	}
}

// UpdateEntryGroupOperation returns a new UpdateEntryGroupOperation from a given name.
// The name must be that of a previously created UpdateEntryGroupOperation, possibly from a different process.
func (c *catalogGRPCClient) UpdateEntryGroupOperation(name string) *UpdateEntryGroupOperation {
	return &UpdateEntryGroupOperation{
		lro: longrunning.InternalNewOperation(*c.LROClient, &longrunningpb.Operation{Name: name}),
	}
}

// UpdateEntryTypeOperation returns a new UpdateEntryTypeOperation from a given name.
// The name must be that of a previously created UpdateEntryTypeOperation, possibly from a different process.
func (c *catalogGRPCClient) UpdateEntryTypeOperation(name string) *UpdateEntryTypeOperation {
	return &UpdateEntryTypeOperation{
		lro: longrunning.InternalNewOperation(*c.LROClient, &longrunningpb.Operation{Name: name}),
	}
}
