ethyca-fides 2.63.1b0__py2.py3-none-any.whl → 2.63.1b3__py2.py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (125) hide show
  1. {ethyca_fides-2.63.1b0.dist-info → ethyca_fides-2.63.1b3.dist-info}/METADATA +1 -1
  2. {ethyca_fides-2.63.1b0.dist-info → ethyca_fides-2.63.1b3.dist-info}/RECORD +124 -112
  3. fides/_version.py +3 -3
  4. fides/api/alembic/migrations/versions/5efcdf18438e_add_manual_task_tables.py +160 -0
  5. fides/api/alembic/migrations/versions/bf713b5a021d_staged_resource_ancestor_link_data_.py +20 -11
  6. fides/api/db/base.py +2 -0
  7. fides/api/migrations/post_upgrade_index_creation.py +3 -3
  8. fides/api/models/attachment.py +36 -23
  9. fides/api/models/manual_tasks/__init__.py +8 -0
  10. fides/api/models/manual_tasks/manual_task.py +110 -0
  11. fides/api/models/manual_tasks/manual_task_log.py +100 -0
  12. fides/api/schemas/manual_tasks/__init__.py +0 -0
  13. fides/api/schemas/manual_tasks/manual_task_schemas.py +79 -0
  14. fides/api/schemas/manual_tasks/manual_task_status.py +151 -0
  15. fides/api/service/privacy_request/attachment_handling.py +132 -0
  16. fides/api/service/privacy_request/dsr_package/dsr_report_builder.py +264 -46
  17. fides/api/service/privacy_request/dsr_package/templates/attachments_index.html +33 -0
  18. fides/api/service/privacy_request/dsr_package/templates/collection_index.html +34 -9
  19. fides/api/service/privacy_request/dsr_package/templates/main.css +45 -2
  20. fides/api/service/privacy_request/dsr_package/templates/welcome.html +12 -8
  21. fides/api/service/privacy_request/request_runner_service.py +258 -139
  22. fides/api/service/storage/gcs.py +15 -3
  23. fides/api/service/storage/s3.py +28 -14
  24. fides/api/service/storage/util.py +45 -7
  25. fides/api/tasks/csv_utils.py +170 -0
  26. fides/api/tasks/encryption_utils.py +42 -0
  27. fides/api/tasks/storage.py +85 -91
  28. fides/api/util/cache.py +77 -1
  29. fides/config/redis_settings.py +99 -8
  30. fides/service/manual_tasks/__init__.py +0 -0
  31. fides/service/manual_tasks/manual_task_service.py +150 -0
  32. fides/service/messaging/aws_ses_service.py +5 -1
  33. fides/ui-build/static/admin/404.html +1 -1
  34. fides/ui-build/static/admin/add-systems/manual.html +1 -1
  35. fides/ui-build/static/admin/add-systems/multiple.html +1 -1
  36. fides/ui-build/static/admin/add-systems.html +1 -1
  37. fides/ui-build/static/admin/consent/configure/add-vendors.html +1 -1
  38. fides/ui-build/static/admin/consent/configure.html +1 -1
  39. fides/ui-build/static/admin/consent/privacy-experience/[id].html +1 -1
  40. fides/ui-build/static/admin/consent/privacy-experience/new.html +1 -1
  41. fides/ui-build/static/admin/consent/privacy-experience.html +1 -1
  42. fides/ui-build/static/admin/consent/privacy-notices/[id].html +1 -1
  43. fides/ui-build/static/admin/consent/privacy-notices/new.html +1 -1
  44. fides/ui-build/static/admin/consent/privacy-notices.html +1 -1
  45. fides/ui-build/static/admin/consent/properties.html +1 -1
  46. fides/ui-build/static/admin/consent/reporting.html +1 -1
  47. fides/ui-build/static/admin/consent.html +1 -1
  48. fides/ui-build/static/admin/data-catalog/[systemId]/projects/[projectUrn]/[resourceUrn].html +1 -1
  49. fides/ui-build/static/admin/data-catalog/[systemId]/projects/[projectUrn].html +1 -1
  50. fides/ui-build/static/admin/data-catalog/[systemId]/projects.html +1 -1
  51. fides/ui-build/static/admin/data-catalog/[systemId]/resources/[resourceUrn].html +1 -1
  52. fides/ui-build/static/admin/data-catalog/[systemId]/resources.html +1 -1
  53. fides/ui-build/static/admin/data-catalog.html +1 -1
  54. fides/ui-build/static/admin/data-discovery/action-center/[monitorId]/[systemId].html +1 -1
  55. fides/ui-build/static/admin/data-discovery/action-center/[monitorId].html +1 -1
  56. fides/ui-build/static/admin/data-discovery/action-center.html +1 -1
  57. fides/ui-build/static/admin/data-discovery/activity.html +1 -1
  58. fides/ui-build/static/admin/data-discovery/detection/[resourceUrn].html +1 -1
  59. fides/ui-build/static/admin/data-discovery/detection.html +1 -1
  60. fides/ui-build/static/admin/data-discovery/discovery/[resourceUrn].html +1 -1
  61. fides/ui-build/static/admin/data-discovery/discovery.html +1 -1
  62. fides/ui-build/static/admin/datamap.html +1 -1
  63. fides/ui-build/static/admin/dataset/[datasetId]/[collectionName]/[...subfieldNames].html +1 -1
  64. fides/ui-build/static/admin/dataset/[datasetId]/[collectionName].html +1 -1
  65. fides/ui-build/static/admin/dataset/[datasetId].html +1 -1
  66. fides/ui-build/static/admin/dataset/new.html +1 -1
  67. fides/ui-build/static/admin/dataset.html +1 -1
  68. fides/ui-build/static/admin/datastore-connection/[id].html +1 -1
  69. fides/ui-build/static/admin/datastore-connection/new.html +1 -1
  70. fides/ui-build/static/admin/datastore-connection.html +1 -1
  71. fides/ui-build/static/admin/index.html +1 -1
  72. fides/ui-build/static/admin/integrations/[id].html +1 -1
  73. fides/ui-build/static/admin/integrations.html +1 -1
  74. fides/ui-build/static/admin/lib/fides-ext-gpp.js +1 -1
  75. fides/ui-build/static/admin/lib/fides-headless.js +1 -1
  76. fides/ui-build/static/admin/lib/fides-preview.js +1 -1
  77. fides/ui-build/static/admin/lib/fides-tcf.js +2 -2
  78. fides/ui-build/static/admin/lib/fides.js +2 -2
  79. fides/ui-build/static/admin/login/[provider].html +1 -1
  80. fides/ui-build/static/admin/login.html +1 -1
  81. fides/ui-build/static/admin/messaging/[id].html +1 -1
  82. fides/ui-build/static/admin/messaging/add-template.html +1 -1
  83. fides/ui-build/static/admin/messaging.html +1 -1
  84. fides/ui-build/static/admin/poc/ant-components.html +1 -1
  85. fides/ui-build/static/admin/poc/form-experiments/AntForm.html +1 -1
  86. fides/ui-build/static/admin/poc/form-experiments/FormikAntFormItem.html +1 -1
  87. fides/ui-build/static/admin/poc/form-experiments/FormikControlled.html +1 -1
  88. fides/ui-build/static/admin/poc/form-experiments/FormikField.html +1 -1
  89. fides/ui-build/static/admin/poc/form-experiments/FormikSpreadField.html +1 -1
  90. fides/ui-build/static/admin/poc/forms.html +1 -1
  91. fides/ui-build/static/admin/poc/table-migration.html +1 -1
  92. fides/ui-build/static/admin/privacy-requests/[id].html +1 -1
  93. fides/ui-build/static/admin/privacy-requests/configure/messaging.html +1 -1
  94. fides/ui-build/static/admin/privacy-requests/configure/storage.html +1 -1
  95. fides/ui-build/static/admin/privacy-requests/configure.html +1 -1
  96. fides/ui-build/static/admin/privacy-requests.html +1 -1
  97. fides/ui-build/static/admin/properties/[id].html +1 -1
  98. fides/ui-build/static/admin/properties/add-property.html +1 -1
  99. fides/ui-build/static/admin/properties.html +1 -1
  100. fides/ui-build/static/admin/reporting/datamap.html +1 -1
  101. fides/ui-build/static/admin/settings/about/alpha.html +1 -1
  102. fides/ui-build/static/admin/settings/about.html +1 -1
  103. fides/ui-build/static/admin/settings/consent/[configuration_id]/[purpose_id].html +1 -1
  104. fides/ui-build/static/admin/settings/consent.html +1 -1
  105. fides/ui-build/static/admin/settings/custom-fields.html +1 -1
  106. fides/ui-build/static/admin/settings/domain-records.html +1 -1
  107. fides/ui-build/static/admin/settings/domains.html +1 -1
  108. fides/ui-build/static/admin/settings/email-templates.html +1 -1
  109. fides/ui-build/static/admin/settings/locations.html +1 -1
  110. fides/ui-build/static/admin/settings/organization.html +1 -1
  111. fides/ui-build/static/admin/settings/regulations.html +1 -1
  112. fides/ui-build/static/admin/systems/configure/[id]/test-datasets.html +1 -1
  113. fides/ui-build/static/admin/systems/configure/[id].html +1 -1
  114. fides/ui-build/static/admin/systems.html +1 -1
  115. fides/ui-build/static/admin/taxonomy.html +1 -1
  116. fides/ui-build/static/admin/user-management/new.html +1 -1
  117. fides/ui-build/static/admin/user-management/profile/[id].html +1 -1
  118. fides/ui-build/static/admin/user-management.html +1 -1
  119. fides/api/service/privacy_request/dsr_package/templates/item.html +0 -37
  120. {ethyca_fides-2.63.1b0.dist-info → ethyca_fides-2.63.1b3.dist-info}/WHEEL +0 -0
  121. {ethyca_fides-2.63.1b0.dist-info → ethyca_fides-2.63.1b3.dist-info}/entry_points.txt +0 -0
  122. {ethyca_fides-2.63.1b0.dist-info → ethyca_fides-2.63.1b3.dist-info}/licenses/LICENSE +0 -0
  123. {ethyca_fides-2.63.1b0.dist-info → ethyca_fides-2.63.1b3.dist-info}/top_level.txt +0 -0
  124. /fides/ui-build/static/admin/_next/static/{j0v5qPG9TaezfK2WMkHhI → ycPcko8qnif6BlkQ6MN4D}/_buildManifest.js +0 -0
  125. /fides/ui-build/static/admin/_next/static/{j0v5qPG9TaezfK2WMkHhI → ycPcko8qnif6BlkQ6MN4D}/_ssgManifest.js +0 -0
