Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allow specifying a different docker build context #853

Closed
diasjorge opened this issue Jun 17, 2019 · 14 comments
Closed

Allow specifying a different docker build context #853

diasjorge opened this issue Jun 17, 2019 · 14 comments
Labels
devex Developer experience and ease of use. discussion

Comments

@diasjorge
Copy link

Bug

Current Behavior

The Dockerfiles must be at the root of the project

Expected behavior

A user is able to specify a context pointing to another directory like with docker-compose

I can't change our project layout to have different structure like in your examples.

I'd like to be able to specify all garden configuration in a subdirectory like:

garden/garden.yml
garden/module1/garden.yml
garden/module2/garden.yml

And have module1 and module2 build from a parent directory.

Currently with docker-compose we specify the context like: ../../

Your environment

garden version

0.9.12

kubectl version

Client Version: version.Info{Major:"1", Minor:"14", GitVersion:"v1.14.3", GitCommit:"5e53fd6bc17c0dec8434817e69b04a25d8ae0ff0", GitTreeState:"clean", BuildDate:"2019-06-07T09:55:27Z", GoVersion:"go1.12.5", Compiler:"gc", Platform:"darwin/amd64"}
Server Version: version.Info{Major:"1", Minor:"12+", GitVersion:"v1.12.7-gke.10", GitCommit:"8d9b8641e72cf7c96efa61421e87f96387242ba1", GitTreeState:"clean", BuildDate:"2019-04-12T22:59:24Z", GoVersion:"go1.10.8b4", Compiler:"gc", Platform:"linux/amd64"}

docker version

Client: Docker Engine - Community
Version: 18.09.2
API version: 1.39
Go version: go1.10.8
Git commit: 6247962
Built: Sun Feb 10 04:12:39 2019
OS/Arch: darwin/amd64
Experimental: false

Server: Docker Engine - Community
Engine:
Version: 18.09.2
API version: 1.39 (minimum version 1.12)
Go version: go1.10.6
Git commit: 6247962
Built: Sun Feb 10 04:13:06 2019
OS/Arch: linux/amd64
Experimental: false

@edvald
Copy link
Collaborator

edvald commented Jun 17, 2019

Hey @diasjorge! That's good feedback. We've done some work to make placement of code+configs more flexible, but we do currently assume source files for a module to be within the directory where the config is. The reason we do that is that we "stage" builds by copying source files into a temporary directory, and allowing arbitrary locations makes that quite a bit more complex to do.

We have wanted to add a buildRoot (or similar) field to the container module type, but we'd likely still need it to be within the module path.

That said, there might be a good solution for this already. Only issue would be that you wouldn't structure the configs the same way you had in mind, but rather put multiple configs into a single garden.yml in your top-level directory where the docker build context is and use the include field to pick the appropriate files for each module.

