// Copyright 2020 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 talent

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"
	talentpb "google.golang.org/genproto/googleapis/cloud/talent/v4beta1"
	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 mockApplicationServer struct {
	// Embed for forward compatibility.
	// Tests will keep working if more methods are added
	// in the future.
	talentpb.ApplicationServiceServer

	reqs []proto.Message

	// If set, all calls return this error.
	err error

	// responses to return if err == nil
	resps []proto.Message
}

func (s *mockApplicationServer) CreateApplication(ctx context.Context, req *talentpb.CreateApplicationRequest) (*talentpb.Application, 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].(*talentpb.Application), nil
}

func (s *mockApplicationServer) GetApplication(ctx context.Context, req *talentpb.GetApplicationRequest) (*talentpb.Application, 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].(*talentpb.Application), nil
}

func (s *mockApplicationServer) UpdateApplication(ctx context.Context, req *talentpb.UpdateApplicationRequest) (*talentpb.Application, 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].(*talentpb.Application), nil
}

func (s *mockApplicationServer) DeleteApplication(ctx context.Context, req *talentpb.DeleteApplicationRequest) (*emptypb.Empty, 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].(*emptypb.Empty), nil
}

func (s *mockApplicationServer) ListApplications(ctx context.Context, req *talentpb.ListApplicationsRequest) (*talentpb.ListApplicationsResponse, 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].(*talentpb.ListApplicationsResponse), nil
}

type mockCompanyServer struct {
	// Embed for forward compatibility.
	// Tests will keep working if more methods are added
	// in the future.
	talentpb.CompanyServiceServer

	reqs []proto.Message

	// If set, all calls return this error.
	err error

	// responses to return if err == nil
	resps []proto.Message
}

func (s *mockCompanyServer) CreateCompany(ctx context.Context, req *talentpb.CreateCompanyRequest) (*talentpb.Company, 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].(*talentpb.Company), nil
}

func (s *mockCompanyServer) GetCompany(ctx context.Context, req *talentpb.GetCompanyRequest) (*talentpb.Company, 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].(*talentpb.Company), nil
}

func (s *mockCompanyServer) UpdateCompany(ctx context.Context, req *talentpb.UpdateCompanyRequest) (*talentpb.Company, 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].(*talentpb.Company), nil
}

func (s *mockCompanyServer) DeleteCompany(ctx context.Context, req *talentpb.DeleteCompanyRequest) (*emptypb.Empty, 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].(*emptypb.Empty), nil
}

func (s *mockCompanyServer) ListCompanies(ctx context.Context, req *talentpb.ListCompaniesRequest) (*talentpb.ListCompaniesResponse, 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].(*talentpb.ListCompaniesResponse), nil
}

type mockCompletionServer struct {
	// Embed for forward compatibility.
	// Tests will keep working if more methods are added
	// in the future.
	talentpb.CompletionServer

	reqs []proto.Message

	// If set, all calls return this error.
	err error

	// responses to return if err == nil
	resps []proto.Message
}

func (s *mockCompletionServer) CompleteQuery(ctx context.Context, req *talentpb.CompleteQueryRequest) (*talentpb.CompleteQueryResponse, 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].(*talentpb.CompleteQueryResponse), nil
}

type mockEventServer struct {
	// Embed for forward compatibility.
	// Tests will keep working if more methods are added
	// in the future.
	talentpb.EventServiceServer

	reqs []proto.Message

	// If set, all calls return this error.
	err error

	// responses to return if err == nil
	resps []proto.Message
}

func (s *mockEventServer) CreateClientEvent(ctx context.Context, req *talentpb.CreateClientEventRequest) (*talentpb.ClientEvent, 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].(*talentpb.ClientEvent), nil
}

type mockJobServer struct {
	// Embed for forward compatibility.
	// Tests will keep working if more methods are added
	// in the future.
	talentpb.JobServiceServer

	reqs []proto.Message

	// If set, all calls return this error.
	err error

	// responses to return if err == nil
	resps []proto.Message
}

func (s *mockJobServer) CreateJob(ctx context.Context, req *talentpb.CreateJobRequest) (*talentpb.Job, 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].(*talentpb.Job), nil
}

func (s *mockJobServer) BatchCreateJobs(ctx context.Context, req *talentpb.BatchCreateJobsRequest) (*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 *mockJobServer) GetJob(ctx context.Context, req *talentpb.GetJobRequest) (*talentpb.Job, 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].(*talentpb.Job), nil
}

func (s *mockJobServer) UpdateJob(ctx context.Context, req *talentpb.UpdateJobRequest) (*talentpb.Job, 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].(*talentpb.Job), nil
}

func (s *mockJobServer) BatchUpdateJobs(ctx context.Context, req *talentpb.BatchUpdateJobsRequest) (*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 *mockJobServer) DeleteJob(ctx context.Context, req *talentpb.DeleteJobRequest) (*emptypb.Empty, 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].(*emptypb.Empty), nil
}

func (s *mockJobServer) BatchDeleteJobs(ctx context.Context, req *talentpb.BatchDeleteJobsRequest) (*emptypb.Empty, 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].(*emptypb.Empty), nil
}

func (s *mockJobServer) ListJobs(ctx context.Context, req *talentpb.ListJobsRequest) (*talentpb.ListJobsResponse, 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].(*talentpb.ListJobsResponse), nil
}

func (s *mockJobServer) SearchJobs(ctx context.Context, req *talentpb.SearchJobsRequest) (*talentpb.SearchJobsResponse, 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].(*talentpb.SearchJobsResponse), nil
}

func (s *mockJobServer) SearchJobsForAlert(ctx context.Context, req *talentpb.SearchJobsRequest) (*talentpb.SearchJobsResponse, 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].(*talentpb.SearchJobsResponse), nil
}

type mockProfileServer struct {
	// Embed for forward compatibility.
	// Tests will keep working if more methods are added
	// in the future.
	talentpb.ProfileServiceServer

	reqs []proto.Message

	// If set, all calls return this error.
	err error

	// responses to return if err == nil
	resps []proto.Message
}

func (s *mockProfileServer) ListProfiles(ctx context.Context, req *talentpb.ListProfilesRequest) (*talentpb.ListProfilesResponse, 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].(*talentpb.ListProfilesResponse), nil
}

func (s *mockProfileServer) CreateProfile(ctx context.Context, req *talentpb.CreateProfileRequest) (*talentpb.Profile, 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].(*talentpb.Profile), nil
}

func (s *mockProfileServer) GetProfile(ctx context.Context, req *talentpb.GetProfileRequest) (*talentpb.Profile, 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].(*talentpb.Profile), nil
}

