v1.0.0
This commit is contained in:
45
CHANGELOG.md
Normal file
45
CHANGELOG.md
Normal file
@@ -0,0 +1,45 @@
|
|||||||
|
## Version 1.0.0
|
||||||
|
|
||||||
|
### Features
|
||||||
|
|
||||||
|
- Add a configurable http-client for interacting with the DECORT cloud platform:
|
||||||
|
- Custom connection retries
|
||||||
|
- Custom auth method - app_id, app_secret pair and jwt-token
|
||||||
|
- Custom parameters for a ssl verify
|
||||||
|
- Custom SSO URL for auth
|
||||||
|
- Custom Decort URL for interacting with DECORT
|
||||||
|
- Add support for a cloudapi api groups:
|
||||||
|
- account
|
||||||
|
- bservice
|
||||||
|
- compute
|
||||||
|
- computeci
|
||||||
|
- disks
|
||||||
|
- extnet
|
||||||
|
- flipgroup
|
||||||
|
- image
|
||||||
|
- k8ci
|
||||||
|
- k8s
|
||||||
|
- kvmppc
|
||||||
|
- kvmx86
|
||||||
|
- lb
|
||||||
|
- locations
|
||||||
|
- rg
|
||||||
|
- sizes
|
||||||
|
- tasks
|
||||||
|
- vins
|
||||||
|
- Add support for a cloudbroker api groups:
|
||||||
|
- account
|
||||||
|
- compute
|
||||||
|
- disks
|
||||||
|
- extnet
|
||||||
|
- grid
|
||||||
|
- image
|
||||||
|
- k8ci
|
||||||
|
- k8s
|
||||||
|
- kvmppc
|
||||||
|
- kvmx86
|
||||||
|
- lb
|
||||||
|
- rg
|
||||||
|
- sep
|
||||||
|
- tasks
|
||||||
|
- vins
|
||||||
5
Makefile
Normal file
5
Makefile
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
.PHONY: lint
|
||||||
|
lint:
|
||||||
|
golangci-lint run --timeout 600s
|
||||||
|
|
||||||
|
.DEFAULT_GOAL := lint
|
||||||
438
README.md
438
README.md
@@ -1,47 +1,427 @@
|
|||||||
# Decort SDK
|
# Decort SDK
|
||||||
|
|
||||||
## Install
|
Decort SDK - это библиотека, написанная на языке GO, позволяющая взаимодействовать с API облачной платформы **DECORT**. Библиотека содеражит в себе структуры и методы, необходимые для отправки запросов. Decort SDK имеет встроенный http-клиент и поддерживает разные способы авторизации на платформе. Библиотека так же содержит в себе модели ответов от платформы.
|
||||||
|
|
||||||
|
## Оглавление
|
||||||
|
|
||||||
|
- [Установка](#установка)
|
||||||
|
- [Список API](#список-api)
|
||||||
|
- [Cloudapi](#cloudapi)
|
||||||
|
- [Cloudbroker](#cloudbroker)
|
||||||
|
- [Работа с библиотекой](#работа-с-библиотекой)
|
||||||
|
- [Настройка конфигурации клиента](#настройка-конфигурации-клиента)
|
||||||
|
- [Создание клиента](#создание-клиента)
|
||||||
|
- [Создание структуры запроса](#cоздание-структуры-запроса)
|
||||||
|
- [Выполнение запроса](#выполнение-запроса)
|
||||||
|
|
||||||
|
## Установка
|
||||||
|
|
||||||
|
Выполните команду в терминале:
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
go get -u github.com/rudecs/decort-sdk
|
go get -u github.com/rudecs/decort-sdk
|
||||||
```
|
```
|
||||||
|
|
||||||
## Example
|
## Список API
|
||||||
|
|
||||||
|
Библиотека поддерживает две группы API платформы:
|
||||||
|
|
||||||
|
- `cloudapi` - пользовательская группа, которая позволяет воспользоваться всем стардартным функционалом платформы;
|
||||||
|
- `cloudbroker` - административная группа, которая позволяет воспользоваться всем стандартным функционалом платформы и расширенными возможностями, включающими в себя управление пользователями, ресурсами, платформами размещения ресурсов и т.д.
|
||||||
|
|
||||||
|
### Cloudapi
|
||||||
|
|
||||||
|
`Cloudapi` позволяет выполнять запросы к группе пользовательских конечных точек
|
||||||
|
Данная группа ручек позволяет выполнять следующие операции в платформе:
|
||||||
|
|
||||||
|
- `Account` - управление аккаунтами - внутренними учетными записями платформы, которые являются владельцами вычислительных ресурсов;
|
||||||
|
- `BService` - управление группами виртуальных машин (computes);
|
||||||
|
- `Compute` - управление виртуальными машинами (индивидуально);
|
||||||
|
- `ComputeCI` - управление конвейром для создания виртуальных машин;
|
||||||
|
- `Disks` - управление виртуальными дисками;
|
||||||
|
- `ExtNet` - управление виртуальными сетями, отвечающими за внешний доступ;
|
||||||
|
- `FLIPgroup` - управление группами "плавающими" ip - адресами;
|
||||||
|
- `Image` - управление образами операционных систем;
|
||||||
|
- `K8CI` - управление конвейром для создания кластера;
|
||||||
|
- `K8S` - управление кластерами kubernetes;
|
||||||
|
- `KVMPPC` - создание виртуальной машины Power PC (IBM);
|
||||||
|
- `KVMx86` - создание виртуальной машины x86;
|
||||||
|
- `LB` - управление балансировщиками нагрузки;
|
||||||
|
- `Locations` - получение информации о grid площадки;
|
||||||
|
- `RG` - управление ресурсными группами аккаунта;
|
||||||
|
- `Sizes` - получение информации о потребляемых ресурсах виртуальными машинами и дисками;
|
||||||
|
- `Tasks` - получение информации о ходе выполнения асинхронных задач (например, создание кластера);
|
||||||
|
- `VINS` - управление виртуальными изолированными сетями.
|
||||||
|
|
||||||
|
### Cloudbroker
|
||||||
|
|
||||||
|
`Cloudbroker` позволяет выполнять запросы к группе пользовательских конечных точек
|
||||||
|
Данная группа ручек позволяет выполнять следующие операции в платформе:
|
||||||
|
|
||||||
|
- `Account` - управление аккаунтами - внутренними учетными записями платформы, которые являются владельцами вычислительных ресурсов;
|
||||||
|
- `Compute` - управление виртуальными машинами (индивидуально);
|
||||||
|
- `Disks` - управление виртуальными дисками;
|
||||||
|
- `ExtNet` - управление виртуальными сетями, отвечающими за внешний доступ;
|
||||||
|
- `Grid` - управление площадками;
|
||||||
|
- `Image` - управление образами операционных систем;
|
||||||
|
- `K8CI` - управление конвейром для создания кластера;
|
||||||
|
- `K8S` - управление кластерами kubernetes;
|
||||||
|
- `KVMPPC` - создание виртуальной машины Power PC (IBM);
|
||||||
|
- `KVMx86` - создание виртуальной машины x86;
|
||||||
|
- `LB` - управление балансировщиками нагрузки;
|
||||||
|
- `RG` - управление ресурсными группами аккаунта;
|
||||||
|
- `SEP` - управление storage endpoint (sep);
|
||||||
|
- `Tasks` - получение информации о ходе выполнения асинхронных задач (например, создание кластера);
|
||||||
|
- `VINS` - управление виртуальными изолированными сетями.
|
||||||
|
|
||||||
|
## Работа с библиотекой
|
||||||
|
|
||||||
|
Алгоритм работы с библиотекой выглядит следующим образом:
|
||||||
|
|
||||||
|
1. Настройка конфигурации клиента.
|
||||||
|
2. Создание клиента.
|
||||||
|
3. Создание структуры запроса.
|
||||||
|
4. Выполнение запроса.
|
||||||
|
|
||||||
|
### Настройка конфигурации клиента
|
||||||
|
|
||||||
|
Сначала, необходимо создать переменную конфигурации клиента. Конфигурация состоит как из обязательных, так и необязательных полей.
|
||||||
|
| Поле | Тип | Обязательный | Описание |
|
||||||
|
| --- | --- | --- | --- |
|
||||||
|
| AppID | string | Да | app_id ключа для выполнения запросов |
|
||||||
|
| AppSecret | string | Да | app_secret ключ для выполнения запроса |
|
||||||
|
| SSOURL | string | Да | URL адрес сервиса аутентификации и авторизации |
|
||||||
|
| DecortURL | string | Да | URL адрес платформы, с которой будет осуществляться взаимодействие |
|
||||||
|
| Retries | uint | Нет | Кол-во неудачных попыток выполнения запроса, по умолчанию - 5 |
|
||||||
|
| SSLSkipVerify | bool | Нет | Пропуск проверки подлинности сертификата, по умолчанию - true |
|
||||||
|
| Token | string | Нет | JWT токен |
|
||||||
|
|
||||||
|
Пример кода:
|
||||||
|
|
||||||
|
```go
|
||||||
|
import (
|
||||||
|
"github.com/rudecs/decort-sdk/config"
|
||||||
|
)
|
||||||
|
func main(){
|
||||||
|
// Настройка конфигурации
|
||||||
|
cfg := config.Config{
|
||||||
|
AppID: "<APP_ID>",
|
||||||
|
AppSecret: "<APP_SECRET>",
|
||||||
|
SSOURL: "https://sso.digitalenergy.online",
|
||||||
|
DecortURL: "https://mr4.digitalenergy.online",
|
||||||
|
Retries: 5,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
### Создание клиента
|
||||||
|
|
||||||
|
Создание клиента происходит с помощью функции-строителя `New` из основного пакета `decort-sdk`, для избежания проблем с именами, пакету можно присвоить алиас `decort`. Функция принимает конфигурацию, возвращает структуру `DecortClient`, с помощью которой можно взаимодействовать с платформой.
|
||||||
|
|
||||||
|
### Пример
|
||||||
|
|
||||||
```go
|
```go
|
||||||
package main
|
package main
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"context"
|
"github.com/rudecs/decort-sdk/config"
|
||||||
"fmt"
|
decort "github.com/rudecs/decort-sdk"
|
||||||
"log"
|
|
||||||
|
|
||||||
"github.com/rudecs/decort-sdk/config"
|
|
||||||
"github.com/rudecs/decort-sdk/pkg/cloudapi/kvmx86"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
func main() {
|
func main() {
|
||||||
cfg := config.Config{
|
// Настройка конфигурации
|
||||||
AppID: "<APPID>",
|
cfg := config.Config{
|
||||||
AppSecret: "<APPSECRET>",
|
AppID: "<APPID>",
|
||||||
SSOURL: "https://sso.digitalenergy.online",
|
AppSecret: "<APPSECRET>",
|
||||||
DecortURL: "https://mr4.digitalenergy.online",
|
SSOURL: "https://sso.digitalenergy.online",
|
||||||
Retries: 5,
|
DecortURL: "https://mr4.digitalenergy.online",
|
||||||
}
|
Retries: 5,
|
||||||
client := decort.New(cfg)
|
}
|
||||||
req := kvmx86.CreateRequest{
|
|
||||||
RGID: 123,
|
|
||||||
Name: "compute",
|
|
||||||
CPU: 4,
|
|
||||||
RAM: 4096,
|
|
||||||
ImageID: 321,
|
|
||||||
}
|
|
||||||
|
|
||||||
res, err := client.KVMX86().Create(context.Background(), req)
|
// Создание клиента
|
||||||
if err != nil {
|
client := decort.New(cfg)
|
||||||
log.Fatal(err)
|
}
|
||||||
}
|
```
|
||||||
|
|
||||||
fmt.Println(res)
|
### Создание структуры запроса
|
||||||
|
|
||||||
|
Структуры запросов определены в пакетах:
|
||||||
|
|
||||||
|
- `pkg/cloudapi` - для `cloudapi`
|
||||||
|
- `pkg/cloudbroker` - для `cloudbroker`
|
||||||
|
|
||||||
|
В каждом пакете находятся пакеты групп API:
|
||||||
|
|
||||||
|
- **cloudapi**:
|
||||||
|
- `pkg/cloudapi/account` - для `Account`
|
||||||
|
- `pkg/cloudapi/bservice` - для `Basic Service`
|
||||||
|
- `pkg/cloudapi/compute` - для `Compute`
|
||||||
|
- `pkg/cloudapi/computeci` - для `ComputeCI`
|
||||||
|
- `pkg/cloudapi/disks` - для `Disks`
|
||||||
|
- `pkg/cloudapi/extnet` - для `ExtNet`
|
||||||
|
- `pkg/cloudapi/flipgroup` - для `FLIPGroup`
|
||||||
|
- `pkg/cloudapi/image` - для `Image`
|
||||||
|
- `pkg/cloudapi/k8ci` - для `K8CI`
|
||||||
|
- `pkg/cloudapi/k8s` - для `K8S`
|
||||||
|
- `pkg/cloudapi/kvmppc` - для `KVMPPC`
|
||||||
|
- `pkg/cloudapi/kvmx86` - для `KVMX86`
|
||||||
|
- `pkg/cloudapi/lb` - для `LB`
|
||||||
|
- `pkg/cloudapi/locations` - для `Locations`
|
||||||
|
- `pkg/cloudapi/rg` - для `RG`
|
||||||
|
- `pkg/cloudapi/sizes` - для `RG`
|
||||||
|
- `pkg/cloudapi/tasks` - для `Tasks`
|
||||||
|
- `pkg/cloudapi/vins` - для `VINS`
|
||||||
|
- **cloudbroker**:
|
||||||
|
- `pkg/cloudbroker/account` - для `Account`
|
||||||
|
- `pkg/cloudbroker/compute` - для `Compute`
|
||||||
|
- `pkg/cloudbroker/disks` - для `Disks`
|
||||||
|
- `pkg/cloudbroker/extnet` - для `ExtNet`
|
||||||
|
- `pkg/cloudbroker/grid` - для `Grid`
|
||||||
|
- `pkg/cloudbroker/image` - для `Image`
|
||||||
|
- `pkg/cloudbroker/k8ci` - для `K8CI`
|
||||||
|
- `pkg/cloudbroker/k8s` - для `K8S`
|
||||||
|
- `pkg/cloudbroker/kvmppc` - для `KVMPPC`
|
||||||
|
- `pkg/cloudbroker/kvmx86` - для `KVMX86`
|
||||||
|
- `pkg/cloudbroker/lb` - для `LB`
|
||||||
|
- `pkg/cloudbroker/rg` - для `RG`
|
||||||
|
- `pkg/cloudbroker/sep` - для `SEP`
|
||||||
|
- `pkg/cloudbroker/tasks` - для `Tasks`
|
||||||
|
- `pkg/cloudbroker/vins` - для `VINS`
|
||||||
|
|
||||||
|
Все поля структуры имеют описание, в которых содержится:
|
||||||
|
|
||||||
|
- Их назначение;
|
||||||
|
- Обязательный или нет - поле required в комментариях;
|
||||||
|
- Доп. информация (допустимые значения, значения по умолчанию).
|
||||||
|
|
||||||
|
#### Пример комментарие структуры
|
||||||
|
|
||||||
|
```go
|
||||||
|
type CreateRequest struct {
|
||||||
|
// ID of the resource group, which will own this VM
|
||||||
|
// Required: true
|
||||||
|
RGID uint64 `url:"rgId"`
|
||||||
|
|
||||||
|
// Name of this VM.
|
||||||
|
// Must be unique among all VMs (including those in DELETED state) in target resource group
|
||||||
|
// Required: true
|
||||||
|
Name string `url:"name"`
|
||||||
|
|
||||||
|
// Number CPUs to allocate to this VM
|
||||||
|
// Required: true
|
||||||
|
CPU uint64 `url:"cpu"`
|
||||||
|
|
||||||
|
// Volume of RAM in MB to allocate to this VM
|
||||||
|
// Required: true
|
||||||
|
RAM uint64 `url:"ram"`
|
||||||
|
|
||||||
|
// ID of the OS image to base this VM on;
|
||||||
|
// Could be boot disk image or CD-ROM image
|
||||||
|
// Required: true
|
||||||
|
ImageID uint64 `url:"imageId"`
|
||||||
|
|
||||||
|
// Size of the boot disk in GB
|
||||||
|
// Required: false
|
||||||
|
BootDisk uint64 `url:"bootDisk,omitempty"`
|
||||||
|
|
||||||
|
// ID of SEP to create boot disk on.
|
||||||
|
// Uses images SEP ID if not set
|
||||||
|
// Required: false
|
||||||
|
SEPID uint64 `url:"sepId,omitempty"`
|
||||||
|
|
||||||
|
// Pool to use if SEP ID is set, can be also empty if needed to be chosen by system
|
||||||
|
// Required: false
|
||||||
|
Pool string `url:"pool,omitempty"`
|
||||||
|
|
||||||
|
// Network type
|
||||||
|
// Should be one of:
|
||||||
|
// - VINS
|
||||||
|
// - EXTNET
|
||||||
|
// - NONE
|
||||||
|
// Required: false
|
||||||
|
NetType string `url:"netType,omitempty"`
|
||||||
|
|
||||||
|
// Network ID for connect to,
|
||||||
|
// for EXTNET - external network ID,
|
||||||
|
// for VINS - VINS ID,
|
||||||
|
// when network type is not "NONE"
|
||||||
|
// Required: false
|
||||||
|
NetID uint64 `url:"netId,omitempty"`
|
||||||
|
|
||||||
|
// IP address to assign to this VM when connecting to the specified network
|
||||||
|
// Required: false
|
||||||
|
IPAddr string `url:"ipAddr,omitempty"`
|
||||||
|
|
||||||
|
// Input data for cloud-init facility
|
||||||
|
// Required: false
|
||||||
|
Userdata string `url:"userdata,omitempty"`
|
||||||
|
|
||||||
|
// Text description of this VM
|
||||||
|
// Required: false
|
||||||
|
Description string `url:"desc,omitempty"`
|
||||||
|
|
||||||
|
// Start VM upon success
|
||||||
|
// Required: false
|
||||||
|
Start bool `url:"start,omitempty"`
|
||||||
|
|
||||||
|
// Stack ID
|
||||||
|
// Required: false
|
||||||
|
StackID uint64 `url:"stackId,omitempty"`
|
||||||
|
|
||||||
|
// System name
|
||||||
|
// Required: false
|
||||||
|
IS string `url:"IS,omitempty"`
|
||||||
|
|
||||||
|
// Compute purpose
|
||||||
|
// Required: false
|
||||||
|
IPAType string `url:"ipaType,omitempty"`
|
||||||
|
|
||||||
|
// Reason for action
|
||||||
|
// Required: false
|
||||||
|
Reason string `url:"reason,omitempty"`
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
#### Пример создания запроса для развертывания виртуальной машины:
|
||||||
|
|
||||||
|
```go
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/rudecs/decort-sdk/config"
|
||||||
|
decort "github.com/rudecs/decort-sdk"
|
||||||
|
"github.com/rudecs/decort-sdk/pkg/cloudapi/kvmx86"
|
||||||
|
)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
// Настройка конфигурации
|
||||||
|
cfg := config.Config{
|
||||||
|
AppID: "<APPID>",
|
||||||
|
AppSecret: "<APPSECRET>",
|
||||||
|
SSOURL: "https://sso.digitalenergy.online",
|
||||||
|
DecortURL: "https://mr4.digitalenergy.online",
|
||||||
|
Retries: 5,
|
||||||
|
}
|
||||||
|
|
||||||
|
// Создание клиента
|
||||||
|
client := decort.New(cfg)
|
||||||
|
|
||||||
|
// Создание структуры запроса
|
||||||
|
// CreateRequest - реквест на создание виртуальной машины
|
||||||
|
req := kvmx86.CreateRequest{
|
||||||
|
RGID: 123,
|
||||||
|
Name: "compute",
|
||||||
|
CPU: 4,
|
||||||
|
RAM: 4096,
|
||||||
|
ImageID: 321,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
### Выполнение запроса
|
||||||
|
|
||||||
|
Чтобы выполнить запрос, необходимо:
|
||||||
|
|
||||||
|
1. Вызвать у клиента метод, отвечаеющий за определение группы API для взаимодействия, это может быть `.CloudAPI()`, либо `.CloudBroker()`. Данные методы возвращаеют соответствующие структуры, с помощью которых можно соверать запросы.
|
||||||
|
2. Вызвать у возвращенной структуры метод, определяющий группу ручек для взаимодействия.
|
||||||
|
|
||||||
|
Доступные методы для `.CloudAPI()`:
|
||||||
|
|
||||||
|
- `.Account()` - для работы с `Account`
|
||||||
|
- `.BService()` - для работы с `BService`
|
||||||
|
- `.Compute()` - для работы с `Compute`
|
||||||
|
- `.ComputeCI()` - для работы с `ComputeCI`
|
||||||
|
- `.Disks()` - для работы с `Disks`
|
||||||
|
- `.ExtNet()` - для работы с `ExtNet`
|
||||||
|
- `.FLIPgroup()` - для работы с `FLIPGroup`
|
||||||
|
- `.Image()` - для работы с `Image`
|
||||||
|
- `.K8CI()` - для работы с `K8CI`
|
||||||
|
- `.K8S()` - для работы с `K8S`
|
||||||
|
- `.KVMPPC()` - для работы с `KVMPPC`
|
||||||
|
- `.KVMx86()` - для работы с `KVMX86`
|
||||||
|
- `.LB()` - для работы с `LB`
|
||||||
|
- `.Locations()` - для работы с `Locations`
|
||||||
|
- `.RG()` - для работы с `RG`
|
||||||
|
- `.Sizes()` - для работы с `Sizes`
|
||||||
|
- `.Tasks()` - для работы с `Tasks`
|
||||||
|
- `.VINS()` - для работы с `VINS`
|
||||||
|
|
||||||
|
Доступные методы для `.CloudBroker()`:
|
||||||
|
|
||||||
|
- `.Account()` - для работы с `Account`
|
||||||
|
- `.Compute()` - для работы с `Compute`
|
||||||
|
- `.Disks()` - для работы с `Disks`
|
||||||
|
- `.ExtNet()` - для работы с `ExtNet`
|
||||||
|
- `.Grid()` - для работы с `Grid`
|
||||||
|
- `.Image()` - для работы с `Image`
|
||||||
|
- `.K8CI()` - для работы с `K8CI`
|
||||||
|
- `.K8S()` - для работы с `K8S`
|
||||||
|
- `.KVMPPC()` - для работы с `KVMPPC`
|
||||||
|
- `.KVMx86()` - для работы с `KVMX86`
|
||||||
|
- `.LB()` - для работы с `LB`
|
||||||
|
- `.RG()` - для работы с `RG`
|
||||||
|
- `.SEP()` - для работы с `SEP`
|
||||||
|
- `.Tasks()` - для работы с `Tasks`
|
||||||
|
- `.VINS()` - для работы с `VINS`
|
||||||
|
|
||||||
|
3. Вызвать метод, отвечающий за выполнение запроса и передать в него:
|
||||||
|
|
||||||
|
- контекст;
|
||||||
|
- структуру запроса.
|
||||||
|
У кождой группы ручек API имеются свои доступные методы, которые определяются платформой.
|
||||||
|
|
||||||
|
4. Обработать результат и ошибки.
|
||||||
|
|
||||||
|
Т.к. все вызовы методов идут последовательно, можно их объеденить в конвейер:
|
||||||
|
Общий вид вонвейра будет выглядеть так:
|
||||||
|
|
||||||
|
```go
|
||||||
|
client.<API>.<группа>.<метод>
|
||||||
|
```
|
||||||
|
|
||||||
|
#### Пример выполнения запроса
|
||||||
|
|
||||||
|
```go
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"log"
|
||||||
|
"fmt"
|
||||||
|
|
||||||
|
"github.com/rudecs/decort-sdk/config"
|
||||||
|
decort "github.com/rudecs/decort-sdk"
|
||||||
|
"github.com/rudecs/decort-sdk/pkg/cloudapi/kvmx86"
|
||||||
|
)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
// Настройка конфигурации
|
||||||
|
cfg := config.Config{
|
||||||
|
AppID: "<APPID>",
|
||||||
|
AppSecret: "<APPSECRET>",
|
||||||
|
SSOURL: "https://sso.digitalenergy.online",
|
||||||
|
DecortURL: "https://mr4.digitalenergy.online",
|
||||||
|
Retries: 5,
|
||||||
|
}
|
||||||
|
|
||||||
|
// Создание клиента
|
||||||
|
client := decort.New(cfg)
|
||||||
|
|
||||||
|
// Создание структуры запроса
|
||||||
|
// CreateRequest - реквест на создание виртуальной машины
|
||||||
|
req := kvmx86.CreateRequest{
|
||||||
|
RGID: 123,
|
||||||
|
Name: "compute",
|
||||||
|
CPU: 4,
|
||||||
|
RAM: 4096,
|
||||||
|
ImageID: 321,
|
||||||
|
}
|
||||||
|
|
||||||
|
//Выполнение запроса с помощью конвейера
|
||||||
|
res, err := client.СloudAPI().KVMX86().Create(context.Background(), req)
|
||||||
|
if err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
fmt.Println(res)
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|||||||
62
README_EN.md
Normal file
62
README_EN.md
Normal file
@@ -0,0 +1,62 @@
|
|||||||
|
# Decort SDK
|
||||||
|
|
||||||
|
Decort SDK is a library, written in GO (Golang) for interact with the **DECORT** API.
|
||||||
|
The library contents structures and methods for requesting to an user (cloudapi) and admin (cloudbroker) groups of API.
|
||||||
|
Also the library have structures for responses.
|
||||||
|
|
||||||
|
## Contents
|
||||||
|
|
||||||
|
- [Install](#install)
|
||||||
|
- [API List](#api-list)
|
||||||
|
- [Examples](#examples)
|
||||||
|
- [Examples2](#examples2)
|
||||||
|
|
||||||
|
## Install
|
||||||
|
|
||||||
|
```bash
|
||||||
|
go get -u github.com/rudecs/decort-sdk
|
||||||
|
```
|
||||||
|
|
||||||
|
## API List
|
||||||
|
|
||||||
|
## Examples
|
||||||
|
|
||||||
|
```go
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"context"
|
||||||
|
"fmt"
|
||||||
|
"log"
|
||||||
|
|
||||||
|
"github.com/rudecs/decort-sdk/config"
|
||||||
|
"github.com/rudecs/decort-sdk/pkg/cloudapi/kvmx86"
|
||||||
|
)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
cfg := config.Config{
|
||||||
|
AppID: "<APPID>",
|
||||||
|
AppSecret: "<APPSECRET>",
|
||||||
|
SSOURL: "https://sso.digitalenergy.online",
|
||||||
|
DecortURL: "https://mr4.digitalenergy.online",
|
||||||
|
Retries: 5,
|
||||||
|
}
|
||||||
|
client := decort.New(cfg)
|
||||||
|
req := kvmx86.CreateRequest{
|
||||||
|
RGID: 123,
|
||||||
|
Name: "compute",
|
||||||
|
CPU: 4,
|
||||||
|
RAM: 4096,
|
||||||
|
ImageID: 321,
|
||||||
|
}
|
||||||
|
|
||||||
|
res, err := client.KVMX86().Create(context.Background(), req)
|
||||||
|
if err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
fmt.Println(res)
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
## Examples2
|
||||||
17
client.go
17
client.go
@@ -15,31 +15,36 @@ import (
|
|||||||
"github.com/rudecs/decort-sdk/internal/client"
|
"github.com/rudecs/decort-sdk/internal/client"
|
||||||
)
|
)
|
||||||
|
|
||||||
type Client struct {
|
// HTTP-client for platform
|
||||||
|
type DecortClient struct {
|
||||||
decortURL string
|
decortURL string
|
||||||
client *http.Client
|
client *http.Client
|
||||||
}
|
}
|
||||||
|
|
||||||
func New(cfg config.Config) *Client {
|
// Сlient builder
|
||||||
|
func New(cfg config.Config) *DecortClient {
|
||||||
if cfg.Retries == 0 {
|
if cfg.Retries == 0 {
|
||||||
cfg.Retries = 5
|
cfg.Retries = 5
|
||||||
}
|
}
|
||||||
|
|
||||||
return &Client{
|
return &DecortClient{
|
||||||
decortURL: cfg.DecortURL,
|
decortURL: cfg.DecortURL,
|
||||||
client: client.NewHttpClient(cfg),
|
client: client.NewHttpClient(cfg),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (dc *Client) CloudApi() *cloudapi.CloudApi {
|
// CloudAPI builder
|
||||||
|
func (dc *DecortClient) CloudAPI() *cloudapi.CloudAPI {
|
||||||
return cloudapi.New(dc)
|
return cloudapi.New(dc)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (dc *Client) CloudBroker() *cloudbroker.CloudBroker {
|
// CloudBroker builder
|
||||||
|
func (dc *DecortClient) CloudBroker() *cloudbroker.CloudBroker {
|
||||||
return cloudbroker.New(dc)
|
return cloudbroker.New(dc)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (dc *Client) DecortApiCall(ctx context.Context, method, url string, params interface{}) ([]byte, error) {
|
// DecortApiCall method for sending requests to the platform
|
||||||
|
func (dc *DecortClient) DecortApiCall(ctx context.Context, method, url string, params interface{}) ([]byte, error) {
|
||||||
values, err := query.Values(params)
|
values, err := query.Values(params)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
|||||||
@@ -1,11 +1,39 @@
|
|||||||
package config
|
package config
|
||||||
|
|
||||||
|
// Configuration for creating request to platform
|
||||||
type Config struct {
|
type Config struct {
|
||||||
Token string
|
// JWT platform token
|
||||||
AppID string
|
// Required: false
|
||||||
AppSecret string
|
// Example: "qwqwdfwv68979we0q9bfv7e9sbvd89798qrwv97ff"
|
||||||
SSOURL string
|
Token string
|
||||||
DecortURL string
|
|
||||||
Retries uint64
|
// Application (client) identifier for authorization
|
||||||
|
// in the cloud platform controller in oauth2 mode.
|
||||||
|
// Required: true
|
||||||
|
// Example: "ewqfrvea7s890avw804389qwguf234h0otfi3w4eiu"
|
||||||
|
AppID string
|
||||||
|
|
||||||
|
// Application (client) secret code for authorization
|
||||||
|
// in the cloud platform controller in oauth2 mode.
|
||||||
|
// Example: "frvet09rvesfis0c9erv9fsov0vsdfi09ovds0f"
|
||||||
|
AppSecret string
|
||||||
|
|
||||||
|
// Platform authentication service address
|
||||||
|
// Required: true
|
||||||
|
// Example: "https://sso.digitalenergy.online"
|
||||||
|
SSOURL string
|
||||||
|
|
||||||
|
// The address of the platform on which the actions are planned
|
||||||
|
// Required: true
|
||||||
|
// Example: "https://mr4.digitalenergy.online"
|
||||||
|
DecortURL string
|
||||||
|
|
||||||
|
// Amount platform request attempts
|
||||||
|
// Default value: 5
|
||||||
|
// Required: false
|
||||||
|
Retries uint64
|
||||||
|
|
||||||
|
// Skip verify, true by default
|
||||||
|
// Required: false
|
||||||
SSLSkipVerify bool
|
SSLSkipVerify bool
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,6 +2,8 @@ package interfaces
|
|||||||
|
|
||||||
import "context"
|
import "context"
|
||||||
|
|
||||||
|
// Interface for sending requests to platform
|
||||||
type Caller interface {
|
type Caller interface {
|
||||||
|
// DecortApiCall method for sending requests to the platform
|
||||||
DecortApiCall(ctx context.Context, method, url string, params interface{}) ([]byte, error)
|
DecortApiCall(ctx context.Context, method, url string, params interface{}) ([]byte, error)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import (
|
|||||||
"github.com/rudecs/decort-sdk/pkg/cloudapi/account"
|
"github.com/rudecs/decort-sdk/pkg/cloudapi/account"
|
||||||
)
|
)
|
||||||
|
|
||||||
func (ca *CloudApi) Account() *account.Account {
|
// Accessing the Account method group
|
||||||
|
func (ca *CloudAPI) Account() *account.Account {
|
||||||
return account.New(ca.client)
|
return account.New(ca.client)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,13 +1,16 @@
|
|||||||
|
// API Actor API for managing account
|
||||||
package account
|
package account
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"github.com/rudecs/decort-sdk/interfaces"
|
"github.com/rudecs/decort-sdk/interfaces"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Structure for creating request to account
|
||||||
type Account struct {
|
type Account struct {
|
||||||
client interfaces.Caller
|
client interfaces.Caller
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Builder for account endpoints
|
||||||
func New(client interfaces.Caller) *Account {
|
func New(client interfaces.Caller) *Account {
|
||||||
return &Account{
|
return &Account{
|
||||||
client,
|
client,
|
||||||
|
|||||||
@@ -9,25 +9,34 @@ import (
|
|||||||
"github.com/rudecs/decort-sdk/internal/validators"
|
"github.com/rudecs/decort-sdk/internal/validators"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for adding permission to access to account for a user
|
||||||
type AddUserRequest struct {
|
type AddUserRequest struct {
|
||||||
AccountID uint64 `url:"accountId"`
|
// ID of account to add to
|
||||||
UserID string `url:"userId"`
|
// Required: true
|
||||||
|
AccountID uint64 `url:"accountId"`
|
||||||
|
|
||||||
|
// Name of the user to be given rights
|
||||||
|
// Required: true
|
||||||
|
UserID string `url:"userId"`
|
||||||
|
|
||||||
|
// Account permission types:
|
||||||
|
// - 'R' for read only access
|
||||||
|
// - 'RCX' for Write
|
||||||
|
// - 'ARCXDU' for Admin
|
||||||
|
// Required: true
|
||||||
AccessType string `url:"accesstype"`
|
AccessType string `url:"accesstype"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq AddUserRequest) Validate() error {
|
func (arq AddUserRequest) validate() error {
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if arq.UserID == "" {
|
if arq.UserID == "" {
|
||||||
return errors.New("validation-error: field UserID can not be empty")
|
return errors.New("validation-error: field UserID can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
if arq.AccessType == "" {
|
if arq.AccessType == "" {
|
||||||
return errors.New("validation-error: field AccessType can not be empty")
|
return errors.New("validation-error: field AccessType can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
isValid := validators.StringInSlice(arq.AccessType, []string{"R", "RCX", "ARCXDU"})
|
isValid := validators.StringInSlice(arq.AccessType, []string{"R", "RCX", "ARCXDU"})
|
||||||
if !isValid {
|
if !isValid {
|
||||||
return errors.New("validation-error: field AccessType can be only R, RCX or ARCXDU")
|
return errors.New("validation-error: field AccessType can be only R, RCX or ARCXDU")
|
||||||
@@ -36,8 +45,9 @@ func (arq AddUserRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// AddUser gives a user access rights.
|
||||||
func (a Account) AddUser(ctx context.Context, req AddUserRequest) (bool, error) {
|
func (a Account) AddUser(ctx context.Context, req AddUserRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for give list account audits
|
||||||
type AuditsRequest struct {
|
type AuditsRequest struct {
|
||||||
|
// ID of the account
|
||||||
|
// Required: true
|
||||||
AccountID uint64 `url:"accountId"`
|
AccountID uint64 `url:"accountId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq AuditsRequest) Validate() error {
|
func (arq AuditsRequest) validate() error {
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,25 +22,26 @@ func (arq AuditsRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (a Account) Audits(ctx context.Context, req AuditsRequest) (AccountAuditsList, error) {
|
// Audits gets audit records for the specified account object
|
||||||
err := req.Validate()
|
func (a Account) Audits(ctx context.Context, req AuditsRequest) (ListAudits, error) {
|
||||||
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/account/audits"
|
url := "/cloudapi/account/audits"
|
||||||
|
|
||||||
auditsRaw, err := a.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := a.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
audits := AccountAuditsList{}
|
list := ListAudits{}
|
||||||
|
|
||||||
err = json.Unmarshal(auditsRaw, &audits)
|
err = json.Unmarshal(res, &list)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return audits, nil
|
return list, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,35 +5,87 @@ import (
|
|||||||
"errors"
|
"errors"
|
||||||
"net/http"
|
"net/http"
|
||||||
"strconv"
|
"strconv"
|
||||||
|
|
||||||
|
"github.com/rudecs/decort-sdk/internal/validators"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for creating account
|
||||||
type CreateRequest struct {
|
type CreateRequest struct {
|
||||||
Name string `url:"name"`
|
// Display name
|
||||||
Username string `url:"username"`
|
// Required: true
|
||||||
EmailAddress string `url:"emailaddress,omitempty"`
|
Name string `url:"name"`
|
||||||
MaxMemoryCapacity uint64 `url:"maxMemoryCapacity,omitempty"`
|
|
||||||
MaxVDiskCapacity uint64 `url:"maxVDiskCapacity,omitempty"`
|
// Name of the account
|
||||||
MaxCPUCapacity uint64 `url:"maxCPUCapacity,omitempty"`
|
// Required: true
|
||||||
|
Username string `url:"username"`
|
||||||
|
|
||||||
|
// Email
|
||||||
|
// Required: false
|
||||||
|
EmailAddress string `url:"emailaddress,omitempty"`
|
||||||
|
|
||||||
|
// Max size of memory in MB
|
||||||
|
// Required: false
|
||||||
|
MaxMemoryCapacity uint64 `url:"maxMemoryCapacity,omitempty"`
|
||||||
|
|
||||||
|
// Max size of aggregated vdisks in GB
|
||||||
|
// Required: false
|
||||||
|
MaxVDiskCapacity uint64 `url:"maxVDiskCapacity,omitempty"`
|
||||||
|
|
||||||
|
// Max number of CPU cores
|
||||||
|
// Required: false
|
||||||
|
MaxCPUCapacity uint64 `url:"maxCPUCapacity,omitempty"`
|
||||||
|
|
||||||
|
// Max sent/received network transfer peering
|
||||||
|
// Required: false
|
||||||
MaxNetworkPeerTransfer uint64 `url:"maxNetworkPeerTransfer,omitempty"`
|
MaxNetworkPeerTransfer uint64 `url:"maxNetworkPeerTransfer,omitempty"`
|
||||||
MaxNumPublicIP uint64 `url:"maxNumPublicIP,omitempty"`
|
|
||||||
SendAccessEmails bool `url:"sendAccessEmails,omitempty"`
|
// Max number of assigned public IPs
|
||||||
GPUUnits uint64 `url:"gpu_units,omitempty"`
|
// Required: false
|
||||||
|
MaxNumPublicIP uint64 `url:"maxNumPublicIP,omitempty"`
|
||||||
|
|
||||||
|
// If true send emails when a user is granted access to resources
|
||||||
|
// Required: false
|
||||||
|
SendAccessEmails bool `url:"sendAccessEmails,omitempty"`
|
||||||
|
|
||||||
|
// Limit (positive) or disable (0) GPU resources
|
||||||
|
// Required: false
|
||||||
|
GPUUnits uint64 `url:"gpu_units,omitempty"`
|
||||||
|
|
||||||
|
// Resource types available to create in this account
|
||||||
|
// Each element in a resource type slice must be one of:
|
||||||
|
// - compute
|
||||||
|
// - vins
|
||||||
|
// - k8s
|
||||||
|
// - openshift
|
||||||
|
// - lb
|
||||||
|
// - flipgroup
|
||||||
|
// Required: false
|
||||||
|
ResTypes []string `url:"resourceTypes,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq CreateRequest) Validate() error {
|
func (arq CreateRequest) validate() error {
|
||||||
if arq.Name == "" {
|
if arq.Name == "" {
|
||||||
return errors.New("validation-error: field Name can not be empty")
|
return errors.New("validation-error: field Name can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
if arq.Username == "" {
|
if arq.Username == "" {
|
||||||
return errors.New("validation-error: field Username can not be empty")
|
return errors.New("validation-error: field Username can not be empty")
|
||||||
}
|
}
|
||||||
|
if len(arq.ResTypes) > 0 {
|
||||||
|
for _, value := range arq.ResTypes {
|
||||||
|
validate := validators.StringInSlice(value, []string{"compute", "vins", "k8s", "openshift", "lb", "flipgroup"})
|
||||||
|
if !validate {
|
||||||
|
return errors.New("validation-error: Every resource type specified should be one of [compute, vins, k8s, openshift, lb, flipgroup]")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Create creates account
|
||||||
|
// Setting a cloud unit maximum to -1 or empty will not put any restrictions on the resource
|
||||||
func (a Account) Create(ctx context.Context, req CreateRequest) (uint64, error) {
|
func (a Account) Create(ctx context.Context, req CreateRequest) (uint64, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return 0, err
|
return 0, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -6,21 +6,27 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for delete account
|
||||||
type DeleteRequest struct {
|
type DeleteRequest struct {
|
||||||
AccountID uint64 `url:"accountId"`
|
// ID of account to delete
|
||||||
Permanently bool `url:"permanently,omitempty"`
|
// Required: true
|
||||||
|
AccountID uint64 `url:"accountId"`
|
||||||
|
|
||||||
|
// Whether to completely delete the account
|
||||||
|
// Required: false
|
||||||
|
Permanently bool `url:"permanently,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq DeleteRequest) Validate() error {
|
func (arq DeleteRequest) validate() error {
|
||||||
|
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID must be set")
|
return errors.New("validation-error: field AccountID must be set")
|
||||||
}
|
}
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Delete completes delete an account from the system Returns true if account is deleted or was already deleted or never existed
|
||||||
func (a Account) Delete(ctx context.Context, req DeleteRequest) (bool, error) {
|
func (a Account) Delete(ctx context.Context, req DeleteRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,17 +7,25 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for revoke access to account
|
||||||
type DeleteUserRequest struct {
|
type DeleteUserRequest struct {
|
||||||
AccountID uint64 `url:"accountId"`
|
// ID of the account
|
||||||
UserID string `url:"userId"`
|
// Required: true
|
||||||
RecursiveDelete bool `url:"recursivedelete,omitempty"`
|
AccountID uint64 `url:"accountId"`
|
||||||
|
|
||||||
|
// ID or emailaddress of the user to remove
|
||||||
|
// Required: true
|
||||||
|
UserID string `url:"userId"`
|
||||||
|
|
||||||
|
// Recursively revoke access rights from owned cloudspaces and vmachines
|
||||||
|
// Required: false
|
||||||
|
RecursiveDelete bool `url:"recursivedelete,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq DeleteUserRequest) Validate() error {
|
func (arq DeleteUserRequest) validate() error {
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if arq.UserID == "" {
|
if arq.UserID == "" {
|
||||||
return errors.New("validation-error: field UserID can not be empty")
|
return errors.New("validation-error: field UserID can not be empty")
|
||||||
}
|
}
|
||||||
@@ -25,8 +33,9 @@ func (arq DeleteUserRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DeleteUser revokes user access from the account
|
||||||
func (a Account) DeleteUser(ctx context.Context, req DeleteUserRequest) (bool, error) {
|
func (a Account) DeleteUser(ctx context.Context, req DeleteUserRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for change status of account
|
||||||
type DisabelEnableRequest struct {
|
type DisabelEnableRequest struct {
|
||||||
|
// ID of account
|
||||||
|
// Required: true
|
||||||
AccountID uint64 `url:"accountId"`
|
AccountID uint64 `url:"accountId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq DisabelEnableRequest) Validate() error {
|
func (arq DisabelEnableRequest) validate() error {
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (arq DisabelEnableRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Disable disables an account
|
||||||
func (a Account) Disable(ctx context.Context, req DisabelEnableRequest) (bool, error) {
|
func (a Account) Disable(ctx context.Context, req DisabelEnableRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
@@ -40,8 +44,9 @@ func (a Account) Disable(ctx context.Context, req DisabelEnableRequest) (bool, e
|
|||||||
return result, nil
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Enable enables an account
|
||||||
func (a Account) Enable(ctx context.Context, req DisabelEnableRequest) (bool, error) {
|
func (a Account) Enable(ctx context.Context, req DisabelEnableRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get information about account
|
||||||
type GetRequest struct {
|
type GetRequest struct {
|
||||||
|
// ID an account
|
||||||
|
// Required: true
|
||||||
AccountID uint64 `url:"accountId"`
|
AccountID uint64 `url:"accountId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq GetRequest) Validate() error {
|
func (arq GetRequest) validate() error {
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (arq GetRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (a Account) Get(ctx context.Context, req GetRequest) (*AccountWithResources, error) {
|
// Get gets account details
|
||||||
err := req.Validate()
|
func (a Account) Get(ctx context.Context, req GetRequest) (*RecordAccount, error) {
|
||||||
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@@ -32,13 +36,13 @@ func (a Account) Get(ctx context.Context, req GetRequest) (*AccountWithResources
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
account := &AccountWithResources{}
|
info := RecordAccount{}
|
||||||
|
|
||||||
err = json.Unmarshal(res, &account)
|
err = json.Unmarshal(res, &info)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return account, nil
|
return &info, nil
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for calculate the currently consumed units for all cloudspaces and resource groups in the account
|
||||||
type GetConsumedAccountUnitsRequest struct {
|
type GetConsumedAccountUnitsRequest struct {
|
||||||
|
// ID an account
|
||||||
|
// Required: true
|
||||||
AccountID uint64 `url:"accountId"`
|
AccountID uint64 `url:"accountId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq GetConsumedAccountUnitsRequest) Validate() error {
|
func (arq GetConsumedAccountUnitsRequest) validate() error {
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,14 @@ func (arq GetConsumedAccountUnitsRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GetConsumedAccountUnits calculates the currently consumed units for all cloudspaces and resource groups in the account.
|
||||||
|
// Calculated cloud units are returned in a dict which includes:
|
||||||
|
// - CU_M: consumed memory in MB
|
||||||
|
// - CU_C: number of cpu cores
|
||||||
|
// - CU_D: consumed vdisk storage in GB
|
||||||
|
// - CU_I: number of public IPs
|
||||||
func (a Account) GetConsumedAccountUnits(ctx context.Context, req GetConsumedAccountUnitsRequest) (*ResourceLimits, error) {
|
func (a Account) GetConsumedAccountUnits(ctx context.Context, req GetConsumedAccountUnitsRequest) (*ResourceLimits, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@@ -32,13 +41,12 @@ func (a Account) GetConsumedAccountUnits(ctx context.Context, req GetConsumedAcc
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
rl := &ResourceLimits{}
|
info := ResourceLimits{}
|
||||||
|
|
||||||
err = json.Unmarshal(res, &rl)
|
err = json.Unmarshal(res, &info)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return rl, nil
|
return &info, nil
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -9,20 +9,24 @@ import (
|
|||||||
"github.com/rudecs/decort-sdk/internal/validators"
|
"github.com/rudecs/decort-sdk/internal/validators"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for calculate the currently consumed cloud units of the specified type for all cloudspaces and resource groups in the account
|
||||||
type GetConsumedCloudUnitsByTypeRequest struct {
|
type GetConsumedCloudUnitsByTypeRequest struct {
|
||||||
|
// ID an account
|
||||||
|
// Required: true
|
||||||
AccountID uint64 `url:"accountId"`
|
AccountID uint64 `url:"accountId"`
|
||||||
CUType string `url:"cutype"`
|
|
||||||
|
// Cloud unit resource type
|
||||||
|
// Required: true
|
||||||
|
CUType string `url:"cutype"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq GetConsumedCloudUnitsByTypeRequest) Validate() error {
|
func (arq GetConsumedCloudUnitsByTypeRequest) validate() error {
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if arq.CUType == "" {
|
if arq.CUType == "" {
|
||||||
return errors.New("validation-error: field CUType can not be empty")
|
return errors.New("validation-error: field CUType can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
isValid := validators.StringInSlice(arq.CUType, []string{"CU_M", "CU_C", "CU_D", "CU_S", "CU_A", "CU_NO", "CU_I", "CU_NP"})
|
isValid := validators.StringInSlice(arq.CUType, []string{"CU_M", "CU_C", "CU_D", "CU_S", "CU_A", "CU_NO", "CU_I", "CU_NP"})
|
||||||
if !isValid {
|
if !isValid {
|
||||||
return errors.New("validation-error: field AccessType can be only CU_M, CU_C, CU_D, CU_S, CU_A, CU_NO, CU_I or CU_NP")
|
return errors.New("validation-error: field AccessType can be only CU_M, CU_C, CU_D, CU_S, CU_A, CU_NO, CU_I or CU_NP")
|
||||||
@@ -31,8 +35,20 @@ func (arq GetConsumedCloudUnitsByTypeRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GetConsumedCloudUnitsByType calculates the currently consumed cloud units of the specified type for all cloudspaces
|
||||||
|
// and resource groups in the account.
|
||||||
|
// Possible types of cloud units are include:
|
||||||
|
//
|
||||||
|
// - CU_M: returns consumed memory in MB
|
||||||
|
// - CU_C: returns number of virtual cpu cores
|
||||||
|
// - CU_D: returns consumed virtual disk storage in GB
|
||||||
|
// - CU_S: returns consumed primary storage (NAS) in TB
|
||||||
|
// - CU_A: returns consumed secondary storage (Archive) in TB
|
||||||
|
// - CU_NO: returns sent/received network transfer in operator in GB
|
||||||
|
// - CU_NP: returns sent/received network transfer peering in GB
|
||||||
|
// - CU_I: returns number of public IPs
|
||||||
func (a Account) GetConsumedCloudUnitsByType(ctx context.Context, req GetConsumedCloudUnitsByTypeRequest) (float64, error) {
|
func (a Account) GetConsumedCloudUnitsByType(ctx context.Context, req GetConsumedCloudUnitsByTypeRequest) (float64, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return 0, err
|
return 0, err
|
||||||
}
|
}
|
||||||
@@ -50,5 +66,4 @@ func (a Account) GetConsumedCloudUnitsByType(ctx context.Context, req GetConsume
|
|||||||
}
|
}
|
||||||
|
|
||||||
return result, nil
|
return result, nil
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -6,21 +6,28 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for download the resources tracking files for an account
|
||||||
type GetConsumtionRequest struct {
|
type GetConsumtionRequest struct {
|
||||||
|
// ID an account
|
||||||
|
// Required: true
|
||||||
AccountID uint64 `url:"accountId"`
|
AccountID uint64 `url:"accountId"`
|
||||||
Start uint64 `url:"start"`
|
|
||||||
End uint64 `url:"end"`
|
// Epoch represents the start time
|
||||||
|
// Required: true
|
||||||
|
Start uint64 `url:"start"`
|
||||||
|
|
||||||
|
// Epoch represents the end time
|
||||||
|
// Required: true
|
||||||
|
End uint64 `url:"end"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq GetConsumtionRequest) Validate() error {
|
func (arq GetConsumtionRequest) validate() error {
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if arq.Start == 0 {
|
if arq.Start == 0 {
|
||||||
return errors.New("validation-error: field Start can not be empty or equal to 0")
|
return errors.New("validation-error: field Start can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if arq.End == 0 {
|
if arq.End == 0 {
|
||||||
return errors.New("validation-error: field End can not be empty or equal to 0")
|
return errors.New("validation-error: field End can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -28,8 +35,9 @@ func (arq GetConsumtionRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GetConsumtion downloads the resources tracking files for an account within a given period
|
||||||
func (a Account) GetConsumtion(ctx context.Context, req GetConsumtionRequest) (string, error) {
|
func (a Account) GetConsumtion(ctx context.Context, req GetConsumtionRequest) (string, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return "", err
|
return "", err
|
||||||
}
|
}
|
||||||
@@ -45,21 +53,19 @@ func (a Account) GetConsumtion(ctx context.Context, req GetConsumtionRequest) (s
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GetConsumtionGet downloads the resources tracking files for an account within a given period
|
||||||
func (a Account) GetConsumtionGet(ctx context.Context, req GetConsumtionRequest) (string, error) {
|
func (a Account) GetConsumtionGet(ctx context.Context, req GetConsumtionRequest) (string, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return "", err
|
return "", err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/account/getConsumtion"
|
url := "/cloudapi//account/getConsumtion"
|
||||||
prefix := "/cloudapi"
|
|
||||||
|
|
||||||
url = prefix + url
|
|
||||||
res, err := a.client.DecortApiCall(ctx, http.MethodGet, url, req)
|
res, err := a.client.DecortApiCall(ctx, http.MethodGet, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return "", err
|
return "", err
|
||||||
}
|
}
|
||||||
|
|
||||||
return string(res), nil
|
return string(res), nil
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for calculate the reserved units for all cloudspaces and resource groups in the account
|
||||||
type GetReservedAccountUnitsRequest struct {
|
type GetReservedAccountUnitsRequest struct {
|
||||||
|
// ID an account
|
||||||
|
// Required: true
|
||||||
AccountID uint64 `url:"accountId"`
|
AccountID uint64 `url:"accountId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq GetReservedAccountUnitsRequest) Validate() error {
|
func (arq GetReservedAccountUnitsRequest) validate() error {
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,15 @@ func (arq GetReservedAccountUnitsRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GetReservedAccountUnits calculates the reserved units for all cloudspaces and resource groups in the account.
|
||||||
|
// Calculated cloud units are returned in a dict which includes:
|
||||||
|
//
|
||||||
|
// - CU_M: reserved memory in MB
|
||||||
|
// - CU_C: number of cpu cores
|
||||||
|
// - CU_D: reserved vdisk storage in GB
|
||||||
|
// - CU_I: number of public IPs
|
||||||
func (a Account) GetReservedAccountUnits(ctx context.Context, req GetReservedAccountUnitsRequest) (*ResourceLimits, error) {
|
func (a Account) GetReservedAccountUnits(ctx context.Context, req GetReservedAccountUnitsRequest) (*ResourceLimits, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@@ -32,13 +42,12 @@ func (a Account) GetReservedAccountUnits(ctx context.Context, req GetReservedAcc
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
rl := &ResourceLimits{}
|
info := ResourceLimits{}
|
||||||
|
|
||||||
err = json.Unmarshal(res, &rl)
|
err = json.Unmarshal(res, &info)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return rl, nil
|
return &info, nil
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -6,12 +6,19 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get list of accounts
|
||||||
type ListRequest struct {
|
type ListRequest struct {
|
||||||
|
// Page number
|
||||||
|
// Required: false
|
||||||
Page uint64 `url:"page"`
|
Page uint64 `url:"page"`
|
||||||
|
|
||||||
|
// Page size
|
||||||
|
// Required: false
|
||||||
Size uint64 `url:"size"`
|
Size uint64 `url:"size"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (a Account) List(ctx context.Context, req ListRequest) (AccountCloudApiList, error) {
|
// List gets list all accounts the user has access to
|
||||||
|
func (a Account) List(ctx context.Context, req ListRequest) (ListAccounts, error) {
|
||||||
url := "/cloudapi/account/list"
|
url := "/cloudapi/account/list"
|
||||||
|
|
||||||
res, err := a.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := a.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
@@ -19,13 +26,12 @@ func (a Account) List(ctx context.Context, req ListRequest) (AccountCloudApiList
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
accountList := AccountCloudApiList{}
|
list := ListAccounts{}
|
||||||
|
|
||||||
err = json.Unmarshal(res, &accountList)
|
err = json.Unmarshal(res, &list)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return accountList, nil
|
return list, nil
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for a get list compute instances
|
||||||
type ListComputesRequest struct {
|
type ListComputesRequest struct {
|
||||||
|
// ID an account
|
||||||
|
// Required: true
|
||||||
AccountID uint64 `url:"accountId"`
|
AccountID uint64 `url:"accountId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq ListComputesRequest) Validate() error {
|
func (arq ListComputesRequest) validate() error {
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (arq ListComputesRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (a Account) ListComputes(ctx context.Context, req ListComputesRequest) (AccountComputesList, error) {
|
// ListComputes gets list all compute instances under specified account, accessible by the user
|
||||||
err := req.Validate()
|
func (a Account) ListComputes(ctx context.Context, req ListComputesRequest) (ListComputes, error) {
|
||||||
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@@ -32,13 +36,12 @@ func (a Account) ListComputes(ctx context.Context, req ListComputesRequest) (Acc
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
accountComputesList := AccountComputesList{}
|
list := ListComputes{}
|
||||||
|
|
||||||
err = json.Unmarshal(res, &accountComputesList)
|
err = json.Unmarshal(res, &list)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return accountComputesList, nil
|
return list, nil
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -6,12 +6,19 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get list deleted accounts
|
||||||
type ListDeletedRequest struct {
|
type ListDeletedRequest struct {
|
||||||
|
// Page number
|
||||||
|
// Required: false
|
||||||
Page uint64 `url:"page"`
|
Page uint64 `url:"page"`
|
||||||
|
|
||||||
|
// Page size
|
||||||
|
// Required: false
|
||||||
Size uint64 `url:"size"`
|
Size uint64 `url:"size"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (a Account) ListDeleted(ctx context.Context, req ListDeletedRequest) (AccountCloudApiList, error) {
|
// ListDeleted gets list all deleted accounts the user has access to
|
||||||
|
func (a Account) ListDeleted(ctx context.Context, req ListDeletedRequest) (ListAccounts, error) {
|
||||||
url := "/cloudapi/account/listDeleted"
|
url := "/cloudapi/account/listDeleted"
|
||||||
|
|
||||||
res, err := a.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := a.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
@@ -19,13 +26,12 @@ func (a Account) ListDeleted(ctx context.Context, req ListDeletedRequest) (Accou
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
accountList := AccountCloudApiList{}
|
list := ListAccounts{}
|
||||||
|
|
||||||
err = json.Unmarshal(res, &accountList)
|
err = json.Unmarshal(res, &list)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return accountList, nil
|
return list, nil
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get list deleted disks
|
||||||
type ListDisksRequest struct {
|
type ListDisksRequest struct {
|
||||||
|
// ID an account
|
||||||
|
// Required: true
|
||||||
AccountID uint64 `url:"accountId"`
|
AccountID uint64 `url:"accountId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq ListDisksRequest) Validate() error {
|
func (arq ListDisksRequest) validate() error {
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (arq ListDisksRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (a Account) ListDisks(ctx context.Context, req ListDisksRequest) (AccountDisksList, error) {
|
// ListDisks gets list all currently unattached disks under specified account
|
||||||
err := req.Validate()
|
func (a Account) ListDisks(ctx context.Context, req ListDisksRequest) (ListDisks, error) {
|
||||||
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@@ -32,13 +36,12 @@ func (a Account) ListDisks(ctx context.Context, req ListDisksRequest) (AccountDi
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
accountDisksList := AccountDisksList{}
|
list := ListDisks{}
|
||||||
|
|
||||||
err = json.Unmarshal(res, &accountDisksList)
|
err = json.Unmarshal(res, &list)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return accountDisksList, nil
|
return list, nil
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
type ListFlipGroupsRequest struct {
|
// Request struct for get list FLIPGroups
|
||||||
|
type ListFLIPGroupsRequest struct {
|
||||||
|
// ID an account
|
||||||
|
// Required: true
|
||||||
AccountID uint64 `url:"accountId"`
|
AccountID uint64 `url:"accountId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq ListFlipGroupsRequest) Validate() error {
|
func (arq ListFLIPGroupsRequest) validate() error {
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (arq ListFlipGroupsRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (a Account) ListFlipGroups(ctx context.Context, req ListFlipGroupsRequest) (AccountFlipGroupsList, error) {
|
// ListFLIPGroups gets list all FLIPGroups under specified account, accessible by the user
|
||||||
err := req.Validate()
|
func (a Account) ListFLIPGroups(ctx context.Context, req ListFLIPGroupsRequest) (ListFLIPGroups, error) {
|
||||||
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@@ -32,13 +36,12 @@ func (a Account) ListFlipGroups(ctx context.Context, req ListFlipGroupsRequest)
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
accountFlipGroupsList := AccountFlipGroupsList{}
|
list := ListFLIPGroups{}
|
||||||
|
|
||||||
err = json.Unmarshal(res, &accountFlipGroupsList)
|
err = json.Unmarshal(res, &list)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return accountFlipGroupsList, nil
|
return list, nil
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get list resource groups
|
||||||
type ListRGRequest struct {
|
type ListRGRequest struct {
|
||||||
|
// ID an account
|
||||||
|
// Required: true
|
||||||
AccountID uint64 `url:"accountId"`
|
AccountID uint64 `url:"accountId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq ListRGRequest) Validate() error {
|
func (arq ListRGRequest) validate() error {
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (arq ListRGRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (a Account) ListRG(ctx context.Context, req ListRGRequest) (AccountRGList, error) {
|
// ListRG gets list all resource groups under specified account, accessible by the user
|
||||||
err := req.Validate()
|
func (a Account) ListRG(ctx context.Context, req ListRGRequest) (ListRG, error) {
|
||||||
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@@ -32,13 +36,12 @@ func (a Account) ListRG(ctx context.Context, req ListRGRequest) (AccountRGList,
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
accountRGList := AccountRGList{}
|
list := ListRG{}
|
||||||
|
|
||||||
err = json.Unmarshal(res, &accountRGList)
|
err = json.Unmarshal(res, &list)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return accountRGList, nil
|
return list, nil
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,12 +7,18 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get list templates
|
||||||
type ListTemplatesRequest struct {
|
type ListTemplatesRequest struct {
|
||||||
AccountID uint64 `url:"accountId"`
|
// ID an account
|
||||||
IncludeDeleted bool `url:"includedeleted"`
|
// Required: true
|
||||||
|
AccountID uint64 `url:"accountId"`
|
||||||
|
|
||||||
|
// Include deleted images
|
||||||
|
// Required: false
|
||||||
|
IncludeDeleted bool `url:"includedeleted"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq ListTemplatesRequest) Validate() error {
|
func (arq ListTemplatesRequest) validate() error {
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -20,8 +26,9 @@ func (arq ListTemplatesRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (a Account) ListTemplates(ctx context.Context, req ListTemplatesRequest) (AccountTemplatesList, error) {
|
// ListTemplates gets list templates which can be managed by this account
|
||||||
err := req.Validate()
|
func (a Account) ListTemplates(ctx context.Context, req ListTemplatesRequest) (ListTemplates, error) {
|
||||||
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@@ -33,13 +40,12 @@ func (a Account) ListTemplates(ctx context.Context, req ListTemplatesRequest) (A
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
accountTemplatesList := AccountTemplatesList{}
|
list := ListTemplates{}
|
||||||
|
|
||||||
err = json.Unmarshal(res, &accountTemplatesList)
|
err = json.Unmarshal(res, &list)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return accountTemplatesList, nil
|
return list, nil
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get list VINS
|
||||||
type ListVINSRequest struct {
|
type ListVINSRequest struct {
|
||||||
|
// ID an account
|
||||||
|
// Required: true
|
||||||
AccountID uint64 `url:"accountId"`
|
AccountID uint64 `url:"accountId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq ListVINSRequest) Validate() error {
|
func (arq ListVINSRequest) validate() error {
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (arq ListVINSRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (a Account) ListVINS(ctx context.Context, req ListVINSRequest) (AccountVINSList, error) {
|
// ListVINS gets list all ViNSes under specified account, accessible by the user
|
||||||
err := req.Validate()
|
func (a Account) ListVINS(ctx context.Context, req ListVINSRequest) (ListVINS, error) {
|
||||||
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@@ -32,13 +36,12 @@ func (a Account) ListVINS(ctx context.Context, req ListVINSRequest) (AccountVINS
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
accountVINSList := AccountVINSList{}
|
list := ListVINS{}
|
||||||
|
|
||||||
err = json.Unmarshal(res, &accountVINSList)
|
err = json.Unmarshal(res, &list)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return accountVINSList, nil
|
return list, nil
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,229 +1,547 @@
|
|||||||
package account
|
package account
|
||||||
|
|
||||||
type AccountACLRecord struct {
|
// Access Control List
|
||||||
IsExplicit bool `json:"explicit"`
|
type RecordACL struct {
|
||||||
GUID string `json:"guid"`
|
// Whether access is explicitly specified
|
||||||
Rights string `json:"right"`
|
IsExplicit bool `json:"explicit"`
|
||||||
Status string `json:"status"`
|
|
||||||
Type string `json:"type"`
|
// GUID
|
||||||
UgroupID string `json:"userGroupId"`
|
GUID string `json:"guid"`
|
||||||
CanBeDeleted bool `json:"canBeDeleted"`
|
|
||||||
|
// Access rights
|
||||||
|
Rights string `json:"right"`
|
||||||
|
|
||||||
|
// Status
|
||||||
|
Status string `json:"status"`
|
||||||
|
|
||||||
|
// Account Type
|
||||||
|
Type string `json:"type"`
|
||||||
|
|
||||||
|
// Account owner ID
|
||||||
|
UgroupID string `json:"userGroupId"`
|
||||||
|
|
||||||
|
// Is it possible to remove
|
||||||
|
CanBeDeleted bool `json:"canBeDeleted"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Resource limits
|
||||||
type ResourceLimits struct {
|
type ResourceLimits struct {
|
||||||
CUC float64 `json:"CU_C"`
|
// Number of cores
|
||||||
CUD float64 `json:"CU_D"`
|
CUC float64 `json:"CU_C"`
|
||||||
CUI float64 `json:"CU_I"`
|
|
||||||
CUM float64 `json:"CU_M"`
|
// Disk size, GB
|
||||||
CUNP float64 `json:"CU_NP"`
|
CUD float64 `json:"CU_D"`
|
||||||
|
|
||||||
|
// Number of public IP addresses
|
||||||
|
CUI float64 `json:"CU_I"`
|
||||||
|
|
||||||
|
// RAM size, MB
|
||||||
|
CUM float64 `json:"CU_M"`
|
||||||
|
|
||||||
|
// Traffic volume, GB
|
||||||
|
CUNP float64 `json:"CU_NP"`
|
||||||
|
|
||||||
|
// Number of graphics cores
|
||||||
GPUUnits float64 `json:"gpu_units"`
|
GPUUnits float64 `json:"gpu_units"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type AccountRecord struct {
|
// Main information of account
|
||||||
DCLocation string `json:"DCLocation"`
|
type InfoAccount struct {
|
||||||
CKey string `jspn:"_ckey"`
|
// Segment
|
||||||
Meta []interface{} `json:"_meta"`
|
DCLocation string `json:"DCLocation"`
|
||||||
ACL []AccountACLRecord `json:"acl"`
|
|
||||||
Company string `json:"company"`
|
// Key
|
||||||
CompanyURL string `json:"companyurl"`
|
CKey string `jspn:"_ckey"`
|
||||||
CreatedBy string `jspn:"createdBy"`
|
|
||||||
CreatedTime uint64 `json:"createdTime"`
|
// Meta
|
||||||
DeactiovationTime float64 `json:"deactivationTime"`
|
Meta []interface{} `json:"_meta"`
|
||||||
DeletedBy string `json:"deletedBy"`
|
|
||||||
DeletedTime uint64 `json:"deletedTime"`
|
// Access Control List
|
||||||
DisplayName string `json:"displayname"`
|
ACL []RecordACL `json:"acl"`
|
||||||
GUID uint64 `json:"guid"`
|
|
||||||
ID uint64 `json:"id"`
|
// Company
|
||||||
Name string `json:"name"`
|
Company string `json:"company"`
|
||||||
ResourceLimits ResourceLimits `json:"resourceLimits"`
|
|
||||||
SendAccessEmails bool `json:"sendAccessEmails"`
|
// Company URL
|
||||||
ServiceAccount bool `json:"serviceAccount"`
|
CompanyURL string `json:"companyurl"`
|
||||||
Status string `json:"status"`
|
|
||||||
UpdatedTime uint64 `json:"updatedTime"`
|
// Created by
|
||||||
Version uint64 `json:"version"`
|
CreatedBy string `jspn:"createdBy"`
|
||||||
VINS []uint64 `json:"vins"`
|
|
||||||
|
// Created time
|
||||||
|
CreatedTime uint64 `json:"createdTime"`
|
||||||
|
|
||||||
|
// Deactiovation time
|
||||||
|
DeactiovationTime float64 `json:"deactivationTime"`
|
||||||
|
|
||||||
|
// Deleted by
|
||||||
|
DeletedBy string `json:"deletedBy"`
|
||||||
|
|
||||||
|
// Deleted time
|
||||||
|
DeletedTime uint64 `json:"deletedTime"`
|
||||||
|
|
||||||
|
// Display name
|
||||||
|
DisplayName string `json:"displayname"`
|
||||||
|
|
||||||
|
// GUID
|
||||||
|
GUID uint64 `json:"guid"`
|
||||||
|
|
||||||
|
// ID
|
||||||
|
ID uint64 `json:"id"`
|
||||||
|
|
||||||
|
// Name
|
||||||
|
Name string `json:"name"`
|
||||||
|
|
||||||
|
// Resource Limits
|
||||||
|
ResourceLimits ResourceLimits `json:"resourceLimits"`
|
||||||
|
|
||||||
|
// If true send emails when a user is granted access to resources
|
||||||
|
SendAccessEmails bool `json:"sendAccessEmails"`
|
||||||
|
|
||||||
|
// Service Account
|
||||||
|
ServiceAccount bool `json:"serviceAccount"`
|
||||||
|
|
||||||
|
// Status
|
||||||
|
Status string `json:"status"`
|
||||||
|
|
||||||
|
// Updated time
|
||||||
|
UpdatedTime uint64 `json:"updatedTime"`
|
||||||
|
|
||||||
|
// Version
|
||||||
|
Version uint64 `json:"version"`
|
||||||
|
|
||||||
|
// List VINS in account
|
||||||
|
VINS []uint64 `json:"vins"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type AccountList []AccountRecord
|
// Main information in one of if the list of accounts
|
||||||
|
type ItemAccount struct {
|
||||||
|
// Access Control List
|
||||||
|
ACL []RecordACL `json:"acl"`
|
||||||
|
|
||||||
type AccountCloudApi struct {
|
// Created time
|
||||||
ACL []AccountACLRecord `json:"acl"`
|
CreatedTime uint64 `json:"createdTime"`
|
||||||
CreatedTime uint64 `json:"createdTime"`
|
|
||||||
DeletedTime uint64 `json:"deletedTime"`
|
// Deleted time
|
||||||
ID uint64 `json:"id"`
|
DeletedTime uint64 `json:"deletedTime"`
|
||||||
Name string `json:"name"`
|
|
||||||
Status string `json:"status"`
|
// ID
|
||||||
UpdatedTime uint64 `json:"updatedTime"`
|
ID uint64 `json:"id"`
|
||||||
|
|
||||||
|
// Name
|
||||||
|
Name string `json:"name"`
|
||||||
|
|
||||||
|
// Status
|
||||||
|
Status string `json:"status"`
|
||||||
|
|
||||||
|
// Updated time
|
||||||
|
UpdatedTime uint64 `json:"updatedTime"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type AccountCloudApiList []AccountCloudApi
|
// List of accounts
|
||||||
|
type ListAccounts []ItemAccount
|
||||||
|
|
||||||
|
// Resources used
|
||||||
type Resource struct {
|
type Resource struct {
|
||||||
CPU int64 `json:"cpu"`
|
// Number of cores
|
||||||
DiskSize int64 `json:"disksize"`
|
CPU int64 `json:"cpu"`
|
||||||
ExtIPs int64 `json:"extips"`
|
|
||||||
|
// Disk size
|
||||||
|
DiskSize int64 `json:"disksize"`
|
||||||
|
|
||||||
|
// Number of External IPs
|
||||||
|
ExtIPs int64 `json:"extips"`
|
||||||
|
|
||||||
|
// External traffic
|
||||||
ExtTraffic int64 `json:"exttraffic"`
|
ExtTraffic int64 `json:"exttraffic"`
|
||||||
GPU int64 `json:"gpu"`
|
|
||||||
RAM int64 `json:"ram"`
|
// Number of grafic cores
|
||||||
|
GPU int64 `json:"gpu"`
|
||||||
|
|
||||||
|
// Number of RAM
|
||||||
|
RAM int64 `json:"ram"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Information about resources
|
||||||
type Resources struct {
|
type Resources struct {
|
||||||
Current Resource `json:"Current"`
|
// Current information about resources
|
||||||
|
Current Resource `json:"Current"`
|
||||||
|
|
||||||
|
// Reserved information about resources
|
||||||
Reserved Resource `json:"Reserved"`
|
Reserved Resource `json:"Reserved"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Information about computes
|
||||||
type Computes struct {
|
type Computes struct {
|
||||||
|
// Number of started computes
|
||||||
Started uint64 `json:"started"`
|
Started uint64 `json:"started"`
|
||||||
|
|
||||||
|
// Number of stopped computes
|
||||||
Stopped uint64 `json:"stopped"`
|
Stopped uint64 `json:"stopped"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Information about machines
|
||||||
type Machines struct {
|
type Machines struct {
|
||||||
|
// Number of running machines
|
||||||
Running uint64 `json:"running"`
|
Running uint64 `json:"running"`
|
||||||
Halted uint64 `json:"halted"`
|
|
||||||
|
// Number of halted machines
|
||||||
|
Halted uint64 `json:"halted"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type AccountWithResources struct {
|
// Сomplete information about account
|
||||||
Account
|
type RecordAccount struct {
|
||||||
|
// Main information about account
|
||||||
|
InfoAccount
|
||||||
|
|
||||||
|
// Resources
|
||||||
Resources Resources `json:"Resources"`
|
Resources Resources `json:"Resources"`
|
||||||
Computes Computes `json:"computes"`
|
|
||||||
Machines Machines `json:"machines"`
|
// Computes
|
||||||
VINSes uint64 `json:"vinses"`
|
Computes Computes `json:"computes"`
|
||||||
|
|
||||||
|
// Machines
|
||||||
|
Machines Machines `json:"machines"`
|
||||||
|
|
||||||
|
// Number of VINSes
|
||||||
|
VINSes uint64 `json:"vinses"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type AccountCompute struct {
|
// Main information about compute
|
||||||
AccountID uint64 `json:"accountId"`
|
type ItemCompute struct {
|
||||||
AccountName string `json:"accountName"`
|
// ID an account
|
||||||
CPUs uint64 `json:"cpus"`
|
AccountID uint64 `json:"accountId"`
|
||||||
CreatedBy string `json:"createdBy"`
|
|
||||||
CreatedTime uint64 `json:"createdTime"`
|
|
||||||
DeletedBy string `json:"deletedBy"`
|
|
||||||
DeletedTime uint64 `json:"deletedTime"`
|
|
||||||
ComputeID uint64 `json:"id"`
|
|
||||||
ComputeName string `json:"name"`
|
|
||||||
RAM uint64 `json:"ram"`
|
|
||||||
Registered bool `json:"registered"`
|
|
||||||
RGID uint64 `json:"rgId"`
|
|
||||||
RGName string `json:"rgName"`
|
|
||||||
Status string `json:"status"`
|
|
||||||
TechStatus string `json:"techStatus"`
|
|
||||||
TotalDisksSize uint64 `json:"totalDisksSize"`
|
|
||||||
UpdatedBy string `json:"updatedBy"`
|
|
||||||
UpdatedTime uint64 `json:"updatedTime"`
|
|
||||||
UserManaged bool `json:"userManaged"`
|
|
||||||
VINSConnected uint64 `json:"vinsConnected"`
|
|
||||||
}
|
|
||||||
|
|
||||||
type AccountComputesList []AccountCompute
|
// Account name
|
||||||
|
|
||||||
type AccountDisk struct {
|
|
||||||
ID uint64 `json:"id"`
|
|
||||||
Name string `json:"name"`
|
|
||||||
Pool string `json:"pool"`
|
|
||||||
SepID uint64 `json:"sepId"`
|
|
||||||
SizeMax uint64 `json:"sizeMax"`
|
|
||||||
Type string `json:"type"`
|
|
||||||
}
|
|
||||||
|
|
||||||
type AccountDisksList []AccountDisk
|
|
||||||
|
|
||||||
type AccountVIN struct {
|
|
||||||
AccountID uint64 `json:"accountId"`
|
|
||||||
AccountName string `json:"accountName"`
|
AccountName string `json:"accountName"`
|
||||||
Computes uint64 `json:"computes"`
|
|
||||||
CreatedBy string `json:"createdBy"`
|
// Number of CPU
|
||||||
|
CPUs uint64 `json:"cpus"`
|
||||||
|
|
||||||
|
// Created by
|
||||||
|
CreatedBy string `json:"createdBy"`
|
||||||
|
|
||||||
|
// Created time
|
||||||
CreatedTime uint64 `json:"createdTime"`
|
CreatedTime uint64 `json:"createdTime"`
|
||||||
DeletedBy string `json:"deletedBy"`
|
|
||||||
|
// Deleted by
|
||||||
|
DeletedBy string `json:"deletedBy"`
|
||||||
|
|
||||||
|
// Deleted time
|
||||||
DeletedTime uint64 `json:"deletedTime"`
|
DeletedTime uint64 `json:"deletedTime"`
|
||||||
ExternalIP string `json:"externalIP"`
|
|
||||||
ID uint64 `json:"id"`
|
// ID compute
|
||||||
Name string `json:"name"`
|
ComputeID uint64 `json:"id"`
|
||||||
Network string `json:"network"`
|
|
||||||
PriVnfDevID uint64 `json:"priVnfDevId"`
|
// Compute name
|
||||||
RGID uint64 `json:"rgId"`
|
ComputeName string `json:"name"`
|
||||||
RGName string `json:"rgName"`
|
|
||||||
Status string `json:"status"`
|
// Number of RAM
|
||||||
UpdatedBy string `json:"updatedBy"`
|
RAM uint64 `json:"ram"`
|
||||||
|
|
||||||
|
// Registered or not
|
||||||
|
Registered bool `json:"registered"`
|
||||||
|
|
||||||
|
// Resource group ID
|
||||||
|
RGID uint64 `json:"rgId"`
|
||||||
|
|
||||||
|
// Resource group Name
|
||||||
|
RGName string `json:"rgName"`
|
||||||
|
|
||||||
|
// Status
|
||||||
|
Status string `json:"status"`
|
||||||
|
|
||||||
|
// Tech status
|
||||||
|
TechStatus string `json:"techStatus"`
|
||||||
|
|
||||||
|
// Total disks size
|
||||||
|
TotalDisksSize uint64 `json:"totalDisksSize"`
|
||||||
|
|
||||||
|
// Updated by
|
||||||
|
UpdatedBy string `json:"updatedBy"`
|
||||||
|
|
||||||
|
// Updated time
|
||||||
|
UpdatedTime uint64 `json:"updatedTime"`
|
||||||
|
|
||||||
|
// User controlled or not
|
||||||
|
UserManaged bool `json:"userManaged"`
|
||||||
|
|
||||||
|
// Number of connected VINS
|
||||||
|
VINSConnected uint64 `json:"vinsConnected"`
|
||||||
|
}
|
||||||
|
|
||||||
|
// List of computes
|
||||||
|
type ListComputes []ItemCompute
|
||||||
|
|
||||||
|
// Main information about disk
|
||||||
|
type ItemDisk struct {
|
||||||
|
// ID
|
||||||
|
ID uint64 `json:"id"`
|
||||||
|
|
||||||
|
// Name
|
||||||
|
Name string `json:"name"`
|
||||||
|
|
||||||
|
// Pool
|
||||||
|
Pool string `json:"pool"`
|
||||||
|
|
||||||
|
// ID SEP
|
||||||
|
SEPID uint64 `json:"sepId"`
|
||||||
|
|
||||||
|
// Max size
|
||||||
|
SizeMax uint64 `json:"sizeMax"`
|
||||||
|
|
||||||
|
// Disk type
|
||||||
|
Type string `json:"type"`
|
||||||
|
}
|
||||||
|
|
||||||
|
// List of disks
|
||||||
|
type ListDisks []ItemDisk
|
||||||
|
|
||||||
|
// Main information about VINS
|
||||||
|
type ItemVINS struct {
|
||||||
|
// Account ID
|
||||||
|
AccountID uint64 `json:"accountId"`
|
||||||
|
|
||||||
|
// Name of account
|
||||||
|
AccountName string `json:"accountName"`
|
||||||
|
|
||||||
|
// Number of computes
|
||||||
|
Computes uint64 `json:"computes"`
|
||||||
|
|
||||||
|
// Created by
|
||||||
|
CreatedBy string `json:"createdBy"`
|
||||||
|
|
||||||
|
// Created time
|
||||||
|
CreatedTime uint64 `json:"createdTime"`
|
||||||
|
|
||||||
|
// Deleted by
|
||||||
|
DeletedBy string `json:"deletedBy"`
|
||||||
|
|
||||||
|
// Deleted time
|
||||||
|
DeletedTime uint64 `json:"deletedTime"`
|
||||||
|
|
||||||
|
// External IP
|
||||||
|
ExternalIP string `json:"externalIP"`
|
||||||
|
|
||||||
|
// ID
|
||||||
|
ID uint64 `json:"id"`
|
||||||
|
|
||||||
|
// Name
|
||||||
|
Name string `json:"name"`
|
||||||
|
|
||||||
|
// Network
|
||||||
|
Network string `json:"network"`
|
||||||
|
|
||||||
|
// NNFDev ID
|
||||||
|
PriVNFDevID uint64 `json:"priVnfDevId"`
|
||||||
|
|
||||||
|
// Resource group ID
|
||||||
|
RGID uint64 `json:"rgId"`
|
||||||
|
|
||||||
|
// Resource group name
|
||||||
|
RGName string `json:"rgName"`
|
||||||
|
|
||||||
|
// Status
|
||||||
|
Status string `json:"status"`
|
||||||
|
|
||||||
|
// Updated by
|
||||||
|
UpdatedBy string `json:"updatedBy"`
|
||||||
|
|
||||||
|
// Updated time
|
||||||
UpdatedTime uint64 `json:"updatedTime"`
|
UpdatedTime uint64 `json:"updatedTime"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type AccountVINSList []AccountVIN
|
// List of VINS
|
||||||
|
type ListVINS []ItemVINS
|
||||||
|
|
||||||
type AccountAudit struct {
|
// Main info about audit
|
||||||
Call string `json:"call"`
|
type ItemAudit struct {
|
||||||
|
// Call
|
||||||
|
Call string `json:"call"`
|
||||||
|
|
||||||
|
// Response time
|
||||||
ResponseTime float64 `json:"responsetime"`
|
ResponseTime float64 `json:"responsetime"`
|
||||||
StatusCode uint64 `json:"statuscode"`
|
|
||||||
Timestamp float64 `json:"timestamp"`
|
// Status code
|
||||||
User string `json:"user"`
|
StatusCode uint64 `json:"statuscode"`
|
||||||
|
|
||||||
|
// Timestamp
|
||||||
|
Timestamp float64 `json:"timestamp"`
|
||||||
|
|
||||||
|
// User
|
||||||
|
User string `json:"user"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type AccountAuditsList []AccountAudit
|
// List of audits
|
||||||
|
type ListAudits []ItemAudit
|
||||||
|
|
||||||
type AccountRGComputes struct {
|
// Information compute in resource group
|
||||||
Started uint64 `json:"Started"`
|
type RGComputes struct {
|
||||||
Stopped uint64 `json:"Stopped"`
|
// Number of started computes
|
||||||
|
Started uint64 `json:"started"`
|
||||||
|
|
||||||
|
// Number of stopped computes
|
||||||
|
Stopped uint64 `json:"stopped"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type AccountRGResources struct {
|
// Resources of Resource group
|
||||||
|
type RGResources struct {
|
||||||
|
// Consumed
|
||||||
Consumed Resource `json:"Consumed"`
|
Consumed Resource `json:"Consumed"`
|
||||||
Limits Resource `json:"Limits"`
|
|
||||||
|
// Limits
|
||||||
|
Limits Resource `json:"Limits"`
|
||||||
|
|
||||||
|
// Reserved
|
||||||
Reserved Resource `json:"Reserved"`
|
Reserved Resource `json:"Reserved"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type AccountRG struct {
|
// Main information about resource group
|
||||||
Computes AccountRGComputes `json:"Computes"`
|
type ItemRG struct {
|
||||||
Resources AccountRGResources `json:"Resources"`
|
// Computes
|
||||||
CreatedBy string `json:"createdBy"`
|
Computes RGComputes `json:"Computes"`
|
||||||
CreatedTime uint64 `json:"createdTime"`
|
|
||||||
DeletedBy string `json:"deletedBy"`
|
|
||||||
DeletedTime uint64 `json:"deletedTime"`
|
|
||||||
RGID uint64 `json:"id"`
|
|
||||||
Milestones uint64 `json:"milestones"`
|
|
||||||
RGName string `json:"name"`
|
|
||||||
Status string `json:"status"`
|
|
||||||
UpdatedBy string `json:"updatedBy"`
|
|
||||||
UpdatedTime uint64 `json:"updatedTime"`
|
|
||||||
VINSes uint64 `json:"vinses"`
|
|
||||||
}
|
|
||||||
|
|
||||||
type AccountRGList []AccountRG
|
// Resources
|
||||||
|
Resources RGResources `json:"Resources"`
|
||||||
|
|
||||||
type AccountTemplate struct {
|
// Created by
|
||||||
UNCPath string `json:"UNCPath"`
|
CreatedBy string `json:"createdBy"`
|
||||||
AccountID uint64 `json:"accountId"`
|
|
||||||
Description string `json:"desc"`
|
|
||||||
ID uint64 `json:"id"`
|
|
||||||
Name string `json:"name"`
|
|
||||||
Public bool `json:"public"`
|
|
||||||
Size uint64 `json:"size"`
|
|
||||||
Status string `json:"status"`
|
|
||||||
Type string `json:"type"`
|
|
||||||
Username string `json:"username"`
|
|
||||||
}
|
|
||||||
|
|
||||||
type AccountTemplatesList []AccountTemplate
|
// Created time
|
||||||
|
|
||||||
type AccountFlipGroup struct {
|
|
||||||
AccountID uint64 `json:"accountId"`
|
|
||||||
ClientType string `json:"clientType"`
|
|
||||||
ConnType string `json:"connType"`
|
|
||||||
CreatedBy string `json:"createdBy"`
|
|
||||||
CreatedTime uint64 `json:"createdTime"`
|
CreatedTime uint64 `json:"createdTime"`
|
||||||
DefaultGW string `json:"defaultGW"`
|
|
||||||
DeletedBy string `json:"deletedBy"`
|
// Deleted by
|
||||||
|
DeletedBy string `json:"deletedBy"`
|
||||||
|
|
||||||
|
// Deleted time
|
||||||
DeletedTime uint64 `json:"deletedTime"`
|
DeletedTime uint64 `json:"deletedTime"`
|
||||||
|
|
||||||
|
// Resource group ID
|
||||||
|
RGID uint64 `json:"id"`
|
||||||
|
|
||||||
|
// Milestones
|
||||||
|
Milestones uint64 `json:"milestones"`
|
||||||
|
|
||||||
|
// Resource group name
|
||||||
|
RGName string `json:"name"`
|
||||||
|
|
||||||
|
// Status
|
||||||
|
Status string `json:"status"`
|
||||||
|
|
||||||
|
// Updated by
|
||||||
|
UpdatedBy string `json:"updatedBy"`
|
||||||
|
|
||||||
|
// Updated time
|
||||||
|
UpdatedTime uint64 `json:"updatedTime"`
|
||||||
|
|
||||||
|
// Number of VINS
|
||||||
|
VINSes uint64 `json:"vinses"`
|
||||||
|
}
|
||||||
|
|
||||||
|
// List of Resource groups
|
||||||
|
type ListRG []ItemRG
|
||||||
|
|
||||||
|
// Main information about template
|
||||||
|
type ItemTemplate struct {
|
||||||
|
// UNCPath
|
||||||
|
UNCPath string `json:"UNCPath"`
|
||||||
|
|
||||||
|
// Account ID
|
||||||
|
AccountID uint64 `json:"accountId"`
|
||||||
|
|
||||||
|
// Description
|
||||||
Description string `json:"desc"`
|
Description string `json:"desc"`
|
||||||
GID uint64 `json:"gid"`
|
|
||||||
GUID uint64 `json:"guid"`
|
// ID
|
||||||
ID uint64 `json:"id"`
|
ID uint64 `json:"id"`
|
||||||
IP string `json:"ip"`
|
|
||||||
Milestones uint64 `json:"milestones"`
|
// Name
|
||||||
Name string `json:"name"`
|
Name string `json:"name"`
|
||||||
NetID uint64 `json:"netId"`
|
|
||||||
NetType string `json:"netType"`
|
// Public or not
|
||||||
NetMask uint64 `json:"netmask"`
|
Public bool `json:"public"`
|
||||||
Status string `json:"status"`
|
|
||||||
UpdatedBy string `json:"updatedBy"`
|
// Size
|
||||||
|
Size uint64 `json:"size"`
|
||||||
|
|
||||||
|
// Status
|
||||||
|
Status string `json:"status"`
|
||||||
|
|
||||||
|
// Type
|
||||||
|
Type string `json:"type"`
|
||||||
|
|
||||||
|
// Username
|
||||||
|
Username string `json:"username"`
|
||||||
|
}
|
||||||
|
|
||||||
|
// List of templates
|
||||||
|
type ListTemplates []ItemTemplate
|
||||||
|
|
||||||
|
// Main information about FLIPGroup
|
||||||
|
type ItemFLIPGroup struct {
|
||||||
|
// Account ID
|
||||||
|
AccountID uint64 `json:"accountId"`
|
||||||
|
|
||||||
|
// Client type
|
||||||
|
ClientType string `json:"clientType"`
|
||||||
|
|
||||||
|
// Connection type
|
||||||
|
ConnType string `json:"connType"`
|
||||||
|
|
||||||
|
// Created by
|
||||||
|
CreatedBy string `json:"createdBy"`
|
||||||
|
|
||||||
|
// Created time
|
||||||
|
CreatedTime uint64 `json:"createdTime"`
|
||||||
|
|
||||||
|
// Default GW
|
||||||
|
DefaultGW string `json:"defaultGW"`
|
||||||
|
|
||||||
|
// Deleted by
|
||||||
|
DeletedBy string `json:"deletedBy"`
|
||||||
|
|
||||||
|
// Deleted time
|
||||||
|
DeletedTime uint64 `json:"deletedTime"`
|
||||||
|
|
||||||
|
// Description
|
||||||
|
Description string `json:"desc"`
|
||||||
|
|
||||||
|
// Grid ID
|
||||||
|
GID uint64 `json:"gid"`
|
||||||
|
|
||||||
|
// GUID
|
||||||
|
GUID uint64 `json:"guid"`
|
||||||
|
|
||||||
|
// ID
|
||||||
|
ID uint64 `json:"id"`
|
||||||
|
|
||||||
|
// IP
|
||||||
|
IP string `json:"ip"`
|
||||||
|
|
||||||
|
// Milestones
|
||||||
|
Milestones uint64 `json:"milestones"`
|
||||||
|
|
||||||
|
// Name
|
||||||
|
Name string `json:"name"`
|
||||||
|
|
||||||
|
// Network ID
|
||||||
|
NetID uint64 `json:"netId"`
|
||||||
|
|
||||||
|
// Network type
|
||||||
|
NetType string `json:"netType"`
|
||||||
|
|
||||||
|
// Network mask
|
||||||
|
NetMask uint64 `json:"netmask"`
|
||||||
|
|
||||||
|
// Status
|
||||||
|
Status string `json:"status"`
|
||||||
|
|
||||||
|
// Updated by
|
||||||
|
UpdatedBy string `json:"updatedBy"`
|
||||||
|
|
||||||
|
// Updated time
|
||||||
UpdatedTime uint64 `json:"updatedTime"`
|
UpdatedTime uint64 `json:"updatedTime"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type AccountFlipGroupsList []AccountFlipGroup
|
// List of FLIPGroups
|
||||||
|
type ListFLIPGroups []ItemFLIPGroup
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for restore a deleted account
|
||||||
type RestoreRequest struct {
|
type RestoreRequest struct {
|
||||||
|
// ID an account
|
||||||
|
// Required: true
|
||||||
AccountID uint64 `url:"accountId"`
|
AccountID uint64 `url:"accountId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq RestoreRequest) Validate() error {
|
func (arq RestoreRequest) validate() error {
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (arq RestoreRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Restore restores a deleted account
|
||||||
func (a Account) Restore(ctx context.Context, req RestoreRequest) (bool, error) {
|
func (a Account) Restore(ctx context.Context, req RestoreRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
@@ -38,5 +42,4 @@ func (a Account) Restore(ctx context.Context, req RestoreRequest) (bool, error)
|
|||||||
}
|
}
|
||||||
|
|
||||||
return result, nil
|
return result, nil
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,30 +5,79 @@ import (
|
|||||||
"errors"
|
"errors"
|
||||||
"net/http"
|
"net/http"
|
||||||
"strconv"
|
"strconv"
|
||||||
|
|
||||||
|
"github.com/rudecs/decort-sdk/internal/validators"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for updaate account
|
||||||
type UpdateRequest struct {
|
type UpdateRequest struct {
|
||||||
AccountID uint64 `url:"accountId"`
|
// ID an account
|
||||||
Name string `url:"name,omitempty"`
|
// Required: true
|
||||||
MaxMemoryCapacity uint64 `url:"maxMemoryCapacity,omitempty"`
|
AccountID uint64 `url:"accountId"`
|
||||||
MaxVDiskCapacity uint64 `url:"maxVDiskCapacity,omitempty"`
|
|
||||||
MaxCPUCapacity uint64 `url:"maxCPUCapacity,omitempty"`
|
// Name of the account
|
||||||
|
// Required: false
|
||||||
|
Name string `url:"name,omitempty"`
|
||||||
|
|
||||||
|
// Max size of memory in MB
|
||||||
|
// Required: false
|
||||||
|
MaxMemoryCapacity uint64 `url:"maxMemoryCapacity,omitempty"`
|
||||||
|
|
||||||
|
// Max size of aggregated vdisks in GB
|
||||||
|
// Required: false
|
||||||
|
MaxVDiskCapacity uint64 `url:"maxVDiskCapacity,omitempty"`
|
||||||
|
|
||||||
|
// Max number of CPU cores
|
||||||
|
// Required: false
|
||||||
|
MaxCPUCapacity uint64 `url:"maxCPUCapacity,omitempty"`
|
||||||
|
|
||||||
|
// Max sent/received network transfer peering
|
||||||
|
// Required: false
|
||||||
MaxNetworkPeerTransfer uint64 `url:"maxNetworkPeerTransfer,omitempty"`
|
MaxNetworkPeerTransfer uint64 `url:"maxNetworkPeerTransfer,omitempty"`
|
||||||
MaxNumPublicIP uint64 `url:"maxNumPublicIP,omitempty"`
|
|
||||||
SendAccessEmails bool `url:"sendAccessEmails,omitempty"`
|
// Max number of assigned public IPs
|
||||||
GPUUnits uint64 `url:"gpu_units,omitempty"`
|
// Required: false
|
||||||
|
MaxNumPublicIP uint64 `url:"maxNumPublicIP,omitempty"`
|
||||||
|
|
||||||
|
// If true send emails when a user is granted access to resources
|
||||||
|
// Required: false
|
||||||
|
SendAccessEmails bool `url:"sendAccessEmails,omitempty"`
|
||||||
|
|
||||||
|
// Limit (positive) or disable (0) GPU resources
|
||||||
|
// Required: false
|
||||||
|
GPUUnits uint64 `url:"gpu_units,omitempty"`
|
||||||
|
|
||||||
|
// Resource types available to create in this account
|
||||||
|
// Each element in a resource type slice must be one of:
|
||||||
|
// - compute
|
||||||
|
// - vins
|
||||||
|
// - k8s
|
||||||
|
// - openshift
|
||||||
|
// - lb
|
||||||
|
// - flipgroup
|
||||||
|
// Required: false
|
||||||
|
ResTypes []string `url:"resourceTypes,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq UpdateRequest) Validate() error {
|
func (arq UpdateRequest) validate() error {
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
if len(arq.ResTypes) > 0 {
|
||||||
|
for _, value := range arq.ResTypes {
|
||||||
|
validate := validators.StringInSlice(value, []string{"compute", "vins", "k8s", "openshift", "lb", "flipgroup"})
|
||||||
|
if !validate {
|
||||||
|
return errors.New("validation-error: Every resource type specified should be one of [compute, vins, k8s, openshift, lb, flipgroup]")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Update updates an account name and resource types and limits
|
||||||
func (a Account) Update(ctx context.Context, req UpdateRequest) (bool, error) {
|
func (a Account) Update(ctx context.Context, req UpdateRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -9,25 +9,34 @@ import (
|
|||||||
"github.com/rudecs/decort-sdk/internal/validators"
|
"github.com/rudecs/decort-sdk/internal/validators"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for update user access rights
|
||||||
type UpdateUserRequest struct {
|
type UpdateUserRequest struct {
|
||||||
AccountID uint64 `url:"accountId"`
|
// ID of the account
|
||||||
UserID string `url:"userId"`
|
// Required: true
|
||||||
|
AccountID uint64 `url:"accountId"`
|
||||||
|
|
||||||
|
// Userid/Email for registered users or emailaddress for unregistered users
|
||||||
|
// Required: true
|
||||||
|
UserID string `url:"userId"`
|
||||||
|
|
||||||
|
// Account permission types:
|
||||||
|
// - 'R' for read only access
|
||||||
|
// - 'RCX' for Write
|
||||||
|
// - 'ARCXDU' for Admin
|
||||||
|
// Required: true
|
||||||
AccessType string `url:"accesstype"`
|
AccessType string `url:"accesstype"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (arq UpdateUserRequest) Validate() error {
|
func (arq UpdateUserRequest) validate() error {
|
||||||
if arq.AccountID == 0 {
|
if arq.AccountID == 0 {
|
||||||
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
return errors.New("validation-error: field AccountID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if arq.UserID == "" {
|
if arq.UserID == "" {
|
||||||
return errors.New("validation-error: field UserID can not be empty")
|
return errors.New("validation-error: field UserID can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
if arq.AccessType == "" {
|
if arq.AccessType == "" {
|
||||||
return errors.New("validation-error: field AccessType can not be empty")
|
return errors.New("validation-error: field AccessType can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
isValid := validators.StringInSlice(arq.AccessType, []string{"R", "RCX", "ARCXDU"})
|
isValid := validators.StringInSlice(arq.AccessType, []string{"R", "RCX", "ARCXDU"})
|
||||||
if !isValid {
|
if !isValid {
|
||||||
return errors.New("validation-error: field AccessType can be only R, RCX or ARCXDU")
|
return errors.New("validation-error: field AccessType can be only R, RCX or ARCXDU")
|
||||||
@@ -36,8 +45,9 @@ func (arq UpdateUserRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// UpdateUser updates user access rights
|
||||||
func (a Account) UpdateUser(ctx context.Context, req UpdateUserRequest) (bool, error) {
|
func (a Account) UpdateUser(ctx context.Context, req UpdateUserRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
8
pkg/cloudapi/bservice.go
Normal file
8
pkg/cloudapi/bservice.go
Normal file
@@ -0,0 +1,8 @@
|
|||||||
|
package cloudapi
|
||||||
|
|
||||||
|
import "github.com/rudecs/decort-sdk/pkg/cloudapi/bservice"
|
||||||
|
|
||||||
|
// Accessing the BService method group
|
||||||
|
func (ca *CloudAPI) BService() *bservice.BService {
|
||||||
|
return bservice.New(ca.client)
|
||||||
|
}
|
||||||
@@ -1,11 +1,14 @@
|
|||||||
|
// API Actor for managing Compute Group. This actor is a final API for endusers to manage Compute Group
|
||||||
package bservice
|
package bservice
|
||||||
|
|
||||||
import "github.com/rudecs/decort-sdk/interfaces"
|
import "github.com/rudecs/decort-sdk/interfaces"
|
||||||
|
|
||||||
|
// Structure for creating request to bservice
|
||||||
type BService struct {
|
type BService struct {
|
||||||
client interfaces.Caller
|
client interfaces.Caller
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Builder for bservice endpoints
|
||||||
func New(client interfaces.Caller) *BService {
|
func New(client interfaces.Caller) *BService {
|
||||||
return &BService{
|
return &BService{
|
||||||
client,
|
client,
|
||||||
|
|||||||
@@ -7,18 +7,29 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for BasicService
|
||||||
type CreateRequest struct {
|
type CreateRequest struct {
|
||||||
Name string `url:"name"`
|
// Name of the service
|
||||||
RGID uint64 `url:"rgId"`
|
// Required: true
|
||||||
|
Name string `url:"name"`
|
||||||
|
|
||||||
|
// ID of the Resource Group where this service will be placed
|
||||||
|
// Required: true
|
||||||
|
RGID uint64 `url:"rgId"`
|
||||||
|
|
||||||
|
// Name of the user to deploy SSH key for. Pass empty string if no SSH key deployment is required
|
||||||
|
// Required: false
|
||||||
SSHUser string `url:"sshUser,omitempty"`
|
SSHUser string `url:"sshUser,omitempty"`
|
||||||
SSHKey string `url:"sshKey,omitempty"`
|
|
||||||
|
// SSH key to deploy for the specified user. Same key will be deployed to all computes of the service
|
||||||
|
// Required: false
|
||||||
|
SSHKey string `url:"sshKey,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq CreateRequest) Validate() error {
|
func (bsrq CreateRequest) validate() error {
|
||||||
if bsrq.Name == "" {
|
if bsrq.Name == "" {
|
||||||
return errors.New("field Name can not be empty")
|
return errors.New("field Name can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.RGID == 0 {
|
if bsrq.RGID == 0 {
|
||||||
return errors.New("field RGID can not be empty or equal to 0")
|
return errors.New("field RGID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -26,16 +37,24 @@ func (bsrq CreateRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Create creates blank BasicService instance
|
||||||
func (b BService) Create(ctx context.Context, req CreateRequest) (uint64, error) {
|
func (b BService) Create(ctx context.Context, req CreateRequest) (uint64, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return 0, err
|
return 0, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/create"
|
url := "/cloudapi/bservice/create"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return 0, err
|
return 0, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseUint(string(res), 10, 64)
|
result, err := strconv.ParseUint(string(res), 10, 64)
|
||||||
|
if err != nil {
|
||||||
|
return 0, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,12 +7,18 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for delete basic service
|
||||||
type DeleteRequest struct {
|
type DeleteRequest struct {
|
||||||
ServiceID uint64 `url:"serviceId"`
|
// ID of the BasicService to be delete
|
||||||
Permanently bool `url:"permanently,omitempty"`
|
// Required: true
|
||||||
|
ServiceID uint64 `url:"serviceId"`
|
||||||
|
|
||||||
|
// If set to False, Basic service will be deleted to recycle bin. Otherwise destroyed immediately
|
||||||
|
// Required: true
|
||||||
|
Permanently bool `url:"permanently,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq DeleteRequest) Validate() error {
|
func (bsrq DeleteRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -20,16 +26,24 @@ func (bsrq DeleteRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Delete deletes BasicService instance
|
||||||
func (b BService) Delete(ctx context.Context, req DeleteRequest) (bool, error) {
|
func (b BService) Delete(ctx context.Context, req DeleteRequest) (bool, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/delete"
|
url := "/cloudapi/bservice/delete"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseBool(string(res))
|
result, err := strconv.ParseBool(string(res))
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for disable service
|
||||||
type DisableRequest struct {
|
type DisableRequest struct {
|
||||||
|
// ID of the service to disable
|
||||||
|
// Required: true
|
||||||
ServiceID uint64 `url:"serviceId"`
|
ServiceID uint64 `url:"serviceId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq DisableRequest) Validate() error {
|
func (bsrq DisableRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,16 +22,26 @@ func (bsrq DisableRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Disable disables service.
|
||||||
|
// Disabling a service technically means setting model status
|
||||||
|
// of all computes and service itself to DISABLED and stopping all computes.
|
||||||
func (b BService) Disable(ctx context.Context, req DisableRequest) (bool, error) {
|
func (b BService) Disable(ctx context.Context, req DisableRequest) (bool, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/delete"
|
url := "/cloudapi/bservice/delete"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseBool(string(res))
|
result, err := strconv.ParseBool(string(res))
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for disable service
|
||||||
type EnableRequest struct {
|
type EnableRequest struct {
|
||||||
|
// ID of the service to enable
|
||||||
|
// Required: true
|
||||||
ServiceID uint64 `url:"serviceId"`
|
ServiceID uint64 `url:"serviceId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq EnableRequest) Validate() error {
|
func (bsrq EnableRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,16 +22,27 @@ func (bsrq EnableRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Enable enables service.
|
||||||
|
// Enabling a service technically means setting model status of
|
||||||
|
// all computes and service itself to ENABLED.
|
||||||
|
// It does not start computes.
|
||||||
func (b BService) Enable(ctx context.Context, req EnableRequest) (bool, error) {
|
func (b BService) Enable(ctx context.Context, req EnableRequest) (bool, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/enable"
|
url := "/cloudapi/bservice/enable"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseBool(string(res))
|
result, err := strconv.ParseBool(string(res))
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get detailed information about service
|
||||||
type GetRequest struct {
|
type GetRequest struct {
|
||||||
|
// ID of the service to query information
|
||||||
|
// Required: true
|
||||||
ServiceID uint64 `url:"serviceId"`
|
ServiceID uint64 `url:"serviceId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq GetRequest) Validate() error {
|
func (bsrq GetRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,21 +22,26 @@ func (bsrq GetRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (b BService) Get(ctx context.Context, req GetRequest) (*BasicService, error) {
|
// Get gets detailed specifications for the BasicService.
|
||||||
if err := req.Validate(); err != nil {
|
func (b BService) Get(ctx context.Context, req GetRequest) (*RecordBasicService, error) {
|
||||||
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/get"
|
url := "/cloudapi/bservice/get"
|
||||||
|
|
||||||
bsRaw, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
bsRaw, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
bs := &BasicService{}
|
info := RecordBasicService{}
|
||||||
if err := json.Unmarshal(bsRaw, bs); err != nil {
|
|
||||||
|
err = json.Unmarshal(bsRaw, &info)
|
||||||
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return bs, nil
|
return &info, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,50 +7,82 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for create new compute group within BasicService
|
||||||
type GroupAddRequest struct {
|
type GroupAddRequest struct {
|
||||||
ServiceID uint64 `url:"serviceId"`
|
// ID of the Basic Service to add a group to
|
||||||
Name string `url:"name"`
|
// Required: true
|
||||||
Count uint64 `url:"count"`
|
ServiceID uint64 `url:"serviceId"`
|
||||||
CPU uint64 `url:"cpu"`
|
|
||||||
RAM uint64 `url:"ram"`
|
// Name of the Compute Group to add
|
||||||
Disk uint64 `url:"disk"`
|
// Required: true
|
||||||
ImageID uint64 `url:"imageId"`
|
Name string `url:"name"`
|
||||||
Driver string `url:"driver"`
|
|
||||||
Role string `url:"role,omitempty"`
|
// Computes number. Defines how many computes must be there in the group
|
||||||
VINSes []uint64 `url:"vinses,omitempty"`
|
// Required: true
|
||||||
ExtNets []uint64 `url:"extnets,omitempty"`
|
Count uint64 `url:"count"`
|
||||||
TimeoutStart uint64 `url:"timeoutStart"`
|
|
||||||
|
// Compute CPU number. All computes in the group have the same CPU count
|
||||||
|
// Required: true
|
||||||
|
CPU uint64 `url:"cpu"`
|
||||||
|
|
||||||
|
// Compute RAM volume in MB. All computes in the group have the same RAM volume
|
||||||
|
// Required: true
|
||||||
|
RAM uint64 `url:"ram"`
|
||||||
|
|
||||||
|
// Compute boot disk size in GB
|
||||||
|
// Required: true
|
||||||
|
Disk uint64 `url:"disk"`
|
||||||
|
|
||||||
|
// OS image ID to create computes from
|
||||||
|
// Required: true
|
||||||
|
ImageID uint64 `url:"imageId"`
|
||||||
|
|
||||||
|
// Compute driver
|
||||||
|
// should be one of:
|
||||||
|
// - KVM_X86
|
||||||
|
// - KVM_PPC
|
||||||
|
// Required: true
|
||||||
|
Driver string `url:"driver"`
|
||||||
|
|
||||||
|
// Group role tag. Can be empty string, does not have to be unique
|
||||||
|
// Required: false
|
||||||
|
Role string `url:"role,omitempty"`
|
||||||
|
|
||||||
|
// List of ViNSes to connect computes to
|
||||||
|
// Required: false
|
||||||
|
VINSes []uint64 `url:"vinses,omitempty"`
|
||||||
|
|
||||||
|
// List of external networks to connect computes to
|
||||||
|
// Required: false
|
||||||
|
ExtNets []uint64 `url:"extnets,omitempty"`
|
||||||
|
|
||||||
|
// Time of Compute Group readiness
|
||||||
|
// Required: false
|
||||||
|
TimeoutStart uint64 `url:"timeoutStart"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq GroupAddRequest) Validate() error {
|
func (bsrq GroupAddRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.Name == "" {
|
if bsrq.Name == "" {
|
||||||
return errors.New("field Name can not be empty")
|
return errors.New("field Name can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.Count == 0 {
|
if bsrq.Count == 0 {
|
||||||
return errors.New("field Count can not be empty or equal to 0")
|
return errors.New("field Count can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.CPU == 0 {
|
if bsrq.CPU == 0 {
|
||||||
return errors.New("field CPU can not be empty or equal to 0")
|
return errors.New("field CPU can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.RAM == 0 {
|
if bsrq.RAM == 0 {
|
||||||
return errors.New("field RAM can not be empty or equal to 0")
|
return errors.New("field RAM can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.Disk == 0 {
|
if bsrq.Disk == 0 {
|
||||||
return errors.New("field Disk can not be empty or equal to 0")
|
return errors.New("field Disk can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.ImageID == 0 {
|
if bsrq.ImageID == 0 {
|
||||||
return errors.New("field ImageID can not be empty or equal to 0")
|
return errors.New("field ImageID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.Driver == "" {
|
if bsrq.Driver == "" {
|
||||||
return errors.New("field Driver can not be empty")
|
return errors.New("field Driver can not be empty")
|
||||||
}
|
}
|
||||||
@@ -58,16 +90,26 @@ func (bsrq GroupAddRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GroupAdd creates new Compute Group within BasicService.
|
||||||
|
// Compute Group is NOT started automatically,
|
||||||
|
// so you need to explicitly start it
|
||||||
func (b BService) GroupAdd(ctx context.Context, req GroupAddRequest) (uint64, error) {
|
func (b BService) GroupAdd(ctx context.Context, req GroupAddRequest) (uint64, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return 0, err
|
return 0, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/groupAdd"
|
url := "/cloudapi/bservice/groupAdd"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return 0, err
|
return 0, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseUint(string(res), 10, 64)
|
result, err := strconv.ParseUint(string(res), 10, 64)
|
||||||
|
if err != nil {
|
||||||
|
return 0, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,21 +7,28 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for remove group compute
|
||||||
type GroupComputeRemoveRequest struct {
|
type GroupComputeRemoveRequest struct {
|
||||||
ServiceID uint64 `url:"serviceId"`
|
// ID of the Basic Service
|
||||||
|
// Required: true
|
||||||
|
ServiceID uint64 `url:"serviceId"`
|
||||||
|
|
||||||
|
// ID of the Compute GROUP
|
||||||
|
// Required: true
|
||||||
CompGroupID uint64 `url:"compgroupId"`
|
CompGroupID uint64 `url:"compgroupId"`
|
||||||
ComputeID uint64 `url:"computeId"`
|
|
||||||
|
// ID of the Compute
|
||||||
|
// Required: true
|
||||||
|
ComputeID uint64 `url:"computeId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq GroupComputeRemoveRequest) Validate() error {
|
func (bsrq GroupComputeRemoveRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.CompGroupID == 0 {
|
if bsrq.CompGroupID == 0 {
|
||||||
return errors.New("field CompGroupID can not be empty or equal to 0")
|
return errors.New("field CompGroupID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.ComputeID == 0 {
|
if bsrq.ComputeID == 0 {
|
||||||
return errors.New("field ComputeID can not be empty or equal to 0")
|
return errors.New("field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -29,16 +36,24 @@ func (bsrq GroupComputeRemoveRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GroupComputeRemove makes group compute remove of the Basic Service
|
||||||
func (b BService) GroupComputeRemove(ctx context.Context, req GroupComputeRemoveRequest) (bool, error) {
|
func (b BService) GroupComputeRemove(ctx context.Context, req GroupComputeRemoveRequest) (bool, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/groupComputeRemove"
|
url := "/cloudapi/bservice/groupComputeRemove"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseBool(string(res))
|
result, err := strconv.ParseBool(string(res))
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,16 +7,21 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get detailed information about Compute Group
|
||||||
type GroupGetRequest struct {
|
type GroupGetRequest struct {
|
||||||
ServiceID uint64 `url:"serviceId"`
|
// ID of the Basic Service of Compute Group
|
||||||
|
// Required: true
|
||||||
|
ServiceID uint64 `url:"serviceId"`
|
||||||
|
|
||||||
|
// ID of the Compute Group
|
||||||
|
// Required: true
|
||||||
CompGroupID uint64 `url:"compgroupId"`
|
CompGroupID uint64 `url:"compgroupId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq GroupGetRequest) Validate() error {
|
func (bsrq GroupGetRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.CompGroupID == 0 {
|
if bsrq.CompGroupID == 0 {
|
||||||
return errors.New("field CompGroupID can not be empty or equal to 0")
|
return errors.New("field CompGroupID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -24,21 +29,26 @@ func (bsrq GroupGetRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (b BService) GroupGet(ctx context.Context, req GroupGetRequest) (*Group, error) {
|
// GroupGet gets detailed specifications for the Compute Group
|
||||||
if err := req.Validate(); err != nil {
|
func (b BService) GroupGet(ctx context.Context, req GroupGetRequest) (*RecordGroup, error) {
|
||||||
return nil, err
|
err := req.validate()
|
||||||
}
|
|
||||||
|
|
||||||
url := "/cloudapi/bservice/groupGet"
|
|
||||||
groupRaw, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
group := &Group{}
|
url := "/cloudapi/bservice/groupGet"
|
||||||
if err := json.Unmarshal(groupRaw, group); err != nil {
|
|
||||||
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return group, nil
|
info := RecordGroup{}
|
||||||
|
|
||||||
|
err = json.Unmarshal(res, &info)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return &info, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,21 +7,29 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for add parent Compute Group relation emove parent Compute Group
|
||||||
|
// relation to the specified Compute Group
|
||||||
type GroupParentAddRequest struct {
|
type GroupParentAddRequest struct {
|
||||||
ServiceID uint64 `url:"serviceId"`
|
// ID of the Basic Service of Compute Group
|
||||||
|
// Required: true
|
||||||
|
ServiceID uint64 `url:"serviceId"`
|
||||||
|
|
||||||
|
// ID of the Compute Group
|
||||||
|
// Required: true
|
||||||
CompGroupID uint64 `url:"compgroupId"`
|
CompGroupID uint64 `url:"compgroupId"`
|
||||||
ParentID uint64 `url:"parentId"`
|
|
||||||
|
// ID of the parent Compute Group to register with the current Compute Group
|
||||||
|
// Required: true
|
||||||
|
ParentID uint64 `url:"parentId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq GroupParentAddRequest) Validate() error {
|
func (bsrq GroupParentAddRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.CompGroupID == 0 {
|
if bsrq.CompGroupID == 0 {
|
||||||
return errors.New("field CompGroupID can not be empty or equal to 0")
|
return errors.New("field CompGroupID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.ParentID == 0 {
|
if bsrq.ParentID == 0 {
|
||||||
return errors.New("field ParentID can not be empty or equal to 0")
|
return errors.New("field ParentID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -29,16 +37,24 @@ func (bsrq GroupParentAddRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GroupParentAdd add parent Compute Group relation to the specified Compute Group
|
||||||
func (b BService) GroupParentAdd(ctx context.Context, req GroupParentAddRequest) (bool, error) {
|
func (b BService) GroupParentAdd(ctx context.Context, req GroupParentAddRequest) (bool, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/groupParentAdd"
|
url := "/cloudapi/bservice/groupParentAdd"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseBool(string(res))
|
result, err := strconv.ParseBool(string(res))
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,21 +7,30 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for remove parent Compute Group
|
||||||
|
// relation to the specified Compute Group
|
||||||
type GroupParentRemoveRequest struct {
|
type GroupParentRemoveRequest struct {
|
||||||
ServiceID uint64 `url:"serviceId"`
|
// ID of the Basic Service of Compute Group
|
||||||
|
// Required: true
|
||||||
|
ServiceID uint64 `url:"serviceId"`
|
||||||
|
|
||||||
|
// ID of the Compute Group
|
||||||
|
// Required: true
|
||||||
CompGroupID uint64 `url:"compgroupId"`
|
CompGroupID uint64 `url:"compgroupId"`
|
||||||
ParentID uint64 `url:"parentId"`
|
|
||||||
|
// ID of the parent Compute Group
|
||||||
|
// to remove from the current Compute Group
|
||||||
|
// Required: true
|
||||||
|
ParentID uint64 `url:"parentId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq GroupParentRemoveRequest) Validate() error {
|
func (bsrq GroupParentRemoveRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.CompGroupID == 0 {
|
if bsrq.CompGroupID == 0 {
|
||||||
return errors.New("field CompGroupID can not be empty or equal to 0")
|
return errors.New("field CompGroupID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.ParentID == 0 {
|
if bsrq.ParentID == 0 {
|
||||||
return errors.New("field ParentID can not be empty or equal to 0")
|
return errors.New("field ParentID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -29,16 +38,24 @@ func (bsrq GroupParentRemoveRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GroupParentRemove removes parent Compute Group relation to the specified Compute Group
|
||||||
func (b BService) GroupParentRemove(ctx context.Context, req GroupParentRemoveRequest) (bool, error) {
|
func (b BService) GroupParentRemove(ctx context.Context, req GroupParentRemoveRequest) (bool, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/groupParentRemove"
|
url := "/cloudapi/bservice/groupParentRemove"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseBool(string(res))
|
result, err := strconv.ParseBool(string(res))
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,16 +7,21 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for destroy the specified Compute Group
|
||||||
type GroupRemoveRequest struct {
|
type GroupRemoveRequest struct {
|
||||||
ServiceID uint64 `url:"serviceId"`
|
// ID of the Basic Service of Compute Group
|
||||||
|
// Required: true
|
||||||
|
ServiceID uint64 `url:"serviceId"`
|
||||||
|
|
||||||
|
// ID of the Compute Group
|
||||||
|
// Required: true
|
||||||
CompGroupID uint64 `url:"compgroupId"`
|
CompGroupID uint64 `url:"compgroupId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq GroupRemoveRequest) Validate() error {
|
func (bsrq GroupRemoveRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.CompGroupID == 0 {
|
if bsrq.CompGroupID == 0 {
|
||||||
return errors.New("field CompGroupID can not be empty or equal to 0")
|
return errors.New("field CompGroupID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -24,17 +29,25 @@ func (bsrq GroupRemoveRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GroupRemove destroy the specified Compute Group
|
||||||
func (b BService) GroupRemove(ctx context.Context, req GroupRemoveRequest) (bool, error) {
|
func (b BService) GroupRemove(ctx context.Context, req GroupRemoveRequest) (bool, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/groupRemove"
|
url := "/cloudapi/bservice/groupRemove"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseBool(string(res))
|
result, err := strconv.ParseBool(string(res))
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -9,43 +9,64 @@ import (
|
|||||||
"github.com/rudecs/decort-sdk/internal/validators"
|
"github.com/rudecs/decort-sdk/internal/validators"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for resize the group
|
||||||
type GroupResizeRequest struct {
|
type GroupResizeRequest struct {
|
||||||
ServiceID uint64 `url:"serviceId"`
|
// ID of the Basic Service of Compute Group
|
||||||
|
// Required: true
|
||||||
|
ServiceID uint64 `url:"serviceId"`
|
||||||
|
|
||||||
|
// ID of the Compute Group to resize
|
||||||
|
// Required: true
|
||||||
CompGroupID uint64 `url:"compgroupId"`
|
CompGroupID uint64 `url:"compgroupId"`
|
||||||
Count int64 `url:"count"`
|
|
||||||
Mode string `url:"mode"`
|
// Either delta or absolute value of computes
|
||||||
|
// Required: true
|
||||||
|
Count int64 `url:"count"`
|
||||||
|
|
||||||
|
// Either delta or absolute value of computes
|
||||||
|
// Should be one of:
|
||||||
|
// - ABSOLUTE
|
||||||
|
// - RELATIVE
|
||||||
|
// Required: true
|
||||||
|
Mode string `url:"mode"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq GroupResizeRequest) Validate() error {
|
func (bsrq GroupResizeRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.CompGroupID == 0 {
|
if bsrq.CompGroupID == 0 {
|
||||||
return errors.New("field CompGroupID can not be empty or equal to 0")
|
return errors.New("field CompGroupID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.Mode == "RELATIVE" && bsrq.Count == 0 {
|
if bsrq.Mode == "RELATIVE" && bsrq.Count == 0 {
|
||||||
return errors.New("field Count can not be equal to 0 if Mode if 'RELATIVE'")
|
return errors.New("field Count can not be equal to 0 if Mode if 'RELATIVE'")
|
||||||
}
|
}
|
||||||
|
validate := validators.StringInSlice(bsrq.Mode, []string{"RELATIVE", "ABSOLUTE"})
|
||||||
if !validators.StringInSlice(bsrq.Mode, []string{"RELATIVE", "ABSOLUTE"}) {
|
if !validate {
|
||||||
return errors.New("field Mode can only be one of 'RELATIVE' or 'ABSOLUTE'")
|
return errors.New("field Mode can only be one of 'RELATIVE' or 'ABSOLUTE'")
|
||||||
}
|
}
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GroupResize resize the group by changing the number of computes
|
||||||
func (b BService) GroupResize(ctx context.Context, req GroupResizeRequest) (uint64, error) {
|
func (b BService) GroupResize(ctx context.Context, req GroupResizeRequest) (uint64, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return 0, err
|
return 0, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/groupResize"
|
url := "/cloudapi/bservice/groupResize"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return 0, err
|
return 0, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseUint(string(res), 10, 64)
|
result, err := strconv.ParseUint(string(res), 10, 64)
|
||||||
|
if err != nil {
|
||||||
|
return 0, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,16 +7,21 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for start the specified Compute Group
|
||||||
type GroupStartRequest struct {
|
type GroupStartRequest struct {
|
||||||
ServiceID uint64 `url:"serviceId"`
|
// ID of the Basic Service of Compute Group
|
||||||
|
// Required: true
|
||||||
|
ServiceID uint64 `url:"serviceId"`
|
||||||
|
|
||||||
|
// ID of the Compute Group to start
|
||||||
|
// Required: true
|
||||||
CompGroupID uint64 `url:"compgroupId"`
|
CompGroupID uint64 `url:"compgroupId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq GroupStartRequest) Validate() error {
|
func (bsrq GroupStartRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.CompGroupID == 0 {
|
if bsrq.CompGroupID == 0 {
|
||||||
return errors.New("field CompGroupID can not be empty or equal to 0")
|
return errors.New("field CompGroupID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -24,16 +29,24 @@ func (bsrq GroupStartRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GroupStart starts the specified Compute Group within BasicService
|
||||||
func (b BService) GroupStart(ctx context.Context, req GroupStartRequest) (bool, error) {
|
func (b BService) GroupStart(ctx context.Context, req GroupStartRequest) (bool, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/groupStart"
|
url := "/cloudapi/bservice/groupStart"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseBool(string(res))
|
result, err := strconv.ParseBool(string(res))
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,17 +7,25 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for stop the specified Compute Group
|
||||||
type GroupStopRequest struct {
|
type GroupStopRequest struct {
|
||||||
ServiceID uint64 `url:"serviceId"`
|
// ID of the Basic Service of Compute Group
|
||||||
|
// Required: true
|
||||||
|
ServiceID uint64 `url:"serviceId"`
|
||||||
|
|
||||||
|
// ID of the Compute Group to stop
|
||||||
|
// Required: true
|
||||||
CompGroupID uint64 `url:"compgroupId"`
|
CompGroupID uint64 `url:"compgroupId"`
|
||||||
Force bool `url:"force,omitempty"`
|
|
||||||
|
// Force stop Compute Group
|
||||||
|
// Required: true
|
||||||
|
Force bool `url:"force,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq GroupStopRequest) Validate() error {
|
func (bsrq GroupStopRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.CompGroupID == 0 {
|
if bsrq.CompGroupID == 0 {
|
||||||
return errors.New("field CompGroupID can not be empty or equal to 0")
|
return errors.New("field CompGroupID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -25,16 +33,24 @@ func (bsrq GroupStopRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GroupStop stops the specified Compute Group within BasicService
|
||||||
func (b BService) GroupStop(ctx context.Context, req GroupStopRequest) (bool, error) {
|
func (b BService) GroupStop(ctx context.Context, req GroupStopRequest) (bool, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/groupStop"
|
url := "/cloudapi/bservice/groupStop"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseBool(string(res))
|
result, err := strconv.ParseBool(string(res))
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,22 +7,45 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for update existing Compute group
|
||||||
type GroupUpdateRequest struct {
|
type GroupUpdateRequest struct {
|
||||||
ServiceID uint64 `url:"serviceId"`
|
// ID of the Basic Service of Compute Group
|
||||||
|
// Required: true
|
||||||
|
ServiceID uint64 `url:"serviceId"`
|
||||||
|
|
||||||
|
// ID of the Compute Group
|
||||||
|
// Required: true
|
||||||
CompGroupID uint64 `url:"compgroupId"`
|
CompGroupID uint64 `url:"compgroupId"`
|
||||||
Name string `url:"name,omitempty"`
|
|
||||||
Role string `url:"role,omitempty"`
|
// Specify non-empty string to update Compute Group name
|
||||||
CPU uint64 `url:"cpu,omitempty"`
|
// Required: false
|
||||||
RAM uint64 `url:"ram,omitempty"`
|
Name string `url:"name,omitempty"`
|
||||||
Disk uint64 `url:"disk,omitempty"`
|
|
||||||
Force bool `url:"force,omitempty"`
|
// Specify non-empty string to update group role
|
||||||
|
// Required: false
|
||||||
|
Role string `url:"role,omitempty"`
|
||||||
|
|
||||||
|
// Specify positive value to set new compute CPU count
|
||||||
|
// Required: false
|
||||||
|
CPU uint64 `url:"cpu,omitempty"`
|
||||||
|
|
||||||
|
// Specify positive value to set new compute RAM volume in MB
|
||||||
|
// Required: false
|
||||||
|
RAM uint64 `url:"ram,omitempty"`
|
||||||
|
|
||||||
|
// Specify new compute boot disk size in GB
|
||||||
|
// Required: false
|
||||||
|
Disk uint64 `url:"disk,omitempty"`
|
||||||
|
|
||||||
|
// Force resize Compute Group
|
||||||
|
// Required: false
|
||||||
|
Force bool `url:"force,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq GroupUpdateRequest) Validate() error {
|
func (bsrq GroupUpdateRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.CompGroupID == 0 {
|
if bsrq.CompGroupID == 0 {
|
||||||
return errors.New("field CompGroupID can not be empty or equal to 0")
|
return errors.New("field CompGroupID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -30,16 +53,24 @@ func (bsrq GroupUpdateRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GroupUpdate updates existing Compute group within Basic Service and apply new settings to its computes as necessary
|
||||||
func (b BService) GroupUpdate(ctx context.Context, req GroupUpdateRequest) (bool, error) {
|
func (b BService) GroupUpdate(ctx context.Context, req GroupUpdateRequest) (bool, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/groupUpdate"
|
url := "/cloudapi/bservice/groupUpdate"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseBool(string(res))
|
result, err := strconv.ParseBool(string(res))
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,17 +7,25 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for update External Network settings
|
||||||
type GroupUpdateExtNetRequest struct {
|
type GroupUpdateExtNetRequest struct {
|
||||||
ServiceID uint64 `url:"serviceId"`
|
// ID of the Basic Service of Compute Group
|
||||||
CompGroupID uint64 `url:"compgroupId"`
|
// Required: true
|
||||||
ExtNets []uint64 `url:"extnets,omitempty"`
|
ServiceID uint64 `url:"serviceId"`
|
||||||
|
|
||||||
|
// ID of the Compute Group
|
||||||
|
// Required: true
|
||||||
|
CompGroupID uint64 `url:"compgroupId"`
|
||||||
|
|
||||||
|
// List of Extnets to connect computes
|
||||||
|
// Required: false
|
||||||
|
ExtNets []uint64 `url:"extnets,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq GroupUpdateExtNetRequest) Validate() error {
|
func (bsrq GroupUpdateExtNetRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.CompGroupID == 0 {
|
if bsrq.CompGroupID == 0 {
|
||||||
return errors.New("field CompGroupID can not be empty or equal to 0")
|
return errors.New("field CompGroupID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -25,16 +33,24 @@ func (bsrq GroupUpdateExtNetRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GroupUpdateExtNet updates External Network settings for the group according to the new list
|
||||||
func (b BService) GroupUpdateExtNet(ctx context.Context, req GroupUpdateExtNetRequest) (bool, error) {
|
func (b BService) GroupUpdateExtNet(ctx context.Context, req GroupUpdateExtNetRequest) (bool, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/groupUpdateExtnet"
|
url := "/cloudapi/bservice/groupUpdateExtnet"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseBool(string(res))
|
result, err := strconv.ParseBool(string(res))
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,17 +7,25 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for update VINS settings
|
||||||
type GroupUpdateVINSRequest struct {
|
type GroupUpdateVINSRequest struct {
|
||||||
ServiceID uint64 `url:"serviceId"`
|
// ID of the Basic Service of Compute Group
|
||||||
CompGroupID uint64 `url:"compgroupId"`
|
// Required: true
|
||||||
VINSes []uint64 `url:"vinses,omitempty"`
|
ServiceID uint64 `url:"serviceId"`
|
||||||
|
|
||||||
|
// ID of the Compute Group
|
||||||
|
// Required: true
|
||||||
|
CompGroupID uint64 `url:"compgroupId"`
|
||||||
|
|
||||||
|
// List of ViNSes to connect computes
|
||||||
|
// Required: false
|
||||||
|
VINSes []uint64 `url:"vinses,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq GroupUpdateVINSRequest) Validate() error {
|
func (bsrq GroupUpdateVINSRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.CompGroupID == 0 {
|
if bsrq.CompGroupID == 0 {
|
||||||
return errors.New("field CompGroupID can not be empty or equal to 0")
|
return errors.New("field CompGroupID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -25,16 +33,24 @@ func (bsrq GroupUpdateVINSRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GroupUpdateVINS update ViNS settings for the group according to the new list
|
||||||
func (b BService) GroupUpdateVINS(ctx context.Context, req GroupUpdateVINSRequest) (bool, error) {
|
func (b BService) GroupUpdateVINS(ctx context.Context, req GroupUpdateVINSRequest) (bool, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/groupUpdateVins"
|
url := "/cloudapi/bservice/groupUpdateVins"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseBool(string(res))
|
result, err := strconv.ParseBool(string(res))
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -6,39 +6,59 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get list/deleted list BasicService instances
|
||||||
type ListRequest struct {
|
type ListRequest struct {
|
||||||
|
// ID of the account to query for BasicService instances
|
||||||
|
// Required: false
|
||||||
AccountID uint64 `url:"accountId,omitempty"`
|
AccountID uint64 `url:"accountId,omitempty"`
|
||||||
RGID uint64 `url:"rgId,omitempty"`
|
|
||||||
Page uint64 `url:"page,omitempty"`
|
// ID of the resource group to query for BasicService instances
|
||||||
Size uint64 `url:"size,omitempty"`
|
// Required: false
|
||||||
|
RGID uint64 `url:"rgId,omitempty"`
|
||||||
|
|
||||||
|
// Page number
|
||||||
|
// Required: false
|
||||||
|
Page uint64 `url:"page,omitempty"`
|
||||||
|
|
||||||
|
// Page size
|
||||||
|
// Required: false
|
||||||
|
Size uint64 `url:"size,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (b BService) List(ctx context.Context, req ListRequest) (BasicServiceList, error) {
|
// List gets list BasicService instances associated with the specified Resource Group
|
||||||
|
func (b BService) List(ctx context.Context, req ListRequest) (ListBasicServices, error) {
|
||||||
url := "/cloudapi/bservice/list"
|
url := "/cloudapi/bservice/list"
|
||||||
bsListRaw, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
|
||||||
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
bsList := BasicServiceList{}
|
list := ListBasicServices{}
|
||||||
if err := json.Unmarshal(bsListRaw, &bsList); err != nil {
|
|
||||||
|
err = json.Unmarshal(res, &list)
|
||||||
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return bsList, nil
|
return list, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (b BService) ListDeleted(ctx context.Context, req ListRequest) (BasicServiceList, error) {
|
// ListDeleted gets list deleted BasicService instances associated with the specified Resource Group
|
||||||
|
func (b BService) ListDeleted(ctx context.Context, req ListRequest) (ListBasicServices, error) {
|
||||||
url := "/cloudapi/bservice/listDeleted"
|
url := "/cloudapi/bservice/listDeleted"
|
||||||
bsListRaw, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
|
||||||
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
bsList := BasicServiceList{}
|
list := ListBasicServices{}
|
||||||
if err := json.Unmarshal(bsListRaw, &bsList); err != nil {
|
|
||||||
|
err = json.Unmarshal(res, &list)
|
||||||
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return bsList, nil
|
return list, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,123 +1,334 @@
|
|||||||
package bservice
|
package bservice
|
||||||
|
|
||||||
type BasicService struct {
|
// Detailed info about BasicService
|
||||||
AccountID uint64 `json:"accountId"`
|
type RecordBasicService struct {
|
||||||
AccountName string `json:"accountName"`
|
// Account ID
|
||||||
BaseDomain string `json:"baseDomain"`
|
AccountID uint64 `json:"accountId"`
|
||||||
Computes []Compute `json:"computes"`
|
|
||||||
CPUTotal uint64 `json:"cpuTotal"`
|
// Account name
|
||||||
CreatedBy string `json:"createdBy"`
|
AccountName string `json:"accountName"`
|
||||||
CreatedTime uint64 `json:"createdTime"`
|
|
||||||
DeletedBy string `json:"deletedBy"`
|
// Base domain
|
||||||
DeletedTime uint64 `json:"deletedTime"`
|
BaseDomain string `json:"baseDomain"`
|
||||||
DiskTotal uint64 `json:"diskTotal"`
|
|
||||||
GID uint64 `json:"gid"`
|
// List Computes
|
||||||
Groups []uint64 `json:"groups"`
|
Computes ListComputes `json:"computes"`
|
||||||
GroupsName []string `json:"groupsName"`
|
|
||||||
GUID uint64 `json:"guid"`
|
// Number of cores
|
||||||
ID uint64 `json:"id"`
|
CPUTotal uint64 `json:"cpuTotal"`
|
||||||
Milestones uint64 `json:"milestones"`
|
|
||||||
Name string `json:"name"`
|
// Created by
|
||||||
ParentSrvID uint64 `json:"parentSrvId"`
|
CreatedBy string `json:"createdBy"`
|
||||||
ParentSrvType string `json:"parentSrvType"`
|
|
||||||
RAMTotal uint64 `json:"ramTotal"`
|
// Created time
|
||||||
RGID uint64 `json:"rgId"`
|
CreatedTime uint64 `json:"createdTime"`
|
||||||
RGName string `json:"rgName"`
|
|
||||||
Snapshots []Snapshot `json:"snapshots"`
|
// Deleted by
|
||||||
SSHKey string `json:"sshKey"`
|
DeletedBy string `json:"deletedBy"`
|
||||||
SSHUser string `json:"sshUser"`
|
|
||||||
Status string `json:"status"`
|
// Deleted time
|
||||||
TechStatus string `json:"techStatus"`
|
DeletedTime uint64 `json:"deletedTime"`
|
||||||
UpdatedBy string `json:"updatedBy"`
|
|
||||||
UpdatedTime uint64 `json:"updatedTime"`
|
// Amount of disk space used, GB
|
||||||
UserManaged bool `json:"userManaged"`
|
DiskTotal uint64 `json:"diskTotal"`
|
||||||
|
|
||||||
|
// Grid ID
|
||||||
|
GID uint64 `json:"gid"`
|
||||||
|
|
||||||
|
// List of Service Compute Group IDs
|
||||||
|
Groups []uint64 `json:"groups"`
|
||||||
|
|
||||||
|
// List of compute groups by name
|
||||||
|
GroupsName []string `json:"groupsName"`
|
||||||
|
|
||||||
|
// GUID
|
||||||
|
GUID uint64 `json:"guid"`
|
||||||
|
|
||||||
|
// ID
|
||||||
|
ID uint64 `json:"id"`
|
||||||
|
|
||||||
|
// Milestones
|
||||||
|
Milestones uint64 `json:"milestones"`
|
||||||
|
|
||||||
|
// Name
|
||||||
|
Name string `json:"name"`
|
||||||
|
|
||||||
|
// Parent service ID
|
||||||
|
ParentSrvID uint64 `json:"parentSrvId"`
|
||||||
|
|
||||||
|
// Parent service type
|
||||||
|
ParentSrvType string `json:"parentSrvType"`
|
||||||
|
|
||||||
|
// Total amount of RAM, MB
|
||||||
|
RAMTotal uint64 `json:"ramTotal"`
|
||||||
|
|
||||||
|
// Resource group ID
|
||||||
|
RGID uint64 `json:"rgId"`
|
||||||
|
|
||||||
|
// Resource group name
|
||||||
|
RGName string `json:"rgName"`
|
||||||
|
|
||||||
|
// List of snapshots
|
||||||
|
Snapshots ListSnapshots `json:"snapshots"`
|
||||||
|
|
||||||
|
// SSH key for connection
|
||||||
|
SSHKey string `json:"sshKey"`
|
||||||
|
|
||||||
|
// Username for SSH connection
|
||||||
|
SSHUser string `json:"sshUser"`
|
||||||
|
|
||||||
|
// status
|
||||||
|
Status string `json:"status"`
|
||||||
|
|
||||||
|
// TechStatus
|
||||||
|
TechStatus string `json:"techStatus"`
|
||||||
|
|
||||||
|
// Updated by
|
||||||
|
UpdatedBy string `json:"updatedBy"`
|
||||||
|
|
||||||
|
// Updated time
|
||||||
|
UpdatedTime uint64 `json:"updatedTime"`
|
||||||
|
|
||||||
|
// Whether user controlled
|
||||||
|
UserManaged bool `json:"userManaged"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type Compute struct {
|
// Main information about Compute
|
||||||
CompGroupID uint64 `json:"compgroupId"`
|
type ItemCompute struct {
|
||||||
|
// Compute group ID
|
||||||
|
CompGroupID uint64 `json:"compgroupId"`
|
||||||
|
|
||||||
|
// Compute group name
|
||||||
CompGroupName string `json:"compgroupName"`
|
CompGroupName string `json:"compgroupName"`
|
||||||
|
|
||||||
|
// compute group role
|
||||||
CompGroupRole string `json:"compgroupRole"`
|
CompGroupRole string `json:"compgroupRole"`
|
||||||
ID uint64 `json:"id"`
|
|
||||||
Name string `json:"name"`
|
// ID
|
||||||
|
ID uint64 `json:"id"`
|
||||||
|
|
||||||
|
// Name
|
||||||
|
Name string `json:"name"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type Snapshot struct {
|
// List of Computes
|
||||||
GUID string `json:"guid"`
|
type ListComputes []ItemCompute
|
||||||
Label string `json:"label"`
|
|
||||||
|
// Main information about Snapshot
|
||||||
|
type ItemSnapshot struct {
|
||||||
|
// GUID
|
||||||
|
GUID string `json:"guid"`
|
||||||
|
|
||||||
|
// Label
|
||||||
|
Label string `json:"label"`
|
||||||
|
|
||||||
|
// Timestamp
|
||||||
Timestamp uint64 `json:"timestamp"`
|
Timestamp uint64 `json:"timestamp"`
|
||||||
Valid bool `json:"valid"`
|
|
||||||
|
// Valid or not
|
||||||
|
Valid bool `json:"valid"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type Group struct {
|
// List of Snapshots
|
||||||
AccountID uint64 `json:"accountId"`
|
type ListSnapshots []ItemSnapshot
|
||||||
AccountName string `json:"accountName"`
|
|
||||||
Computes []GroupCompute `json:"computes"`
|
// Main information about Group
|
||||||
Consistency bool `json:"consistency"`
|
type RecordGroup struct {
|
||||||
CPU uint64 `json:"cpu"`
|
// Account ID
|
||||||
CreatedBy string `json:"createdBy"`
|
AccountID uint64 `json:"accountId"`
|
||||||
CreatedTime uint64 `json:"createdTime"`
|
|
||||||
DeletedBy string `json:"deletedBy"`
|
// Account Name
|
||||||
DeletedTime uint64 `json:"deletedTime"`
|
AccountName string `json:"accountName"`
|
||||||
Disk uint64 `json:"disk"`
|
|
||||||
Driver string `json:"driver"`
|
// List of Computes
|
||||||
ExtNets []uint64 `json:"extnets"`
|
Computes ListGroupComputes `json:"computes"`
|
||||||
GID uint64 `json:"gid"`
|
|
||||||
GUID uint64 `json:"guid"`
|
// Consistency or not
|
||||||
ID uint64 `json:"id"`
|
Consistency bool `json:"consistency"`
|
||||||
ImageID uint64 `json:"imageId"`
|
|
||||||
Milestones uint64 `json:"milestones"`
|
// Number of CPU
|
||||||
Name string `json:"name"`
|
CPU uint64 `json:"cpu"`
|
||||||
Parents []uint64 `json:"parents"`
|
|
||||||
RAM uint64 `json:"ram"`
|
// Created by
|
||||||
RGID uint64 `json:"rgId"`
|
CreatedBy string `json:"createdBy"`
|
||||||
RGName string `json:"rgName"`
|
|
||||||
Role string `json:"role"`
|
// Created time
|
||||||
SepID uint64 `json:"sepId"`
|
CreatedTime uint64 `json:"createdTime"`
|
||||||
SeqNo uint64 `json:"seqNo"`
|
|
||||||
ServiceID uint64 `json:"serviceId"`
|
// Deleted by
|
||||||
Status string `json:"status"`
|
DeletedBy string `json:"deletedBy"`
|
||||||
TechStatus string `json:"techStatus"`
|
|
||||||
TimeoutStart uint64 `json:"timeoutStart"`
|
// Deleted time
|
||||||
UpdatedBy string `json:"updatedBy"`
|
DeletedTime uint64 `json:"deletedTime"`
|
||||||
UpdatedTime uint64 `json:"updatedTime"`
|
|
||||||
VINSes []uint64 `json:"vinses"`
|
// Amount of disk
|
||||||
|
Disk uint64 `json:"disk"`
|
||||||
|
|
||||||
|
// Driver
|
||||||
|
Driver string `json:"driver"`
|
||||||
|
|
||||||
|
// list of External Network IDs
|
||||||
|
ExtNets []uint64 `json:"extnets"`
|
||||||
|
|
||||||
|
// Grid ID
|
||||||
|
GID uint64 `json:"gid"`
|
||||||
|
|
||||||
|
// GUID
|
||||||
|
GUID uint64 `json:"guid"`
|
||||||
|
|
||||||
|
// ID
|
||||||
|
ID uint64 `json:"id"`
|
||||||
|
|
||||||
|
// Image ID
|
||||||
|
ImageID uint64 `json:"imageId"`
|
||||||
|
|
||||||
|
// Milestones
|
||||||
|
Milestones uint64 `json:"milestones"`
|
||||||
|
|
||||||
|
// Name
|
||||||
|
Name string `json:"name"`
|
||||||
|
|
||||||
|
// List of Parent IDs
|
||||||
|
Parents []uint64 `json:"parents"`
|
||||||
|
|
||||||
|
// Number of RAM, MB
|
||||||
|
RAM uint64 `json:"ram"`
|
||||||
|
|
||||||
|
// Resource group ID
|
||||||
|
RGID uint64 `json:"rgId"`
|
||||||
|
|
||||||
|
// Resource group name
|
||||||
|
RGName string `json:"rgName"`
|
||||||
|
|
||||||
|
// Role
|
||||||
|
Role string `json:"role"`
|
||||||
|
|
||||||
|
// SEPID
|
||||||
|
SEPID uint64 `json:"sepId"`
|
||||||
|
|
||||||
|
// Sequence number
|
||||||
|
SeqNo uint64 `json:"seqNo"`
|
||||||
|
|
||||||
|
// Service ID
|
||||||
|
ServiceID uint64 `json:"serviceId"`
|
||||||
|
|
||||||
|
// Status
|
||||||
|
Status string `json:"status"`
|
||||||
|
|
||||||
|
// TechStatus
|
||||||
|
TechStatus string `json:"techStatus"`
|
||||||
|
|
||||||
|
// Timeout Start
|
||||||
|
TimeoutStart uint64 `json:"timeoutStart"`
|
||||||
|
|
||||||
|
// Updated by
|
||||||
|
UpdatedBy string `json:"updatedBy"`
|
||||||
|
|
||||||
|
// Updated time
|
||||||
|
UpdatedTime uint64 `json:"updatedTime"`
|
||||||
|
|
||||||
|
// List of VINS IDs
|
||||||
|
VINSes []uint64 `json:"vinses"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type GroupCompute struct {
|
// Main information about Group Compute
|
||||||
ID uint64 `json:"id"`
|
type ItemGroupCompute struct {
|
||||||
|
// ID
|
||||||
|
ID uint64 `json:"id"`
|
||||||
|
|
||||||
|
// IP Addresses
|
||||||
IPAddresses []string `json:"ipAddresses"`
|
IPAddresses []string `json:"ipAddresses"`
|
||||||
Name string `json:"name"`
|
|
||||||
OSUsers []OSUser `json:"osUsers"`
|
// Name
|
||||||
|
Name string `json:"name"`
|
||||||
|
|
||||||
|
// List of information about OS Users
|
||||||
|
OSUsers ListOSUsers `json:"osUsers"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type OSUser struct {
|
// List of Group Computes
|
||||||
Login string `json:"login"`
|
type ListGroupComputes []ItemGroupCompute
|
||||||
|
|
||||||
|
// Main information about OS User
|
||||||
|
type ItemOSUser struct {
|
||||||
|
// Login
|
||||||
|
Login string `json:"login"`
|
||||||
|
|
||||||
|
// Password
|
||||||
Password string `json:"password"`
|
Password string `json:"password"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type BasicServiceShort struct {
|
// List of information about OS Users
|
||||||
AccountID uint64 `json:"accountId"`
|
type ListOSUsers []ItemOSUser
|
||||||
AccountName string `json:"accountName"`
|
|
||||||
BaseDomain string `json:"baseDomain"`
|
// Main information about BasicService
|
||||||
CreatedBy string `json:"createdBy"`
|
type ItemBasicService struct {
|
||||||
CreatedTime uint64 `json:"createdTime"`
|
// Account ID
|
||||||
DeletedBy string `json:"deletedBy"`
|
AccountID uint64 `json:"accountId"`
|
||||||
DeletedTime uint64 `json:"deletedTime"`
|
|
||||||
GID uint64 `json:"gid"`
|
// Account name
|
||||||
Groups []uint64 `json:"groups"`
|
AccountName string `json:"accountName"`
|
||||||
GUID uint64 `json:"guid"`
|
|
||||||
ID uint64 `json:"id"`
|
// Base domain
|
||||||
Name string `json:"name"`
|
BaseDomain string `json:"baseDomain"`
|
||||||
ParentSrvID uint64 `json:"parentSrvId"`
|
|
||||||
ParentSrvType string `json:"parentSrvType"`
|
// Created by
|
||||||
RGID uint64 `json:"rgId"`
|
CreatedBy string `json:"createdBy"`
|
||||||
RGName string `json:"rgName"`
|
|
||||||
SSHUser string `json:"sshUser"`
|
// Created time
|
||||||
Status string `json:"status"`
|
CreatedTime uint64 `json:"createdTime"`
|
||||||
TechStatus string `json:"techStatus"`
|
|
||||||
UpdatedBy string `json:"updatedBy"`
|
// Deleted by
|
||||||
UpdatedTime uint64 `json:"updatedTime"`
|
DeletedBy string `json:"deletedBy"`
|
||||||
UserManaged bool `json:"userManaged"`
|
|
||||||
|
// Deleted time
|
||||||
|
DeletedTime uint64 `json:"deletedTime"`
|
||||||
|
|
||||||
|
// Grid ID
|
||||||
|
GID uint64 `json:"gid"`
|
||||||
|
|
||||||
|
// List of group IDs
|
||||||
|
Groups []uint64 `json:"groups"`
|
||||||
|
|
||||||
|
// GUID
|
||||||
|
GUID uint64 `json:"guid"`
|
||||||
|
|
||||||
|
// ID
|
||||||
|
ID uint64 `json:"id"`
|
||||||
|
|
||||||
|
// Name
|
||||||
|
Name string `json:"name"`
|
||||||
|
|
||||||
|
// Parent service ID
|
||||||
|
ParentSrvID uint64 `json:"parentSrvId"`
|
||||||
|
|
||||||
|
// Parent service type
|
||||||
|
ParentSrvType string `json:"parentSrvType"`
|
||||||
|
|
||||||
|
// Resource group ID
|
||||||
|
RGID uint64 `json:"rgId"`
|
||||||
|
|
||||||
|
// Resource group name
|
||||||
|
RGName string `json:"rgName"`
|
||||||
|
|
||||||
|
// SSH user
|
||||||
|
SSHUser string `json:"sshUser"`
|
||||||
|
|
||||||
|
// Status
|
||||||
|
Status string `json:"status"`
|
||||||
|
|
||||||
|
// TechStatus
|
||||||
|
TechStatus string `json:"techStatus"`
|
||||||
|
|
||||||
|
// Updated by
|
||||||
|
UpdatedBy string `json:"updatedBy"`
|
||||||
|
|
||||||
|
// Updated time
|
||||||
|
UpdatedTime uint64 `json:"updatedTime"`
|
||||||
|
|
||||||
|
// User Managed or not
|
||||||
|
UserManaged bool `json:"userManaged"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type BasicServiceList []BasicServiceShort
|
// List of BasicServices
|
||||||
|
type ListBasicServices []ItemBasicService
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for restores BasicService instance
|
||||||
type RestoreRequest struct {
|
type RestoreRequest struct {
|
||||||
|
// ID of the BasicService to be restored
|
||||||
|
// Required: true
|
||||||
ServiceID uint64 `url:"serviceId"`
|
ServiceID uint64 `url:"serviceId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq RestoreRequest) Validate() error {
|
func (bsrq RestoreRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,16 +22,24 @@ func (bsrq RestoreRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Restore restores BasicService instance
|
||||||
func (b BService) Restore(ctx context.Context, req RestoreRequest) (bool, error) {
|
func (b BService) Restore(ctx context.Context, req RestoreRequest) (bool, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/restore"
|
url := "/cloudapi/bservice/restore"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseBool(string(res))
|
result, err := strconv.ParseBool(string(res))
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,16 +7,21 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for create snapshot
|
||||||
type SnapshotCreateRequest struct {
|
type SnapshotCreateRequest struct {
|
||||||
|
// ID of the Basic Service
|
||||||
|
// Required: true
|
||||||
ServiceID uint64 `url:"serviceId"`
|
ServiceID uint64 `url:"serviceId"`
|
||||||
Label string `url:"label"`
|
|
||||||
|
// Label of the snapshot
|
||||||
|
// Required: true
|
||||||
|
Label string `url:"label"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq SnapshotCreateRequest) Validate() error {
|
func (bsrq SnapshotCreateRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.Label == "" {
|
if bsrq.Label == "" {
|
||||||
return errors.New("field Label can not be empty")
|
return errors.New("field Label can not be empty")
|
||||||
}
|
}
|
||||||
@@ -24,16 +29,24 @@ func (bsrq SnapshotCreateRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// SnapshotCreate create snapshot of the Basic Service
|
||||||
func (b BService) SnapshotCreate(ctx context.Context, req SnapshotCreateRequest) (bool, error) {
|
func (b BService) SnapshotCreate(ctx context.Context, req SnapshotCreateRequest) (bool, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/snapshotCreate"
|
url := "/cloudapi/bservice/snapshotCreate"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseBool(string(res))
|
result, err := strconv.ParseBool(string(res))
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,16 +7,21 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for delete snapshot
|
||||||
type SnapshotDeleteRequest struct {
|
type SnapshotDeleteRequest struct {
|
||||||
|
// ID of the Basic Service
|
||||||
|
// Required: true
|
||||||
ServiceID uint64 `url:"serviceId"`
|
ServiceID uint64 `url:"serviceId"`
|
||||||
Label string `url:"label"`
|
|
||||||
|
// Label of the snapshot
|
||||||
|
// Required: true
|
||||||
|
Label string `url:"label"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq SnapshotDeleteRequest) Validate() error {
|
func (bsrq SnapshotDeleteRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.Label == "" {
|
if bsrq.Label == "" {
|
||||||
return errors.New("field Label can not be empty")
|
return errors.New("field Label can not be empty")
|
||||||
}
|
}
|
||||||
@@ -24,16 +29,24 @@ func (bsrq SnapshotDeleteRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// SnapshotDelete delete snapshot of the Basic Service
|
||||||
func (b BService) SnapshotDelete(ctx context.Context, req SnapshotDeleteRequest) (bool, error) {
|
func (b BService) SnapshotDelete(ctx context.Context, req SnapshotDeleteRequest) (bool, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/snapshotDelete"
|
url := "/cloudapi/bservice/snapshotDelete"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseBool(string(res))
|
result, err := strconv.ParseBool(string(res))
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get list existing snapshots
|
||||||
type SnapshotListRequest struct {
|
type SnapshotListRequest struct {
|
||||||
|
// ID of the Basic Service
|
||||||
|
// Required: true
|
||||||
ServiceID uint64 `url:"serviceId"`
|
ServiceID uint64 `url:"serviceId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq SnapshotListRequest) Validate() error {
|
func (bsrq SnapshotListRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,21 +22,26 @@ func (bsrq SnapshotListRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (b BService) SnapshotList(ctx context.Context, req SnapshotListRequest) ([]Snapshot, error) {
|
// SnapshotList gets list existing snapshots of the Basic Service
|
||||||
if err := req.Validate(); err != nil {
|
func (b BService) SnapshotList(ctx context.Context, req SnapshotListRequest) (ListSnapshots, error) {
|
||||||
return nil, err
|
err := req.validate()
|
||||||
}
|
|
||||||
|
|
||||||
url := "/cloudapi/bservice/snapshotList"
|
|
||||||
snapshotListRaw, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
snapshotList := []Snapshot{}
|
url := "/cloudapi/bservice/snapshotList"
|
||||||
if err := json.Unmarshal(snapshotListRaw, &snapshotList); err != nil {
|
|
||||||
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return snapshotList, nil
|
list := ListSnapshots{}
|
||||||
|
|
||||||
|
err = json.Unmarshal(res, &list)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return list, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,16 +7,21 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for rollback snapshot
|
||||||
type SnapshotRollbackRequest struct {
|
type SnapshotRollbackRequest struct {
|
||||||
|
// ID of the Basic Service
|
||||||
|
// Required: true
|
||||||
ServiceID uint64 `url:"serviceId"`
|
ServiceID uint64 `url:"serviceId"`
|
||||||
Label string `url:"label"`
|
|
||||||
|
// Label of the snapshot
|
||||||
|
// Required: true
|
||||||
|
Label string `url:"label"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq SnapshotRollbackRequest) Validate() error {
|
func (bsrq SnapshotRollbackRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if bsrq.Label == "" {
|
if bsrq.Label == "" {
|
||||||
return errors.New("field Label can not be empty")
|
return errors.New("field Label can not be empty")
|
||||||
}
|
}
|
||||||
@@ -24,16 +29,24 @@ func (bsrq SnapshotRollbackRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// SnapshotRollback rollback snapshot of the Basic Service
|
||||||
func (b BService) SnapshotRollback(ctx context.Context, req SnapshotRollbackRequest) (bool, error) {
|
func (b BService) SnapshotRollback(ctx context.Context, req SnapshotRollbackRequest) (bool, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/snapshotRollback"
|
url := "/cloudapi/bservice/snapshotRollback"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseBool(string(res))
|
result, err := strconv.ParseBool(string(res))
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for start service
|
||||||
type StartRequest struct {
|
type StartRequest struct {
|
||||||
|
// ID of the service to start
|
||||||
|
// Required: true
|
||||||
ServiceID uint64 `url:"serviceId"`
|
ServiceID uint64 `url:"serviceId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq StartRequest) Validate() error {
|
func (bsrq StartRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,16 +22,26 @@ func (bsrq StartRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Start starts service.
|
||||||
|
// Starting a service technically means starting computes from all
|
||||||
|
// service groups according to group relations
|
||||||
func (b BService) Start(ctx context.Context, req StartRequest) (bool, error) {
|
func (b BService) Start(ctx context.Context, req StartRequest) (bool, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/start"
|
url := "/cloudapi/bservice/start"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseBool(string(res))
|
result, err := strconv.ParseBool(string(res))
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for stop service
|
||||||
type StopRequest struct {
|
type StopRequest struct {
|
||||||
|
// ID of the service to stop
|
||||||
|
// Required: true
|
||||||
ServiceID uint64 `url:"serviceId"`
|
ServiceID uint64 `url:"serviceId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bsrq StopRequest) Validate() error {
|
func (bsrq StopRequest) validate() error {
|
||||||
if bsrq.ServiceID == 0 {
|
if bsrq.ServiceID == 0 {
|
||||||
return errors.New("field ServiceID can not be empty or equal to 0")
|
return errors.New("field ServiceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,16 +22,26 @@ func (bsrq StopRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Stop stops service.
|
||||||
|
// Stopping a service technically means stopping computes from
|
||||||
|
// all service groups
|
||||||
func (b BService) Stop(ctx context.Context, req StopRequest) (bool, error) {
|
func (b BService) Stop(ctx context.Context, req StopRequest) (bool, error) {
|
||||||
if err := req.Validate(); err != nil {
|
err := req.validate()
|
||||||
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/cloudapi/bservice/stop"
|
url := "/cloudapi/bservice/stop"
|
||||||
|
|
||||||
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := b.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return strconv.ParseBool(string(res))
|
result, err := strconv.ParseBool(string(res))
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,15 +1,18 @@
|
|||||||
|
// List of method groups for the user
|
||||||
package cloudapi
|
package cloudapi
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"github.com/rudecs/decort-sdk/interfaces"
|
"github.com/rudecs/decort-sdk/interfaces"
|
||||||
)
|
)
|
||||||
|
|
||||||
type CloudApi struct {
|
// Structure for creating request to CloudAPI groups
|
||||||
|
type CloudAPI struct {
|
||||||
client interfaces.Caller
|
client interfaces.Caller
|
||||||
}
|
}
|
||||||
|
|
||||||
func New(client interfaces.Caller) *CloudApi {
|
// Builder to get access to CloudAPI
|
||||||
return &CloudApi{
|
func New(client interfaces.Caller) *CloudAPI {
|
||||||
|
return &CloudAPI{
|
||||||
client: client,
|
client: client,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import (
|
|||||||
"github.com/rudecs/decort-sdk/pkg/cloudapi/compute"
|
"github.com/rudecs/decort-sdk/pkg/cloudapi/compute"
|
||||||
)
|
)
|
||||||
|
|
||||||
func (ca *CloudApi) Compute() *compute.Compute {
|
// Accessing the Compute method group
|
||||||
|
func (ca *CloudAPI) Compute() *compute.Compute {
|
||||||
return compute.New(ca.client)
|
return compute.New(ca.client)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -6,12 +6,18 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for check all computes with current affinity label can start
|
||||||
type AffinityGroupCheckStartRequest struct {
|
type AffinityGroupCheckStartRequest struct {
|
||||||
RGID uint64 `url:"rgId"`
|
// ID of the resource group
|
||||||
|
// Required: true
|
||||||
|
RGID uint64 `url:"rgId"`
|
||||||
|
|
||||||
|
// Affinity group label
|
||||||
|
// Required: true
|
||||||
AffinityLabel string `url:"affinityLabel"`
|
AffinityLabel string `url:"affinityLabel"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq AffinityGroupCheckStartRequest) Validate() error {
|
func (crq AffinityGroupCheckStartRequest) validate() error {
|
||||||
if crq.RGID == 0 {
|
if crq.RGID == 0 {
|
||||||
return errors.New("validation-error: field RGID can not be empty or equal to 0")
|
return errors.New("validation-error: field RGID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -22,8 +28,9 @@ func (crq AffinityGroupCheckStartRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// AffinityGroupCheckStart check all computes with current affinity label can start
|
||||||
func (c Compute) AffinityGroupCheckStart(ctx context.Context, req AffinityGroupCheckStartRequest) (string, error) {
|
func (c Compute) AffinityGroupCheckStart(ctx context.Context, req AffinityGroupCheckStartRequest) (string, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return "", err
|
return "", err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for clear affinity label for compute
|
||||||
type AffinityLabelRemoveRequest struct {
|
type AffinityLabelRemoveRequest struct {
|
||||||
|
// ID of the compute instance
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq AffinityLabelRemoveRequest) Validate() error {
|
func (crq AffinityLabelRemoveRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (crq AffinityLabelRemoveRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// AffinityLabelRemove clear affinity label for compute
|
||||||
func (c Compute) AffinityLabelRemove(ctx context.Context, req AffinityLabelRemoveRequest) (bool, error) {
|
func (c Compute) AffinityLabelRemove(ctx context.Context, req AffinityLabelRemoveRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,12 +7,18 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for set affinity label for compute
|
||||||
type AffinityLabelSetRequest struct {
|
type AffinityLabelSetRequest struct {
|
||||||
ComputeID uint64 `url:"computeId"`
|
// ID of the compute instance
|
||||||
|
// Required: true
|
||||||
|
ComputeID uint64 `url:"computeId"`
|
||||||
|
|
||||||
|
// Affinity group label
|
||||||
|
// Required: true
|
||||||
AffinityLabel string `url:"affinityLabel"`
|
AffinityLabel string `url:"affinityLabel"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq AffinityLabelSetRequest) Validate() error {
|
func (crq AffinityLabelSetRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -23,8 +29,9 @@ func (crq AffinityLabelSetRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// AffinityLabelSet set affinity label for compute
|
||||||
func (c Compute) AffinityLabelSet(ctx context.Context, req AffinityLabelSetRequest) (bool, error) {
|
func (c Compute) AffinityLabelSet(ctx context.Context, req AffinityLabelSetRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,12 +7,14 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get dict of computes
|
||||||
type AffinityRelationsRequest struct {
|
type AffinityRelationsRequest struct {
|
||||||
ComputeID uint64 `url:"computeId"`
|
// ID of the compute instance
|
||||||
AffinityLabel string `url:"affinityLabel"`
|
// Required: true
|
||||||
|
ComputeID uint64 `url:"computeId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq AffinityRelationsRequest) Validate() error {
|
func (crq AffinityRelationsRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -20,8 +22,9 @@ func (crq AffinityRelationsRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c Compute) AffinityRelations(ctx context.Context, req AffinityRelationsRequest) (*AffinityRelations, error) {
|
// AffinityRelations gets dict of computes divided by affinity and anti affinity rules
|
||||||
err := req.Validate()
|
func (c Compute) AffinityRelations(ctx context.Context, req AffinityRelationsRequest) (*RecordAffinityRelations, error) {
|
||||||
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@@ -33,12 +36,12 @@ func (c Compute) AffinityRelations(ctx context.Context, req AffinityRelationsReq
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
relations := &AffinityRelations{}
|
info := RecordAffinityRelations{}
|
||||||
|
|
||||||
err = json.Unmarshal(res, relations)
|
err = json.Unmarshal(res, &info)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return relations, nil
|
return &info, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -9,50 +9,68 @@ import (
|
|||||||
"github.com/rudecs/decort-sdk/internal/validators"
|
"github.com/rudecs/decort-sdk/internal/validators"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for add affinity rule
|
||||||
type AffinityRuleAddRequest struct {
|
type AffinityRuleAddRequest struct {
|
||||||
|
// ID of the compute instance
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
Topology string `url:"topology"`
|
|
||||||
Policy string `url:"policy"`
|
// Compute or node, for whom rule applies
|
||||||
Mode string `url:"mode"`
|
// Required: true
|
||||||
Key string `url:"key"`
|
Topology string `url:"topology"`
|
||||||
Value string `url:"value"`
|
|
||||||
|
// The degree of 'strictness' of this rule
|
||||||
|
// Should be one of:
|
||||||
|
// - RECOMMENDED
|
||||||
|
// - REQUIRED
|
||||||
|
// Required: true
|
||||||
|
Policy string `url:"policy"`
|
||||||
|
|
||||||
|
// The comparison mode is 'value', recorded by the specified 'key'
|
||||||
|
// Should be one of:
|
||||||
|
// - EQ
|
||||||
|
// - EN
|
||||||
|
// - ANY
|
||||||
|
// Required: true
|
||||||
|
Mode string `url:"mode"`
|
||||||
|
|
||||||
|
// Key that are taken into account when analyzing this rule will be identified
|
||||||
|
// Required: true
|
||||||
|
Key string `url:"key"`
|
||||||
|
|
||||||
|
// Value that must match the key to be taken into account when analyzing this rule
|
||||||
|
// Required: true
|
||||||
|
Value string `url:"value"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq AffinityRuleAddRequest) Validate() error {
|
func (crq AffinityRuleAddRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
if crq.Topology == "" {
|
if crq.Topology == "" {
|
||||||
return errors.New("validation-error: field Topology can not be empty")
|
return errors.New("validation-error: field Topology can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
validator := validators.StringInSlice(crq.Topology, []string{"compute", "node"})
|
validator := validators.StringInSlice(crq.Topology, []string{"compute", "node"})
|
||||||
if !validator {
|
if !validator {
|
||||||
return errors.New("validation-error: field Topology can be only compute or node")
|
return errors.New("validation-error: field Topology can be only compute or node")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Policy == "" {
|
if crq.Policy == "" {
|
||||||
return errors.New("validation-error: field Policy can not be empty")
|
return errors.New("validation-error: field Policy can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
validator = validators.StringInSlice(crq.Policy, []string{"RECOMMENDED", "REQUIRED"})
|
validator = validators.StringInSlice(crq.Policy, []string{"RECOMMENDED", "REQUIRED"})
|
||||||
if !validator {
|
if !validator {
|
||||||
return errors.New("validation-error: field Policy can be only RECOMMENDED or REQUIRED")
|
return errors.New("validation-error: field Policy can be only RECOMMENDED or REQUIRED")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Mode == "" {
|
if crq.Mode == "" {
|
||||||
return errors.New("validation-error: field Mode can not be empty")
|
return errors.New("validation-error: field Mode can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
validator = validators.StringInSlice(crq.Mode, []string{"EQ", "NE", "ANY"})
|
validator = validators.StringInSlice(crq.Mode, []string{"EQ", "NE", "ANY"})
|
||||||
if !validator {
|
if !validator {
|
||||||
return errors.New("validation-error: field Mode can be only EQ, NE or ANY")
|
return errors.New("validation-error: field Mode can be only EQ, NE or ANY")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Key == "" {
|
if crq.Key == "" {
|
||||||
return errors.New("validation-error: field Key can not be empty")
|
return errors.New("validation-error: field Key can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Value == "" {
|
if crq.Value == "" {
|
||||||
return errors.New("validation-error: field Value can not be empty")
|
return errors.New("validation-error: field Value can not be empty")
|
||||||
}
|
}
|
||||||
@@ -60,8 +78,9 @@ func (crq AffinityRuleAddRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// AffinityRuleAdd add affinity rule
|
||||||
func (c Compute) AffinityRuleAdd(ctx context.Context, req AffinityRuleAddRequest) (bool, error) {
|
func (c Compute) AffinityRuleAdd(ctx context.Context, req AffinityRuleAddRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -9,50 +9,68 @@ import (
|
|||||||
"github.com/rudecs/decort-sdk/internal/validators"
|
"github.com/rudecs/decort-sdk/internal/validators"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for remove affinity rule
|
||||||
type AffinityRuleRemoveRequest struct {
|
type AffinityRuleRemoveRequest struct {
|
||||||
|
// ID of the compute instance
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
Topology string `url:"topology"`
|
|
||||||
Policy string `url:"policy"`
|
// Compute or node, for whom rule applies
|
||||||
Mode string `url:"mode"`
|
// Required: true
|
||||||
Key string `url:"key"`
|
Topology string `url:"topology"`
|
||||||
Value string `url:"value"`
|
|
||||||
|
// The degree of 'strictness' of this rule
|
||||||
|
// Should be one of:
|
||||||
|
// - RECOMMENDED
|
||||||
|
// - REQUIRED
|
||||||
|
// Required: true
|
||||||
|
Policy string `url:"policy"`
|
||||||
|
|
||||||
|
// The comparison mode is 'value', recorded by the specified 'key'
|
||||||
|
// Should be one of:
|
||||||
|
// - EQ
|
||||||
|
// - EN
|
||||||
|
// - ANY
|
||||||
|
// Required: true
|
||||||
|
Mode string `url:"mode"`
|
||||||
|
|
||||||
|
// Key that are taken into account when analyzing this rule will be identified
|
||||||
|
// Required: true
|
||||||
|
Key string `url:"key"`
|
||||||
|
|
||||||
|
// Value that must match the key to be taken into account when analyzing this rule
|
||||||
|
// Required: true
|
||||||
|
Value string `url:"value"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq AffinityRuleRemoveRequest) Validate() error {
|
func (crq AffinityRuleRemoveRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
if crq.Topology == "" {
|
if crq.Topology == "" {
|
||||||
return errors.New("validation-error: field Topology can not be empty")
|
return errors.New("validation-error: field Topology can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
validator := validators.StringInSlice(crq.Topology, []string{"compute", "node"})
|
validator := validators.StringInSlice(crq.Topology, []string{"compute", "node"})
|
||||||
if !validator {
|
if !validator {
|
||||||
return errors.New("validation-error: field Topology can be only compute or node")
|
return errors.New("validation-error: field Topology can be only compute or node")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Policy == "" {
|
if crq.Policy == "" {
|
||||||
return errors.New("validation-error: field Policy can not be empty")
|
return errors.New("validation-error: field Policy can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
validator = validators.StringInSlice(crq.Policy, []string{"RECOMMENDED", "REQUIRED"})
|
validator = validators.StringInSlice(crq.Policy, []string{"RECOMMENDED", "REQUIRED"})
|
||||||
if !validator {
|
if !validator {
|
||||||
return errors.New("validation-error: field Policy can be only RECOMMENDED or REQUIRED")
|
return errors.New("validation-error: field Policy can be only RECOMMENDED or REQUIRED")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Mode == "" {
|
if crq.Mode == "" {
|
||||||
return errors.New("validation-error: field Mode can not be empty")
|
return errors.New("validation-error: field Mode can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
validator = validators.StringInSlice(crq.Mode, []string{"EQ", "NE", "ANY"})
|
validator = validators.StringInSlice(crq.Mode, []string{"EQ", "NE", "ANY"})
|
||||||
if !validator {
|
if !validator {
|
||||||
return errors.New("validation-error: field Mode can be only EQ, NE or ANY")
|
return errors.New("validation-error: field Mode can be only EQ, NE or ANY")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Key == "" {
|
if crq.Key == "" {
|
||||||
return errors.New("validation-error: field Key can not be empty")
|
return errors.New("validation-error: field Key can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Value == "" {
|
if crq.Value == "" {
|
||||||
return errors.New("validation-error: field Value can not be empty")
|
return errors.New("validation-error: field Value can not be empty")
|
||||||
}
|
}
|
||||||
@@ -60,8 +78,9 @@ func (crq AffinityRuleRemoveRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// AffinityRuleRemove remove affinity rule
|
||||||
func (c Compute) AffinityRuleRemove(ctx context.Context, req AffinityRuleRemoveRequest) (bool, error) {
|
func (c Compute) AffinityRuleRemove(ctx context.Context, req AffinityRuleRemoveRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for clear affinity rules
|
||||||
type AffinityRulesClearRequest struct {
|
type AffinityRulesClearRequest struct {
|
||||||
|
// ID of the compute instance
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq AffinityRulesClearRequest) Validate() error {
|
func (crq AffinityRulesClearRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (crq AffinityRulesClearRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// AffinityRulesClear clear affinity rules
|
||||||
func (c Compute) AffinityRulesClear(ctx context.Context, req AffinityRulesClearRequest) (bool, error) {
|
func (c Compute) AffinityRulesClear(ctx context.Context, req AffinityRulesClearRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -9,50 +9,68 @@ import (
|
|||||||
"github.com/rudecs/decort-sdk/internal/validators"
|
"github.com/rudecs/decort-sdk/internal/validators"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for add anti affinity rule
|
||||||
type AntiAffinityRuleAddRequest struct {
|
type AntiAffinityRuleAddRequest struct {
|
||||||
|
// ID of the compute instance
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
Topology string `url:"topology"`
|
|
||||||
Policy string `url:"policy"`
|
// Compute or node, for whom rule applies
|
||||||
Mode string `url:"mode"`
|
// Required: true
|
||||||
Key string `url:"key"`
|
Topology string `url:"topology"`
|
||||||
Value string `url:"value"`
|
|
||||||
|
// The degree of 'strictness' of this rule
|
||||||
|
// Should be one of:
|
||||||
|
// - RECOMMENDED
|
||||||
|
// - REQUIRED
|
||||||
|
// Required: true
|
||||||
|
Policy string `url:"policy"`
|
||||||
|
|
||||||
|
// The comparison mode is 'value', recorded by the specified 'key'
|
||||||
|
// Should be one of:
|
||||||
|
// - EQ
|
||||||
|
// - EN
|
||||||
|
// - ANY
|
||||||
|
// Required: true
|
||||||
|
Mode string `url:"mode"`
|
||||||
|
|
||||||
|
// Key that are taken into account when analyzing this rule will be identified
|
||||||
|
// Required: true
|
||||||
|
Key string `url:"key"`
|
||||||
|
|
||||||
|
// Value that must match the key to be taken into account when analyzing this rule
|
||||||
|
// Required: true
|
||||||
|
Value string `url:"value"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq AntiAffinityRuleAddRequest) Validate() error {
|
func (crq AntiAffinityRuleAddRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
if crq.Topology == "" {
|
if crq.Topology == "" {
|
||||||
return errors.New("validation-error: field Topology can not be empty")
|
return errors.New("validation-error: field Topology can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
validator := validators.StringInSlice(crq.Topology, []string{"compute", "node"})
|
validator := validators.StringInSlice(crq.Topology, []string{"compute", "node"})
|
||||||
if !validator {
|
if !validator {
|
||||||
return errors.New("validation-error: field Topology can be only compute or node")
|
return errors.New("validation-error: field Topology can be only compute or node")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Policy == "" {
|
if crq.Policy == "" {
|
||||||
return errors.New("validation-error: field Policy can not be empty")
|
return errors.New("validation-error: field Policy can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
validator = validators.StringInSlice(crq.Policy, []string{"RECOMMENDED", "REQUIRED"})
|
validator = validators.StringInSlice(crq.Policy, []string{"RECOMMENDED", "REQUIRED"})
|
||||||
if !validator {
|
if !validator {
|
||||||
return errors.New("validation-error: field Policy can be only RECOMMENDED or REQUIRED")
|
return errors.New("validation-error: field Policy can be only RECOMMENDED or REQUIRED")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Mode == "" {
|
if crq.Mode == "" {
|
||||||
return errors.New("validation-error: field Mode can not be empty")
|
return errors.New("validation-error: field Mode can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
validator = validators.StringInSlice(crq.Mode, []string{"EQ", "NE", "ANY"})
|
validator = validators.StringInSlice(crq.Mode, []string{"EQ", "NE", "ANY"})
|
||||||
if !validator {
|
if !validator {
|
||||||
return errors.New("validation-error: field Mode can be only EQ, NE or ANY")
|
return errors.New("validation-error: field Mode can be only EQ, NE or ANY")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Key == "" {
|
if crq.Key == "" {
|
||||||
return errors.New("validation-error: field Key can not be empty")
|
return errors.New("validation-error: field Key can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Value == "" {
|
if crq.Value == "" {
|
||||||
return errors.New("validation-error: field Value can not be empty")
|
return errors.New("validation-error: field Value can not be empty")
|
||||||
}
|
}
|
||||||
@@ -60,8 +78,9 @@ func (crq AntiAffinityRuleAddRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// AntiAffinityRuleAdd add anti affinity rule
|
||||||
func (c Compute) AntiAffinityRuleAdd(ctx context.Context, req AntiAffinityRuleAddRequest) (bool, error) {
|
func (c Compute) AntiAffinityRuleAdd(ctx context.Context, req AntiAffinityRuleAddRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -9,50 +9,68 @@ import (
|
|||||||
"github.com/rudecs/decort-sdk/internal/validators"
|
"github.com/rudecs/decort-sdk/internal/validators"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for remove anti affinity rule
|
||||||
type AntiAffinityRuleRemoveRequest struct {
|
type AntiAffinityRuleRemoveRequest struct {
|
||||||
|
// ID of the compute instance
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
Topology string `url:"topology"`
|
|
||||||
Policy string `url:"policy"`
|
// Compute or node, for whom rule applies
|
||||||
Mode string `url:"mode"`
|
// Required: true
|
||||||
Key string `url:"key"`
|
Topology string `url:"topology"`
|
||||||
Value string `url:"value"`
|
|
||||||
|
// The degree of 'strictness' of this rule
|
||||||
|
// Should be one of:
|
||||||
|
// - RECOMMENDED
|
||||||
|
// - REQUIRED
|
||||||
|
// Required: true
|
||||||
|
Policy string `url:"policy"`
|
||||||
|
|
||||||
|
// The comparison mode is 'value', recorded by the specified 'key'
|
||||||
|
// Should be one of:
|
||||||
|
// - EQ
|
||||||
|
// - EN
|
||||||
|
// - ANY
|
||||||
|
// Required: true
|
||||||
|
Mode string `url:"mode"`
|
||||||
|
|
||||||
|
// Key that are taken into account when analyzing this rule will be identified
|
||||||
|
// Required: true
|
||||||
|
Key string `url:"key"`
|
||||||
|
|
||||||
|
// Value that must match the key to be taken into account when analyzing this rule
|
||||||
|
// Required: true
|
||||||
|
Value string `url:"value"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq AntiAffinityRuleRemoveRequest) Validate() error {
|
func (crq AntiAffinityRuleRemoveRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
if crq.Topology == "" {
|
if crq.Topology == "" {
|
||||||
return errors.New("validation-error: field Topology can not be empty")
|
return errors.New("validation-error: field Topology can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
validator := validators.StringInSlice(crq.Topology, []string{"compute", "node"})
|
validator := validators.StringInSlice(crq.Topology, []string{"compute", "node"})
|
||||||
if !validator {
|
if !validator {
|
||||||
return errors.New("validation-error: field Topology can be only compute or node")
|
return errors.New("validation-error: field Topology can be only compute or node")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Policy == "" {
|
if crq.Policy == "" {
|
||||||
return errors.New("validation-error: field Policy can not be empty")
|
return errors.New("validation-error: field Policy can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
validator = validators.StringInSlice(crq.Policy, []string{"RECOMMENDED", "REQUIRED"})
|
validator = validators.StringInSlice(crq.Policy, []string{"RECOMMENDED", "REQUIRED"})
|
||||||
if !validator {
|
if !validator {
|
||||||
return errors.New("validation-error: field Policy can be only RECOMMENDED or REQUIRED")
|
return errors.New("validation-error: field Policy can be only RECOMMENDED or REQUIRED")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Mode == "" {
|
if crq.Mode == "" {
|
||||||
return errors.New("validation-error: field Mode can not be empty")
|
return errors.New("validation-error: field Mode can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
validator = validators.StringInSlice(crq.Mode, []string{"EQ", "NE", "ANY"})
|
validator = validators.StringInSlice(crq.Mode, []string{"EQ", "NE", "ANY"})
|
||||||
if !validator {
|
if !validator {
|
||||||
return errors.New("validation-error: field Mode can be only EQ, NE or ANY")
|
return errors.New("validation-error: field Mode can be only EQ, NE or ANY")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Key == "" {
|
if crq.Key == "" {
|
||||||
return errors.New("validation-error: field Key can not be empty")
|
return errors.New("validation-error: field Key can not be empty")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Value == "" {
|
if crq.Value == "" {
|
||||||
return errors.New("validation-error: field Value can not be empty")
|
return errors.New("validation-error: field Value can not be empty")
|
||||||
}
|
}
|
||||||
@@ -60,8 +78,9 @@ func (crq AntiAffinityRuleRemoveRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// AntiAffinityRuleRemove remove anti affinity rule
|
||||||
func (c Compute) AntiAffinityRuleRemove(ctx context.Context, req AntiAffinityRuleRemoveRequest) (bool, error) {
|
func (c Compute) AntiAffinityRuleRemove(ctx context.Context, req AntiAffinityRuleRemoveRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for clear anti affinity rules
|
||||||
type AntiAffinityRulesClearRequest struct {
|
type AntiAffinityRulesClearRequest struct {
|
||||||
|
// ID of the compute instance
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq AntiAffinityRulesClearRequest) Validate() error {
|
func (crq AntiAffinityRulesClearRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (crq AntiAffinityRulesClearRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// AntiAffinityRulesClear clear anti affinity rules
|
||||||
func (c Compute) AntiAffinityRulesClear(ctx context.Context, req AntiAffinityRulesClearRequest) (bool, error) {
|
func (c Compute) AntiAffinityRulesClear(ctx context.Context, req AntiAffinityRulesClearRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,16 +7,21 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for attach GPU for compute
|
||||||
type AttachGPURequest struct {
|
type AttachGPURequest struct {
|
||||||
|
// Identifier compute
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
VGPUID uint64 `url:"vgpuId"`
|
|
||||||
|
// Identifier vGPU
|
||||||
|
// Required: true
|
||||||
|
VGPUID uint64 `url:"vgpuId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq AttachGPURequest) Validate() error {
|
func (crq AttachGPURequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.VGPUID == 0 {
|
if crq.VGPUID == 0 {
|
||||||
return errors.New("validation-error: field VGPUID can not be empty or equal to 0")
|
return errors.New("validation-error: field VGPUID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -24,8 +29,9 @@ func (crq AttachGPURequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// AttachGPU attach GPU for compute, returns vgpu id on success
|
||||||
func (c Compute) AttachGPU(ctx context.Context, req AttachGPURequest) (uint64, error) {
|
func (c Compute) AttachGPU(ctx context.Context, req AttachGPURequest) (uint64, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return 0, err
|
return 0, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,16 +7,21 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
type AttachPciDeviceRequest struct {
|
// Request struct for atttach PCI device
|
||||||
|
type AttachPCIDeviceRequest struct {
|
||||||
|
// Identifier compute
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
DeviceID uint64 `url:"deviceId"`
|
|
||||||
|
// PCI device ID
|
||||||
|
// Required: true
|
||||||
|
DeviceID uint64 `url:"deviceId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq AttachPciDeviceRequest) Validate() error {
|
func (crq AttachPCIDeviceRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.DeviceID == 0 {
|
if crq.DeviceID == 0 {
|
||||||
return errors.New("validation-error: field DeviceID can not be empty or equal to 0")
|
return errors.New("validation-error: field DeviceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -24,8 +29,9 @@ func (crq AttachPciDeviceRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c Compute) AttachPciDevice(ctx context.Context, req AttachPciDeviceRequest) (bool, error) {
|
// AttachPCIDevice attach PCI device
|
||||||
err := req.Validate()
|
func (c Compute) AttachPCIDevice(ctx context.Context, req AttachPCIDeviceRequest) (bool, error) {
|
||||||
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get audit records
|
||||||
type AuditsRequest struct {
|
type AuditsRequest struct {
|
||||||
|
// ID of the compute
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq AuditsRequest) Validate() error {
|
func (crq AuditsRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("field ComputeID can not be empty or equal to 0")
|
return errors.New("field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,21 +22,26 @@ func (crq AuditsRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c Compute) Audits(ctx context.Context, req AuditsRequest) (AuditList, error) {
|
// Audits gets audit records for the specified compute object
|
||||||
if err := req.Validate(); err != nil {
|
func (c Compute) Audits(ctx context.Context, req AuditsRequest) (ListAudits, error) {
|
||||||
return nil, err
|
err := req.validate()
|
||||||
}
|
|
||||||
|
|
||||||
url := "/cloudapi/compute/audits"
|
|
||||||
auditListRaw, err := c.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
auditList := AuditList{}
|
url := "/cloudapi/compute/audits"
|
||||||
if err := json.Unmarshal(auditListRaw, &auditList); err != nil {
|
|
||||||
|
res, err := c.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return auditList, nil
|
list := ListAudits{}
|
||||||
|
|
||||||
|
err = json.Unmarshal(res, &list)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return list, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for eject CD image
|
||||||
type CDEjectRequest struct {
|
type CDEjectRequest struct {
|
||||||
|
// ID of compute instance
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq CDEjectRequest) Validate() error {
|
func (crq CDEjectRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (crq CDEjectRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// CDEject eject CD image to compute's CD-ROM
|
||||||
func (c Compute) CDEject(ctx context.Context, req CDEjectRequest) (bool, error) {
|
func (c Compute) CDEject(ctx context.Context, req CDEjectRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,12 +7,18 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for insert new CD image
|
||||||
type CDInsertRequest struct {
|
type CDInsertRequest struct {
|
||||||
|
// ID of compute instance
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
CDROMID uint64 `url:"cdromId"`
|
|
||||||
|
// ID of CD-ROM image
|
||||||
|
// Required: true
|
||||||
|
CDROMID uint64 `url:"cdromId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq CDInsertRequest) Validate() error {
|
func (crq CDInsertRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -23,8 +29,9 @@ func (crq CDInsertRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// CDInsert insert new CD image to compute's CD-ROM
|
||||||
func (c Compute) CDInsert(ctx context.Context, req CDInsertRequest) (bool, error) {
|
func (c Compute) CDInsert(ctx context.Context, req CDInsertRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,14 +7,26 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for clone compute instance
|
||||||
type CloneRequest struct {
|
type CloneRequest struct {
|
||||||
ComputeID uint64 `url:"computeId"`
|
// ID of compute instance
|
||||||
Name string `url:"name"`
|
// Required: true
|
||||||
|
ComputeID uint64 `url:"computeId"`
|
||||||
|
|
||||||
|
// Name of the clone
|
||||||
|
// Required: true
|
||||||
|
Name string `url:"name"`
|
||||||
|
|
||||||
|
// Timestamp of the parent's snapshot to create clone from
|
||||||
|
// Required: false
|
||||||
SnapshotTimestamp uint64 `url:"snapshotTimestamp"`
|
SnapshotTimestamp uint64 `url:"snapshotTimestamp"`
|
||||||
SnapshotName string `url:"snapshotName"`
|
|
||||||
|
// Name of the parent's snapshot to create clone from
|
||||||
|
// Required: false
|
||||||
|
SnapshotName string `url:"snapshotName"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq CloneRequest) Validate() error {
|
func (crq CloneRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -25,8 +37,9 @@ func (crq CloneRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Clone clones compute instance
|
||||||
func (c Compute) Clone(ctx context.Context, req CloneRequest) (uint64, error) {
|
func (c Compute) Clone(ctx context.Context, req CloneRequest) (uint64, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return 0, err
|
return 0, err
|
||||||
}
|
}
|
||||||
@@ -42,5 +55,6 @@ func (c Compute) Clone(ctx context.Context, req CloneRequest) (uint64, error) {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return 0, err
|
return 0, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return result, nil
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,13 +1,16 @@
|
|||||||
|
// API Actor for managing Compute. This actor is a final API for endusers to manage Compute
|
||||||
package compute
|
package compute
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"github.com/rudecs/decort-sdk/interfaces"
|
"github.com/rudecs/decort-sdk/interfaces"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Structure for creating request to compute
|
||||||
type Compute struct {
|
type Compute struct {
|
||||||
client interfaces.Caller
|
client interfaces.Caller
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Builder for compute endpoints
|
||||||
func New(client interfaces.Caller) *Compute {
|
func New(client interfaces.Caller) *Compute {
|
||||||
return &Compute{
|
return &Compute{
|
||||||
client,
|
client,
|
||||||
|
|||||||
@@ -8,17 +8,27 @@ import (
|
|||||||
"strings"
|
"strings"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for create template
|
||||||
type CreateTemplateRequest struct {
|
type CreateTemplateRequest struct {
|
||||||
|
// ID of the compute to create template from
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
Name string `url:"name"`
|
|
||||||
Async bool `url:"async"`
|
// Name to assign to the template being created
|
||||||
|
// Required: true
|
||||||
|
Name string `url:"name"`
|
||||||
|
|
||||||
|
// Async API call
|
||||||
|
// For async call use CreateTemplateAsync
|
||||||
|
// For sync call use CreateTemplate
|
||||||
|
// Required: true
|
||||||
|
async bool `url:"async"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq CreateTemplateRequest) Validate() error {
|
func (crq CreateTemplateRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Name == "" {
|
if crq.Name == "" {
|
||||||
return errors.New("validation-error: field Name can not be empty")
|
return errors.New("validation-error: field Name can not be empty")
|
||||||
}
|
}
|
||||||
@@ -26,13 +36,14 @@ func (crq CreateTemplateRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// CreateTemplate create template from compute instance
|
||||||
func (c Compute) CreateTemplate(ctx context.Context, req CreateTemplateRequest) (uint64, error) {
|
func (c Compute) CreateTemplate(ctx context.Context, req CreateTemplateRequest) (uint64, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return 0, err
|
return 0, err
|
||||||
}
|
}
|
||||||
|
|
||||||
req.Async = false
|
req.async = false
|
||||||
|
|
||||||
url := "/cloudapi/compute/createTemplate"
|
url := "/cloudapi/compute/createTemplate"
|
||||||
|
|
||||||
@@ -49,13 +60,14 @@ func (c Compute) CreateTemplate(ctx context.Context, req CreateTemplateRequest)
|
|||||||
return result, nil
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// CreateTemplateAsync create template from compute instance
|
||||||
func (c Compute) CreateTemplateAsync(ctx context.Context, req CreateTemplateRequest) (string, error) {
|
func (c Compute) CreateTemplateAsync(ctx context.Context, req CreateTemplateRequest) (string, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return "", err
|
return "", err
|
||||||
}
|
}
|
||||||
|
|
||||||
req.Async = true
|
req.async = true
|
||||||
|
|
||||||
url := "/cloudapi/compute/createTemplate"
|
url := "/cloudapi/compute/createTemplate"
|
||||||
|
|
||||||
|
|||||||
@@ -7,13 +7,22 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for delete compute
|
||||||
type DeleteRequest struct {
|
type DeleteRequest struct {
|
||||||
ComputeID uint64 `url:"computeId"`
|
// ID of compute instance
|
||||||
Permanently bool `url:"permanently,omitempty"`
|
// Required: true
|
||||||
DetachDisks bool `url:"detachDisks,omitempty"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
|
|
||||||
|
// Delete permanently
|
||||||
|
// Required: false
|
||||||
|
Permanently bool `url:"permanently,omitempty"`
|
||||||
|
|
||||||
|
// Set True if you want to detach data disks (if any) from the compute before its deletion
|
||||||
|
// Required: false
|
||||||
|
DetachDisks bool `url:"detachDisks,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq DeleteRequest) Validate() error {
|
func (crq DeleteRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -21,8 +30,9 @@ func (crq DeleteRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Delete deletes compute
|
||||||
func (c Compute) Delete(ctx context.Context, req DeleteRequest) (bool, error) {
|
func (c Compute) Delete(ctx context.Context, req DeleteRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
@@ -38,5 +48,6 @@ func (c Compute) Delete(ctx context.Context, req DeleteRequest) (bool, error) {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return result, nil
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,12 +7,18 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for detach vgpu for compute
|
||||||
type DetachGPURequest struct {
|
type DetachGPURequest struct {
|
||||||
|
// Identifier compute
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
VGPUID int64 `url:"vgpuId,omitempty"`
|
|
||||||
|
// Identifier virtual GPU
|
||||||
|
// Required: false
|
||||||
|
VGPUID int64 `url:"vgpuId,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq DetachGPURequest) Validate() error {
|
func (crq DetachGPURequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -20,8 +26,10 @@ func (crq DetachGPURequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DetachGPU detach vgpu for compute.
|
||||||
|
// If param vgpuid is equivalent -1, then detach all vgpu for compute
|
||||||
func (c Compute) DetachGPU(ctx context.Context, req DetachGPURequest) (bool, error) {
|
func (c Compute) DetachGPU(ctx context.Context, req DetachGPURequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,16 +7,21 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
type DetachPciDeviceRequest struct {
|
// Request struct for detach PCI device
|
||||||
|
type DetachPCIDeviceRequest struct {
|
||||||
|
// Identifier compute
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
DeviceID uint64 `url:"deviceId"`
|
|
||||||
|
// Pci device ID
|
||||||
|
// Required: true
|
||||||
|
DeviceID uint64 `url:"deviceId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq DetachPciDeviceRequest) Validate() error {
|
func (crq DetachPCIDeviceRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.DeviceID == 0 {
|
if crq.DeviceID == 0 {
|
||||||
return errors.New("validation-error: field DeviceID can not be empty or equal to 0")
|
return errors.New("validation-error: field DeviceID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -24,8 +29,9 @@ func (crq DetachPciDeviceRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c Compute) DetachPciDevice(ctx context.Context, req DetachPciDeviceRequest) (bool, error) {
|
// DetachPCIDevice detach PCI device
|
||||||
err := req.Validate()
|
func (c Compute) DetachPCIDevice(ctx context.Context, req DetachPCIDeviceRequest) (bool, error) {
|
||||||
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for disable compute
|
||||||
type DisableRequest struct {
|
type DisableRequest struct {
|
||||||
|
// ID of compute instance
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq DisableRequest) Validate() error {
|
func (crq DisableRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (crq DisableRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Disable disables compute
|
||||||
func (c Compute) Disable(ctx context.Context, req DisableRequest) (bool, error) {
|
func (c Compute) Disable(ctx context.Context, req DisableRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,26 +7,53 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for create and attach disk to compute
|
||||||
type DiskAddRequest struct {
|
type DiskAddRequest struct {
|
||||||
ComputeID uint64 `url:"computeId"`
|
// ID of compute instance
|
||||||
DiskName string `url:"diskName"`
|
// Required: true
|
||||||
Size uint64 `url:"size"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
DiskType string `url:"diskType,omitempty"`
|
|
||||||
SepID uint64 `url:"sepId,omitempty"`
|
// Name for disk
|
||||||
Pool string `url:"pool,omitempty"`
|
// Required: true
|
||||||
|
DiskName string `url:"diskName"`
|
||||||
|
|
||||||
|
// Disk size in GB
|
||||||
|
// Required: true
|
||||||
|
Size uint64 `url:"size"`
|
||||||
|
|
||||||
|
// Type of the disk
|
||||||
|
// Should be one of:
|
||||||
|
// - D
|
||||||
|
// - B
|
||||||
|
// Required: false
|
||||||
|
DiskType string `url:"diskType,omitempty"`
|
||||||
|
|
||||||
|
// Storage endpoint provider ID
|
||||||
|
// By default the same with boot disk
|
||||||
|
// Required: false
|
||||||
|
SepID uint64 `url:"sepId,omitempty"`
|
||||||
|
|
||||||
|
// Pool name
|
||||||
|
// By default will be chosen automatically
|
||||||
|
// Required: false
|
||||||
|
Pool string `url:"pool,omitempty"`
|
||||||
|
|
||||||
|
// Optional description
|
||||||
|
// Required: false
|
||||||
Description string `url:"desc,omitempty"`
|
Description string `url:"desc,omitempty"`
|
||||||
ImageID uint64 `url:"imageId,omitempty"`
|
|
||||||
|
// Specify image id for create disk from template
|
||||||
|
// Required: false
|
||||||
|
ImageID uint64 `url:"imageId,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq DiskAddRequest) Validate() error {
|
func (crq DiskAddRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Size == 0 {
|
if crq.Size == 0 {
|
||||||
return errors.New("validation-error: field Size can not be empty or equal to 0")
|
return errors.New("validation-error: field Size can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.DiskName == "" {
|
if crq.DiskName == "" {
|
||||||
return errors.New("validation-error: field DiskName can not be empty or equal to 0")
|
return errors.New("validation-error: field DiskName can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -34,8 +61,9 @@ func (crq DiskAddRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DiskAdd creates new disk and attach to compute
|
||||||
func (c Compute) DiskAdd(ctx context.Context, req DiskAddRequest) (uint64, error) {
|
func (c Compute) DiskAdd(ctx context.Context, req DiskAddRequest) (uint64, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return 0, err
|
return 0, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,16 +7,21 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for attach disk to compute
|
||||||
type DiskAttachRequest struct {
|
type DiskAttachRequest struct {
|
||||||
|
// ID of compute instance
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
DiskID uint64 `url:"diskId"`
|
|
||||||
|
// ID of the disk to attach
|
||||||
|
// Required: true
|
||||||
|
DiskID uint64 `url:"diskId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq DiskAttachRequest) Validate() error {
|
func (crq DiskAttachRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.DiskID == 0 {
|
if crq.DiskID == 0 {
|
||||||
return errors.New("validation-error: field DiskID can not be empty or equal to 0")
|
return errors.New("validation-error: field DiskID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -24,8 +29,9 @@ func (crq DiskAttachRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DiskAttach attach disk to compute
|
||||||
func (c Compute) DiskAttach(ctx context.Context, req DiskAttachRequest) (bool, error) {
|
func (c Compute) DiskAttach(ctx context.Context, req DiskAttachRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,17 +7,25 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for detach and delete disk from compute
|
||||||
type DiskDelRequest struct {
|
type DiskDelRequest struct {
|
||||||
ComputeID uint64 `url:"computeId"`
|
// ID of compute instance
|
||||||
DiskID uint64 `url:"diskId"`
|
// Required: true
|
||||||
Permanently bool `url:"permanently"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
|
|
||||||
|
// ID of disk instance
|
||||||
|
// Required: true
|
||||||
|
DiskID uint64 `url:"diskId"`
|
||||||
|
|
||||||
|
// False if disk is to be deleted to recycle bin
|
||||||
|
// Required: true
|
||||||
|
Permanently bool `url:"permanently"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq DiskDelRequest) Validate() error {
|
func (crq DiskDelRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.DiskID == 0 {
|
if crq.DiskID == 0 {
|
||||||
return errors.New("validation-error: field DiskID can not be empty or equal to 0")
|
return errors.New("validation-error: field DiskID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -25,8 +33,9 @@ func (crq DiskDelRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DiskDel delete disk and detach from compute
|
||||||
func (c Compute) DiskDel(ctx context.Context, req DiskDelRequest) (bool, error) {
|
func (c Compute) DiskDel(ctx context.Context, req DiskDelRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,16 +7,21 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for detach disk from compute
|
||||||
type DiskDetachRequest struct {
|
type DiskDetachRequest struct {
|
||||||
|
// ID of compute instance
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
DiskID uint64 `url:"diskId"`
|
|
||||||
|
// ID of the disk to detach
|
||||||
|
// Required: true
|
||||||
|
DiskID uint64 `url:"diskId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq DiskDetachRequest) Validate() error {
|
func (crq DiskDetachRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.DiskID == 0 {
|
if crq.DiskID == 0 {
|
||||||
return errors.New("validation-error: field DiskID can not be empty or equal to 0")
|
return errors.New("validation-error: field DiskID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -24,8 +29,9 @@ func (crq DiskDetachRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DiskDetach detach disk from compute
|
||||||
func (c Compute) DiskDetach(ctx context.Context, req DiskDetachRequest) (bool, error) {
|
func (c Compute) DiskDetach(ctx context.Context, req DiskDetachRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,21 +7,28 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for change QoS of the disk
|
||||||
type DiskQOSRequest struct {
|
type DiskQOSRequest struct {
|
||||||
|
// ID of compute instance
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
DiskID uint64 `url:"diskId"`
|
|
||||||
Limits string `url:"limits"`
|
// ID of the disk to apply limits
|
||||||
|
// Required: true
|
||||||
|
DiskID uint64 `url:"diskId"`
|
||||||
|
|
||||||
|
// Limit IO for a certain disk total and read/write options are not allowed to be combined
|
||||||
|
// Required: true
|
||||||
|
Limits string `url:"limits"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq DiskQOSRequest) Validate() error {
|
func (crq DiskQOSRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.DiskID == 0 {
|
if crq.DiskID == 0 {
|
||||||
return errors.New("validation-error: field DiskID can not be empty or equal to 0")
|
return errors.New("validation-error: field DiskID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Limits == "" {
|
if crq.Limits == "" {
|
||||||
return errors.New("validation-error: field Limits can not be empty")
|
return errors.New("validation-error: field Limits can not be empty")
|
||||||
}
|
}
|
||||||
@@ -29,8 +36,9 @@ func (crq DiskQOSRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DiskQOS change QoS of the disk
|
||||||
func (c Compute) DiskQOS(ctx context.Context, req DiskQOSRequest) (bool, error) {
|
func (c Compute) DiskQOS(ctx context.Context, req DiskQOSRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,21 +7,28 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for change disk size
|
||||||
type DiskResizeRequest struct {
|
type DiskResizeRequest struct {
|
||||||
|
// ID of compute instance
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
DiskID uint64 `url:"diskId"`
|
|
||||||
Size uint64 `url:"size"`
|
// ID of the disk to resize
|
||||||
|
// Required: true
|
||||||
|
DiskID uint64 `url:"diskId"`
|
||||||
|
|
||||||
|
// New disk size
|
||||||
|
// Required: true
|
||||||
|
Size uint64 `url:"size"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq DiskResizeRequest) Validate() error {
|
func (crq DiskResizeRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.DiskID == 0 {
|
if crq.DiskID == 0 {
|
||||||
return errors.New("validation-error: field DiskID can not be empty or equal to 0")
|
return errors.New("validation-error: field DiskID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Size == 0 {
|
if crq.Size == 0 {
|
||||||
return errors.New("validation-error: field Size can not be empty or equal to 0")
|
return errors.New("validation-error: field Size can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -29,8 +36,9 @@ func (crq DiskResizeRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DiskResize change disk size
|
||||||
func (c Compute) DiskResize(ctx context.Context, req DiskResizeRequest) (bool, error) {
|
func (c Compute) DiskResize(ctx context.Context, req DiskResizeRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for enable compute
|
||||||
type EnableRequest struct {
|
type EnableRequest struct {
|
||||||
|
// ID of compute instance
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq EnableRequest) Validate() error {
|
func (crq EnableRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (crq EnableRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Enable enables compute
|
||||||
func (c Compute) Enable(ctx context.Context, req EnableRequest) (bool, error) {
|
func (c Compute) Enable(ctx context.Context, req EnableRequest) (bool, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request for get information about compute
|
||||||
type GetRequest struct {
|
type GetRequest struct {
|
||||||
|
// ID of compute instance
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq GetRequest) Validate() error {
|
func (crq GetRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (crq GetRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c Compute) Get(ctx context.Context, req GetRequest) (*ComputeRecord, error) {
|
// Get Gets information about compute
|
||||||
err := req.Validate()
|
func (c Compute) Get(ctx context.Context, req GetRequest) (*RecordCompute, error) {
|
||||||
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@@ -32,11 +36,12 @@ func (c Compute) Get(ctx context.Context, req GetRequest) (*ComputeRecord, error
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
compute := &ComputeRecord{}
|
info := RecordCompute{}
|
||||||
err = json.Unmarshal(res, compute)
|
|
||||||
|
err = json.Unmarshal(res, &info)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return compute, nil
|
return &info, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get compute audits
|
||||||
type GetAuditsRequest struct {
|
type GetAuditsRequest struct {
|
||||||
|
// ID of compute instance
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq GetAuditsRequest) Validate() error {
|
func (crq GetAuditsRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (crq GetAuditsRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c Compute) GetAudits(ctx context.Context, req GetAuditsRequest) (AuditShortList, error) {
|
// GetAudits gets compute audits
|
||||||
err := req.Validate()
|
func (c Compute) GetAudits(ctx context.Context, req GetAuditsRequest) (ListShortAudits, error) {
|
||||||
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@@ -32,11 +36,12 @@ func (c Compute) GetAudits(ctx context.Context, req GetAuditsRequest) (AuditShor
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
auditsList := AuditShortList{}
|
list := ListShortAudits{}
|
||||||
err = json.Unmarshal(res, &auditsList)
|
|
||||||
|
err = json.Unmarshal(res, &list)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return auditsList, nil
|
return list, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"strings"
|
"strings"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get console URL
|
||||||
type GetConsoleURLRequest struct {
|
type GetConsoleURLRequest struct {
|
||||||
|
// ID of compute instance to get console for
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq GetConsoleURLRequest) Validate() error {
|
func (crq GetConsoleURLRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (crq GetConsoleURLRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GetConsoleURL gets computes console URL
|
||||||
func (c Compute) GetConsoleURL(ctx context.Context, req GetConsoleURLRequest) (string, error) {
|
func (c Compute) GetConsoleURL(ctx context.Context, req GetConsoleURLRequest) (string, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return "", err
|
return "", err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -6,16 +6,21 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get compute logs
|
||||||
type GetLogRequest struct {
|
type GetLogRequest struct {
|
||||||
|
// ID of compute instance to get log for
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
Path string `url:"path"`
|
|
||||||
|
// Path to log file
|
||||||
|
// Required: true
|
||||||
|
Path string `url:"path"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq GetLogRequest) Validate() error {
|
func (crq GetLogRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
|
|
||||||
if crq.Path == "" {
|
if crq.Path == "" {
|
||||||
return errors.New("validation-error: field Path can not be empty")
|
return errors.New("validation-error: field Path can not be empty")
|
||||||
}
|
}
|
||||||
@@ -23,8 +28,9 @@ func (crq GetLogRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GetLog gets compute's log file by path
|
||||||
func (c Compute) GetLog(ctx context.Context, req GetLogRequest) (string, error) {
|
func (c Compute) GetLog(ctx context.Context, req GetLogRequest) (string, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return "", err
|
return "", err
|
||||||
}
|
}
|
||||||
@@ -39,16 +45,15 @@ func (c Compute) GetLog(ctx context.Context, req GetLogRequest) (string, error)
|
|||||||
return string(res), nil
|
return string(res), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GetLogGet gets compute's log file by path
|
||||||
func (c Compute) GetLogGet(ctx context.Context, req GetLogRequest) (string, error) {
|
func (c Compute) GetLogGet(ctx context.Context, req GetLogRequest) (string, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return "", err
|
return "", err
|
||||||
}
|
}
|
||||||
|
|
||||||
url := "/compute/getLog"
|
url := "/cloudapi//compute/getLog"
|
||||||
prefix := "/cloudapi"
|
|
||||||
|
|
||||||
url = prefix + url
|
|
||||||
res, err := c.client.DecortApiCall(ctx, http.MethodGet, url, req)
|
res, err := c.client.DecortApiCall(ctx, http.MethodGet, url, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return "", err
|
return "", err
|
||||||
|
|||||||
@@ -6,14 +6,24 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get list available computes
|
||||||
type ListRequest struct {
|
type ListRequest struct {
|
||||||
IncludeDeleted bool `url:"includedeleted,omitempty"`
|
// Include deleted computes
|
||||||
Page uint64 `url:"page,omitempty"`
|
// Required: false
|
||||||
Size uint64 `url:"size,omitempty"`
|
IncludeDeleted bool `url:"includedeleted,omitempty"`
|
||||||
|
|
||||||
|
// Page number
|
||||||
|
// Required: false
|
||||||
|
Page uint64 `url:"page,omitempty"`
|
||||||
|
|
||||||
|
// Page size
|
||||||
|
// Required: false
|
||||||
|
Size uint64 `url:"size,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c Compute) List(ctx context.Context, req ListRequest) (ComputeList, error) {
|
// List gets list of the available computes.
|
||||||
|
// Filtering based on status is possible
|
||||||
|
func (c Compute) List(ctx context.Context, req ListRequest) (ListComputes, error) {
|
||||||
url := "/cloudapi/compute/list"
|
url := "/cloudapi/compute/list"
|
||||||
|
|
||||||
res, err := c.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := c.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
@@ -21,12 +31,12 @@ func (c Compute) List(ctx context.Context, req ListRequest) (ComputeList, error)
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
computeList := ComputeList{}
|
list := ListComputes{}
|
||||||
|
|
||||||
err = json.Unmarshal(res, &computeList)
|
err = json.Unmarshal(res, &list)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return computeList, nil
|
return list, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -6,13 +6,19 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get deleted computes list
|
||||||
type ListDeletedRequest struct {
|
type ListDeletedRequest struct {
|
||||||
|
// Page number
|
||||||
|
// Required: false
|
||||||
Page uint64 `url:"page,omitempty"`
|
Page uint64 `url:"page,omitempty"`
|
||||||
|
|
||||||
|
// Page size
|
||||||
|
// Required: false
|
||||||
Size uint64 `url:"size,omitempty"`
|
Size uint64 `url:"size,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c Compute) ListDeleted(ctx context.Context, req ListDeletedRequest) (ComputeList, error) {
|
// ListDeleted gets list all deleted computes
|
||||||
|
func (c Compute) ListDeleted(ctx context.Context, req ListDeletedRequest) (ListComputes, error) {
|
||||||
url := "/cloudapi/compute/listDeleted"
|
url := "/cloudapi/compute/listDeleted"
|
||||||
|
|
||||||
res, err := c.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
res, err := c.client.DecortApiCall(ctx, http.MethodPost, url, req)
|
||||||
@@ -20,12 +26,12 @@ func (c Compute) ListDeleted(ctx context.Context, req ListDeletedRequest) (Compu
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
computeList := ComputeList{}
|
list := ListComputes{}
|
||||||
|
|
||||||
err = json.Unmarshal(res, &computeList)
|
err = json.Unmarshal(res, &list)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return computeList, nil
|
return list, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get list PCI devices
|
||||||
type ListPCIDeviceRequest struct {
|
type ListPCIDeviceRequest struct {
|
||||||
|
// Identifier compute
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq ListPCIDeviceRequest) Validate() error {
|
func (crq ListPCIDeviceRequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (crq ListPCIDeviceRequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ListPCIDevice gets list PCI device
|
||||||
func (c Compute) ListPCIDevice(ctx context.Context, req ListPCIDeviceRequest) ([]interface{}, error) {
|
func (c Compute) ListPCIDevice(ctx context.Context, req ListPCIDeviceRequest) ([]interface{}, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@@ -32,12 +36,12 @@ func (c Compute) ListPCIDevice(ctx context.Context, req ListPCIDeviceRequest) ([
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
pciDeviceList := []interface{}{}
|
list := []interface{}{}
|
||||||
|
|
||||||
err = json.Unmarshal(res, &pciDeviceList)
|
err = json.Unmarshal(res, &list)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return pciDeviceList, nil
|
return list, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,11 +7,14 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Request struct for get list vGPU
|
||||||
type ListVGPURequest struct {
|
type ListVGPURequest struct {
|
||||||
|
// Identifier compute
|
||||||
|
// Required: true
|
||||||
ComputeID uint64 `url:"computeId"`
|
ComputeID uint64 `url:"computeId"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (crq ListVGPURequest) Validate() error {
|
func (crq ListVGPURequest) validate() error {
|
||||||
if crq.ComputeID == 0 {
|
if crq.ComputeID == 0 {
|
||||||
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
return errors.New("validation-error: field ComputeID can not be empty or equal to 0")
|
||||||
}
|
}
|
||||||
@@ -19,8 +22,9 @@ func (crq ListVGPURequest) Validate() error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ListVGPU gets list vGPU
|
||||||
func (c Compute) ListVGPU(ctx context.Context, req ListVGPURequest) ([]interface{}, error) {
|
func (c Compute) ListVGPU(ctx context.Context, req ListVGPURequest) ([]interface{}, error) {
|
||||||
err := req.Validate()
|
err := req.validate()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@@ -32,12 +36,12 @@ func (c Compute) ListVGPU(ctx context.Context, req ListVGPURequest) ([]interface
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
pciDeviceList := []interface{}{}
|
list := []interface{}{}
|
||||||
|
|
||||||
err = json.Unmarshal(res, &pciDeviceList)
|
err = json.Unmarshal(res, &list)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return pciDeviceList, nil
|
return list, nil
|
||||||
}
|
}
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user