So your combined garden.yml would look something like this (I'm guessing as to how your sources are structured btw):

kind: Project
name: my-project
...
---
kind: Module
type: container
name: module1
...
---
kind: Module
type: container
name: module2
include: ["other-module-sources/**/*"]
dockerfile: other.Dockerfile
...

How exactly is your current code structured? There might be other approaches needed if I'm guessing your structure wrong.

@diasjorge
Copy link
Author

hi @edvald thanks for such a quick reply. I'll try your proposal and report back.

edvald added a commit that referenced this issue Jun 23, 2019
We add a `path` rule, with options to disallow absolute paths or parent
paths, i.e. stepping up a directory tree, in order to ensure that some
paths are sub-paths of a project or module.

This required a refactor where we use a custom Joi instance across our
codebase, hence the size of the change.

This is done both for general hardening, and in preparation of #853 and
other similar configuration options.
edvald added a commit that referenced this issue Jun 23, 2019
We add a `path` rule, with options to disallow absolute paths or parent
paths, i.e. stepping up a directory tree, in order to ensure that some
paths are sub-paths of a project or module.

This required a refactor where we use a custom Joi instance across our
codebase, hence the size of the change.

This is done both for general hardening, and in preparation of #853 and
other similar configuration options.
edvald added a commit that referenced this issue Jun 23, 2019
We add a `path` rule, with options to disallow absolute paths or parent
paths, i.e. stepping up a directory tree, in order to ensure that some
paths are sub-paths of a project or module.

This required a refactor where we use a custom Joi instance across our
codebase, hence the size of the change.

This is done both for general hardening, and in preparation of #853 and
other similar configuration options.
edvald added a commit that referenced this issue Jun 24, 2019
We add a `path` rule, with options to disallow absolute paths or parent
paths, i.e. stepping up a directory tree, in order to ensure that some
paths are sub-paths of a project or module.

This required a refactor where we use a custom Joi instance across our
codebase, hence the size of the change.

This is done both for general hardening, and in preparation of #853 and
other similar configuration options.
edvald added a commit that referenced this issue Jun 24, 2019
We add a `path` rule, with options to disallow absolute paths or parent
paths, i.e. stepping up a directory tree, in order to ensure that some
paths are sub-paths of a project or module.

This required a refactor where we use a custom Joi instance across our
codebase, hence the size of the change.

This is done both for general hardening, and in preparation of #853 and
other similar configuration options.
thsig pushed a commit that referenced this issue Jun 24, 2019
We add a `path` rule, with options to disallow absolute paths or parent
paths, i.e. stepping up a directory tree, in order to ensure that some
paths are sub-paths of a project or module.

This required a refactor where we use a custom Joi instance across our
codebase, hence the size of the change.

This is done both for general hardening, and in preparation of #853 and
other similar configuration options.
@diasjorge
Copy link
Author

@edvald I tried your approach and I was able to build the project that way. I see you're working on this issue so looking forward to the upcoming changes to facilitate this :)

@eysi09
Copy link
Collaborator

eysi09 commented Dec 8, 2019

Closing since it's possible to workaround this by "hoisting" the module configuration to a common parent directory and using the inlcude and exclude directives.

@eysi09 eysi09 closed this as completed Dec 8, 2019
@jmaroeder
Copy link
Contributor

I'd love to re-open this issue if possible - I am working on a project whose repo has several Dockerfiles, intended to be built from their own contexts. Each of the Dockerfiles assumes the context is in the directory of the Dockerfile.

I want to use garden to build and deploy these, but I can't seem to find a good way to do that with the current expectations.

Example structure:

.
├── api
│   └── Dockerfile
├── frontend
│   └── Dockerfile
└── garden.yml

@edvald
Copy link
Collaborator

edvald commented Feb 23, 2020

For this case, the advised approach is to place the garden.yml file for each Dockerfile next to the Dockerfile. So it'd be:

.
├── api
│   └── Dockerfile
│   └── garden.yml
├── frontend
│   └── Dockerfile
│   └── garden.yml
└── garden.yml

Would that cover your case?

@jmaroeder
Copy link
Contributor

Sorry, I skipped a layer. The api and frontend directories are inside another repository, which I don't have direct control over.

.
├── garden.yml
└── project-repo
    ├── .git
    ├── api
    │   └── Dockerfile
    └── frontend
        └── Dockerfile

I understand that this is probably pushing the bounds of the scenario garden is intended for, but it would go a long way toward flexibility.

@edvald
Copy link
Collaborator

edvald commented Feb 24, 2020

Aaah I see. That makes sense then. Sure, we can reopen.

Meanwhile, you might be able to use remote module sources for this scenario, which may be a good approach if the external code is not something you're editing much: https://docs.garden.io/guides/using-remote-sources#remote-modules

@edvald edvald reopened this Feb 24, 2020
@atcastel
Copy link

atcastel commented Mar 4, 2020

I run into this same issue. Specifically, the "correct" way of building dotnetcore projects in containers must have the context of the whole repo to deal with project dependencies. Defining all of the modules in the garden project file seems very messy

@atcastel
Copy link

atcastel commented Mar 5, 2020

Here is an example dockerfile, scrubbed of personal information, that is the standard template for dotnetcore projects in a visual studio solution:

#See https://aka.ms/containerfastmode to understand how Visual Studio uses this Dockerfile to build your images for faster debugging.
FROM mcr.microsoft.com/dotnet/core/aspnet:3.1-buster-slim AS base
WORKDIR /app
EXPOSE 80
EXPOSE 443
FROM mcr.microsoft.com/dotnet/core/sdk:3.1-buster AS build
WORKDIR /src
COPY ["<ProjectFolder>/<MyProject>.csproj", "<ProjectFolder>/"]
RUN dotnet restore "<ProjectFolder>/<MyProject>.csproj"
COPY . .
WORKDIR "<ProjectFolder>"
RUN dotnet build "<MyProject>.csproj" -c Release -o /app/build
FROM build AS publish
RUN dotnet publish "<MyProject>.csproj" -c Release -o /app/publish
FROM base AS final
WORKDIR /app
COPY --from=publish /app/publish .
ENTRYPOINT ["dotnet", "<MyProject>.csproj.dll"]

@stale
Copy link

stale bot commented May 4, 2020

This issue has been automatically marked as stale because it hasn't had any activity in 60 days. It will be closed in 14 days if no further activity occurs (e.g. changing labels, comments, commits, etc.). Please feel free to tag a maintainer and ask them to remove the label if you think it doesn't apply. Thank you for submitting this issue and helping make Garden a better product!

@stale stale bot added the stale Label that's automatically set by stalebot. Stale issues get closed after 14 days of inactivity. label May 4, 2020
@edvald edvald removed the stale Label that's automatically set by stalebot. Stale issues get closed after 14 days of inactivity. label May 4, 2020
@stale
Copy link

stale bot commented Jul 3, 2020

This issue has been automatically marked as stale because it hasn't had any activity in 60 days. It will be closed in 14 days if no further activity occurs (e.g. changing labels, comments, commits, etc.). Please feel free to tag a maintainer and ask them to remove the label if you think it doesn't apply. Thank you for submitting this issue and helping make Garden a better product!

@stale stale bot added the stale Label that's automatically set by stalebot. Stale issues get closed after 14 days of inactivity. label Jul 3, 2020
@eysi09 eysi09 added discussion and removed stale Label that's automatically set by stalebot. Stale issues get closed after 14 days of inactivity. labels Jul 14, 2020
@thsig thsig added the devex Developer experience and ease of use. label Apr 14, 2022
@ShavaShav
Copy link

ShavaShav commented Jan 31, 2023

I also would like the ability to specify the build context. I have a project that looks like this:

- .project.garden.yaml
- .modules.garden.yaml
- services
  - myservice
    - src
    - Dockerfile

Where .modules.garden.yaml contains:

kind: Module
type: container
name: service-image
include: [services/myservice/**/*]
dockerfile: services/myservice/Dockerfile

But the resulting build context is not at .garden/build/myservice-image/services/myservice, its at the root (.garden/build/myservice-image), so garden fails to build the image.

I.e. garden is building the image like this:
docker build -t myservice --file project/.garden/build/myservice-image/services/myservice/Dockerfile project/.garden/build/myservice-image

But I want it to build like this:
docker build -t myservice --file project/.garden/build/myservice-image/services/myservice/Dockerfile project/.garden/build/myservice-image/services/myservice

I don't want to put a garden.yaml next to the Dockerfile in /myservice for various reasons; one being that myservice might be a git submodule that I want to build from the Dockerfile, without committing a garden.yaml in it's repo (which is specific to my project and not the myservice repo). I can't use remote module sources because I want to use dev mode (syncing changes from the submodule code to the deployment). I would also like to define all my garden configurations in one place for organization.

Is there a workaround for this?

@vvagaytsev
Copy link
Collaborator

vvagaytsev commented Jul 4, 2023

The original issue has already been resolved in Bonsai (garden 0.13). Feel free to reopen if it's still an issue in Bonsai.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
devex Developer experience and ease of use. discussion
Projects
None yet
Development

No branches or pull requests

9 participants