traefik/vendor/github.com/sacloud/libsacloud/api/archive.go
Ludovic Fernandez 139f280f35 ACME TLS ALPN
2018-07-03 12:44:04 +02:00

344 lines
14 KiB
Go

package api
import (
"fmt"
"github.com/sacloud/libsacloud/sacloud"
"github.com/sacloud/libsacloud/sacloud/ostype"
"strings"
"time"
)
// ArchiveAPI アーカイブAPI
type ArchiveAPI struct {
*baseAPI
findFuncMapPerOSType map[ostype.ArchiveOSTypes]func() (*sacloud.Archive, error)
}
var (
archiveLatestStableCentOSTags = []string{"current-stable", "distro-centos"}
archiveLatestStableCentOS6Tags = []string{"distro-centos", "distro-ver-6.9"}
archiveLatestStableUbuntuTags = []string{"current-stable", "distro-ubuntu"}
archiveLatestStableDebianTags = []string{"current-stable", "distro-debian"}
archiveLatestStableVyOSTags = []string{"current-stable", "distro-vyos"}
archiveLatestStableCoreOSTags = []string{"current-stable", "distro-coreos"}
archiveLatestStableRancherOSTags = []string{"current-stable", "distro-rancheros"}
archiveLatestStableKusanagiTags = []string{"current-stable", "pkg-kusanagi"}
archiveLatestStableSophosUTMTags = []string{"current-stable", "pkg-sophosutm"}
archiveLatestStableFreeBSDTags = []string{"current-stable", "distro-freebsd"}
archiveLatestStableWindows2012Tags = []string{"os-windows", "distro-ver-2012.2"}
archiveLatestStableWindows2012RDSTags = []string{"os-windows", "distro-ver-2012.2", "windows-rds"}
archiveLatestStableWindows2012RDSOfficeTags = []string{"os-windows", "distro-ver-2012.2", "windows-rds", "with-office"}
archiveLatestStableWindows2016Tags = []string{"os-windows", "distro-ver-2016"}
archiveLatestStableWindows2016RDSTags = []string{"os-windows", "distro-ver-2016", "windows-rds"}
archiveLatestStableWindows2016RDSOfficeTags = []string{"os-windows", "distro-ver-2016", "windows-rds", "with-office"}
archiveLatestStableWindows2016SQLServerWeb = []string{"os-windows", "distro-ver-2016", "windows-sqlserver", "sqlserver-2016", "edition-web"}
archiveLatestStableWindows2016SQLServerStandard = []string{"os-windows", "distro-ver-2016", "windows-sqlserver", "sqlserver-2016", "edition-standard"}
archiveLatestStableWindows2016SQLServerStandardAll = []string{"os-windows", "distro-ver-2016", "windows-sqlserver", "sqlserver-2016", "edition-standard", "windows-rds", "with-office"}
)
// NewArchiveAPI アーカイブAPI作成
func NewArchiveAPI(client *Client) *ArchiveAPI {
api := &ArchiveAPI{
baseAPI: &baseAPI{
client: client,
FuncGetResourceURL: func() string {
return "archive"
},
},
}
api.findFuncMapPerOSType = map[ostype.ArchiveOSTypes]func() (*sacloud.Archive, error){
ostype.CentOS: api.FindLatestStableCentOS,
ostype.CentOS6: api.FindLatestStableCentOS6,
ostype.Ubuntu: api.FindLatestStableUbuntu,
ostype.Debian: api.FindLatestStableDebian,
ostype.VyOS: api.FindLatestStableVyOS,
ostype.CoreOS: api.FindLatestStableCoreOS,
ostype.RancherOS: api.FindLatestStableRancherOS,
ostype.Kusanagi: api.FindLatestStableKusanagi,
ostype.SophosUTM: api.FindLatestStableSophosUTM,
ostype.FreeBSD: api.FindLatestStableFreeBSD,
ostype.Windows2012: api.FindLatestStableWindows2012,
ostype.Windows2012RDS: api.FindLatestStableWindows2012RDS,
ostype.Windows2012RDSOffice: api.FindLatestStableWindows2012RDSOffice,
ostype.Windows2016: api.FindLatestStableWindows2016,
ostype.Windows2016RDS: api.FindLatestStableWindows2016RDS,
ostype.Windows2016RDSOffice: api.FindLatestStableWindows2016RDSOffice,
ostype.Windows2016SQLServerWeb: api.FindLatestStableWindows2016SQLServerWeb,
ostype.Windows2016SQLServerStandard: api.FindLatestStableWindows2016SQLServerStandard,
ostype.Windows2016SQLServerStandardAll: api.FindLatestStableWindows2016SQLServerStandardAll,
}
return api
}
// OpenFTP FTP接続開始
func (api *ArchiveAPI) OpenFTP(id int64) (*sacloud.FTPServer, error) {
var (
method = "PUT"
uri = fmt.Sprintf("%s/%d/ftp", api.getResourceURL(), id)
//body = map[string]bool{"ChangePassword": reset}
res = &sacloud.Response{}
)
result, err := api.action(method, uri, nil, res)
if !result || err != nil {
return nil, err
}
return res.FTPServer, nil
}
// CloseFTP FTP接続終了
func (api *ArchiveAPI) CloseFTP(id int64) (bool, error) {
var (
method = "DELETE"
uri = fmt.Sprintf("%s/%d/ftp", api.getResourceURL(), id)
)
return api.modify(method, uri, nil)
}
// SleepWhileCopying コピー終了まで待機
func (api *ArchiveAPI) SleepWhileCopying(id int64, timeout time.Duration) error {
handler := waitingForAvailableFunc(func() (hasAvailable, error) {
return api.Read(id)
}, 0)
return blockingPoll(handler, timeout)
}
// AsyncSleepWhileCopying コピー終了まで待機(非同期)
func (api *ArchiveAPI) AsyncSleepWhileCopying(id int64, timeout time.Duration) (chan (interface{}), chan (interface{}), chan (error)) {
handler := waitingForAvailableFunc(func() (hasAvailable, error) {
return api.Read(id)
}, 0)
return poll(handler, timeout)
}
// CanEditDisk ディスクの修正が可能か判定
func (api *ArchiveAPI) CanEditDisk(id int64) (bool, error) {
archive, err := api.Read(id)
if err != nil {
return false, err
}
if archive == nil {
return false, nil
}
// BundleInfoがあれば編集不可
if archive.BundleInfo != nil && archive.BundleInfo.HostClass == bundleInfoWindowsHostClass {
// Windows
return false, nil
}
// SophosUTMであれば編集不可
if archive.HasTag("pkg-sophosutm") || archive.IsSophosUTM() {
return false, nil
}
for _, t := range allowDiskEditTags {
if archive.HasTag(t) {
// 対応OSインストール済みディスク
return true, nil
}
}
// ここまできても判定できないならソースに投げる
if archive.SourceDisk != nil && archive.SourceDisk.Availability != "discontinued" {
return api.client.Disk.CanEditDisk(archive.SourceDisk.ID)
}
if archive.SourceArchive != nil && archive.SourceArchive.Availability != "discontinued" {
return api.client.Archive.CanEditDisk(archive.SourceArchive.ID)
}
return false, nil
}
// GetPublicArchiveIDFromAncestors 祖先の中からパブリックアーカイブのIDを検索
func (api *ArchiveAPI) GetPublicArchiveIDFromAncestors(id int64) (int64, bool) {
emptyID := int64(0)
archive, err := api.Read(id)
if err != nil {
return emptyID, false
}
if archive == nil {
return emptyID, false
}
// BundleInfoがあれば編集不可
if archive.BundleInfo != nil && archive.BundleInfo.HostClass == bundleInfoWindowsHostClass {
// Windows
return emptyID, false
}
// SophosUTMであれば編集不可
if archive.HasTag("pkg-sophosutm") || archive.IsSophosUTM() {
return emptyID, false
}
for _, t := range allowDiskEditTags {
if archive.HasTag(t) {
// 対応OSインストール済みディスク
return archive.ID, true
}
}
// ここまできても判定できないならソースに投げる
if archive.SourceDisk != nil && archive.SourceDisk.Availability != "discontinued" {
return api.client.Disk.GetPublicArchiveIDFromAncestors(archive.SourceDisk.ID)
}
if archive.SourceArchive != nil && archive.SourceArchive.Availability != "discontinued" {
return api.client.Archive.GetPublicArchiveIDFromAncestors(archive.SourceArchive.ID)
}
return emptyID, false
}
// FindLatestStableCentOS 安定版最新のCentOSパブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableCentOS() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableCentOSTags)
}
// FindLatestStableCentOS6 安定版最新のCentOS6パブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableCentOS6() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableCentOS6Tags)
}
// FindLatestStableDebian 安定版最新のDebianパブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableDebian() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableDebianTags)
}
// FindLatestStableUbuntu 安定版最新のUbuntuパブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableUbuntu() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableUbuntuTags)
}
// FindLatestStableVyOS 安定版最新のVyOSパブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableVyOS() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableVyOSTags)
}
// FindLatestStableCoreOS 安定版最新のCoreOSパブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableCoreOS() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableCoreOSTags)
}
// FindLatestStableRancherOS 安定版最新のRancherOSパブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableRancherOS() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableRancherOSTags)
}
// FindLatestStableKusanagi 安定版最新のKusanagiパブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableKusanagi() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableKusanagiTags)
}
// FindLatestStableSophosUTM 安定板最新のSophosUTMパブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableSophosUTM() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableSophosUTMTags)
}
// FindLatestStableFreeBSD 安定版最新のFreeBSDパブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableFreeBSD() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableFreeBSDTags)
}
// FindLatestStableWindows2012 安定版最新のWindows2012パブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableWindows2012() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableWindows2012Tags, map[string]interface{}{
"Name": "Windows Server 2012 R2 Datacenter Edition",
})
}
// FindLatestStableWindows2012RDS 安定版最新のWindows2012RDSパブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableWindows2012RDS() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableWindows2012RDSTags, map[string]interface{}{
"Name": "Windows Server 2012 R2 for RDS",
})
}
// FindLatestStableWindows2012RDSOffice 安定版最新のWindows2012RDS(Office)パブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableWindows2012RDSOffice() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableWindows2012RDSOfficeTags, map[string]interface{}{
"Name": "Windows Server 2012 R2 for RDS(MS Office付)",
})
}
// FindLatestStableWindows2016 安定版最新のWindows2016パブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableWindows2016() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableWindows2016Tags, map[string]interface{}{
"Name": "Windows Server 2016 Datacenter Edition",
})
}
// FindLatestStableWindows2016RDS 安定版最新のWindows2016RDSパブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableWindows2016RDS() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableWindows2016RDSTags, map[string]interface{}{
"Name": "Windows Server 2016 for RDS",
})
}
// FindLatestStableWindows2016RDSOffice 安定版最新のWindows2016RDS(Office)パブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableWindows2016RDSOffice() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableWindows2016RDSOfficeTags, map[string]interface{}{
"Name": "Windows Server 2016 for RDS(MS Office付)",
})
}
// FindLatestStableWindows2016SQLServerWeb 安定版最新のWindows2016 SQLServer(Web) パブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableWindows2016SQLServerWeb() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableWindows2016SQLServerWeb, map[string]interface{}{
"Name": "Windows Server 2016 for MS SQL 2016(Web)",
})
}
// FindLatestStableWindows2016SQLServerStandard 安定版最新のWindows2016 SQLServer(Standard) パブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableWindows2016SQLServerStandard() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableWindows2016SQLServerStandard, map[string]interface{}{
"Name": "Windows Server 2016 for MS SQL 2016(Standard)",
})
}
// FindLatestStableWindows2016SQLServerStandardAll 安定版最新のWindows2016 SQLServer(RDS+Office) パブリックアーカイブを取得
func (api *ArchiveAPI) FindLatestStableWindows2016SQLServerStandardAll() (*sacloud.Archive, error) {
return api.findByOSTags(archiveLatestStableWindows2016SQLServerStandard, map[string]interface{}{
"Name": "Windows Server 2016 for MS SQL 2016(Std) with RDS / MS Office",
})
}
// FindByOSType 指定のOS種別の安定版最新のパブリックアーカイブを取得
func (api *ArchiveAPI) FindByOSType(os ostype.ArchiveOSTypes) (*sacloud.Archive, error) {
if f, ok := api.findFuncMapPerOSType[os]; ok {
return f()
}
return nil, fmt.Errorf("OSType [%s] is invalid", os)
}
func (api *ArchiveAPI) findByOSTags(tags []string, filterMap ...map[string]interface{}) (*sacloud.Archive, error) {
api.Reset().WithTags(tags)
for _, filters := range filterMap {
for key, filter := range filters {
api.FilterMultiBy(key, filter)
}
}
res, err := api.Find()
if err != nil {
return nil, fmt.Errorf("Archive [%s] error : %s", strings.Join(tags, ","), err)
}
if len(res.Archives) == 0 {
return nil, fmt.Errorf("Archive [%s] Not Found", strings.Join(tags, ","))
}
return &res.Archives[0], nil
}