Skip to content

Commit

Permalink
Update cloud configuration API (#23141)
Browse files Browse the repository at this point in the history
* changes to test configuration files

* designate cloud environment and pass in authority scope

* small test fixes

* working toward ignoring anonymous access tests in national clouds

* update logic for anonymous client

* experimental API for specifying ACR audience

* swagger updates

* update audience to extensible enum

* fix build

* updates

* update track 1 mgmt plane library base url

* update tests to use new constructor pattern

* add recorded tests

* update samples

* update recorded tests

* don't test samples in national clouds

* update enum names per pr fb

* update enum names per pr fb

* update docstring for Audience property
  • Loading branch information
annelo-msft authored Aug 9, 2021
1 parent 0ff1ee1 commit 1911ff2
Show file tree
Hide file tree
Showing 100 changed files with 8,191 additions and 6,871 deletions.
61 changes: 49 additions & 12 deletions sdk/containerregistry/Azure.Containers.ContainerRegistry/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,11 @@ When you're developing and debugging your application locally, you can use your
```C#
// Create a ContainerRegistryClient that will authenticate to your registry through Azure Active Directory
Uri endpoint = new Uri("https://myregistry.azurecr.io");
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential());
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential(),
new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});
```

Please see the [Azure Identity README][identity] for more approaches to authenticating with `DefaultAzureCredential`, both locally and in deployment environments. To connect to registries in non-public Azure Clouds, see the samples below.
Expand Down Expand Up @@ -104,7 +108,11 @@ Iterate through the collection of repositories in the registry.
Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a new ContainerRegistryClient
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential());
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential(),
new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});

// Get the collection of repository names from the registry
Pageable<string> repositories = client.GetRepositoryNames();
Expand All @@ -121,7 +129,10 @@ foreach (string repository in repositories)
Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a new ContainerRegistryClient for anonymous access
ContainerRegistryClient client = new ContainerRegistryClient(endpoint);
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});

// Obtain a RegistryArtifact object to get access to image operations
RegistryArtifact image = client.GetArtifact("library/hello-world", "latest");
Expand All @@ -144,7 +155,11 @@ foreach (ArtifactTagProperties tag in tags)
Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a new ContainerRegistryClient and RegistryArtifact to access image operations
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential());
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential(),
new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});
RegistryArtifact image = client.GetArtifact("library/hello-world", "latest");

// Set permissions on the v1 image's "latest" tag
Expand All @@ -165,7 +180,11 @@ using Azure.Identity;
Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a new ContainerRegistryClient
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential());
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential(),
new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});

// Iterate through repositories
Pageable<string> repositoryNames = client.GetRepositoryNames();
Expand Down Expand Up @@ -202,7 +221,11 @@ The asynchronous APIs are identical to their synchronous counterparts, but metho
Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a new ContainerRegistryClient
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential());
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential(),
new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});

// Get the collection of repository names from the registry
AsyncPageable<string> repositories = client.GetRepositoryNamesAsync();
Expand All @@ -219,7 +242,10 @@ await foreach (string repository in repositories)
Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a new ContainerRegistryClient for anonymous access
ContainerRegistryClient client = new ContainerRegistryClient(endpoint);
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});

// Obtain a RegistryArtifact object to get access to image operations
RegistryArtifact image = client.GetArtifact("library/hello-world", "latest");
Expand All @@ -242,7 +268,10 @@ await foreach (ArtifactTagProperties tag in tags)
Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a new ContainerRegistryClient and RegistryArtifact to access image operations
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential());
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential(),
new ContainerRegistryClientOptions() {
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});
RegistryArtifact image = client.GetArtifact("library/hello-world", "v1");

// Set permissions on the image's "latest" tag
Expand All @@ -264,7 +293,11 @@ using Azure.Identity;
Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a new ContainerRegistryClient
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential());
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential(),
new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});

// Iterate through repositories
AsyncPageable<string> repositoryNames = client.GetRepositoryNamesAsync();
Expand Down Expand Up @@ -297,7 +330,7 @@ await foreach (string repositoryName in repositoryNames)
To authenticate with a registry in a [National Cloud](https://docs.microsoft.com/azure/active-directory/develop/authentication-national-cloud), you will need to make the following additions to your client configuration:

- Set the `AuthorityHost` in the credential options or via the `AZURE_AUTHORITY_HOST` environment variable
- Set the `AuthenticationScope` in `ContainerRegistryClientOptions`
- Set the `Audience` in `ContainerRegistryClientOptions`

```C#
// Create a ContainerRegistryClient that will authenticate through AAD in the China national cloud
Expand All @@ -310,7 +343,7 @@ ContainerRegistryClient client = new ContainerRegistryClient(endpoint,
}),
new ContainerRegistryClientOptions()
{
AuthenticationScope = "https://management.chinacloudapi.cn/.default"
Audience = ContainerRegistryAudience.AzureChina
});
```

Expand All @@ -324,7 +357,11 @@ Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a ContainerRepository class for an invalid repository
string fakeRepositoryName = "doesnotexist";
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential());
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential(),
new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});
ContainerRepository repository = client.GetRepository(fakeRepositoryName);

