diff --git a/asset/apiv1/doc.go b/asset/apiv1/doc.go
index 7ddfd35..103b9ad 100644
--- a/asset/apiv1/doc.go
+++ b/asset/apiv1/doc.go
@@ -97,4 +97,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/asset/apiv1beta1/doc.go b/asset/apiv1beta1/doc.go
index 6cd9ab7..826e590 100644
--- a/asset/apiv1beta1/doc.go
+++ b/asset/apiv1beta1/doc.go
@@ -97,4 +97,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/asset/apiv1p2beta1/doc.go b/asset/apiv1p2beta1/doc.go
index bbf5761..3db4577 100644
--- a/asset/apiv1p2beta1/doc.go
+++ b/asset/apiv1p2beta1/doc.go
@@ -97,4 +97,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/automl/apiv1/auto_ml_client.go b/automl/apiv1/auto_ml_client.go
new file mode 100644
index 0000000..d3f0b34
--- /dev/null
+++ b/automl/apiv1/auto_ml_client.go
@@ -0,0 +1,929 @@
+// Copyright 2019 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 gapic-generator. DO NOT EDIT.
+
+package automl
+
+import (
+	"context"
+	"fmt"
+	"math"
+	"net/url"
+	"time"
+
+	"cloud.google.com/go/longrunning"
+	lroauto "cloud.google.com/go/longrunning/autogen"
+	"github.com/golang/protobuf/proto"
+	gax "github.com/googleapis/gax-go/v2"
+	"google.golang.org/api/iterator"
+	"google.golang.org/api/option"
+	"google.golang.org/api/transport"
+	automlpb "google.golang.org/genproto/googleapis/cloud/automl/v1"
+	longrunningpb "google.golang.org/genproto/googleapis/longrunning"
+	"google.golang.org/grpc"
+	"google.golang.org/grpc/codes"
+	"google.golang.org/grpc/metadata"
+)
+
+// CallOptions contains the retry settings for each method of Client.
+type CallOptions struct {
+	CreateDataset        []gax.CallOption
+	UpdateDataset        []gax.CallOption
+	GetDataset           []gax.CallOption
+	ListDatasets         []gax.CallOption
+	DeleteDataset        []gax.CallOption
+	ImportData           []gax.CallOption
+	ExportData           []gax.CallOption
+	CreateModel          []gax.CallOption
+	GetModel             []gax.CallOption
+	UpdateModel          []gax.CallOption
+	ListModels           []gax.CallOption
+	DeleteModel          []gax.CallOption
+	GetModelEvaluation   []gax.CallOption
+	ListModelEvaluations []gax.CallOption
+}
+
+func defaultClientOptions() []option.ClientOption {
+	return []option.ClientOption{
+		option.WithEndpoint("automl.googleapis.com:443"),
+		option.WithScopes(DefaultAuthScopes()...),
+		option.WithGRPCDialOption(grpc.WithDefaultCallOptions(
+			grpc.MaxCallRecvMsgSize(math.MaxInt32))),
+	}
+}
+
+func defaultCallOptions() *CallOptions {
+	retry := map[[2]string][]gax.CallOption{
+		{"default", "idempotent"}: {
+			gax.WithRetry(func() gax.Retryer {
+				return gax.OnCodes([]codes.Code{
+					codes.DeadlineExceeded,
+					codes.Unavailable,
+				}, gax.Backoff{
+					Initial:    100 * time.Millisecond,
+					Max:        60000 * time.Millisecond,
+					Multiplier: 1.3,
+				})
+			}),
+		},
+	}
+	return &CallOptions{
+		CreateDataset:        retry[[2]string{"default", "non_idempotent"}],
+		UpdateDataset:        retry[[2]string{"default", "non_idempotent"}],
+		GetDataset:           retry[[2]string{"default", "idempotent"}],
+		ListDatasets:         retry[[2]string{"default", "idempotent"}],
+		DeleteDataset:        retry[[2]string{"default", "idempotent"}],
+		ImportData:           retry[[2]string{"default", "non_idempotent"}],
+		ExportData:           retry[[2]string{"default", "non_idempotent"}],
+		CreateModel:          retry[[2]string{"default", "non_idempotent"}],
+		GetModel:             retry[[2]string{"default", "idempotent"}],
+		UpdateModel:          retry[[2]string{"default", "non_idempotent"}],
+		ListModels:           retry[[2]string{"default", "idempotent"}],
+		DeleteModel:          retry[[2]string{"default", "idempotent"}],
+		GetModelEvaluation:   retry[[2]string{"default", "idempotent"}],
+		ListModelEvaluations: retry[[2]string{"default", "idempotent"}],
+	}
+}
+
+// Client is a client for interacting with Cloud AutoML API.
+//
+// Methods, except Close, may be called concurrently. However, fields must not be modified concurrently with method calls.
+type Client struct {
+	// The connection to the service.
+	conn *grpc.ClientConn
+
+	// The gRPC API client.
+	client automlpb.AutoMlClient
+
+	// LROClient is used internally to handle longrunning operations.
+	// It is exposed so that its CallOptions can be modified if required.
+	// Users should not Close this client.
+	LROClient *lroauto.OperationsClient
+
+	// The call options for this service.
+	CallOptions *CallOptions
+
+	// The x-goog-* metadata to be sent with each request.
+	xGoogMetadata metadata.MD
+}
+
+// NewClient creates a new auto ml client.
+//
+// AutoML Server API.
+//
+// The resource names are assigned by the server.
+// The server never reuses names that it has created after the resources with
+// those names are deleted.
+//
+// An ID of a resource is the last element of the item's resource name. For
+// projects/{project_id}/locations/{location_id}/datasets/{dataset_id}, then
+// the id for the item is {dataset_id}.
+//
+// Currently the only supported location_id is "us-central1".
+//
+// On any input that is documented to expect a string parameter in
+// snake_case or kebab-case, either of those cases is accepted.
+func NewClient(ctx context.Context, opts ...option.ClientOption) (*Client, error) {
+	conn, err := transport.DialGRPC(ctx, append(defaultClientOptions(), opts...)...)
+	if err != nil {
+		return nil, err
+	}
+	c := &Client{
+		conn:        conn,
+		CallOptions: defaultCallOptions(),
+
+		client: automlpb.NewAutoMlClient(conn),
+	}
+	c.setGoogleClientInfo()
+
+	c.LROClient, err = lroauto.NewOperationsClient(ctx, option.WithGRPCConn(conn))
+	if err != nil {
+		// This error "should not happen", since we are just reusing old connection
+		// and never actually need to dial.
+		// If this does happen, we could leak conn. However, we cannot close conn:
+		// If the user invoked the function with option.WithGRPCConn,
+		// we would close a connection that's still in use.
+		// TODO(pongad): investigate error conditions.
+		return nil, err
+	}
+	return c, nil
+}
+
+// Connection returns the client's connection to the API service.
+func (c *Client) Connection() *grpc.ClientConn {
+	return c.conn
+}
+
+// Close closes the connection to the API service. The user should invoke this when
+// the client is no longer required.
+func (c *Client) Close() error {
+	return c.conn.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 *Client) setGoogleClientInfo(keyval ...string) {
+	kv := append([]string{"gl-go", versionGo()}, keyval...)
+	kv = append(kv, "gapic", versionClient, "gax", gax.Version, "grpc", grpc.Version)
+	c.xGoogMetadata = metadata.Pairs("x-goog-api-client", gax.XGoogHeader(kv...))
+}
+
+// CreateDataset creates a dataset.
+func (c *Client) CreateDataset(ctx context.Context, req *automlpb.CreateDatasetRequest, opts ...gax.CallOption) (*longrunningpb.Operation, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.CreateDataset[0:len(c.CallOptions.CreateDataset):len(c.CallOptions.CreateDataset)], opts...)
+	var resp *longrunningpb.Operation
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.client.CreateDataset(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return resp, nil
+}
+
+// UpdateDataset updates a dataset.
+func (c *Client) UpdateDataset(ctx context.Context, req *automlpb.UpdateDatasetRequest, opts ...gax.CallOption) (*automlpb.Dataset, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "dataset.name", url.QueryEscape(req.GetDataset().GetName())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.UpdateDataset[0:len(c.CallOptions.UpdateDataset):len(c.CallOptions.UpdateDataset)], opts...)
+	var resp *automlpb.Dataset
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.client.UpdateDataset(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return resp, nil
+}
+
+// GetDataset gets a dataset.
+func (c *Client) GetDataset(ctx context.Context, req *automlpb.GetDatasetRequest, opts ...gax.CallOption) (*automlpb.Dataset, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.GetDataset[0:len(c.CallOptions.GetDataset):len(c.CallOptions.GetDataset)], opts...)
+	var resp *automlpb.Dataset
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.client.GetDataset(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return resp, nil
+}
+
+// ListDatasets lists datasets in a project.
+func (c *Client) ListDatasets(ctx context.Context, req *automlpb.ListDatasetsRequest, opts ...gax.CallOption) *DatasetIterator {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.ListDatasets[0:len(c.CallOptions.ListDatasets):len(c.CallOptions.ListDatasets)], opts...)
+	it := &DatasetIterator{}
+	req = proto.Clone(req).(*automlpb.ListDatasetsRequest)
+	it.InternalFetch = func(pageSize int, pageToken string) ([]*automlpb.Dataset, string, error) {
+		var resp *automlpb.ListDatasetsResponse
+		req.PageToken = pageToken
+		if pageSize > math.MaxInt32 {
+			req.PageSize = math.MaxInt32
+		} else {
+			req.PageSize = int32(pageSize)
+		}
+		err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+			var err error
+			resp, err = c.client.ListDatasets(ctx, req, settings.GRPC...)
+			return err
+		}, opts...)
+		if err != nil {
+			return nil, "", err
+		}
+		return resp.Datasets, resp.NextPageToken, 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.PageSize)
+	it.pageInfo.Token = req.PageToken
+	return it
+}
+
+// DeleteDataset deletes a dataset and all of its contents.
+// Returns empty response in the
+// [response][google.longrunning.Operation.response] field when it completes,
+// and delete_details in the
+// [metadata][google.longrunning.Operation.metadata] field.
+func (c *Client) DeleteDataset(ctx context.Context, req *automlpb.DeleteDatasetRequest, opts ...gax.CallOption) (*DeleteDatasetOperation, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.DeleteDataset[0:len(c.CallOptions.DeleteDataset):len(c.CallOptions.DeleteDataset)], opts...)
+	var resp *longrunningpb.Operation
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.client.DeleteDataset(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return &DeleteDatasetOperation{
+		lro: longrunning.InternalNewOperation(c.LROClient, resp),
+	}, nil
+}
+
+// ImportData imports data into a dataset.
+func (c *Client) ImportData(ctx context.Context, req *automlpb.ImportDataRequest, opts ...gax.CallOption) (*ImportDataOperation, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.ImportData[0:len(c.CallOptions.ImportData):len(c.CallOptions.ImportData)], opts...)
+	var resp *longrunningpb.Operation
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.client.ImportData(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return &ImportDataOperation{
+		lro: longrunning.InternalNewOperation(c.LROClient, resp),
+	}, nil
+}
+
+// ExportData exports dataset's data to the provided output location.
+// Returns an empty response in the
+// [response][google.longrunning.Operation.response] field when it completes.
+func (c *Client) ExportData(ctx context.Context, req *automlpb.ExportDataRequest, opts ...gax.CallOption) (*ExportDataOperation, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.ExportData[0:len(c.CallOptions.ExportData):len(c.CallOptions.ExportData)], opts...)
+	var resp *longrunningpb.Operation
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.client.ExportData(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return &ExportDataOperation{
+		lro: longrunning.InternalNewOperation(c.LROClient, resp),
+	}, nil
+}
+
+// CreateModel creates a model.
+// Returns a Model in the [response][google.longrunning.Operation.response]
+// field when it completes.
+// When you create a model, several model evaluations are created for it:
+// a global evaluation, and one evaluation for each annotation spec.
+func (c *Client) CreateModel(ctx context.Context, req *automlpb.CreateModelRequest, opts ...gax.CallOption) (*CreateModelOperation, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.CreateModel[0:len(c.CallOptions.CreateModel):len(c.CallOptions.CreateModel)], opts...)
+	var resp *longrunningpb.Operation
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.client.CreateModel(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return &CreateModelOperation{
+		lro: longrunning.InternalNewOperation(c.LROClient, resp),
+	}, nil
+}
+
+// GetModel gets a model.
+func (c *Client) GetModel(ctx context.Context, req *automlpb.GetModelRequest, opts ...gax.CallOption) (*automlpb.Model, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.GetModel[0:len(c.CallOptions.GetModel):len(c.CallOptions.GetModel)], opts...)
+	var resp *automlpb.Model
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.client.GetModel(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return resp, nil
+}
+
+// UpdateModel updates a model.
+func (c *Client) UpdateModel(ctx context.Context, req *automlpb.UpdateModelRequest, opts ...gax.CallOption) (*automlpb.Model, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "model.name", url.QueryEscape(req.GetModel().GetName())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.UpdateModel[0:len(c.CallOptions.UpdateModel):len(c.CallOptions.UpdateModel)], opts...)
+	var resp *automlpb.Model
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.client.UpdateModel(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return resp, nil
+}
+
+// ListModels lists models.
+func (c *Client) ListModels(ctx context.Context, req *automlpb.ListModelsRequest, opts ...gax.CallOption) *ModelIterator {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.ListModels[0:len(c.CallOptions.ListModels):len(c.CallOptions.ListModels)], opts...)
+	it := &ModelIterator{}
+	req = proto.Clone(req).(*automlpb.ListModelsRequest)
+	it.InternalFetch = func(pageSize int, pageToken string) ([]*automlpb.Model, string, error) {
+		var resp *automlpb.ListModelsResponse
+		req.PageToken = pageToken
+		if pageSize > math.MaxInt32 {
+			req.PageSize = math.MaxInt32
+		} else {
+			req.PageSize = int32(pageSize)
+		}
+		err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+			var err error
+			resp, err = c.client.ListModels(ctx, req, settings.GRPC...)
+			return err
+		}, opts...)
+		if err != nil {
+			return nil, "", err
+		}
+		return resp.Model, resp.NextPageToken, 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.PageSize)
+	it.pageInfo.Token = req.PageToken
+	return it
+}
+
+// DeleteModel deletes a model.
+// Returns google.protobuf.Empty in the
+// [response][google.longrunning.Operation.response] field when it completes,
+// and delete_details in the
+// [metadata][google.longrunning.Operation.metadata] field.
+func (c *Client) DeleteModel(ctx context.Context, req *automlpb.DeleteModelRequest, opts ...gax.CallOption) (*DeleteModelOperation, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.DeleteModel[0:len(c.CallOptions.DeleteModel):len(c.CallOptions.DeleteModel)], opts...)
+	var resp *longrunningpb.Operation
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.client.DeleteModel(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return &DeleteModelOperation{
+		lro: longrunning.InternalNewOperation(c.LROClient, resp),
+	}, nil
+}
+
+// GetModelEvaluation gets a model evaluation.
+func (c *Client) GetModelEvaluation(ctx context.Context, req *automlpb.GetModelEvaluationRequest, opts ...gax.CallOption) (*automlpb.ModelEvaluation, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.GetModelEvaluation[0:len(c.CallOptions.GetModelEvaluation):len(c.CallOptions.GetModelEvaluation)], opts...)
+	var resp *automlpb.ModelEvaluation
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.client.GetModelEvaluation(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return resp, nil
+}
+
+// ListModelEvaluations lists model evaluations.
+func (c *Client) ListModelEvaluations(ctx context.Context, req *automlpb.ListModelEvaluationsRequest, opts ...gax.CallOption) *ModelEvaluationIterator {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.ListModelEvaluations[0:len(c.CallOptions.ListModelEvaluations):len(c.CallOptions.ListModelEvaluations)], opts...)
+	it := &ModelEvaluationIterator{}
+	req = proto.Clone(req).(*automlpb.ListModelEvaluationsRequest)
+	it.InternalFetch = func(pageSize int, pageToken string) ([]*automlpb.ModelEvaluation, string, error) {
+		var resp *automlpb.ListModelEvaluationsResponse
+		req.PageToken = pageToken
+		if pageSize > math.MaxInt32 {
+			req.PageSize = math.MaxInt32
+		} else {
+			req.PageSize = int32(pageSize)
+		}
+		err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+			var err error
+			resp, err = c.client.ListModelEvaluations(ctx, req, settings.GRPC...)
+			return err
+		}, opts...)
+		if err != nil {
+			return nil, "", err
+		}
+		return resp.ModelEvaluation, resp.NextPageToken, 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.PageSize)
+	it.pageInfo.Token = req.PageToken
+	return it
+}
+
+// DatasetIterator manages a stream of *automlpb.Dataset.
+type DatasetIterator struct {
+	items    []*automlpb.Dataset
+	pageInfo *iterator.PageInfo
+	nextFunc func() error
+
+	// InternalFetch is for use by the Google Cloud Libraries only.
+	// It is not part of the stable interface of this package.
+	//
+	// InternalFetch returns results from a single call to the underlying RPC.
+	// The number of results is no greater than pageSize.
+	// If there are no more results, nextPageToken is empty and err is nil.
+	InternalFetch func(pageSize int, pageToken string) (results []*automlpb.Dataset, nextPageToken string, err error)
+}
+
+// PageInfo supports pagination. See the google.golang.org/api/iterator package for details.
+func (it *DatasetIterator) PageInfo() *iterator.PageInfo {
+	return it.pageInfo
+}
+
+// Next returns the next result. Its second return value is iterator.Done if there are no more
+// results. Once Next returns Done, all subsequent calls will return Done.
+func (it *DatasetIterator) Next() (*automlpb.Dataset, error) {
+	var item *automlpb.Dataset
+	if err := it.nextFunc(); err != nil {
+		return item, err
+	}
+	item = it.items[0]
+	it.items = it.items[1:]
+	return item, nil
+}
+
+func (it *DatasetIterator) bufLen() int {
+	return len(it.items)
+}
+
+func (it *DatasetIterator) takeBuf() interface{} {
+	b := it.items
+	it.items = nil
+	return b
+}
+
+// ModelEvaluationIterator manages a stream of *automlpb.ModelEvaluation.
+type ModelEvaluationIterator struct {
+	items    []*automlpb.ModelEvaluation
+	pageInfo *iterator.PageInfo
+	nextFunc func() error
+
+	// InternalFetch is for use by the Google Cloud Libraries only.
+	// It is not part of the stable interface of this package.
+	//
+	// InternalFetch returns results from a single call to the underlying RPC.
+	// The number of results is no greater than pageSize.
+	// If there are no more results, nextPageToken is empty and err is nil.
+	InternalFetch func(pageSize int, pageToken string) (results []*automlpb.ModelEvaluation, nextPageToken string, err error)
+}
+
+// PageInfo supports pagination. See the google.golang.org/api/iterator package for details.
+func (it *ModelEvaluationIterator) PageInfo() *iterator.PageInfo {
+	return it.pageInfo
+}
+
+// Next returns the next result. Its second return value is iterator.Done if there are no more
+// results. Once Next returns Done, all subsequent calls will return Done.
+func (it *ModelEvaluationIterator) Next() (*automlpb.ModelEvaluation, error) {
+	var item *automlpb.ModelEvaluation
+	if err := it.nextFunc(); err != nil {
+		return item, err
+	}
+	item = it.items[0]
+	it.items = it.items[1:]
+	return item, nil
+}
+
+func (it *ModelEvaluationIterator) bufLen() int {
+	return len(it.items)
+}
+
+func (it *ModelEvaluationIterator) takeBuf() interface{} {
+	b := it.items
+	it.items = nil
+	return b
+}
+
+// ModelIterator manages a stream of *automlpb.Model.
+type ModelIterator struct {
+	items    []*automlpb.Model
+	pageInfo *iterator.PageInfo
+	nextFunc func() error
+
+	// InternalFetch is for use by the Google Cloud Libraries only.
+	// It is not part of the stable interface of this package.
+	//
+	// InternalFetch returns results from a single call to the underlying RPC.
+	// The number of results is no greater than pageSize.
+	// If there are no more results, nextPageToken is empty and err is nil.
+	InternalFetch func(pageSize int, pageToken string) (results []*automlpb.Model, nextPageToken string, err error)
+}
+
+// PageInfo supports pagination. See the google.golang.org/api/iterator package for details.
+func (it *ModelIterator) PageInfo() *iterator.PageInfo {
+	return it.pageInfo
+}
+
+// Next returns the next result. Its second return value is iterator.Done if there are no more
+// results. Once Next returns Done, all subsequent calls will return Done.
+func (it *ModelIterator) Next() (*automlpb.Model, error) {
+	var item *automlpb.Model
+	if err := it.nextFunc(); err != nil {
+		return item, err
+	}
+	item = it.items[0]
+	it.items = it.items[1:]
+	return item, nil
+}
+
+func (it *ModelIterator) bufLen() int {
+	return len(it.items)
+}
+
+func (it *ModelIterator) takeBuf() interface{} {
+	b := it.items
+	it.items = nil
+	return b
+}
+
+// CreateModelOperation manages a long-running operation from CreateModel.
+type CreateModelOperation struct {
+	lro *longrunning.Operation
+}
+
+// CreateModelOperation returns a new CreateModelOperation from a given name.
+// The name must be that of a previously created CreateModelOperation, possibly from a different process.
+func (c *Client) CreateModelOperation(name string) *CreateModelOperation {
+	return &CreateModelOperation{
+		lro: longrunning.InternalNewOperation(c.LROClient, &longrunningpb.Operation{Name: name}),
+	}
+}
+
+// Wait blocks until the long-running operation is completed, returning the response and any errors encountered.
+//
+// See documentation of Poll for error-handling information.
+func (op *CreateModelOperation) Wait(ctx context.Context, opts ...gax.CallOption) (*automlpb.Model, error) {
+	var resp automlpb.Model
+	if err := op.lro.WaitWithInterval(ctx, &resp, 5000*time.Millisecond, opts...); err != nil {
+		return nil, err
+	}
+	return &resp, nil
+}
+
+// Poll fetches the latest state of the long-running operation.
+//
+// Poll also fetches the latest metadata, which can be retrieved by Metadata.
+//
+// If Poll fails, the error is returned and op is unmodified. If Poll succeeds and
+// the operation has completed with failure, the error is returned and op.Done will return true.
+// If Poll succeeds and the operation has completed successfully,
+// op.Done will return true, and the response of the operation is returned.
+// If Poll succeeds and the operation has not completed, the returned response and error are both nil.
+func (op *CreateModelOperation) Poll(ctx context.Context, opts ...gax.CallOption) (*automlpb.Model, error) {
+	var resp automlpb.Model
+	if err := op.lro.Poll(ctx, &resp, opts...); err != nil {
+		return nil, err
+	}
+	if !op.Done() {
+		return nil, nil
+	}
+	return &resp, nil
+}
+
+// Metadata returns metadata associated with the long-running operation.
+// Metadata itself does not contact the server, but Poll does.
+// To get the latest metadata, call this method after a successful call to Poll.
+// If the metadata is not available, the returned metadata and error are both nil.
+func (op *CreateModelOperation) Metadata() (*automlpb.OperationMetadata, error) {
+	var meta automlpb.OperationMetadata
+	if err := op.lro.Metadata(&meta); err == longrunning.ErrNoMetadata {
+		return nil, nil
+	} else if err != nil {
+		return nil, err
+	}
+	return &meta, nil
+}
+
+// Done reports whether the long-running operation has completed.
+func (op *CreateModelOperation) Done() bool {
+	return op.lro.Done()
+}
+
+// Name returns the name of the long-running operation.
+// The name is assigned by the server and is unique within the service from which the operation is created.
+func (op *CreateModelOperation) Name() string {
+	return op.lro.Name()
+}
+
+// DeleteDatasetOperation manages a long-running operation from DeleteDataset.
+type DeleteDatasetOperation struct {
+	lro *longrunning.Operation
+}
+
+// DeleteDatasetOperation returns a new DeleteDatasetOperation from a given name.
+// The name must be that of a previously created DeleteDatasetOperation, possibly from a different process.
+func (c *Client) DeleteDatasetOperation(name string) *DeleteDatasetOperation {
+	return &DeleteDatasetOperation{
+		lro: longrunning.InternalNewOperation(c.LROClient, &longrunningpb.Operation{Name: name}),
+	}
+}
+
+// Wait blocks until the long-running operation is completed, returning any error encountered.
+//
+// See documentation of Poll for error-handling information.
+func (op *DeleteDatasetOperation) Wait(ctx context.Context, opts ...gax.CallOption) error {
+	return op.lro.WaitWithInterval(ctx, nil, 5000*time.Millisecond, opts...)
+}
+
+// Poll fetches the latest state of the long-running operation.
+//
+// Poll also fetches the latest metadata, which can be retrieved by Metadata.
+//
+// If Poll fails, the error is returned and op is unmodified. If Poll succeeds and
+// the operation has completed with failure, the error is returned and op.Done will return true.
+// If Poll succeeds and the operation has completed successfully, op.Done will return true.
+func (op *DeleteDatasetOperation) Poll(ctx context.Context, opts ...gax.CallOption) error {
+	return op.lro.Poll(ctx, nil, opts...)
+}
+
+// Metadata returns metadata associated with the long-running operation.
+// Metadata itself does not contact the server, but Poll does.
+// To get the latest metadata, call this method after a successful call to Poll.
+// If the metadata is not available, the returned metadata and error are both nil.
+func (op *DeleteDatasetOperation) Metadata() (*automlpb.OperationMetadata, error) {
+	var meta automlpb.OperationMetadata
+	if err := op.lro.Metadata(&meta); err == longrunning.ErrNoMetadata {
+		return nil, nil
+	} else if err != nil {
+		return nil, err
+	}
+	return &meta, nil
+}
+
+// Done reports whether the long-running operation has completed.
+func (op *DeleteDatasetOperation) Done() bool {
+	return op.lro.Done()
+}
+
+// Name returns the name of the long-running operation.
+// The name is assigned by the server and is unique within the service from which the operation is created.
+func (op *DeleteDatasetOperation) Name() string {
+	return op.lro.Name()
+}
+
+// DeleteModelOperation manages a long-running operation from DeleteModel.
+type DeleteModelOperation struct {
+	lro *longrunning.Operation
+}
+
+// DeleteModelOperation returns a new DeleteModelOperation from a given name.
+// The name must be that of a previously created DeleteModelOperation, possibly from a different process.
+func (c *Client) DeleteModelOperation(name string) *DeleteModelOperation {
+	return &DeleteModelOperation{
+		lro: longrunning.InternalNewOperation(c.LROClient, &longrunningpb.Operation{Name: name}),
+	}
+}
+
+// Wait blocks until the long-running operation is completed, returning any error encountered.
+//
+// See documentation of Poll for error-handling information.
+func (op *DeleteModelOperation) Wait(ctx context.Context, opts ...gax.CallOption) error {
+	return op.lro.WaitWithInterval(ctx, nil, 5000*time.Millisecond, opts...)
+}
+
+// Poll fetches the latest state of the long-running operation.
+//
+// Poll also fetches the latest metadata, which can be retrieved by Metadata.
+//
+// If Poll fails, the error is returned and op is unmodified. If Poll succeeds and
+// the operation has completed with failure, the error is returned and op.Done will return true.
+// If Poll succeeds and the operation has completed successfully, op.Done will return true.
+func (op *DeleteModelOperation) Poll(ctx context.Context, opts ...gax.CallOption) error {
+	return op.lro.Poll(ctx, nil, opts...)
+}
+
+// Metadata returns metadata associated with the long-running operation.
+// Metadata itself does not contact the server, but Poll does.
+// To get the latest metadata, call this method after a successful call to Poll.
+// If the metadata is not available, the returned metadata and error are both nil.
+func (op *DeleteModelOperation) Metadata() (*automlpb.OperationMetadata, error) {
+	var meta automlpb.OperationMetadata
+	if err := op.lro.Metadata(&meta); err == longrunning.ErrNoMetadata {
+		return nil, nil
+	} else if err != nil {
+		return nil, err
+	}
+	return &meta, nil
+}
+
+// Done reports whether the long-running operation has completed.
+func (op *DeleteModelOperation) Done() bool {
+	return op.lro.Done()
+}
+
+// Name returns the name of the long-running operation.
+// The name is assigned by the server and is unique within the service from which the operation is created.
+func (op *DeleteModelOperation) Name() string {
+	return op.lro.Name()
+}
+
+// ExportDataOperation manages a long-running operation from ExportData.
+type ExportDataOperation struct {
+	lro *longrunning.Operation
+}
+
+// ExportDataOperation returns a new ExportDataOperation from a given name.
+// The name must be that of a previously created ExportDataOperation, possibly from a different process.
+func (c *Client) ExportDataOperation(name string) *ExportDataOperation {
+	return &ExportDataOperation{
+		lro: longrunning.InternalNewOperation(c.LROClient, &longrunningpb.Operation{Name: name}),
+	}
+}
+
+// Wait blocks until the long-running operation is completed, returning any error encountered.
+//
+// See documentation of Poll for error-handling information.
+func (op *ExportDataOperation) Wait(ctx context.Context, opts ...gax.CallOption) error {
+	return op.lro.WaitWithInterval(ctx, nil, 5000*time.Millisecond, opts...)
+}
+
+// Poll fetches the latest state of the long-running operation.
+//
+// Poll also fetches the latest metadata, which can be retrieved by Metadata.
+//
+// If Poll fails, the error is returned and op is unmodified. If Poll succeeds and
+// the operation has completed with failure, the error is returned and op.Done will return true.
+// If Poll succeeds and the operation has completed successfully, op.Done will return true.
+func (op *ExportDataOperation) Poll(ctx context.Context, opts ...gax.CallOption) error {
+	return op.lro.Poll(ctx, nil, opts...)
+}
+
+// Metadata returns metadata associated with the long-running operation.
+// Metadata itself does not contact the server, but Poll does.
+// To get the latest metadata, call this method after a successful call to Poll.
+// If the metadata is not available, the returned metadata and error are both nil.
+func (op *ExportDataOperation) Metadata() (*automlpb.OperationMetadata, error) {
+	var meta automlpb.OperationMetadata
+	if err := op.lro.Metadata(&meta); err == longrunning.ErrNoMetadata {
+		return nil, nil
+	} else if err != nil {
+		return nil, err
+	}
+	return &meta, nil
+}
+
+// Done reports whether the long-running operation has completed.
+func (op *ExportDataOperation) Done() bool {
+	return op.lro.Done()
+}
+
+// Name returns the name of the long-running operation.
+// The name is assigned by the server and is unique within the service from which the operation is created.
+func (op *ExportDataOperation) Name() string {
+	return op.lro.Name()
+}
+
+// ImportDataOperation manages a long-running operation from ImportData.
+type ImportDataOperation struct {
+	lro *longrunning.Operation
+}
+
+// ImportDataOperation returns a new ImportDataOperation from a given name.
+// The name must be that of a previously created ImportDataOperation, possibly from a different process.
+func (c *Client) ImportDataOperation(name string) *ImportDataOperation {
+	return &ImportDataOperation{
+		lro: longrunning.InternalNewOperation(c.LROClient, &longrunningpb.Operation{Name: name}),
+	}
+}
+
+// Wait blocks until the long-running operation is completed, returning any error encountered.
+//
+// See documentation of Poll for error-handling information.
+func (op *ImportDataOperation) Wait(ctx context.Context, opts ...gax.CallOption) error {
+	return op.lro.WaitWithInterval(ctx, nil, 5000*time.Millisecond, opts...)
+}
+
+// Poll fetches the latest state of the long-running operation.
+//
+// Poll also fetches the latest metadata, which can be retrieved by Metadata.
+//
+// If Poll fails, the error is returned and op is unmodified. If Poll succeeds and
+// the operation has completed with failure, the error is returned and op.Done will return true.
+// If Poll succeeds and the operation has completed successfully, op.Done will return true.
+func (op *ImportDataOperation) Poll(ctx context.Context, opts ...gax.CallOption) error {
+	return op.lro.Poll(ctx, nil, opts...)
+}
+
+// Metadata returns metadata associated with the long-running operation.
+// Metadata itself does not contact the server, but Poll does.
+// To get the latest metadata, call this method after a successful call to Poll.
+// If the metadata is not available, the returned metadata and error are both nil.
+func (op *ImportDataOperation) Metadata() (*automlpb.OperationMetadata, error) {
+	var meta automlpb.OperationMetadata
+	if err := op.lro.Metadata(&meta); err == longrunning.ErrNoMetadata {
+		return nil, nil
+	} else if err != nil {
+		return nil, err
+	}
+	return &meta, nil
+}
+
+// Done reports whether the long-running operation has completed.
+func (op *ImportDataOperation) Done() bool {
+	return op.lro.Done()
+}
+
+// Name returns the name of the long-running operation.
+// The name is assigned by the server and is unique within the service from which the operation is created.
+func (op *ImportDataOperation) Name() string {
+	return op.lro.Name()
+}
diff --git a/automl/apiv1/auto_ml_client_example_test.go b/automl/apiv1/auto_ml_client_example_test.go
new file mode 100644
index 0000000..a56623e
--- /dev/null
+++ b/automl/apiv1/auto_ml_client_example_test.go
@@ -0,0 +1,314 @@
+// Copyright 2019 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 gapic-generator. DO NOT EDIT.
+
+package automl_test
+
+import (
+	"context"
+
+	automl "cloud.google.com/go/automl/apiv1"
+	"google.golang.org/api/iterator"
+	automlpb "google.golang.org/genproto/googleapis/cloud/automl/v1"
+)
+
+func ExampleNewClient() {
+	ctx := context.Background()
+	c, err := automl.NewClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+	// TODO: Use client.
+	_ = c
+}
+
+func ExampleClient_CreateDataset() {
+	ctx := context.Background()
+	c, err := automl.NewClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &automlpb.CreateDatasetRequest{
+		// TODO: Fill request struct fields.
+	}
+	resp, err := c.CreateDataset(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+	// TODO: Use resp.
+	_ = resp
+}
+
+func ExampleClient_UpdateDataset() {
+	ctx := context.Background()
+	c, err := automl.NewClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &automlpb.UpdateDatasetRequest{
+		// TODO: Fill request struct fields.
+	}
+	resp, err := c.UpdateDataset(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+	// TODO: Use resp.
+	_ = resp
+}
+
+func ExampleClient_GetDataset() {
+	ctx := context.Background()
+	c, err := automl.NewClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &automlpb.GetDatasetRequest{
+		// TODO: Fill request struct fields.
+	}
+	resp, err := c.GetDataset(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+	// TODO: Use resp.
+	_ = resp
+}
+
+func ExampleClient_ListDatasets() {
+	ctx := context.Background()
+	c, err := automl.NewClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &automlpb.ListDatasetsRequest{
+		// TODO: Fill request struct fields.
+	}
+	it := c.ListDatasets(ctx, req)
+	for {
+		resp, err := it.Next()
+		if err == iterator.Done {
+			break
+		}
+		if err != nil {
+			// TODO: Handle error.
+		}
+		// TODO: Use resp.
+		_ = resp
+	}
+}
+
+func ExampleClient_DeleteDataset() {
+	ctx := context.Background()
+	c, err := automl.NewClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &automlpb.DeleteDatasetRequest{
+		// TODO: Fill request struct fields.
+	}
+	op, err := c.DeleteDataset(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	err = op.Wait(ctx)
+	// TODO: Handle error.
+}
+
+func ExampleClient_ImportData() {
+	ctx := context.Background()
+	c, err := automl.NewClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &automlpb.ImportDataRequest{
+		// TODO: Fill request struct fields.
+	}
+	op, err := c.ImportData(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	err = op.Wait(ctx)
+	// TODO: Handle error.
+}
+
+func ExampleClient_ExportData() {
+	ctx := context.Background()
+	c, err := automl.NewClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &automlpb.ExportDataRequest{
+		// TODO: Fill request struct fields.
+	}
+	op, err := c.ExportData(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	err = op.Wait(ctx)
+	// TODO: Handle error.
+}
+
+func ExampleClient_CreateModel() {
+	ctx := context.Background()
+	c, err := automl.NewClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &automlpb.CreateModelRequest{
+		// TODO: Fill request struct fields.
+	}
+	op, err := c.CreateModel(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	resp, err := op.Wait(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+	// TODO: Use resp.
+	_ = resp
+}
+
+func ExampleClient_GetModel() {
+	ctx := context.Background()
+	c, err := automl.NewClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &automlpb.GetModelRequest{
+		// TODO: Fill request struct fields.
+	}
+	resp, err := c.GetModel(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+	// TODO: Use resp.
+	_ = resp
+}
+
+func ExampleClient_UpdateModel() {
+	ctx := context.Background()
+	c, err := automl.NewClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &automlpb.UpdateModelRequest{
+		// TODO: Fill request struct fields.
+	}
+	resp, err := c.UpdateModel(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+	// TODO: Use resp.
+	_ = resp
+}
+
+func ExampleClient_ListModels() {
+	ctx := context.Background()
+	c, err := automl.NewClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &automlpb.ListModelsRequest{
+		// TODO: Fill request struct fields.
+	}
+	it := c.ListModels(ctx, req)
+	for {
+		resp, err := it.Next()
+		if err == iterator.Done {
+			break
+		}
+		if err != nil {
+			// TODO: Handle error.
+		}
+		// TODO: Use resp.
+		_ = resp
+	}
+}
+
+func ExampleClient_DeleteModel() {
+	ctx := context.Background()
+	c, err := automl.NewClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &automlpb.DeleteModelRequest{
+		// TODO: Fill request struct fields.
+	}
+	op, err := c.DeleteModel(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	err = op.Wait(ctx)
+	// TODO: Handle error.
+}
+
+func ExampleClient_GetModelEvaluation() {
+	ctx := context.Background()
+	c, err := automl.NewClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &automlpb.GetModelEvaluationRequest{
+		// TODO: Fill request struct fields.
+	}
+	resp, err := c.GetModelEvaluation(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+	// TODO: Use resp.
+	_ = resp
+}
+
+func ExampleClient_ListModelEvaluations() {
+	ctx := context.Background()
+	c, err := automl.NewClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &automlpb.ListModelEvaluationsRequest{
+		// TODO: Fill request struct fields.
+	}
+	it := c.ListModelEvaluations(ctx, req)
+	for {
+		resp, err := it.Next()
+		if err == iterator.Done {
+			break
+		}
+		if err != nil {
+			// TODO: Handle error.
+		}
+		// TODO: Use resp.
+		_ = resp
+	}
+}
diff --git a/automl/apiv1/doc.go b/automl/apiv1/doc.go
new file mode 100644
index 0000000..0a353c3
--- /dev/null
+++ b/automl/apiv1/doc.go
@@ -0,0 +1,101 @@
+// Copyright 2019 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 gapic-generator. DO NOT EDIT.
+
+// Package automl is an auto-generated package for the
+// Cloud AutoML API.
+//
+//   NOTE: This package is in alpha. It is not stable, and is likely to change.
+//
+// Train high-quality custom machine learning models with minimum effort and
+// machine learning expertise.
+//
+// Use of Context
+//
+// The ctx passed to NewClient is used for authentication requests and
+// for creating the underlying connection, but is not used for subsequent calls.
+// Individual methods on the client use the ctx given to them.
+//
+// To close the open connection, use the Close() method.
+//
+// For information about setting deadlines, reusing contexts, and more
+// please visit godoc.org/cloud.google.com/go.
+package automl // import "cloud.google.com/go/automl/apiv1"
+
+import (
+	"context"
+	"runtime"
+	"strings"
+	"unicode"
+
+	"google.golang.org/grpc/metadata"
+)
+
+func insertMetadata(ctx context.Context, mds ...metadata.MD) context.Context {
+	out, _ := metadata.FromOutgoingContext(ctx)
+	out = out.Copy()
+	for _, md := range mds {
+		for k, v := range md {
+			out[k] = append(out[k], v...)
+		}
+	}
+	return metadata.NewOutgoingContext(ctx, out)
+}
+
+// DefaultAuthScopes reports the default set of authentication scopes to use with this package.
+func DefaultAuthScopes() []string {
+	return []string{
+		"https://www.googleapis.com/auth/cloud-platform",
+	}
+}
+
+// versionGo returns the Go runtime version. The returned string
+// has no whitespace, suitable for reporting in header.
+func versionGo() string {
+	const develPrefix = "devel +"
+
+	s := runtime.Version()
+	if strings.HasPrefix(s, develPrefix) {
+		s = s[len(develPrefix):]
+		if p := strings.IndexFunc(s, unicode.IsSpace); p >= 0 {
+			s = s[:p]
+		}
+		return s
+	}
+
+	notSemverRune := func(r rune) bool {
+		return strings.IndexRune("0123456789.", r) < 0
+	}
+
+	if strings.HasPrefix(s, "go1") {
+		s = s[2:]
+		var prerelease string
+		if p := strings.IndexFunc(s, notSemverRune); p >= 0 {
+			s, prerelease = s[:p], s[p:]
+		}
+		if strings.HasSuffix(s, ".") {
+			s += "0"
+		} else if strings.Count(s, ".") < 2 {
+			s += ".0"
+		}
+		if prerelease != "" {
+			s += "-" + prerelease
+		}
+		return s
+	}
+	return "UNKNOWN"
+}
+
+const versionClient = "20191004"
diff --git a/automl/apiv1/mock_test.go b/automl/apiv1/mock_test.go
new file mode 100644
index 0000000..89229cd
--- /dev/null
+++ b/automl/apiv1/mock_test.go
@@ -0,0 +1,1379 @@
+// Copyright 2019 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 gapic-generator. DO NOT EDIT.
+
+package automl
+
+import (
+	"context"
+	"flag"
+	"fmt"
+	"io"
+	"log"
+	"net"
+	"os"
+	"strings"
+	"testing"
+
+	"github.com/golang/protobuf/proto"
+	"github.com/golang/protobuf/ptypes"
+	emptypb "github.com/golang/protobuf/ptypes/empty"
+	"google.golang.org/api/option"
+	automlpb "google.golang.org/genproto/googleapis/cloud/automl/v1"
+	longrunningpb "google.golang.org/genproto/googleapis/longrunning"
+	field_maskpb "google.golang.org/genproto/protobuf/field_mask"
+
+	status "google.golang.org/genproto/googleapis/rpc/status"
+	"google.golang.org/grpc"
+	"google.golang.org/grpc/codes"
+	"google.golang.org/grpc/metadata"
+
+	gstatus "google.golang.org/grpc/status"
+)
+
+var _ = io.EOF
+var _ = ptypes.MarshalAny
+var _ status.Status
+
+type mockAutoMlServer struct {
+	// Embed for forward compatibility.
+	// Tests will keep working if more methods are added
+	// in the future.
+	automlpb.AutoMlServer
+
+	reqs []proto.Message
+
+	// If set, all calls return this error.
+	err error
+
+	// responses to return if err == nil
+	resps []proto.Message
+}
+
+func (s *mockAutoMlServer) CreateDataset(ctx context.Context, req *automlpb.CreateDatasetRequest) (*longrunningpb.Operation, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*longrunningpb.Operation), nil
+}
+
+func (s *mockAutoMlServer) GetDataset(ctx context.Context, req *automlpb.GetDatasetRequest) (*automlpb.Dataset, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*automlpb.Dataset), nil
+}
+
+func (s *mockAutoMlServer) ListDatasets(ctx context.Context, req *automlpb.ListDatasetsRequest) (*automlpb.ListDatasetsResponse, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*automlpb.ListDatasetsResponse), nil
+}
+
+func (s *mockAutoMlServer) UpdateDataset(ctx context.Context, req *automlpb.UpdateDatasetRequest) (*automlpb.Dataset, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*automlpb.Dataset), nil
+}
+
+func (s *mockAutoMlServer) DeleteDataset(ctx context.Context, req *automlpb.DeleteDatasetRequest) (*longrunningpb.Operation, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*longrunningpb.Operation), nil
+}
+
+func (s *mockAutoMlServer) ImportData(ctx context.Context, req *automlpb.ImportDataRequest) (*longrunningpb.Operation, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*longrunningpb.Operation), nil
+}
+
+func (s *mockAutoMlServer) ExportData(ctx context.Context, req *automlpb.ExportDataRequest) (*longrunningpb.Operation, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*longrunningpb.Operation), nil
+}
+
+func (s *mockAutoMlServer) CreateModel(ctx context.Context, req *automlpb.CreateModelRequest) (*longrunningpb.Operation, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*longrunningpb.Operation), nil
+}
+
+func (s *mockAutoMlServer) GetModel(ctx context.Context, req *automlpb.GetModelRequest) (*automlpb.Model, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*automlpb.Model), nil
+}
+
+func (s *mockAutoMlServer) ListModels(ctx context.Context, req *automlpb.ListModelsRequest) (*automlpb.ListModelsResponse, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*automlpb.ListModelsResponse), nil
+}
+
+func (s *mockAutoMlServer) DeleteModel(ctx context.Context, req *automlpb.DeleteModelRequest) (*longrunningpb.Operation, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*longrunningpb.Operation), nil
+}
+
+func (s *mockAutoMlServer) UpdateModel(ctx context.Context, req *automlpb.UpdateModelRequest) (*automlpb.Model, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*automlpb.Model), nil
+}
+
+func (s *mockAutoMlServer) GetModelEvaluation(ctx context.Context, req *automlpb.GetModelEvaluationRequest) (*automlpb.ModelEvaluation, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*automlpb.ModelEvaluation), nil
+}
+
+func (s *mockAutoMlServer) ListModelEvaluations(ctx context.Context, req *automlpb.ListModelEvaluationsRequest) (*automlpb.ListModelEvaluationsResponse, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*automlpb.ListModelEvaluationsResponse), nil
+}
+
+type mockPredictionServer struct {
+	// Embed for forward compatibility.
+	// Tests will keep working if more methods are added
+	// in the future.
+	automlpb.PredictionServiceServer
+
+	reqs []proto.Message
+
+	// If set, all calls return this error.
+	err error
+
+	// responses to return if err == nil
+	resps []proto.Message
+}
+
+func (s *mockPredictionServer) Predict(ctx context.Context, req *automlpb.PredictRequest) (*automlpb.PredictResponse, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*automlpb.PredictResponse), nil
+}
+
+// clientOpt is the option tests should use to connect to the test server.
+// It is initialized by TestMain.
+var clientOpt option.ClientOption
+
+var (
+	mockAutoMl     mockAutoMlServer
+	mockPrediction mockPredictionServer
+)
+
+func TestMain(m *testing.M) {
+	flag.Parse()
+
+	serv := grpc.NewServer()
+	automlpb.RegisterAutoMlServer(serv, &mockAutoMl)
+	automlpb.RegisterPredictionServiceServer(serv, &mockPrediction)
+
+	lis, err := net.Listen("tcp", "localhost:0")
+	if err != nil {
+		log.Fatal(err)
+	}
+	go serv.Serve(lis)
+
+	conn, err := grpc.Dial(lis.Addr().String(), grpc.WithInsecure())
+	if err != nil {
+		log.Fatal(err)
+	}
+	clientOpt = option.WithGRPCConn(conn)
+
+	os.Exit(m.Run())
+}
+
+func TestAutoMlCreateDataset(t *testing.T) {
+	var name string = "name3373707"
+	var done bool = true
+	var expectedResponse = &longrunningpb.Operation{
+		Name: name,
+		Done: done,
+	}
+
+	mockAutoMl.err = nil
+	mockAutoMl.reqs = nil
+
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], expectedResponse)
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var dataset *automlpb.Dataset = &automlpb.Dataset{}
+	var request = &automlpb.CreateDatasetRequest{
+		Parent:  formattedParent,
+		Dataset: dataset,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.CreateDataset(context.Background(), request)
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockAutoMl.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	if want, got := expectedResponse, resp; !proto.Equal(want, got) {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestAutoMlCreateDatasetError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockAutoMl.err = gstatus.Error(errCode, "test error")
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var dataset *automlpb.Dataset = &automlpb.Dataset{}
+	var request = &automlpb.CreateDatasetRequest{
+		Parent:  formattedParent,
+		Dataset: dataset,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.CreateDataset(context.Background(), request)
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
+func TestAutoMlUpdateDataset(t *testing.T) {
+	var name string = "name3373707"
+	var displayName string = "displayName1615086568"
+	var description string = "description-1724546052"
+	var exampleCount int32 = 1517063674
+	var etag string = "etag3123477"
+	var expectedResponse = &automlpb.Dataset{
+		Name:         name,
+		DisplayName:  displayName,
+		Description:  description,
+		ExampleCount: exampleCount,
+		Etag:         etag,
+	}
+
+	mockAutoMl.err = nil
+	mockAutoMl.reqs = nil
+
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], expectedResponse)
+
+	var dataset *automlpb.Dataset = &automlpb.Dataset{}
+	var updateMask *field_maskpb.FieldMask = &field_maskpb.FieldMask{}
+	var request = &automlpb.UpdateDatasetRequest{
+		Dataset:    dataset,
+		UpdateMask: updateMask,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.UpdateDataset(context.Background(), request)
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockAutoMl.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	if want, got := expectedResponse, resp; !proto.Equal(want, got) {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestAutoMlUpdateDatasetError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockAutoMl.err = gstatus.Error(errCode, "test error")
+
+	var dataset *automlpb.Dataset = &automlpb.Dataset{}
+	var updateMask *field_maskpb.FieldMask = &field_maskpb.FieldMask{}
+	var request = &automlpb.UpdateDatasetRequest{
+		Dataset:    dataset,
+		UpdateMask: updateMask,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.UpdateDataset(context.Background(), request)
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
+func TestAutoMlGetDataset(t *testing.T) {
+	var name2 string = "name2-1052831874"
+	var displayName string = "displayName1615086568"
+	var description string = "description-1724546052"
+	var exampleCount int32 = 1517063674
+	var etag string = "etag3123477"
+	var expectedResponse = &automlpb.Dataset{
+		Name:         name2,
+		DisplayName:  displayName,
+		Description:  description,
+		ExampleCount: exampleCount,
+		Etag:         etag,
+	}
+
+	mockAutoMl.err = nil
+	mockAutoMl.reqs = nil
+
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], expectedResponse)
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/datasets/%s", "[PROJECT]", "[LOCATION]", "[DATASET]")
+	var request = &automlpb.GetDatasetRequest{
+		Name: formattedName,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.GetDataset(context.Background(), request)
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockAutoMl.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	if want, got := expectedResponse, resp; !proto.Equal(want, got) {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestAutoMlGetDatasetError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockAutoMl.err = gstatus.Error(errCode, "test error")
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/datasets/%s", "[PROJECT]", "[LOCATION]", "[DATASET]")
+	var request = &automlpb.GetDatasetRequest{
+		Name: formattedName,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.GetDataset(context.Background(), request)
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
+func TestAutoMlListDatasets(t *testing.T) {
+	var nextPageToken string = ""
+	var datasetsElement *automlpb.Dataset = &automlpb.Dataset{}
+	var datasets = []*automlpb.Dataset{datasetsElement}
+	var expectedResponse = &automlpb.ListDatasetsResponse{
+		NextPageToken: nextPageToken,
+		Datasets:      datasets,
+	}
+
+	mockAutoMl.err = nil
+	mockAutoMl.reqs = nil
+
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], expectedResponse)
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var request = &automlpb.ListDatasetsRequest{
+		Parent: formattedParent,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.ListDatasets(context.Background(), request).Next()
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockAutoMl.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	want := (interface{})(expectedResponse.Datasets[0])
+	got := (interface{})(resp)
+	var ok bool
+
+	switch want := (want).(type) {
+	case proto.Message:
+		ok = proto.Equal(want, got.(proto.Message))
+	default:
+		ok = want == got
+	}
+	if !ok {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestAutoMlListDatasetsError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockAutoMl.err = gstatus.Error(errCode, "test error")
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var request = &automlpb.ListDatasetsRequest{
+		Parent: formattedParent,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.ListDatasets(context.Background(), request).Next()
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
+func TestAutoMlDeleteDataset(t *testing.T) {
+	var expectedResponse *emptypb.Empty = &emptypb.Empty{}
+
+	mockAutoMl.err = nil
+	mockAutoMl.reqs = nil
+
+	any, err := ptypes.MarshalAny(expectedResponse)
+	if err != nil {
+		t.Fatal(err)
+	}
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], &longrunningpb.Operation{
+		Name:   "longrunning-test",
+		Done:   true,
+		Result: &longrunningpb.Operation_Response{Response: any},
+	})
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/datasets/%s", "[PROJECT]", "[LOCATION]", "[DATASET]")
+	var request = &automlpb.DeleteDatasetRequest{
+		Name: formattedName,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	respLRO, err := c.DeleteDataset(context.Background(), request)
+	if err != nil {
+		t.Fatal(err)
+	}
+	err = respLRO.Wait(context.Background())
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockAutoMl.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+}
+
+func TestAutoMlDeleteDatasetError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockAutoMl.err = nil
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], &longrunningpb.Operation{
+		Name: "longrunning-test",
+		Done: true,
+		Result: &longrunningpb.Operation_Error{
+			Error: &status.Status{
+				Code:    int32(errCode),
+				Message: "test error",
+			},
+		},
+	})
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/datasets/%s", "[PROJECT]", "[LOCATION]", "[DATASET]")
+	var request = &automlpb.DeleteDatasetRequest{
+		Name: formattedName,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	respLRO, err := c.DeleteDataset(context.Background(), request)
+	if err != nil {
+		t.Fatal(err)
+	}
+	err = respLRO.Wait(context.Background())
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+}
+func TestAutoMlImportData(t *testing.T) {
+	var expectedResponse *emptypb.Empty = &emptypb.Empty{}
+
+	mockAutoMl.err = nil
+	mockAutoMl.reqs = nil
+
+	any, err := ptypes.MarshalAny(expectedResponse)
+	if err != nil {
+		t.Fatal(err)
+	}
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], &longrunningpb.Operation{
+		Name:   "longrunning-test",
+		Done:   true,
+		Result: &longrunningpb.Operation_Response{Response: any},
+	})
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/datasets/%s", "[PROJECT]", "[LOCATION]", "[DATASET]")
+	var inputConfig *automlpb.InputConfig = &automlpb.InputConfig{}
+	var request = &automlpb.ImportDataRequest{
+		Name:        formattedName,
+		InputConfig: inputConfig,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	respLRO, err := c.ImportData(context.Background(), request)
+	if err != nil {
+		t.Fatal(err)
+	}
+	err = respLRO.Wait(context.Background())
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockAutoMl.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+}
+
+func TestAutoMlImportDataError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockAutoMl.err = nil
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], &longrunningpb.Operation{
+		Name: "longrunning-test",
+		Done: true,
+		Result: &longrunningpb.Operation_Error{
+			Error: &status.Status{
+				Code:    int32(errCode),
+				Message: "test error",
+			},
+		},
+	})
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/datasets/%s", "[PROJECT]", "[LOCATION]", "[DATASET]")
+	var inputConfig *automlpb.InputConfig = &automlpb.InputConfig{}
+	var request = &automlpb.ImportDataRequest{
+		Name:        formattedName,
+		InputConfig: inputConfig,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	respLRO, err := c.ImportData(context.Background(), request)
+	if err != nil {
+		t.Fatal(err)
+	}
+	err = respLRO.Wait(context.Background())
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+}
+func TestAutoMlExportData(t *testing.T) {
+	var expectedResponse *emptypb.Empty = &emptypb.Empty{}
+
+	mockAutoMl.err = nil
+	mockAutoMl.reqs = nil
+
+	any, err := ptypes.MarshalAny(expectedResponse)
+	if err != nil {
+		t.Fatal(err)
+	}
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], &longrunningpb.Operation{
+		Name:   "longrunning-test",
+		Done:   true,
+		Result: &longrunningpb.Operation_Response{Response: any},
+	})
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/datasets/%s", "[PROJECT]", "[LOCATION]", "[DATASET]")
+	var outputConfig *automlpb.OutputConfig = &automlpb.OutputConfig{}
+	var request = &automlpb.ExportDataRequest{
+		Name:         formattedName,
+		OutputConfig: outputConfig,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	respLRO, err := c.ExportData(context.Background(), request)
+	if err != nil {
+		t.Fatal(err)
+	}
+	err = respLRO.Wait(context.Background())
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockAutoMl.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+}
+
+func TestAutoMlExportDataError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockAutoMl.err = nil
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], &longrunningpb.Operation{
+		Name: "longrunning-test",
+		Done: true,
+		Result: &longrunningpb.Operation_Error{
+			Error: &status.Status{
+				Code:    int32(errCode),
+				Message: "test error",
+			},
+		},
+	})
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/datasets/%s", "[PROJECT]", "[LOCATION]", "[DATASET]")
+	var outputConfig *automlpb.OutputConfig = &automlpb.OutputConfig{}
+	var request = &automlpb.ExportDataRequest{
+		Name:         formattedName,
+		OutputConfig: outputConfig,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	respLRO, err := c.ExportData(context.Background(), request)
+	if err != nil {
+		t.Fatal(err)
+	}
+	err = respLRO.Wait(context.Background())
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+}
+func TestAutoMlCreateModel(t *testing.T) {
+	var name string = "name3373707"
+	var displayName string = "displayName1615086568"
+	var datasetId string = "datasetId-2115646910"
+	var expectedResponse = &automlpb.Model{
+		Name:        name,
+		DisplayName: displayName,
+		DatasetId:   datasetId,
+	}
+
+	mockAutoMl.err = nil
+	mockAutoMl.reqs = nil
+
+	any, err := ptypes.MarshalAny(expectedResponse)
+	if err != nil {
+		t.Fatal(err)
+	}
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], &longrunningpb.Operation{
+		Name:   "longrunning-test",
+		Done:   true,
+		Result: &longrunningpb.Operation_Response{Response: any},
+	})
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var model *automlpb.Model = &automlpb.Model{}
+	var request = &automlpb.CreateModelRequest{
+		Parent: formattedParent,
+		Model:  model,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	respLRO, err := c.CreateModel(context.Background(), request)
+	if err != nil {
+		t.Fatal(err)
+	}
+	resp, err := respLRO.Wait(context.Background())
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockAutoMl.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	if want, got := expectedResponse, resp; !proto.Equal(want, got) {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestAutoMlCreateModelError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockAutoMl.err = nil
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], &longrunningpb.Operation{
+		Name: "longrunning-test",
+		Done: true,
+		Result: &longrunningpb.Operation_Error{
+			Error: &status.Status{
+				Code:    int32(errCode),
+				Message: "test error",
+			},
+		},
+	})
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var model *automlpb.Model = &automlpb.Model{}
+	var request = &automlpb.CreateModelRequest{
+		Parent: formattedParent,
+		Model:  model,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	respLRO, err := c.CreateModel(context.Background(), request)
+	if err != nil {
+		t.Fatal(err)
+	}
+	resp, err := respLRO.Wait(context.Background())
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
+func TestAutoMlGetModel(t *testing.T) {
+	var name2 string = "name2-1052831874"
+	var displayName string = "displayName1615086568"
+	var datasetId string = "datasetId-2115646910"
+	var expectedResponse = &automlpb.Model{
+		Name:        name2,
+		DisplayName: displayName,
+		DatasetId:   datasetId,
+	}
+
+	mockAutoMl.err = nil
+	mockAutoMl.reqs = nil
+
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], expectedResponse)
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/models/%s", "[PROJECT]", "[LOCATION]", "[MODEL]")
+	var request = &automlpb.GetModelRequest{
+		Name: formattedName,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.GetModel(context.Background(), request)
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockAutoMl.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	if want, got := expectedResponse, resp; !proto.Equal(want, got) {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestAutoMlGetModelError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockAutoMl.err = gstatus.Error(errCode, "test error")
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/models/%s", "[PROJECT]", "[LOCATION]", "[MODEL]")
+	var request = &automlpb.GetModelRequest{
+		Name: formattedName,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.GetModel(context.Background(), request)
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
+func TestAutoMlUpdateModel(t *testing.T) {
+	var name string = "name3373707"
+	var displayName string = "displayName1615086568"
+	var datasetId string = "datasetId-2115646910"
+	var expectedResponse = &automlpb.Model{
+		Name:        name,
+		DisplayName: displayName,
+		DatasetId:   datasetId,
+	}
+
+	mockAutoMl.err = nil
+	mockAutoMl.reqs = nil
+
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], expectedResponse)
+
+	var model *automlpb.Model = &automlpb.Model{}
+	var updateMask *field_maskpb.FieldMask = &field_maskpb.FieldMask{}
+	var request = &automlpb.UpdateModelRequest{
+		Model:      model,
+		UpdateMask: updateMask,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.UpdateModel(context.Background(), request)
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockAutoMl.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	if want, got := expectedResponse, resp; !proto.Equal(want, got) {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestAutoMlUpdateModelError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockAutoMl.err = gstatus.Error(errCode, "test error")
+
+	var model *automlpb.Model = &automlpb.Model{}
+	var updateMask *field_maskpb.FieldMask = &field_maskpb.FieldMask{}
+	var request = &automlpb.UpdateModelRequest{
+		Model:      model,
+		UpdateMask: updateMask,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.UpdateModel(context.Background(), request)
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
+func TestAutoMlListModels(t *testing.T) {
+	var nextPageToken string = ""
+	var modelElement *automlpb.Model = &automlpb.Model{}
+	var model = []*automlpb.Model{modelElement}
+	var expectedResponse = &automlpb.ListModelsResponse{
+		NextPageToken: nextPageToken,
+		Model:         model,
+	}
+
+	mockAutoMl.err = nil
+	mockAutoMl.reqs = nil
+
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], expectedResponse)
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var request = &automlpb.ListModelsRequest{
+		Parent: formattedParent,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.ListModels(context.Background(), request).Next()
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockAutoMl.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	want := (interface{})(expectedResponse.Model[0])
+	got := (interface{})(resp)
+	var ok bool
+
+	switch want := (want).(type) {
+	case proto.Message:
+		ok = proto.Equal(want, got.(proto.Message))
+	default:
+		ok = want == got
+	}
+	if !ok {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestAutoMlListModelsError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockAutoMl.err = gstatus.Error(errCode, "test error")
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var request = &automlpb.ListModelsRequest{
+		Parent: formattedParent,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.ListModels(context.Background(), request).Next()
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
+func TestAutoMlDeleteModel(t *testing.T) {
+	var expectedResponse *emptypb.Empty = &emptypb.Empty{}
+
+	mockAutoMl.err = nil
+	mockAutoMl.reqs = nil
+
+	any, err := ptypes.MarshalAny(expectedResponse)
+	if err != nil {
+		t.Fatal(err)
+	}
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], &longrunningpb.Operation{
+		Name:   "longrunning-test",
+		Done:   true,
+		Result: &longrunningpb.Operation_Response{Response: any},
+	})
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/models/%s", "[PROJECT]", "[LOCATION]", "[MODEL]")
+	var request = &automlpb.DeleteModelRequest{
+		Name: formattedName,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	respLRO, err := c.DeleteModel(context.Background(), request)
+	if err != nil {
+		t.Fatal(err)
+	}
+	err = respLRO.Wait(context.Background())
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockAutoMl.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+}
+
+func TestAutoMlDeleteModelError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockAutoMl.err = nil
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], &longrunningpb.Operation{
+		Name: "longrunning-test",
+		Done: true,
+		Result: &longrunningpb.Operation_Error{
+			Error: &status.Status{
+				Code:    int32(errCode),
+				Message: "test error",
+			},
+		},
+	})
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/models/%s", "[PROJECT]", "[LOCATION]", "[MODEL]")
+	var request = &automlpb.DeleteModelRequest{
+		Name: formattedName,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	respLRO, err := c.DeleteModel(context.Background(), request)
+	if err != nil {
+		t.Fatal(err)
+	}
+	err = respLRO.Wait(context.Background())
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+}
+func TestAutoMlGetModelEvaluation(t *testing.T) {
+	var name2 string = "name2-1052831874"
+	var annotationSpecId string = "annotationSpecId60690191"
+	var evaluatedExampleCount int32 = 277565350
+	var expectedResponse = &automlpb.ModelEvaluation{
+		Name:                  name2,
+		AnnotationSpecId:      annotationSpecId,
+		EvaluatedExampleCount: evaluatedExampleCount,
+	}
+
+	mockAutoMl.err = nil
+	mockAutoMl.reqs = nil
+
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], expectedResponse)
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/models/%s/modelEvaluations/%s", "[PROJECT]", "[LOCATION]", "[MODEL]", "[MODEL_EVALUATION]")
+	var request = &automlpb.GetModelEvaluationRequest{
+		Name: formattedName,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.GetModelEvaluation(context.Background(), request)
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockAutoMl.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	if want, got := expectedResponse, resp; !proto.Equal(want, got) {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestAutoMlGetModelEvaluationError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockAutoMl.err = gstatus.Error(errCode, "test error")
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/models/%s/modelEvaluations/%s", "[PROJECT]", "[LOCATION]", "[MODEL]", "[MODEL_EVALUATION]")
+	var request = &automlpb.GetModelEvaluationRequest{
+		Name: formattedName,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.GetModelEvaluation(context.Background(), request)
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
+func TestAutoMlListModelEvaluations(t *testing.T) {
+	var nextPageToken string = ""
+	var modelEvaluationElement *automlpb.ModelEvaluation = &automlpb.ModelEvaluation{}
+	var modelEvaluation = []*automlpb.ModelEvaluation{modelEvaluationElement}
+	var expectedResponse = &automlpb.ListModelEvaluationsResponse{
+		NextPageToken:   nextPageToken,
+		ModelEvaluation: modelEvaluation,
+	}
+
+	mockAutoMl.err = nil
+	mockAutoMl.reqs = nil
+
+	mockAutoMl.resps = append(mockAutoMl.resps[:0], expectedResponse)
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s/models/%s", "[PROJECT]", "[LOCATION]", "[MODEL]")
+	var filter string = "filter-1274492040"
+	var request = &automlpb.ListModelEvaluationsRequest{
+		Parent: formattedParent,
+		Filter: filter,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.ListModelEvaluations(context.Background(), request).Next()
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockAutoMl.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	want := (interface{})(expectedResponse.ModelEvaluation[0])
+	got := (interface{})(resp)
+	var ok bool
+
+	switch want := (want).(type) {
+	case proto.Message:
+		ok = proto.Equal(want, got.(proto.Message))
+	default:
+		ok = want == got
+	}
+	if !ok {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestAutoMlListModelEvaluationsError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockAutoMl.err = gstatus.Error(errCode, "test error")
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s/models/%s", "[PROJECT]", "[LOCATION]", "[MODEL]")
+	var filter string = "filter-1274492040"
+	var request = &automlpb.ListModelEvaluationsRequest{
+		Parent: formattedParent,
+		Filter: filter,
+	}
+
+	c, err := NewClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.ListModelEvaluations(context.Background(), request).Next()
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
+func TestPredictionServicePredict(t *testing.T) {
+	var expectedResponse *automlpb.PredictResponse = &automlpb.PredictResponse{}
+
+	mockPrediction.err = nil
+	mockPrediction.reqs = nil
+
+	mockPrediction.resps = append(mockPrediction.resps[:0], expectedResponse)
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/models/%s", "[PROJECT]", "[LOCATION]", "[MODEL]")
+	var payload *automlpb.ExamplePayload = &automlpb.ExamplePayload{}
+	var request = &automlpb.PredictRequest{
+		Name:    formattedName,
+		Payload: payload,
+	}
+
+	c, err := NewPredictionClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.Predict(context.Background(), request)
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockPrediction.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	if want, got := expectedResponse, resp; !proto.Equal(want, got) {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestPredictionServicePredictError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockPrediction.err = gstatus.Error(errCode, "test error")
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/models/%s", "[PROJECT]", "[LOCATION]", "[MODEL]")
+	var payload *automlpb.ExamplePayload = &automlpb.ExamplePayload{}
+	var request = &automlpb.PredictRequest{
+		Name:    formattedName,
+		Payload: payload,
+	}
+
+	c, err := NewPredictionClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.Predict(context.Background(), request)
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
diff --git a/automl/apiv1/prediction_client.go b/automl/apiv1/prediction_client.go
new file mode 100644
index 0000000..aadac67
--- /dev/null
+++ b/automl/apiv1/prediction_client.go
@@ -0,0 +1,132 @@
+// Copyright 2019 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 gapic-generator. DO NOT EDIT.
+
+package automl
+
+import (
+	"context"
+	"fmt"
+	"math"
+	"net/url"
+
+	gax "github.com/googleapis/gax-go/v2"
+	"google.golang.org/api/option"
+	"google.golang.org/api/transport"
+	automlpb "google.golang.org/genproto/googleapis/cloud/automl/v1"
+	"google.golang.org/grpc"
+	"google.golang.org/grpc/metadata"
+)
+
+// PredictionCallOptions contains the retry settings for each method of PredictionClient.
+type PredictionCallOptions struct {
+	Predict []gax.CallOption
+}
+
+func defaultPredictionClientOptions() []option.ClientOption {
+	return []option.ClientOption{
+		option.WithEndpoint("automl.googleapis.com:443"),
+		option.WithScopes(DefaultAuthScopes()...),
+		option.WithGRPCDialOption(grpc.WithDefaultCallOptions(
+			grpc.MaxCallRecvMsgSize(math.MaxInt32))),
+	}
+}
+
+func defaultPredictionCallOptions() *PredictionCallOptions {
+	retry := map[[2]string][]gax.CallOption{}
+	return &PredictionCallOptions{
+		Predict: retry[[2]string{"default", "non_idempotent"}],
+	}
+}
+
+// PredictionClient is a client for interacting with Cloud AutoML API.
+//
+// Methods, except Close, may be called concurrently. However, fields must not be modified concurrently with method calls.
+type PredictionClient struct {
+	// The connection to the service.
+	conn *grpc.ClientConn
+
+	// The gRPC API client.
+	predictionClient automlpb.PredictionServiceClient
+
+	// The call options for this service.
+	CallOptions *PredictionCallOptions
+
+	// The x-goog-* metadata to be sent with each request.
+	xGoogMetadata metadata.MD
+}
+
+// NewPredictionClient creates a new prediction service client.
+//
+// AutoML Prediction API.
+//
+// On any input that is documented to expect a string parameter in
+// snake_case or kebab-case, either of those cases is accepted.
+func NewPredictionClient(ctx context.Context, opts ...option.ClientOption) (*PredictionClient, error) {
+	conn, err := transport.DialGRPC(ctx, append(defaultPredictionClientOptions(), opts...)...)
+	if err != nil {
+		return nil, err
+	}
+	c := &PredictionClient{
+		conn:        conn,
+		CallOptions: defaultPredictionCallOptions(),
+
+		predictionClient: automlpb.NewPredictionServiceClient(conn),
+	}
+	c.setGoogleClientInfo()
+	return c, nil
+}
+
+// Connection returns the client's connection to the API service.
+func (c *PredictionClient) Connection() *grpc.ClientConn {
+	return c.conn
+}
+
+// Close closes the connection to the API service. The user should invoke this when
+// the client is no longer required.
+func (c *PredictionClient) Close() error {
+	return c.conn.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 *PredictionClient) setGoogleClientInfo(keyval ...string) {
+	kv := append([]string{"gl-go", versionGo()}, keyval...)
+	kv = append(kv, "gapic", versionClient, "gax", gax.Version, "grpc", grpc.Version)
+	c.xGoogMetadata = metadata.Pairs("x-goog-api-client", gax.XGoogHeader(kv...))
+}
+
+// Predict perform an online prediction. The prediction result will be directly
+// returned in the response.
+// Available for following ML problems, and their expected request payloads:
+//
+//   Translation - TextSnippet, content up to 25,000 characters, UTF-8
+//   encoded.
+func (c *PredictionClient) Predict(ctx context.Context, req *automlpb.PredictRequest, opts ...gax.CallOption) (*automlpb.PredictResponse, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.Predict[0:len(c.CallOptions.Predict):len(c.CallOptions.Predict)], opts...)
+	var resp *automlpb.PredictResponse
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.predictionClient.Predict(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return resp, nil
+}
diff --git a/automl/apiv1/prediction_client_example_test.go b/automl/apiv1/prediction_client_example_test.go
new file mode 100644
index 0000000..475d3e5
--- /dev/null
+++ b/automl/apiv1/prediction_client_example_test.go
@@ -0,0 +1,52 @@
+// Copyright 2019 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 gapic-generator. DO NOT EDIT.
+
+package automl_test
+
+import (
+	"context"
+
+	automl "cloud.google.com/go/automl/apiv1"
+	automlpb "google.golang.org/genproto/googleapis/cloud/automl/v1"
+)
+
+func ExampleNewPredictionClient() {
+	ctx := context.Background()
+	c, err := automl.NewPredictionClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+	// TODO: Use client.
+	_ = c
+}
+
+func ExamplePredictionClient_Predict() {
+	ctx := context.Background()
+	c, err := automl.NewPredictionClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &automlpb.PredictRequest{
+		// TODO: Fill request struct fields.
+	}
+	resp, err := c.Predict(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+	// TODO: Use resp.
+	_ = resp
+}
diff --git a/automl/apiv1beta1/doc.go b/automl/apiv1beta1/doc.go
index 8749b41..49ceba9 100644
--- a/automl/apiv1beta1/doc.go
+++ b/automl/apiv1beta1/doc.go
@@ -98,4 +98,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/bigquery/datatransfer/apiv1/doc.go b/bigquery/datatransfer/apiv1/doc.go
index 8262ff2..c4f1d9f 100644
--- a/bigquery/datatransfer/apiv1/doc.go
+++ b/bigquery/datatransfer/apiv1/doc.go
@@ -99,4 +99,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/bigquery/storage/apiv1beta1/doc.go b/bigquery/storage/apiv1beta1/doc.go
index 62c32be..3274a6e 100644
--- a/bigquery/storage/apiv1beta1/doc.go
+++ b/bigquery/storage/apiv1beta1/doc.go
@@ -98,4 +98,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/cloudtasks/apiv2/doc.go b/cloudtasks/apiv2/doc.go
index 7cba675..dea8394 100644
--- a/cloudtasks/apiv2/doc.go
+++ b/cloudtasks/apiv2/doc.go
@@ -96,4 +96,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/cloudtasks/apiv2beta2/doc.go b/cloudtasks/apiv2beta2/doc.go
index 37592a6..576456f 100644
--- a/cloudtasks/apiv2beta2/doc.go
+++ b/cloudtasks/apiv2beta2/doc.go
@@ -97,4 +97,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/cloudtasks/apiv2beta3/doc.go b/cloudtasks/apiv2beta3/doc.go
index 1b43da6..b8dee54 100644
--- a/cloudtasks/apiv2beta3/doc.go
+++ b/cloudtasks/apiv2beta3/doc.go
@@ -97,4 +97,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/containeranalysis/apiv1beta1/doc.go b/containeranalysis/apiv1beta1/doc.go
index f88feed..7d58c11 100644
--- a/containeranalysis/apiv1beta1/doc.go
+++ b/containeranalysis/apiv1beta1/doc.go
@@ -99,4 +99,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/dataproc/apiv1/doc.go b/dataproc/apiv1/doc.go
index 1ae9e76..c9b0eaa 100644
--- a/dataproc/apiv1/doc.go
+++ b/dataproc/apiv1/doc.go
@@ -97,4 +97,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/dataproc/apiv1beta2/doc.go b/dataproc/apiv1beta2/doc.go
index 5e5d5c0..98a69dc 100644
--- a/dataproc/apiv1beta2/doc.go
+++ b/dataproc/apiv1beta2/doc.go
@@ -97,4 +97,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/debugger/apiv2/doc.go b/debugger/apiv2/doc.go
index 6b68314..1f4bb0f 100644
--- a/debugger/apiv2/doc.go
+++ b/debugger/apiv2/doc.go
@@ -101,4 +101,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/dialogflow/apiv2/doc.go b/dialogflow/apiv2/doc.go
index cb1c8b6..a642c4d 100644
--- a/dialogflow/apiv2/doc.go
+++ b/dialogflow/apiv2/doc.go
@@ -99,4 +99,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/dlp/apiv2/doc.go b/dlp/apiv2/doc.go
index 17e03a5..d234d63 100644
--- a/dlp/apiv2/doc.go
+++ b/dlp/apiv2/doc.go
@@ -98,4 +98,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/errorreporting/apiv1beta1/doc.go b/errorreporting/apiv1beta1/doc.go
index 0fff4b3..da89fa4 100644
--- a/errorreporting/apiv1beta1/doc.go
+++ b/errorreporting/apiv1beta1/doc.go
@@ -101,4 +101,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/expr/apiv1alpha1/doc.go b/expr/apiv1alpha1/doc.go
index 0def90b..6a60bb4 100644
--- a/expr/apiv1alpha1/doc.go
+++ b/expr/apiv1alpha1/doc.go
@@ -95,4 +95,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20190925"
+const versionClient = "20191004"
diff --git a/firestore/apiv1/admin/doc.go b/firestore/apiv1/admin/doc.go
index 4b45c44..8d8ecac 100644
--- a/firestore/apiv1/admin/doc.go
+++ b/firestore/apiv1/admin/doc.go
@@ -99,4 +99,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/firestore/apiv1beta1/doc.go b/firestore/apiv1beta1/doc.go
index 4ed1bbc..76d9c27 100644
--- a/firestore/apiv1beta1/doc.go
+++ b/firestore/apiv1beta1/doc.go
@@ -99,4 +99,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/gapics.txt b/gapics.txt
index dfb543c..5234693 100644
--- a/gapics.txt
+++ b/gapics.txt
@@ -4,6 +4,7 @@
 google/cloud/asset/artman_cloudasset_v1p2beta1.yaml
 google/cloud/asset/artman_cloudasset_v1.yaml
 google/iam/credentials/artman_iamcredentials_v1.yaml
+google/cloud/automl/artman_automl_v1.yaml
 google/cloud/automl/artman_automl_v1beta1.yaml
 google/cloud/bigquery/datatransfer/artman_bigquerydatatransfer.yaml
 google/cloud/bigquery/storage/artman_bigquerystorage_v1beta1.yaml
@@ -32,6 +33,7 @@
 google/cloud/tasks/artman_cloudtasks_v2beta2.yaml
 google/cloud/tasks/artman_cloudtasks_v2beta3.yaml
 google/cloud/tasks/artman_cloudtasks_v2.yaml
+google/cloud/translate/artman_translate_v3.yaml
 google/cloud/videointelligence/artman_videointelligence_v1.yaml
 google/cloud/videointelligence/artman_videointelligence_v1beta1.yaml
 google/cloud/videointelligence/artman_videointelligence_v1beta2.yaml
diff --git a/go.mod b/go.mod
index 62f3dcd..e68b806 100644
--- a/go.mod
+++ b/go.mod
@@ -22,7 +22,7 @@
 	golang.org/x/text v0.3.2
 	golang.org/x/tools v0.0.0-20191002183253-8a18b87bf663
 	google.golang.org/api v0.9.0
-	google.golang.org/genproto v0.0.0-20190927181202-20e1ac93f88c
+	google.golang.org/genproto v0.0.0-20191007162740-aa923e3a3354
 	google.golang.org/grpc v1.21.1
 	honnef.co/go/tools v0.0.1-2019.2.3
 )
diff --git a/go.sum b/go.sum
index bcb8482..17ad3d2 100644
--- a/go.sum
+++ b/go.sum
@@ -186,8 +186,8 @@
 google.golang.org/genproto v0.0.0-20190819201941-24fa4b261c55/go.mod h1:DMBHOl98Agz4BDEuKkezgsaosCRResVns1a3J2ZsMNc=
 google.golang.org/genproto v0.0.0-20190911173649-1774047e7e51 h1:Ex1mq5jaJof+kRnYi3SlYJ8KKa9Ao3NHyIT5XJ1gF6U=
 google.golang.org/genproto v0.0.0-20190911173649-1774047e7e51/go.mod h1:IbNlFCBrqXvoKpeg0TB2l7cyZUmoaFKYIwrEpbDKLA8=
-google.golang.org/genproto v0.0.0-20190927181202-20e1ac93f88c h1:hrpEMCZ2O7DR5gC1n2AJGVhrwiEjOi35+jxtIuZpTMo=
-google.golang.org/genproto v0.0.0-20190927181202-20e1ac93f88c/go.mod h1:IbNlFCBrqXvoKpeg0TB2l7cyZUmoaFKYIwrEpbDKLA8=
+google.golang.org/genproto v0.0.0-20191007162740-aa923e3a3354 h1:KJxw2DvYTCIxlEY4yqWyLdvFGlci4EKTCbrZwfyxDME=
+google.golang.org/genproto v0.0.0-20191007162740-aa923e3a3354/go.mod h1:n3cpQtvxv34hfy77yVDNjmbRyujviMdxYliBSkLhpCc=
 google.golang.org/grpc v1.19.0 h1:cfg4PD8YEdSFnm7qLV4++93WcmhH2nIUhMjhdCvl3j8=
 google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c=
 google.golang.org/grpc v1.20.1 h1:Hz2g2wirWK7H0qIIhGIqRGTuMwTE8HEKFnDZZ7lm9NU=
diff --git a/iam/admin/apiv1/doc.go b/iam/admin/apiv1/doc.go
index 8c99c36..2585b4f 100644
--- a/iam/admin/apiv1/doc.go
+++ b/iam/admin/apiv1/doc.go
@@ -100,4 +100,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/iam/credentials/apiv1/doc.go b/iam/credentials/apiv1/doc.go
index aac0da0..3e5ea3c 100644
--- a/iam/credentials/apiv1/doc.go
+++ b/iam/credentials/apiv1/doc.go
@@ -97,4 +97,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/iot/apiv1/doc.go b/iot/apiv1/doc.go
index 7a09e74..c1e19d6 100644
--- a/iot/apiv1/doc.go
+++ b/iot/apiv1/doc.go
@@ -99,4 +99,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/irm/apiv1alpha2/doc.go b/irm/apiv1alpha2/doc.go
index 885bb09..332cd50 100644
--- a/irm/apiv1alpha2/doc.go
+++ b/irm/apiv1alpha2/doc.go
@@ -96,4 +96,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/kms/apiv1/doc.go b/kms/apiv1/doc.go
index c90633d..a1d44b2 100644
--- a/kms/apiv1/doc.go
+++ b/kms/apiv1/doc.go
@@ -98,4 +98,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/language/apiv1/doc.go b/language/apiv1/doc.go
index 48ddba9..1c09461 100644
--- a/language/apiv1/doc.go
+++ b/language/apiv1/doc.go
@@ -100,4 +100,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/language/apiv1beta2/doc.go b/language/apiv1beta2/doc.go
index cd86e1d..5c318b8 100644
--- a/language/apiv1beta2/doc.go
+++ b/language/apiv1beta2/doc.go
@@ -99,4 +99,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/logging/apiv2/doc.go b/logging/apiv2/doc.go
index 7e28d6d..bd9af2f 100644
--- a/logging/apiv2/doc.go
+++ b/logging/apiv2/doc.go
@@ -106,4 +106,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/longrunning/autogen/doc.go b/longrunning/autogen/doc.go
index fdbe26c..5b2322f 100644
--- a/longrunning/autogen/doc.go
+++ b/longrunning/autogen/doc.go
@@ -96,4 +96,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/monitoring/apiv3/doc.go b/monitoring/apiv3/doc.go
index f8ec54f..5dfced8 100644
--- a/monitoring/apiv3/doc.go
+++ b/monitoring/apiv3/doc.go
@@ -102,4 +102,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/oslogin/apiv1/doc.go b/oslogin/apiv1/doc.go
index 6ead7c5..c63c6e1 100644
--- a/oslogin/apiv1/doc.go
+++ b/oslogin/apiv1/doc.go
@@ -100,4 +100,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/oslogin/apiv1beta/doc.go b/oslogin/apiv1beta/doc.go
index 2c66bda..3374758 100644
--- a/oslogin/apiv1beta/doc.go
+++ b/oslogin/apiv1beta/doc.go
@@ -100,4 +100,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/phishingprotection/apiv1beta1/doc.go b/phishingprotection/apiv1beta1/doc.go
index d7789ec..edf92f9 100644
--- a/phishingprotection/apiv1beta1/doc.go
+++ b/phishingprotection/apiv1beta1/doc.go
@@ -96,4 +96,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/pubsub/apiv1/doc.go b/pubsub/apiv1/doc.go
index 6de75d0..c0aa298 100644
--- a/pubsub/apiv1/doc.go
+++ b/pubsub/apiv1/doc.go
@@ -100,4 +100,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/recaptchaenterprise/apiv1beta1/doc.go b/recaptchaenterprise/apiv1beta1/doc.go
index f47718c..7995de4 100644
--- a/recaptchaenterprise/apiv1beta1/doc.go
+++ b/recaptchaenterprise/apiv1beta1/doc.go
@@ -96,4 +96,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/recommender/apiv1beta1/doc.go b/recommender/apiv1beta1/doc.go
index 63bd1ff..bbb3193 100644
--- a/recommender/apiv1beta1/doc.go
+++ b/recommender/apiv1beta1/doc.go
@@ -96,4 +96,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/redis/apiv1/doc.go b/redis/apiv1/doc.go
index c5e0411..6a76244 100644
--- a/redis/apiv1/doc.go
+++ b/redis/apiv1/doc.go
@@ -97,4 +97,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/redis/apiv1beta1/doc.go b/redis/apiv1beta1/doc.go
index f084695..55baa75 100644
--- a/redis/apiv1beta1/doc.go
+++ b/redis/apiv1beta1/doc.go
@@ -97,4 +97,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/scheduler/apiv1/doc.go b/scheduler/apiv1/doc.go
index aa133bd..bb15be6 100644
--- a/scheduler/apiv1/doc.go
+++ b/scheduler/apiv1/doc.go
@@ -96,4 +96,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/scheduler/apiv1beta1/doc.go b/scheduler/apiv1beta1/doc.go
index fe38aee..4e4f8c1 100644
--- a/scheduler/apiv1beta1/doc.go
+++ b/scheduler/apiv1beta1/doc.go
@@ -97,4 +97,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/securitycenter/apiv1/doc.go b/securitycenter/apiv1/doc.go
index 916e557..2e4fdc7 100644
--- a/securitycenter/apiv1/doc.go
+++ b/securitycenter/apiv1/doc.go
@@ -98,4 +98,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/securitycenter/apiv1beta1/doc.go b/securitycenter/apiv1beta1/doc.go
index 329e5e8..0d1aac7 100644
--- a/securitycenter/apiv1beta1/doc.go
+++ b/securitycenter/apiv1beta1/doc.go
@@ -98,4 +98,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/spanner/admin/database/apiv1/doc.go b/spanner/admin/database/apiv1/doc.go
index 1c959df..db6b3f7 100644
--- a/spanner/admin/database/apiv1/doc.go
+++ b/spanner/admin/database/apiv1/doc.go
@@ -97,4 +97,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/spanner/admin/instance/apiv1/doc.go b/spanner/admin/instance/apiv1/doc.go
index 63bf541..8247bba 100644
--- a/spanner/admin/instance/apiv1/doc.go
+++ b/spanner/admin/instance/apiv1/doc.go
@@ -97,4 +97,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/spanner/apiv1/doc.go b/spanner/apiv1/doc.go
index 6fc72d3..a8481d9 100644
--- a/spanner/apiv1/doc.go
+++ b/spanner/apiv1/doc.go
@@ -100,4 +100,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/speech/apiv1/doc.go b/speech/apiv1/doc.go
index 347ce23..730c11a 100644
--- a/speech/apiv1/doc.go
+++ b/speech/apiv1/doc.go
@@ -96,4 +96,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/speech/apiv1p1beta1/doc.go b/speech/apiv1p1beta1/doc.go
index 3cd63cc..10b6e0a 100644
--- a/speech/apiv1p1beta1/doc.go
+++ b/speech/apiv1p1beta1/doc.go
@@ -97,4 +97,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/talent/apiv4beta1/doc.go b/talent/apiv4beta1/doc.go
index d3d54e1..2489a76 100644
--- a/talent/apiv4beta1/doc.go
+++ b/talent/apiv4beta1/doc.go
@@ -99,4 +99,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/texttospeech/apiv1/doc.go b/texttospeech/apiv1/doc.go
index 0905fce..9783589 100644
--- a/texttospeech/apiv1/doc.go
+++ b/texttospeech/apiv1/doc.go
@@ -98,4 +98,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/trace/apiv1/doc.go b/trace/apiv1/doc.go
index d152cd8..ac2762c 100644
--- a/trace/apiv1/doc.go
+++ b/trace/apiv1/doc.go
@@ -105,4 +105,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/trace/apiv2/doc.go b/trace/apiv2/doc.go
index 6eeca76..42857d3 100644
--- a/trace/apiv2/doc.go
+++ b/trace/apiv2/doc.go
@@ -102,4 +102,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/translate/apiv3/doc.go b/translate/apiv3/doc.go
new file mode 100644
index 0000000..32fca9c
--- /dev/null
+++ b/translate/apiv3/doc.go
@@ -0,0 +1,101 @@
+// Copyright 2019 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 gapic-generator. DO NOT EDIT.
+
+// Package translate is an auto-generated package for the
+// Cloud Translation API.
+//
+//   NOTE: This package is in alpha. It is not stable, and is likely to change.
+//
+// Integrates text translation into your website or application.
+//
+// Use of Context
+//
+// The ctx passed to NewClient is used for authentication requests and
+// for creating the underlying connection, but is not used for subsequent calls.
+// Individual methods on the client use the ctx given to them.
+//
+// To close the open connection, use the Close() method.
+//
+// For information about setting deadlines, reusing contexts, and more
+// please visit godoc.org/cloud.google.com/go.
+package translate // import "cloud.google.com/go/translate/apiv3"
+
+import (
+	"context"
+	"runtime"
+	"strings"
+	"unicode"
+
+	"google.golang.org/grpc/metadata"
+)
+
+func insertMetadata(ctx context.Context, mds ...metadata.MD) context.Context {
+	out, _ := metadata.FromOutgoingContext(ctx)
+	out = out.Copy()
+	for _, md := range mds {
+		for k, v := range md {
+			out[k] = append(out[k], v...)
+		}
+	}
+	return metadata.NewOutgoingContext(ctx, out)
+}
+
+// DefaultAuthScopes reports the default set of authentication scopes to use with this package.
+func DefaultAuthScopes() []string {
+	return []string{
+		"https://www.googleapis.com/auth/cloud-platform",
+		"https://www.googleapis.com/auth/cloud-translation",
+	}
+}
+
+// versionGo returns the Go runtime version. The returned string
+// has no whitespace, suitable for reporting in header.
+func versionGo() string {
+	const develPrefix = "devel +"
+
+	s := runtime.Version()
+	if strings.HasPrefix(s, develPrefix) {
+		s = s[len(develPrefix):]
+		if p := strings.IndexFunc(s, unicode.IsSpace); p >= 0 {
+			s = s[:p]
+		}
+		return s
+	}
+
+	notSemverRune := func(r rune) bool {
+		return strings.IndexRune("0123456789.", r) < 0
+	}
+
+	if strings.HasPrefix(s, "go1") {
+		s = s[2:]
+		var prerelease string
+		if p := strings.IndexFunc(s, notSemverRune); p >= 0 {
+			s, prerelease = s[:p], s[p:]
+		}
+		if strings.HasSuffix(s, ".") {
+			s += "0"
+		} else if strings.Count(s, ".") < 2 {
+			s += ".0"
+		}
+		if prerelease != "" {
+			s += "-" + prerelease
+		}
+		return s
+	}
+	return "UNKNOWN"
+}
+
+const versionClient = "20191004"
diff --git a/translate/apiv3/mock_test.go b/translate/apiv3/mock_test.go
new file mode 100644
index 0000000..4e01bde
--- /dev/null
+++ b/translate/apiv3/mock_test.go
@@ -0,0 +1,777 @@
+// Copyright 2019 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 gapic-generator. DO NOT EDIT.
+
+package translate
+
+import (
+	"context"
+	"flag"
+	"fmt"
+	"io"
+	"log"
+	"net"
+	"os"
+	"strings"
+	"testing"
+
+	"github.com/golang/protobuf/proto"
+	"github.com/golang/protobuf/ptypes"
+	"google.golang.org/api/option"
+	translatepb "google.golang.org/genproto/googleapis/cloud/translate/v3"
+	longrunningpb "google.golang.org/genproto/googleapis/longrunning"
+
+	status "google.golang.org/genproto/googleapis/rpc/status"
+	"google.golang.org/grpc"
+	"google.golang.org/grpc/codes"
+	"google.golang.org/grpc/metadata"
+
+	gstatus "google.golang.org/grpc/status"
+)
+
+var _ = io.EOF
+var _ = ptypes.MarshalAny
+var _ status.Status
+
+type mockTranslationServer struct {
+	// Embed for forward compatibility.
+	// Tests will keep working if more methods are added
+	// in the future.
+	translatepb.TranslationServiceServer
+
+	reqs []proto.Message
+
+	// If set, all calls return this error.
+	err error
+
+	// responses to return if err == nil
+	resps []proto.Message
+}
+
+func (s *mockTranslationServer) TranslateText(ctx context.Context, req *translatepb.TranslateTextRequest) (*translatepb.TranslateTextResponse, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*translatepb.TranslateTextResponse), nil
+}
+
+func (s *mockTranslationServer) DetectLanguage(ctx context.Context, req *translatepb.DetectLanguageRequest) (*translatepb.DetectLanguageResponse, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*translatepb.DetectLanguageResponse), nil
+}
+
+func (s *mockTranslationServer) GetSupportedLanguages(ctx context.Context, req *translatepb.GetSupportedLanguagesRequest) (*translatepb.SupportedLanguages, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*translatepb.SupportedLanguages), nil
+}
+
+func (s *mockTranslationServer) BatchTranslateText(ctx context.Context, req *translatepb.BatchTranslateTextRequest) (*longrunningpb.Operation, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*longrunningpb.Operation), nil
+}
+
+func (s *mockTranslationServer) CreateGlossary(ctx context.Context, req *translatepb.CreateGlossaryRequest) (*longrunningpb.Operation, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*longrunningpb.Operation), nil
+}
+
+func (s *mockTranslationServer) ListGlossaries(ctx context.Context, req *translatepb.ListGlossariesRequest) (*translatepb.ListGlossariesResponse, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*translatepb.ListGlossariesResponse), nil
+}
+
+func (s *mockTranslationServer) GetGlossary(ctx context.Context, req *translatepb.GetGlossaryRequest) (*translatepb.Glossary, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*translatepb.Glossary), nil
+}
+
+func (s *mockTranslationServer) DeleteGlossary(ctx context.Context, req *translatepb.DeleteGlossaryRequest) (*longrunningpb.Operation, error) {
+	md, _ := metadata.FromIncomingContext(ctx)
+	if xg := md["x-goog-api-client"]; len(xg) == 0 || !strings.Contains(xg[0], "gl-go/") {
+		return nil, fmt.Errorf("x-goog-api-client = %v, expected gl-go key", xg)
+	}
+	s.reqs = append(s.reqs, req)
+	if s.err != nil {
+		return nil, s.err
+	}
+	return s.resps[0].(*longrunningpb.Operation), nil
+}
+
+// clientOpt is the option tests should use to connect to the test server.
+// It is initialized by TestMain.
+var clientOpt option.ClientOption
+
+var (
+	mockTranslation mockTranslationServer
+)
+
+func TestMain(m *testing.M) {
+	flag.Parse()
+
+	serv := grpc.NewServer()
+	translatepb.RegisterTranslationServiceServer(serv, &mockTranslation)
+
+	lis, err := net.Listen("tcp", "localhost:0")
+	if err != nil {
+		log.Fatal(err)
+	}
+	go serv.Serve(lis)
+
+	conn, err := grpc.Dial(lis.Addr().String(), grpc.WithInsecure())
+	if err != nil {
+		log.Fatal(err)
+	}
+	clientOpt = option.WithGRPCConn(conn)
+
+	os.Exit(m.Run())
+}
+
+func TestTranslationServiceTranslateText(t *testing.T) {
+	var expectedResponse *translatepb.TranslateTextResponse = &translatepb.TranslateTextResponse{}
+
+	mockTranslation.err = nil
+	mockTranslation.reqs = nil
+
+	mockTranslation.resps = append(mockTranslation.resps[:0], expectedResponse)
+
+	var contents []string = nil
+	var targetLanguageCode string = "targetLanguageCode1323228230"
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var request = &translatepb.TranslateTextRequest{
+		Contents:           contents,
+		TargetLanguageCode: targetLanguageCode,
+		Parent:             formattedParent,
+	}
+
+	c, err := NewTranslationClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.TranslateText(context.Background(), request)
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockTranslation.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	if want, got := expectedResponse, resp; !proto.Equal(want, got) {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestTranslationServiceTranslateTextError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockTranslation.err = gstatus.Error(errCode, "test error")
+
+	var contents []string = nil
+	var targetLanguageCode string = "targetLanguageCode1323228230"
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var request = &translatepb.TranslateTextRequest{
+		Contents:           contents,
+		TargetLanguageCode: targetLanguageCode,
+		Parent:             formattedParent,
+	}
+
+	c, err := NewTranslationClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.TranslateText(context.Background(), request)
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
+func TestTranslationServiceDetectLanguage(t *testing.T) {
+	var expectedResponse *translatepb.DetectLanguageResponse = &translatepb.DetectLanguageResponse{}
+
+	mockTranslation.err = nil
+	mockTranslation.reqs = nil
+
+	mockTranslation.resps = append(mockTranslation.resps[:0], expectedResponse)
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var request = &translatepb.DetectLanguageRequest{
+		Parent: formattedParent,
+	}
+
+	c, err := NewTranslationClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.DetectLanguage(context.Background(), request)
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockTranslation.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	if want, got := expectedResponse, resp; !proto.Equal(want, got) {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestTranslationServiceDetectLanguageError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockTranslation.err = gstatus.Error(errCode, "test error")
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var request = &translatepb.DetectLanguageRequest{
+		Parent: formattedParent,
+	}
+
+	c, err := NewTranslationClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.DetectLanguage(context.Background(), request)
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
+func TestTranslationServiceGetSupportedLanguages(t *testing.T) {
+	var expectedResponse *translatepb.SupportedLanguages = &translatepb.SupportedLanguages{}
+
+	mockTranslation.err = nil
+	mockTranslation.reqs = nil
+
+	mockTranslation.resps = append(mockTranslation.resps[:0], expectedResponse)
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var request = &translatepb.GetSupportedLanguagesRequest{
+		Parent: formattedParent,
+	}
+
+	c, err := NewTranslationClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.GetSupportedLanguages(context.Background(), request)
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockTranslation.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	if want, got := expectedResponse, resp; !proto.Equal(want, got) {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestTranslationServiceGetSupportedLanguagesError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockTranslation.err = gstatus.Error(errCode, "test error")
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var request = &translatepb.GetSupportedLanguagesRequest{
+		Parent: formattedParent,
+	}
+
+	c, err := NewTranslationClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.GetSupportedLanguages(context.Background(), request)
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
+func TestTranslationServiceBatchTranslateText(t *testing.T) {
+	var totalCharacters int64 = 1368640955
+	var translatedCharacters int64 = 1337326221
+	var failedCharacters int64 = 1723028396
+	var expectedResponse = &translatepb.BatchTranslateResponse{
+		TotalCharacters:      totalCharacters,
+		TranslatedCharacters: translatedCharacters,
+		FailedCharacters:     failedCharacters,
+	}
+
+	mockTranslation.err = nil
+	mockTranslation.reqs = nil
+
+	any, err := ptypes.MarshalAny(expectedResponse)
+	if err != nil {
+		t.Fatal(err)
+	}
+	mockTranslation.resps = append(mockTranslation.resps[:0], &longrunningpb.Operation{
+		Name:   "longrunning-test",
+		Done:   true,
+		Result: &longrunningpb.Operation_Response{Response: any},
+	})
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var sourceLanguageCode string = "sourceLanguageCode1687263568"
+	var targetLanguageCodes []string = nil
+	var inputConfigs []*translatepb.InputConfig = nil
+	var outputConfig *translatepb.OutputConfig = &translatepb.OutputConfig{}
+	var request = &translatepb.BatchTranslateTextRequest{
+		Parent:              formattedParent,
+		SourceLanguageCode:  sourceLanguageCode,
+		TargetLanguageCodes: targetLanguageCodes,
+		InputConfigs:        inputConfigs,
+		OutputConfig:        outputConfig,
+	}
+
+	c, err := NewTranslationClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	respLRO, err := c.BatchTranslateText(context.Background(), request)
+	if err != nil {
+		t.Fatal(err)
+	}
+	resp, err := respLRO.Wait(context.Background())
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockTranslation.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	if want, got := expectedResponse, resp; !proto.Equal(want, got) {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestTranslationServiceBatchTranslateTextError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockTranslation.err = nil
+	mockTranslation.resps = append(mockTranslation.resps[:0], &longrunningpb.Operation{
+		Name: "longrunning-test",
+		Done: true,
+		Result: &longrunningpb.Operation_Error{
+			Error: &status.Status{
+				Code:    int32(errCode),
+				Message: "test error",
+			},
+		},
+	})
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var sourceLanguageCode string = "sourceLanguageCode1687263568"
+	var targetLanguageCodes []string = nil
+	var inputConfigs []*translatepb.InputConfig = nil
+	var outputConfig *translatepb.OutputConfig = &translatepb.OutputConfig{}
+	var request = &translatepb.BatchTranslateTextRequest{
+		Parent:              formattedParent,
+		SourceLanguageCode:  sourceLanguageCode,
+		TargetLanguageCodes: targetLanguageCodes,
+		InputConfigs:        inputConfigs,
+		OutputConfig:        outputConfig,
+	}
+
+	c, err := NewTranslationClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	respLRO, err := c.BatchTranslateText(context.Background(), request)
+	if err != nil {
+		t.Fatal(err)
+	}
+	resp, err := respLRO.Wait(context.Background())
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
+func TestTranslationServiceCreateGlossary(t *testing.T) {
+	var name string = "name3373707"
+	var entryCount int32 = 811131134
+	var expectedResponse = &translatepb.Glossary{
+		Name:       name,
+		EntryCount: entryCount,
+	}
+
+	mockTranslation.err = nil
+	mockTranslation.reqs = nil
+
+	any, err := ptypes.MarshalAny(expectedResponse)
+	if err != nil {
+		t.Fatal(err)
+	}
+	mockTranslation.resps = append(mockTranslation.resps[:0], &longrunningpb.Operation{
+		Name:   "longrunning-test",
+		Done:   true,
+		Result: &longrunningpb.Operation_Response{Response: any},
+	})
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var glossary *translatepb.Glossary = &translatepb.Glossary{}
+	var request = &translatepb.CreateGlossaryRequest{
+		Parent:   formattedParent,
+		Glossary: glossary,
+	}
+
+	c, err := NewTranslationClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	respLRO, err := c.CreateGlossary(context.Background(), request)
+	if err != nil {
+		t.Fatal(err)
+	}
+	resp, err := respLRO.Wait(context.Background())
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockTranslation.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	if want, got := expectedResponse, resp; !proto.Equal(want, got) {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestTranslationServiceCreateGlossaryError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockTranslation.err = nil
+	mockTranslation.resps = append(mockTranslation.resps[:0], &longrunningpb.Operation{
+		Name: "longrunning-test",
+		Done: true,
+		Result: &longrunningpb.Operation_Error{
+			Error: &status.Status{
+				Code:    int32(errCode),
+				Message: "test error",
+			},
+		},
+	})
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var glossary *translatepb.Glossary = &translatepb.Glossary{}
+	var request = &translatepb.CreateGlossaryRequest{
+		Parent:   formattedParent,
+		Glossary: glossary,
+	}
+
+	c, err := NewTranslationClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	respLRO, err := c.CreateGlossary(context.Background(), request)
+	if err != nil {
+		t.Fatal(err)
+	}
+	resp, err := respLRO.Wait(context.Background())
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
+func TestTranslationServiceListGlossaries(t *testing.T) {
+	var nextPageToken string = ""
+	var glossariesElement *translatepb.Glossary = &translatepb.Glossary{}
+	var glossaries = []*translatepb.Glossary{glossariesElement}
+	var expectedResponse = &translatepb.ListGlossariesResponse{
+		NextPageToken: nextPageToken,
+		Glossaries:    glossaries,
+	}
+
+	mockTranslation.err = nil
+	mockTranslation.reqs = nil
+
+	mockTranslation.resps = append(mockTranslation.resps[:0], expectedResponse)
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var request = &translatepb.ListGlossariesRequest{
+		Parent: formattedParent,
+	}
+
+	c, err := NewTranslationClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.ListGlossaries(context.Background(), request).Next()
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockTranslation.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	want := (interface{})(expectedResponse.Glossaries[0])
+	got := (interface{})(resp)
+	var ok bool
+
+	switch want := (want).(type) {
+	case proto.Message:
+		ok = proto.Equal(want, got.(proto.Message))
+	default:
+		ok = want == got
+	}
+	if !ok {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestTranslationServiceListGlossariesError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockTranslation.err = gstatus.Error(errCode, "test error")
+
+	var formattedParent string = fmt.Sprintf("projects/%s/locations/%s", "[PROJECT]", "[LOCATION]")
+	var request = &translatepb.ListGlossariesRequest{
+		Parent: formattedParent,
+	}
+
+	c, err := NewTranslationClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.ListGlossaries(context.Background(), request).Next()
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
+func TestTranslationServiceGetGlossary(t *testing.T) {
+	var name2 string = "name2-1052831874"
+	var entryCount int32 = 811131134
+	var expectedResponse = &translatepb.Glossary{
+		Name:       name2,
+		EntryCount: entryCount,
+	}
+
+	mockTranslation.err = nil
+	mockTranslation.reqs = nil
+
+	mockTranslation.resps = append(mockTranslation.resps[:0], expectedResponse)
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/glossaries/%s", "[PROJECT]", "[LOCATION]", "[GLOSSARY]")
+	var request = &translatepb.GetGlossaryRequest{
+		Name: formattedName,
+	}
+
+	c, err := NewTranslationClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.GetGlossary(context.Background(), request)
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockTranslation.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	if want, got := expectedResponse, resp; !proto.Equal(want, got) {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestTranslationServiceGetGlossaryError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockTranslation.err = gstatus.Error(errCode, "test error")
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/glossaries/%s", "[PROJECT]", "[LOCATION]", "[GLOSSARY]")
+	var request = &translatepb.GetGlossaryRequest{
+		Name: formattedName,
+	}
+
+	c, err := NewTranslationClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	resp, err := c.GetGlossary(context.Background(), request)
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
+func TestTranslationServiceDeleteGlossary(t *testing.T) {
+	var name2 string = "name2-1052831874"
+	var expectedResponse = &translatepb.DeleteGlossaryResponse{
+		Name: name2,
+	}
+
+	mockTranslation.err = nil
+	mockTranslation.reqs = nil
+
+	any, err := ptypes.MarshalAny(expectedResponse)
+	if err != nil {
+		t.Fatal(err)
+	}
+	mockTranslation.resps = append(mockTranslation.resps[:0], &longrunningpb.Operation{
+		Name:   "longrunning-test",
+		Done:   true,
+		Result: &longrunningpb.Operation_Response{Response: any},
+	})
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/glossaries/%s", "[PROJECT]", "[LOCATION]", "[GLOSSARY]")
+	var request = &translatepb.DeleteGlossaryRequest{
+		Name: formattedName,
+	}
+
+	c, err := NewTranslationClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	respLRO, err := c.DeleteGlossary(context.Background(), request)
+	if err != nil {
+		t.Fatal(err)
+	}
+	resp, err := respLRO.Wait(context.Background())
+
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	if want, got := request, mockTranslation.reqs[0]; !proto.Equal(want, got) {
+		t.Errorf("wrong request %q, want %q", got, want)
+	}
+
+	if want, got := expectedResponse, resp; !proto.Equal(want, got) {
+		t.Errorf("wrong response %q, want %q)", got, want)
+	}
+}
+
+func TestTranslationServiceDeleteGlossaryError(t *testing.T) {
+	errCode := codes.PermissionDenied
+	mockTranslation.err = nil
+	mockTranslation.resps = append(mockTranslation.resps[:0], &longrunningpb.Operation{
+		Name: "longrunning-test",
+		Done: true,
+		Result: &longrunningpb.Operation_Error{
+			Error: &status.Status{
+				Code:    int32(errCode),
+				Message: "test error",
+			},
+		},
+	})
+
+	var formattedName string = fmt.Sprintf("projects/%s/locations/%s/glossaries/%s", "[PROJECT]", "[LOCATION]", "[GLOSSARY]")
+	var request = &translatepb.DeleteGlossaryRequest{
+		Name: formattedName,
+	}
+
+	c, err := NewTranslationClient(context.Background(), clientOpt)
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	respLRO, err := c.DeleteGlossary(context.Background(), request)
+	if err != nil {
+		t.Fatal(err)
+	}
+	resp, err := respLRO.Wait(context.Background())
+
+	if st, ok := gstatus.FromError(err); !ok {
+		t.Errorf("got error %v, expected grpc error", err)
+	} else if c := st.Code(); c != errCode {
+		t.Errorf("got error code %q, want %q", c, errCode)
+	}
+	_ = resp
+}
diff --git a/translate/apiv3/translation_client.go b/translate/apiv3/translation_client.go
new file mode 100644
index 0000000..2e4934c
--- /dev/null
+++ b/translate/apiv3/translation_client.go
@@ -0,0 +1,581 @@
+// Copyright 2019 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 gapic-generator. DO NOT EDIT.
+
+package translate
+
+import (
+	"context"
+	"fmt"
+	"math"
+	"net/url"
+	"time"
+
+	"cloud.google.com/go/longrunning"
+	lroauto "cloud.google.com/go/longrunning/autogen"
+	"github.com/golang/protobuf/proto"
+	gax "github.com/googleapis/gax-go/v2"
+	"google.golang.org/api/iterator"
+	"google.golang.org/api/option"
+	"google.golang.org/api/transport"
+	translatepb "google.golang.org/genproto/googleapis/cloud/translate/v3"
+	longrunningpb "google.golang.org/genproto/googleapis/longrunning"
+	"google.golang.org/grpc"
+	"google.golang.org/grpc/codes"
+	"google.golang.org/grpc/metadata"
+)
+
+// TranslationCallOptions contains the retry settings for each method of TranslationClient.
+type TranslationCallOptions struct {
+	TranslateText         []gax.CallOption
+	DetectLanguage        []gax.CallOption
+	GetSupportedLanguages []gax.CallOption
+	BatchTranslateText    []gax.CallOption
+	CreateGlossary        []gax.CallOption
+	ListGlossaries        []gax.CallOption
+	GetGlossary           []gax.CallOption
+	DeleteGlossary        []gax.CallOption
+}
+
+func defaultTranslationClientOptions() []option.ClientOption {
+	return []option.ClientOption{
+		option.WithEndpoint("translate.googleapis.com:443"),
+		option.WithScopes(DefaultAuthScopes()...),
+		option.WithGRPCDialOption(grpc.WithDefaultCallOptions(
+			grpc.MaxCallRecvMsgSize(math.MaxInt32))),
+	}
+}
+
+func defaultTranslationCallOptions() *TranslationCallOptions {
+	retry := map[[2]string][]gax.CallOption{
+		{"default", "idempotent"}: {
+			gax.WithRetry(func() gax.Retryer {
+				return gax.OnCodes([]codes.Code{
+					codes.DeadlineExceeded,
+					codes.Unavailable,
+				}, gax.Backoff{
+					Initial:    100 * time.Millisecond,
+					Max:        60000 * time.Millisecond,
+					Multiplier: 1.3,
+				})
+			}),
+		},
+	}
+	return &TranslationCallOptions{
+		TranslateText:         retry[[2]string{"default", "non_idempotent"}],
+		DetectLanguage:        retry[[2]string{"default", "non_idempotent"}],
+		GetSupportedLanguages: retry[[2]string{"default", "idempotent"}],
+		BatchTranslateText:    retry[[2]string{"default", "non_idempotent"}],
+		CreateGlossary:        retry[[2]string{"default", "non_idempotent"}],
+		ListGlossaries:        retry[[2]string{"default", "idempotent"}],
+		GetGlossary:           retry[[2]string{"default", "idempotent"}],
+		DeleteGlossary:        retry[[2]string{"default", "non_idempotent"}],
+	}
+}
+
+// TranslationClient is a client for interacting with Cloud Translation API.
+//
+// Methods, except Close, may be called concurrently. However, fields must not be modified concurrently with method calls.
+type TranslationClient struct {
+	// The connection to the service.
+	conn *grpc.ClientConn
+
+	// The gRPC API client.
+	translationClient translatepb.TranslationServiceClient
+
+	// LROClient is used internally to handle longrunning operations.
+	// It is exposed so that its CallOptions can be modified if required.
+	// Users should not Close this client.
+	LROClient *lroauto.OperationsClient
+
+	// The call options for this service.
+	CallOptions *TranslationCallOptions
+
+	// The x-goog-* metadata to be sent with each request.
+	xGoogMetadata metadata.MD
+}
+
+// NewTranslationClient creates a new translation service client.
+//
+// Provides natural language translation operations.
+func NewTranslationClient(ctx context.Context, opts ...option.ClientOption) (*TranslationClient, error) {
+	conn, err := transport.DialGRPC(ctx, append(defaultTranslationClientOptions(), opts...)...)
+	if err != nil {
+		return nil, err
+	}
+	c := &TranslationClient{
+		conn:        conn,
+		CallOptions: defaultTranslationCallOptions(),
+
+		translationClient: translatepb.NewTranslationServiceClient(conn),
+	}
+	c.setGoogleClientInfo()
+
+	c.LROClient, err = lroauto.NewOperationsClient(ctx, option.WithGRPCConn(conn))
+	if err != nil {
+		// This error "should not happen", since we are just reusing old connection
+		// and never actually need to dial.
+		// If this does happen, we could leak conn. However, we cannot close conn:
+		// If the user invoked the function with option.WithGRPCConn,
+		// we would close a connection that's still in use.
+		// TODO(pongad): investigate error conditions.
+		return nil, err
+	}
+	return c, nil
+}
+
+// Connection returns the client's connection to the API service.
+func (c *TranslationClient) Connection() *grpc.ClientConn {
+	return c.conn
+}
+
+// Close closes the connection to the API service. The user should invoke this when
+// the client is no longer required.
+func (c *TranslationClient) Close() error {
+	return c.conn.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 *TranslationClient) setGoogleClientInfo(keyval ...string) {
+	kv := append([]string{"gl-go", versionGo()}, keyval...)
+	kv = append(kv, "gapic", versionClient, "gax", gax.Version, "grpc", grpc.Version)
+	c.xGoogMetadata = metadata.Pairs("x-goog-api-client", gax.XGoogHeader(kv...))
+}
+
+// TranslateText translates input text and returns translated text.
+func (c *TranslationClient) TranslateText(ctx context.Context, req *translatepb.TranslateTextRequest, opts ...gax.CallOption) (*translatepb.TranslateTextResponse, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.TranslateText[0:len(c.CallOptions.TranslateText):len(c.CallOptions.TranslateText)], opts...)
+	var resp *translatepb.TranslateTextResponse
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.translationClient.TranslateText(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return resp, nil
+}
+
+// DetectLanguage detects the language of text within a request.
+func (c *TranslationClient) DetectLanguage(ctx context.Context, req *translatepb.DetectLanguageRequest, opts ...gax.CallOption) (*translatepb.DetectLanguageResponse, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.DetectLanguage[0:len(c.CallOptions.DetectLanguage):len(c.CallOptions.DetectLanguage)], opts...)
+	var resp *translatepb.DetectLanguageResponse
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.translationClient.DetectLanguage(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return resp, nil
+}
+
+// GetSupportedLanguages returns a list of supported languages for translation.
+func (c *TranslationClient) GetSupportedLanguages(ctx context.Context, req *translatepb.GetSupportedLanguagesRequest, opts ...gax.CallOption) (*translatepb.SupportedLanguages, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.GetSupportedLanguages[0:len(c.CallOptions.GetSupportedLanguages):len(c.CallOptions.GetSupportedLanguages)], opts...)
+	var resp *translatepb.SupportedLanguages
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.translationClient.GetSupportedLanguages(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return resp, nil
+}
+
+// BatchTranslateText translates a large volume of text in asynchronous batch mode.
+// This function provides real-time output as the inputs are being processed.
+// If caller cancels a request, the partial results (for an input file, it's
+// all or nothing) may still be available on the specified output location.
+//
+// This call returns immediately and you can
+// use google.longrunning.Operation.name to poll the status of the call.
+func (c *TranslationClient) BatchTranslateText(ctx context.Context, req *translatepb.BatchTranslateTextRequest, opts ...gax.CallOption) (*BatchTranslateTextOperation, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.BatchTranslateText[0:len(c.CallOptions.BatchTranslateText):len(c.CallOptions.BatchTranslateText)], opts...)
+	var resp *longrunningpb.Operation
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.translationClient.BatchTranslateText(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return &BatchTranslateTextOperation{
+		lro: longrunning.InternalNewOperation(c.LROClient, resp),
+	}, nil
+}
+
+// CreateGlossary creates a glossary and returns the long-running operation. Returns
+// NOT_FOUND, if the project doesn't exist.
+func (c *TranslationClient) CreateGlossary(ctx context.Context, req *translatepb.CreateGlossaryRequest, opts ...gax.CallOption) (*CreateGlossaryOperation, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.CreateGlossary[0:len(c.CallOptions.CreateGlossary):len(c.CallOptions.CreateGlossary)], opts...)
+	var resp *longrunningpb.Operation
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.translationClient.CreateGlossary(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return &CreateGlossaryOperation{
+		lro: longrunning.InternalNewOperation(c.LROClient, resp),
+	}, nil
+}
+
+// ListGlossaries lists glossaries in a project. Returns NOT_FOUND, if the project doesn't
+// exist.
+func (c *TranslationClient) ListGlossaries(ctx context.Context, req *translatepb.ListGlossariesRequest, opts ...gax.CallOption) *GlossaryIterator {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "parent", url.QueryEscape(req.GetParent())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.ListGlossaries[0:len(c.CallOptions.ListGlossaries):len(c.CallOptions.ListGlossaries)], opts...)
+	it := &GlossaryIterator{}
+	req = proto.Clone(req).(*translatepb.ListGlossariesRequest)
+	it.InternalFetch = func(pageSize int, pageToken string) ([]*translatepb.Glossary, string, error) {
+		var resp *translatepb.ListGlossariesResponse
+		req.PageToken = pageToken
+		if pageSize > math.MaxInt32 {
+			req.PageSize = math.MaxInt32
+		} else {
+			req.PageSize = int32(pageSize)
+		}
+		err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+			var err error
+			resp, err = c.translationClient.ListGlossaries(ctx, req, settings.GRPC...)
+			return err
+		}, opts...)
+		if err != nil {
+			return nil, "", err
+		}
+		return resp.Glossaries, resp.NextPageToken, 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.PageSize)
+	it.pageInfo.Token = req.PageToken
+	return it
+}
+
+// GetGlossary gets a glossary. Returns NOT_FOUND, if the glossary doesn't
+// exist.
+func (c *TranslationClient) GetGlossary(ctx context.Context, req *translatepb.GetGlossaryRequest, opts ...gax.CallOption) (*translatepb.Glossary, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.GetGlossary[0:len(c.CallOptions.GetGlossary):len(c.CallOptions.GetGlossary)], opts...)
+	var resp *translatepb.Glossary
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.translationClient.GetGlossary(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return resp, nil
+}
+
+// DeleteGlossary deletes a glossary, or cancels glossary construction
+// if the glossary isn't created yet.
+// Returns NOT_FOUND, if the glossary doesn't exist.
+func (c *TranslationClient) DeleteGlossary(ctx context.Context, req *translatepb.DeleteGlossaryRequest, opts ...gax.CallOption) (*DeleteGlossaryOperation, error) {
+	md := metadata.Pairs("x-goog-request-params", fmt.Sprintf("%s=%v", "name", url.QueryEscape(req.GetName())))
+	ctx = insertMetadata(ctx, c.xGoogMetadata, md)
+	opts = append(c.CallOptions.DeleteGlossary[0:len(c.CallOptions.DeleteGlossary):len(c.CallOptions.DeleteGlossary)], opts...)
+	var resp *longrunningpb.Operation
+	err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
+		var err error
+		resp, err = c.translationClient.DeleteGlossary(ctx, req, settings.GRPC...)
+		return err
+	}, opts...)
+	if err != nil {
+		return nil, err
+	}
+	return &DeleteGlossaryOperation{
+		lro: longrunning.InternalNewOperation(c.LROClient, resp),
+	}, nil
+}
+
+// GlossaryIterator manages a stream of *translatepb.Glossary.
+type GlossaryIterator struct {
+	items    []*translatepb.Glossary
+	pageInfo *iterator.PageInfo
+	nextFunc func() error
+
+	// InternalFetch is for use by the Google Cloud Libraries only.
+	// It is not part of the stable interface of this package.
+	//
+	// InternalFetch returns results from a single call to the underlying RPC.
+	// The number of results is no greater than pageSize.
+	// If there are no more results, nextPageToken is empty and err is nil.
+	InternalFetch func(pageSize int, pageToken string) (results []*translatepb.Glossary, nextPageToken string, err error)
+}
+
+// PageInfo supports pagination. See the google.golang.org/api/iterator package for details.
+func (it *GlossaryIterator) PageInfo() *iterator.PageInfo {
+	return it.pageInfo
+}
+
+// Next returns the next result. Its second return value is iterator.Done if there are no more
+// results. Once Next returns Done, all subsequent calls will return Done.
+func (it *GlossaryIterator) Next() (*translatepb.Glossary, error) {
+	var item *translatepb.Glossary
+	if err := it.nextFunc(); err != nil {
+		return item, err
+	}
+	item = it.items[0]
+	it.items = it.items[1:]
+	return item, nil
+}
+
+func (it *GlossaryIterator) bufLen() int {
+	return len(it.items)
+}
+
+func (it *GlossaryIterator) takeBuf() interface{} {
+	b := it.items
+	it.items = nil
+	return b
+}
+
+// BatchTranslateTextOperation manages a long-running operation from BatchTranslateText.
+type BatchTranslateTextOperation struct {
+	lro *longrunning.Operation
+}
+
+// BatchTranslateTextOperation returns a new BatchTranslateTextOperation from a given name.
+// The name must be that of a previously created BatchTranslateTextOperation, possibly from a different process.
+func (c *TranslationClient) BatchTranslateTextOperation(name string) *BatchTranslateTextOperation {
+	return &BatchTranslateTextOperation{
+		lro: longrunning.InternalNewOperation(c.LROClient, &longrunningpb.Operation{Name: name}),
+	}
+}
+
+// Wait blocks until the long-running operation is completed, returning the response and any errors encountered.
+//
+// See documentation of Poll for error-handling information.
+func (op *BatchTranslateTextOperation) Wait(ctx context.Context, opts ...gax.CallOption) (*translatepb.BatchTranslateResponse, error) {
+	var resp translatepb.BatchTranslateResponse
+	if err := op.lro.WaitWithInterval(ctx, &resp, 5000*time.Millisecond, opts...); err != nil {
+		return nil, err
+	}
+	return &resp, nil
+}
+
+// Poll fetches the latest state of the long-running operation.
+//
+// Poll also fetches the latest metadata, which can be retrieved by Metadata.
+//
+// If Poll fails, the error is returned and op is unmodified. If Poll succeeds and
+// the operation has completed with failure, the error is returned and op.Done will return true.
+// If Poll succeeds and the operation has completed successfully,
+// op.Done will return true, and the response of the operation is returned.
+// If Poll succeeds and the operation has not completed, the returned response and error are both nil.
+func (op *BatchTranslateTextOperation) Poll(ctx context.Context, opts ...gax.CallOption) (*translatepb.BatchTranslateResponse, error) {
+	var resp translatepb.BatchTranslateResponse
+	if err := op.lro.Poll(ctx, &resp, opts...); err != nil {
+		return nil, err
+	}
+	if !op.Done() {
+		return nil, nil
+	}
+	return &resp, nil
+}
+
+// Metadata returns metadata associated with the long-running operation.
+// Metadata itself does not contact the server, but Poll does.
+// To get the latest metadata, call this method after a successful call to Poll.
+// If the metadata is not available, the returned metadata and error are both nil.
+func (op *BatchTranslateTextOperation) Metadata() (*translatepb.BatchTranslateMetadata, error) {
+	var meta translatepb.BatchTranslateMetadata
+	if err := op.lro.Metadata(&meta); err == longrunning.ErrNoMetadata {
+		return nil, nil
+	} else if err != nil {
+		return nil, err
+	}
+	return &meta, nil
+}
+
+// Done reports whether the long-running operation has completed.
+func (op *BatchTranslateTextOperation) Done() bool {
+	return op.lro.Done()
+}
+
+// Name returns the name of the long-running operation.
+// The name is assigned by the server and is unique within the service from which the operation is created.
+func (op *BatchTranslateTextOperation) Name() string {
+	return op.lro.Name()
+}
+
+// CreateGlossaryOperation manages a long-running operation from CreateGlossary.
+type CreateGlossaryOperation struct {
+	lro *longrunning.Operation
+}
+
+// CreateGlossaryOperation returns a new CreateGlossaryOperation from a given name.
+// The name must be that of a previously created CreateGlossaryOperation, possibly from a different process.
+func (c *TranslationClient) CreateGlossaryOperation(name string) *CreateGlossaryOperation {
+	return &CreateGlossaryOperation{
+		lro: longrunning.InternalNewOperation(c.LROClient, &longrunningpb.Operation{Name: name}),
+	}
+}
+
+// Wait blocks until the long-running operation is completed, returning the response and any errors encountered.
+//
+// See documentation of Poll for error-handling information.
+func (op *CreateGlossaryOperation) Wait(ctx context.Context, opts ...gax.CallOption) (*translatepb.Glossary, error) {
+	var resp translatepb.Glossary
+	if err := op.lro.WaitWithInterval(ctx, &resp, 5000*time.Millisecond, opts...); err != nil {
+		return nil, err
+	}
+	return &resp, nil
+}
+
+// Poll fetches the latest state of the long-running operation.
+//
+// Poll also fetches the latest metadata, which can be retrieved by Metadata.
+//
+// If Poll fails, the error is returned and op is unmodified. If Poll succeeds and
+// the operation has completed with failure, the error is returned and op.Done will return true.
+// If Poll succeeds and the operation has completed successfully,
+// op.Done will return true, and the response of the operation is returned.
+// If Poll succeeds and the operation has not completed, the returned response and error are both nil.
+func (op *CreateGlossaryOperation) Poll(ctx context.Context, opts ...gax.CallOption) (*translatepb.Glossary, error) {
+	var resp translatepb.Glossary
+	if err := op.lro.Poll(ctx, &resp, opts...); err != nil {
+		return nil, err
+	}
+	if !op.Done() {
+		return nil, nil
+	}
+	return &resp, nil
+}
+
+// Metadata returns metadata associated with the long-running operation.
+// Metadata itself does not contact the server, but Poll does.
+// To get the latest metadata, call this method after a successful call to Poll.
+// If the metadata is not available, the returned metadata and error are both nil.
+func (op *CreateGlossaryOperation) Metadata() (*translatepb.CreateGlossaryMetadata, error) {
+	var meta translatepb.CreateGlossaryMetadata
+	if err := op.lro.Metadata(&meta); err == longrunning.ErrNoMetadata {
+		return nil, nil
+	} else if err != nil {
+		return nil, err
+	}
+	return &meta, nil
+}
+
+// Done reports whether the long-running operation has completed.
+func (op *CreateGlossaryOperation) Done() bool {
+	return op.lro.Done()
+}
+
+// Name returns the name of the long-running operation.
+// The name is assigned by the server and is unique within the service from which the operation is created.
+func (op *CreateGlossaryOperation) Name() string {
+	return op.lro.Name()
+}
+
+// DeleteGlossaryOperation manages a long-running operation from DeleteGlossary.
+type DeleteGlossaryOperation struct {
+	lro *longrunning.Operation
+}
+
+// DeleteGlossaryOperation returns a new DeleteGlossaryOperation from a given name.
+// The name must be that of a previously created DeleteGlossaryOperation, possibly from a different process.
+func (c *TranslationClient) DeleteGlossaryOperation(name string) *DeleteGlossaryOperation {
+	return &DeleteGlossaryOperation{
+		lro: longrunning.InternalNewOperation(c.LROClient, &longrunningpb.Operation{Name: name}),
+	}
+}
+
+// Wait blocks until the long-running operation is completed, returning the response and any errors encountered.
+//
+// See documentation of Poll for error-handling information.
+func (op *DeleteGlossaryOperation) Wait(ctx context.Context, opts ...gax.CallOption) (*translatepb.DeleteGlossaryResponse, error) {
+	var resp translatepb.DeleteGlossaryResponse
+	if err := op.lro.WaitWithInterval(ctx, &resp, 5000*time.Millisecond, opts...); err != nil {
+		return nil, err
+	}
+	return &resp, nil
+}
+
+// Poll fetches the latest state of the long-running operation.
+//
+// Poll also fetches the latest metadata, which can be retrieved by Metadata.
+//
+// If Poll fails, the error is returned and op is unmodified. If Poll succeeds and
+// the operation has completed with failure, the error is returned and op.Done will return true.
+// If Poll succeeds and the operation has completed successfully,
+// op.Done will return true, and the response of the operation is returned.
+// If Poll succeeds and the operation has not completed, the returned response and error are both nil.
+func (op *DeleteGlossaryOperation) Poll(ctx context.Context, opts ...gax.CallOption) (*translatepb.DeleteGlossaryResponse, error) {
+	var resp translatepb.DeleteGlossaryResponse
+	if err := op.lro.Poll(ctx, &resp, opts...); err != nil {
+		return nil, err
+	}
+	if !op.Done() {
+		return nil, nil
+	}
+	return &resp, nil
+}
+
+// Metadata returns metadata associated with the long-running operation.
+// Metadata itself does not contact the server, but Poll does.
+// To get the latest metadata, call this method after a successful call to Poll.
+// If the metadata is not available, the returned metadata and error are both nil.
+func (op *DeleteGlossaryOperation) Metadata() (*translatepb.DeleteGlossaryMetadata, error) {
+	var meta translatepb.DeleteGlossaryMetadata
+	if err := op.lro.Metadata(&meta); err == longrunning.ErrNoMetadata {
+		return nil, nil
+	} else if err != nil {
+		return nil, err
+	}
+	return &meta, nil
+}
+
+// Done reports whether the long-running operation has completed.
+func (op *DeleteGlossaryOperation) Done() bool {
+	return op.lro.Done()
+}
+
+// Name returns the name of the long-running operation.
+// The name is assigned by the server and is unique within the service from which the operation is created.
+func (op *DeleteGlossaryOperation) Name() string {
+	return op.lro.Name()
+}
diff --git a/translate/apiv3/translation_client_example_test.go b/translate/apiv3/translation_client_example_test.go
new file mode 100644
index 0000000..9f9e880b
--- /dev/null
+++ b/translate/apiv3/translation_client_example_test.go
@@ -0,0 +1,200 @@
+// Copyright 2019 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 gapic-generator. DO NOT EDIT.
+
+package translate_test
+
+import (
+	"context"
+
+	translate "cloud.google.com/go/translate/apiv3"
+	"google.golang.org/api/iterator"
+	translatepb "google.golang.org/genproto/googleapis/cloud/translate/v3"
+)
+
+func ExampleNewTranslationClient() {
+	ctx := context.Background()
+	c, err := translate.NewTranslationClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+	// TODO: Use client.
+	_ = c
+}
+
+func ExampleTranslationClient_TranslateText() {
+	ctx := context.Background()
+	c, err := translate.NewTranslationClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &translatepb.TranslateTextRequest{
+		// TODO: Fill request struct fields.
+	}
+	resp, err := c.TranslateText(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+	// TODO: Use resp.
+	_ = resp
+}
+
+func ExampleTranslationClient_DetectLanguage() {
+	ctx := context.Background()
+	c, err := translate.NewTranslationClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &translatepb.DetectLanguageRequest{
+		// TODO: Fill request struct fields.
+	}
+	resp, err := c.DetectLanguage(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+	// TODO: Use resp.
+	_ = resp
+}
+
+func ExampleTranslationClient_GetSupportedLanguages() {
+	ctx := context.Background()
+	c, err := translate.NewTranslationClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &translatepb.GetSupportedLanguagesRequest{
+		// TODO: Fill request struct fields.
+	}
+	resp, err := c.GetSupportedLanguages(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+	// TODO: Use resp.
+	_ = resp
+}
+
+func ExampleTranslationClient_BatchTranslateText() {
+	ctx := context.Background()
+	c, err := translate.NewTranslationClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &translatepb.BatchTranslateTextRequest{
+		// TODO: Fill request struct fields.
+	}
+	op, err := c.BatchTranslateText(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	resp, err := op.Wait(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+	// TODO: Use resp.
+	_ = resp
+}
+
+func ExampleTranslationClient_CreateGlossary() {
+	ctx := context.Background()
+	c, err := translate.NewTranslationClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &translatepb.CreateGlossaryRequest{
+		// TODO: Fill request struct fields.
+	}
+	op, err := c.CreateGlossary(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	resp, err := op.Wait(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+	// TODO: Use resp.
+	_ = resp
+}
+
+func ExampleTranslationClient_ListGlossaries() {
+	ctx := context.Background()
+	c, err := translate.NewTranslationClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &translatepb.ListGlossariesRequest{
+		// TODO: Fill request struct fields.
+	}
+	it := c.ListGlossaries(ctx, req)
+	for {
+		resp, err := it.Next()
+		if err == iterator.Done {
+			break
+		}
+		if err != nil {
+			// TODO: Handle error.
+		}
+		// TODO: Use resp.
+		_ = resp
+	}
+}
+
+func ExampleTranslationClient_GetGlossary() {
+	ctx := context.Background()
+	c, err := translate.NewTranslationClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &translatepb.GetGlossaryRequest{
+		// TODO: Fill request struct fields.
+	}
+	resp, err := c.GetGlossary(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+	// TODO: Use resp.
+	_ = resp
+}
+
+func ExampleTranslationClient_DeleteGlossary() {
+	ctx := context.Background()
+	c, err := translate.NewTranslationClient(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	req := &translatepb.DeleteGlossaryRequest{
+		// TODO: Fill request struct fields.
+	}
+	op, err := c.DeleteGlossary(ctx, req)
+	if err != nil {
+		// TODO: Handle error.
+	}
+
+	resp, err := op.Wait(ctx)
+	if err != nil {
+		// TODO: Handle error.
+	}
+	// TODO: Use resp.
+	_ = resp
+}
diff --git a/videointelligence/apiv1/doc.go b/videointelligence/apiv1/doc.go
index 39b1d81..9324256 100644
--- a/videointelligence/apiv1/doc.go
+++ b/videointelligence/apiv1/doc.go
@@ -99,4 +99,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/videointelligence/apiv1beta1/doc.go b/videointelligence/apiv1beta1/doc.go
index 350b336..5b74093 100644
--- a/videointelligence/apiv1beta1/doc.go
+++ b/videointelligence/apiv1beta1/doc.go
@@ -99,4 +99,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/videointelligence/apiv1beta2/doc.go b/videointelligence/apiv1beta2/doc.go
index 0028904..00aad7f 100644
--- a/videointelligence/apiv1beta2/doc.go
+++ b/videointelligence/apiv1beta2/doc.go
@@ -99,4 +99,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/vision/apiv1/doc.go b/vision/apiv1/doc.go
index dc2e3db..0d79373 100644
--- a/vision/apiv1/doc.go
+++ b/vision/apiv1/doc.go
@@ -99,4 +99,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/vision/apiv1p1beta1/doc.go b/vision/apiv1p1beta1/doc.go
index b29846c..70c0b56 100644
--- a/vision/apiv1p1beta1/doc.go
+++ b/vision/apiv1p1beta1/doc.go
@@ -101,4 +101,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
diff --git a/webrisk/apiv1beta1/doc.go b/webrisk/apiv1beta1/doc.go
index 20f50c6..bbc2a0c 100644
--- a/webrisk/apiv1beta1/doc.go
+++ b/webrisk/apiv1beta1/doc.go
@@ -96,4 +96,4 @@
 	return "UNKNOWN"
 }
 
-const versionClient = "20191002"
+const versionClient = "20191004"