fides/api/util/cache.py CHANGED
@@ -1,4 +1,5 @@
1
1
  import json
2
+ import os
2
3
  from typing import Any, Dict, List, Optional, Union
3
4
  from urllib.parse import unquote_to_bytes
4
5
 
@@ -27,6 +28,7 @@ from fides.config import CONFIG
27
28
  RedisValue = Union[bytes, float, int, str]
28
29
 
29
30
  _connection = None
31
+ _read_only_connection = None
30
32
 
31
33
 
32
34
  class FidesopsRedis(Redis):
@@ -157,6 +159,36 @@ class FidesopsRedis(Redis):
157
159
  return list_length
158
160
 
159
161
 
162
+ # FIXME: Ideally we don't want our code to be aware of the way tests are run,
163
+ # e.g that we run them in parallel with pytest-xdist. We need to find a way
164
+ # to change the pytest_configure_node hook to set the correct environment variable
165
+ # like we do for the readonly database. It wasn't working so we're using this workaround for now.
166
+ def _determine_redis_db_index(
167
+ read_only: Optional[bool] = False,
168
+ ) -> int: # pragma: no cover
169
+ """Return the Redis DB index that should be used for the current process.
170
+
171
+ Behavior:
172
+ 1. Test mode:
173
+ - If running under xdist, map `gwN` → DB `N + 1` (reserve DB 0).
174
+ - If *not* running under xdist, always use DB 1.
175
+
176
+ 2. Non-test mode: return the value already present in `CONFIG.redis.db_index`
177
+ """
178
+
179
+ # 1. Test mode logic
180
+ if CONFIG.test_mode:
181
+ worker_id = os.getenv("PYTEST_XDIST_WORKER")
182
+ if worker_id and worker_id.startswith("gw"):
183
+ suffix = worker_id[2:]
184
+ if suffix.isdigit():
185
+ return int(suffix) + 1 # gw0 -> 1, gw1 -> 2, etc.
186
+ return CONFIG.redis.test_db_index
187
+
188
+ # 2. Non-test mode
189
+ return CONFIG.redis.read_only_db_index if read_only else CONFIG.redis.db_index
190
+
191
+
160
192
  def get_cache(should_log: Optional[bool] = False) -> FidesopsRedis:
