//
// Licensed to the Apache Software Foundation (ASF) under one
// or more contributor license agreements.  See the NOTICE file
// distributed with this work for additional information
// regarding copyright ownership.  The ASF licenses this file
// to you 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
//
//   http://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 MockGen. DO NOT EDIT.
// Source: ./cloudstack/ObjectStoreService.go
//
// Generated by this command:
//
//	mockgen -destination=./cloudstack/ObjectStoreService_mock.go -package=cloudstack -copyright_file=header.txt -source=./cloudstack/ObjectStoreService.go
//

// Package cloudstack is a generated GoMock package.
package cloudstack

import (
	reflect "reflect"

	gomock "go.uber.org/mock/gomock"
)

// MockObjectStoreServiceIface is a mock of ObjectStoreServiceIface interface.
type MockObjectStoreServiceIface struct {
	ctrl     *gomock.Controller
	recorder *MockObjectStoreServiceIfaceMockRecorder
	isgomock struct{}
}

// MockObjectStoreServiceIfaceMockRecorder is the mock recorder for MockObjectStoreServiceIface.
type MockObjectStoreServiceIfaceMockRecorder struct {
	mock *MockObjectStoreServiceIface
}

// NewMockObjectStoreServiceIface creates a new mock instance.
func NewMockObjectStoreServiceIface(ctrl *gomock.Controller) *MockObjectStoreServiceIface {
	mock := &MockObjectStoreServiceIface{ctrl: ctrl}
	mock.recorder = &MockObjectStoreServiceIfaceMockRecorder{mock}
	return mock
}

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

// CreateBucket mocks base method.
func (m *MockObjectStoreServiceIface) CreateBucket(p *CreateBucketParams) (*CreateBucketResponse, error) {
	m.ctrl.T.Helper()
	ret := m.ctrl.Call(m, "CreateBucket", p)
	ret0, _ := ret[0].(*CreateBucketResponse)
	ret1, _ := ret[1].(error)
	return ret0, ret1
}

// CreateBucket indicates an expected call of CreateBucket.
func (mr *MockObjectStoreServiceIfaceMockRecorder) CreateBucket(p any) *gomock.Call {
	mr.mock.ctrl.T.Helper()
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateBucket", reflect.TypeOf((*MockObjectStoreServiceIface)(nil).CreateBucket), p)
}

// DeleteBucket mocks base method.
func (m *MockObjectStoreServiceIface) DeleteBucket(p *DeleteBucketParams) (*DeleteBucketResponse, error) {
	m.ctrl.T.Helper()
	ret := m.ctrl.Call(m, "DeleteBucket", p)
	ret0, _ := ret[0].(*DeleteBucketResponse)
	ret1, _ := ret[1].(error)
	return ret0, ret1
}

// DeleteBucket indicates an expected call of DeleteBucket.
func (mr *MockObjectStoreServiceIfaceMockRecorder) DeleteBucket(p any) *gomock.Call {
	mr.mock.ctrl.T.Helper()
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "DeleteBucket", reflect.TypeOf((*MockObjectStoreServiceIface)(nil).DeleteBucket), p)
}

// GetBucketByID mocks base method.
func (m *MockObjectStoreServiceIface) GetBucketByID(id string, opts ...OptionFunc) (*Bucket, int, error) {
	m.ctrl.T.Helper()
	varargs := []any{id}
	for _, a := range opts {
		varargs = append(varargs, a)
	}
	ret := m.ctrl.Call(m, "GetBucketByID", varargs...)
	ret0, _ := ret[0].(*Bucket)
	ret1, _ := ret[1].(int)
	ret2, _ := ret[2].(error)
	return ret0, ret1, ret2
}

// GetBucketByID indicates an expected call of GetBucketByID.
func (mr *MockObjectStoreServiceIfaceMockRecorder) GetBucketByID(id any, opts ...any) *gomock.Call {
	mr.mock.ctrl.T.Helper()
	varargs := append([]any{id}, opts...)
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetBucketByID", reflect.TypeOf((*MockObjectStoreServiceIface)(nil).GetBucketByID), varargs...)
}

// GetBucketByName mocks base method.
func (m *MockObjectStoreServiceIface) GetBucketByName(name string, opts ...OptionFunc) (*Bucket, int, error) {
	m.ctrl.T.Helper()
	varargs := []any{name}
	for _, a := range opts {
		varargs = append(varargs, a)
	}
	ret := m.ctrl.Call(m, "GetBucketByName", varargs...)
	ret0, _ := ret[0].(*Bucket)
	ret1, _ := ret[1].(int)
	ret2, _ := ret[2].(error)
	return ret0, ret1, ret2
}

// GetBucketByName indicates an expected call of GetBucketByName.
func (mr *MockObjectStoreServiceIfaceMockRecorder) GetBucketByName(name any, opts ...any) *gomock.Call {
	mr.mock.ctrl.T.Helper()
	varargs := append([]any{name}, opts...)
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetBucketByName", reflect.TypeOf((*MockObjectStoreServiceIface)(nil).GetBucketByName), varargs...)
}

