Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
46 changes: 45 additions & 1 deletion e2e/tests/deploy/deploy.go
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,51 @@ var _ = DevSpaceDescribe("deploy", func() {
})

ginkgo.It("should deploy kustomize application", func() {
// TODO
tempDir, err := framework.CopyToTempDir("tests/deploy/testdata/kustomize")
framework.ExpectNoError(err)
defer framework.CleanupTempDir(initialDir, tempDir)

ns, err := kubeClient.CreateNamespace("deploy")
framework.ExpectNoError(err)
defer func() {
err := kubeClient.DeleteNamespace(ns)
framework.ExpectNoError(err)
}()

// create a new deploy command
deployCmd := &cmd.RunPipelineCmd{
GlobalFlags: &flags.GlobalFlags{
NoWarn: true,
Namespace: ns,
},
Pipeline: "deploy",
}

// run the command
err = deployCmd.RunDefault(f)
framework.ExpectNoError(err)

// check if services are there
service, err := kubeClient.RawClient().CoreV1().Services(ns).Get(context.TODO(), "my-service", metav1.GetOptions{})
framework.ExpectNoError(err)
framework.ExpectEqual(service.Labels["kustomize-app"], "devspace")

// create a new purge command
purgeCmd := &cmd.RunPipelineCmd{
GlobalFlags: &flags.GlobalFlags{
NoWarn: true,
Namespace: ns,
},
Pipeline: "purge",
}

// run the command
err = purgeCmd.RunDefault(f)
framework.ExpectNoError(err)

// check if services are there
_, err = kubeClient.RawClient().CoreV1().Services(ns).Get(context.TODO(), "my-service", metav1.GetOptions{})
framework.ExpectError(err)
})