161
193
  """Return a singleton connection to our Redis cache"""
162
194
 
@@ -173,7 +205,7 @@ def get_cache(should_log: Optional[bool] = False) -> FidesopsRedis:
173
205
  decode_responses=CONFIG.redis.decode_responses,
174
206
  host=CONFIG.redis.host,
175
207
  port=CONFIG.redis.port,
176
- db=CONFIG.redis.db_index,
208
+ db=_determine_redis_db_index(),
177
209
  username=CONFIG.redis.user,
178
210
  password=CONFIG.redis.password,
179
211
  ssl=CONFIG.redis.ssl,
@@ -202,6 +234,50 @@ def get_cache(should_log: Optional[bool] = False) -> FidesopsRedis:
202
234
  return _connection
203
235
 
204
236
 
237
+ def get_read_only_cache() -> FidesopsRedis:
238
+ """
239
+ Return a singleton connection to the read-only Redis cache.
240
+ If read-only is not enabled, return the regular cache.
241
+ """
242
+ # If read-only is not enabled, return the regular cache
243
+ if not CONFIG.redis.read_only_enabled:
244
+ logger.debug(
245
+ "Read-only Redis is not enabled. Returning writeable cache connection instead."
246
+ )
247
+ return get_cache()
248
+
249
+ global _read_only_connection # pylint: disable=W0603
250
+ if _read_only_connection is None:
251
+ logger.debug("Creating new read-only Redis connection...")
252
+ _read_only_connection = FidesopsRedis( # type: ignore[call-overload]
253
+ charset=CONFIG.redis.charset,
254
+ decode_responses=CONFIG.redis.decode_responses,
255
+ host=CONFIG.redis.read_only_host,
256
+ port=CONFIG.redis.read_only_port,
257
+ db=_determine_redis_db_index(read_only=True),
258
+ username=CONFIG.redis.read_only_user,
259
+ password=CONFIG.redis.read_only_password,
260
+ ssl=CONFIG.redis.read_only_ssl,
261
+ ssl_ca_certs=CONFIG.redis.read_only_ssl_ca_certs,
262
+ ssl_cert_reqs=CONFIG.redis.read_only_ssl_cert_reqs,
263
+ )
264
+ logger.debug("New read-only Redis connection created.")
265
+
266
+ try:
267
+ connected = _read_only_connection.ping()
268
+ logger.debug("Read-only Redis connection succeeded.")
269
+ except ConnectionErrorFromRedis:
270
+ connected = False
271
+
272
+ if not connected:
273
+ logger.error(
274
+ "Unable to establish read-only Redis connection. Returning writeable cache connection instead."
275
+ )
276
+ return get_cache()
277
+
278
+ return _read_only_connection
279
+
280
+
205
281
  def get_identity_cache_key(privacy_request_id: str, identity_attribute: str) -> str:
206
282
  """Return the key at which to save this PrivacyRequest's identity for the passed in attribute"""
207
283
  # TODO: Remove this prefix
@@ -20,6 +20,10 @@ class RedisSettings(FidesSettings):
20
20
  default=0,
21
21
  description="The application will use this index in the Redis cache to cache data.",
22
22
  )
23
+ test_db_index: int = Field(
24
+ default=1,
25
+ description="The application will use this index in the Redis cache to cache data for testing.",
26
+ )
23
27
  decode_responses: bool = Field(
24
28
  default=True,
25
29
  description="Whether or not to automatically decode the values fetched from Redis. Decodes using the `charset` configuration value.",
@@ -64,14 +68,57 @@ class RedisSettings(FidesSettings):
64
68
  default="", description="The user with which to login to the Redis cache."
65
69
  )
66
70
 
71
+ # Read-only Redis settings
72
+ read_only_enabled: bool = Field(
73
+ default=False,
74
+ description="Whether a read-only Redis cache is enabled.",
75
+ )
76
+ read_only_host: str = Field(
77
+ default="",
78
+ description="The network address for the read-only Redis cache.",
79
+ )
80
+ read_only_port: int = Field(
81
+ default=6379,
82
+ description="The port at which the read-only Redis cache will be accessible.",
83
+ )
84
+ read_only_user: str = Field(
85
+ default="",
86
+ description="The user with which to login to the read-only Redis cache.",
87
+ )
88
+ read_only_password: str = Field(
89
+ default="",
90
+ description="The password with which to login to the read-only Redis cache.",
91
+ )
92
+ read_only_db_index: int = Field(
93
+ default=0,
94
+ description="The application will use this index in the read-only Redis cache to cache data.",
95
+ )
96
+ read_only_ssl: bool = Field(
97
+ default=False,
98
+ description="Whether the application's connections to the read-only cache should be encrypted using TLS.",
99
+ )
100
+ read_only_ssl_cert_reqs: Optional[str] = Field(
101
+ default="required",
102
+ description="If using TLS encryption, set this to 'required' if you wish to enforce the read-only Redis cache to provide a certificate. Note that not all cache providers support this without setting ssl_ca_certs (e.g. AWS Elasticache).",
103
+ )
104
+ read_only_ssl_ca_certs: str = Field(
105
+ default="",
106
+ description="If using TLS encryption rooted with a custom Certificate Authority, set this to the path of the CA certificate.",
107
+ )
108
+
67
109
  # This relies on other values to get built so must be last
