From f524f55151909f3a987c9d42e44613ef51b88a2a Mon Sep 17 00:00:00 2001 From: Rick Anderson <3605364+Rick-Anderson@users.noreply.github.com> Date: Tue, 16 Jul 2024 12:46:52 -1000 Subject: [PATCH 01/16] DataProtection and scaling --- .../data-protection/configuration/scaling.md | 42 +++++++++++++++++++ .../scaling/includes/scaling7.md | 8 ++++ 2 files changed, 50 insertions(+) create mode 100644 aspnetcore/security/data-protection/configuration/scaling.md create mode 100644 aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md diff --git a/aspnetcore/security/data-protection/configuration/scaling.md b/aspnetcore/security/data-protection/configuration/scaling.md new file mode 100644 index 000000000000..423ae382f280 --- /dev/null +++ b/aspnetcore/security/data-protection/configuration/scaling.md @@ -0,0 +1,42 @@ +--- +title: Configure ASP.NET Core Data Protection in distributed or load-balanced environments +author: acasey +description: Learn how to configure Data Protection in ASP.NET Core for multi-instance apps. +ms.author: acasey +ms.custom: mvc +ms.date: 7/15/2024 +uid: security/data-protection/configuration/scaling +--- + +# Configure ASP.NET Core Data Protection in distributed or load-balanced environments + +:::moniker range=">= aspnetcore-8.0" + +ASP.NET Core [Data Protection](xref:security/data-protection/introduction) is a library that provides a cryptographic API to protect data. Data Protection: + +* Protects anti-forgery tokens, authentication cookies, and other sensitive data. +* Is designed to be easy to use and secure by default. + +However, in some distributed environments that don't utilize shared storage, when an app scales horizontally by adding more instances: + +* It's necessary to explicitly configure Data Protection to establish a shared storage location for Data Protection keys. +* There’s ***NO*** guarantee that the HTTP POST request, used to submit a form, will be routed to the same instance that served the initial page via an HTTP GET request. If the requests are handled by different instances, the antiforgery tokens aren’t synchronized, and an exception occurs. + +The following distributed environments provide automatic key storage in a shared location: + +* [Azure apps](/aspnet/core/security/data-protection/configuration/default-settings). +* Newly created Azure Container Apps built using ASP.NET Core Kestrel . For more information see [Autoscaling considerations +](/azure/container-apps/dotnet-overview#autoscaling-considerations). +* Azure Apps. For more information see . + +The following distributed environments do ***NOT*** provide automatic key storage in a shared location: + +* Separate [deployment slots](/azure/app-service/deploy-staging-slots), such as Staging and Production. When the app is swapped between deployment slots, any app using Data Protection won't be able to decrypt stored data using the key ring inside the previous slot. For example, swapping Staging to Production or using A/B testing, Data Protection is not synchronized. +* Asp.net core apps hosted on multiple VMs. +* In a web farm. For more information, see [Data Protection in a web farm](xref:host-and-deploy/web-farm#data-protection). +* Azure Container Apps built using ASP.NET Core Kestrel 7.0 or earlier. For more information see [Autoscaling considerations +](/azure/container-apps/dotnet-overview#autoscaling-considerations). + +:::moniker-end + +[!INCLUDE[](~/security/data-protection/configuration/scaling/includes/scaling7.md)] diff --git a/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md b/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md new file mode 100644 index 000000000000..850a17fe7b28 --- /dev/null +++ b/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md @@ -0,0 +1,8 @@ + +:::moniker range=">= aspnetcore-8.0" + +Duplicate of what we agree on in the V8+ scaling.md file with the following removed + + Newly created Azure Container Apps built using ASP.NET Core Kestrel 8.0 and later . For more information see [Autoscaling considerations + +:::moniker-end From 7e7f446749c88ccfb0ac57908f4f02d0d6dd3b2e Mon Sep 17 00:00:00 2001 From: Rick Anderson <3605364+Rick-Anderson@users.noreply.github.com> Date: Tue, 16 Jul 2024 12:50:39 -1000 Subject: [PATCH 02/16] DataProtection and scaling --- .../data-protection/configuration/scaling/includes/scaling7.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md b/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md index 850a17fe7b28..7d3934967d2e 100644 --- a/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md +++ b/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md @@ -1,5 +1,5 @@ -:::moniker range=">= aspnetcore-8.0" +:::moniker range="< aspnetcore-8.0" Duplicate of what we agree on in the V8+ scaling.md file with the following removed From 09a8106c59c6020be754c53d8fb062c6a0dabd4b Mon Sep 17 00:00:00 2001 From: Rick Anderson <3605364+Rick-Anderson@users.noreply.github.com> Date: Tue, 16 Jul 2024 13:37:11 -1000 Subject: [PATCH 03/16] DataProtection and scaling --- aspnetcore/host-and-deploy/web-farm.md | 4 ++-- .../data-protection/configuration/default-settings.md | 2 +- .../security/data-protection/configuration/scaling.md | 10 ++-------- 3 files changed, 5 insertions(+), 11 deletions(-) diff --git a/aspnetcore/host-and-deploy/web-farm.md b/aspnetcore/host-and-deploy/web-farm.md index e1a2676f0b8c..bac55376a5c1 100644 --- a/aspnetcore/host-and-deploy/web-farm.md +++ b/aspnetcore/host-and-deploy/web-farm.md @@ -38,11 +38,11 @@ When an app is scaled to multiple instances, there might be app state that requi ## Required configuration -Data Protection and Caching require configuration for apps deployed to a web farm. +Data Protection and Caching may require configuration for apps deployed to a web farm. ### Data Protection -The [ASP.NET Core Data Protection system](xref:security/data-protection/introduction) is used by apps to protect data. Data Protection relies upon a set of cryptographic keys stored in a *key ring*. When the Data Protection system is initialized, it applies [default settings](xref:security/data-protection/configuration/default-settings) that store the key ring locally. Under the default configuration, a unique key ring is stored on each node of the web farm. Consequently, each web farm node can't decrypt data that's encrypted by an app on any other node. The default configuration isn't generally appropriate for hosting apps in a web farm. An alternative to implementing a shared key ring is to always route user requests to the same node. For more information on Data Protection system configuration for web farm deployments, see . +The [ASP.NET Core Data Protection system](xref:security/data-protection/introduction) is used by apps to protect data. Data Protection relies upon a set of cryptographic keys stored in a *key ring*. When the Data Protection system is initialized, it applies [default settings](xref:security/data-protection/ configuration/default-settings) that store the key ring locally. For more information, see . ### Caching diff --git a/aspnetcore/security/data-protection/configuration/default-settings.md b/aspnetcore/security/data-protection/configuration/default-settings.md index 82efecdf5298..ccfd13a1da99 100644 --- a/aspnetcore/security/data-protection/configuration/default-settings.md +++ b/aspnetcore/security/data-protection/configuration/default-settings.md @@ -14,7 +14,7 @@ By [Rick Anderson](https://twitter.com/RickAndMSFT) The app attempts to detect its operational environment and handle key configuration on its own. -1. If the app is hosted in [Azure Apps](https://azure.microsoft.com/services/app-service/), keys are persisted to the *%HOME%\ASP.NET\DataProtection-Keys* folder. This folder is backed by network storage and is synchronized across all machines hosting the app. +1. If the app is hosted in [Azure Apps](/azure/app-service/overview), keys are persisted to the *%HOME%\ASP.NET\DataProtection-Keys* folder. This folder is backed by network storage and is synchronized across all machines hosting the app. * Keys aren't protected at rest. * The *DataProtection-Keys* folder supplies the key ring to all instances of an app in a single deployment slot. * Separate deployment slots, such as Staging and Production, don't share a key ring. When you swap between deployment slots, for example swapping Staging to Production or using A/B testing, any app using Data Protection won't be able to decrypt stored data using the key ring inside the previous slot. This leads to users being logged out of an app that uses the standard ASP.NET Core cookie authentication, as it uses Data Protection to protect its cookies. If you desire slot-independent key rings, use an external key ring provider, such as Azure Blob Storage, Azure Key Vault, a SQL store, or Redis cache. diff --git a/aspnetcore/security/data-protection/configuration/scaling.md b/aspnetcore/security/data-protection/configuration/scaling.md index 423ae382f280..c7be6ee9909a 100644 --- a/aspnetcore/security/data-protection/configuration/scaling.md +++ b/aspnetcore/security/data-protection/configuration/scaling.md @@ -12,12 +12,7 @@ uid: security/data-protection/configuration/scaling :::moniker range=">= aspnetcore-8.0" -ASP.NET Core [Data Protection](xref:security/data-protection/introduction) is a library that provides a cryptographic API to protect data. Data Protection: - -* Protects anti-forgery tokens, authentication cookies, and other sensitive data. -* Is designed to be easy to use and secure by default. - -However, in some distributed environments that don't utilize shared storage, when an app scales horizontally by adding more instances: +ASP.NET Core [Data Protection](xref:security/data-protection/introduction) is a library that provides a cryptographic API to protect data. Data Protection protects anti-forgery tokens, authentication cookies, and other sensitive data. However, in some distributed environments that don't utilize shared storage, when an app scales horizontally by adding more instances: * It's necessary to explicitly configure Data Protection to establish a shared storage location for Data Protection keys. * There’s ***NO*** guarantee that the HTTP POST request, used to submit a form, will be routed to the same instance that served the initial page via an HTTP GET request. If the requests are handled by different instances, the antiforgery tokens aren’t synchronized, and an exception occurs. @@ -32,8 +27,7 @@ The following distributed environments provide automatic key storage in a shared The following distributed environments do ***NOT*** provide automatic key storage in a shared location: * Separate [deployment slots](/azure/app-service/deploy-staging-slots), such as Staging and Production. When the app is swapped between deployment slots, any app using Data Protection won't be able to decrypt stored data using the key ring inside the previous slot. For example, swapping Staging to Production or using A/B testing, Data Protection is not synchronized. -* Asp.net core apps hosted on multiple VMs. -* In a web farm. For more information, see [Data Protection in a web farm](xref:host-and-deploy/web-farm#data-protection). +* Asp.net core apps hosted on multiple VMs that don't use [Application Request Routing cookies]/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling), known as an ARR Affinity. * Azure Container Apps built using ASP.NET Core Kestrel 7.0 or earlier. For more information see [Autoscaling considerations ](/azure/container-apps/dotnet-overview#autoscaling-considerations). From ba71c7be08cabe30a7ea281f7afc0714f214daec Mon Sep 17 00:00:00 2001 From: Rick Anderson <3605364+Rick-Anderson@users.noreply.github.com> Date: Tue, 16 Jul 2024 13:42:17 -1000 Subject: [PATCH 04/16] DataProtection and scaling --- aspnetcore/host-and-deploy/web-farm.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/aspnetcore/host-and-deploy/web-farm.md b/aspnetcore/host-and-deploy/web-farm.md index bac55376a5c1..0e7110e5e222 100644 --- a/aspnetcore/host-and-deploy/web-farm.md +++ b/aspnetcore/host-and-deploy/web-farm.md @@ -42,7 +42,7 @@ Data Protection and Caching may require configuration for apps deployed to a web ### Data Protection -The [ASP.NET Core Data Protection system](xref:security/data-protection/introduction) is used by apps to protect data. Data Protection relies upon a set of cryptographic keys stored in a *key ring*. When the Data Protection system is initialized, it applies [default settings](xref:security/data-protection/ configuration/default-settings) that store the key ring locally. For more information, see . +The [ASP.NET Core Data Protection system](xref:security/data-protection/introduction) is used by apps to protect data. Data Protection relies upon a set of cryptographic keys stored in a *key ring*. When the Data Protection system is initialized, it applies [default settings](xref:security/data-protection/ configuration/default-settings) that store the key ring locally. For more information, see . ### Caching From 36f94236701d574679e5fe870c3a2956287b3c21 Mon Sep 17 00:00:00 2001 From: Rick Anderson <3605364+Rick-Anderson@users.noreply.github.com> Date: Tue, 16 Jul 2024 14:34:38 -1000 Subject: [PATCH 05/16] Apply suggestions from code review Co-authored-by: Andrew Casey --- aspnetcore/host-and-deploy/web-farm.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/aspnetcore/host-and-deploy/web-farm.md b/aspnetcore/host-and-deploy/web-farm.md index 0e7110e5e222..9f0eb1150dc2 100644 --- a/aspnetcore/host-and-deploy/web-farm.md +++ b/aspnetcore/host-and-deploy/web-farm.md @@ -42,7 +42,7 @@ Data Protection and Caching may require configuration for apps deployed to a web ### Data Protection -The [ASP.NET Core Data Protection system](xref:security/data-protection/introduction) is used by apps to protect data. Data Protection relies upon a set of cryptographic keys stored in a *key ring*. When the Data Protection system is initialized, it applies [default settings](xref:security/data-protection/ configuration/default-settings) that store the key ring locally. For more information, see . +The [ASP.NET Core Data Protection system](xref:security/data-protection/introduction) is used by apps to protect data. Data Protection relies upon a set of cryptographic keys stored in a *key ring*. When the Data Protection system is initialized, it applies [default settings](xref:security/data-protection/configuration/default-settings) that store the key ring locally. For more information, see . ### Caching From 1973c82a8a70be4181b3a43d79289d79066a0c31 Mon Sep 17 00:00:00 2001 From: Rick Anderson <3605364+Rick-Anderson@users.noreply.github.com> Date: Tue, 16 Jul 2024 14:47:49 -1000 Subject: [PATCH 06/16] DataProtection and scaling --- aspnetcore/host-and-deploy/web-farm.md | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/aspnetcore/host-and-deploy/web-farm.md b/aspnetcore/host-and-deploy/web-farm.md index 9f0eb1150dc2..24e1d5d0c6c2 100644 --- a/aspnetcore/host-and-deploy/web-farm.md +++ b/aspnetcore/host-and-deploy/web-farm.md @@ -40,9 +40,15 @@ When an app is scaled to multiple instances, there might be app state that requi Data Protection and Caching may require configuration for apps deployed to a web farm. -### Data Protection +### Data Protection in distributed environments -The [ASP.NET Core Data Protection system](xref:security/data-protection/introduction) is used by apps to protect data. Data Protection relies upon a set of cryptographic keys stored in a *key ring*. When the Data Protection system is initialized, it applies [default settings](xref:security/data-protection/configuration/default-settings) that store the key ring locally. For more information, see . +The [ASP.NET Core Data Protection system](xref:security/data-protection/introduction) is used by apps to protect data. Data Protection relies upon a set of cryptographic keys stored in a *key ring*. When the Data Protection system is initialized, it applies [default settings](xref:security/data-protection/configuration/default-settings) that store the key ring locally. The default configuration is appropriate for apps that run in a single instance. + +Apps that are running in distributed environments that don't configure Data Protection automatically need to explicitly configure Data Protection. See for environments that require explicit configuration of the Data Protection and those that don't. + +Under the default configuration, a unique key ring is stored on each node of the web farm. Consequently, each web farm node can't decrypt data that's encrypted by an app on any other node. The default configuration isn't generally appropriate for hosting apps in a web farm. [Application Request Routing](/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling) is an alternative to implementing a shared key ring is to always route user requests to the same node using. Application Request Routing is is known as ARR Affinity. + +For more information on Data Protection system configuration for web farm deployments, see . ### Caching From 73d70c1a855ee0201e847ba2e3642f08277b326d Mon Sep 17 00:00:00 2001 From: Rick Anderson <3605364+Rick-Anderson@users.noreply.github.com> Date: Tue, 16 Jul 2024 14:58:59 -1000 Subject: [PATCH 07/16] DataProtection and scaling --- aspnetcore/host-and-deploy/web-farm.md | 4 ++-- .../data-protection/configuration/scaling.md | 15 ++++++++------- 2 files changed, 10 insertions(+), 9 deletions(-) diff --git a/aspnetcore/host-and-deploy/web-farm.md b/aspnetcore/host-and-deploy/web-farm.md index 24e1d5d0c6c2..1fd8539de193 100644 --- a/aspnetcore/host-and-deploy/web-farm.md +++ b/aspnetcore/host-and-deploy/web-farm.md @@ -44,9 +44,9 @@ Data Protection and Caching may require configuration for apps deployed to a web The [ASP.NET Core Data Protection system](xref:security/data-protection/introduction) is used by apps to protect data. Data Protection relies upon a set of cryptographic keys stored in a *key ring*. When the Data Protection system is initialized, it applies [default settings](xref:security/data-protection/configuration/default-settings) that store the key ring locally. The default configuration is appropriate for apps that run in a single instance. -Apps that are running in distributed environments that don't configure Data Protection automatically need to explicitly configure Data Protection. See for environments that require explicit configuration of the Data Protection and those that don't. +Apps that are running in distributed environments that don't configure Data Protection automatically need to explicitly configure Data Protection. See for environments that require explicit Data Protection configuration and those that don't. -Under the default configuration, a unique key ring is stored on each node of the web farm. Consequently, each web farm node can't decrypt data that's encrypted by an app on any other node. The default configuration isn't generally appropriate for hosting apps in a web farm. [Application Request Routing](/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling) is an alternative to implementing a shared key ring is to always route user requests to the same node using. Application Request Routing is is known as ARR Affinity. +Under the default configuration, a unique key ring is stored on each node of the web farm. Consequently, each web farm node can't decrypt data that's encrypted by an app on any other node. The default configuration isn't generally appropriate for hosting apps in a web farm. [ARR Affinity](/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling) is an alternative to implementing a shared key ring is to always route user requests to the same node. However, ARR can reduce the scalability of a web farm. For more information on Data Protection system configuration for web farm deployments, see . diff --git a/aspnetcore/security/data-protection/configuration/scaling.md b/aspnetcore/security/data-protection/configuration/scaling.md index c7be6ee9909a..42f7132eb658 100644 --- a/aspnetcore/security/data-protection/configuration/scaling.md +++ b/aspnetcore/security/data-protection/configuration/scaling.md @@ -3,8 +3,9 @@ title: Configure ASP.NET Core Data Protection in distributed or load-balanced en author: acasey description: Learn how to configure Data Protection in ASP.NET Core for multi-instance apps. ms.author: acasey -ms.custom: mvc -ms.date: 7/15/2024 +ms.date: 7/18/2024 +content_well_notification: AI-contribution +ms.prod: aspnet-core uid: security/data-protection/configuration/scaling --- @@ -19,15 +20,15 @@ ASP.NET Core [Data Protection](xref:security/data-protection/introduction) is a The following distributed environments provide automatic key storage in a shared location: -* [Azure apps](/aspnet/core/security/data-protection/configuration/default-settings). -* Newly created Azure Container Apps built using ASP.NET Core Kestrel . For more information see [Autoscaling considerations +* [Azure apps](/aspnet/core/security/data-protection/configuration/default-settings). For more information see . +* Newly created Azure Container Apps built using ASP.NET Core Kestrel. For more information see [Autoscaling considerations ](/azure/container-apps/dotnet-overview#autoscaling-considerations). -* Azure Apps. For more information see . +* Azure Apps. The following distributed environments do ***NOT*** provide automatic key storage in a shared location: -* Separate [deployment slots](/azure/app-service/deploy-staging-slots), such as Staging and Production. When the app is swapped between deployment slots, any app using Data Protection won't be able to decrypt stored data using the key ring inside the previous slot. For example, swapping Staging to Production or using A/B testing, Data Protection is not synchronized. -* Asp.net core apps hosted on multiple VMs that don't use [Application Request Routing cookies]/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling), known as an ARR Affinity. +* Separate [deployment slots](/azure/app-service/deploy-staging-slots), such as Staging and Production. +* Asp.net core apps hosted on multiple non-Azure VMs that don't use server affinity. * Azure Container Apps built using ASP.NET Core Kestrel 7.0 or earlier. For more information see [Autoscaling considerations ](/azure/container-apps/dotnet-overview#autoscaling-considerations). From 907cfc6f317de1cba14f7064234c426b53e91b89 Mon Sep 17 00:00:00 2001 From: Rick Anderson <3605364+Rick-Anderson@users.noreply.github.com> Date: Tue, 16 Jul 2024 14:59:22 -1000 Subject: [PATCH 08/16] react to feedback --- aspnetcore/security/data-protection/configuration/scaling.md | 1 - 1 file changed, 1 deletion(-) diff --git a/aspnetcore/security/data-protection/configuration/scaling.md b/aspnetcore/security/data-protection/configuration/scaling.md index 42f7132eb658..b0d1ee4ef3c7 100644 --- a/aspnetcore/security/data-protection/configuration/scaling.md +++ b/aspnetcore/security/data-protection/configuration/scaling.md @@ -23,7 +23,6 @@ The following distributed environments provide automatic key storage in a shared * [Azure apps](/aspnet/core/security/data-protection/configuration/default-settings). For more information see . * Newly created Azure Container Apps built using ASP.NET Core Kestrel. For more information see [Autoscaling considerations ](/azure/container-apps/dotnet-overview#autoscaling-considerations). -* Azure Apps. The following distributed environments do ***NOT*** provide automatic key storage in a shared location: From 6ea6eeca14563f49269559603fa40c954b31d0db Mon Sep 17 00:00:00 2001 From: Rick Anderson <3605364+Rick-Anderson@users.noreply.github.com> Date: Tue, 16 Jul 2024 14:59:50 -1000 Subject: [PATCH 09/16] react to feedback --- aspnetcore/security/data-protection/configuration/scaling.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/aspnetcore/security/data-protection/configuration/scaling.md b/aspnetcore/security/data-protection/configuration/scaling.md index b0d1ee4ef3c7..ac5bc5027c6e 100644 --- a/aspnetcore/security/data-protection/configuration/scaling.md +++ b/aspnetcore/security/data-protection/configuration/scaling.md @@ -27,9 +27,9 @@ The following distributed environments provide automatic key storage in a shared The following distributed environments do ***NOT*** provide automatic key storage in a shared location: * Separate [deployment slots](/azure/app-service/deploy-staging-slots), such as Staging and Production. -* Asp.net core apps hosted on multiple non-Azure VMs that don't use server affinity. * Azure Container Apps built using ASP.NET Core Kestrel 7.0 or earlier. For more information see [Autoscaling considerations ](/azure/container-apps/dotnet-overview#autoscaling-considerations). +* Asp.net core apps hosted on multiple non-Azure VMs that don't use server affinity. :::moniker-end From 8c27b9187af8cf3dbeb116736969b3b69d8533bb Mon Sep 17 00:00:00 2001 From: Rick Anderson <3605364+Rick-Anderson@users.noreply.github.com> Date: Tue, 16 Jul 2024 15:13:05 -1000 Subject: [PATCH 10/16] react to feedback --- aspnetcore/host-and-deploy/web-farm.md | 2 +- .../data-protection/configuration/scaling.md | 2 +- .../scaling/includes/scaling7.md | 23 +++++++++++++++++-- 3 files changed, 23 insertions(+), 4 deletions(-) diff --git a/aspnetcore/host-and-deploy/web-farm.md b/aspnetcore/host-and-deploy/web-farm.md index 1fd8539de193..4cdc2d46dd0a 100644 --- a/aspnetcore/host-and-deploy/web-farm.md +++ b/aspnetcore/host-and-deploy/web-farm.md @@ -46,7 +46,7 @@ The [ASP.NET Core Data Protection system](xref:security/data-protection/introduc Apps that are running in distributed environments that don't configure Data Protection automatically need to explicitly configure Data Protection. See for environments that require explicit Data Protection configuration and those that don't. -Under the default configuration, a unique key ring is stored on each node of the web farm. Consequently, each web farm node can't decrypt data that's encrypted by an app on any other node. The default configuration isn't generally appropriate for hosting apps in a web farm. [ARR Affinity](/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling) is an alternative to implementing a shared key ring is to always route user requests to the same node. However, ARR can reduce the scalability of a web farm. +Under the default configuration, a unique key ring is stored on each node of the web farm. Consequently, each web farm node can't decrypt data that's encrypted by an app on any other node. The default configuration isn't generally appropriate for hosting apps in a web farm. Sticky sessions using [ARR Affinity](/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling) is an alternative to implementing a shared key ring is to always route user requests to the same node. However, ARR can reduce the scalability of a web farm. For more information on Data Protection system configuration for web farm deployments, see . diff --git a/aspnetcore/security/data-protection/configuration/scaling.md b/aspnetcore/security/data-protection/configuration/scaling.md index ac5bc5027c6e..c0ec403de392 100644 --- a/aspnetcore/security/data-protection/configuration/scaling.md +++ b/aspnetcore/security/data-protection/configuration/scaling.md @@ -16,7 +16,7 @@ uid: security/data-protection/configuration/scaling ASP.NET Core [Data Protection](xref:security/data-protection/introduction) is a library that provides a cryptographic API to protect data. Data Protection protects anti-forgery tokens, authentication cookies, and other sensitive data. However, in some distributed environments that don't utilize shared storage, when an app scales horizontally by adding more instances: * It's necessary to explicitly configure Data Protection to establish a shared storage location for Data Protection keys. -* There’s ***NO*** guarantee that the HTTP POST request, used to submit a form, will be routed to the same instance that served the initial page via an HTTP GET request. If the requests are handled by different instances, the antiforgery tokens aren’t synchronized, and an exception occurs. +* There’s ***NO*** guarantee that the HTTP POST request, used to submit a form, will be routed to the same instance that served the initial page via an HTTP GET request. If the requests are handled by different instances, the antiforgery tokens aren’t synchronized, and an exception occurs. Sticky sessions via [ARR Affinity](/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling) routes user requests to the same node, however, ARR can reduce the scalability of a web farm. The following distributed environments provide automatic key storage in a shared location: diff --git a/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md b/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md index 7d3934967d2e..994cbb654523 100644 --- a/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md +++ b/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md @@ -1,8 +1,27 @@ :::moniker range="< aspnetcore-8.0" -Duplicate of what we agree on in the V8+ scaling.md file with the following removed + - Newly created Azure Container Apps built using ASP.NET Core Kestrel 8.0 and later . For more information see [Autoscaling considerations +ASP.NET Core [Data Protection](xref:security/data-protection/introduction) is a library that provides a cryptographic API to protect data. Data Protection protects anti-forgery tokens, authentication cookies, and other sensitive data. However, in some distributed environments that don't utilize shared storage, when an app scales horizontally by adding more instances: + +* It's necessary to explicitly configure Data Protection to establish a shared storage location for Data Protection keys. +* There’s ***NO*** guarantee that the HTTP POST request, used to submit a form, will be routed to the same instance that served the initial page via an HTTP GET request. If the requests are handled by different instances, the antiforgery tokens aren’t synchronized, and an exception occurs. Sticky sessions via [ARR Affinity](/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling) routes user requests to the same node, however, ARR can reduce the scalability of a web farm. + +The following distributed environments provide automatic key storage in a shared location: + +* [Azure apps](/aspnet/core/security/data-protection/configuration/default-settings) using .NET 8.0 and later. For more information see . +* Newly created Azure Container Apps built using ASP.NET Core Kestrel. For more information see [Autoscaling considerations +](/azure/container-apps/dotnet-overview#autoscaling-considerations). + +The following distributed environments do ***NOT*** provide automatic key storage in a shared location: + +* Separate [deployment slots](/azure/app-service/deploy-staging-slots), such as Staging and Production. +* Azure Container Apps built using ASP.NET Core Kestrel 7.0 or earlier. For more information see [Autoscaling considerations +](/azure/container-apps/dotnet-overview#autoscaling-considerations). +* Asp.net core apps hosted on multiple non-Azure VMs that don't use server affinity. :::moniker-end From 5dea93a164c75236a95282a771e36bdabbac0cd5 Mon Sep 17 00:00:00 2001 From: Rick Anderson <3605364+Rick-Anderson@users.noreply.github.com> Date: Tue, 16 Jul 2024 15:17:10 -1000 Subject: [PATCH 11/16] react to feedback --- .../data-protection/configuration/scaling/includes/scaling7.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md b/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md index 994cbb654523..a2a6add11c48 100644 --- a/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md +++ b/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md @@ -6,7 +6,7 @@ Duplicate of primary doc, only change using .NET 8.0 --> -ASP.NET Core [Data Protection](xref:security/data-protection/introduction) is a library that provides a cryptographic API to protect data. Data Protection protects anti-forgery tokens, authentication cookies, and other sensitive data. However, in some distributed environments that don't utilize shared storage, when an app scales horizontally by adding more instances: +ASP.NET Core [Data Protection](xref:security/data-protection/introduction) is a library that provides a cryptographic API to protect data. Data Protection protects anti-forgery tokens, authentication cookies, and other sensitive data. However, in some distributed environments that don't put data protection keys in shared storage, when an app scales horizontally by adding more instances: * It's necessary to explicitly configure Data Protection to establish a shared storage location for Data Protection keys. * There’s ***NO*** guarantee that the HTTP POST request, used to submit a form, will be routed to the same instance that served the initial page via an HTTP GET request. If the requests are handled by different instances, the antiforgery tokens aren’t synchronized, and an exception occurs. Sticky sessions via [ARR Affinity](/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling) routes user requests to the same node, however, ARR can reduce the scalability of a web farm. From ba6186bca9b9010cdaebf875e6af51b07d1c7ae7 Mon Sep 17 00:00:00 2001 From: Rick Anderson <3605364+Rick-Anderson@users.noreply.github.com> Date: Tue, 16 Jul 2024 15:23:23 -1000 Subject: [PATCH 12/16] react to feedback --- .../data-protection/configuration/scaling.md | 2 +- .../scaling/includes/scaling7.md | 20 +------------------ 2 files changed, 2 insertions(+), 20 deletions(-) diff --git a/aspnetcore/security/data-protection/configuration/scaling.md b/aspnetcore/security/data-protection/configuration/scaling.md index c0ec403de392..0a5f1d62a5f0 100644 --- a/aspnetcore/security/data-protection/configuration/scaling.md +++ b/aspnetcore/security/data-protection/configuration/scaling.md @@ -13,7 +13,7 @@ uid: security/data-protection/configuration/scaling :::moniker range=">= aspnetcore-8.0" -ASP.NET Core [Data Protection](xref:security/data-protection/introduction) is a library that provides a cryptographic API to protect data. Data Protection protects anti-forgery tokens, authentication cookies, and other sensitive data. However, in some distributed environments that don't utilize shared storage, when an app scales horizontally by adding more instances: +ASP.NET Core [Data Protection](xref:security/data-protection/introduction) is a library that provides a cryptographic API to protect data. Data Protection protects anti-forgery tokens, authentication cookies, and other sensitive data. However, in some distributed environments that don't put data protection keys in shared storage, when an app scales horizontally by adding more instances: * It's necessary to explicitly configure Data Protection to establish a shared storage location for Data Protection keys. * There’s ***NO*** guarantee that the HTTP POST request, used to submit a form, will be routed to the same instance that served the initial page via an HTTP GET request. If the requests are handled by different instances, the antiforgery tokens aren’t synchronized, and an exception occurs. Sticky sessions via [ARR Affinity](/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling) routes user requests to the same node, however, ARR can reduce the scalability of a web farm. diff --git a/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md b/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md index a2a6add11c48..03c3a1659262 100644 --- a/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md +++ b/aspnetcore/security/data-protection/configuration/scaling/includes/scaling7.md @@ -2,26 +2,8 @@ :::moniker range="< aspnetcore-8.0" -ASP.NET Core [Data Protection](xref:security/data-protection/introduction) is a library that provides a cryptographic API to protect data. Data Protection protects anti-forgery tokens, authentication cookies, and other sensitive data. However, in some distributed environments that don't put data protection keys in shared storage, when an app scales horizontally by adding more instances: - -* It's necessary to explicitly configure Data Protection to establish a shared storage location for Data Protection keys. -* There’s ***NO*** guarantee that the HTTP POST request, used to submit a form, will be routed to the same instance that served the initial page via an HTTP GET request. If the requests are handled by different instances, the antiforgery tokens aren’t synchronized, and an exception occurs. Sticky sessions via [ARR Affinity](/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling) routes user requests to the same node, however, ARR can reduce the scalability of a web farm. - -The following distributed environments provide automatic key storage in a shared location: - -* [Azure apps](/aspnet/core/security/data-protection/configuration/default-settings) using .NET 8.0 and later. For more information see . -* Newly created Azure Container Apps built using ASP.NET Core Kestrel. For more information see [Autoscaling considerations -](/azure/container-apps/dotnet-overview#autoscaling-considerations). - -The following distributed environments do ***NOT*** provide automatic key storage in a shared location: - -* Separate [deployment slots](/azure/app-service/deploy-staging-slots), such as Staging and Production. -* Azure Container Apps built using ASP.NET Core Kestrel 7.0 or earlier. For more information see [Autoscaling considerations -](/azure/container-apps/dotnet-overview#autoscaling-considerations). -* Asp.net core apps hosted on multiple non-Azure VMs that don't use server affinity. - :::moniker-end From 0d6f57de493d98b4fe2e7ca133cd25bb957e13e1 Mon Sep 17 00:00:00 2001 From: Rick Anderson <3605364+Rick-Anderson@users.noreply.github.com> Date: Wed, 17 Jul 2024 08:45:38 -1000 Subject: [PATCH 13/16] Apply suggestions from code review Co-authored-by: Andrew Casey --- aspnetcore/security/data-protection/configuration/scaling.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/aspnetcore/security/data-protection/configuration/scaling.md b/aspnetcore/security/data-protection/configuration/scaling.md index 0a5f1d62a5f0..1e9b2f1157c8 100644 --- a/aspnetcore/security/data-protection/configuration/scaling.md +++ b/aspnetcore/security/data-protection/configuration/scaling.md @@ -21,7 +21,7 @@ ASP.NET Core [Data Protection](xref:security/data-protection/introduction) is a The following distributed environments provide automatic key storage in a shared location: * [Azure apps](/aspnet/core/security/data-protection/configuration/default-settings). For more information see . -* Newly created Azure Container Apps built using ASP.NET Core Kestrel. For more information see [Autoscaling considerations +* Newly created Azure Container Apps built using ASP.NET Core. For more information see [Autoscaling considerations ](/azure/container-apps/dotnet-overview#autoscaling-considerations). The following distributed environments do ***NOT*** provide automatic key storage in a shared location: From 33d328c88f4e42d1029fa42e50a37d15af5fbeaa Mon Sep 17 00:00:00 2001 From: Rick Anderson <3605364+Rick-Anderson@users.noreply.github.com> Date: Wed, 17 Jul 2024 08:53:42 -1000 Subject: [PATCH 14/16] react to feedback --- .../security/data-protection/configuration/scaling.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/aspnetcore/security/data-protection/configuration/scaling.md b/aspnetcore/security/data-protection/configuration/scaling.md index 1e9b2f1157c8..7ea736b62fc7 100644 --- a/aspnetcore/security/data-protection/configuration/scaling.md +++ b/aspnetcore/security/data-protection/configuration/scaling.md @@ -16,7 +16,7 @@ uid: security/data-protection/configuration/scaling ASP.NET Core [Data Protection](xref:security/data-protection/introduction) is a library that provides a cryptographic API to protect data. Data Protection protects anti-forgery tokens, authentication cookies, and other sensitive data. However, in some distributed environments that don't put data protection keys in shared storage, when an app scales horizontally by adding more instances: * It's necessary to explicitly configure Data Protection to establish a shared storage location for Data Protection keys. -* There’s ***NO*** guarantee that the HTTP POST request, used to submit a form, will be routed to the same instance that served the initial page via an HTTP GET request. If the requests are handled by different instances, the antiforgery tokens aren’t synchronized, and an exception occurs. Sticky sessions via [ARR Affinity](/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling) routes user requests to the same node, however, ARR can reduce the scalability of a web farm. +* There’s ***NO*** guarantee that the HTTP POST request, used to submit a form, will be routed to the same instance that served the initial page via an HTTP GET request. If the requests are handled by different instances, the anti-forgery tokens aren’t synchronized, and an exception occurs. Sticky sessions via [ARR Affinity](/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling) routes user requests to the same node, however, ARR can reduce the scalability of a web farm. The following distributed environments provide automatic key storage in a shared location: @@ -24,12 +24,12 @@ The following distributed environments provide automatic key storage in a shared * Newly created Azure Container Apps built using ASP.NET Core. For more information see [Autoscaling considerations ](/azure/container-apps/dotnet-overview#autoscaling-considerations). -The following distributed environments do ***NOT*** provide automatic key storage in a shared location: +The following scenarios do ***NOT*** provide automatic key storage in a shared location: * Separate [deployment slots](/azure/app-service/deploy-staging-slots), such as Staging and Production. * Azure Container Apps built using ASP.NET Core Kestrel 7.0 or earlier. For more information see [Autoscaling considerations ](/azure/container-apps/dotnet-overview#autoscaling-considerations). -* Asp.net core apps hosted on multiple non-Azure VMs that don't use server affinity. +* Asp.net core apps hosted on multiple non-Azure VMs that don't use server affinity. Server affinity doesn't provide a shared location, it makes shared storage unnecessary. Server affinity ensures that a client's requests are always routed to the same server. For more information see [Server affinity](/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling). :::moniker-end From fff74ab8f4bcd35674f956349558b849a57eb521 Mon Sep 17 00:00:00 2001 From: Rick Anderson <3605364+Rick-Anderson@users.noreply.github.com> Date: Wed, 17 Jul 2024 10:49:15 -1000 Subject: [PATCH 15/16] react to feedback --- aspnetcore/security/data-protection/configuration/scaling.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/aspnetcore/security/data-protection/configuration/scaling.md b/aspnetcore/security/data-protection/configuration/scaling.md index 7ea736b62fc7..c8d9fcfc55df 100644 --- a/aspnetcore/security/data-protection/configuration/scaling.md +++ b/aspnetcore/security/data-protection/configuration/scaling.md @@ -16,7 +16,7 @@ uid: security/data-protection/configuration/scaling ASP.NET Core [Data Protection](xref:security/data-protection/introduction) is a library that provides a cryptographic API to protect data. Data Protection protects anti-forgery tokens, authentication cookies, and other sensitive data. However, in some distributed environments that don't put data protection keys in shared storage, when an app scales horizontally by adding more instances: * It's necessary to explicitly configure Data Protection to establish a shared storage location for Data Protection keys. -* There’s ***NO*** guarantee that the HTTP POST request, used to submit a form, will be routed to the same instance that served the initial page via an HTTP GET request. If the requests are handled by different instances, the anti-forgery tokens aren’t synchronized, and an exception occurs. Sticky sessions via [ARR Affinity](/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling) routes user requests to the same node, however, ARR can reduce the scalability of a web farm. +* There’s ***NO*** guarantee that the HTTP POST request, used to submit a form, will be routed to the same instance that served the initial page via an HTTP GET request. If the requests are handled by different instances, the anti-forgery tokens aren’t synchronized, and an exception occurs. Sticky sessions via [ARR Affinity](/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling) routes user requests to the same node. However, ARR can reduce the scalability of a web farm. The following distributed environments provide automatic key storage in a shared location: @@ -29,7 +29,7 @@ The following scenarios do ***NOT*** provide automatic key storage in a shared l * Separate [deployment slots](/azure/app-service/deploy-staging-slots), such as Staging and Production. * Azure Container Apps built using ASP.NET Core Kestrel 7.0 or earlier. For more information see [Autoscaling considerations ](/azure/container-apps/dotnet-overview#autoscaling-considerations). -* Asp.net core apps hosted on multiple non-Azure VMs that don't use server affinity. Server affinity doesn't provide a shared location, it makes shared storage unnecessary. Server affinity ensures that a client's requests are always routed to the same server. For more information see [Server affinity](/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling). +* Asp.net core apps hosted on multiple non-Azure VMs that don't use server affinity. Server affinity ensures that a client's requests are always routed to the same server so having the keys in a shared location is not necessary. For more information see [Server affinity](/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling). :::moniker-end From 4963274c06bb5750c569e846b5cbaf754e8569c8 Mon Sep 17 00:00:00 2001 From: Rick Anderson <3605364+Rick-Anderson@users.noreply.github.com> Date: Fri, 19 Jul 2024 08:19:05 -1000 Subject: [PATCH 16/16] react to feedback --- aspnetcore/security/data-protection/configuration/scaling.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/aspnetcore/security/data-protection/configuration/scaling.md b/aspnetcore/security/data-protection/configuration/scaling.md index c8d9fcfc55df..371f82d86af5 100644 --- a/aspnetcore/security/data-protection/configuration/scaling.md +++ b/aspnetcore/security/data-protection/configuration/scaling.md @@ -29,7 +29,7 @@ The following scenarios do ***NOT*** provide automatic key storage in a shared l * Separate [deployment slots](/azure/app-service/deploy-staging-slots), such as Staging and Production. * Azure Container Apps built using ASP.NET Core Kestrel 7.0 or earlier. For more information see [Autoscaling considerations ](/azure/container-apps/dotnet-overview#autoscaling-considerations). -* Asp.net core apps hosted on multiple non-Azure VMs that don't use server affinity. Server affinity ensures that a client's requests are always routed to the same server so having the keys in a shared location is not necessary. For more information see [Server affinity](/azure/app-service/manage-automatic-scaling?#how-does-arr-affinity-affect-automatic-scaling). +* Distributed apps that don't have a shared storage location or synchronization mechanism for Data Protection keys. :::moniker-end