diff --git a/cloudstack/HostService.go b/cloudstack/HostService.go index 973ce28..2ace49b 100644 --- a/cloudstack/HostService.go +++ b/cloudstack/HostService.go @@ -96,6 +96,8 @@ type HostServiceIface interface { NewListHostHAResourcesParams() *ListHostHAResourcesParams DeclareHostAsDegraded(p *DeclareHostAsDegradedParams) (*DeclareHostAsDegradedResponse, error) NewDeclareHostAsDegradedParams(id string) *DeclareHostAsDegradedParams + UpdateSecondaryStorageSelector(p *UpdateSecondaryStorageSelectorParams) (*UpdateSecondaryStorageSelectorResponse, error) + NewUpdateSecondaryStorageSelectorParams(heuristicrule string, id string) *UpdateSecondaryStorageSelectorParams } type AddBaremetalHostParams struct { @@ -5535,11 +5537,14 @@ func (s *HostService) CreateSecondaryStorageSelector(p *CreateSecondaryStorageSe if err != nil { return nil, err } - - var r CreateSecondaryStorageSelectorResponse - if err := json.Unmarshal(resp, &r); err != nil { + fmt.Println(string(resp)) + var nested struct { + Response CreateSecondaryStorageSelectorResponse `json:"heuristics"` + } + if err := json.Unmarshal(resp, &nested); err != nil { return nil, err } + r := nested.Response return &r, nil } @@ -5865,3 +5870,104 @@ type DeclareHostAsDegradedResponseGpugroupVgpu struct { Vgputype string `json:"vgputype"` Videoram int64 `json:"videoram"` } + +type UpdateSecondaryStorageSelectorParams struct { + p map[string]interface{} +} + +func (p *UpdateSecondaryStorageSelectorParams) toURLValues() url.Values { + u := url.Values{} + if p.p == nil { + return u + } + if v, found := p.p["heuristicrule"]; found { + u.Set("heuristicrule", v.(string)) + } + if v, found := p.p["id"]; found { + u.Set("id", v.(string)) + } + return u +} + +func (p *UpdateSecondaryStorageSelectorParams) SetHeuristicrule(v string) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + p.p["heuristicrule"] = v +} + +func (p *UpdateSecondaryStorageSelectorParams) ResetHeuristicrule() { + if p.p != nil && p.p["heuristicrule"] != nil { + delete(p.p, "heuristicrule") + } +} + +func (p *UpdateSecondaryStorageSelectorParams) GetHeuristicrule() (string, bool) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + value, ok := p.p["heuristicrule"].(string) + return value, ok +} + +func (p *UpdateSecondaryStorageSelectorParams) SetId(v string) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + p.p["id"] = v +} + +func (p *UpdateSecondaryStorageSelectorParams) ResetId() { + if p.p != nil && p.p["id"] != nil { + delete(p.p, "id") + } +} + +func (p *UpdateSecondaryStorageSelectorParams) GetId() (string, bool) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + value, ok := p.p["id"].(string) + return value, ok +} + +// You should always use this function to get a new UpdateSecondaryStorageSelectorParams instance, +// as then you are sure you have configured all required params +func (s *HostService) NewUpdateSecondaryStorageSelectorParams(heuristicrule string, id string) *UpdateSecondaryStorageSelectorParams { + p := &UpdateSecondaryStorageSelectorParams{} + p.p = make(map[string]interface{}) + p.p["heuristicrule"] = heuristicrule + p.p["id"] = id + return p +} + +// Updates an existing secondary storage selector. +func (s *HostService) UpdateSecondaryStorageSelector(p *UpdateSecondaryStorageSelectorParams) (*UpdateSecondaryStorageSelectorResponse, error) { + resp, err := s.cs.newRequest("updateSecondaryStorageSelector", p.toURLValues()) + if err != nil { + return nil, err + } + + var nested struct { + Response UpdateSecondaryStorageSelectorResponse `json:"heuristics"` + } + if err := json.Unmarshal(resp, &nested); err != nil { + return nil, err + } + r := nested.Response + + return &r, nil +} + +type UpdateSecondaryStorageSelectorResponse struct { + Created string `json:"created"` + Description string `json:"description"` + Heuristicrule string `json:"heuristicrule"` + Id string `json:"id"` + JobID string `json:"jobid"` + Jobstatus int `json:"jobstatus"` + Name string `json:"name"` + Removed string `json:"removed"` + Type string `json:"type"` + Zoneid string `json:"zoneid"` +} diff --git a/cloudstack/HostService_mock.go b/cloudstack/HostService_mock.go index 6e5c796..badb90e 100644 --- a/cloudstack/HostService_mock.go +++ b/cloudstack/HostService_mock.go @@ -985,6 +985,20 @@ func (mr *MockHostServiceIfaceMockRecorder) NewUpdateHostPasswordParams(password return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NewUpdateHostPasswordParams", reflect.TypeOf((*MockHostServiceIface)(nil).NewUpdateHostPasswordParams), password, username) } +// NewUpdateSecondaryStorageSelectorParams mocks base method. +func (m *MockHostServiceIface) NewUpdateSecondaryStorageSelectorParams(heuristicrule, id string) *UpdateSecondaryStorageSelectorParams { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "NewUpdateSecondaryStorageSelectorParams", heuristicrule, id) + ret0, _ := ret[0].(*UpdateSecondaryStorageSelectorParams) + return ret0 +} + +// NewUpdateSecondaryStorageSelectorParams indicates an expected call of NewUpdateSecondaryStorageSelectorParams. +func (mr *MockHostServiceIfaceMockRecorder) NewUpdateSecondaryStorageSelectorParams(heuristicrule, id interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NewUpdateSecondaryStorageSelectorParams", reflect.TypeOf((*MockHostServiceIface)(nil).NewUpdateSecondaryStorageSelectorParams), heuristicrule, id) +} + // PrepareHostForMaintenance mocks base method. func (m *MockHostServiceIface) PrepareHostForMaintenance(p *PrepareHostForMaintenanceParams) (*PrepareHostForMaintenanceResponse, error) { m.ctrl.T.Helper() @@ -1089,3 +1103,18 @@ func (mr *MockHostServiceIfaceMockRecorder) UpdateHostPassword(p interface{}) *g mr.mock.ctrl.T.Helper() return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateHostPassword", reflect.TypeOf((*MockHostServiceIface)(nil).UpdateHostPassword), p) } + +// UpdateSecondaryStorageSelector mocks base method. +func (m *MockHostServiceIface) UpdateSecondaryStorageSelector(p *UpdateSecondaryStorageSelectorParams) (*UpdateSecondaryStorageSelectorResponse, error) { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "UpdateSecondaryStorageSelector", p) + ret0, _ := ret[0].(*UpdateSecondaryStorageSelectorResponse) + ret1, _ := ret[1].(error) + return ret0, ret1 +} + +// UpdateSecondaryStorageSelector indicates an expected call of UpdateSecondaryStorageSelector. +func (mr *MockHostServiceIfaceMockRecorder) UpdateSecondaryStorageSelector(p interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateSecondaryStorageSelector", reflect.TypeOf((*MockHostServiceIface)(nil).UpdateSecondaryStorageSelector), p) +} diff --git a/cloudstack/ManagementService.go b/cloudstack/ManagementService.go new file mode 100644 index 0000000..8398c8d --- /dev/null +++ b/cloudstack/ManagementService.go @@ -0,0 +1,298 @@ +// +// 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. +// + +package cloudstack + +import ( + "encoding/json" + "fmt" + "net/url" + "strconv" + "strings" +) + +type ManagementServiceIface interface { + ListManagementServers(p *ListManagementServersParams) (*ListManagementServersResponse, error) + NewListManagementServersParams() *ListManagementServersParams + GetManagementServerID(name string, opts ...OptionFunc) (string, int, error) + GetManagementServerByName(name string, opts ...OptionFunc) (*ManagementServer, int, error) + GetManagementServerByID(id string, opts ...OptionFunc) (*ManagementServer, int, error) +} + +type ListManagementServersParams struct { + p map[string]interface{} +} + +func (p *ListManagementServersParams) toURLValues() url.Values { + u := url.Values{} + if p.p == nil { + return u + } + if v, found := p.p["id"]; found { + u.Set("id", v.(string)) + } + if v, found := p.p["keyword"]; found { + u.Set("keyword", v.(string)) + } + if v, found := p.p["name"]; found { + u.Set("name", v.(string)) + } + if v, found := p.p["page"]; found { + vv := strconv.Itoa(v.(int)) + u.Set("page", vv) + } + if v, found := p.p["pagesize"]; found { + vv := strconv.Itoa(v.(int)) + u.Set("pagesize", vv) + } + return u +} + +func (p *ListManagementServersParams) SetId(v string) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + p.p["id"] = v +} + +func (p *ListManagementServersParams) ResetId() { + if p.p != nil && p.p["id"] != nil { + delete(p.p, "id") + } +} + +func (p *ListManagementServersParams) GetId() (string, bool) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + value, ok := p.p["id"].(string) + return value, ok +} + +func (p *ListManagementServersParams) SetKeyword(v string) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + p.p["keyword"] = v +} + +func (p *ListManagementServersParams) ResetKeyword() { + if p.p != nil && p.p["keyword"] != nil { + delete(p.p, "keyword") + } +} + +func (p *ListManagementServersParams) GetKeyword() (string, bool) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + value, ok := p.p["keyword"].(string) + return value, ok +} + +func (p *ListManagementServersParams) SetName(v string) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + p.p["name"] = v +} + +func (p *ListManagementServersParams) ResetName() { + if p.p != nil && p.p["name"] != nil { + delete(p.p, "name") + } +} + +func (p *ListManagementServersParams) GetName() (string, bool) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + value, ok := p.p["name"].(string) + return value, ok +} + +func (p *ListManagementServersParams) SetPage(v int) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + p.p["page"] = v +} + +func (p *ListManagementServersParams) ResetPage() { + if p.p != nil && p.p["page"] != nil { + delete(p.p, "page") + } +} + +func (p *ListManagementServersParams) GetPage() (int, bool) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + value, ok := p.p["page"].(int) + return value, ok +} + +func (p *ListManagementServersParams) SetPagesize(v int) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + p.p["pagesize"] = v +} + +func (p *ListManagementServersParams) ResetPagesize() { + if p.p != nil && p.p["pagesize"] != nil { + delete(p.p, "pagesize") + } +} + +func (p *ListManagementServersParams) GetPagesize() (int, bool) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + value, ok := p.p["pagesize"].(int) + return value, ok +} + +// You should always use this function to get a new ListManagementServersParams instance, +// as then you are sure you have configured all required params +func (s *ManagementService) NewListManagementServersParams() *ListManagementServersParams { + p := &ListManagementServersParams{} + p.p = make(map[string]interface{}) + return p +} + +// This is a courtesy helper function, which in some cases may not work as expected! +func (s *ManagementService) GetManagementServerID(name string, opts ...OptionFunc) (string, int, error) { + p := &ListManagementServersParams{} + p.p = make(map[string]interface{}) + + p.p["name"] = name + + for _, fn := range append(s.cs.options, opts...) { + if err := fn(s.cs, p); err != nil { + return "", -1, err + } + } + + l, err := s.ListManagementServers(p) + if err != nil { + return "", -1, err + } + + if l.Count == 0 { + return "", l.Count, fmt.Errorf("No match found for %s: %+v", name, l) + } + + if l.Count == 1 { + return l.ManagementServers[0].Id, l.Count, nil + } + + if l.Count > 1 { + for _, v := range l.ManagementServers { + if v.Name == name { + return v.Id, l.Count, nil + } + } + } + return "", l.Count, fmt.Errorf("Could not find an exact match for %s: %+v", name, l) +} + +// This is a courtesy helper function, which in some cases may not work as expected! +func (s *ManagementService) GetManagementServerByName(name string, opts ...OptionFunc) (*ManagementServer, int, error) { + id, count, err := s.GetManagementServerID(name, opts...) + if err != nil { + return nil, count, err + } + + r, count, err := s.GetManagementServerByID(id, opts...) + if err != nil { + return nil, count, err + } + return r, count, nil +} + +// This is a courtesy helper function, which in some cases may not work as expected! +func (s *ManagementService) GetManagementServerByID(id string, opts ...OptionFunc) (*ManagementServer, int, error) { + p := &ListManagementServersParams{} + p.p = make(map[string]interface{}) + + p.p["id"] = id + + for _, fn := range append(s.cs.options, opts...) { + if err := fn(s.cs, p); err != nil { + return nil, -1, err + } + } + + l, err := s.ListManagementServers(p) + if err != nil { + if strings.Contains(err.Error(), fmt.Sprintf( + "Invalid parameter id value=%s due to incorrect long value format, "+ + "or entity does not exist", id)) { + return nil, 0, fmt.Errorf("No match found for %s: %+v", id, l) + } + return nil, -1, err + } + + if l.Count == 0 { + return nil, l.Count, fmt.Errorf("No match found for %s: %+v", id, l) + } + + if l.Count == 1 { + return l.ManagementServers[0], l.Count, nil + } + return nil, l.Count, fmt.Errorf("There is more then one result for ManagementServer UUID: %s!", id) +} + +// Lists management servers. +func (s *ManagementService) ListManagementServers(p *ListManagementServersParams) (*ListManagementServersResponse, error) { + resp, err := s.cs.newRequest("listManagementServers", p.toURLValues()) + if err != nil { + return nil, err + } + + var r ListManagementServersResponse + if err := json.Unmarshal(resp, &r); err != nil { + return nil, err + } + + return &r, nil +} + +type ListManagementServersResponse struct { + Count int `json:"count"` + ManagementServers []*ManagementServer `json:"managementserver"` +} + +type ManagementServer struct { + Id string `json:"id"` + Javadistribution string `json:"javadistribution"` + Javaversion string `json:"javaversion"` + JobID string `json:"jobid"` + Jobstatus int `json:"jobstatus"` + Kernelversion string `json:"kernelversion"` + Lastboottime string `json:"lastboottime"` + Lastserverstart string `json:"lastserverstart"` + Lastserverstop string `json:"lastserverstop"` + Name string `json:"name"` + Osdistribution string `json:"osdistribution"` + Serviceip string `json:"serviceip"` + State string `json:"state"` + Version string `json:"version"` +} diff --git a/cloudstack/ManagementService_mock.go b/cloudstack/ManagementService_mock.go new file mode 100644 index 0000000..2b1e31b --- /dev/null +++ b/cloudstack/ManagementService_mock.go @@ -0,0 +1,145 @@ +// +// 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/ManagementService.go + +// Package cloudstack is a generated GoMock package. +package cloudstack + +import ( + reflect "reflect" + + gomock "github.com/golang/mock/gomock" +) + +// MockManagementServiceIface is a mock of ManagementServiceIface interface. +type MockManagementServiceIface struct { + ctrl *gomock.Controller + recorder *MockManagementServiceIfaceMockRecorder +} + +// MockManagementServiceIfaceMockRecorder is the mock recorder for MockManagementServiceIface. +type MockManagementServiceIfaceMockRecorder struct { + mock *MockManagementServiceIface +} + +// NewMockManagementServiceIface creates a new mock instance. +func NewMockManagementServiceIface(ctrl *gomock.Controller) *MockManagementServiceIface { + mock := &MockManagementServiceIface{ctrl: ctrl} + mock.recorder = &MockManagementServiceIfaceMockRecorder{mock} + return mock +} + +// EXPECT returns an object that allows the caller to indicate expected use. +func (m *MockManagementServiceIface) EXPECT() *MockManagementServiceIfaceMockRecorder { + return m.recorder +} + +// GetManagementServerByID mocks base method. +func (m *MockManagementServiceIface) GetManagementServerByID(id string, opts ...OptionFunc) (*ManagementServer, int, error) { + m.ctrl.T.Helper() + varargs := []interface{}{id} + for _, a := range opts { + varargs = append(varargs, a) + } + ret := m.ctrl.Call(m, "GetManagementServerByID", varargs...) + ret0, _ := ret[0].(*ManagementServer) + ret1, _ := ret[1].(int) + ret2, _ := ret[2].(error) + return ret0, ret1, ret2 +} + +// GetManagementServerByID indicates an expected call of GetManagementServerByID. +func (mr *MockManagementServiceIfaceMockRecorder) GetManagementServerByID(id interface{}, opts ...interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + varargs := append([]interface{}{id}, opts...) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetManagementServerByID", reflect.TypeOf((*MockManagementServiceIface)(nil).GetManagementServerByID), varargs...) +} + +// GetManagementServerByName mocks base method. +func (m *MockManagementServiceIface) GetManagementServerByName(name string, opts ...OptionFunc) (*ManagementServer, int, error) { + m.ctrl.T.Helper() + varargs := []interface{}{name} + for _, a := range opts { + varargs = append(varargs, a) + } + ret := m.ctrl.Call(m, "GetManagementServerByName", varargs...) + ret0, _ := ret[0].(*ManagementServer) + ret1, _ := ret[1].(int) + ret2, _ := ret[2].(error) + return ret0, ret1, ret2 +} + +// GetManagementServerByName indicates an expected call of GetManagementServerByName. +func (mr *MockManagementServiceIfaceMockRecorder) GetManagementServerByName(name interface{}, opts ...interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + varargs := append([]interface{}{name}, opts...) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetManagementServerByName", reflect.TypeOf((*MockManagementServiceIface)(nil).GetManagementServerByName), varargs...) +} + +// GetManagementServerID mocks base method. +func (m *MockManagementServiceIface) GetManagementServerID(name string, opts ...OptionFunc) (string, int, error) { + m.ctrl.T.Helper() + varargs := []interface{}{name} + for _, a := range opts { + varargs = append(varargs, a) + } + ret := m.ctrl.Call(m, "GetManagementServerID", varargs...) + ret0, _ := ret[0].(string) + ret1, _ := ret[1].(int) + ret2, _ := ret[2].(error) + return ret0, ret1, ret2 +} + +// GetManagementServerID indicates an expected call of GetManagementServerID. +func (mr *MockManagementServiceIfaceMockRecorder) GetManagementServerID(name interface{}, opts ...interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + varargs := append([]interface{}{name}, opts...) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetManagementServerID", reflect.TypeOf((*MockManagementServiceIface)(nil).GetManagementServerID), varargs...) +} + +// ListManagementServers mocks base method. +func (m *MockManagementServiceIface) ListManagementServers(p *ListManagementServersParams) (*ListManagementServersResponse, error) { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "ListManagementServers", p) + ret0, _ := ret[0].(*ListManagementServersResponse) + ret1, _ := ret[1].(error) + return ret0, ret1 +} + +// ListManagementServers indicates an expected call of ListManagementServers. +func (mr *MockManagementServiceIfaceMockRecorder) ListManagementServers(p interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "ListManagementServers", reflect.TypeOf((*MockManagementServiceIface)(nil).ListManagementServers), p) +} + +// NewListManagementServersParams mocks base method. +func (m *MockManagementServiceIface) NewListManagementServersParams() *ListManagementServersParams { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "NewListManagementServersParams") + ret0, _ := ret[0].(*ListManagementServersParams) + return ret0 +} + +// NewListManagementServersParams indicates an expected call of NewListManagementServersParams. +func (mr *MockManagementServiceIfaceMockRecorder) NewListManagementServersParams() *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NewListManagementServersParams", reflect.TypeOf((*MockManagementServiceIface)(nil).NewListManagementServersParams)) +} diff --git a/cloudstack/UserService.go b/cloudstack/UserService.go index ac35291..afaa6e3 100644 --- a/cloudstack/UserService.go +++ b/cloudstack/UserService.go @@ -62,6 +62,8 @@ type UserServiceIface interface { NewRegisterUserDataParams(name string, userdata string) *RegisterUserDataParams MoveUser(p *MoveUserParams) (*MoveUserResponse, error) NewMoveUserParams(id string) *MoveUserParams + SetupUserTwoFactorAuthentication(p *SetupUserTwoFactorAuthenticationParams) (*SetupUserTwoFactorAuthenticationResponse, error) + NewSetupUserTwoFactorAuthenticationParams() *SetupUserTwoFactorAuthenticationParams } type CreateUserParams struct { @@ -2691,3 +2693,123 @@ func (r *MoveUserResponse) UnmarshalJSON(b []byte) error { type alias MoveUserResponse return json.Unmarshal(b, (*alias)(r)) } + +type SetupUserTwoFactorAuthenticationParams struct { + p map[string]interface{} +} + +func (p *SetupUserTwoFactorAuthenticationParams) toURLValues() url.Values { + u := url.Values{} + if p.p == nil { + return u + } + if v, found := p.p["enable"]; found { + vv := strconv.FormatBool(v.(bool)) + u.Set("enable", vv) + } + if v, found := p.p["provider"]; found { + u.Set("provider", v.(string)) + } + if v, found := p.p["userid"]; found { + u.Set("userid", v.(string)) + } + return u +} + +func (p *SetupUserTwoFactorAuthenticationParams) SetEnable(v bool) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + p.p["enable"] = v +} + +func (p *SetupUserTwoFactorAuthenticationParams) ResetEnable() { + if p.p != nil && p.p["enable"] != nil { + delete(p.p, "enable") + } +} + +func (p *SetupUserTwoFactorAuthenticationParams) GetEnable() (bool, bool) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + value, ok := p.p["enable"].(bool) + return value, ok +} + +func (p *SetupUserTwoFactorAuthenticationParams) SetProvider(v string) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + p.p["provider"] = v +} + +func (p *SetupUserTwoFactorAuthenticationParams) ResetProvider() { + if p.p != nil && p.p["provider"] != nil { + delete(p.p, "provider") + } +} + +func (p *SetupUserTwoFactorAuthenticationParams) GetProvider() (string, bool) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + value, ok := p.p["provider"].(string) + return value, ok +} + +func (p *SetupUserTwoFactorAuthenticationParams) SetUserid(v string) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + p.p["userid"] = v +} + +func (p *SetupUserTwoFactorAuthenticationParams) ResetUserid() { + if p.p != nil && p.p["userid"] != nil { + delete(p.p, "userid") + } +} + +func (p *SetupUserTwoFactorAuthenticationParams) GetUserid() (string, bool) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + value, ok := p.p["userid"].(string) + return value, ok +} + +// You should always use this function to get a new SetupUserTwoFactorAuthenticationParams instance, +// as then you are sure you have configured all required params +func (s *UserService) NewSetupUserTwoFactorAuthenticationParams() *SetupUserTwoFactorAuthenticationParams { + p := &SetupUserTwoFactorAuthenticationParams{} + p.p = make(map[string]interface{}) + return p +} + +// Setup the 2FA for the user. +func (s *UserService) SetupUserTwoFactorAuthentication(p *SetupUserTwoFactorAuthenticationParams) (*SetupUserTwoFactorAuthenticationResponse, error) { + resp, err := s.cs.newPostRequest("setupUserTwoFactorAuthentication", p.toURLValues()) + if err != nil { + return nil, err + } + + var nested struct { + Response SetupUserTwoFactorAuthenticationResponse `json:"setup2fa"` + } + if err := json.Unmarshal(resp, &nested); err != nil { + return nil, err + } + r := nested.Response + + return &r, nil +} + +type SetupUserTwoFactorAuthenticationResponse struct { + Accountid string `json:"accountid"` + Id string `json:"id"` + JobID string `json:"jobid"` + Jobstatus int `json:"jobstatus"` + Secretcode string `json:"secretcode"` + Username string `json:"username"` +} diff --git a/cloudstack/UserService_mock.go b/cloudstack/UserService_mock.go index 834f7dc..6d65e2c 100644 --- a/cloudstack/UserService_mock.go +++ b/cloudstack/UserService_mock.go @@ -512,6 +512,20 @@ func (mr *MockUserServiceIfaceMockRecorder) NewRegisterUserKeysParams(id interfa return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NewRegisterUserKeysParams", reflect.TypeOf((*MockUserServiceIface)(nil).NewRegisterUserKeysParams), id) } +// NewSetupUserTwoFactorAuthenticationParams mocks base method. +func (m *MockUserServiceIface) NewSetupUserTwoFactorAuthenticationParams() *SetupUserTwoFactorAuthenticationParams { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "NewSetupUserTwoFactorAuthenticationParams") + ret0, _ := ret[0].(*SetupUserTwoFactorAuthenticationParams) + return ret0 +} + +// NewSetupUserTwoFactorAuthenticationParams indicates an expected call of NewSetupUserTwoFactorAuthenticationParams. +func (mr *MockUserServiceIfaceMockRecorder) NewSetupUserTwoFactorAuthenticationParams() *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NewSetupUserTwoFactorAuthenticationParams", reflect.TypeOf((*MockUserServiceIface)(nil).NewSetupUserTwoFactorAuthenticationParams)) +} + // NewUpdateUserParams mocks base method. func (m *MockUserServiceIface) NewUpdateUserParams(id string) *UpdateUserParams { m.ctrl.T.Helper() @@ -556,6 +570,21 @@ func (mr *MockUserServiceIfaceMockRecorder) RegisterUserKeys(p interface{}) *gom return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "RegisterUserKeys", reflect.TypeOf((*MockUserServiceIface)(nil).RegisterUserKeys), p) } +// SetupUserTwoFactorAuthentication mocks base method. +func (m *MockUserServiceIface) SetupUserTwoFactorAuthentication(p *SetupUserTwoFactorAuthenticationParams) (*SetupUserTwoFactorAuthenticationResponse, error) { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "SetupUserTwoFactorAuthentication", p) + ret0, _ := ret[0].(*SetupUserTwoFactorAuthenticationResponse) + ret1, _ := ret[1].(error) + return ret0, ret1 +} + +// SetupUserTwoFactorAuthentication indicates an expected call of SetupUserTwoFactorAuthentication. +func (mr *MockUserServiceIfaceMockRecorder) SetupUserTwoFactorAuthentication(p interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "SetupUserTwoFactorAuthentication", reflect.TypeOf((*MockUserServiceIface)(nil).SetupUserTwoFactorAuthentication), p) +} + // UpdateUser mocks base method. func (m *MockUserServiceIface) UpdateUser(p *UpdateUserParams) (*UpdateUserResponse, error) { m.ctrl.T.Helper() diff --git a/cloudstack/VirtualMachineService.go b/cloudstack/VirtualMachineService.go index 673d13e..e9b8693 100644 --- a/cloudstack/VirtualMachineService.go +++ b/cloudstack/VirtualMachineService.go @@ -98,6 +98,8 @@ type VirtualMachineServiceIface interface { ListVMSchedule(p *ListVMScheduleParams) (*ListVMScheduleResponse, error) NewListVMScheduleParams(virtualmachineid string) *ListVMScheduleParams GetVMScheduleByID(id string, virtualmachineid string, opts ...OptionFunc) (*VMSchedule, int, error) + DeleteVMSchedule(p *DeleteVMScheduleParams) (*DeleteVMScheduleResponse, error) + NewDeleteVMScheduleParams(virtualmachineid string) *DeleteVMScheduleParams } type AddNicToVirtualMachineParams struct { @@ -12514,3 +12516,146 @@ type VMSchedule struct { Timezone string `json:"timezone"` Virtualmachineid string `json:"virtualmachineid"` } + +type DeleteVMScheduleParams struct { + p map[string]interface{} +} + +func (p *DeleteVMScheduleParams) toURLValues() url.Values { + u := url.Values{} + if p.p == nil { + return u + } + if v, found := p.p["id"]; found { + u.Set("id", v.(string)) + } + if v, found := p.p["ids"]; found { + vv := strings.Join(v.([]string), ",") + u.Set("ids", vv) + } + if v, found := p.p["virtualmachineid"]; found { + u.Set("virtualmachineid", v.(string)) + } + return u +} + +func (p *DeleteVMScheduleParams) SetId(v string) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + p.p["id"] = v +} + +func (p *DeleteVMScheduleParams) ResetId() { + if p.p != nil && p.p["id"] != nil { + delete(p.p, "id") + } +} + +func (p *DeleteVMScheduleParams) GetId() (string, bool) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + value, ok := p.p["id"].(string) + return value, ok +} + +func (p *DeleteVMScheduleParams) SetIds(v []string) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + p.p["ids"] = v +} + +func (p *DeleteVMScheduleParams) ResetIds() { + if p.p != nil && p.p["ids"] != nil { + delete(p.p, "ids") + } +} + +func (p *DeleteVMScheduleParams) GetIds() ([]string, bool) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + value, ok := p.p["ids"].([]string) + return value, ok +} + +func (p *DeleteVMScheduleParams) SetVirtualmachineid(v string) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + p.p["virtualmachineid"] = v +} + +func (p *DeleteVMScheduleParams) ResetVirtualmachineid() { + if p.p != nil && p.p["virtualmachineid"] != nil { + delete(p.p, "virtualmachineid") + } +} + +func (p *DeleteVMScheduleParams) GetVirtualmachineid() (string, bool) { + if p.p == nil { + p.p = make(map[string]interface{}) + } + value, ok := p.p["virtualmachineid"].(string) + return value, ok +} + +// You should always use this function to get a new DeleteVMScheduleParams instance, +// as then you are sure you have configured all required params +func (s *VirtualMachineService) NewDeleteVMScheduleParams(virtualmachineid string) *DeleteVMScheduleParams { + p := &DeleteVMScheduleParams{} + p.p = make(map[string]interface{}) + p.p["virtualmachineid"] = virtualmachineid + return p +} + +// Delete VM Schedule. +func (s *VirtualMachineService) DeleteVMSchedule(p *DeleteVMScheduleParams) (*DeleteVMScheduleResponse, error) { + resp, err := s.cs.newRequest("deleteVMSchedule", p.toURLValues()) + if err != nil { + return nil, err + } + + var r DeleteVMScheduleResponse + if err := json.Unmarshal(resp, &r); err != nil { + return nil, err + } + + return &r, nil +} + +type DeleteVMScheduleResponse struct { + Displaytext string `json:"displaytext"` + JobID string `json:"jobid"` + Jobstatus int `json:"jobstatus"` + Success bool `json:"success"` +} + +func (r *DeleteVMScheduleResponse) UnmarshalJSON(b []byte) error { + var m map[string]interface{} + err := json.Unmarshal(b, &m) + if err != nil { + return err + } + + if success, ok := m["success"].(string); ok { + m["success"] = success == "true" + b, err = json.Marshal(m) + if err != nil { + return err + } + } + + if ostypeid, ok := m["ostypeid"].(float64); ok { + m["ostypeid"] = strconv.Itoa(int(ostypeid)) + b, err = json.Marshal(m) + if err != nil { + return err + } + } + + type alias DeleteVMScheduleResponse + return json.Unmarshal(b, (*alias)(r)) +} diff --git a/cloudstack/VirtualMachineService_mock.go b/cloudstack/VirtualMachineService_mock.go index fd4e8b7..531df17 100644 --- a/cloudstack/VirtualMachineService_mock.go +++ b/cloudstack/VirtualMachineService_mock.go @@ -127,6 +127,21 @@ func (mr *MockVirtualMachineServiceIfaceMockRecorder) CreateVMSchedule(p interfa return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateVMSchedule", reflect.TypeOf((*MockVirtualMachineServiceIface)(nil).CreateVMSchedule), p) } +// DeleteVMSchedule mocks base method. +func (m *MockVirtualMachineServiceIface) DeleteVMSchedule(p *DeleteVMScheduleParams) (*DeleteVMScheduleResponse, error) { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "DeleteVMSchedule", p) + ret0, _ := ret[0].(*DeleteVMScheduleResponse) + ret1, _ := ret[1].(error) + return ret0, ret1 +} + +// DeleteVMSchedule indicates an expected call of DeleteVMSchedule. +func (mr *MockVirtualMachineServiceIfaceMockRecorder) DeleteVMSchedule(p interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "DeleteVMSchedule", reflect.TypeOf((*MockVirtualMachineServiceIface)(nil).DeleteVMSchedule), p) +} + // DeployVirtualMachine mocks base method. func (m *MockVirtualMachineServiceIface) DeployVirtualMachine(p *DeployVirtualMachineParams) (*DeployVirtualMachineResponse, error) { m.ctrl.T.Helper() @@ -602,6 +617,20 @@ func (mr *MockVirtualMachineServiceIfaceMockRecorder) NewCreateVMScheduleParams( return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NewCreateVMScheduleParams", reflect.TypeOf((*MockVirtualMachineServiceIface)(nil).NewCreateVMScheduleParams), action, schedule, timezone, virtualmachineid) } +// NewDeleteVMScheduleParams mocks base method. +func (m *MockVirtualMachineServiceIface) NewDeleteVMScheduleParams(virtualmachineid string) *DeleteVMScheduleParams { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "NewDeleteVMScheduleParams", virtualmachineid) + ret0, _ := ret[0].(*DeleteVMScheduleParams) + return ret0 +} + +// NewDeleteVMScheduleParams indicates an expected call of NewDeleteVMScheduleParams. +func (mr *MockVirtualMachineServiceIfaceMockRecorder) NewDeleteVMScheduleParams(virtualmachineid interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NewDeleteVMScheduleParams", reflect.TypeOf((*MockVirtualMachineServiceIface)(nil).NewDeleteVMScheduleParams), virtualmachineid) +} + // NewDeployVirtualMachineParams mocks base method. func (m *MockVirtualMachineServiceIface) NewDeployVirtualMachineParams(serviceofferingid, templateid, zoneid string) *DeployVirtualMachineParams { m.ctrl.T.Helper() diff --git a/cloudstack/cloudstack.go b/cloudstack/cloudstack.go index 49b6b00..4b51101 100644 --- a/cloudstack/cloudstack.go +++ b/cloudstack/cloudstack.go @@ -133,6 +133,7 @@ type CloudStackClient struct { LDAP LDAPServiceIface Limit LimitServiceIface LoadBalancer LoadBalancerServiceIface + Management ManagementServiceIface Metrics MetricsServiceIface NAT NATServiceIface NetworkACL NetworkACLServiceIface @@ -246,6 +247,7 @@ func newClient(apiurl string, apikey string, secret string, async bool, verifyss cs.LDAP = NewLDAPService(cs) cs.Limit = NewLimitService(cs) cs.LoadBalancer = NewLoadBalancerService(cs) + cs.Management = NewManagementService(cs) cs.Metrics = NewMetricsService(cs) cs.NAT = NewNATService(cs) cs.NetworkACL = NewNetworkACLService(cs) @@ -332,6 +334,7 @@ func newMockClient(ctrl *gomock.Controller) *CloudStackClient { cs.LDAP = NewMockLDAPServiceIface(ctrl) cs.Limit = NewMockLimitServiceIface(ctrl) cs.LoadBalancer = NewMockLoadBalancerServiceIface(ctrl) + cs.Management = NewMockManagementServiceIface(ctrl) cs.Metrics = NewMockMetricsServiceIface(ctrl) cs.NAT = NewMockNATServiceIface(ctrl) cs.NetworkACL = NewMockNetworkACLServiceIface(ctrl) @@ -1032,6 +1035,14 @@ func NewLoadBalancerService(cs *CloudStackClient) LoadBalancerServiceIface { return &LoadBalancerService{cs: cs} } +type ManagementService struct { + cs *CloudStackClient +} + +func NewManagementService(cs *CloudStackClient) ManagementServiceIface { + return &ManagementService{cs: cs} +} + type MetricsService struct { cs *CloudStackClient } diff --git a/generate/generate.go b/generate/generate.go index ec38a67..0aa09e4 100644 --- a/generate/generate.go +++ b/generate/generate.go @@ -99,29 +99,32 @@ var mapRequireList = map[string]map[string]bool{ // that responses fields are nested in a parent object. The map value // gives the object field name. var nestedResponse = map[string]string{ - "getUploadParamsForTemplate": "getuploadparams", - "getUploadParamsForVolume": "getuploadparams", - "createRole": "role", - "createRolePermission": "rolepermission", - "getCloudIdentifier": "cloudidentifier", - "getKubernetesClusterConfig": "clusterconfig", - "getPathForVolume": "apipathforvolume", - "createConsoleEndpoint": "consoleendpoint", - "addVmwareDc": "vmwaredc", - "updateVmwareDc": "vmwaredc", - "createProjectRole": "projectrole", - "updateProjectRole": "projectrole", - "registerUserData": "userdata", - "updateSecurityGroup": "securitygroup", - "updateOauthProvider": "oauthprovider", - "readyForShutdown": "readyforshutdown", - "updateObjectStoragePool": "objectstore", - "addObjectStoragePool": "objectstore", - "updateImageStore": "imagestore", - "linkUserDataToTemplate": "template", - "assignVolume": "volume", - "createVMSchedule": "vmschedule", - "updateVMSchedule": "vmschedule", + "getUploadParamsForTemplate": "getuploadparams", + "getUploadParamsForVolume": "getuploadparams", + "createRole": "role", + "createRolePermission": "rolepermission", + "getCloudIdentifier": "cloudidentifier", + "getKubernetesClusterConfig": "clusterconfig", + "getPathForVolume": "apipathforvolume", + "createConsoleEndpoint": "consoleendpoint", + "addVmwareDc": "vmwaredc", + "updateVmwareDc": "vmwaredc", + "createProjectRole": "projectrole", + "updateProjectRole": "projectrole", + "registerUserData": "userdata", + "updateSecurityGroup": "securitygroup", + "updateOauthProvider": "oauthprovider", + "readyForShutdown": "readyforshutdown", + "updateObjectStoragePool": "objectstore", + "addObjectStoragePool": "objectstore", + "updateImageStore": "imagestore", + "linkUserDataToTemplate": "template", + "assignVolume": "volume", + "createVMSchedule": "vmschedule", + "updateVMSchedule": "vmschedule", + "setupUserTwoFactorAuthentication": "setup2fa", + "updateSecondaryStorageSelector": "heuristics", + "createSecondaryStorageSelector": "heuristics", } // longToStringConvertedParams is a prefilled map with the list of diff --git a/generate/layout.go b/generate/layout.go index eeb7267..518276e 100644 --- a/generate/layout.go +++ b/generate/layout.go @@ -124,6 +124,7 @@ var layout = apiInfo{ "createVMSchedule", "updateVMSchedule", "listVMSchedule", + "deleteVMSchedule", }, "VPNService": { "addVpnUser", @@ -222,6 +223,7 @@ var layout = apiInfo{ "removeSecondaryStorageSelector", "listHostHAResources", "declareHostAsDegraded", + "updateSecondaryStorageSelector", }, "VolumeService": { "attachVolume", @@ -355,6 +357,7 @@ var layout = apiInfo{ "deleteUserData", "registerUserData", "moveUser", + "setupUserTwoFactorAuthentication", }, "LDAPService": { "addLdapConfiguration", @@ -796,4 +799,7 @@ var layout = apiInfo{ "MetricsService": { "listInfrastructure", }, + "ManagementService": { + "listManagementServers", + }, } diff --git a/test/HostService_test.go b/test/HostService_test.go index f1141ea..1abcc56 100644 --- a/test/HostService_test.go +++ b/test/HostService_test.go @@ -431,4 +431,19 @@ func TestHostService(t *testing.T) { } t.Run("DeclareHostAsDegraded", testdeclareHostAsDegraded) + testupdateSecondaryStorageSelector := func(t *testing.T) { + if _, ok := response["updateSecondaryStorageSelector"]; !ok { + t.Skipf("Skipping as no json response is provided in testdata") + } + p := client.Host.NewUpdateSecondaryStorageSelectorParams("heuristicrule", "id") + r, err := client.Host.UpdateSecondaryStorageSelector(p) + if err != nil { + t.Errorf(err.Error()) + } + if r.Id == "" { + t.Errorf("Failed to parse response. ID not found") + } + } + t.Run("UpdateSecondaryStorageSelector", testupdateSecondaryStorageSelector) + } diff --git a/test/ManagementService_test.go b/test/ManagementService_test.go new file mode 100644 index 0000000..a09d9f4 --- /dev/null +++ b/test/ManagementService_test.go @@ -0,0 +1,50 @@ +// +// 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. +// + +package test + +import ( + "testing" + + "github.com/apache/cloudstack-go/v2/cloudstack" +) + +func TestManagementService(t *testing.T) { + service := "ManagementService" + response, err := readData(service) + if err != nil { + t.Skipf("Skipping test as %v", err) + } + server := CreateTestServer(t, response) + client := cloudstack.NewClient(server.URL, "APIKEY", "SECRETKEY", true) + defer server.Close() + + testlistManagementServers := func(t *testing.T) { + if _, ok := response["listManagementServers"]; !ok { + t.Skipf("Skipping as no json response is provided in testdata") + } + p := client.Management.NewListManagementServersParams() + _, err := client.Management.ListManagementServers(p) + if err != nil { + t.Errorf(err.Error()) + } + } + t.Run("ListManagementServers", testlistManagementServers) + +} diff --git a/test/UserService_test.go b/test/UserService_test.go index 95e7155..4f88e8f 100644 --- a/test/UserService_test.go +++ b/test/UserService_test.go @@ -233,4 +233,19 @@ func TestUserService(t *testing.T) { } t.Run("MoveUser", testmoveUser) + testsetupUserTwoFactorAuthentication := func(t *testing.T) { + if _, ok := response["setupUserTwoFactorAuthentication"]; !ok { + t.Skipf("Skipping as no json response is provided in testdata") + } + p := client.User.NewSetupUserTwoFactorAuthenticationParams() + r, err := client.User.SetupUserTwoFactorAuthentication(p) + if err != nil { + t.Errorf(err.Error()) + } + if r.Id == "" { + t.Errorf("Failed to parse response. ID not found") + } + } + t.Run("SetupUserTwoFactorAuthentication", testsetupUserTwoFactorAuthentication) + } diff --git a/test/VirtualMachineService_test.go b/test/VirtualMachineService_test.go index e7d2c70..5041a5b 100644 --- a/test/VirtualMachineService_test.go +++ b/test/VirtualMachineService_test.go @@ -455,4 +455,16 @@ func TestVirtualMachineService(t *testing.T) { } t.Run("ListVMSchedule", testlistVMSchedule) + testdeleteVMSchedule := func(t *testing.T) { + if _, ok := response["deleteVMSchedule"]; !ok { + t.Skipf("Skipping as no json response is provided in testdata") + } + p := client.VirtualMachine.NewDeleteVMScheduleParams("virtualmachineid") + _, err := client.VirtualMachine.DeleteVMSchedule(p) + if err != nil { + t.Errorf(err.Error()) + } + } + t.Run("DeleteVMSchedule", testdeleteVMSchedule) + }