Skip to content

Commit 5f88d0a

Browse files
baronfelSurayya Huseyn Zada
authored and
Surayya Huseyn Zada
committed
Allow users to set a specific ContainerImageFormat to force OCI support (dotnet#46011)
1 parent 01a9c07 commit 5f88d0a

26 files changed

+306
-98
lines changed

src/Containers/Microsoft.NET.Build.Containers/ContainerBuilder.cs

+16
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,12 @@
66

77
namespace Microsoft.NET.Build.Containers;
88

9+
internal enum KnownImageFormats
10+
{
11+
OCI,
12+
Docker
13+
}
14+
915
internal static class ContainerBuilder
1016
{
1117
internal static async Task<int> ContainerizeAsync(
@@ -33,6 +39,7 @@ internal static async Task<int> ContainerizeAsync(
3339
string? archiveOutputPath,
3440
bool generateLabels,
3541
bool generateDigestLabel,
42+
KnownImageFormats? imageFormat,
3643
ILoggerFactory loggerFactory,
3744
CancellationToken cancellationToken)
3845
{
@@ -98,6 +105,15 @@ internal static async Task<int> ContainerizeAsync(
98105
logger.LogInformation(Strings.ContainerBuilder_StartBuildingImage, imageName, string.Join(",", imageName), sourceImageReference);
99106
cancellationToken.ThrowIfCancellationRequested();
100107

108+
// forcibly change the media type if required
109+
imageBuilder.ManifestMediaType = imageFormat switch
110+
{
111+
null => imageBuilder.ManifestMediaType,
112+
KnownImageFormats.Docker => SchemaTypes.DockerManifestV2,
113+
KnownImageFormats.OCI => SchemaTypes.OciManifestV1,
114+
_ => imageBuilder.ManifestMediaType // should be impossible unless we add to the enum
115+
};
116+
101117
Layer newLayer = Layer.FromDirectory(publishDirectory.FullName, workingDir, imageBuilder.IsWindows, imageBuilder.ManifestMediaType);
102118
imageBuilder.AddLayer(newLayer);
103119
imageBuilder.SetWorkingDirectory(workingDir);

src/Containers/Microsoft.NET.Build.Containers/ImageBuilder.cs

+11-6
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,6 @@ internal sealed class ImageBuilder
2020

2121
// the mutable internal manifest that we're building by modifying the base and applying customizations
2222
private readonly ManifestV2 _manifest;
23-
private readonly string _manifestMediaType;
2423
private readonly ImageConfig _baseImageConfig;
2524
private readonly ILogger _logger;
2625

@@ -33,15 +32,15 @@ internal sealed class ImageBuilder
3332
public ImageConfig BaseImageConfig => _baseImageConfig;
3433

3534
/// <summary>
36-
/// MediaType of the output manifest.
35+
/// MediaType of the output manifest. By default, this will be the same as the base image manifest.
3736
/// </summary>
38-
public string ManifestMediaType => _manifestMediaType; // output the same media type as the base image manifest.
37+
public string ManifestMediaType { get; set; }
3938

4039
internal ImageBuilder(ManifestV2 manifest, string manifestMediaType, ImageConfig baseImageConfig, ILogger logger)
4140
{
4241
_baseImageManifest = manifest;
4342
_manifest = new ManifestV2() { SchemaVersion = manifest.SchemaVersion, Config = manifest.Config, Layers = new(manifest.Layers), MediaType = manifest.MediaType };
44-
_manifestMediaType = manifestMediaType;
43+
ManifestMediaType = manifestMediaType;
4544
_baseImageConfig = baseImageConfig;
4645
_logger = logger;
4746
}
@@ -71,14 +70,20 @@ internal BuiltImage Build()
7170
ManifestConfig newManifestConfig = _manifest.Config with
7271
{
7372
digest = imageDigest,
74-
size = imageSize
73+
size = imageSize,
74+
mediaType = ManifestMediaType switch
75+
{
76+
SchemaTypes.OciManifestV1 => SchemaTypes.OciImageConfigV1,
77+
SchemaTypes.DockerManifestV2 => SchemaTypes.DockerContainerV1,
78+
_ => SchemaTypes.OciImageConfigV1 // opinion - defaulting to modern here, but really this should never happen
79+
}
7580
};
7681

7782
ManifestV2 newManifest = new ManifestV2()
7883
{
7984
Config = newManifestConfig,
8085
SchemaVersion = _manifest.SchemaVersion,
81-
MediaType = _manifest.MediaType,
86+
MediaType = ManifestMediaType,
8287
Layers = _manifest.Layers
8388
};
8489

src/Containers/Microsoft.NET.Build.Containers/PublicAPI/net472/PublicAPI.Unshipped.txt

+2
Original file line numberDiff line numberDiff line change
@@ -88,6 +88,8 @@ Microsoft.NET.Build.Containers.Tasks.CreateNewImage.GenerateDigestLabel.get -> b
8888
Microsoft.NET.Build.Containers.Tasks.CreateNewImage.GenerateDigestLabel.set -> void
8989
Microsoft.NET.Build.Containers.Tasks.CreateNewImage.GeneratedContainerNames.get -> Microsoft.Build.Framework.ITaskItem![]!
9090
Microsoft.NET.Build.Containers.Tasks.CreateNewImage.GeneratedContainerNames.set -> void
91+
Microsoft.NET.Build.Containers.Tasks.CreateNewImage.ImageFormat.get -> string?
92+
Microsoft.NET.Build.Containers.Tasks.CreateNewImage.ImageFormat.set -> void
9193
override Microsoft.NET.Build.Containers.Tasks.CreateNewImage.ToolName.get -> string!
9294
override Microsoft.NET.Build.Containers.Tasks.CreateNewImage.GenerateCommandLineCommands() -> string!
9395
override Microsoft.NET.Build.Containers.Tasks.CreateNewImage.GenerateFullPathToTool() -> string!

src/Containers/Microsoft.NET.Build.Containers/PublicAPI/net8.0/PublicAPI.Unshipped.txt

+2
Original file line numberDiff line numberDiff line change
@@ -241,6 +241,8 @@ Microsoft.NET.Build.Containers.Tasks.CreateNewImage.GenerateDigestLabel.get -> b
241241
Microsoft.NET.Build.Containers.Tasks.CreateNewImage.GenerateDigestLabel.set -> void
242242
Microsoft.NET.Build.Containers.Tasks.CreateNewImage.GeneratedContainerNames.get -> Microsoft.Build.Framework.ITaskItem![]!
243243
Microsoft.NET.Build.Containers.Tasks.CreateNewImage.GeneratedContainerNames.set -> void
244+
Microsoft.NET.Build.Containers.Tasks.CreateNewImage.ImageFormat.get -> string?
245+
Microsoft.NET.Build.Containers.Tasks.CreateNewImage.ImageFormat.set -> void
244246
Microsoft.NET.Build.Containers.Tasks.ParseContainerProperties
245247
Microsoft.NET.Build.Containers.Tasks.ParseContainerProperties.ContainerEnvironmentVariables.get -> Microsoft.Build.Framework.ITaskItem![]!
246248
Microsoft.NET.Build.Containers.Tasks.ParseContainerProperties.ContainerEnvironmentVariables.set -> void

src/Containers/Microsoft.NET.Build.Containers/Registry/SchemaTypes.cs

+3
Original file line numberDiff line numberDiff line change
@@ -9,8 +9,11 @@ internal class SchemaTypes
99
internal const string DockerContainerV1 = "application/vnd.docker.container.image.v1+json";
1010
internal const string DockerManifestListV2 = "application/vnd.docker.distribution.manifest.list.v2+json";
1111
internal const string DockerManifestV2 = "application/vnd.docker.distribution.manifest.v2+json";
12+
1213
internal const string OciManifestV1 = "application/vnd.oci.image.manifest.v1+json"; // https://containers.gitbook.io/build-containers-the-hard-way/#registry-format-oci-image-manifest
1314
internal const string OciImageIndexV1 = "application/vnd.oci.image.index.v1+json";
15+
internal const string OciImageConfigV1 = "application/vnd.oci.image.config.v1+json";
16+
1417
internal const string DockerLayerGzip = "application/vnd.docker.image.rootfs.diff.tar.gzip";
1518
internal const string OciLayerGzipV1 = "application/vnd.oci.image.layer.v1.tar+gzip";
1619
}

0 commit comments

Comments
 (0)