try
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -110,6 +110,26 @@ public ArtifactTagProperties() { }
public string RegistryLoginServer { get { throw null; } }
public string RepositoryName { get { throw null; } }
}
[System.Runtime.InteropServices.StructLayoutAttribute(System.Runtime.InteropServices.LayoutKind.Sequential)]
public readonly partial struct ContainerRegistryAudience : System.IEquatable<Azure.Containers.ContainerRegistry.ContainerRegistryAudience>
{
private readonly object _dummy;
private readonly int _dummyPrimitive;
public ContainerRegistryAudience(string value) { throw null; }
public static Azure.Containers.ContainerRegistry.ContainerRegistryAudience AzureResourceManagerChina { get { throw null; } }
public static Azure.Containers.ContainerRegistry.ContainerRegistryAudience AzureResourceManagerGermany { get { throw null; } }
public static Azure.Containers.ContainerRegistry.ContainerRegistryAudience AzureResourceManagerGovernment { get { throw null; } }
public static Azure.Containers.ContainerRegistry.ContainerRegistryAudience AzureResourceManagerPublicCloud { get { throw null; } }
public bool Equals(Azure.Containers.ContainerRegistry.ContainerRegistryAudience other) { throw null; }
[System.ComponentModel.EditorBrowsableAttribute(System.ComponentModel.EditorBrowsableState.Never)]
public override bool Equals(object obj) { throw null; }
[System.ComponentModel.EditorBrowsableAttribute(System.ComponentModel.EditorBrowsableState.Never)]
public override int GetHashCode() { throw null; }
public static bool operator ==(Azure.Containers.ContainerRegistry.ContainerRegistryAudience left, Azure.Containers.ContainerRegistry.ContainerRegistryAudience right) { throw null; }
public static implicit operator Azure.Containers.ContainerRegistry.ContainerRegistryAudience (string value) { throw null; }
public static bool operator !=(Azure.Containers.ContainerRegistry.ContainerRegistryAudience left, Azure.Containers.ContainerRegistry.ContainerRegistryAudience right) { throw null; }
public override string ToString() { throw null; }
}
public partial class ContainerRegistryClient
{
protected ContainerRegistryClient() { }
Expand All @@ -128,7 +148,7 @@ public ContainerRegistryClient(System.Uri endpoint, Azure.Core.TokenCredential c
public partial class ContainerRegistryClientOptions : Azure.Core.ClientOptions
{
public ContainerRegistryClientOptions(Azure.Containers.ContainerRegistry.ContainerRegistryClientOptions.ServiceVersion version = Azure.Containers.ContainerRegistry.ContainerRegistryClientOptions.ServiceVersion.V1_0) { }
public string AuthenticationScope { get { throw null; } set { } }
public Azure.Containers.ContainerRegistry.ContainerRegistryAudience? Audience { get { throw null; } set { } }
public enum ServiceVersion
{
V1_0 = 1,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,11 @@ public sealed class ListArtifacts : ContainerRegistryPerfTest

public ListArtifacts(PerfOptions options) : base(options)
{
_client = new ContainerRegistryClient(new Uri(PerfTestEnvironment.Instance.Endpoint), PerfTestEnvironment.Instance.Credential);
_client = new ContainerRegistryClient(new Uri(PerfTestEnvironment.Instance.Endpoint), PerfTestEnvironment.Instance.Credential,
new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});
}

public override async Task GlobalSetupAsync()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,11 @@ public sealed class ListRepositories : ContainerRegistryPerfTest

public ListRepositories(PerfOptions options) : base(options)
{
_client = new ContainerRegistryClient(new Uri(PerfTestEnvironment.Instance.Endpoint), PerfTestEnvironment.Instance.Credential);
_client = new ContainerRegistryClient(new Uri(PerfTestEnvironment.Instance.Endpoint), PerfTestEnvironment.Instance.Credential,
new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});
}

public override void Run(CancellationToken cancellationToken)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,11 @@ Create a `ContainerRegistryClient` and send a request.
Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a new ContainerRegistryClient
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential());
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential(),
new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});