// GetBucketID mocks base method.
func (m *MockObjectStoreServiceIface) GetBucketID(name string, opts ...OptionFunc) (string, int, error) {
	m.ctrl.T.Helper()
	varargs := []any{name}
	for _, a := range opts {
		varargs = append(varargs, a)
	}
	ret := m.ctrl.Call(m, "GetBucketID", varargs...)
	ret0, _ := ret[0].(string)
	ret1, _ := ret[1].(int)
	ret2, _ := ret[2].(error)
	return ret0, ret1, ret2
}

// GetBucketID indicates an expected call of GetBucketID.
func (mr *MockObjectStoreServiceIfaceMockRecorder) GetBucketID(name any, opts ...any) *gomock.Call {
	mr.mock.ctrl.T.Helper()
	varargs := append([]any{name}, opts...)
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetBucketID", reflect.TypeOf((*MockObjectStoreServiceIface)(nil).GetBucketID), varargs...)
}

// ListBuckets mocks base method.
func (m *MockObjectStoreServiceIface) ListBuckets(p *ListBucketsParams) (*ListBucketsResponse, error) {
	m.ctrl.T.Helper()
	ret := m.ctrl.Call(m, "ListBuckets", p)
	ret0, _ := ret[0].(*ListBucketsResponse)
	ret1, _ := ret[1].(error)
	return ret0, ret1
}

// ListBuckets indicates an expected call of ListBuckets.
func (mr *MockObjectStoreServiceIfaceMockRecorder) ListBuckets(p any) *gomock.Call {
	mr.mock.ctrl.T.Helper()
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "ListBuckets", reflect.TypeOf((*MockObjectStoreServiceIface)(nil).ListBuckets), p)
}

// NewCreateBucketParams mocks base method.
func (m *MockObjectStoreServiceIface) NewCreateBucketParams(name, objectstorageid string) *CreateBucketParams {
	m.ctrl.T.Helper()
	ret := m.ctrl.Call(m, "NewCreateBucketParams", name, objectstorageid)
	ret0, _ := ret[0].(*CreateBucketParams)
	return ret0
}

// NewCreateBucketParams indicates an expected call of NewCreateBucketParams.
func (mr *MockObjectStoreServiceIfaceMockRecorder) NewCreateBucketParams(name, objectstorageid any) *gomock.Call {
	mr.mock.ctrl.T.Helper()
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NewCreateBucketParams", reflect.TypeOf((*MockObjectStoreServiceIface)(nil).NewCreateBucketParams), name, objectstorageid)
}

// NewDeleteBucketParams mocks base method.
func (m *MockObjectStoreServiceIface) NewDeleteBucketParams(id string) *DeleteBucketParams {
	m.ctrl.T.Helper()
	ret := m.ctrl.Call(m, "NewDeleteBucketParams", id)
	ret0, _ := ret[0].(*DeleteBucketParams)
	return ret0
}

// NewDeleteBucketParams indicates an expected call of NewDeleteBucketParams.
func (mr *MockObjectStoreServiceIfaceMockRecorder) NewDeleteBucketParams(id any) *gomock.Call {
	mr.mock.ctrl.T.Helper()
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NewDeleteBucketParams", reflect.TypeOf((*MockObjectStoreServiceIface)(nil).NewDeleteBucketParams), id)
}

// NewListBucketsParams mocks base method.
func (m *MockObjectStoreServiceIface) NewListBucketsParams() *ListBucketsParams {
	m.ctrl.T.Helper()
	ret := m.ctrl.Call(m, "NewListBucketsParams")
	ret0, _ := ret[0].(*ListBucketsParams)
	return ret0
}

// NewListBucketsParams indicates an expected call of NewListBucketsParams.
func (mr *MockObjectStoreServiceIfaceMockRecorder) NewListBucketsParams() *gomock.Call {
	mr.mock.ctrl.T.Helper()
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NewListBucketsParams", reflect.TypeOf((*MockObjectStoreServiceIface)(nil).NewListBucketsParams))
}

// NewUpdateBucketParams mocks base method.
func (m *MockObjectStoreServiceIface) NewUpdateBucketParams(id string) *UpdateBucketParams {
	m.ctrl.T.Helper()
	ret := m.ctrl.Call(m, "NewUpdateBucketParams", id)
	ret0, _ := ret[0].(*UpdateBucketParams)
	return ret0
}

// NewUpdateBucketParams indicates an expected call of NewUpdateBucketParams.
func (mr *MockObjectStoreServiceIfaceMockRecorder) NewUpdateBucketParams(id any) *gomock.Call {
	mr.mock.ctrl.T.Helper()
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NewUpdateBucketParams", reflect.TypeOf((*MockObjectStoreServiceIface)(nil).NewUpdateBucketParams), id)
}

// UpdateBucket mocks base method.
func (m *MockObjectStoreServiceIface) UpdateBucket(p *UpdateBucketParams) (*UpdateBucketResponse, error) {
	m.ctrl.T.Helper()
	ret := m.ctrl.Call(m, "UpdateBucket", p)
	ret0, _ := ret[0].(*UpdateBucketResponse)
	ret1, _ := ret[1].(error)
	return ret0, ret1
}

// UpdateBucket indicates an expected call of UpdateBucket.
func (mr *MockObjectStoreServiceIfaceMockRecorder) UpdateBucket(p any) *gomock.Call {
	mr.mock.ctrl.T.Helper()
	return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateBucket", reflect.TypeOf((*MockObjectStoreServiceIface)(nil).UpdateBucket), p)
}
