|
|
|
@ -18,7 +18,7 @@ package main
|
|
|
|
|
|
|
|
|
|
import (
|
|
|
|
|
"encoding/json"
|
|
|
|
|
"flag"
|
|
|
|
|
"errors"
|
|
|
|
|
"fmt"
|
|
|
|
|
"io"
|
|
|
|
|
"io/ioutil"
|
|
|
|
@ -32,21 +32,20 @@ import (
|
|
|
|
|
|
|
|
|
|
"github.com/ghodss/yaml"
|
|
|
|
|
"github.com/gorilla/mux"
|
|
|
|
|
|
|
|
|
|
"github.com/kubernetes/deployment-manager/cmd/manager/manager"
|
|
|
|
|
"github.com/kubernetes/deployment-manager/cmd/manager/repository"
|
|
|
|
|
"github.com/kubernetes/deployment-manager/cmd/manager/repository/persistent"
|
|
|
|
|
"github.com/kubernetes/deployment-manager/cmd/manager/repository/transient"
|
|
|
|
|
"github.com/kubernetes/deployment-manager/cmd/manager/router"
|
|
|
|
|
"github.com/kubernetes/deployment-manager/pkg/common"
|
|
|
|
|
"github.com/kubernetes/deployment-manager/pkg/httputil"
|
|
|
|
|
"github.com/kubernetes/deployment-manager/pkg/registry"
|
|
|
|
|
"github.com/kubernetes/deployment-manager/pkg/util"
|
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
var deployments = []Route{
|
|
|
|
|
{"ListDeployments", "/deployments", "GET", listDeploymentsHandlerFunc, ""},
|
|
|
|
|
{"GetDeployment", "/deployments/{deployment}", "GET", getDeploymentHandlerFunc, ""},
|
|
|
|
|
{"CreateDeployment", "/deployments", "POST", createDeploymentHandlerFunc, "JSON"},
|
|
|
|
|
{"DeleteDeployment", "/deployments/{deployment}", "DELETE", deleteDeploymentHandlerFunc, ""},
|
|
|
|
|
{"DeleteDeplyment", "/deployments/{deployment}", "DELETE", deleteDeploymentHandlerFunc, ""},
|
|
|
|
|
{"PutDeployment", "/deployments/{deployment}", "PUT", putDeploymentHandlerFunc, "JSON"},
|
|
|
|
|
{"ListManifests", "/deployments/{deployment}/manifests", "GET", listManifestsHandlerFunc, ""},
|
|
|
|
|
{"GetManifest", "/deployments/{deployment}/manifests/{manifest}", "GET", getManifestHandlerFunc, ""},
|
|
|
|
@ -65,57 +64,83 @@ var deployments = []Route{
|
|
|
|
|
{"GetCredential", "/credentials/{credential}", "GET", getCredentialHandlerFunc, ""},
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
var (
|
|
|
|
|
maxLength = flag.Int64("maxLength", 1024, "The maximum length (KB) of a template.")
|
|
|
|
|
expanderName = flag.String("expander", "expandybird-service", "The DNS name of the expander service.")
|
|
|
|
|
expanderURL = flag.String("expanderURL", "", "The URL for the expander service.")
|
|
|
|
|
deployerName = flag.String("deployer", "resourcifier-service", "The DNS name of the deployer service.")
|
|
|
|
|
deployerURL = flag.String("deployerURL", "", "The URL for the deployer service.")
|
|
|
|
|
credentialFile = flag.String("credentialFile", "", "Local file to use for credentials.")
|
|
|
|
|
credentialSecrets = flag.Bool("credentialSecrets", true, "Use secrets for credentials.")
|
|
|
|
|
mongoName = flag.String("mongoName", "mongodb", "The DNS name of the mongodb service.")
|
|
|
|
|
mongoPort = flag.String("mongoPort", "27017", "The port of the mongodb service.")
|
|
|
|
|
mongoAddress = flag.String("mongoAddress", "mongodb:27017", "The address of the mongodb service.")
|
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
// Deprecated. Use Context.Manager instead.
|
|
|
|
|
var backend manager.Manager
|
|
|
|
|
|
|
|
|
|
func init() {
|
|
|
|
|
if !flag.Parsed() {
|
|
|
|
|
flag.Parse()
|
|
|
|
|
// Route defines a routing table entry to be registered with gorilla/mux.
|
|
|
|
|
//
|
|
|
|
|
// Route is deprecated. Use router.Routes instead.
|
|
|
|
|
type Route struct {
|
|
|
|
|
Name string
|
|
|
|
|
Path string
|
|
|
|
|
Methods string
|
|
|
|
|
HandlerFunc http.HandlerFunc
|
|
|
|
|
Type string
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
func registerRoutes(c *router.Context, h *router.Handler) {
|
|
|
|
|
re := regexp.MustCompile("{[a-z]+}")
|
|
|
|
|
|
|
|
|
|
h.Add("GET /healthz", healthz)
|
|
|
|
|
h.Add("GET /deployments", listDeploymentsHandlerFunc)
|
|
|
|
|
h.Add("GET /deployments/*", getDeploymentHandlerFunc)
|
|
|
|
|
|
|
|
|
|
// TODO: Replace these routes with updated ones.
|
|
|
|
|
for _, d := range deployments {
|
|
|
|
|
path := fmt.Sprintf("%s %s", d.Methods, re.ReplaceAllString(d.Path, "*"))
|
|
|
|
|
fmt.Printf("\t%s\n", path)
|
|
|
|
|
h.Add(path, func(w http.ResponseWriter, r *http.Request, c *router.Context) error {
|
|
|
|
|
d.HandlerFunc(w, r)
|
|
|
|
|
return nil
|
|
|
|
|
})
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
routes = append(routes, deployments...)
|
|
|
|
|
func healthz(w http.ResponseWriter, r *http.Request, c *router.Context) error {
|
|
|
|
|
log.Println("manager: healthz checkpoint")
|
|
|
|
|
// TODO: This should check the availability of the repository, and fail if it
|
|
|
|
|
// cannot connect.
|
|
|
|
|
fmt.Fprintln(w, "OK")
|
|
|
|
|
return nil
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
func setupDependencies(c *router.Context) error {
|
|
|
|
|
var credentialProvider common.CredentialProvider
|
|
|
|
|
if *credentialFile != "" {
|
|
|
|
|
if *credentialSecrets {
|
|
|
|
|
panic(fmt.Errorf("Both credentialFile and credentialSecrets are set"))
|
|
|
|
|
if c.Config.CredentialFile != "" {
|
|
|
|
|
if c.Config.CredentialSecrets {
|
|
|
|
|
return errors.New("Both credentialFile and credentialSecrets are set")
|
|
|
|
|
}
|
|
|
|
|
var err error
|
|
|
|
|
credentialProvider, err = registry.NewFilebasedCredentialProvider(*credentialFile)
|
|
|
|
|
credentialProvider, err = registry.NewFilebasedCredentialProvider(c.Config.CredentialFile)
|
|
|
|
|
if err != nil {
|
|
|
|
|
panic(fmt.Errorf("cannot create credential provider %s: %s", *credentialFile, err))
|
|
|
|
|
return fmt.Errorf("cannot create credential provider %s: %s", c.Config.CredentialFile, err)
|
|
|
|
|
}
|
|
|
|
|
} else if *credentialSecrets {
|
|
|
|
|
credentialProvider = registry.NewSecretsCredentialProvider()
|
|
|
|
|
} else {
|
|
|
|
|
credentialProvider = registry.NewInmemCredentialProvider()
|
|
|
|
|
}
|
|
|
|
|
backend = newManager(credentialProvider)
|
|
|
|
|
c.CredentialProvider = credentialProvider
|
|
|
|
|
c.Manager = newManager(c)
|
|
|
|
|
|
|
|
|
|
// FIXME: As soon as we can, we need to get rid of this.
|
|
|
|
|
backend = c.Manager
|
|
|
|
|
return nil
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const expanderPort = "8080"
|
|
|
|
|
const deployerPort = "8080"
|
|
|
|
|
|
|
|
|
|
func newManager(cp common.CredentialProvider) manager.Manager {
|
|
|
|
|
func newManager(c *router.Context) manager.Manager {
|
|
|
|
|
cfg := c.Config
|
|
|
|
|
service := registry.NewInmemRegistryService()
|
|
|
|
|
registryProvider := registry.NewDefaultRegistryProvider(cp, service)
|
|
|
|
|
registryProvider := registry.NewDefaultRegistryProvider(c.CredentialProvider, service)
|
|
|
|
|
resolver := manager.NewTypeResolver(registryProvider, util.DefaultHTTPClient())
|
|
|
|
|
expander := manager.NewExpander(getServiceURL(*expanderURL, *expanderName, expanderPort), resolver)
|
|
|
|
|
deployer := manager.NewDeployer(getServiceURL(*deployerURL, *deployerName, deployerPort))
|
|
|
|
|
address := strings.TrimPrefix(getServiceURL(*mongoAddress, *mongoName, *mongoPort), "http://")
|
|
|
|
|
expander := manager.NewExpander(getServiceURL(cfg.ExpanderURL, cfg.ExpanderName, expanderPort), resolver)
|
|
|
|
|
deployer := manager.NewDeployer(getServiceURL(cfg.DeployerURL, cfg.DeployerName, deployerPort))
|
|
|
|
|
address := strings.TrimPrefix(getServiceURL(cfg.MongoAddress, cfg.MongoName, cfg.MongoPort), "http://")
|
|
|
|
|
repository := createRepository(address)
|
|
|
|
|
return manager.NewManager(expander, deployer, repository, registryProvider, service, cp)
|
|
|
|
|
return manager.NewManager(expander, deployer, repository, registryProvider, service, c.CredentialProvider)
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
func createRepository(address string) repository.Repository {
|
|
|
|
@ -162,13 +187,13 @@ func makeEnvVariableName(str string) string {
|
|
|
|
|
return strings.ToUpper(strings.Replace(str, "-", "_", -1))
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
func listDeploymentsHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
func listDeploymentsHandlerFunc(w http.ResponseWriter, r *http.Request, c *router.Context) error {
|
|
|
|
|
handler := "manager: list deployments"
|
|
|
|
|
util.LogHandlerEntry(handler, r)
|
|
|
|
|
l, err := backend.ListDeployments()
|
|
|
|
|
if err != nil {
|
|
|
|
|
util.LogAndReturnError(handler, http.StatusInternalServerError, err, w)
|
|
|
|
|
return
|
|
|
|
|
return nil
|
|
|
|
|
}
|
|
|
|
|
var names []string
|
|
|
|
|
for _, d := range l {
|
|
|
|
@ -176,23 +201,25 @@ func listDeploymentsHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
util.LogHandlerExitWithJSON(handler, w, names, http.StatusOK)
|
|
|
|
|
return nil
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
func getDeploymentHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
func getDeploymentHandlerFunc(w http.ResponseWriter, r *http.Request, c *router.Context) error {
|
|
|
|
|
handler := "manager: get deployment"
|
|
|
|
|
util.LogHandlerEntry(handler, r)
|
|
|
|
|
name, err := getPathVariable(w, r, "deployment", handler)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return
|
|
|
|
|
return nil
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
d, err := backend.GetDeployment(name)
|
|
|
|
|
if err != nil {
|
|
|
|
|
util.LogAndReturnError(handler, http.StatusBadRequest, err, w)
|
|
|
|
|
return
|
|
|
|
|
return nil
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
util.LogHandlerExitWithJSON(handler, w, d, http.StatusOK)
|
|
|
|
|
return nil
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
func createDeploymentHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
@ -216,7 +243,7 @@ func deleteDeploymentHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
handler := "manager: delete deployment"
|
|
|
|
|
util.LogHandlerEntry(handler, r)
|
|
|
|
|
defer r.Body.Close()
|
|
|
|
|
name, err := getPathVariable(w, r, "deployment", handler)
|
|
|
|
|
name, err := pos(w, r, 2) //getPathVariable(w, r, "deployment", handler)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
@ -234,7 +261,7 @@ func putDeploymentHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
handler := "manager: update deployment"
|
|
|
|
|
util.LogHandlerEntry(handler, r)
|
|
|
|
|
defer r.Body.Close()
|
|
|
|
|
name, err := getPathVariable(w, r, "deployment", handler)
|
|
|
|
|
name, err := pos(w, r, 2) //getPathVariable(w, r, "deployment", handler)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
@ -251,6 +278,15 @@ func putDeploymentHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
func pos(w http.ResponseWriter, r *http.Request, i int) (string, error) {
|
|
|
|
|
parts := strings.Split(r.URL.Path, "/")
|
|
|
|
|
if len(parts) < i-1 {
|
|
|
|
|
httputil.BadRequest(w, r)
|
|
|
|
|
return "", fmt.Errorf("No index for %d", i)
|
|
|
|
|
}
|
|
|
|
|
return parts[i], nil
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
func getPathVariable(w http.ResponseWriter, r *http.Request, variable, handler string) (string, error) {
|
|
|
|
|
vars := mux.Vars(r)
|
|
|
|
|
escaped, ok := vars[variable]
|
|
|
|
@ -291,7 +327,7 @@ func getTemplate(w http.ResponseWriter, r *http.Request, handler string) *common
|
|
|
|
|
func listManifestsHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
handler := "manager: list manifests"
|
|
|
|
|
util.LogHandlerEntry(handler, r)
|
|
|
|
|
deploymentName, err := getPathVariable(w, r, "deployment", handler)
|
|
|
|
|
deploymentName, err := pos(w, r, 2)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
@ -313,12 +349,12 @@ func listManifestsHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
func getManifestHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
handler := "manager: get manifest"
|
|
|
|
|
util.LogHandlerEntry(handler, r)
|
|
|
|
|
deploymentName, err := getPathVariable(w, r, "deployment", handler)
|
|
|
|
|
deploymentName, err := pos(w, r, 2)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
manifestName, err := getPathVariable(w, r, "manifest", handler)
|
|
|
|
|
manifestName, err := pos(w, r, 4)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
@ -366,7 +402,7 @@ func listTypesHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
func listTypeInstancesHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
handler := "manager: list instances"
|
|
|
|
|
util.LogHandlerEntry(handler, r)
|
|
|
|
|
typeName, err := getPathVariable(w, r, "type", handler)
|
|
|
|
|
typeName, err := pos(w, r, 2)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
@ -383,7 +419,7 @@ func listTypeInstancesHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
func getRegistryForTypeHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
handler := "manager: get type registry"
|
|
|
|
|
util.LogHandlerEntry(handler, r)
|
|
|
|
|
typeName, err := getPathVariable(w, r, "type", handler)
|
|
|
|
|
typeName, err := pos(w, r, 2)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
@ -400,7 +436,7 @@ func getRegistryForTypeHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
func getMetadataForTypeHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
handler := "manager: get type metadata"
|
|
|
|
|
util.LogHandlerEntry(handler, r)
|
|
|
|
|
typeName, err := getPathVariable(w, r, "type", handler)
|
|
|
|
|
typeName, err := pos(w, r, 2)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
@ -430,7 +466,7 @@ func listRegistriesHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
func getRegistryHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
handler := "manager: get registry"
|
|
|
|
|
util.LogHandlerEntry(handler, r)
|
|
|
|
|
registryName, err := getPathVariable(w, r, "registry", handler)
|
|
|
|
|
registryName, err := pos(w, r, 2)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
@ -465,7 +501,7 @@ func createRegistryHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
handler := "manager: create registry"
|
|
|
|
|
util.LogHandlerEntry(handler, r)
|
|
|
|
|
defer r.Body.Close()
|
|
|
|
|
registryName, err := getPathVariable(w, r, "registry", handler)
|
|
|
|
|
registryName, err := pos(w, r, 2)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
@ -490,7 +526,7 @@ func createRegistryHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
func listRegistryTypesHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
handler := "manager: list registry types"
|
|
|
|
|
util.LogHandlerEntry(handler, r)
|
|
|
|
|
registryName, err := getPathVariable(w, r, "registry", handler)
|
|
|
|
|
registryName, err := pos(w, r, 2)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
@ -523,12 +559,12 @@ func listRegistryTypesHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
func getDownloadURLsHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
handler := "manager: get download URLs"
|
|
|
|
|
util.LogHandlerEntry(handler, r)
|
|
|
|
|
registryName, err := getPathVariable(w, r, "registry", handler)
|
|
|
|
|
registryName, err := pos(w, r, 2)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
typeName, err := getPathVariable(w, r, "type", handler)
|
|
|
|
|
typeName, err := pos(w, r, 4)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
@ -555,7 +591,7 @@ func getDownloadURLsHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
func getFileHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
handler := "manager: get file"
|
|
|
|
|
util.LogHandlerEntry(handler, r)
|
|
|
|
|
registryName, err := getPathVariable(w, r, "registry", handler)
|
|
|
|
|
registryName, err := pos(w, r, 2)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
@ -595,7 +631,7 @@ func createCredentialHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
handler := "manager: create credential"
|
|
|
|
|
util.LogHandlerEntry(handler, r)
|
|
|
|
|
defer r.Body.Close()
|
|
|
|
|
credentialName, err := getPathVariable(w, r, "credential", handler)
|
|
|
|
|
credentialName, err := pos(w, r, 2)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
@ -615,7 +651,7 @@ func createCredentialHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
func getCredentialHandlerFunc(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
handler := "manager: get credential"
|
|
|
|
|
util.LogHandlerEntry(handler, r)
|
|
|
|
|
credentialName, err := getPathVariable(w, r, "credential", handler)
|
|
|
|
|
credentialName, err := pos(w, r, 2)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|