// Get the collection of repository names from the registry
Pageable<string> repositories = client.GetRepositoryNames();
Expand All @@ -36,7 +40,11 @@ Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a ContainerRepository class for an invalid repository
string fakeRepositoryName = "doesnotexist";
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential());
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential(),
new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});
ContainerRepository repository = client.GetRepository(fakeRepositoryName);

try
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,11 @@ Create a `ContainerRegistryClient` and send a request.
Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a new ContainerRegistryClient
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential());
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential(),
new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});

// Get the collection of repository names from the registry
AsyncPageable<string> repositories = client.GetRepositoryNamesAsync();
Expand All @@ -36,7 +40,11 @@ Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a ContainerRepository class for an invalid repository
string fakeRepositoryName = "doesnotexist";
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential());
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential(),
new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});
ContainerRepository repository = client.GetRepository(fakeRepositoryName);

try
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,11 @@ using Azure.Identity;
Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a new ContainerRegistryClient
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential());
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential(),
new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});

// Iterate through repositories
Pageable<string> repositoryNames = client.GetRepositoryNames();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,11 @@ using Azure.Identity;
Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a new ContainerRegistryClient
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential());
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential(),
new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});

// Iterate through repositories
AsyncPageable<string> repositoryNames = client.GetRepositoryNamesAsync();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,11 @@ The following sample assumes the registry `myacr.azurecr.io` has a repository `h
Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a new ContainerRegistryClient and RegistryArtifact to access image operations
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential());
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential(),
new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});
RegistryArtifact image = client.GetArtifact("library/hello-world", "latest");

// Set permissions on the v1 image's "latest" tag
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,10 @@ The following sample assumes the registry `myacr.azurecr.io` has a repository `h
Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a new ContainerRegistryClient and RegistryArtifact to access image operations
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential());
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new DefaultAzureCredential(),
new ContainerRegistryClientOptions() {
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});
RegistryArtifact image = client.GetArtifact("library/hello-world", "v1");

// Set permissions on the image's "latest" tag
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,10 @@ This sample shows how to list the tags for an image with anonymous access.
Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a new ContainerRegistryClient for anonymous access
ContainerRegistryClient client = new ContainerRegistryClient(endpoint);
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});

// Obtain a RegistryArtifact object to get access to image operations
RegistryArtifact image = client.GetArtifact("library/hello-world", "latest");
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,10 @@ This sample shows how to list the tags for an image with anonymous access.
Uri endpoint = new Uri(Environment.GetEnvironmentVariable("REGISTRY_ENDPOINT"));

// Create a new ContainerRegistryClient for anonymous access
ContainerRegistryClient client = new ContainerRegistryClient(endpoint);
ContainerRegistryClient client = new ContainerRegistryClient(endpoint, new ContainerRegistryClientOptions()
{
Audience = ContainerRegistryAudience.AzureResourceManagerPublicCloud
});

// Obtain a RegistryArtifact object to get access to image operations
RegistryArtifact image = client.GetArtifact("library/hello-world", "latest");
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -72,14 +72,20 @@ public ContainerRegistryClient(Uri endpoint, TokenCredential credential, Contain
Argument.AssertNotNull(credential, nameof(credential));
Argument.AssertNotNull(options, nameof(options));

if (options.Audience == null)
{
throw new InvalidOperationException("ContainerRegistryClientOptions.Audience property must be set to initialize ContainerRegistryClient.");
}

_endpoint = endpoint;
_registryName = endpoint.Host.Split('.')[0];
_clientDiagnostics = new ClientDiagnostics(options);

_acrAuthPipeline = HttpPipelineBuilder.Build(options);
_acrAuthClient = new AuthenticationRestClient(_clientDiagnostics, _acrAuthPipeline, endpoint.AbsoluteUri);

_pipeline = HttpPipelineBuilder.Build(options, new ContainerRegistryChallengeAuthenticationPolicy(credential, options.AuthenticationScope, _acrAuthClient));
string defaultScope = options.Audience + "/.default";
_pipeline = HttpPipelineBuilder.Build(options, new ContainerRegistryChallengeAuthenticationPolicy(credential, defaultScope, _acrAuthClient));
_restClient = new ContainerRegistryRestClient(_clientDiagnostics, _pipeline, _endpoint.AbsoluteUri);
}

Expand Down
Loading

0 comments on commit 1911ff2

Please sign in to comment.