func (s *mockProfileServer) UpdateProfile(ctx context.Context, req *talentpb.UpdateProfileRequest) (*talentpb.Profile, 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].(*talentpb.Profile), nil
}

func (s *mockProfileServer) DeleteProfile(ctx context.Context, req *talentpb.DeleteProfileRequest) (*emptypb.Empty, 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].(*emptypb.Empty), nil
}

func (s *mockProfileServer) SearchProfiles(ctx context.Context, req *talentpb.SearchProfilesRequest) (*talentpb.SearchProfilesResponse, 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].(*talentpb.SearchProfilesResponse), nil
}

type mockTenantServer struct {
	// Embed for forward compatibility.
	// Tests will keep working if more methods are added
	// in the future.
	talentpb.TenantServiceServer

	reqs []proto.Message

	// If set, all calls return this error.
	err error

	// responses to return if err == nil
	resps []proto.Message
}

func (s *mockTenantServer) CreateTenant(ctx context.Context, req *talentpb.CreateTenantRequest) (*talentpb.Tenant, 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].(*talentpb.Tenant), nil
}

func (s *mockTenantServer) GetTenant(ctx context.Context, req *talentpb.GetTenantRequest) (*talentpb.Tenant, 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].(*talentpb.Tenant), nil
}

func (s *mockTenantServer) UpdateTenant(ctx context.Context, req *talentpb.UpdateTenantRequest) (*talentpb.Tenant, 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].(*talentpb.Tenant), nil
}

func (s *mockTenantServer) DeleteTenant(ctx context.Context, req *talentpb.DeleteTenantRequest) (*emptypb.Empty, 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].(*emptypb.Empty), nil
}

func (s *mockTenantServer) ListTenants(ctx context.Context, req *talentpb.ListTenantsRequest) (*talentpb.ListTenantsResponse, 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].(*talentpb.ListTenantsResponse), nil
}

// clientOpt is the option tests should use to connect to the test server.
// It is initialized by TestMain.
var clientOpt option.ClientOption

var (
	mockApplication mockApplicationServer
	mockCompany     mockCompanyServer
	mockCompletion  mockCompletionServer
	mockEvent       mockEventServer
	mockJob         mockJobServer
	mockProfile     mockProfileServer
	mockTenant      mockTenantServer
)

