{"id":39261102,"url":"https://github.com/jerrettdavis/jd.msbuild.containers","last_synced_at":"2026-06-16T07:01:18.255Z","repository":{"id":332866028,"uuid":"1135294878","full_name":"JerrettDavis/JD.MSBuild.Containers","owner":"JerrettDavis","description":"MSBuild tasks, targets, and props to integrate OCI containers with your .NET projects","archived":false,"fork":false,"pushed_at":"2026-06-16T02:35:26.000Z","size":1251,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":0,"default_branch":"main","last_synced_at":"2026-06-16T03:11:29.311Z","etag":null,"topics":["build","build-automation","c","containers","csharp","docker","msbuild"],"latest_commit_sha":null,"homepage":"https://jerrettdavis.github.io/JD.MSBuild.Containers/","language":"C#","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/JerrettDavis.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":"CONTRIBUTING.md","funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2026-01-15T22:44:37.000Z","updated_at":"2026-06-16T02:35:30.000Z","dependencies_parsed_at":"2026-01-20T06:01:23.681Z","dependency_job_id":null,"html_url":"https://github.com/JerrettDavis/JD.MSBuild.Containers","commit_stats":null,"previous_names":["jerrettdavis/jd.msbuild.containers"],"tags_count":12,"template":false,"template_full_name":null,"purl":"pkg:github/JerrettDavis/JD.MSBuild.Containers","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/JerrettDavis%2FJD.MSBuild.Containers","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/JerrettDavis%2FJD.MSBuild.Containers/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/JerrettDavis%2FJD.MSBuild.Containers/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/JerrettDavis%2FJD.MSBuild.Containers/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/JerrettDavis","download_url":"https://codeload.github.com/JerrettDavis/JD.MSBuild.Containers/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/JerrettDavis%2FJD.MSBuild.Containers/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":34393305,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-05-26T15:22:16.424Z","status":"online","status_checked_at":"2026-06-16T02:00:06.860Z","response_time":126,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["build","build-automation","c","containers","csharp","docker","msbuild"],"created_at":"2026-01-18T00:28:11.792Z","updated_at":"2026-06-16T07:01:18.202Z","avatar_url":"https://github.com/JerrettDavis.png","language":"C#","funding_links":[],"categories":[],"sub_categories":[],"readme":"# JD.MSBuild.Containers\n\n**MSBuild tasks, targets, and props to integrate OCI containers with your .NET projects**\n\n[![NuGet](https://img.shields.io/nuget/v/JD.MSBuild.Containers.svg)](https://www.nuget.org/packages/JD.MSBuild.Containers/)\n[![License](https://img.shields.io/github/license/jerrettdavis/JD.MSBuild.Containers.svg)](LICENSE)\n[![CI](https://github.com/JerrettDavis/JD.MSBuild.Containers/actions/workflows/ci.yml/badge.svg)](https://github.com/JerrettDavis/JD.MSBuild.Containers/actions/workflows/ci.yml)\n[![CodeQL](https://github.com/JerrettDavis/JD.MSBuild.Containers/actions/workflows/codeql-analysis.yml/badge.svg)](https://github.com/JerrettDavis/JD.MSBuild.Containers/security/code-scanning)\n[![codecov](https://codecov.io/gh/JerrettDavis/JD.MSBuild.Containers/branch/main/graph/badge.svg)](https://codecov.io/gh/JerrettDavis/JD.MSBuild.Containers)\n[![Documentation](https://img.shields.io/badge/docs-online-blue)](https://jerrettdavis.github.io/JD.MSBuild.Containers/)\n\nAutomate Docker containerization during `dotnet build`. Zero manual steps, full CI/CD support, reproducible container builds with granular control over every step of the process.\n\n## 📚 Documentation\n\n**[View Complete Documentation](https://jerrettdavis.github.io/JD.MSBuild.Containers/)**\n\n- [Introduction](https://jerrettdavis.github.io/JD.MSBuild.Containers/articles/introduction.html) - Project overview and architecture\n- [Getting Started](https://jerrettdavis.github.io/JD.MSBuild.Containers/articles/getting-started.html) - Installation and quick start guide\n- [Tutorials](https://jerrettdavis.github.io/JD.MSBuild.Containers/tutorials/tutorial-basic.html) - Step-by-step walkthroughs\n- [API Reference](https://jerrettdavis.github.io/JD.MSBuild.Containers/api/) - Complete property and task reference\n- [Samples](https://jerrettdavis.github.io/JD.MSBuild.Containers/samples/sample-overview.html) - Working example projects\n\n## Quick Start\n\n### Installation\n\n```bash\ndotnet add package JD.MSBuild.Containers\n```\n\n### Basic Usage - Generate Dockerfile Only\n\n```xml\n\u003cProject Sdk=\"Microsoft.NET.Sdk.Web\"\u003e\n  \u003cPropertyGroup\u003e\n    \u003cTargetFramework\u003enet8.0\u003c/TargetFramework\u003e\n    \n    \u003c!-- Enable Docker integration --\u003e\n    \u003cDockerEnabled\u003etrue\u003c/DockerEnabled\u003e\n    \n    \u003c!-- Generate Dockerfile (default when DockerEnabled=true) --\u003e\n    \u003cDockerGenerateDockerfile\u003etrue\u003c/DockerGenerateDockerfile\u003e\n  \u003c/PropertyGroup\u003e\n  \n  \u003cItemGroup\u003e\n    \u003cPackageReference Include=\"JD.MSBuild.Containers\" Version=\"*\" /\u003e\n  \u003c/ItemGroup\u003e\n\u003c/Project\u003e\n```\n\nRun `dotnet build` and a Dockerfile will be generated in your project directory.\n\n### Full Automation - Generate and Build\n\n```xml\n\u003cPropertyGroup\u003e\n  \u003cDockerEnabled\u003etrue\u003c/DockerEnabled\u003e\n  \u003cDockerGenerateDockerfile\u003etrue\u003c/DockerGenerateDockerfile\u003e\n  \u003cDockerBuildImage\u003etrue\u003c/DockerBuildImage\u003e\n  \u003cDockerBuildOnPublish\u003etrue\u003c/DockerBuildOnPublish\u003e\n\u003c/PropertyGroup\u003e\n```\n\nRun `dotnet publish` to generate the Dockerfile and build the Docker image.\n\n### Build-Only Mode - Use Existing Dockerfile\n\n```xml\n\u003cPropertyGroup\u003e\n  \u003cDockerEnabled\u003etrue\u003c/DockerEnabled\u003e\n  \n  \u003c!-- Don't generate, use existing Dockerfile --\u003e\n  \u003cDockerGenerateDockerfile\u003efalse\u003c/DockerGenerateDockerfile\u003e\n  \n  \u003c!-- Build the image --\u003e\n  \u003cDockerBuildImage\u003etrue\u003c/DockerBuildImage\u003e\n  \u003cDockerBuildOnPublish\u003etrue\u003c/DockerBuildOnPublish\u003e\n  \n  \u003c!-- Optional: specify custom Dockerfile location --\u003e\n  \u003cDockerfileSource\u003e$(MSBuildProjectDirectory)\\custom.Dockerfile\u003c/DockerfileSource\u003e\n\u003c/PropertyGroup\u003e\n```\n\n## Key Features\n\n### Granular Control\n\nJD.MSBuild.Containers is designed as a **configurable OCI MSBuild shim integration**. Every feature can be independently enabled or disabled:\n\n- ✅ **Generate Dockerfile** - Auto-generate optimized multi-stage Dockerfiles\n- ✅ **Build Images** - Execute `docker build` during MSBuild\n- ✅ **Run Containers** - Start containers after build (opt-in)\n- ✅ **Push to Registry** - Automatically push to container registries\n- ✅ **Pre/Post Scripts** - Execute custom scripts at any stage\n- ✅ **Incremental Builds** - Skip regeneration when nothing changes\n- ✅ **MSBuild Hooks** - Integrate with Build, Clean, Publish, Run targets\n\n### Configuration Modes\n\n| Mode | Generate | Build | Use Case |\n|------|----------|-------|----------|\n| **Generate-Only** | ✅ | ❌ | Review/commit Dockerfiles, manual builds |\n| **Build-Only** | ❌ | ✅ | Use existing Dockerfiles, custom templates |\n| **Full Automation** | ✅ | ✅ | Complete CI/CD, zero manual steps |\n| **Custom Hooks** | ➖ | ➖ | Execute scripts only, manual everything else |\n\n## Configuration Reference\n\n### Core Enablement\n\n| Property | Default | Description |\n|----------|---------|-------------|\n| `DockerEnabled` | `false` | Master switch for Docker integration |\n| `DockerGenerateDockerfile` | `true` (when enabled) | Controls Dockerfile generation |\n| `DockerBuildImage` | `false` | Controls Docker image building |\n| `DockerRunContainer` | `false` | Controls container execution |\n| `DockerPushImage` | `false` | Controls pushing to registry |\n\n### Hook Integration\n\n| Property | Default | Description |\n|----------|---------|-------------|\n| `DockerGenerateOnBuild` | `true` | Generate Dockerfile during Build |\n| `DockerBuildOnBuild` | `false` | Build image during Build |\n| `DockerBuildOnPublish` | `true` | Build image during Publish |\n| `DockerRunOnBuild` | `false` | Run container after Build |\n| `DockerPushOnPublish` | `true` | Push image after Publish |\n\n### Script Execution\n\n| Property | Default | Description |\n|----------|---------|-------------|\n| `DockerPreBuildScript` | - | Path to pre-build script |\n| `DockerPostBuildScript` | - | Path to post-build script |\n| `DockerPrePublishScript` | - | Path to pre-publish script |\n| `DockerPostPublishScript` | - | Path to post-publish script |\n| `DockerExecutePreBuildScript` | `true` (if script set) | Enable pre-build script |\n| `DockerExecutePostBuildScript` | `true` (if script set) | Enable post-build script |\n| `DockerExecutePrePublishScript` | `true` (if script set) | Enable pre-publish script |\n| `DockerExecutePostPublishScript` | `true` (if script set) | Enable post-publish script |\n\n### Image Configuration\n\n| Property | Default | Description |\n|----------|---------|-------------|\n| `DockerImageName` | `$(AssemblyName).ToLower()` | Docker image name |\n| `DockerImageTag` | `latest` | Docker image tag |\n| `DockerRegistry` | - | Container registry URL |\n| `DockerBaseImageRuntime` | `mcr.microsoft.com/dotnet/aspnet` | Runtime base image |\n| `DockerBaseImageSdk` | `mcr.microsoft.com/dotnet/sdk` | SDK base image |\n| `DockerBaseImageVersion` | Auto-detected | Base image version |\n\n### Build Options\n\n| Property | Default | Description |\n|----------|---------|-------------|\n| `DockerBuildContext` | `$(MSBuildProjectDirectory)` | Docker build context |\n| `DockerBuildArgs` | - | Additional build arguments |\n| `DockerBuildPlatform` | - | Target platform (e.g., `linux/amd64`) |\n| `DockerBuildTarget` | - | Target stage in multi-stage builds |\n| `DockerUseMultiStage` | `true` | Use multi-stage Dockerfiles |\n| `DockerOptimizeLayers` | `true` | Optimize Docker layers |\n\n### File Paths\n\n| Property | Default | Description |\n|----------|---------|-------------|\n| `DockerfileOutput` | `$(MSBuildProjectDirectory)\\Dockerfile` | Generated Dockerfile path |\n| `DockerfileSource` | `$(MSBuildProjectDirectory)\\Dockerfile` | Existing Dockerfile path |\n| `DockerOutput` | `$(BaseIntermediateOutputPath)docker\\` | Build output directory |\n| `DockerTemplateFile` | - | Custom Dockerfile template |\n\n### Advanced Options\n\n| Property | Default | Description |\n|----------|---------|-------------|\n| `DockerUseFingerprinting` | `true` | Enable incremental builds |\n| `DockerLogVerbosity` | `minimal` | Logging level (quiet/minimal/normal/detailed/diagnostic) |\n| `DockerCommand` | `docker` | Docker CLI command |\n| `DockerProjectType` | Auto-detected | Project type (console/library) |\n| `DockerExposePort` | `8080` (ASP.NET) | Exposed port |\n| `DockerUser` | `app` | Container user |\n| `DockerCreateUser` | `true` | Create non-root user |\n\n## Usage Examples\n\n### Example 1: Generate-Only Mode (Default)\n\nPerfect for committing Dockerfiles to version control and reviewing before build:\n\n```xml\n\u003cPropertyGroup\u003e\n  \u003cDockerEnabled\u003etrue\u003c/DockerEnabled\u003e\n  \u003c!-- DockerGenerateDockerfile defaults to true --\u003e\n  \u003c!-- DockerBuildImage defaults to false --\u003e\n\u003c/PropertyGroup\u003e\n```\n\n```bash\ndotnet build\n# Dockerfile generated at ./Dockerfile\n# No Docker image built\n```\n\n### Example 2: Build-Only Mode\n\nUse your own hand-crafted Dockerfile:\n\n```xml\n\u003cPropertyGroup\u003e\n  \u003cDockerEnabled\u003etrue\u003c/DockerEnabled\u003e\n  \u003cDockerGenerateDockerfile\u003efalse\u003c/DockerGenerateDockerfile\u003e\n  \u003cDockerBuildImage\u003etrue\u003c/DockerBuildImage\u003e\n  \u003cDockerBuildOnPublish\u003etrue\u003c/DockerBuildOnPublish\u003e\n  \n  \u003c!-- Optional: custom Dockerfile location --\u003e\n  \u003cDockerfileSource\u003e$(MSBuildProjectDirectory)\\deploy\\Dockerfile\u003c/DockerfileSource\u003e\n\u003c/PropertyGroup\u003e\n```\n\n```bash\ndotnet publish\n# Uses existing Dockerfile at ./deploy/Dockerfile\n# Builds Docker image\n```\n\n### Example 3: Full Automation\n\nGenerate and build automatically:\n\n```xml\n\u003cPropertyGroup\u003e\n  \u003cDockerEnabled\u003etrue\u003c/DockerEnabled\u003e\n  \u003cDockerGenerateDockerfile\u003etrue\u003c/DockerGenerateDockerfile\u003e\n  \u003cDockerBuildImage\u003etrue\u003c/DockerBuildImage\u003e\n  \u003cDockerBuildOnPublish\u003etrue\u003c/DockerBuildOnPublish\u003e\n  \n  \u003cDockerImageName\u003emyapp\u003c/DockerImageName\u003e\n  \u003cDockerImageTag\u003e$(Version)\u003c/DockerImageTag\u003e\n  \u003cDockerRegistry\u003emyregistry.azurecr.io\u003c/DockerRegistry\u003e\n\u003c/PropertyGroup\u003e\n```\n\n```bash\ndotnet publish\n# Generates Dockerfile\n# Builds image: myregistry.azurecr.io/myapp:1.0.0\n```\n\n### Example 4: CI/CD with Scripts and Push\n\n```xml\n\u003cPropertyGroup\u003e\n  \u003cDockerEnabled\u003etrue\u003c/DockerEnabled\u003e\n  \u003cDockerGenerateDockerfile\u003etrue\u003c/DockerGenerateDockerfile\u003e\n  \u003cDockerBuildImage\u003etrue\u003c/DockerBuildImage\u003e\n  \u003cDockerBuildOnPublish\u003etrue\u003c/DockerBuildOnPublish\u003e\n  \u003cDockerPushImage\u003etrue\u003c/DockerPushImage\u003e\n  \u003cDockerPushOnPublish\u003etrue\u003c/DockerPushOnPublish\u003e\n  \n  \u003c!-- Pre/Post scripts --\u003e\n  \u003cDockerPreBuildScript\u003e$(MSBuildProjectDirectory)\\scripts\\pre-build.sh\u003c/DockerPreBuildScript\u003e\n  \u003cDockerPostPublishScript\u003e$(MSBuildProjectDirectory)\\scripts\\deploy.ps1\u003c/DockerPostPublishScript\u003e\n  \n  \u003cDockerRegistry\u003emyregistry.azurecr.io\u003c/DockerRegistry\u003e\n  \u003cDockerImageName\u003emyapp\u003c/DockerImageName\u003e\n  \u003cDockerImageTag\u003e$(GitVersion_SemVer)\u003c/DockerImageTag\u003e\n\u003c/PropertyGroup\u003e\n```\n\n### Example 5: Development Workflow with Auto-Run\n\n```xml\n\u003cPropertyGroup\u003e\n  \u003cDockerEnabled\u003etrue\u003c/DockerEnabled\u003e\n  \u003cDockerGenerateDockerfile\u003etrue\u003c/DockerGenerateDockerfile\u003e\n  \u003cDockerBuildImage\u003etrue\u003c/DockerBuildImage\u003e\n  \u003cDockerBuildOnBuild\u003etrue\u003c/DockerBuildOnBuild\u003e\n  \u003cDockerRunContainer\u003etrue\u003c/DockerRunContainer\u003e\n  \u003cDockerRunOnBuild\u003etrue\u003c/DockerRunOnBuild\u003e\n  \n  \u003c!-- Container configuration --\u003e\n  \u003cDockerPortMappings\u003e8080:8080\u003c/DockerPortMappings\u003e\n  \u003cDockerEnvironmentVariables\u003eASPNETCORE_ENVIRONMENT=Development\u003c/DockerEnvironmentVariables\u003e\n  \u003cDockerVolumeMappings\u003e$(MSBuildProjectDirectory)/data:/app/data\u003c/DockerVolumeMappings\u003e\n\u003c/PropertyGroup\u003e\n```\n\n```bash\ndotnet build\n# Generates Dockerfile\n# Builds image\n# Starts container with port mappings\n```\n\n### Example 6: Selective Script Execution\n\nExecute only specific scripts:\n\n```xml\n\u003cPropertyGroup\u003e\n  \u003cDockerEnabled\u003etrue\u003c/DockerEnabled\u003e\n  \u003cDockerGenerateDockerfile\u003etrue\u003c/DockerGenerateDockerfile\u003e\n  \n  \u003c!-- Define scripts --\u003e\n  \u003cDockerPreBuildScript\u003e$(MSBuildProjectDirectory)\\scripts\\setup.sh\u003c/DockerPreBuildScript\u003e\n  \u003cDockerPostBuildScript\u003e$(MSBuildProjectDirectory)\\scripts\\cleanup.sh\u003c/DockerPostBuildScript\u003e\n  \n  \u003c!-- Enable only pre-build script --\u003e\n  \u003cDockerExecutePreBuildScript\u003etrue\u003c/DockerExecutePreBuildScript\u003e\n  \u003cDockerExecutePostBuildScript\u003efalse\u003c/DockerExecutePostBuildScript\u003e\n\u003c/PropertyGroup\u003e\n```\n\n## Lifecycle Hooks\n\nJD.MSBuild.Containers provides extensibility points at every stage:\n\n```\nBuild:\n  ├─ BeforeDockerGeneration\n  ├─ DockerResolveInputs\n  ├─ DockerComputeFingerprint\n  ├─ DockerGenerateDockerfile\n  ├─ AfterDockerGeneration\n  ├─ DockerExecutePreBuildScript\n  ├─ BeforeDockerBuild\n  ├─ DockerBuild\n  ├─ AfterDockerBuild\n  ├─ DockerExecutePostBuildScript\n  ├─ BeforeDockerRun\n  ├─ DockerRun\n  └─ AfterDockerRun\n\nPublish:\n  ├─ DockerExecutePrePublishScript\n  ├─ DockerPublish (generates + builds)\n  ├─ DockerExecutePostPublishScript\n  └─ DockerPushImage (if enabled)\n\nClean:\n  └─ DockerClean (removes generated files)\n```\n\nYou can define custom targets that depend on or extend these hooks:\n\n```xml\n\u003cTarget Name=\"MyCustomPreBuild\" BeforeTargets=\"DockerBuild\"\u003e\n  \u003cMessage Text=\"Running custom logic before Docker build\" Importance=\"high\" /\u003e\n\u003c/Target\u003e\n\n\u003cTarget Name=\"MyCustomPostBuild\" AfterTargets=\"AfterDockerBuild\"\u003e\n  \u003cMessage Text=\"Running custom logic after Docker build\" Importance=\"high\" /\u003e\n\u003c/Target\u003e\n```\n\n## Requirements\n\n- **.NET SDK 8.0+**\n- **Docker** (when building images)\n\n## Comparison with Alternatives\n\n| Feature | JD.MSBuild.Containers | Built-in SDK | Docker Desktop |\n|---------|----------------------|--------------|----------------|\n| Auto-generate Dockerfiles | ✅ | ❌ | ❌ |\n| Granular control | ✅ | ❌ | ❌ |\n| Build-only mode | ✅ | ❌ | N/A |\n| Generate-only mode | ✅ | N/A | N/A |\n| Pre/Post scripts | ✅ | ❌ | ❌ |\n| MSBuild integration | ✅ | Limited | ❌ |\n| Incremental builds | ✅ | ❌ | ❌ |\n| Custom templates | ✅ | ❌ | N/A |\n| Multi-stage support | ✅ | ❌ | ✅ |\n\n## Code Coverage\n\nThis project maintains comprehensive code coverage with automated reporting:\n\n- 📊 **Coverage reports** generated on every PR\n- 📈 **Historical tracking** via [Codecov](https://codecov.io/gh/JerrettDavis/JD.MSBuild.Containers)\n- 💬 **PR comments** with coverage summaries\n- 📦 **HTML reports** available as CI artifacts\n\nSee [CODE_COVERAGE.md](CODE_COVERAGE.md) for detailed configuration and usage.\n\n## Contributing\n\nContributions are welcome! Please open an issue first to discuss changes.\n\n## License\n\nThis project is licensed under the MIT License. See [LICENSE](LICENSE) for details.\n\n## Acknowledgments\n\n- Architecture inspired by [JD.Efcpt.Build](https://github.com/jerrettdavis/JD.Efcpt.Build)\n- Docker for container runtime\n- Microsoft for .NET SDK and MSBuild\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjerrettdavis%2Fjd.msbuild.containers","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fjerrettdavis%2Fjd.msbuild.containers","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjerrettdavis%2Fjd.msbuild.containers/lists"}