// Copyright 2018 The Fuchsia Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

// Code generated by MockGen. DO NOT EDIT.
// Source: service.go

// Package service is a generated GoMock package.
package resultstore

import (
	context "context"
	reflect "reflect"

	gomock "github.com/golang/mock/gomock"
)

// MockService is a mock of Service interface
type MockService struct {
	ctrl     *gomock.Controller
	recorder *MockServiceMockRecorder
}

// MockServiceMockRecorder is the mock recorder for MockService
type MockServiceMockRecorder struct {
	mock *MockService
}

// NewMockService creates a new mock instance
func NewMockService(ctrl *gomock.Controller) *MockService {
	mock := &MockService{ctrl: ctrl}
	mock.recorder = &MockServiceMockRecorder{mock}
	return mock
}

// EXPECT returns an object that allows the caller to indicate expected use
func (m *MockService) EXPECT() *MockServiceMockRecorder {
	return m.recorder
}

// CreateInvocation mocks base method
func (m *MockService) CreateInvocation(arg0 context.Context, arg1 *Invocation) (*Invocation, error) {
	ret := m.ctrl.Call(m, "CreateInvocation", arg0, arg1)
	ret0, _ := ret[0].(*Invocation)
	ret1, _ := ret[1].(error)
	return ret0, ret1
}

// CreateInvocation indicates an expected call of CreateInvocation
func (mr *MockServiceMockRecorder) CreateInvocation(arg0, arg1 interface{}) *gomock.Call {
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateInvocation", reflect.TypeOf((*MockService)(nil).CreateInvocation), arg0, arg1)
}

// CreateConfiguration mocks base method
func (m *MockService) CreateConfiguration(arg0 context.Context, arg1 *Configuration, arg2 string) (*Configuration, error) {
	ret := m.ctrl.Call(m, "CreateConfiguration", arg0, arg1, arg2)
	ret0, _ := ret[0].(*Configuration)
	ret1, _ := ret[1].(error)
	return ret0, ret1
}

// CreateConfiguration indicates an expected call of CreateConfiguration
func (mr *MockServiceMockRecorder) CreateConfiguration(arg0, arg1, arg2 interface{}) *gomock.Call {
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateConfiguration", reflect.TypeOf((*MockService)(nil).CreateConfiguration), arg0, arg1, arg2)
}

// CreateTarget mocks base method
func (m *MockService) CreateTarget(arg0 context.Context, arg1 *Target, arg2 string) (*Target, error) {
	ret := m.ctrl.Call(m, "CreateTarget", arg0, arg1, arg2)
	ret0, _ := ret[0].(*Target)
	ret1, _ := ret[1].(error)
	return ret0, ret1
}

// CreateTarget indicates an expected call of CreateTarget
func (mr *MockServiceMockRecorder) CreateTarget(arg0, arg1, arg2 interface{}) *gomock.Call {
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateTarget", reflect.TypeOf((*MockService)(nil).CreateTarget), arg0, arg1, arg2)
}

// CreateConfiguredTarget mocks base method
func (m *MockService) CreateConfiguredTarget(arg0 context.Context, arg1 *ConfiguredTarget, arg2 string) (*ConfiguredTarget, error) {
	ret := m.ctrl.Call(m, "CreateConfiguredTarget", arg0, arg1, arg2)
	ret0, _ := ret[0].(*ConfiguredTarget)
	ret1, _ := ret[1].(error)
	return ret0, ret1
}

// CreateConfiguredTarget indicates an expected call of CreateConfiguredTarget
func (mr *MockServiceMockRecorder) CreateConfiguredTarget(arg0, arg1, arg2 interface{}) *gomock.Call {
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateConfiguredTarget", reflect.TypeOf((*MockService)(nil).CreateConfiguredTarget), arg0, arg1, arg2)
}

// CreateTestAction mocks base method
func (m *MockService) CreateTestAction(arg0 context.Context, arg1 *TestAction, arg2 string) (*TestAction, error) {
	ret := m.ctrl.Call(m, "CreateTestAction", arg0, arg1, arg2)
	ret0, _ := ret[0].(*TestAction)
	ret1, _ := ret[1].(error)
	return ret0, ret1
}

// CreateTestAction indicates an expected call of CreateTestAction
func (mr *MockServiceMockRecorder) CreateTestAction(arg0, arg1, arg2 interface{}) *gomock.Call {
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateTestAction", reflect.TypeOf((*MockService)(nil).CreateTestAction), arg0, arg1, arg2)
}