func TestMain(m *testing.M) {
	flag.Parse()

	serv := grpc.NewServer()
	talentpb.RegisterApplicationServiceServer(serv, &mockApplication)
	talentpb.RegisterCompanyServiceServer(serv, &mockCompany)
	talentpb.RegisterCompletionServer(serv, &mockCompletion)
	talentpb.RegisterEventServiceServer(serv, &mockEvent)
	talentpb.RegisterJobServiceServer(serv, &mockJob)
	talentpb.RegisterProfileServiceServer(serv, &mockProfile)
	talentpb.RegisterTenantServiceServer(serv, &mockTenant)

	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 TestApplicationServiceCreateApplication(t *testing.T) {
	var name string = "name3373707"
	var externalId string = "externalId-1153075697"
	var profile string = "profile-309425751"
	var job string = "job105405"
	var company string = "company950484093"
	var outcomeNotes string = "outcomeNotes-355961964"
	var jobTitleSnippet string = "jobTitleSnippet-1100512972"
	var expectedResponse = &talentpb.Application{
		Name:            name,
		ExternalId:      externalId,
		Profile:         profile,
		Job:             job,
		Company:         company,
		OutcomeNotes:    outcomeNotes,
		JobTitleSnippet: jobTitleSnippet,
	}

	mockApplication.err = nil
	mockApplication.reqs = nil

	mockApplication.resps = append(mockApplication.resps[:0], expectedResponse)

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s/profiles/%s", "[PROJECT]", "[TENANT]", "[PROFILE]")
	var application *talentpb.Application = &talentpb.Application{}
	var request = &talentpb.CreateApplicationRequest{
		Parent:      formattedParent,
		Application: application,
	}

	c, err := NewApplicationClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.CreateApplication(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockApplication.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 TestApplicationServiceCreateApplicationError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockApplication.err = gstatus.Error(errCode, "test error")

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s/profiles/%s", "[PROJECT]", "[TENANT]", "[PROFILE]")
	var application *talentpb.Application = &talentpb.Application{}
	var request = &talentpb.CreateApplicationRequest{
		Parent:      formattedParent,
		Application: application,
	}

	c, err := NewApplicationClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.CreateApplication(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 TestApplicationServiceGetApplication(t *testing.T) {
	var name2 string = "name2-1052831874"
	var externalId string = "externalId-1153075697"
	var profile string = "profile-309425751"
	var job string = "job105405"
	var company string = "company950484093"
	var outcomeNotes string = "outcomeNotes-355961964"
	var jobTitleSnippet string = "jobTitleSnippet-1100512972"
	var expectedResponse = &talentpb.Application{
		Name:            name2,
		ExternalId:      externalId,
		Profile:         profile,
		Job:             job,
		Company:         company,
		OutcomeNotes:    outcomeNotes,
		JobTitleSnippet: jobTitleSnippet,
	}

	mockApplication.err = nil
	mockApplication.reqs = nil

	mockApplication.resps = append(mockApplication.resps[:0], expectedResponse)

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s/profiles/%s/applications/%s", "[PROJECT]", "[TENANT]", "[PROFILE]", "[APPLICATION]")
	var request = &talentpb.GetApplicationRequest{
		Name: formattedName,
	}

	c, err := NewApplicationClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.GetApplication(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockApplication.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 TestApplicationServiceGetApplicationError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockApplication.err = gstatus.Error(errCode, "test error")

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s/profiles/%s/applications/%s", "[PROJECT]", "[TENANT]", "[PROFILE]", "[APPLICATION]")
	var request = &talentpb.GetApplicationRequest{
		Name: formattedName,
	}

	c, err := NewApplicationClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.GetApplication(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 TestApplicationServiceUpdateApplication(t *testing.T) {
	var name string = "name3373707"
	var externalId string = "externalId-1153075697"
	var profile string = "profile-309425751"
	var job string = "job105405"
	var company string = "company950484093"
	var outcomeNotes string = "outcomeNotes-355961964"
	var jobTitleSnippet string = "jobTitleSnippet-1100512972"
	var expectedResponse = &talentpb.Application{
		Name:            name,
		ExternalId:      externalId,
		Profile:         profile,
		Job:             job,
		Company:         company,
		OutcomeNotes:    outcomeNotes,
		JobTitleSnippet: jobTitleSnippet,
	}

	mockApplication.err = nil
	mockApplication.reqs = nil

	mockApplication.resps = append(mockApplication.resps[:0], expectedResponse)

	var application *talentpb.Application = &talentpb.Application{}
	var request = &talentpb.UpdateApplicationRequest{
		Application: application,
	}

	c, err := NewApplicationClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.UpdateApplication(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockApplication.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 TestApplicationServiceUpdateApplicationError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockApplication.err = gstatus.Error(errCode, "test error")

	var application *talentpb.Application = &talentpb.Application{}
	var request = &talentpb.UpdateApplicationRequest{
		Application: application,
	}

	c, err := NewApplicationClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.UpdateApplication(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 TestApplicationServiceDeleteApplication(t *testing.T) {
	var expectedResponse *emptypb.Empty = &emptypb.Empty{}

	mockApplication.err = nil
	mockApplication.reqs = nil

	mockApplication.resps = append(mockApplication.resps[:0], expectedResponse)

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s/profiles/%s/applications/%s", "[PROJECT]", "[TENANT]", "[PROFILE]", "[APPLICATION]")
	var request = &talentpb.DeleteApplicationRequest{
		Name: formattedName,
	}

	c, err := NewApplicationClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	err = c.DeleteApplication(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockApplication.reqs[0]; !proto.Equal(want, got) {
		t.Errorf("wrong request %q, want %q", got, want)
	}

}

func TestApplicationServiceDeleteApplicationError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockApplication.err = gstatus.Error(errCode, "test error")

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s/profiles/%s/applications/%s", "[PROJECT]", "[TENANT]", "[PROFILE]", "[APPLICATION]")
	var request = &talentpb.DeleteApplicationRequest{
		Name: formattedName,
	}

	c, err := NewApplicationClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	err = c.DeleteApplication(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)
	}
}
func TestApplicationServiceListApplications(t *testing.T) {
	var nextPageToken string = ""
	var applicationsElement *talentpb.Application = &talentpb.Application{}
	var applications = []*talentpb.Application{applicationsElement}
	var expectedResponse = &talentpb.ListApplicationsResponse{
		NextPageToken: nextPageToken,
		Applications:  applications,
	}

	mockApplication.err = nil
	mockApplication.reqs = nil

	mockApplication.resps = append(mockApplication.resps[:0], expectedResponse)

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s/profiles/%s", "[PROJECT]", "[TENANT]", "[PROFILE]")
	var request = &talentpb.ListApplicationsRequest{
		Parent: formattedParent,
	}

	c, err := NewApplicationClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.ListApplications(context.Background(), request).Next()

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockApplication.reqs[0]; !proto.Equal(want, got) {
		t.Errorf("wrong request %q, want %q", got, want)
	}

	want := (interface{})(expectedResponse.Applications[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 TestApplicationServiceListApplicationsError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockApplication.err = gstatus.Error(errCode, "test error")

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s/profiles/%s", "[PROJECT]", "[TENANT]", "[PROFILE]")
	var request = &talentpb.ListApplicationsRequest{
		Parent: formattedParent,
	}

	c, err := NewApplicationClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.ListApplications(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 TestCompanyServiceCreateCompany(t *testing.T) {
	var name string = "name3373707"
	var displayName string = "displayName1615086568"
	var externalId string = "externalId-1153075697"
	var headquartersAddress string = "headquartersAddress-1879520036"
	var hiringAgency bool = false
	var eeoText string = "eeoText-1652097123"
	var websiteUri string = "websiteUri-2118185016"
	var careerSiteUri string = "careerSiteUri1223331861"
	var imageUri string = "imageUri-877823864"
	var suspended bool = false
	var expectedResponse = &talentpb.Company{
		Name:                name,
		DisplayName:         displayName,
		ExternalId:          externalId,
		HeadquartersAddress: headquartersAddress,
		HiringAgency:        hiringAgency,
		EeoText:             eeoText,
		WebsiteUri:          websiteUri,
		CareerSiteUri:       careerSiteUri,
		ImageUri:            imageUri,
		Suspended:           suspended,
	}

	mockCompany.err = nil
	mockCompany.reqs = nil

	mockCompany.resps = append(mockCompany.resps[:0], expectedResponse)

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var company *talentpb.Company = &talentpb.Company{}
	var request = &talentpb.CreateCompanyRequest{
		Parent:  formattedParent,
		Company: company,
	}

	c, err := NewCompanyClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.CreateCompany(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockCompany.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 TestCompanyServiceCreateCompanyError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockCompany.err = gstatus.Error(errCode, "test error")

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var company *talentpb.Company = &talentpb.Company{}
	var request = &talentpb.CreateCompanyRequest{
		Parent:  formattedParent,
		Company: company,
	}

	c, err := NewCompanyClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.CreateCompany(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 TestCompanyServiceGetCompany(t *testing.T) {
	var name2 string = "name2-1052831874"
	var displayName string = "displayName1615086568"
	var externalId string = "externalId-1153075697"
	var headquartersAddress string = "headquartersAddress-1879520036"
	var hiringAgency bool = false
	var eeoText string = "eeoText-1652097123"
	var websiteUri string = "websiteUri-2118185016"
	var careerSiteUri string = "careerSiteUri1223331861"
	var imageUri string = "imageUri-877823864"
	var suspended bool = false
	var expectedResponse = &talentpb.Company{
		Name:                name2,
		DisplayName:         displayName,
		ExternalId:          externalId,
		HeadquartersAddress: headquartersAddress,
		HiringAgency:        hiringAgency,
		EeoText:             eeoText,
		WebsiteUri:          websiteUri,
		CareerSiteUri:       careerSiteUri,
		ImageUri:            imageUri,
		Suspended:           suspended,
	}

	mockCompany.err = nil
	mockCompany.reqs = nil

	mockCompany.resps = append(mockCompany.resps[:0], expectedResponse)

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s/companies/%s", "[PROJECT]", "[TENANT]", "[COMPANY]")
	var request = &talentpb.GetCompanyRequest{
		Name: formattedName,
	}

	c, err := NewCompanyClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.GetCompany(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockCompany.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 TestCompanyServiceGetCompanyError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockCompany.err = gstatus.Error(errCode, "test error")

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s/companies/%s", "[PROJECT]", "[TENANT]", "[COMPANY]")
	var request = &talentpb.GetCompanyRequest{
		Name: formattedName,
	}

	c, err := NewCompanyClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.GetCompany(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 TestCompanyServiceUpdateCompany(t *testing.T) {
	var name string = "name3373707"
	var displayName string = "displayName1615086568"
	var externalId string = "externalId-1153075697"
	var headquartersAddress string = "headquartersAddress-1879520036"
	var hiringAgency bool = false
	var eeoText string = "eeoText-1652097123"
	var websiteUri string = "websiteUri-2118185016"
	var careerSiteUri string = "careerSiteUri1223331861"
	var imageUri string = "imageUri-877823864"
	var suspended bool = false
	var expectedResponse = &talentpb.Company{
		Name:                name,
		DisplayName:         displayName,
		ExternalId:          externalId,
		HeadquartersAddress: headquartersAddress,
		HiringAgency:        hiringAgency,
		EeoText:             eeoText,
		WebsiteUri:          websiteUri,
		CareerSiteUri:       careerSiteUri,
		ImageUri:            imageUri,
		Suspended:           suspended,
	}

	mockCompany.err = nil
	mockCompany.reqs = nil

	mockCompany.resps = append(mockCompany.resps[:0], expectedResponse)

	var company *talentpb.Company = &talentpb.Company{}
	var request = &talentpb.UpdateCompanyRequest{
		Company: company,
	}

	c, err := NewCompanyClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.UpdateCompany(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockCompany.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 TestCompanyServiceUpdateCompanyError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockCompany.err = gstatus.Error(errCode, "test error")

	var company *talentpb.Company = &talentpb.Company{}
	var request = &talentpb.UpdateCompanyRequest{
		Company: company,
	}

	c, err := NewCompanyClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.UpdateCompany(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 TestCompanyServiceDeleteCompany(t *testing.T) {
	var expectedResponse *emptypb.Empty = &emptypb.Empty{}

	mockCompany.err = nil
	mockCompany.reqs = nil

	mockCompany.resps = append(mockCompany.resps[:0], expectedResponse)

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s/companies/%s", "[PROJECT]", "[TENANT]", "[COMPANY]")
	var request = &talentpb.DeleteCompanyRequest{
		Name: formattedName,
	}

	c, err := NewCompanyClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	err = c.DeleteCompany(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockCompany.reqs[0]; !proto.Equal(want, got) {
		t.Errorf("wrong request %q, want %q", got, want)
	}

}

func TestCompanyServiceDeleteCompanyError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockCompany.err = gstatus.Error(errCode, "test error")

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s/companies/%s", "[PROJECT]", "[TENANT]", "[COMPANY]")
	var request = &talentpb.DeleteCompanyRequest{
		Name: formattedName,
	}

	c, err := NewCompanyClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	err = c.DeleteCompany(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)
	}
}
func TestCompanyServiceListCompanies(t *testing.T) {
	var nextPageToken string = ""
	var companiesElement *talentpb.Company = &talentpb.Company{}
	var companies = []*talentpb.Company{companiesElement}
	var expectedResponse = &talentpb.ListCompaniesResponse{
		NextPageToken: nextPageToken,
		Companies:     companies,
	}

	mockCompany.err = nil
	mockCompany.reqs = nil

	mockCompany.resps = append(mockCompany.resps[:0], expectedResponse)

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var request = &talentpb.ListCompaniesRequest{
		Parent: formattedParent,
	}

	c, err := NewCompanyClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.ListCompanies(context.Background(), request).Next()

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockCompany.reqs[0]; !proto.Equal(want, got) {
		t.Errorf("wrong request %q, want %q", got, want)
	}

	want := (interface{})(expectedResponse.Companies[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 TestCompanyServiceListCompaniesError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockCompany.err = gstatus.Error(errCode, "test error")

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var request = &talentpb.ListCompaniesRequest{
		Parent: formattedParent,
	}

	c, err := NewCompanyClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.ListCompanies(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 TestCompletionCompleteQuery(t *testing.T) {
	var expectedResponse *talentpb.CompleteQueryResponse = &talentpb.CompleteQueryResponse{}

	mockCompletion.err = nil
	mockCompletion.reqs = nil

	mockCompletion.resps = append(mockCompletion.resps[:0], expectedResponse)

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var query string = "query107944136"
	var pageSize int32 = 883849137
	var request = &talentpb.CompleteQueryRequest{
		Parent:   formattedParent,
		Query:    query,
		PageSize: pageSize,
	}

	c, err := NewCompletionClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.CompleteQuery(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockCompletion.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 TestCompletionCompleteQueryError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockCompletion.err = gstatus.Error(errCode, "test error")

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var query string = "query107944136"
	var pageSize int32 = 883849137
	var request = &talentpb.CompleteQueryRequest{
		Parent:   formattedParent,
		Query:    query,
		PageSize: pageSize,
	}

	c, err := NewCompletionClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.CompleteQuery(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 TestEventServiceCreateClientEvent(t *testing.T) {
	var requestId string = "requestId37109963"
	var eventId string = "eventId278118624"
	var eventNotes string = "eventNotes445073628"
	var expectedResponse = &talentpb.ClientEvent{
		RequestId:  requestId,
		EventId:    eventId,
		EventNotes: eventNotes,
	}

	mockEvent.err = nil
	mockEvent.reqs = nil

	mockEvent.resps = append(mockEvent.resps[:0], expectedResponse)

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var clientEvent *talentpb.ClientEvent = &talentpb.ClientEvent{}
	var request = &talentpb.CreateClientEventRequest{
		Parent:      formattedParent,
		ClientEvent: clientEvent,
	}

	c, err := NewEventClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.CreateClientEvent(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockEvent.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 TestEventServiceCreateClientEventError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockEvent.err = gstatus.Error(errCode, "test error")

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var clientEvent *talentpb.ClientEvent = &talentpb.ClientEvent{}
	var request = &talentpb.CreateClientEventRequest{
		Parent:      formattedParent,
		ClientEvent: clientEvent,
	}

	c, err := NewEventClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.CreateClientEvent(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 TestJobServiceCreateJob(t *testing.T) {
	var name string = "name3373707"
	var company string = "company950484093"
	var requisitionId string = "requisitionId980224926"
	var title string = "title110371416"
	var description string = "description-1724546052"
	var department string = "department848184146"
	var incentives string = "incentives-1262874520"
	var languageCode string = "languageCode-412800396"
	var promotionValue int32 = 353413845
	var qualifications string = "qualifications1903501412"
	var responsibilities string = "responsibilities-926952660"
	var companyDisplayName string = "companyDisplayName1982424170"
	var expectedResponse = &talentpb.Job{
		Name:               name,
		Company:            company,
		RequisitionId:      requisitionId,
		Title:              title,
		Description:        description,
		Department:         department,
		Incentives:         incentives,
		LanguageCode:       languageCode,
		PromotionValue:     promotionValue,
		Qualifications:     qualifications,
		Responsibilities:   responsibilities,
		CompanyDisplayName: companyDisplayName,
	}

	mockJob.err = nil
	mockJob.reqs = nil

	mockJob.resps = append(mockJob.resps[:0], expectedResponse)

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var job *talentpb.Job = &talentpb.Job{}
	var request = &talentpb.CreateJobRequest{
		Parent: formattedParent,
		Job:    job,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.CreateJob(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockJob.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 TestJobServiceCreateJobError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockJob.err = gstatus.Error(errCode, "test error")

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var job *talentpb.Job = &talentpb.Job{}
	var request = &talentpb.CreateJobRequest{
		Parent: formattedParent,
		Job:    job,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.CreateJob(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 TestJobServiceGetJob(t *testing.T) {
	var name2 string = "name2-1052831874"
	var company string = "company950484093"
	var requisitionId string = "requisitionId980224926"
	var title string = "title110371416"
	var description string = "description-1724546052"
	var department string = "department848184146"
	var incentives string = "incentives-1262874520"
	var languageCode string = "languageCode-412800396"
	var promotionValue int32 = 353413845
	var qualifications string = "qualifications1903501412"
	var responsibilities string = "responsibilities-926952660"
	var companyDisplayName string = "companyDisplayName1982424170"
	var expectedResponse = &talentpb.Job{
		Name:               name2,
		Company:            company,
		RequisitionId:      requisitionId,
		Title:              title,
		Description:        description,
		Department:         department,
		Incentives:         incentives,
		LanguageCode:       languageCode,
		PromotionValue:     promotionValue,
		Qualifications:     qualifications,
		Responsibilities:   responsibilities,
		CompanyDisplayName: companyDisplayName,
	}

	mockJob.err = nil
	mockJob.reqs = nil

	mockJob.resps = append(mockJob.resps[:0], expectedResponse)

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s/jobs/%s", "[PROJECT]", "[TENANT]", "[JOBS]")
	var request = &talentpb.GetJobRequest{
		Name: formattedName,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.GetJob(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockJob.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 TestJobServiceGetJobError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockJob.err = gstatus.Error(errCode, "test error")

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s/jobs/%s", "[PROJECT]", "[TENANT]", "[JOBS]")
	var request = &talentpb.GetJobRequest{
		Name: formattedName,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.GetJob(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 TestJobServiceUpdateJob(t *testing.T) {
	var name string = "name3373707"
	var company string = "company950484093"
	var requisitionId string = "requisitionId980224926"
	var title string = "title110371416"
	var description string = "description-1724546052"
	var department string = "department848184146"
	var incentives string = "incentives-1262874520"
	var languageCode string = "languageCode-412800396"
	var promotionValue int32 = 353413845
	var qualifications string = "qualifications1903501412"
	var responsibilities string = "responsibilities-926952660"
	var companyDisplayName string = "companyDisplayName1982424170"
	var expectedResponse = &talentpb.Job{
		Name:               name,
		Company:            company,
		RequisitionId:      requisitionId,
		Title:              title,
		Description:        description,
		Department:         department,
		Incentives:         incentives,
		LanguageCode:       languageCode,
		PromotionValue:     promotionValue,
		Qualifications:     qualifications,
		Responsibilities:   responsibilities,
		CompanyDisplayName: companyDisplayName,
	}

	mockJob.err = nil
	mockJob.reqs = nil

	mockJob.resps = append(mockJob.resps[:0], expectedResponse)

	var job *talentpb.Job = &talentpb.Job{}
	var request = &talentpb.UpdateJobRequest{
		Job: job,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.UpdateJob(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockJob.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 TestJobServiceUpdateJobError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockJob.err = gstatus.Error(errCode, "test error")

	var job *talentpb.Job = &talentpb.Job{}
	var request = &talentpb.UpdateJobRequest{
		Job: job,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.UpdateJob(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 TestJobServiceDeleteJob(t *testing.T) {
	var expectedResponse *emptypb.Empty = &emptypb.Empty{}

	mockJob.err = nil
	mockJob.reqs = nil

	mockJob.resps = append(mockJob.resps[:0], expectedResponse)

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s/jobs/%s", "[PROJECT]", "[TENANT]", "[JOBS]")
	var request = &talentpb.DeleteJobRequest{
		Name: formattedName,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	err = c.DeleteJob(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockJob.reqs[0]; !proto.Equal(want, got) {
		t.Errorf("wrong request %q, want %q", got, want)
	}

}

func TestJobServiceDeleteJobError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockJob.err = gstatus.Error(errCode, "test error")

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s/jobs/%s", "[PROJECT]", "[TENANT]", "[JOBS]")
	var request = &talentpb.DeleteJobRequest{
		Name: formattedName,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	err = c.DeleteJob(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)
	}
}
func TestJobServiceListJobs(t *testing.T) {
	var nextPageToken string = ""
	var jobsElement *talentpb.Job = &talentpb.Job{}
	var jobs = []*talentpb.Job{jobsElement}
	var expectedResponse = &talentpb.ListJobsResponse{
		NextPageToken: nextPageToken,
		Jobs:          jobs,
	}

	mockJob.err = nil
	mockJob.reqs = nil

	mockJob.resps = append(mockJob.resps[:0], expectedResponse)

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var filter string = "filter-1274492040"
	var request = &talentpb.ListJobsRequest{
		Parent: formattedParent,
		Filter: filter,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.ListJobs(context.Background(), request).Next()

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockJob.reqs[0]; !proto.Equal(want, got) {
		t.Errorf("wrong request %q, want %q", got, want)
	}

	want := (interface{})(expectedResponse.Jobs[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 TestJobServiceListJobsError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockJob.err = gstatus.Error(errCode, "test error")

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var filter string = "filter-1274492040"
	var request = &talentpb.ListJobsRequest{
		Parent: formattedParent,
		Filter: filter,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.ListJobs(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 TestJobServiceBatchDeleteJobs(t *testing.T) {
	var expectedResponse *emptypb.Empty = &emptypb.Empty{}

	mockJob.err = nil
	mockJob.reqs = nil

	mockJob.resps = append(mockJob.resps[:0], expectedResponse)

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var filter string = "filter-1274492040"
	var request = &talentpb.BatchDeleteJobsRequest{
		Parent: formattedParent,
		Filter: filter,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	err = c.BatchDeleteJobs(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockJob.reqs[0]; !proto.Equal(want, got) {
		t.Errorf("wrong request %q, want %q", got, want)
	}

}

func TestJobServiceBatchDeleteJobsError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockJob.err = gstatus.Error(errCode, "test error")

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var filter string = "filter-1274492040"
	var request = &talentpb.BatchDeleteJobsRequest{
		Parent: formattedParent,
		Filter: filter,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	err = c.BatchDeleteJobs(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)
	}
}
func TestJobServiceSearchJobs(t *testing.T) {
	var nextPageToken string = ""
	var estimatedTotalSize int32 = 1882144769
	var totalSize int32 = 705419236
	var broadenedQueryJobsCount int32 = 1432104658
	var matchingJobsElement *talentpb.SearchJobsResponse_MatchingJob = &talentpb.SearchJobsResponse_MatchingJob{}
	var matchingJobs = []*talentpb.SearchJobsResponse_MatchingJob{matchingJobsElement}
	var expectedResponse = &talentpb.SearchJobsResponse{
		NextPageToken:           nextPageToken,
		EstimatedTotalSize:      estimatedTotalSize,
		TotalSize:               totalSize,
		BroadenedQueryJobsCount: broadenedQueryJobsCount,
		MatchingJobs:            matchingJobs,
	}

	mockJob.err = nil
	mockJob.reqs = nil

	mockJob.resps = append(mockJob.resps[:0], expectedResponse)

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var requestMetadata *talentpb.RequestMetadata = &talentpb.RequestMetadata{}
	var request = &talentpb.SearchJobsRequest{
		Parent:          formattedParent,
		RequestMetadata: requestMetadata,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.SearchJobs(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockJob.reqs[0]; !proto.Equal(want, got) {
		t.Errorf("wrong request %q, want %q", got, want)
	}

	want := (interface{})(expectedResponse.MatchingJobs[0])
	got := (interface{})(resp.MatchingJobs[0])
	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 TestJobServiceSearchJobsError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockJob.err = gstatus.Error(errCode, "test error")

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var requestMetadata *talentpb.RequestMetadata = &talentpb.RequestMetadata{}
	var request = &talentpb.SearchJobsRequest{
		Parent:          formattedParent,
		RequestMetadata: requestMetadata,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.SearchJobs(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 TestJobServiceSearchJobsForAlert(t *testing.T) {
	var nextPageToken string = ""
	var estimatedTotalSize int32 = 1882144769
	var totalSize int32 = 705419236
	var broadenedQueryJobsCount int32 = 1432104658
	var matchingJobsElement *talentpb.SearchJobsResponse_MatchingJob = &talentpb.SearchJobsResponse_MatchingJob{}
	var matchingJobs = []*talentpb.SearchJobsResponse_MatchingJob{matchingJobsElement}
	var expectedResponse = &talentpb.SearchJobsResponse{
		NextPageToken:           nextPageToken,
		EstimatedTotalSize:      estimatedTotalSize,
		TotalSize:               totalSize,
		BroadenedQueryJobsCount: broadenedQueryJobsCount,
		MatchingJobs:            matchingJobs,
	}

	mockJob.err = nil
	mockJob.reqs = nil

	mockJob.resps = append(mockJob.resps[:0], expectedResponse)

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var requestMetadata *talentpb.RequestMetadata = &talentpb.RequestMetadata{}
	var request = &talentpb.SearchJobsRequest{
		Parent:          formattedParent,
		RequestMetadata: requestMetadata,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.SearchJobsForAlert(context.Background(), request).Next()

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockJob.reqs[0]; !proto.Equal(want, got) {
		t.Errorf("wrong request %q, want %q", got, want)
	}

	want := (interface{})(expectedResponse.MatchingJobs[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 TestJobServiceSearchJobsForAlertError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockJob.err = gstatus.Error(errCode, "test error")

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var requestMetadata *talentpb.RequestMetadata = &talentpb.RequestMetadata{}
	var request = &talentpb.SearchJobsRequest{
		Parent:          formattedParent,
		RequestMetadata: requestMetadata,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.SearchJobsForAlert(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 TestJobServiceBatchCreateJobs(t *testing.T) {
	var expectedResponse *talentpb.JobOperationResult = &talentpb.JobOperationResult{}

	mockJob.err = nil
	mockJob.reqs = nil

	any, err := ptypes.MarshalAny(expectedResponse)
	if err != nil {
		t.Fatal(err)
	}
	mockJob.resps = append(mockJob.resps[:0], &longrunningpb.Operation{
		Name:   "longrunning-test",
		Done:   true,
		Result: &longrunningpb.Operation_Response{Response: any},
	})

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var jobs []*talentpb.Job = nil
	var request = &talentpb.BatchCreateJobsRequest{
		Parent: formattedParent,
		Jobs:   jobs,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	respLRO, err := c.BatchCreateJobs(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, mockJob.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 TestJobServiceBatchCreateJobsError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockJob.err = nil
	mockJob.resps = append(mockJob.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/tenants/%s", "[PROJECT]", "[TENANT]")
	var jobs []*talentpb.Job = nil
	var request = &talentpb.BatchCreateJobsRequest{
		Parent: formattedParent,
		Jobs:   jobs,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	respLRO, err := c.BatchCreateJobs(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 TestJobServiceBatchUpdateJobs(t *testing.T) {
	var expectedResponse *talentpb.JobOperationResult = &talentpb.JobOperationResult{}

	mockJob.err = nil
	mockJob.reqs = nil

	any, err := ptypes.MarshalAny(expectedResponse)
	if err != nil {
		t.Fatal(err)
	}
	mockJob.resps = append(mockJob.resps[:0], &longrunningpb.Operation{
		Name:   "longrunning-test",
		Done:   true,
		Result: &longrunningpb.Operation_Response{Response: any},
	})

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var jobs []*talentpb.Job = nil
	var request = &talentpb.BatchUpdateJobsRequest{
		Parent: formattedParent,
		Jobs:   jobs,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	respLRO, err := c.BatchUpdateJobs(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, mockJob.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 TestJobServiceBatchUpdateJobsError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockJob.err = nil
	mockJob.resps = append(mockJob.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/tenants/%s", "[PROJECT]", "[TENANT]")
	var jobs []*talentpb.Job = nil
	var request = &talentpb.BatchUpdateJobsRequest{
		Parent: formattedParent,
		Jobs:   jobs,
	}

	c, err := NewJobClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	respLRO, err := c.BatchUpdateJobs(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 TestProfileServiceListProfiles(t *testing.T) {
	var nextPageToken string = ""
	var profilesElement *talentpb.Profile = &talentpb.Profile{}
	var profiles = []*talentpb.Profile{profilesElement}
	var expectedResponse = &talentpb.ListProfilesResponse{
		NextPageToken: nextPageToken,
		Profiles:      profiles,
	}

	mockProfile.err = nil
	mockProfile.reqs = nil

	mockProfile.resps = append(mockProfile.resps[:0], expectedResponse)

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var request = &talentpb.ListProfilesRequest{
		Parent: formattedParent,
	}

	c, err := NewProfileClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.ListProfiles(context.Background(), request).Next()

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockProfile.reqs[0]; !proto.Equal(want, got) {
		t.Errorf("wrong request %q, want %q", got, want)
	}

	want := (interface{})(expectedResponse.Profiles[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 TestProfileServiceListProfilesError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockProfile.err = gstatus.Error(errCode, "test error")

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var request = &talentpb.ListProfilesRequest{
		Parent: formattedParent,
	}

	c, err := NewProfileClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.ListProfiles(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 TestProfileServiceCreateProfile(t *testing.T) {
	var name string = "name3373707"
	var externalId string = "externalId-1153075697"
	var source string = "source-896505829"
	var uri string = "uri116076"
	var groupId string = "groupId506361563"
	var processed bool = true
	var keywordSnippet string = "keywordSnippet1325317319"
	var expectedResponse = &talentpb.Profile{
		Name:           name,
		ExternalId:     externalId,
		Source:         source,
		Uri:            uri,
		GroupId:        groupId,
		Processed:      processed,
		KeywordSnippet: keywordSnippet,
	}

	mockProfile.err = nil
	mockProfile.reqs = nil

	mockProfile.resps = append(mockProfile.resps[:0], expectedResponse)

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var profile *talentpb.Profile = &talentpb.Profile{}
	var request = &talentpb.CreateProfileRequest{
		Parent:  formattedParent,
		Profile: profile,
	}

	c, err := NewProfileClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.CreateProfile(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockProfile.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 TestProfileServiceCreateProfileError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockProfile.err = gstatus.Error(errCode, "test error")

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var profile *talentpb.Profile = &talentpb.Profile{}
	var request = &talentpb.CreateProfileRequest{
		Parent:  formattedParent,
		Profile: profile,
	}

	c, err := NewProfileClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.CreateProfile(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 TestProfileServiceGetProfile(t *testing.T) {
	var name2 string = "name2-1052831874"
	var externalId string = "externalId-1153075697"
	var source string = "source-896505829"
	var uri string = "uri116076"
	var groupId string = "groupId506361563"
	var processed bool = true
	var keywordSnippet string = "keywordSnippet1325317319"
	var expectedResponse = &talentpb.Profile{
		Name:           name2,
		ExternalId:     externalId,
		Source:         source,
		Uri:            uri,
		GroupId:        groupId,
		Processed:      processed,
		KeywordSnippet: keywordSnippet,
	}

	mockProfile.err = nil
	mockProfile.reqs = nil

	mockProfile.resps = append(mockProfile.resps[:0], expectedResponse)

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s/profiles/%s", "[PROJECT]", "[TENANT]", "[PROFILE]")
	var request = &talentpb.GetProfileRequest{
		Name: formattedName,
	}

	c, err := NewProfileClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.GetProfile(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockProfile.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 TestProfileServiceGetProfileError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockProfile.err = gstatus.Error(errCode, "test error")

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s/profiles/%s", "[PROJECT]", "[TENANT]", "[PROFILE]")
	var request = &talentpb.GetProfileRequest{
		Name: formattedName,
	}

	c, err := NewProfileClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.GetProfile(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 TestProfileServiceUpdateProfile(t *testing.T) {
	var name string = "name3373707"
	var externalId string = "externalId-1153075697"
	var source string = "source-896505829"
	var uri string = "uri116076"
	var groupId string = "groupId506361563"
	var processed bool = true
	var keywordSnippet string = "keywordSnippet1325317319"
	var expectedResponse = &talentpb.Profile{
		Name:           name,
		ExternalId:     externalId,
		Source:         source,
		Uri:            uri,
		GroupId:        groupId,
		Processed:      processed,
		KeywordSnippet: keywordSnippet,
	}

	mockProfile.err = nil
	mockProfile.reqs = nil

	mockProfile.resps = append(mockProfile.resps[:0], expectedResponse)

	var profile *talentpb.Profile = &talentpb.Profile{}
	var request = &talentpb.UpdateProfileRequest{
		Profile: profile,
	}

	c, err := NewProfileClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.UpdateProfile(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockProfile.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 TestProfileServiceUpdateProfileError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockProfile.err = gstatus.Error(errCode, "test error")

	var profile *talentpb.Profile = &talentpb.Profile{}
	var request = &talentpb.UpdateProfileRequest{
		Profile: profile,
	}

	c, err := NewProfileClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.UpdateProfile(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 TestProfileServiceDeleteProfile(t *testing.T) {
	var expectedResponse *emptypb.Empty = &emptypb.Empty{}

	mockProfile.err = nil
	mockProfile.reqs = nil

	mockProfile.resps = append(mockProfile.resps[:0], expectedResponse)

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s/profiles/%s", "[PROJECT]", "[TENANT]", "[PROFILE]")
	var request = &talentpb.DeleteProfileRequest{
		Name: formattedName,
	}

	c, err := NewProfileClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	err = c.DeleteProfile(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockProfile.reqs[0]; !proto.Equal(want, got) {
		t.Errorf("wrong request %q, want %q", got, want)
	}

}

func TestProfileServiceDeleteProfileError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockProfile.err = gstatus.Error(errCode, "test error")

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s/profiles/%s", "[PROJECT]", "[TENANT]", "[PROFILE]")
	var request = &talentpb.DeleteProfileRequest{
		Name: formattedName,
	}

	c, err := NewProfileClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	err = c.DeleteProfile(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)
	}
}
func TestProfileServiceSearchProfiles(t *testing.T) {
	var estimatedTotalSize int64 = 1882144769
	var nextPageToken string = ""
	var resultSetId string = "resultSetId-770306950"
	var summarizedProfilesElement *talentpb.SummarizedProfile = &talentpb.SummarizedProfile{}
	var summarizedProfiles = []*talentpb.SummarizedProfile{summarizedProfilesElement}
	var expectedResponse = &talentpb.SearchProfilesResponse{
		EstimatedTotalSize: estimatedTotalSize,
		NextPageToken:      nextPageToken,
		ResultSetId:        resultSetId,
		SummarizedProfiles: summarizedProfiles,
	}

	mockProfile.err = nil
	mockProfile.reqs = nil

	mockProfile.resps = append(mockProfile.resps[:0], expectedResponse)

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var requestMetadata *talentpb.RequestMetadata = &talentpb.RequestMetadata{}
	var request = &talentpb.SearchProfilesRequest{
		Parent:          formattedParent,
		RequestMetadata: requestMetadata,
	}

	c, err := NewProfileClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.SearchProfiles(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockProfile.reqs[0]; !proto.Equal(want, got) {
		t.Errorf("wrong request %q, want %q", got, want)
	}

	want := (interface{})(expectedResponse.SummarizedProfiles[0])
	got := (interface{})(resp.SummarizedProfiles[0])
	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 TestProfileServiceSearchProfilesError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockProfile.err = gstatus.Error(errCode, "test error")

	var formattedParent string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var requestMetadata *talentpb.RequestMetadata = &talentpb.RequestMetadata{}
	var request = &talentpb.SearchProfilesRequest{
		Parent:          formattedParent,
		RequestMetadata: requestMetadata,
	}

	c, err := NewProfileClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.SearchProfiles(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 TestTenantServiceCreateTenant(t *testing.T) {
	var name string = "name3373707"
	var externalId string = "externalId-1153075697"
	var expectedResponse = &talentpb.Tenant{
		Name:       name,
		ExternalId: externalId,
	}

	mockTenant.err = nil
	mockTenant.reqs = nil

	mockTenant.resps = append(mockTenant.resps[:0], expectedResponse)

	var formattedParent string = fmt.Sprintf("projects/%s", "[PROJECT]")
	var tenant *talentpb.Tenant = &talentpb.Tenant{}
	var request = &talentpb.CreateTenantRequest{
		Parent: formattedParent,
		Tenant: tenant,
	}

	c, err := NewTenantClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.CreateTenant(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockTenant.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 TestTenantServiceCreateTenantError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockTenant.err = gstatus.Error(errCode, "test error")

	var formattedParent string = fmt.Sprintf("projects/%s", "[PROJECT]")
	var tenant *talentpb.Tenant = &talentpb.Tenant{}
	var request = &talentpb.CreateTenantRequest{
		Parent: formattedParent,
		Tenant: tenant,
	}

	c, err := NewTenantClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.CreateTenant(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 TestTenantServiceGetTenant(t *testing.T) {
	var name2 string = "name2-1052831874"
	var externalId string = "externalId-1153075697"
	var expectedResponse = &talentpb.Tenant{
		Name:       name2,
		ExternalId: externalId,
	}

	mockTenant.err = nil
	mockTenant.reqs = nil

	mockTenant.resps = append(mockTenant.resps[:0], expectedResponse)

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var request = &talentpb.GetTenantRequest{
		Name: formattedName,
	}

	c, err := NewTenantClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.GetTenant(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockTenant.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 TestTenantServiceGetTenantError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockTenant.err = gstatus.Error(errCode, "test error")

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var request = &talentpb.GetTenantRequest{
		Name: formattedName,
	}

	c, err := NewTenantClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.GetTenant(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 TestTenantServiceUpdateTenant(t *testing.T) {
	var name string = "name3373707"
	var externalId string = "externalId-1153075697"
	var expectedResponse = &talentpb.Tenant{
		Name:       name,
		ExternalId: externalId,
	}

	mockTenant.err = nil
	mockTenant.reqs = nil

	mockTenant.resps = append(mockTenant.resps[:0], expectedResponse)

	var tenant *talentpb.Tenant = &talentpb.Tenant{}
	var request = &talentpb.UpdateTenantRequest{
		Tenant: tenant,
	}

	c, err := NewTenantClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.UpdateTenant(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockTenant.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 TestTenantServiceUpdateTenantError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockTenant.err = gstatus.Error(errCode, "test error")

	var tenant *talentpb.Tenant = &talentpb.Tenant{}
	var request = &talentpb.UpdateTenantRequest{
		Tenant: tenant,
	}

	c, err := NewTenantClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.UpdateTenant(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 TestTenantServiceDeleteTenant(t *testing.T) {
	var expectedResponse *emptypb.Empty = &emptypb.Empty{}

	mockTenant.err = nil
	mockTenant.reqs = nil

	mockTenant.resps = append(mockTenant.resps[:0], expectedResponse)

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var request = &talentpb.DeleteTenantRequest{
		Name: formattedName,
	}

	c, err := NewTenantClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	err = c.DeleteTenant(context.Background(), request)

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockTenant.reqs[0]; !proto.Equal(want, got) {
		t.Errorf("wrong request %q, want %q", got, want)
	}

}

func TestTenantServiceDeleteTenantError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockTenant.err = gstatus.Error(errCode, "test error")

	var formattedName string = fmt.Sprintf("projects/%s/tenants/%s", "[PROJECT]", "[TENANT]")
	var request = &talentpb.DeleteTenantRequest{
		Name: formattedName,
	}

	c, err := NewTenantClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	err = c.DeleteTenant(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)
	}
}
func TestTenantServiceListTenants(t *testing.T) {
	var nextPageToken string = ""
	var tenantsElement *talentpb.Tenant = &talentpb.Tenant{}
	var tenants = []*talentpb.Tenant{tenantsElement}
	var expectedResponse = &talentpb.ListTenantsResponse{
		NextPageToken: nextPageToken,
		Tenants:       tenants,
	}

	mockTenant.err = nil
	mockTenant.reqs = nil

	mockTenant.resps = append(mockTenant.resps[:0], expectedResponse)

	var formattedParent string = fmt.Sprintf("projects/%s", "[PROJECT]")
	var request = &talentpb.ListTenantsRequest{
		Parent: formattedParent,
	}

	c, err := NewTenantClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.ListTenants(context.Background(), request).Next()

	if err != nil {
		t.Fatal(err)
	}

	if want, got := request, mockTenant.reqs[0]; !proto.Equal(want, got) {
		t.Errorf("wrong request %q, want %q", got, want)
	}

	want := (interface{})(expectedResponse.Tenants[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 TestTenantServiceListTenantsError(t *testing.T) {
	errCode := codes.PermissionDenied
	mockTenant.err = gstatus.Error(errCode, "test error")

	var formattedParent string = fmt.Sprintf("projects/%s", "[PROJECT]")
	var request = &talentpb.ListTenantsRequest{
		Parent: formattedParent,
	}

	c, err := NewTenantClient(context.Background(), clientOpt)
	if err != nil {
		t.Fatal(err)
	}

	resp, err := c.ListTenants(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
}