68
110
  connection_url: Optional[str] = Field(
69
111
  default=None,
70
112
  description="A full connection URL to the Redis cache. If not specified, this URL is automatically assembled from the host, port, password and db_index specified above.",
71
113
  exclude=True,
72
114
  )
115
+ read_only_connection_url: Optional[str] = Field(
116
+ default=None,
117
+ description="A full connection URL to the read-only Redis cache. If not specified, this URL is automatically assembled from the read_only_host, read_only_port, read_only_password and read_only_db_index specified above.",
118
+ exclude=True,
119
+ )
73
120
 
74
- @field_validator("connection_url", mode="before")
121
+ @field_validator("connection_url", "read_only_connection_url", mode="before")
75
122
  @classmethod
76
123
  def assemble_connection_url(
77
124
  cls,
@@ -83,22 +130,50 @@ class RedisSettings(FidesSettings):
83
130
  # If the whole URL is provided via the config, preference that
84
131
  return v
85
132
 
133
+ is_read_only = info.field_name == "read_only_connection_url"
134
+
86
135
  connection_protocol = "redis"
87
136
  params_str = ""
88
- use_tls = info.data.get("ssl", False)
137
+ use_tls = (
138
+ info.data.get("read_only_ssl")
139
+ if is_read_only
140
+ else info.data.get("ssl", False)
141
+ )
89
142
 
90
143
  # These vars are intentionally fetched with `or ""` as the default to account
91
144
  # for the edge case where `None` is explicitly set in `values` by Pydantic because
92
145
  # it is not overridden by the config file or an env var
93
- user = info.data.get("user") or ""
94
- password = info.data.get("password") or ""
95
- db_index = info.data.get("db_index") or ""
146
+ user = (
147
+ info.data.get("read_only_user", "")
148
+ if is_read_only
149
+ else info.data.get("user", "")
150
+ )
151
+ password = (
152
+ info.data.get("read_only_password", "")
153
+ if is_read_only
154
+ else info.data.get("password", "")
155
+ )
156
+ db_index = (
157
+ info.data.get("read_only_db_index", "")
158
+ if is_read_only
159
+ else info.data.get("db_index", "")
160
+ )
96
161
  if use_tls:
97
162
  # If using TLS update the connection URL format
98
163
  connection_protocol = "rediss"
99
- cert_reqs = info.data.get("ssl_cert_reqs", "none")
164
+ cert_reqs = (
165
+ info.data.get("read_only_ssl_cert_reqs", "none")
166
+ if is_read_only
167
+ else info.data.get("ssl_cert_reqs", "none")
168
+ )
100
169
  params = {"ssl_cert_reqs": quote_plus(cert_reqs)}
101
- if ssl_ca_certs := info.data.get("ssl_ca_certs", ""):
170
+
171
+ ssl_ca_certs = (
172
+ info.data.get("read_only_ssl_ca_certs", "")
173
+ if is_read_only
174
+ else info.data.get("ssl_ca_certs", "")
175
+ )
176
+ if ssl_ca_certs:
102
177
  params["ssl_ca_certs"] = quote(ssl_ca_certs, safe="/")
103
178
  params_str = "?" + urlencode(params, quote_via=quote, safe="/")
104
179
 
@@ -108,7 +183,23 @@ class RedisSettings(FidesSettings):
108
183
  if password or user:
109
184
  auth_prefix = f"{quote_plus(user)}:{quote_plus(password)}@"
110
185
 
111
- connection_url = f"{connection_protocol}://{auth_prefix}{info.data.get('host', '')}:{info.data.get('port', '')}/{db_index}{params_str}"
186
+ host = (
187
+ info.data.get("read_only_host", "")
188
+ if is_read_only
189
+ else info.data.get("host", "")
190
+ )
191
+ port = (
192
+ info.data.get("read_only_port", "")
193
+ if is_read_only
194
+ else info.data.get("port", "")
195
+ )
196
+
197
+ # Only include database index in URL if it's not the default (0)
198
+ db_path = f"{db_index}" if db_index != 0 else ""
199
+
200
+ connection_url = (
201
+ f"{connection_protocol}://{auth_prefix}{host}:{port}/{db_path}{params_str}"
202
+ )
112
203
  return connection_url
113
204
 
114
205
  model_config = SettingsConfigDict(env_prefix=ENV_PREFIX)
File without changes
@@ -0,0 +1,150 @@
1
+ from typing import Optional
2
+
3
+ from loguru import logger
4
+ from sqlalchemy import select
5
+ from sqlalchemy.orm import Session
6
+
7
+ from fides.api.models.fides_user import FidesUser
8
+ from fides.api.models.manual_tasks.manual_task import ManualTask, ManualTaskReference
9
+ from fides.api.models.manual_tasks.manual_task_log import ManualTaskLog
10
+ from fides.api.schemas.manual_tasks.manual_task_schemas import (
11
+ ManualTaskLogStatus,
12
+ ManualTaskParentEntityType,
13
+ ManualTaskReferenceType,
14
+ ManualTaskType,
15
+ )
16
+
17
+
18
+ class ManualTaskService:
19
+ def __init__(self, db: Session):
20
+ self.db = db
21
+
22
+ def get_task(
23
+ self,
24
+ task_id: Optional[str] = None,
25
+ parent_entity_id: Optional[str] = None,
26
+ parent_entity_type: Optional[ManualTaskParentEntityType] = None,
27
+ task_type: Optional[ManualTaskType] = None,
28
+ ) -> Optional[ManualTask]:
29
+ """Get the manual task using provided filters.
30
+
31
+ Args:
32
+ task_id: The task ID
33
+ parent_entity_id: The parent entity ID
34
+ parent_entity_type: The parent entity type
35
+ task_type: The task type
36
+
37
+ Returns:
38
+ Optional[ManualTask]: The manual task for the connection, if it exists
39
+ """
40
+ if not any([task_id, parent_entity_id, parent_entity_type, task_type]):
41
+ logger.warning("No filters provided to get_task. Returning None.")
42
+ return None
43
+
44
+ stmt = select(ManualTask) # type: ignore[arg-type]
45
+ if task_id:
46
+ stmt = stmt.where(ManualTask.id == task_id)
47
+ if parent_entity_id:
48
+ stmt = stmt.where(ManualTask.parent_entity_id == parent_entity_id)
49
+ if parent_entity_type:
50
+ stmt = stmt.where(ManualTask.parent_entity_type == parent_entity_type)
51
+ if task_type:
52
+ stmt = stmt.where(ManualTask.task_type == task_type)
53
+ return self.db.execute(stmt).scalar_one_or_none()
54
+
55
+ # User Management
56
+ def assign_users_to_task(
57
+ self, db: Session, task: ManualTask, user_ids: list[str]
58
+ ) -> None:
59
+ """Assigns users to this task. We can assign one or more users to a task.
60
+
61
+ Args:
62
+ db: Database session
63
+ task: The task to assign users to
64
+ user_ids: List of user IDs to assign
65
+ """
66
+ user_ids = list(set(user_ids))
67
+ if not user_ids:
68
+ raise ValueError("User ID is required for assignment")
69
+
70
+ # Create new user assignment
71
+ for user_id in user_ids:
72
+ # if user is already assigned, skip
73
+ if user_id in task.assigned_users:
74
+ continue
75
+ # verify user exists
76
+ user = db.query(FidesUser).filter_by(id=user_id).first()
77
+ if not user:
78
+ ManualTaskLog.create_error_log(
79
+ db=db,
80
+ task_id=task.id,
81
+ message=f"Failed to add user {user_id} to task {task.id}: user does not exist",
82
+ details={"user_id": user_id},
83
+ )
84
+ continue
85
+
86
+ ManualTaskReference.create(
87
+ db=db,
88
+ data={
89
+ "task_id": task.id,
90
+ "reference_id": user_id,
91
+ "reference_type": ManualTaskReferenceType.assigned_user,
92
+ },
93
+ )
94
+
95
+ # Log the user assignment
96
+ ManualTaskLog.create_log(
97
+ db=db,
98
+ task_id=task.id,
99
+ status=ManualTaskLogStatus.updated,
100
+ message=f"User {user_id} assigned to task",
101
+ details={"assigned_user_id": user_id},
102
+ )
103
+
104
+ def unassign_users_from_task(
105
+ self, db: Session, task: ManualTask, user_ids: list[str]
106
+ ) -> None:
107
+ """Remove the user assignment from this task.
108
+
109
+ Args:
110
+ db: Database session
111
+ task: The task to unassign users from
112
+ user_ids: List of user IDs to unassign
113
+ """
114
+ user_ids = list(set(user_ids))
115
+ if not user_ids:
116
+ raise ValueError("User ID is required for unassignment")
117
+
118
+ # Get references to unassign
119
+ references_to_unassign = (
120
+ db.query(ManualTaskReference)
121
+ .filter(
122
+ ManualTaskReference.task_id == task.id,
123
+ ManualTaskReference.reference_type
124
+ == ManualTaskReferenceType.assigned_user,
125
+ ManualTaskReference.reference_id.in_(user_ids),
126
+ )
127
+ .all()
128
+ )
129
+
130
+ # Delete references and log unassignments
131
+ for ref in references_to_unassign:
132
+ ref.delete(db)
133
+ ManualTaskLog.create_log(
134
+ db=db,
135
+ task_id=task.id,
136
+ status=ManualTaskLogStatus.updated,
137
+ message=f"User {ref.reference_id} unassigned from task",
138
+ details={"unassigned_user_id": ref.reference_id},
139
+ )
140
+
141
+ # Check if any users weren't unassigned
142
+ unassigned_user_ids = [ref.reference_id for ref in references_to_unassign]
143
+ left_over_user_ids = [
144
+ user_id for user_id in user_ids if user_id not in unassigned_user_ids
145
+ ]
146
+ if left_over_user_ids:
147
+ logger.warning(
148
+ f"Failed to unassign users {left_over_user_ids} from task {task.id}: "
149
+ "users were not assigned to the task"
150
+ )
@@ -3,6 +3,7 @@ from typing import Any, Optional
3
3
  from loguru import logger
4
4
 
5
5
  from fides.api.models.messaging import MessagingConfig
6
+ from fides.api.models.property import CONFIG
6
7
  from fides.api.schemas.messaging.messaging import (
7
8
  MessagingServiceDetailsAWS_SES,
8
9
  MessagingServiceSecretsAWS_SES,
@@ -86,7 +87,10 @@ class AWS_SES_Service:
86
87
  aws_session = get_aws_session(
87
88
  auth_method=self.messaging_config_secrets.auth_method.value,
88
89
  storage_secrets=storage_secrets, # type: ignore[arg-type]
89
- assume_role_arn=self.messaging_config_secrets.aws_assume_role_arn,
90
+ assume_role_arn=CONFIG.credentials.get( # pylint: disable=no-member
91
+ "notifications", {}
92
+ ).get("aws_ses_assume_role_arn")
93
+ or self.messaging_config_secrets.aws_assume_role_arn,
90
94
  )
91
95
  aws_ses_client = aws_session.client(
92
96
  "ses", region_name=self.messaging_config_details.aws_region
@@ -1 +1 @@
1
- <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/pages/404-ec04f826f3dd79ea.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_buildManifest.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/404","query":{},"buildId":"j0v5qPG9TaezfK2WMkHhI","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
1
+ <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/pages/404-ec04f826f3dd79ea.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_buildManifest.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/404","query":{},"buildId":"ycPcko8qnif6BlkQ6MN4D","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
@@ -1 +1 @@
1
- <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><link rel="preload" href="/_next/static/css/92fc10cc7ed1aba3.css" as="style"/><link rel="stylesheet" href="/_next/static/css/92fc10cc7ed1aba3.css" data-n-p=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/c78d26b1-88a3e1bacb2a03c2.js" defer=""></script><script src="/_next/static/chunks/6060-cb1ab5be7067bf7b.js" defer=""></script><script src="/_next/static/chunks/2858-0b44609b6be7850b.js" defer=""></script><script src="/_next/static/chunks/2866-a73888c17a195cbe.js" defer=""></script><script src="/_next/static/chunks/9278-9b1b5970f0702668.js" defer=""></script><script src="/_next/static/chunks/5277-e8a036319456127f.js" defer=""></script><script src="/_next/static/chunks/7553-08bc3d9f66695111.js" defer=""></script><script src="/_next/static/chunks/4481-7f6710c928bb0cb0.js" defer=""></script><script src="/_next/static/chunks/401-7e800aed05537126.js" defer=""></script><script src="/_next/static/chunks/7980-736f9fd1e749ddd2.js" defer=""></script><script src="/_next/static/chunks/8499-1fd392d0be9e8ee4.js" defer=""></script><script src="/_next/static/chunks/6202-081545c7822d09af.js" defer=""></script><script src="/_next/static/chunks/4132-9b1731bfec6ee537.js" defer=""></script><script src="/_next/static/chunks/8032-74d94f7bd5b81c89.js" defer=""></script><script src="/_next/static/chunks/pages/add-systems/manual-1bec086d567aacff.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_buildManifest.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/add-systems/manual","query":{},"buildId":"j0v5qPG9TaezfK2WMkHhI","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
1
+ <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><link rel="preload" href="/_next/static/css/92fc10cc7ed1aba3.css" as="style"/><link rel="stylesheet" href="/_next/static/css/92fc10cc7ed1aba3.css" data-n-p=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/c78d26b1-88a3e1bacb2a03c2.js" defer=""></script><script src="/_next/static/chunks/6060-cb1ab5be7067bf7b.js" defer=""></script><script src="/_next/static/chunks/2858-0b44609b6be7850b.js" defer=""></script><script src="/_next/static/chunks/2866-a73888c17a195cbe.js" defer=""></script><script src="/_next/static/chunks/9278-9b1b5970f0702668.js" defer=""></script><script src="/_next/static/chunks/5277-e8a036319456127f.js" defer=""></script><script src="/_next/static/chunks/7553-08bc3d9f66695111.js" defer=""></script><script src="/_next/static/chunks/4481-7f6710c928bb0cb0.js" defer=""></script><script src="/_next/static/chunks/401-7e800aed05537126.js" defer=""></script><script src="/_next/static/chunks/7980-736f9fd1e749ddd2.js" defer=""></script><script src="/_next/static/chunks/8499-1fd392d0be9e8ee4.js" defer=""></script><script src="/_next/static/chunks/6202-081545c7822d09af.js" defer=""></script><script src="/_next/static/chunks/4132-9b1731bfec6ee537.js" defer=""></script><script src="/_next/static/chunks/8032-74d94f7bd5b81c89.js" defer=""></script><script src="/_next/static/chunks/pages/add-systems/manual-1bec086d567aacff.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_buildManifest.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/add-systems/manual","query":{},"buildId":"ycPcko8qnif6BlkQ6MN4D","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
@@ -1 +1 @@
1
- <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/c78d26b1-88a3e1bacb2a03c2.js" defer=""></script><script src="/_next/static/chunks/6060-cb1ab5be7067bf7b.js" defer=""></script><script src="/_next/static/chunks/7553-08bc3d9f66695111.js" defer=""></script><script src="/_next/static/chunks/4481-7f6710c928bb0cb0.js" defer=""></script><script src="/_next/static/chunks/401-7e800aed05537126.js" defer=""></script><script src="/_next/static/chunks/3923-b4f701ada3ef0ee0.js" defer=""></script><script src="/_next/static/chunks/796-d6586308ed44334b.js" defer=""></script><script src="/_next/static/chunks/pages/add-systems/multiple-f68bf100e4e60e88.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_buildManifest.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/add-systems/multiple","query":{},"buildId":"j0v5qPG9TaezfK2WMkHhI","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
1
+ <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/c78d26b1-88a3e1bacb2a03c2.js" defer=""></script><script src="/_next/static/chunks/6060-cb1ab5be7067bf7b.js" defer=""></script><script src="/_next/static/chunks/7553-08bc3d9f66695111.js" defer=""></script><script src="/_next/static/chunks/4481-7f6710c928bb0cb0.js" defer=""></script><script src="/_next/static/chunks/401-7e800aed05537126.js" defer=""></script><script src="/_next/static/chunks/3923-b4f701ada3ef0ee0.js" defer=""></script><script src="/_next/static/chunks/796-d6586308ed44334b.js" defer=""></script><script src="/_next/static/chunks/pages/add-systems/multiple-f68bf100e4e60e88.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_buildManifest.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/add-systems/multiple","query":{},"buildId":"ycPcko8qnif6BlkQ6MN4D","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
@@ -1 +1 @@
1
- <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><link rel="preload" href="/_next/static/css/972dc7eef106ee7c.css" as="style"/><link rel="stylesheet" href="/_next/static/css/972dc7eef106ee7c.css" data-n-p=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/7553-08bc3d9f66695111.js" defer=""></script><script src="/_next/static/chunks/pages/add-systems-effde5cfe49de55f.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_buildManifest.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/add-systems","query":{},"buildId":"j0v5qPG9TaezfK2WMkHhI","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
1
+ <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><link rel="preload" href="/_next/static/css/972dc7eef106ee7c.css" as="style"/><link rel="stylesheet" href="/_next/static/css/972dc7eef106ee7c.css" data-n-p=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/7553-08bc3d9f66695111.js" defer=""></script><script src="/_next/static/chunks/pages/add-systems-effde5cfe49de55f.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_buildManifest.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/add-systems","query":{},"buildId":"ycPcko8qnif6BlkQ6MN4D","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
@@ -1 +1 @@
1
- <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/c78d26b1-88a3e1bacb2a03c2.js" defer=""></script><script src="/_next/static/chunks/6060-cb1ab5be7067bf7b.js" defer=""></script><script src="/_next/static/chunks/7553-08bc3d9f66695111.js" defer=""></script><script src="/_next/static/chunks/4481-7f6710c928bb0cb0.js" defer=""></script><script src="/_next/static/chunks/401-7e800aed05537126.js" defer=""></script><script src="/_next/static/chunks/3923-b4f701ada3ef0ee0.js" defer=""></script><script src="/_next/static/chunks/796-d6586308ed44334b.js" defer=""></script><script src="/_next/static/chunks/pages/consent/configure/add-vendors-ec95ed8cb0712828.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_buildManifest.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/consent/configure/add-vendors","query":{},"buildId":"j0v5qPG9TaezfK2WMkHhI","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
1
+ <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/c78d26b1-88a3e1bacb2a03c2.js" defer=""></script><script src="/_next/static/chunks/6060-cb1ab5be7067bf7b.js" defer=""></script><script src="/_next/static/chunks/7553-08bc3d9f66695111.js" defer=""></script><script src="/_next/static/chunks/4481-7f6710c928bb0cb0.js" defer=""></script><script src="/_next/static/chunks/401-7e800aed05537126.js" defer=""></script><script src="/_next/static/chunks/3923-b4f701ada3ef0ee0.js" defer=""></script><script src="/_next/static/chunks/796-d6586308ed44334b.js" defer=""></script><script src="/_next/static/chunks/pages/consent/configure/add-vendors-ec95ed8cb0712828.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_buildManifest.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/consent/configure/add-vendors","query":{},"buildId":"ycPcko8qnif6BlkQ6MN4D","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
@@ -1 +1 @@
1
- <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/c78d26b1-88a3e1bacb2a03c2.js" defer=""></script><script src="/_next/static/chunks/6060-cb1ab5be7067bf7b.js" defer=""></script><script src="/_next/static/chunks/7553-08bc3d9f66695111.js" defer=""></script><script src="/_next/static/chunks/4481-7f6710c928bb0cb0.js" defer=""></script><script src="/_next/static/chunks/401-7e800aed05537126.js" defer=""></script><script src="/_next/static/chunks/3923-b4f701ada3ef0ee0.js" defer=""></script><script src="/_next/static/chunks/pages/consent/configure-4cc195e15e0c3cc8.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_buildManifest.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/consent/configure","query":{},"buildId":"j0v5qPG9TaezfK2WMkHhI","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
1
+ <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/c78d26b1-88a3e1bacb2a03c2.js" defer=""></script><script src="/_next/static/chunks/6060-cb1ab5be7067bf7b.js" defer=""></script><script src="/_next/static/chunks/7553-08bc3d9f66695111.js" defer=""></script><script src="/_next/static/chunks/4481-7f6710c928bb0cb0.js" defer=""></script><script src="/_next/static/chunks/401-7e800aed05537126.js" defer=""></script><script src="/_next/static/chunks/3923-b4f701ada3ef0ee0.js" defer=""></script><script src="/_next/static/chunks/pages/consent/configure-4cc195e15e0c3cc8.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_buildManifest.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/consent/configure","query":{},"buildId":"ycPcko8qnif6BlkQ6MN4D","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
@@ -1 +1 @@
1
- <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/2858-0b44609b6be7850b.js" defer=""></script><script src="/_next/static/chunks/2866-a73888c17a195cbe.js" defer=""></script><script src="/_next/static/chunks/3662-f6a1ddca5ee42076.js" defer=""></script><script src="/_next/static/chunks/3670-2abd9b2f17770872.js" defer=""></script><script src="/_next/static/chunks/69-00cba94689b9e740.js" defer=""></script><script src="/_next/static/chunks/6277-459e054b2702c60e.js" defer=""></script><script src="/_next/static/chunks/1817-951f58ddd5d46081.js" defer=""></script><script src="/_next/static/chunks/pages/consent/privacy-experience/%5Bid%5D-be8972c79fb39705.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_buildManifest.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/consent/privacy-experience/[id]","query":{},"buildId":"j0v5qPG9TaezfK2WMkHhI","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
1
+ <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/2858-0b44609b6be7850b.js" defer=""></script><script src="/_next/static/chunks/2866-a73888c17a195cbe.js" defer=""></script><script src="/_next/static/chunks/3662-f6a1ddca5ee42076.js" defer=""></script><script src="/_next/static/chunks/3670-2abd9b2f17770872.js" defer=""></script><script src="/_next/static/chunks/69-00cba94689b9e740.js" defer=""></script><script src="/_next/static/chunks/6277-459e054b2702c60e.js" defer=""></script><script src="/_next/static/chunks/1817-951f58ddd5d46081.js" defer=""></script><script src="/_next/static/chunks/pages/consent/privacy-experience/%5Bid%5D-be8972c79fb39705.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_buildManifest.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/consent/privacy-experience/[id]","query":{},"buildId":"ycPcko8qnif6BlkQ6MN4D","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
@@ -1 +1 @@
1
- <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/2858-0b44609b6be7850b.js" defer=""></script><script src="/_next/static/chunks/2866-a73888c17a195cbe.js" defer=""></script><script src="/_next/static/chunks/3662-f6a1ddca5ee42076.js" defer=""></script><script src="/_next/static/chunks/3670-2abd9b2f17770872.js" defer=""></script><script src="/_next/static/chunks/69-00cba94689b9e740.js" defer=""></script><script src="/_next/static/chunks/6277-459e054b2702c60e.js" defer=""></script><script src="/_next/static/chunks/1817-951f58ddd5d46081.js" defer=""></script><script src="/_next/static/chunks/pages/consent/privacy-experience/new-a0039f216fb3eb93.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_buildManifest.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/consent/privacy-experience/new","query":{},"buildId":"j0v5qPG9TaezfK2WMkHhI","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
1
+ <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/2858-0b44609b6be7850b.js" defer=""></script><script src="/_next/static/chunks/2866-a73888c17a195cbe.js" defer=""></script><script src="/_next/static/chunks/3662-f6a1ddca5ee42076.js" defer=""></script><script src="/_next/static/chunks/3670-2abd9b2f17770872.js" defer=""></script><script src="/_next/static/chunks/69-00cba94689b9e740.js" defer=""></script><script src="/_next/static/chunks/6277-459e054b2702c60e.js" defer=""></script><script src="/_next/static/chunks/1817-951f58ddd5d46081.js" defer=""></script><script src="/_next/static/chunks/pages/consent/privacy-experience/new-a0039f216fb3eb93.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_buildManifest.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/consent/privacy-experience/new","query":{},"buildId":"ycPcko8qnif6BlkQ6MN4D","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
@@ -1 +1 @@
1
- <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/c78d26b1-88a3e1bacb2a03c2.js" defer=""></script><script src="/_next/static/chunks/6060-cb1ab5be7067bf7b.js" defer=""></script><script src="/_next/static/chunks/5277-e8a036319456127f.js" defer=""></script><script src="/_next/static/chunks/7553-08bc3d9f66695111.js" defer=""></script><script src="/_next/static/chunks/4481-7f6710c928bb0cb0.js" defer=""></script><script src="/_next/static/chunks/6853-688df0b88fe65fd5.js" defer=""></script><script src="/_next/static/chunks/pages/consent/privacy-experience-ccf96207de3b74ea.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_buildManifest.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/consent/privacy-experience","query":{},"buildId":"j0v5qPG9TaezfK2WMkHhI","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
1
+ <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/c78d26b1-88a3e1bacb2a03c2.js" defer=""></script><script src="/_next/static/chunks/6060-cb1ab5be7067bf7b.js" defer=""></script><script src="/_next/static/chunks/5277-e8a036319456127f.js" defer=""></script><script src="/_next/static/chunks/7553-08bc3d9f66695111.js" defer=""></script><script src="/_next/static/chunks/4481-7f6710c928bb0cb0.js" defer=""></script><script src="/_next/static/chunks/6853-688df0b88fe65fd5.js" defer=""></script><script src="/_next/static/chunks/pages/consent/privacy-experience-ccf96207de3b74ea.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_buildManifest.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/consent/privacy-experience","query":{},"buildId":"ycPcko8qnif6BlkQ6MN4D","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
@@ -1 +1 @@
1
- <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/2858-0b44609b6be7850b.js" defer=""></script><script src="/_next/static/chunks/2866-a73888c17a195cbe.js" defer=""></script><script src="/_next/static/chunks/3662-f6a1ddca5ee42076.js" defer=""></script><script src="/_next/static/chunks/6659-b2088f525bf13c17.js" defer=""></script><script src="/_next/static/chunks/69-00cba94689b9e740.js" defer=""></script><script src="/_next/static/chunks/6277-459e054b2702c60e.js" defer=""></script><script src="/_next/static/chunks/6954-4e313b4599b8763d.js" defer=""></script><script src="/_next/static/chunks/pages/consent/privacy-notices/%5Bid%5D-b9823cc008372cee.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_buildManifest.js" defer=""></script><script src="/_next/static/j0v5qPG9TaezfK2WMkHhI/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/consent/privacy-notices/[id]","query":{},"buildId":"j0v5qPG9TaezfK2WMkHhI","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>
1
+ <!DOCTYPE html><html lang="en"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width"/><meta name="next-head-count" content="2"/><link data-next-font="" rel="preconnect" href="/" crossorigin="anonymous"/><link rel="preload" href="/_next/static/css/1fdf5c593349dbc6.css" as="style"/><link rel="stylesheet" href="/_next/static/css/1fdf5c593349dbc6.css" data-n-g=""/><noscript data-n-css=""></noscript><script defer="" nomodule="" src="/_next/static/chunks/polyfills-42372ed130431b0a.js"></script><script src="/_next/static/chunks/webpack-8457bad7859c44f0.js" defer=""></script><script src="/_next/static/chunks/framework-c92fc3344e6fd165.js" defer=""></script><script src="/_next/static/chunks/main-090643377c8254e6.js" defer=""></script><script src="/_next/static/chunks/pages/_app-33bc23b79bffe07c.js" defer=""></script><script src="/_next/static/chunks/2858-0b44609b6be7850b.js" defer=""></script><script src="/_next/static/chunks/2866-a73888c17a195cbe.js" defer=""></script><script src="/_next/static/chunks/3662-f6a1ddca5ee42076.js" defer=""></script><script src="/_next/static/chunks/6659-b2088f525bf13c17.js" defer=""></script><script src="/_next/static/chunks/69-00cba94689b9e740.js" defer=""></script><script src="/_next/static/chunks/6277-459e054b2702c60e.js" defer=""></script><script src="/_next/static/chunks/6954-4e313b4599b8763d.js" defer=""></script><script src="/_next/static/chunks/pages/consent/privacy-notices/%5Bid%5D-b9823cc008372cee.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_buildManifest.js" defer=""></script><script src="/_next/static/ycPcko8qnif6BlkQ6MN4D/_ssgManifest.js" defer=""></script><style>.data-ant-cssinjs-cache-path{content:"";}</style></head><body><div id="__next"><div style="height:100%;display:flex"></div></div><script id="__NEXT_DATA__" type="application/json">{"props":{"pageProps":{}},"page":"/consent/privacy-notices/[id]","query":{},"buildId":"ycPcko8qnif6BlkQ6MN4D","nextExport":true,"autoExport":true,"isFallback":false,"scriptLoader":[]}</script></body></html>