15003: Add dispatch-cloud configs to default/template file.
[arvados.git] / sdk / go / arvados / config.go
index 6edd18418bb8015087f8b486acf6ee21d2d26db4..b25164c3d159c310284efb1b0889cdc2db3c7445 100644 (file)
@@ -8,6 +8,7 @@ import (
        "encoding/json"
        "errors"
        "fmt"
+       "net/url"
        "os"
 
        "git.curoverse.com/arvados.git/sdk/go/config"
@@ -50,14 +51,70 @@ func (sc *Config) GetCluster(clusterID string) (*Cluster, error) {
        }
 }
 
+type API struct {
+       MaxItemsPerResponse     int
+       MaxRequestAmplification int
+       RequestTimeout          Duration
+}
+
 type Cluster struct {
-       ClusterID          string `json:"-"`
-       ManagementToken    string
-       NodeProfiles       map[string]NodeProfile
-       InstanceTypes      InstanceTypeMap
-       HTTPRequestTimeout Duration
-       RemoteClusters     map[string]RemoteCluster
-       PostgreSQL         PostgreSQL
+       ClusterID       string `json:"-"`
+       ManagementToken string
+       SystemRootToken string
+       Services        Services
+       NodeProfiles    map[string]NodeProfile
+       InstanceTypes   InstanceTypeMap
+       Containers      ContainersConfig
+       RemoteClusters  map[string]RemoteCluster
+       PostgreSQL      PostgreSQL
+       API             API
+       SystemLogs      SystemLogs
+       TLS             TLS
+}
+
+type Services struct {
+       Controller    Service
+       DispatchCloud Service
+       Health        Service
+       Keepbalance   Service
+       Keepproxy     Service
+       Keepstore     Service
+       Nodemanager   Service
+       RailsAPI      Service
+       WebDAV        Service
+       Websocket     Service
+       Workbench1    Service
+       Workbench2    Service
+}
+
+type Service struct {
+       InternalURLs map[URL]ServiceInstance `json:",omitempty"`
+       ExternalURL  URL
+}
+
+// URL is a url.URL that is also usable as a JSON key/value.
+type URL url.URL
+
+// UnmarshalText implements encoding.TextUnmarshaler so URL can be
+// used as a JSON key/value.
+func (su *URL) UnmarshalText(text []byte) error {
+       u, err := url.Parse(string(text))
+       if err == nil {
+               *su = URL(*u)
+       }
+       return err
+}
+
+func (su URL) MarshalText() ([]byte, error) {
+       return []byte(fmt.Sprintf("%s", (*url.URL)(&su).String())), nil
+}
+
+type ServiceInstance struct{}
+
+type SystemLogs struct {
+       LogLevel                string
+       Format                  string
+       MaxRequestLogParamsSize int
 }
 
 type PostgreSQL struct {
@@ -80,13 +137,43 @@ type RemoteCluster struct {
 }
 
 type InstanceType struct {
-       Name         string
-       ProviderType string
-       VCPUs        int
-       RAM          ByteSize
-       Scratch      ByteSize
-       Price        float64
-       Preemptible  bool
+       Name            string
+       ProviderType    string
+       VCPUs           int
+       RAM             ByteSize
+       Scratch         ByteSize
+       IncludedScratch ByteSize
+       AddedScratch    ByteSize
+       Price           float64
+       Preemptible     bool
+}
+
+type ContainersConfig struct {
+       CloudVMs           CloudVMsConfig
+       DispatchPrivateKey string
+       StaleLockTimeout   Duration
+}
+
+type CloudVMsConfig struct {
+       Enable bool
+
+       BootProbeCommand     string
+       ImageID              string
+       MaxCloudOpsPerSecond int
+       MaxProbesPerSecond   int
+       PollInterval         Duration
+       ProbeInterval        Duration
+       SSHPort              string
+       SyncInterval         Duration
+       TimeoutBooting       Duration
+       TimeoutIdle          Duration
+       TimeoutProbe         Duration
+       TimeoutShutdown      Duration
+       TimeoutSignal        Duration
+       TimeoutTERM          Duration
+
+       Driver           string
+       DriverParameters json.RawMessage
 }
 
 type InstanceTypeMap map[string]InstanceType
@@ -111,6 +198,20 @@ func (it *InstanceTypeMap) UnmarshalJSON(data []byte) error {
                        if _, ok := (*it)[t.Name]; ok {
                                return errDuplicateInstanceTypeName
                        }
+                       if t.ProviderType == "" {
+                               t.ProviderType = t.Name
+                       }
+                       if t.Scratch == 0 {
+                               t.Scratch = t.IncludedScratch + t.AddedScratch
+                       } else if t.AddedScratch == 0 {
+                               t.AddedScratch = t.Scratch - t.IncludedScratch
+                       } else if t.IncludedScratch == 0 {
+                               t.IncludedScratch = t.Scratch - t.AddedScratch
+                       }
+
+                       if t.Scratch != (t.IncludedScratch + t.AddedScratch) {
+                               return fmt.Errorf("%v: Scratch != (IncludedScratch + AddedScratch)", t.Name)
+                       }
                        (*it)[t.Name] = t
                }
                return nil
@@ -120,10 +221,14 @@ func (it *InstanceTypeMap) UnmarshalJSON(data []byte) error {
        if err != nil {
                return err
        }
-       // Fill in Name field using hash key.
+       // Fill in Name field (and ProviderType field, if not
+       // specified) using hash key.
        *it = InstanceTypeMap(hash)
        for name, t := range *it {
                t.Name = name
+               if t.ProviderType == "" {
+                       t.ProviderType = name
+               }
                (*it)[name] = t
        }
        return nil
@@ -153,42 +258,48 @@ func (cc *Cluster) GetNodeProfile(node string) (*NodeProfile, error) {
 }
 
 type NodeProfile struct {
-       Controller  SystemServiceInstance `json:"arvados-controller"`
-       Health      SystemServiceInstance `json:"arvados-health"`
-       Keepproxy   SystemServiceInstance `json:"keepproxy"`
-       Keepstore   SystemServiceInstance `json:"keepstore"`
-       Keepweb     SystemServiceInstance `json:"keep-web"`
-       Nodemanager SystemServiceInstance `json:"arvados-node-manager"`
-       RailsAPI    SystemServiceInstance `json:"arvados-api-server"`
-       Websocket   SystemServiceInstance `json:"arvados-ws"`
-       Workbench   SystemServiceInstance `json:"arvados-workbench"`
+       Controller    SystemServiceInstance `json:"arvados-controller"`
+       Health        SystemServiceInstance `json:"arvados-health"`
+       Keepbalance   SystemServiceInstance `json:"keep-balance"`
+       Keepproxy     SystemServiceInstance `json:"keepproxy"`
+       Keepstore     SystemServiceInstance `json:"keepstore"`
+       Keepweb       SystemServiceInstance `json:"keep-web"`
+       Nodemanager   SystemServiceInstance `json:"arvados-node-manager"`
+       DispatchCloud SystemServiceInstance `json:"arvados-dispatch-cloud"`
+       RailsAPI      SystemServiceInstance `json:"arvados-api-server"`
+       Websocket     SystemServiceInstance `json:"arvados-ws"`
+       Workbench     SystemServiceInstance `json:"arvados-workbench"`
 }
 
 type ServiceName string
 
 const (
-       ServiceNameRailsAPI    ServiceName = "arvados-api-server"
-       ServiceNameController  ServiceName = "arvados-controller"
-       ServiceNameNodemanager ServiceName = "arvados-node-manager"
-       ServiceNameWorkbench   ServiceName = "arvados-workbench"
-       ServiceNameWebsocket   ServiceName = "arvados-ws"
-       ServiceNameKeepweb     ServiceName = "keep-web"
-       ServiceNameKeepproxy   ServiceName = "keepproxy"
-       ServiceNameKeepstore   ServiceName = "keepstore"
+       ServiceNameRailsAPI      ServiceName = "arvados-api-server"
+       ServiceNameController    ServiceName = "arvados-controller"
+       ServiceNameDispatchCloud ServiceName = "arvados-dispatch-cloud"
+       ServiceNameNodemanager   ServiceName = "arvados-node-manager"
+       ServiceNameWorkbench     ServiceName = "arvados-workbench"
+       ServiceNameWebsocket     ServiceName = "arvados-ws"
+       ServiceNameKeepbalance   ServiceName = "keep-balance"
+       ServiceNameKeepweb       ServiceName = "keep-web"
+       ServiceNameKeepproxy     ServiceName = "keepproxy"
+       ServiceNameKeepstore     ServiceName = "keepstore"
 )
 
 // ServicePorts returns the configured listening address (or "" if
 // disabled) for each service on the node.
 func (np *NodeProfile) ServicePorts() map[ServiceName]string {
        return map[ServiceName]string{
-               ServiceNameRailsAPI:    np.RailsAPI.Listen,
-               ServiceNameController:  np.Controller.Listen,
-               ServiceNameNodemanager: np.Nodemanager.Listen,
-               ServiceNameWorkbench:   np.Workbench.Listen,
-               ServiceNameWebsocket:   np.Websocket.Listen,
-               ServiceNameKeepweb:     np.Keepweb.Listen,
-               ServiceNameKeepproxy:   np.Keepproxy.Listen,
-               ServiceNameKeepstore:   np.Keepstore.Listen,
+               ServiceNameRailsAPI:      np.RailsAPI.Listen,
+               ServiceNameController:    np.Controller.Listen,
+               ServiceNameDispatchCloud: np.DispatchCloud.Listen,
+               ServiceNameNodemanager:   np.Nodemanager.Listen,
+               ServiceNameWorkbench:     np.Workbench.Listen,
+               ServiceNameWebsocket:     np.Websocket.Listen,
+               ServiceNameKeepbalance:   np.Keepbalance.Listen,
+               ServiceNameKeepweb:       np.Keepweb.Listen,
+               ServiceNameKeepproxy:     np.Keepproxy.Listen,
+               ServiceNameKeepstore:     np.Keepstore.Listen,
        }
 }
 
@@ -197,3 +308,9 @@ type SystemServiceInstance struct {
        TLS      bool
        Insecure bool
 }
+
+type TLS struct {
+       Certificate string
+       Key         string
+       Insecure    bool
+}