// UpdateTestAction mocks base method
func (m *MockService) UpdateTestAction(arg0 context.Context, arg1 *TestAction) (*TestAction, error) {
	ret := m.ctrl.Call(m, "UpdateTestAction", arg0, arg1)
	ret0, _ := ret[0].(*TestAction)
	ret1, _ := ret[1].(error)
	return ret0, ret1
}

// UpdateTestAction indicates an expected call of UpdateTestAction
func (mr *MockServiceMockRecorder) UpdateTestAction(arg0, arg1 interface{}) *gomock.Call {
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateTestAction", reflect.TypeOf((*MockService)(nil).UpdateTestAction), arg0, arg1)
}

// UpdateConfiguredTarget mocks base method
func (m *MockService) UpdateConfiguredTarget(arg0 context.Context, arg1 *ConfiguredTarget) (*ConfiguredTarget, error) {
	ret := m.ctrl.Call(m, "UpdateConfiguredTarget", arg0, arg1)
	ret0, _ := ret[0].(*ConfiguredTarget)
	ret1, _ := ret[1].(error)
	return ret0, ret1
}

// UpdateConfiguredTarget indicates an expected call of UpdateConfiguredTarget
func (mr *MockServiceMockRecorder) UpdateConfiguredTarget(arg0, arg1 interface{}) *gomock.Call {
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateConfiguredTarget", reflect.TypeOf((*MockService)(nil).UpdateConfiguredTarget), arg0, arg1)
}

// UpdateTarget mocks base method
func (m *MockService) UpdateTarget(arg0 context.Context, arg1 *Target) (*Target, error) {
	ret := m.ctrl.Call(m, "UpdateTarget", arg0, arg1)
	ret0, _ := ret[0].(*Target)
	ret1, _ := ret[1].(error)
	return ret0, ret1
}

// UpdateTarget indicates an expected call of UpdateTarget
func (mr *MockServiceMockRecorder) UpdateTarget(arg0, arg1 interface{}) *gomock.Call {
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateTarget", reflect.TypeOf((*MockService)(nil).UpdateTarget), arg0, arg1)
}

// UpdateInvocation mocks base method
func (m *MockService) UpdateInvocation(arg0 context.Context, arg1 *Invocation) (*Invocation, error) {
	ret := m.ctrl.Call(m, "UpdateInvocation", arg0, arg1)
	ret0, _ := ret[0].(*Invocation)
	ret1, _ := ret[1].(error)
	return ret0, ret1
}

// UpdateInvocation indicates an expected call of UpdateInvocation
func (mr *MockServiceMockRecorder) UpdateInvocation(arg0, arg1 interface{}) *gomock.Call {
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateInvocation", reflect.TypeOf((*MockService)(nil).UpdateInvocation), arg0, arg1)
}

// FinishConfiguredTarget mocks base method
func (m *MockService) FinishConfiguredTarget(arg0 context.Context, arg1 string) error {
	ret := m.ctrl.Call(m, "FinishConfiguredTarget", arg0, arg1)
	ret0, _ := ret[0].(error)
	return ret0
}

// FinishConfiguredTarget indicates an expected call of FinishConfiguredTarget
func (mr *MockServiceMockRecorder) FinishConfiguredTarget(arg0, arg1 interface{}) *gomock.Call {
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "FinishConfiguredTarget", reflect.TypeOf((*MockService)(nil).FinishConfiguredTarget), arg0, arg1)
}

// FinishTarget mocks base method
func (m *MockService) FinishTarget(arg0 context.Context, arg1 string) error {
	ret := m.ctrl.Call(m, "FinishTarget", arg0, arg1)
	ret0, _ := ret[0].(error)
	return ret0
}

// FinishTarget indicates an expected call of FinishTarget
func (mr *MockServiceMockRecorder) FinishTarget(arg0, arg1 interface{}) *gomock.Call {
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "FinishTarget", reflect.TypeOf((*MockService)(nil).FinishTarget), arg0, arg1)
}

// FinishInvocation mocks base method
func (m *MockService) FinishInvocation(arg0 context.Context, arg1 string) error {
	ret := m.ctrl.Call(m, "FinishInvocation", arg0, arg1)
	ret0, _ := ret[0].(error)
	return ret0
}

// FinishInvocation indicates an expected call of FinishInvocation
func (mr *MockServiceMockRecorder) FinishInvocation(arg0, arg1 interface{}) *gomock.Call {
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "FinishInvocation", reflect.TypeOf((*MockService)(nil).FinishInvocation), arg0, arg1)
}