ginkgo.It("should deploy multiple namespaces", func() {
Expand Down
2 changes: 0 additions & 2 deletions e2e/tests/deploy/testdata/different_namespaces/devspace.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,6 @@ vars:

deployments:
helm:
namespace: ""
helm:
chart:
path: chart
Expand All @@ -16,7 +15,6 @@ deployments:
namespace2: ${NAMESPACE2}

kubectl:
namespace: ""
kubectl:
manifests:
- kube
8 changes: 8 additions & 0 deletions e2e/tests/deploy/testdata/kustomize/devspace.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
version: v2beta1

deployments:
my-deployment:
kubectl:
kustomize: true
manifests:
- kube
5 changes: 5 additions & 0 deletions e2e/tests/deploy/testdata/kustomize/kube/kustomization.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
commonLabels:
kustomize-app: devspace

resources:
- service.yaml
10 changes: 10 additions & 0 deletions e2e/tests/deploy/testdata/kustomize/kube/service.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
kind: Service
apiVersion: v1
metadata:
name: my-service
spec:
selector:
app.kubernetes.io/component: default
ports:
- protocol: TCP
port: 3000
2 changes: 1 addition & 1 deletion pkg/devspace/config/versions/latest/schema.go
Original file line number Diff line number Diff line change
Expand Up @@ -587,7 +587,7 @@ type DeploymentConfig struct {
// Name of the deployment
Name string `yaml:"name,omitempty" json:"name,omitempty"`
// Namespace where to deploy this deployment
Namespace *string `yaml:"namespace,omitempty" json:"namespace,omitempty"`
Namespace string `yaml:"namespace,omitempty" json:"namespace,omitempty"`
// UpdateImageTags lets you define if DevSpace should update the tags of the images defined in the
// images section with their most recent built tag.
UpdateImageTags *bool `yaml:"updateImageTags,omitempty" json:"updateImageTags,omitempty"`
Expand Down
6 changes: 2 additions & 4 deletions pkg/devspace/config/versions/v1beta11/upgrade.go
Original file line number Diff line number Diff line change
Expand Up @@ -415,10 +415,8 @@ func (c *Config) Upgrade(log log.Logger) (config.Config, error) {

name := encoding.Convert(deployment.Name)
nextConfig.Deployments[name] = &next.DeploymentConfig{
Name: name,
}
if deployment.Namespace != "" {
nextConfig.Deployments[name].Namespace = &deployment.Namespace
Name: name,
Namespace: deployment.Namespace,
}
if deployment.Helm != nil {
nextConfig.Deployments[name].Helm = &next.HelmConfig{
Expand Down
4 changes: 2 additions & 2 deletions pkg/devspace/deploy/deploy.go
Original file line number Diff line number Diff line change
Expand Up @@ -171,8 +171,8 @@ func (c *controller) deployOne(ctx devspacecontext.Context, deployConfig *latest
method string
)

if !options.Render && deployConfig.Namespace != nil && *deployConfig.Namespace != "" {
err = kubectlclient.EnsureNamespace(ctx.Context(), ctx.KubeClient(), *deployConfig.Namespace, ctx.Log())
if !options.Render && deployConfig.Namespace != "" {
err = kubectlclient.EnsureNamespace(ctx.Context(), ctx.KubeClient(), deployConfig.Namespace, ctx.Log())
if err != nil {
return false, err
}
Expand Down
8 changes: 4 additions & 4 deletions pkg/devspace/deploy/deployer/helm/deploy.go
Original file line number Diff line number Diff line change
Expand Up @@ -33,8 +33,8 @@ func (d *DeployConfig) Deploy(ctx devspacecontext.Context, forceDeploy bool) (bo
)

releaseNamespace := ctx.KubeClient().Namespace()
if d.DeploymentConfig.Namespace != nil && *d.DeploymentConfig.Namespace != "" {
releaseNamespace = *d.DeploymentConfig.Namespace
if d.DeploymentConfig.Namespace != "" {
releaseNamespace = d.DeploymentConfig.Namespace
}

// Hash the chart directory if there is any
Expand Down Expand Up @@ -155,8 +155,8 @@ func (d *DeployConfig) internalDeploy(ctx devspacecontext.Context, overwriteValu
releaseName = d.DeploymentConfig.Name
)
releaseNamespace := ctx.KubeClient().Namespace()
if d.DeploymentConfig.Namespace != nil && *d.DeploymentConfig.Namespace != "" {
releaseNamespace = *d.DeploymentConfig.Namespace
if d.DeploymentConfig.Namespace != "" {
releaseNamespace = d.DeploymentConfig.Namespace
}

if out != nil {
Expand Down
47 changes: 30 additions & 17 deletions pkg/devspace/deploy/deployer/kubectl/builder.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,10 @@ package kubectl
import (
"context"
"fmt"
"io/ioutil"
"k8s.io/client-go/tools/clientcmd"
clientcmdapi "k8s.io/client-go/tools/clientcmd/api"
"os"
"os/exec"
"regexp"
"strings"
Expand Down Expand Up @@ -56,21 +60,17 @@ func (k *kustomizeBuilder) Build(ctx context.Context, dir, manifest string) ([]*
}

type kubectlBuilder struct {
path string
config *latest.DeploymentConfig
context string
namespace string
isInCluster bool
path string
config *latest.DeploymentConfig
kubeConfig clientcmdapi.Config
}

// NewKubectlBuilder creates a new kubectl manifest builder
func NewKubectlBuilder(path string, config *latest.DeploymentConfig, context, namespace string, isInCluster bool) Builder {
func NewKubectlBuilder(path string, config *latest.DeploymentConfig, kubeConfig clientcmdapi.Config) Builder {
return &kubectlBuilder{
path: path,
config: config,
context: context,
namespace: namespace,
isInCluster: isInCluster,
path: path,
config: config,
kubeConfig: kubeConfig,
}
}

Expand Down Expand Up @@ -102,14 +102,25 @@ var useOldDryRun = func(ctx context.Context, dir, path string) (bool, error) {
}

func (k *kubectlBuilder) Build(ctx context.Context, dir, manifest string) ([]*unstructured.Unstructured, error) {
args := []string{"create"}
if k.context != "" && !k.isInCluster {
args = append(args, "--context", k.context)
tempFile, err := ioutil.TempFile("", "")
if err != nil {
return nil, err
}
if k.namespace != "" {
args = append(args, "--namespace", k.namespace)
defer os.Remove(tempFile.Name())

data, err := clientcmd.Write(k.kubeConfig)
if err != nil {
return nil, err
}

_, err = tempFile.Write(data)
if err != nil {
return nil, err
}
_ = tempFile.Close()

args := []string{"create"}

// decides which --dry-run value is to be used
uodr, err := useOldDryRun(ctx, dir, k.path)
if err != nil {
Expand All @@ -132,7 +143,9 @@ func (k *kubectlBuilder) Build(ctx context.Context, dir, manifest string) ([]*un
args = append(args, k.config.Kubectl.CreateArgs...)

// Execute command
output, err := command.Output(ctx, dir, k.path, args...)
output, err := command.OutputWithEnv(ctx, dir, map[string]string{
"KUBECONFIG": tempFile.Name(),
}, k.path, args...)
if err != nil {
exitError, ok := err.(*exec.ExitError)
if ok {
Expand Down
28 changes: 18 additions & 10 deletions pkg/devspace/deploy/deployer/kubectl/kubectl.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ package kubectl

import (
"context"
"github.com/loft-sh/devspace/pkg/util/ptr"
"fmt"
"io"
"strings"

Expand Down Expand Up @@ -81,15 +81,15 @@ func New(ctx devspacecontext.Context, deployConfig *latest.DeploymentConfig) (de
}

namespace := deployConfig.Namespace
if namespace == nil {
namespace = ptr.String(ctx.KubeClient().Namespace())
if namespace == "" {
namespace = ctx.KubeClient().Namespace()
}

return &DeployConfig{
Name: deployConfig.Name,
CmdPath: cmdPath,
Context: ctx.KubeClient().CurrentContext(),
Namespace: *namespace,
Namespace: namespace,
Manifests: manifests,
IsInCluster: ctx.KubeClient().IsInCluster(),

Expand Down Expand Up @@ -177,10 +177,9 @@ func (d *DeployConfig) Deploy(ctx devspacecontext.Context, _ bool) (bool, error)

kubeObjects = append(kubeObjects, parsedObjects...)
if shouldRedeploy || forceDeploy {
stringReader := strings.NewReader(replacedManifest)
args := d.getCmdArgs("apply", "--force")
args = append(args, d.DeploymentConfig.Kubectl.ApplyArgs...)
err = command.Command(ctx.Context(), ctx.WorkingDir(), writer, writer, stringReader, d.CmdPath, args...)
err = command.Command(ctx.Context(), ctx.WorkingDir(), writer, writer, strings.NewReader(replacedManifest), d.CmdPath, args...)
if err != nil {
return false, errors.Errorf("%v\nPlease make sure the command `kubectl apply` does work locally with manifest `%s`", err, manifest)
}
Expand Down Expand Up @@ -220,6 +219,9 @@ func (d *DeployConfig) getReplacedManifest(ctx devspacecontext.Context, manifest
if resource.Object == nil {
continue
}
if resource.GetNamespace() == "" {
resource.SetNamespace(d.Namespace)
}

kubeObjects = append(kubeObjects, remotecache.KubectlObject{
APIVersion: resource.GetAPIVersion(),
Expand Down Expand Up @@ -253,9 +255,6 @@ func (d *DeployConfig) getCmdArgs(method string, additionalArgs ...string) []str
if d.Context != "" && !d.IsInCluster {
args = append(args, "--context", d.Context)
}
if d.Namespace != "" {
args = append(args, "--namespace", d.Namespace)
}

args = append(args, method)
if additionalArgs != nil {
Expand All @@ -277,8 +276,17 @@ func (d *DeployConfig) buildManifests(ctx devspacecontext.Context, manifest stri
return NewKustomizeBuilder(kustomizePath, d.DeploymentConfig, ctx.Log()).Build(ctx.Context(), ctx.WorkingDir(), manifest)
}

raw, err := ctx.KubeClient().KubeConfigLoader().LoadConfig().RawConfig()
if err != nil {
return nil, fmt.Errorf("get raw config")
}
copied := raw.DeepCopy()
for key := range copied.Contexts {
copied.Contexts[key].Namespace = d.Namespace
}

// Build with kubectl
return NewKubectlBuilder(d.CmdPath, d.DeploymentConfig, d.Context, d.Namespace, d.IsInCluster).Build(ctx.Context(), ctx.WorkingDir(), manifest)
return NewKubectlBuilder(d.CmdPath, d.DeploymentConfig, *copied).Build(ctx.Context(), ctx.WorkingDir(), manifest)
}

func (d *DeployConfig) isKustomizeInstalled(ctx context.Context, dir, path string) bool {
Expand Down
4 changes: 2 additions & 2 deletions pkg/devspace/deploy/deployer/kubectl/kubectl_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,7 @@ func TestNew(t *testing.T) {
name: "Everything given",
deployConfig: &latest.DeploymentConfig{
Name: "someDeploy2",
Namespace: ptr.String("overwriteNamespace"),
Namespace: "overwriteNamespace",
Kubectl: &latest.KubectlConfig{
KubectlBinaryPath: "someCmdPath2",
Manifests: []string{},
Expand All @@ -80,7 +80,7 @@ func TestNew(t *testing.T) {
Namespace: "overwriteNamespace",
DeploymentConfig: &latest.DeploymentConfig{
Name: "someDeploy2",
Namespace: ptr.String("overwriteNamespace"),
Namespace: "overwriteNamespace",
Kubectl: &latest.KubectlConfig{
KubectlBinaryPath: "someCmdPath2",
Manifests: []string{},
Expand Down
6 changes: 5 additions & 1 deletion pkg/util/command/command.go
Original file line number Diff line number Diff line change
Expand Up @@ -142,8 +142,12 @@ func CombinedOutputWithEnv(ctx context.Context, dir string, extraEnvVars map[str
}

func Output(ctx context.Context, dir string, cmd string, args ...string) ([]byte, error) {
return OutputWithEnv(ctx, dir, nil, cmd, args...)
}

func OutputWithEnv(ctx context.Context, dir string, extraEnvVars map[string]string, cmd string, args ...string) ([]byte, error) {
stdout := &bytes.Buffer{}
err := CommandWithEnv(ctx, dir, stdout, nil, nil, nil, cmd, args...)
err := CommandWithEnv(ctx, dir, stdout, nil, nil, extraEnvVars, cmd, args...)
return stdout.Bytes(), err
}

Expand Down