diff --git a/Changelog.md b/Changelog.md
index ac852abafd6257877a7c85f5fb8d5d2579fff948..d8715c301edf264ed448616e6dae6e6b1f671533 100644
--- a/Changelog.md
+++ b/Changelog.md
@@ -1,4 +1,8 @@
 # Changelog
+## [2.42] - 2025-03-13
+- Send a separate notification email for failed prefix list checks.
+- Upgrade `orchestrator-core` to 3.1.1.
+
 ## [2.41] - 2025-02-28
 - Check uniqueness of GS, GA and VC IDs against active subscriptions.
 - `migrate_l3_core_service`: Update in parameters passed to Moodi to target the destination node.
diff --git a/gso/cli/imports.py b/gso/cli/imports.py
index 6444aba8963fcd8c2364eccc0afb3ee85b40d59b..85db5b756101ab06f7aa86cd54d696586f75641d 100644
--- a/gso/cli/imports.py
+++ b/gso/cli/imports.py
@@ -12,8 +12,9 @@ import typer
 import yaml
 from orchestrator.db import db
 from orchestrator.services.processes import start_process
-from orchestrator.types import SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from pydantic import BaseModel, NonNegativeInt, ValidationError, field_validator, model_validator
+from pydantic_forms.types import UUIDstr
 from sqlalchemy.exc import SQLAlchemyError
 
 from gso.db.models import PartnerTable
diff --git a/gso/graphql_api/types.py b/gso/graphql_api/types.py
index c6fb920048f5080797fb1454a54bd01ee9f4288a..0a1a7ac89c6f26431d591074bcb5318d958b1ee6 100644
--- a/gso/graphql_api/types.py
+++ b/gso/graphql_api/types.py
@@ -1,11 +1,11 @@
 """Map some Orchestrator types to scalars."""
 
 from ipaddress import IPv4Network, IPv6Network
-from typing import Any, NewType
+from typing import NewType
 
 import strawberry
 from orchestrator.graphql.types import serialize_to_string
-from strawberry.custom_scalar import ScalarDefinition, ScalarWrapper
+from strawberry.types.scalar import ScalarDefinition, ScalarWrapper
 
 IPv4NetworkType = strawberry.scalar(
     NewType("IPv4NetworkType", str),
@@ -21,7 +21,7 @@ IPv6NetworkType = strawberry.scalar(
     parse_value=lambda v: v,
 )
 
-GSO_SCALAR_OVERRIDES: dict[object, Any | ScalarWrapper | ScalarDefinition] = {
-    IPv4Network: IPv4NetworkType,
-    IPv6Network: IPv6NetworkType,
+GSO_SCALAR_OVERRIDES: dict[object, type | ScalarWrapper | ScalarDefinition] = {
+    IPv4Network: IPv4NetworkType,  # type: ignore[dict-item]
+    IPv6Network: IPv6NetworkType,  # type: ignore[dict-item]
 }
diff --git a/gso/migrations/versions/2025-02-28_931c0d9d81d6_validate_prefix_list.py b/gso/migrations/versions/2025-02-28_931c0d9d81d6_validate_prefix_list.py
new file mode 100644
index 0000000000000000000000000000000000000000..e931173b9a2f90b485dbf9d23da1087d3912cf4a
--- /dev/null
+++ b/gso/migrations/versions/2025-02-28_931c0d9d81d6_validate_prefix_list.py
@@ -0,0 +1,45 @@
+"""validate-prefix-list.
+
+Revision ID: 931c0d9d81d6
+Revises: efebcde91f2f
+Create Date: 2025-02-28 14:13:57.181314
+
+"""
+import sqlalchemy as sa
+from alembic import op
+
+# revision identifiers, used by Alembic.
+revision = '931c0d9d81d6'
+down_revision = 'efebcde91f2f'
+branch_labels = None
+depends_on = None
+
+
+from orchestrator.migrations.helpers import create_workflow, delete_workflow
+
+new_workflows = [
+    {
+        "name": "validate_prefix_list",
+        "target": "SYSTEM",
+        "description": "Validate Prefix-List",
+        "product_type": "L3CoreService"
+    },
+    {
+        "name": "deploy_prefix_list",
+        "target": "SYSTEM",
+        "description": "Deploy Prefix-List",
+        "product_type": "L3CoreService"
+    }
+]
+
+
+def upgrade() -> None:
+    conn = op.get_bind()
+    for workflow in new_workflows:
+        create_workflow(conn, workflow)
+
+
+def downgrade() -> None:
+    conn = op.get_bind()
+    for workflow in new_workflows:
+        delete_workflow(conn, workflow["name"])
diff --git a/gso/migrations/versions/2025-03-11_b96b0ecf6906_add_orchestrator_3_1_1_migrations.py b/gso/migrations/versions/2025-03-11_b96b0ecf6906_add_orchestrator_3_1_1_migrations.py
new file mode 100644
index 0000000000000000000000000000000000000000..df29a0319d2c2507b7c6f628147c2ab4540f9bd1
--- /dev/null
+++ b/gso/migrations/versions/2025-03-11_b96b0ecf6906_add_orchestrator_3_1_1_migrations.py
@@ -0,0 +1,20 @@
+"""Add upstream migrations from orchestrator-core 3.1.1.
+
+Revision ID: b96b0ecf6906
+Revises: 844aa61c09ce
+Create Date: 2024-10-10 10:00:08.539591
+
+"""
+# revision identifiers, used by Alembic.
+revision = 'b96b0ecf6906'
+down_revision = '931c0d9d81d6'
+branch_labels = None
+depends_on = 'bac6be6f2b4f'
+
+
+def upgrade() -> None:
+    pass
+
+
+def downgrade() -> None:
+    pass
diff --git a/gso/products/product_blocks/edge_port.py b/gso/products/product_blocks/edge_port.py
index 1603f5a39776fbc0ce10ed6ed20d4c5a3a49514f..7fa1b5c706d2e2ecc5a106f6f42e158112c7c06d 100644
--- a/gso/products/product_blocks/edge_port.py
+++ b/gso/products/product_blocks/edge_port.py
@@ -5,7 +5,8 @@ different technological domain, still managed by GÉANT. In other words, an Edge
 """
 
 from orchestrator.domain.base import ProductBlockModel
-from orchestrator.types import SubscriptionLifecycle, strEnum
+from orchestrator.types import SubscriptionLifecycle
+from pydantic_forms.types import strEnum
 
 from gso.products.product_blocks.router import RouterBlock, RouterBlockInactive, RouterBlockProvisioning
 from gso.utils.types.interfaces import LAGMemberList, PhysicalPortCapacity
diff --git a/gso/products/product_blocks/iptrunk.py b/gso/products/product_blocks/iptrunk.py
index 1f67f312a84e16346277ed0bdb84f4e4674628ce..698800d9c7583b0ce9cb55cb5cc747e2fe76ef29 100644
--- a/gso/products/product_blocks/iptrunk.py
+++ b/gso/products/product_blocks/iptrunk.py
@@ -5,8 +5,9 @@ from typing import Annotated
 
 from annotated_types import Len
 from orchestrator.domain.base import ProductBlockModel, T
-from orchestrator.types import SubscriptionLifecycle, strEnum
+from orchestrator.types import SubscriptionLifecycle
 from pydantic import AfterValidator
+from pydantic_forms.types import strEnum
 from pydantic_forms.validators import validate_unique_list
 from typing_extensions import Doc
 
diff --git a/gso/products/product_blocks/router.py b/gso/products/product_blocks/router.py
index de428138a9e305e67cbb0bfbfc705866b5d17135..b45082225bb77700ee079c9dc05cd04557cb2ce6 100644
--- a/gso/products/product_blocks/router.py
+++ b/gso/products/product_blocks/router.py
@@ -1,7 +1,8 @@
 """Product block for `Router` products."""
 
 from orchestrator.domain.base import ProductBlockModel
-from orchestrator.types import SubscriptionLifecycle, strEnum
+from orchestrator.types import SubscriptionLifecycle
+from pydantic_forms.types import strEnum
 
 from gso.products.product_blocks.site import (
     SiteBlock,
diff --git a/gso/products/product_blocks/site.py b/gso/products/product_blocks/site.py
index 22cc4940094ca50d494bc90507466a57b125e299..52db8df31321458489c254075cb2e509a9ed9b4e 100644
--- a/gso/products/product_blocks/site.py
+++ b/gso/products/product_blocks/site.py
@@ -1,7 +1,8 @@
 """The product block that describes a site subscription."""
 
 from orchestrator.domain.base import ProductBlockModel
-from orchestrator.types import SubscriptionLifecycle, strEnum
+from orchestrator.types import SubscriptionLifecycle
+from pydantic_forms.types import strEnum
 
 from gso.utils.types.coordinates import LatitudeCoordinate, LongitudeCoordinate
 from gso.utils.types.ip_address import IPAddress
diff --git a/gso/services/lso_client.py b/gso/services/lso_client.py
index e6268e5c4859d77af7ef14ea91bc86224dc7c27e..2318cffd7396e51c620fa55087faea21e7043187 100644
--- a/gso/services/lso_client.py
+++ b/gso/services/lso_client.py
@@ -11,11 +11,10 @@ import requests
 from orchestrator import step
 from orchestrator.config.assignee import Assignee
 from orchestrator.forms import SubmitFormPage
-from orchestrator.types import State
 from orchestrator.utils.errors import ProcessFailureError
 from orchestrator.workflow import Step, StepList, begin, callback_step, conditional, inputstep
 from pydantic import ConfigDict
-from pydantic_forms.types import FormGenerator
+from pydantic_forms.types import FormGenerator, State
 from pydantic_forms.validators import Label, LongText, ReadOnlyField
 from unidecode import unidecode
 
diff --git a/gso/services/netbox_client.py b/gso/services/netbox_client.py
index 2928263c920da52e0993fbb43ddc4dbfa2d20283..7ff8e29c2326dcfbbf60143b0800e2c952282c0a 100644
--- a/gso/services/netbox_client.py
+++ b/gso/services/netbox_client.py
@@ -5,7 +5,7 @@ from uuid import UUID
 
 import pydantic
 import pynetbox
-from orchestrator.types import UUIDstr
+from pydantic_forms.types import UUIDstr
 from pynetbox.models.dcim import Devices, DeviceTypes, Interfaces
 
 from gso.products.product_types.router import Router
diff --git a/gso/services/processes.py b/gso/services/processes.py
index c33f17a285b57513ab7dd7bfe5cf1925a80bb87e..5d6f5105ddc27271e6e87c55ca58362ff57368e4 100644
--- a/gso/services/processes.py
+++ b/gso/services/processes.py
@@ -5,9 +5,15 @@ or inconsistent when not careful. These methods are related to operations regard
 """
 
 from orchestrator.db import ProcessTable, WorkflowTable, db
-from orchestrator.types import UUIDstr
 from orchestrator.workflow import ProcessStatus
+from pydantic_forms.types import UUIDstr
 from sqlalchemy import ScalarResult, or_, select
+from sqlalchemy.orm import Query
+
+
+def get_processes_by_workflow_name(workflow_name: str) -> Query:
+    """Get all processes for a given workflow name."""
+    return ProcessTable.query.join(WorkflowTable).filter(WorkflowTable.name == workflow_name)
 
 
 def count_incomplete_validate_products() -> int:
@@ -16,19 +22,29 @@ def count_incomplete_validate_products() -> int:
     Returns:
         The count of incomplete 'validate_geant_products' processes.
     """
-    return ProcessTable.query.filter(
-        ProcessTable.workflow_name == "validate_geant_products",
-        ProcessTable.last_status != ProcessStatus.COMPLETED.value,
-    ).count()
+    return (
+        get_processes_by_workflow_name("validate_geant_products")
+        .filter(ProcessTable.last_status != ProcessStatus.COMPLETED)
+        .count()
+    )
 
 
 def get_failed_tasks() -> list[ProcessTable]:
     """Get all tasks that have failed."""
     return ProcessTable.query.filter(
-        ProcessTable.is_task.is_(True), ProcessTable.last_status == ProcessStatus.FAILED.value
+        ProcessTable.is_task.is_(True), ProcessTable.last_status == ProcessStatus.FAILED
     ).all()
 
 
+def get_failed_tasks_by_workflow_name(workflow_name: str) -> list[ProcessTable]:
+    """Get all tasks that have failed for a specific workflow name."""
+    return (
+        get_processes_by_workflow_name(workflow_name)
+        .filter(ProcessTable.is_task.is_(True), ProcessTable.last_status == ProcessStatus.FAILED)
+        .all()
+    )
+
+
 def get_all_cleanup_tasks() -> list[WorkflowTable]:
     """Get a list of all cleanup tasks that run on a schedule."""
     return WorkflowTable.query.filter(
diff --git a/gso/services/sharepoint.py b/gso/services/sharepoint.py
index e846f78c6a92228d75a4a5e2325753ce6f8268e1..567d946c599b976b312b06421d0e0d1292e8dc0a 100644
--- a/gso/services/sharepoint.py
+++ b/gso/services/sharepoint.py
@@ -3,7 +3,7 @@
 import asyncio
 
 from azure.identity.aio import CertificateCredential
-from msgraph import GraphServiceClient
+from msgraph import GraphServiceClient  # type: ignore[attr-defined]
 from msgraph.generated.models.field_value_set import FieldValueSet
 from msgraph.generated.models.list_item import ListItem
 from msgraph.generated.models.list_item_collection_response import ListItemCollectionResponse
@@ -77,6 +77,6 @@ class SharePointClient:
             )
 
             #  Strip the last part of the URL, since we want the link to the list, not the list item.
-            return new_item.web_url.rsplit("/", 1)[0]
+            return new_item.web_url.rsplit("/", 1)[0]  # type: ignore[union-attr]
 
         return asyncio.run(_new_list_item())
diff --git a/gso/services/subscriptions.py b/gso/services/subscriptions.py
index 543fae4a1f24def0afbce8b2a5f5f7607dc56ca7..9f3623b723969e5d7caef5488db951b9e4af0c4a 100644
--- a/gso/services/subscriptions.py
+++ b/gso/services/subscriptions.py
@@ -18,7 +18,8 @@ from orchestrator.db import (
 )
 from orchestrator.domain import SubscriptionModel
 from orchestrator.services.subscriptions import query_in_use_by_subscriptions
-from orchestrator.types import SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
+from pydantic_forms.types import UUIDstr
 from sqlalchemy import and_, text
 from sqlalchemy.exc import SQLAlchemyError
 
diff --git a/gso/settings.py b/gso/settings.py
index e7326dbbcb27b6c0fcef7a5dc15c9b5bbc482fb3..fbd4286411019fe56be9dedfcb615a86dcbbfc81 100644
--- a/gso/settings.py
+++ b/gso/settings.py
@@ -10,9 +10,8 @@ import logging
 import os
 from pathlib import Path
 
-from orchestrator.types import UUIDstr
 from pydantic import EmailStr
-from pydantic_forms.types import strEnum
+from pydantic_forms.types import UUIDstr, strEnum
 from pydantic_settings import BaseSettings
 
 from gso.utils.types.ip_address import IPv4Netmask, IPv6Netmask, PortNumber
diff --git a/gso/translations/en-GB.json b/gso/translations/en-GB.json
index c5d17a43401cfe1b9e454990189a885b0c7d0db1..d59dc7aa58cd0818de9466119d4ca4aeaecb8d34 100644
--- a/gso/translations/en-GB.json
+++ b/gso/translations/en-GB.json
@@ -84,6 +84,7 @@
         "create_imported_l3_core_service": "NOT FOR HUMANS -- Import existing L3 Core Service",
         "create_imported_switch": "NOT FOR HUMANS -- Import existing Switch",
         "create_imported_lan_switch_interconnect": "NOT FOR HUMANS -- Import existing LAN Switch Interconnect",
+        "deploy_prefix_list": "Deploy Prefix-List",
         "import_site": "NOT FOR HUMANS -- Finalize import into a Site product",
         "import_router": "NOT FOR HUMANS -- Finalize import into a Router product",
         "import_iptrunk": "NOT FOR HUMANS -- Finalize import into an IP trunk product",
@@ -100,6 +101,7 @@
         "validate_edge_port": "Validate Edge Port",
         "validate_lan_switch_interconnect": "Validate LAN Switch Interconnect",
         "validate_l3_core_service": "Validate L3 Core Service",
+        "validate_prefix_list": "Validate Prefix-List",
         "task_validate_geant_products": "Validation task for GEANT products",
         "task_send_email_notifications": "Send email notifications for failed tasks",
         "task_create_partners": "Create partner task",
diff --git a/gso/utils/types/netbox_router.py b/gso/utils/types/netbox_router.py
index c184c09bebba0583afd5628b55587d9d05f4121d..a0f50a6987b8a57973d206423a634b50dd1ac0ba 100644
--- a/gso/utils/types/netbox_router.py
+++ b/gso/utils/types/netbox_router.py
@@ -2,8 +2,8 @@
 
 from typing import Annotated, TypeVar
 
-from orchestrator.types import UUIDstr
 from pydantic import AfterValidator
+from pydantic_forms.types import UUIDstr
 
 from gso.products.product_types.router import Router
 from gso.services.netbox_client import NetboxClient
diff --git a/gso/utils/workflow_steps.py b/gso/utils/workflow_steps.py
index 754af0819ae239fa1064c7320dace6572fd62f32..6c90f051cb19b312a1706db411a6084b5be1b5fe 100644
--- a/gso/utils/workflow_steps.py
+++ b/gso/utils/workflow_steps.py
@@ -6,12 +6,11 @@ from typing import Any
 from orchestrator import inputstep, step
 from orchestrator.config.assignee import Assignee
 from orchestrator.forms import SubmitFormPage
-from orchestrator.types import State, UUIDstr
 from orchestrator.utils.errors import ProcessFailureError
 from orchestrator.utils.json import json_dumps
 from orchestrator.workflow import StepList, conditional
 from pydantic import ConfigDict
-from pydantic_forms.types import FormGenerator
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 from pydantic_forms.validators import Label
 
 from gso.products.product_blocks.router import RouterRole
diff --git a/gso/workflows/__init__.py b/gso/workflows/__init__.py
index 74f67c01f108350adb5ac7c8ce3667d762c21f66..0e38f2262c75ba89160208432065554788f17c4d 100644
--- a/gso/workflows/__init__.py
+++ b/gso/workflows/__init__.py
@@ -126,6 +126,8 @@ LazyWorkflowInstance("gso.workflows.l3_core_service.import_l3_core_service", "im
 LazyWorkflowInstance("gso.workflows.l3_core_service.migrate_l3_core_service", "migrate_l3_core_service")
 LazyWorkflowInstance("gso.workflows.l3_core_service.validate_l3_core_service", "validate_l3_core_service")
 LazyWorkflowInstance("gso.workflows.l3_core_service.terminate_l3_core_service", "terminate_l3_core_service")
+LazyWorkflowInstance("gso.workflows.l3_core_service.validate_prefix_list", "validate_prefix_list")
+LazyWorkflowInstance("gso.workflows.l3_core_service.deploy_prefix_list", "deploy_prefix_list")
 
 # Layer 2 Circuit workflows
 LazyWorkflowInstance("gso.workflows.l2_circuit.create_layer_2_circuit", "create_layer_2_circuit")
diff --git a/gso/workflows/edge_port/create_edge_port.py b/gso/workflows/edge_port/create_edge_port.py
index 7526ad69dd5de092769108370b328d01f56fd52c..6686e2669472ae68ee7965e726c515ec8d013307 100644
--- a/gso/workflows/edge_port/create_edge_port.py
+++ b/gso/workflows/edge_port/create_edge_port.py
@@ -7,12 +7,13 @@ from annotated_types import Len
 from orchestrator import step, workflow
 from orchestrator.forms import FormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.utils.errors import ProcessFailureError
 from orchestrator.workflow import StepList, begin, done
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription
 from orchestrator.workflows.utils import wrap_create_initial_input_form
 from pydantic import AfterValidator, ConfigDict, model_validator
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 from pydantic_forms.validators import validate_unique_list
 from pynetbox.models.dcim import Interfaces
 
diff --git a/gso/workflows/edge_port/create_imported_edge_port.py b/gso/workflows/edge_port/create_imported_edge_port.py
index ef5d2d033203e082c67a67f88eb511043d4e2a51..6a0067275fcd032ea936ca57580dfe2bdc482ffe 100644
--- a/gso/workflows/edge_port/create_imported_edge_port.py
+++ b/gso/workflows/edge_port/create_imported_edge_port.py
@@ -6,11 +6,11 @@ from uuid import uuid4
 from orchestrator import workflow
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done, step
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription
 from pydantic import AfterValidator, ConfigDict
-from pydantic_forms.types import UUIDstr
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 from pydantic_forms.validators import validate_unique_list
 
 from gso.products import ProductName
diff --git a/gso/workflows/edge_port/import_edge_port.py b/gso/workflows/edge_port/import_edge_port.py
index 3193489a6606eaff8f553e4358f5621352bca613..0d5bd41bcfd66df61029ea0ba44acab195e3860a 100644
--- a/gso/workflows/edge_port/import_edge_port.py
+++ b/gso/workflows/edge_port/import_edge_port.py
@@ -1,10 +1,10 @@
 """A modification workflow for migrating an ImportedEdgePort to an EdgePort subscription."""
 
 from orchestrator.targets import Target
-from orchestrator.types import State, UUIDstr
 from orchestrator.workflow import StepList, done, init, step, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import State, UUIDstr
 
 from gso.products import ProductName
 from gso.products.product_types.edge_port import EdgePort, ImportedEdgePort
diff --git a/gso/workflows/edge_port/migrate_edge_port.py b/gso/workflows/edge_port/migrate_edge_port.py
index 4602d72dd4dff19598d9932034b25f535d0f7271..afd2d6d0f46e9dd6a81f9fe1e290af0ff3b217d0 100644
--- a/gso/workflows/edge_port/migrate_edge_port.py
+++ b/gso/workflows/edge_port/migrate_edge_port.py
@@ -10,13 +10,13 @@ from orchestrator import step, workflow
 from orchestrator.config.assignee import Assignee
 from orchestrator.forms import FormPage, SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, UUIDstr
 from orchestrator.utils.errors import ProcessFailureError
 from orchestrator.utils.json import json_dumps
 from orchestrator.workflow import StepList, begin, done, inputstep
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
 from pydantic import AfterValidator, ConfigDict, Field
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 from pydantic_forms.validators import Divider, Label, ReadOnlyField, validate_unique_list
 from pynetbox.models.dcim import Interfaces
 
diff --git a/gso/workflows/edge_port/terminate_edge_port.py b/gso/workflows/edge_port/terminate_edge_port.py
index 608294b113f842eb8716571c13e1b3d08a37e0ff..8776347b556adffa5ec28f91dd4af240071eda70 100644
--- a/gso/workflows/edge_port/terminate_edge_port.py
+++ b/gso/workflows/edge_port/terminate_edge_port.py
@@ -2,7 +2,7 @@
 
 from typing import Any
 
-from orchestrator import workflow
+from orchestrator import conditional, workflow
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
 from orchestrator.types import SubscriptionLifecycle
@@ -14,6 +14,7 @@ from pydantic_forms.types import FormGenerator, UUIDstr
 from gso.products.product_types.edge_port import EdgePort
 from gso.services.lso_client import LSOState, lso_interaction
 from gso.services.netbox_client import NetboxClient
+from gso.utils.shared_enums import Vendor
 from gso.utils.types.tt_number import TTNumber
 
 
@@ -65,7 +66,7 @@ def remove_edge_port_real(subscription: dict[str, Any], tt_number: str, process_
 
 @step("Netbox Clean Up")
 def netbox_clean_up(subscription: EdgePort) -> None:
-    """Update Netbox to remove the edge port LAG interface and all the LAG members."""
+    """Update Netbox to remove the edge port LAG interface and all the LAG members. This is only for Nokia routers."""
     nbclient = NetboxClient()
 
     for member in subscription.edge_port.edge_port_ae_members:
@@ -81,13 +82,15 @@ def netbox_clean_up(subscription: EdgePort) -> None:
 )
 def terminate_edge_port() -> StepList:
     """Terminate a new edge port in the network."""
+    router_is_nokia = conditional(lambda state: state["subscription"]["edge_port"]["node"]["vendor"] == Vendor.NOKIA)
+
     return (
         begin
         >> store_process_subscription(Target.TERMINATE)
         >> unsync
         >> lso_interaction(remove_edge_port_dry)
         >> lso_interaction(remove_edge_port_real)
-        >> netbox_clean_up
+        >> router_is_nokia(netbox_clean_up)
         >> set_status(SubscriptionLifecycle.TERMINATED)
         >> resync
         >> done
diff --git a/gso/workflows/edge_port/validate_edge_port.py b/gso/workflows/edge_port/validate_edge_port.py
index 6932b2be338c076e6a3299cb98a727c0578cb990..1bbf60e3dd3b7368adf1a085aeaf333ee269fee9 100644
--- a/gso/workflows/edge_port/validate_edge_port.py
+++ b/gso/workflows/edge_port/validate_edge_port.py
@@ -3,11 +3,11 @@
 from typing import Any
 
 from orchestrator.targets import Target
-from orchestrator.types import State, UUIDstr
 from orchestrator.utils.errors import ProcessFailureError
 from orchestrator.workflow import StepList, begin, done, step, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import State, UUIDstr
 
 from gso.products.product_types.edge_port import EdgePort
 from gso.services.lso_client import LSOState, anonymous_lso_interaction
diff --git a/gso/workflows/iptrunk/activate_iptrunk.py b/gso/workflows/iptrunk/activate_iptrunk.py
index af37f2f24fa81545cbd9e546b3605703dfe0b7c7..eaca69db1297f5e7c5c0ea9111516c0cc52a701f 100644
--- a/gso/workflows/iptrunk/activate_iptrunk.py
+++ b/gso/workflows/iptrunk/activate_iptrunk.py
@@ -8,10 +8,11 @@ from orchestrator.config.assignee import Assignee
 from orchestrator.forms import SubmitFormPage
 from orchestrator.forms.validators import Label
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done, inputstep, workflow
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import FormGenerator, UUIDstr
 
 from gso.products.product_types.iptrunk import Iptrunk
 
diff --git a/gso/workflows/iptrunk/create_imported_iptrunk.py b/gso/workflows/iptrunk/create_imported_iptrunk.py
index db1bdb6eb452a836eefa20216e5167e7c36baf0b..5e00dd29c984d2f7e58e687f5513804af0e7103d 100644
--- a/gso/workflows/iptrunk/create_imported_iptrunk.py
+++ b/gso/workflows/iptrunk/create_imported_iptrunk.py
@@ -7,10 +7,11 @@ from uuid import uuid4
 from orchestrator import workflow
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done, step
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription
 from pydantic import AfterValidator, ConfigDict
+from pydantic_forms.types import FormGenerator, State
 from pydantic_forms.validators import validate_unique_list
 
 from gso.products import ProductName
diff --git a/gso/workflows/iptrunk/create_iptrunk.py b/gso/workflows/iptrunk/create_iptrunk.py
index c42ec7024d86d9b85305b7d5383a0e8a5bc97704..b50b50cbb6dcf4a4aea7b96872c81d2403a1e4bf 100644
--- a/gso/workflows/iptrunk/create_iptrunk.py
+++ b/gso/workflows/iptrunk/create_iptrunk.py
@@ -34,7 +34,7 @@ from annotated_types import Len
 from orchestrator.forms import FormPage
 from orchestrator.forms.validators import Choice, Label
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.utils.errors import ProcessFailureError
 from orchestrator.utils.json import json_dumps
 from orchestrator.workflow import StepList, begin, conditional, done, step, step_group, workflow
@@ -42,6 +42,7 @@ from orchestrator.workflows.steps import resync, set_status, store_process_subsc
 from orchestrator.workflows.utils import wrap_create_initial_input_form
 from ping3 import ping
 from pydantic import ConfigDict
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 from pydantic_forms.validators import ReadOnlyField
 from pynetbox.models.dcim import Interfaces
 
diff --git a/gso/workflows/iptrunk/deploy_twamp.py b/gso/workflows/iptrunk/deploy_twamp.py
index 93c476ec4c38a5f930f2e75731bcdbc5c9d2bbf0..323963e7c3750e8e3d523745d41f4f29ceb84e36 100644
--- a/gso/workflows/iptrunk/deploy_twamp.py
+++ b/gso/workflows/iptrunk/deploy_twamp.py
@@ -9,11 +9,11 @@ import json
 from orchestrator.forms import SubmitFormPage
 from orchestrator.forms.validators import Label
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, UUIDstr
 from orchestrator.utils.json import json_dumps
 from orchestrator.workflow import StepList, begin, done, step, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import FormGenerator, UUIDstr
 
 from gso.products.product_types.iptrunk import Iptrunk
 from gso.services.lso_client import LSOState, lso_interaction
diff --git a/gso/workflows/iptrunk/import_iptrunk.py b/gso/workflows/iptrunk/import_iptrunk.py
index 36dce40de9daa4167b58f3e97458523a507b8203..05fff8c2dc2cc430ed205e1e9ce6cf38edb4a40d 100644
--- a/gso/workflows/iptrunk/import_iptrunk.py
+++ b/gso/workflows/iptrunk/import_iptrunk.py
@@ -1,10 +1,10 @@
 """A modification workflow for migrating an ImportedIptrunk to an Iptrunk subscription."""
 
 from orchestrator.targets import Target
-from orchestrator.types import State, UUIDstr
 from orchestrator.workflow import StepList, done, init, step, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import State, UUIDstr
 
 from gso.products import ProductName
 from gso.products.product_types.iptrunk import ImportedIptrunk, Iptrunk
diff --git a/gso/workflows/iptrunk/migrate_iptrunk.py b/gso/workflows/iptrunk/migrate_iptrunk.py
index 60602b8e6b9034c2289948186493e8ba499c32fa..24b1fdb0a89d8f316fa891734d87df3075663238 100644
--- a/gso/workflows/iptrunk/migrate_iptrunk.py
+++ b/gso/workflows/iptrunk/migrate_iptrunk.py
@@ -17,12 +17,12 @@ from orchestrator.config.assignee import Assignee
 from orchestrator.forms import FormPage, SubmitFormPage
 from orchestrator.forms.validators import Choice, Label
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, UUIDstr
 from orchestrator.utils.json import json_dumps
 from orchestrator.workflow import StepList, begin, conditional, done, inputstep
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
 from pydantic import ConfigDict
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 from pydantic_forms.validators import ReadOnlyField
 from pynetbox.models.dcim import Interfaces
 
diff --git a/gso/workflows/iptrunk/modify_isis_metric.py b/gso/workflows/iptrunk/modify_isis_metric.py
index e144a147a68a4f8f6f5e61b011af132d9fa67c3b..03c73c15c28104072b575b06122dc04dbe8c5182 100644
--- a/gso/workflows/iptrunk/modify_isis_metric.py
+++ b/gso/workflows/iptrunk/modify_isis_metric.py
@@ -8,11 +8,11 @@ import json
 
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, UUIDstr
 from orchestrator.utils.json import json_dumps
 from orchestrator.workflow import StepList, begin, done, step, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 
 from gso.products.product_types.iptrunk import Iptrunk
 from gso.services.lso_client import LSOState, lso_interaction
diff --git a/gso/workflows/iptrunk/modify_trunk_interface.py b/gso/workflows/iptrunk/modify_trunk_interface.py
index fd533613d911a9e56b8566c4a0f5de876cbc459c..46de31d9940e1bb542fa23d4f56346aba895a111 100644
--- a/gso/workflows/iptrunk/modify_trunk_interface.py
+++ b/gso/workflows/iptrunk/modify_trunk_interface.py
@@ -14,12 +14,12 @@ from uuid import UUID, uuid4
 from annotated_types import Len
 from orchestrator.forms import FormPage, SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, UUIDstr
 from orchestrator.utils.json import json_dumps
 from orchestrator.workflow import StepList, begin, conditional, done, step, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
 from pydantic import AfterValidator, ConfigDict, Field
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 from pydantic_forms.validators import Label, ReadOnlyField
 
 from gso.products.product_blocks.iptrunk import (
diff --git a/gso/workflows/iptrunk/terminate_iptrunk.py b/gso/workflows/iptrunk/terminate_iptrunk.py
index 2d0682a1c3006eeaa27cd9c38ed400e30b06b95d..47fceae0695eae68565d619f2894c65ce29d32f7 100644
--- a/gso/workflows/iptrunk/terminate_iptrunk.py
+++ b/gso/workflows/iptrunk/terminate_iptrunk.py
@@ -17,7 +17,7 @@ import json
 from orchestrator.forms import SubmitFormPage
 from orchestrator.forms.validators import Label
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.utils.json import json_dumps
 from orchestrator.workflow import StepList, begin, conditional, done, step, workflow
 from orchestrator.workflows.steps import (
@@ -27,6 +27,7 @@ from orchestrator.workflows.steps import (
     unsync,
 )
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 
 from gso.products.product_blocks.iptrunk import IptrunkSideBlock
 from gso.products.product_types.iptrunk import Iptrunk
diff --git a/gso/workflows/l2_circuit/create_imported_layer_2_circuit.py b/gso/workflows/l2_circuit/create_imported_layer_2_circuit.py
index 6dbd052ebc9d9d9494e42152d4b89a1d0a85cf26..8b835edc12ea4c87ffb22aad7308fdf625f8ba21 100644
--- a/gso/workflows/l2_circuit/create_imported_layer_2_circuit.py
+++ b/gso/workflows/l2_circuit/create_imported_layer_2_circuit.py
@@ -6,11 +6,11 @@ from uuid import uuid4
 from orchestrator import step, workflow
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription
 from pydantic import BaseModel, ConfigDict, model_validator
-from pydantic_forms.types import UUIDstr
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 
 from gso.products import ProductName
 from gso.products.product_blocks.layer_2_circuit import Layer2CircuitSideBlockInactive, Layer2CircuitType
diff --git a/gso/workflows/l2_circuit/create_layer_2_circuit.py b/gso/workflows/l2_circuit/create_layer_2_circuit.py
index 20cc4c866199dae6bc50b418cf61e78d18597d1b..6007e74cda516795f958310485df8fd9782f81a0 100644
--- a/gso/workflows/l2_circuit/create_layer_2_circuit.py
+++ b/gso/workflows/l2_circuit/create_layer_2_circuit.py
@@ -52,11 +52,11 @@ def initial_input_generator(product_name: str) -> FormGenerator:
 
     def _vlan_range_field(*, is_vlan: bool) -> VLAN_ID:
         """Return the appropriate field type based on whether the circuit is VLAN."""
-        return VLAN_ID if is_vlan else ReadOnlyField(None, default_type=int)
+        return VLAN_ID if is_vlan else ReadOnlyField(None, default_type=int)  # type: ignore[return-value]
 
     def _policer_field(*, policer_enabled: bool) -> BandwidthString:
         """Return the appropriate field type based on whether the policer is enabled."""
-        return BandwidthString if policer_enabled else ReadOnlyField(None, default_type=str)
+        return BandwidthString if policer_enabled else ReadOnlyField(None, default_type=str)  # type: ignore[return-value]
 
     class Layer2CircuitServiceSidesPage(SubmitFormPage):
         model_config = ConfigDict(title=f"{product_name} - Configure Edge Ports")
diff --git a/gso/workflows/l2_circuit/import_layer_2_circuit.py b/gso/workflows/l2_circuit/import_layer_2_circuit.py
index 01224e86cbdb614eb879dfc2622fdbfb2804d19b..35ed7755b47b915cb98ad1f0552f58535fb3b45c 100644
--- a/gso/workflows/l2_circuit/import_layer_2_circuit.py
+++ b/gso/workflows/l2_circuit/import_layer_2_circuit.py
@@ -1,11 +1,11 @@
 """A modification workflow for migrating an ImportedLayer2Circuit to an Layer2Circuit subscription."""
 
 from orchestrator.targets import Target
-from orchestrator.types import State, UUIDstr
 from orchestrator.utils.errors import ProcessFailureError
 from orchestrator.workflow import StepList, done, init, step, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import State, UUIDstr
 
 from gso.products import ProductName
 from gso.products.product_types.layer_2_circuit import ImportedLayer2Circuit, Layer2Circuit, Layer2CircuitServiceType
diff --git a/gso/workflows/l2_circuit/modify_layer_2_circuit.py b/gso/workflows/l2_circuit/modify_layer_2_circuit.py
index 6d7b15ff3a6d72f9e1b19e18a4f75e44c051193b..bd75b14fcf12f1e8dbb993d4e999383c9ab00f04 100644
--- a/gso/workflows/l2_circuit/modify_layer_2_circuit.py
+++ b/gso/workflows/l2_circuit/modify_layer_2_circuit.py
@@ -3,11 +3,11 @@
 from orchestrator import begin, done, workflow
 from orchestrator.forms import FormPage, SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, UUIDstr
 from orchestrator.workflow import StepList, step
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
 from pydantic import ConfigDict, Field
+from pydantic_forms.types import FormGenerator, UUIDstr
 from pydantic_forms.validators import Divider, Label, ReadOnlyField
 
 from gso.products.product_blocks.layer_2_circuit import Layer2CircuitType
diff --git a/gso/workflows/l2_circuit/terminate_layer_2_circuit.py b/gso/workflows/l2_circuit/terminate_layer_2_circuit.py
index f985c69cc76f83e9263baaec327d7980b1435cd9..e8773a678ea5ce19c0dddef11e19d036f622460e 100644
--- a/gso/workflows/l2_circuit/terminate_layer_2_circuit.py
+++ b/gso/workflows/l2_circuit/terminate_layer_2_circuit.py
@@ -3,11 +3,11 @@
 from orchestrator import begin, workflow
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, done
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
-from pydantic_forms.types import FormGenerator
+from pydantic_forms.types import FormGenerator, UUIDstr
 
 from gso.products.product_types.layer_2_circuit import Layer2Circuit
 from gso.utils.types.tt_number import TTNumber
diff --git a/gso/workflows/l3_core_service/create_imported_l3_core_service.py b/gso/workflows/l3_core_service/create_imported_l3_core_service.py
index ebb73fb95687fbd6b31f59861c8f2bc1e27bba6f..70753dd08b427c3fc0930ada60a64713a636e4b8 100644
--- a/gso/workflows/l3_core_service/create_imported_l3_core_service.py
+++ b/gso/workflows/l3_core_service/create_imported_l3_core_service.py
@@ -5,12 +5,12 @@ from uuid import uuid4
 from orchestrator import workflow
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, SubscriptionLifecycle
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.utils.errors import ProcessFailureError
 from orchestrator.workflow import StepList, begin, done, step
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription
 from pydantic import BaseModel, NonNegativeInt
-from pydantic_forms.types import UUIDstr
+from pydantic_forms.types import FormGenerator, UUIDstr
 
 from gso.products import ProductName
 from gso.products.product_blocks.bgp_session import BGPSession, IPFamily, IPTypes
diff --git a/gso/workflows/l3_core_service/create_l3_core_service.py b/gso/workflows/l3_core_service/create_l3_core_service.py
index 3069bdacec12f1a035238a03eb9e17a0e6b4f7fd..ab3114c25a5adaea9fe305a616bb32caeabcf8db 100644
--- a/gso/workflows/l3_core_service/create_l3_core_service.py
+++ b/gso/workflows/l3_core_service/create_l3_core_service.py
@@ -6,11 +6,12 @@ from uuid import uuid4
 from orchestrator.forms import FormPage, SubmitFormPage
 from orchestrator.forms.validators import Label
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done, step, workflow
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription
 from orchestrator.workflows.utils import wrap_create_initial_input_form
 from pydantic import BaseModel, ConfigDict, Field, NonNegativeInt, computed_field, model_validator
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 from pydantic_forms.validators import Divider
 
 from gso.products.product_blocks.bgp_session import BGPSession, IPFamily, IPTypes
@@ -78,12 +79,12 @@ def initial_input_form_generator(product_name: str) -> FormGenerator:
         add_v4_multicast: bool = Field(default=False, exclude=True)
         send_default_route: bool = False
 
-        @computed_field  # type: ignore[misc]
+        @computed_field  # type: ignore[prop-decorator]
         @property
         def families(self) -> list[IPFamily]:
             return [IPFamily.V4UNICAST, IPFamily.V4MULTICAST] if self.add_v4_multicast else [IPFamily.V4UNICAST]
 
-        @computed_field  # type: ignore[misc]
+        @computed_field  # type: ignore[prop-decorator]
         @property
         def ip_type(self) -> IPTypes:
             return IPTypes.IPV4
@@ -99,12 +100,12 @@ def initial_input_form_generator(product_name: str) -> FormGenerator:
         add_v6_multicast: bool = Field(default=False, exclude=True)
         send_default_route: bool = False
 
-        @computed_field  # type: ignore[misc]
+        @computed_field  # type: ignore[prop-decorator]
         @property
         def families(self) -> list[IPFamily]:
             return [IPFamily.V6UNICAST, IPFamily.V6MULTICAST] if self.add_v6_multicast else [IPFamily.V6UNICAST]
 
-        @computed_field  # type: ignore[misc]
+        @computed_field  # type: ignore[prop-decorator]
         @property
         def ip_type(self) -> IPTypes:
             return IPTypes.IPV6
diff --git a/gso/workflows/l3_core_service/deploy_prefix_list.py b/gso/workflows/l3_core_service/deploy_prefix_list.py
new file mode 100644
index 0000000000000000000000000000000000000000..ea0c6b07d7a72e0ac458a5a3415c56e6906710d8
--- /dev/null
+++ b/gso/workflows/l3_core_service/deploy_prefix_list.py
@@ -0,0 +1,76 @@
+"""Prefix Deployment workflow for L3 Core Service subscription objects."""
+
+from typing import Any
+
+from orchestrator.targets import Target
+from orchestrator.workflow import StepList, begin, done, step, workflow
+from orchestrator.workflows.steps import resync, store_process_subscription, unsync
+from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import State, UUIDstr
+
+from gso.products.product_types.l3_core_service import L3CoreService
+from gso.services.lso_client import LSOState, lso_interaction
+from gso.services.partners import get_partner_by_id
+
+
+@step("Prepare list of all Access Ports")
+def build_fqdn_list(subscription_id: UUIDstr) -> State:
+    """Build the list of all FQDNs that are in the list of access ports of a L3 Core Service subscription."""
+    subscription = L3CoreService.from_subscription(subscription_id)
+    ap_fqdn_list = [ap.sbp.edge_port.node.router_fqdn for ap in subscription.l3_core_service.ap_list]
+    return {"ap_fqdn_list": ap_fqdn_list, "subscription": subscription}
+
+
+@step("[DRY RUN] Deploy Prefix-Lists")
+def deploy_prefix_lists_dry(subscription: dict[str, Any], process_id: UUIDstr, ap_fqdn_list: list[str]) -> LSOState:
+    """Workflow step for running a playbook that deploys prefix-lists in dry run mode."""
+    extra_vars = {
+        "subscription": subscription,
+        "partner_name": get_partner_by_id(subscription["customer_id"]).name,
+        "dry_run": True,
+        "verb": "deploy",
+        "object": "prefix_list",
+        "is_verification_workflow": "false",
+        "commit_comment": f"GSO_PROCESS_ID: {process_id} - Deploy prefix-lists for {subscription["description"]}",
+    }
+
+    return {
+        "playbook_name": "gap_ansible/playbooks/deploy_prefix_list.yaml",
+        "inventory": {"all": {"hosts": dict.fromkeys(ap_fqdn_list)}},
+        "extra_vars": extra_vars,
+    }
+
+
+@step("[REAL] Deploy Prefix-Lists")
+def deploy_prefix_lists_real(subscription: dict[str, Any], process_id: UUIDstr, ap_fqdn_list: list[str]) -> LSOState:
+    """Workflow step for running a playbook that deploys prefix-lists."""
+    extra_vars = {
+        "subscription": subscription,
+        "partner_name": get_partner_by_id(subscription["customer_id"]).name,
+        "dry_run": False,
+        "verb": "deploy",
+        "object": "prefix_list",
+        "is_verification_workflow": "false",
+        "commit_comment": (f"GSO_PROCESS_ID: {process_id} - Deploy prefix-lists for {subscription["description"]}"),
+    }
+
+    return {
+        "playbook_name": "gap_ansible/playbooks/deploy_prefix_list.yaml",
+        "inventory": {"all": {"hosts": dict.fromkeys(ap_fqdn_list)}},
+        "extra_vars": extra_vars,
+    }
+
+
+@workflow("Deploy Prefix-List", target=Target.SYSTEM, initial_input_form=(wrap_modify_initial_input_form(None)))
+def deploy_prefix_list() -> StepList:
+    """Deploy prefix-lists for an existing L3 Core Service subscription."""
+    return (
+        begin
+        >> store_process_subscription(Target.SYSTEM)
+        >> unsync
+        >> build_fqdn_list
+        >> lso_interaction(deploy_prefix_lists_dry)
+        >> lso_interaction(deploy_prefix_lists_real)
+        >> resync
+        >> done
+    )
diff --git a/gso/workflows/l3_core_service/import_l3_core_service.py b/gso/workflows/l3_core_service/import_l3_core_service.py
index d7f0d06ee85ebb28e8a1dac60769d8f4014187a7..1c9d85def744dfe543560ef12ce8e309022bb308 100644
--- a/gso/workflows/l3_core_service/import_l3_core_service.py
+++ b/gso/workflows/l3_core_service/import_l3_core_service.py
@@ -1,11 +1,11 @@
 """A modification workflow for migrating an `ImportedGeantIP` to a `GeantIP` subscription."""
 
 from orchestrator.targets import Target
-from orchestrator.types import State, UUIDstr
 from orchestrator.utils.errors import ProcessFailureError
 from orchestrator.workflow import StepList, done, init, step, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import State, UUIDstr
 
 from gso.products import ProductName
 from gso.products.product_types.l3_core_service import (
diff --git a/gso/workflows/l3_core_service/modify_l3_core_service.py b/gso/workflows/l3_core_service/modify_l3_core_service.py
index 949cc280dc35f3c25dbfa759f917ec7af4f6d3d6..e8f5b8af1bc6d76844b5b2913e7eb9aed9d1dd93 100644
--- a/gso/workflows/l3_core_service/modify_l3_core_service.py
+++ b/gso/workflows/l3_core_service/modify_l3_core_service.py
@@ -6,12 +6,11 @@ from uuid import uuid4
 from orchestrator import begin, conditional, done, step, workflow
 from orchestrator.forms import FormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, UUIDstr
 from orchestrator.workflow import StepList
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
 from pydantic import AfterValidator, BaseModel, ConfigDict, Field, NonNegativeInt, computed_field
-from pydantic_forms.types import State
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 from pydantic_forms.validators import Divider, Label
 
 from gso.products.product_blocks.bgp_session import BGPSession, IPFamily, IPTypes
@@ -76,12 +75,12 @@ def initial_input_form_generator(subscription_id: UUIDstr) -> FormGenerator:
         add_v4_multicast: bool = Field(default=False, exclude=True)
         send_default_route: bool = False
 
-        @computed_field  # type: ignore[misc]
+        @computed_field  # type: ignore[prop-decorator]
         @property
         def families(self) -> list[IPFamily]:
             return [IPFamily.V4UNICAST, IPFamily.V4MULTICAST] if self.add_v4_multicast else [IPFamily.V4UNICAST]
 
-        @computed_field  # type: ignore[misc]
+        @computed_field  # type: ignore[prop-decorator]
         @property
         def ip_type(self) -> IPTypes:
             return IPTypes.IPV4
@@ -97,12 +96,12 @@ def initial_input_form_generator(subscription_id: UUIDstr) -> FormGenerator:
         add_v6_multicast: bool = Field(default=False, exclude=True)
         send_default_route: bool = False
 
-        @computed_field  # type: ignore[misc]
+        @computed_field  # type: ignore[prop-decorator]
         @property
         def families(self) -> list[IPFamily]:
             return [IPFamily.V6UNICAST, IPFamily.V6MULTICAST] if self.add_v6_multicast else [IPFamily.V6UNICAST]
 
-        @computed_field  # type: ignore[misc]
+        @computed_field  # type: ignore[prop-decorator]
         @property
         def ip_type(self) -> IPTypes:
             return IPTypes.IPV6
@@ -156,8 +155,7 @@ def initial_input_form_generator(subscription_id: UUIDstr) -> FormGenerator:
 
         class BindingPortModificationForm(FormPage):
             model_config = ConfigDict(
-                title=f"{product_name} - Modify Edge Port configuration "
-                f"({access_port_index + 1}/{len(input_ap_list)})"
+                title=f"{product_name} - Modify Edge Port configuration ({access_port_index + 1}/{len(input_ap_list)})"
             )
             current_ep_label: Label = Field(
                 f"Currently configuring on {access_port.sbp.edge_port.edge_port_description} "
@@ -230,7 +228,9 @@ def initial_input_form_generator(subscription_id: UUIDstr) -> FormGenerator:
             is_tagged: bool = False
             vlan_id: VLAN_ID
             ipv4_address: IPv4AddressType
+            ipv4_mask: IPv4Netmask
             ipv6_address: IPv6AddressType
+            ipv6_mask: IPv6Netmask
             custom_firewall_filters: bool = False
             v4_bfd_settings: BFDInputModel
             v6_bfd_settings: BFDInputModel
@@ -297,7 +297,9 @@ def modify_existing_sbp_blocks(subscription: L3CoreService, modified_sbp_list: l
         current_sbp.gs_id = modified_sbp_data["gs_id"]
         current_sbp.is_tagged = modified_sbp_data["is_tagged"]
         current_sbp.ipv4_address = modified_sbp_data["ipv4_address"]
+        current_sbp.ipv4_mask = modified_sbp_data["ipv4_mask"]
         current_sbp.ipv6_address = modified_sbp_data["ipv6_address"]
+        current_sbp.ipv6_mask = modified_sbp_data["ipv6_mask"]
         current_sbp.custom_firewall_filters = modified_sbp_data["custom_firewall_filters"]
         access_port.ap_type = modified_sbp_data["new_ap_type"]
         access_port.custom_service_name = modified_sbp_data["custom_service_name"]
diff --git a/gso/workflows/l3_core_service/terminate_l3_core_service.py b/gso/workflows/l3_core_service/terminate_l3_core_service.py
index 9cf401a5c89edbef1169e9f642ef603fff9b27bb..8cae6c430b4a635906cf80fb3d67d25444a9a8ef 100644
--- a/gso/workflows/l3_core_service/terminate_l3_core_service.py
+++ b/gso/workflows/l3_core_service/terminate_l3_core_service.py
@@ -3,11 +3,11 @@
 from orchestrator import begin, workflow
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, done
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
-from pydantic_forms.types import FormGenerator
+from pydantic_forms.types import FormGenerator, UUIDstr
 
 from gso.products.product_types.l3_core_service import L3CoreService
 from gso.utils.types.tt_number import TTNumber
diff --git a/gso/workflows/l3_core_service/validate_prefix_list.py b/gso/workflows/l3_core_service/validate_prefix_list.py
new file mode 100644
index 0000000000000000000000000000000000000000..e2c6cbbf85a09608cca982ffd63105d94631c53b
--- /dev/null
+++ b/gso/workflows/l3_core_service/validate_prefix_list.py
@@ -0,0 +1,53 @@
+"""Prefix Validation workflow for L3 Core Service subscription objects."""
+
+from typing import Any
+
+from orchestrator.targets import Target
+from orchestrator.workflow import StepList, begin, done, step, workflow
+from orchestrator.workflows.steps import store_process_subscription
+from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import State, UUIDstr
+
+from gso.products.product_types.l3_core_service import L3CoreService
+from gso.services.lso_client import LSOState, anonymous_lso_interaction
+from gso.services.partners import get_partner_by_id
+
+
+@step("Prepare list of all Access Ports")
+def build_fqdn_list(subscription_id: UUIDstr) -> State:
+    """Build the list of all FQDNs that are in the list of access ports of a L3 Core Service subscription."""
+    subscription = L3CoreService.from_subscription(subscription_id)
+    ap_fqdn_list = [ap.sbp.edge_port.node.router_fqdn for ap in subscription.l3_core_service.ap_list]
+    return {"ap_fqdn_list": ap_fqdn_list, "subscription": subscription}
+
+
+@step("[DRY RUN] Validate Prefix-Lists")
+def validate_prefix_lists_dry(subscription: dict[str, Any], process_id: UUIDstr, ap_fqdn_list: list[str]) -> LSOState:
+    """Workflow step for running a playbook that validates prefix-lists in dry run mode."""
+    extra_vars = {
+        "subscription": subscription,
+        "partner_name": get_partner_by_id(subscription["customer_id"]).name,
+        "dry_run": True,
+        "verb": "deploy",
+        "object": "prefix_list",
+        "is_verification_workflow": "true",
+        "commit_comment": f"GSO_PROCESS_ID: {process_id} - Validate prefix-lists for {subscription["description"]}",
+    }
+
+    return {
+        "playbook_name": "gap_ansible/playbooks/validate_prefix_list.yaml",
+        "inventory": {"all": {"hosts": dict.fromkeys(ap_fqdn_list)}},
+        "extra_vars": extra_vars,
+    }
+
+
+@workflow("Validate Prefix-List", target=Target.SYSTEM, initial_input_form=(wrap_modify_initial_input_form(None)))
+def validate_prefix_list() -> StepList:
+    """Validate prefix-lists for an existing L3 Core Service subscription."""
+    return (
+        begin
+        >> store_process_subscription(Target.SYSTEM)
+        >> build_fqdn_list
+        >> anonymous_lso_interaction(validate_prefix_lists_dry)
+        >> done
+    )
diff --git a/gso/workflows/lan_switch_interconnect/create_imported_lan_switch_interconnect.py b/gso/workflows/lan_switch_interconnect/create_imported_lan_switch_interconnect.py
index 03c6e8aa8216809b82d10c51186a2bb56f25634e..12bcff95047f27e385655766bbbfa0f3a4020bbb 100644
--- a/gso/workflows/lan_switch_interconnect/create_imported_lan_switch_interconnect.py
+++ b/gso/workflows/lan_switch_interconnect/create_imported_lan_switch_interconnect.py
@@ -5,9 +5,10 @@ from uuid import uuid4
 from orchestrator import step, workflow
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription
+from pydantic_forms.types import FormGenerator, State
 
 from gso.cli.imports import LanSwitchInterconnectRouterSideImportModel, LanSwitchInterconnectSwitchSideImportModel
 from gso.products import ProductName
diff --git a/gso/workflows/lan_switch_interconnect/create_lan_switch_interconnect.py b/gso/workflows/lan_switch_interconnect/create_lan_switch_interconnect.py
index 0c5f74850a8c518740d1eb73510e8aa0af80a198..4ebd46d9accd4992e29ead9a5afd78ab232b1ce1 100644
--- a/gso/workflows/lan_switch_interconnect/create_lan_switch_interconnect.py
+++ b/gso/workflows/lan_switch_interconnect/create_lan_switch_interconnect.py
@@ -7,12 +7,13 @@ from uuid import uuid4
 from annotated_types import Len
 from orchestrator.forms import FormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.utils.errors import ProcessFailureError
 from orchestrator.workflow import StepList, begin, done, step, workflow
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription
 from orchestrator.workflows.utils import wrap_create_initial_input_form
 from pydantic import AfterValidator, ConfigDict
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 from pydantic_forms.validators import ReadOnlyField
 
 from gso.products.product_blocks.lan_switch_interconnect import (
diff --git a/gso/workflows/lan_switch_interconnect/import_lan_switch_interconnect.py b/gso/workflows/lan_switch_interconnect/import_lan_switch_interconnect.py
index 0de05997aad2dc5ffd930c98f6f271174add6b82..32d47addfb270856f00ca4ccc2493f654899e0e4 100644
--- a/gso/workflows/lan_switch_interconnect/import_lan_switch_interconnect.py
+++ b/gso/workflows/lan_switch_interconnect/import_lan_switch_interconnect.py
@@ -2,10 +2,10 @@
 
 from orchestrator import step, workflow
 from orchestrator.targets import Target
-from orchestrator.types import State, UUIDstr
 from orchestrator.workflow import StepList, begin, done
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import State, UUIDstr
 
 from gso.products import ProductName
 from gso.products.product_types.lan_switch_interconnect import ImportedLanSwitchInterconnect, LanSwitchInterconnect
diff --git a/gso/workflows/lan_switch_interconnect/terminate_lan_switch_interconnect.py b/gso/workflows/lan_switch_interconnect/terminate_lan_switch_interconnect.py
index 47e1865478179b1baffb0542dc5020aabe5f44d3..b878b7d6afc27ee0eebbdf76b18708b586a72148 100644
--- a/gso/workflows/lan_switch_interconnect/terminate_lan_switch_interconnect.py
+++ b/gso/workflows/lan_switch_interconnect/terminate_lan_switch_interconnect.py
@@ -3,11 +3,11 @@
 from orchestrator import begin, workflow
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, done, step
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
-from pydantic_forms.types import FormGenerator
+from pydantic_forms.types import FormGenerator, UUIDstr
 from pydantic_forms.validators import Label
 
 from gso.products.product_types.lan_switch_interconnect import LanSwitchInterconnect
diff --git a/gso/workflows/office_router/create_imported_office_router.py b/gso/workflows/office_router/create_imported_office_router.py
index c1280c13d0b1e0e729843078939b091573267f14..9dbef9f32fd5f5b7eb4a0b1c4f09f54eb556e0d8 100644
--- a/gso/workflows/office_router/create_imported_office_router.py
+++ b/gso/workflows/office_router/create_imported_office_router.py
@@ -3,10 +3,11 @@
 from orchestrator import workflow
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done, step
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription
 from pydantic import ConfigDict
+from pydantic_forms.types import FormGenerator, State
 
 from gso.products import ProductName
 from gso.products.product_types.office_router import ImportedOfficeRouterInactive
diff --git a/gso/workflows/office_router/import_office_router.py b/gso/workflows/office_router/import_office_router.py
index 0d1d67abdd28b7a67c68cec92f05d0268e52de1f..6ae3240b5d976a18357608e49123bb500a3237da 100644
--- a/gso/workflows/office_router/import_office_router.py
+++ b/gso/workflows/office_router/import_office_router.py
@@ -1,10 +1,10 @@
 """A modification workflow for migrating an ImportedOfficeRouter to an OfficeRouter subscription."""
 
 from orchestrator.targets import Target
-from orchestrator.types import State, UUIDstr
 from orchestrator.workflow import StepList, done, init, step, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import State, UUIDstr
 
 from gso.products import ProductName
 from gso.products.product_types.office_router import ImportedOfficeRouter, OfficeRouter
diff --git a/gso/workflows/opengear/create_imported_opengear.py b/gso/workflows/opengear/create_imported_opengear.py
index a7433f2bfed6a6b5400893d0f52b669a1e70fc9a..47f157f0f11e22f7181bd0eb623d4e16b4703ee8 100644
--- a/gso/workflows/opengear/create_imported_opengear.py
+++ b/gso/workflows/opengear/create_imported_opengear.py
@@ -3,10 +3,11 @@
 from orchestrator import workflow
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, done, init, step
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription
 from pydantic import ConfigDict
+from pydantic_forms.types import FormGenerator, State
 
 from gso.products import ProductName
 from gso.products.product_types.opengear import ImportedOpengearInactive
diff --git a/gso/workflows/opengear/import_opengear.py b/gso/workflows/opengear/import_opengear.py
index d9bb75306a39161dc03c78ca47cc70449cd56850..1b34b55a7e4598e07d8c61a41de7c95c0b26661d 100644
--- a/gso/workflows/opengear/import_opengear.py
+++ b/gso/workflows/opengear/import_opengear.py
@@ -1,10 +1,10 @@
 """A modification workflow for migrating an ImportedOpengear to an Opengear subscription."""
 
 from orchestrator.targets import Target
-from orchestrator.types import State, UUIDstr
 from orchestrator.workflow import StepList, done, init, step, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import State, UUIDstr
 
 from gso.products import ProductName
 from gso.products.product_types.opengear import ImportedOpengear, Opengear
diff --git a/gso/workflows/router/activate_router.py b/gso/workflows/router/activate_router.py
index 683292d764c332ce665faaaf1000645633e54957..e5b65ca5c4e0e674b9f7700fcc54dc59ff98fe0a 100644
--- a/gso/workflows/router/activate_router.py
+++ b/gso/workflows/router/activate_router.py
@@ -8,10 +8,11 @@ from orchestrator.config.assignee import Assignee
 from orchestrator.forms import SubmitFormPage
 from orchestrator.forms.validators import Label
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done, inputstep, workflow
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import FormGenerator, UUIDstr
 
 from gso.products.product_types.router import Router
 
diff --git a/gso/workflows/router/create_imported_router.py b/gso/workflows/router/create_imported_router.py
index 81acba1aedb5209a3e113ba5542a57492270667b..56640256ab700eb0207f25e18b72b3bd591fd96e 100644
--- a/gso/workflows/router/create_imported_router.py
+++ b/gso/workflows/router/create_imported_router.py
@@ -3,10 +3,11 @@
 from orchestrator import workflow
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done, step
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription
 from pydantic import ConfigDict
+from pydantic_forms.types import FormGenerator, State
 
 from gso.products import ProductName
 from gso.products.product_blocks.router import RouterRole
diff --git a/gso/workflows/router/create_router.py b/gso/workflows/router/create_router.py
index 6cd77a108e8c3bf3aaf62827f3b69156b20c1fbe..8c7a8434424c7f6ee4d7801597dd9975a4ebd27a 100644
--- a/gso/workflows/router/create_router.py
+++ b/gso/workflows/router/create_router.py
@@ -46,12 +46,13 @@ from orchestrator.config.assignee import Assignee
 from orchestrator.forms import FormPage, SubmitFormPage
 from orchestrator.forms.validators import Label
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.utils.errors import ProcessFailureError
 from orchestrator.workflow import StepList, begin, conditional, done, inputstep, step, workflow
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription
 from orchestrator.workflows.utils import wrap_create_initial_input_form
 from pydantic import ConfigDict, model_validator
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 from pydantic_forms.validators import ReadOnlyField
 
 from gso.products.product_blocks.router import RouterRole
diff --git a/gso/workflows/router/import_router.py b/gso/workflows/router/import_router.py
index 1421ff0faac2638d15e15bea867865ea887e16ec..efe39a1ae4c400924ec948205ccb269d89721ae9 100644
--- a/gso/workflows/router/import_router.py
+++ b/gso/workflows/router/import_router.py
@@ -1,10 +1,10 @@
 """A modification workflow for setting a new ISIS metric for an IP trunk."""
 
 from orchestrator.targets import Target
-from orchestrator.types import State, UUIDstr
 from orchestrator.workflow import StepList, done, init, step, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import State, UUIDstr
 
 from gso.products import ProductName
 from gso.products.product_types.router import ImportedRouter, Router
diff --git a/gso/workflows/router/modify_connection_strategy.py b/gso/workflows/router/modify_connection_strategy.py
index e571cfc44243a3a172ad9ce86377e380ef4e06b9..93cca08daf5f8cd6294f00a0f8657fd8712bc628 100644
--- a/gso/workflows/router/modify_connection_strategy.py
+++ b/gso/workflows/router/modify_connection_strategy.py
@@ -6,11 +6,11 @@ loopback interface.
 
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, UUIDstr
 from orchestrator.workflow import StepList, begin, done, step, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
 from pydantic import ConfigDict
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 
 from gso.products.product_types.router import Router
 from gso.utils.shared_enums import ConnectionStrategy
diff --git a/gso/workflows/router/modify_kentik_license.py b/gso/workflows/router/modify_kentik_license.py
index 3a809fc0379072bb1bbd110608afcc7c24846bec..5b15f62fa6c4ae77e0ff13cf8cef66dda772a4c7 100644
--- a/gso/workflows/router/modify_kentik_license.py
+++ b/gso/workflows/router/modify_kentik_license.py
@@ -9,12 +9,12 @@ from typing import Any
 
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, UUIDstr
 from orchestrator.utils.errors import ProcessFailureError
 from orchestrator.workflow import StepList, begin, done, step, workflow
 from orchestrator.workflows.steps import store_process_subscription
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
 from pydantic import model_validator
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 from pydantic_forms.validators import Choice
 
 from gso.products.product_blocks.router import RouterRole
diff --git a/gso/workflows/router/promote_p_to_pe.py b/gso/workflows/router/promote_p_to_pe.py
index 63f59a24cf66e68962278b2b6d305d570c042a08..ce961ed10581017bc7a592031fd36c1197c8cad7 100644
--- a/gso/workflows/router/promote_p_to_pe.py
+++ b/gso/workflows/router/promote_p_to_pe.py
@@ -7,12 +7,12 @@ from orchestrator.config.assignee import Assignee
 from orchestrator.forms import SubmitFormPage
 from orchestrator.forms.validators import Label
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, UUIDstr
 from orchestrator.utils.json import json_dumps
 from orchestrator.workflow import StepList, begin, done, inputstep, step, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
 from pydantic import ConfigDict, model_validator
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 
 from gso.products.product_blocks.router import RouterRole
 from gso.products.product_types.router import Router
diff --git a/gso/workflows/router/redeploy_base_config.py b/gso/workflows/router/redeploy_base_config.py
index bd64fb7e276a940af816c81aeda3f29b23bc90e6..11c4264dc754f2e7289241a2324ba7b00dabf2c7 100644
--- a/gso/workflows/router/redeploy_base_config.py
+++ b/gso/workflows/router/redeploy_base_config.py
@@ -11,10 +11,10 @@ run. After confirmation by an operator, the configuration is committed to the ma
 from orchestrator.forms import SubmitFormPage
 from orchestrator.forms.validators import Label
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, UUIDstr
 from orchestrator.workflow import StepList, begin, done, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import FormGenerator, UUIDstr
 
 from gso.products.product_types.router import Router
 from gso.services.lso_client import lso_interaction
diff --git a/gso/workflows/router/terminate_router.py b/gso/workflows/router/terminate_router.py
index a908bc8e184a147023fff8b81052feba81da300d..9c73b13e5ca3ae08dc6ef8e1c6bbffd133fd37e9 100644
--- a/gso/workflows/router/terminate_router.py
+++ b/gso/workflows/router/terminate_router.py
@@ -22,7 +22,7 @@ import logging
 from orchestrator.forms import SubmitFormPage
 from orchestrator.forms.validators import Label
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.utils.errors import ProcessFailureError
 from orchestrator.utils.json import json_dumps
 from orchestrator.workflow import StepList, begin, conditional, done, step, workflow
@@ -33,6 +33,7 @@ from orchestrator.workflows.steps import (
     unsync,
 )
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 from requests import HTTPError
 
 from gso.products.product_blocks.router import RouterRole
diff --git a/gso/workflows/router/update_ibgp_mesh.py b/gso/workflows/router/update_ibgp_mesh.py
index b0fa37c6da14f778074e5f05fc7e5dd9115e4f44..2c8c9db00fbc54649a8182f236e48648a899e359 100644
--- a/gso/workflows/router/update_ibgp_mesh.py
+++ b/gso/workflows/router/update_ibgp_mesh.py
@@ -24,11 +24,12 @@ from orchestrator.config.assignee import Assignee
 from orchestrator.forms import SubmitFormPage
 from orchestrator.forms.validators import Label
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, conditional, done, inputstep, step, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
 from pydantic import ConfigDict, model_validator
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 
 from gso.products.product_blocks.router import RouterRole
 from gso.products.product_types.router import Router
diff --git a/gso/workflows/router/validate_router.py b/gso/workflows/router/validate_router.py
index a469237e5a4bdf365934203edaf90a7cfad17d16..25bd3176c50b8506117dc3c09767944c85707baa 100644
--- a/gso/workflows/router/validate_router.py
+++ b/gso/workflows/router/validate_router.py
@@ -3,11 +3,11 @@
 from typing import Any
 
 from orchestrator.targets import Target
-from orchestrator.types import State, UUIDstr
 from orchestrator.utils.errors import ProcessFailureError
 from orchestrator.workflow import StepList, begin, conditional, done, step, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import State, UUIDstr
 
 from gso.products.product_blocks.router import RouterRole
 from gso.products.product_types.router import Router
diff --git a/gso/workflows/site/create_imported_site.py b/gso/workflows/site/create_imported_site.py
index 16f2471f7fd97b0d6918be70da8e0645415cf3b4..05d73eff24afd1fdaf4ff56c3953ef87c89f3786 100644
--- a/gso/workflows/site/create_imported_site.py
+++ b/gso/workflows/site/create_imported_site.py
@@ -4,10 +4,11 @@ from uuid import UUID
 
 from orchestrator.forms import FormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done, step, workflow
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription
 from pydantic import ConfigDict
+from pydantic_forms.types import FormGenerator, State
 
 from gso.products import ProductName
 from gso.products.product_blocks.site import SiteTier
diff --git a/gso/workflows/site/create_site.py b/gso/workflows/site/create_site.py
index 149178e346c5526f2d42bcee95aae89e977a3c68..40f5ae0a148c968054cce5755f8ca0cc5ccf036d 100644
--- a/gso/workflows/site/create_site.py
+++ b/gso/workflows/site/create_site.py
@@ -6,11 +6,12 @@ The `create_site` workflow creates a new site object in the service database, an
 
 from orchestrator.forms import FormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done, step, workflow
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription
 from orchestrator.workflows.utils import wrap_create_initial_input_form
 from pydantic import ConfigDict
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 from pydantic_forms.validators import ReadOnlyField
 
 from gso.products.product_blocks import site as site_pb
diff --git a/gso/workflows/site/import_site.py b/gso/workflows/site/import_site.py
index f2130354c35095082dd1fcd2444f9ad924eaf719..20f19ff266504d41c56c04dccdd9df8f1506a6b4 100644
--- a/gso/workflows/site/import_site.py
+++ b/gso/workflows/site/import_site.py
@@ -1,10 +1,10 @@
 """A modification workflow for migrating an ImportedSite to a Site subscription."""
 
 from orchestrator.targets import Target
-from orchestrator.types import State, UUIDstr
 from orchestrator.workflow import StepList, done, init, step, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import State, UUIDstr
 
 from gso.products import ProductName
 from gso.products.product_types.site import ImportedSite, Site
diff --git a/gso/workflows/site/modify_site.py b/gso/workflows/site/modify_site.py
index 2a1913f6bbdeb56ff2b9e4ed7b26025566ccc9f3..8776bc3e4ea7f5acc78ec783be663465a1cd19da 100644
--- a/gso/workflows/site/modify_site.py
+++ b/gso/workflows/site/modify_site.py
@@ -17,7 +17,7 @@ from typing import Annotated
 
 from orchestrator.forms import FormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done, step, workflow
 from orchestrator.workflows.steps import (
     resync,
@@ -27,6 +27,7 @@ from orchestrator.workflows.steps import (
 )
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
 from pydantic import AfterValidator, ConfigDict
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 from pydantic_forms.validators import ReadOnlyField
 
 from gso.products.product_blocks.site import SiteTier
diff --git a/gso/workflows/site/terminate_site.py b/gso/workflows/site/terminate_site.py
index 0e34f209cb50e1cd5f4ac1b446f30baabd9d7dbc..5e21a4cbfc610ce83cb237e4424a891f912190b0 100644
--- a/gso/workflows/site/terminate_site.py
+++ b/gso/workflows/site/terminate_site.py
@@ -8,7 +8,7 @@ unavailable for an operator to run, accompanied by an error message explaining t
 from orchestrator.forms import SubmitFormPage
 from orchestrator.forms.validators import Label
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done, workflow
 from orchestrator.workflows.steps import (
     resync,
@@ -17,6 +17,7 @@ from orchestrator.workflows.steps import (
     unsync,
 )
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import FormGenerator, UUIDstr
 
 from gso.products.product_types.site import Site
 
diff --git a/gso/workflows/super_pop_switch/create_imported_super_pop_switch.py b/gso/workflows/super_pop_switch/create_imported_super_pop_switch.py
index 6b34253173ce2b5ec72963cd274b78141fba2504..e0e1eb7526f5ad45366311af98b466dd62960fa4 100644
--- a/gso/workflows/super_pop_switch/create_imported_super_pop_switch.py
+++ b/gso/workflows/super_pop_switch/create_imported_super_pop_switch.py
@@ -3,10 +3,11 @@
 from orchestrator import workflow
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done, step
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription
 from pydantic import ConfigDict
+from pydantic_forms.types import FormGenerator, State
 
 from gso.products import ProductName
 from gso.products.product_types.super_pop_switch import ImportedSuperPopSwitchInactive
diff --git a/gso/workflows/super_pop_switch/import_super_pop_switch.py b/gso/workflows/super_pop_switch/import_super_pop_switch.py
index 63c7148f978a7d11eb9b97f0d3bfabb9dc71b30c..e29e9d9fc74360dcae256e963cb3a2bcadbff28f 100644
--- a/gso/workflows/super_pop_switch/import_super_pop_switch.py
+++ b/gso/workflows/super_pop_switch/import_super_pop_switch.py
@@ -1,10 +1,10 @@
 """A modification workflow for migrating an ImportedSuperPoPSwitch to a SuperPopSwitch subscription."""
 
 from orchestrator.targets import Target
-from orchestrator.types import State, UUIDstr
 from orchestrator.workflow import StepList, done, init, step, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import State, UUIDstr
 
 from gso.products import ProductName
 from gso.products.product_types.super_pop_switch import ImportedSuperPopSwitch, SuperPopSwitch
diff --git a/gso/workflows/switch/activate_switch.py b/gso/workflows/switch/activate_switch.py
index dc71cfa7d821765032f4f062e79919c39a2700ec..2957faa58d3020510b2c2c2c7c4054bf288cac3b 100644
--- a/gso/workflows/switch/activate_switch.py
+++ b/gso/workflows/switch/activate_switch.py
@@ -4,10 +4,11 @@ from orchestrator.config.assignee import Assignee
 from orchestrator.forms import SubmitFormPage
 from orchestrator.forms.validators import Label
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done, inputstep, workflow
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import FormGenerator, UUIDstr
 
 from gso.products.product_types.switch import Switch
 
diff --git a/gso/workflows/switch/create_imported_switch.py b/gso/workflows/switch/create_imported_switch.py
index 30d7ea46360d01d431c6c635bc8813af39146e07..76133b5f8930cd4540b90091b7e6e9e08d684797 100644
--- a/gso/workflows/switch/create_imported_switch.py
+++ b/gso/workflows/switch/create_imported_switch.py
@@ -3,9 +3,10 @@
 from orchestrator import step, workflow
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 
 from gso.products import ProductName
 from gso.products.product_blocks.switch import SwitchModel
diff --git a/gso/workflows/switch/create_switch.py b/gso/workflows/switch/create_switch.py
index 09b0a03ea25af0880dbf6ef89ac02e6bd49f1a45..d2b7ec337a6dcd99098348da3eeb612933579469 100644
--- a/gso/workflows/switch/create_switch.py
+++ b/gso/workflows/switch/create_switch.py
@@ -5,11 +5,12 @@ from typing import Self
 from orchestrator.config.assignee import Assignee
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done, inputstep, step, workflow
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription
 from orchestrator.workflows.utils import wrap_create_initial_input_form
 from pydantic import ConfigDict, model_validator
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 from pydantic_forms.validators import Choice, Label, ReadOnlyField
 
 from gso.products.product_blocks.switch import SwitchModel
diff --git a/gso/workflows/switch/import_switch.py b/gso/workflows/switch/import_switch.py
index 8ecf2d43930b1e40f84d1866f2db0a7cf8115306..f0caa5eb6c1eaae8f3899e7dfaa8c55bb100c506 100644
--- a/gso/workflows/switch/import_switch.py
+++ b/gso/workflows/switch/import_switch.py
@@ -2,10 +2,10 @@
 
 from orchestrator import step, workflow
 from orchestrator.targets import Target
-from orchestrator.types import State, UUIDstr
 from orchestrator.workflow import StepList, begin, done
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
+from pydantic_forms.types import State, UUIDstr
 
 from gso.products import ProductName
 from gso.products.product_types.switch import ImportedSwitch, Switch
diff --git a/gso/workflows/switch/terminate_switch.py b/gso/workflows/switch/terminate_switch.py
index 84bea41dc5543631cec790a7dacb9bd729ea1f0d..01f149b1dae9717a955afbb78636942ce5d26e71 100644
--- a/gso/workflows/switch/terminate_switch.py
+++ b/gso/workflows/switch/terminate_switch.py
@@ -3,11 +3,11 @@
 from orchestrator import begin, done, workflow
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, step
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
-from pydantic_forms.types import FormGenerator
+from pydantic_forms.types import FormGenerator, UUIDstr
 from pydantic_forms.validators import Label
 
 from gso.products.product_types.switch import Switch
diff --git a/gso/workflows/tasks/create_partners.py b/gso/workflows/tasks/create_partners.py
index e6e4e4b04703de62b46a74081327163bbde0bd56..3b82e41fba5a93cb2f744396e6ee82a34f5dc8e7 100644
--- a/gso/workflows/tasks/create_partners.py
+++ b/gso/workflows/tasks/create_partners.py
@@ -2,9 +2,9 @@
 
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State
 from orchestrator.workflow import StepList, begin, done, step, workflow
 from pydantic import ConfigDict
+from pydantic_forms.types import FormGenerator, State
 
 from gso.services.partners import PartnerEmail, PartnerName, PartnerSchema, create_partner
 
diff --git a/gso/workflows/tasks/delete_partners.py b/gso/workflows/tasks/delete_partners.py
index 15cbe2ac2f932ad2de5fc0d584ce5e00eb3325e5..eaa97d7e9fb443fef9efa9758de6043b1fb6996c 100644
--- a/gso/workflows/tasks/delete_partners.py
+++ b/gso/workflows/tasks/delete_partners.py
@@ -4,9 +4,9 @@ from enum import Enum
 
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, UUIDstr
 from orchestrator.workflow import StepList, begin, done, step, workflow
 from pydantic import ConfigDict, EmailStr, field_validator
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 
 from gso.services.partners import delete_partner, get_partner_by_name
 from gso.services.subscriptions import get_subscriptions
diff --git a/gso/workflows/tasks/modify_partners.py b/gso/workflows/tasks/modify_partners.py
index 0445ceeeb65f82bb4e7ea8e1124bc2bc8613c34d..5910a7bd8e6fe6190bb5bccfd0c1428e63c43d7c 100644
--- a/gso/workflows/tasks/modify_partners.py
+++ b/gso/workflows/tasks/modify_partners.py
@@ -2,9 +2,9 @@
 
 from orchestrator.forms import FormPage, SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, UUIDstr
 from orchestrator.workflow import StepList, begin, done, step, workflow
 from pydantic import ConfigDict, EmailStr, field_validator
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 
 from gso.services.partners import (
     ModifiedPartnerSchema,
diff --git a/gso/workflows/tasks/send_email_notifications.py b/gso/workflows/tasks/send_email_notifications.py
index 42b94bd421f4d2e45af354efa00205f975530c07..527ea7f985d7d09f064d14a1b98565de4246c738 100644
--- a/gso/workflows/tasks/send_email_notifications.py
+++ b/gso/workflows/tasks/send_email_notifications.py
@@ -1,27 +1,37 @@
-"""Send email notifications for all tasks that have failed."""
+"""Send email notifications for all tasks that have failed.
+
+When validation tasks have failed, at most two separate emails will be sent. The first will contain all general failures
+of subscription validation workflows. The second email contains an overview of the prefix list validations that have
+failed.
+"""
+
+from typing import Any
 
 from orchestrator.targets import Target
-from orchestrator.types import State
 from orchestrator.workflow import StepList, conditional, done, init, step, workflow
+from pydantic_forms.types import State
 
 from gso.services.mailer import send_mail
-from gso.services.processes import get_failed_tasks
+from gso.services.processes import get_failed_tasks, get_failed_tasks_by_workflow_name
 from gso.services.subscriptions import get_subscription_by_process_id
 from gso.settings import load_oss_params
 
 
-@step("Gather all tasks that recently failed")
+@step("Gather all tasks that have failed")
 def gather_failed_tasks() -> State:
     """Gather all tasks that have failed."""
-    return {"failed_tasks": get_failed_tasks()}
+    failed_prefix_list_tasks = get_failed_tasks_by_workflow_name("validate_prefix_list")
+    all_other_tasks = list(set(get_failed_tasks()) - set(failed_prefix_list_tasks))
 
+    return {"failed_tasks": all_other_tasks, "failed_prefix_list_checks": failed_prefix_list_tasks}
 
-@step("Send notification emails for all failed tasks")
-def send_email_notifications(state: State) -> None:
+
+@step("Send notification email for failed tasks")
+def send_email_notification(failed_tasks: list[dict[str, Any]]) -> None:
     """Send out an email notification for all tasks that have failed."""
     general_settings = load_oss_params().GENERAL
     all_alerts = ""
-    for failure in state["failed_tasks"]:
+    for failure in failed_tasks:
         failed_task_url = f"{general_settings.public_hostname}/workflows/{failure["process_id"]}"
         failed_subscription = get_subscription_by_process_id(failure["process_id"])
         all_alerts = f"{all_alerts}------\n\n"
@@ -45,9 +55,45 @@ def send_email_notifications(state: State) -> None:
     )
 
 
+@step("Send notification emails for failed prefix list tasks")
+def send_prefix_list_email_notification(failed_prefix_list_checks: list[dict[str, Any]]) -> None:
+    """Send out an email notification for all prefix list validation tasks that have failed."""
+    general_settings = load_oss_params().GENERAL
+    all_alerts = ""
+    for failure in failed_prefix_list_checks:
+        failed_task_url = f"{general_settings.public_hostname}/workflows/{failure["process_id"]}"
+        failed_subscription = get_subscription_by_process_id(failure["process_id"])
+        all_alerts = f"{all_alerts}------\n\n"
+        if failed_subscription:
+            all_alerts = (
+                f"{all_alerts}Product name: {failed_subscription.product.name}\n"
+                f"Description: {failed_subscription.description}\n"
+            )
+        all_alerts = (
+            f'{all_alerts}The step "{failure["last_step"]}" failed for the following reason: '
+            f'"{failure["failed_reason"]}".\n\nPlease inspect the full workflow at the following link: '
+            f'{failed_task_url}.\n\n'
+        )
+
+    send_mail(
+        f"GAP {general_settings.environment} environment - One or more prefix lists have diverged!",
+        (
+            f"Please check the following tasks in GAP which have failed.\n\n{all_alerts}------"
+            f"\n\nRegards, the GÉANT Automation Platform.\n\n"
+        ),
+    )
+
+
 @workflow("Send email notifications for all failed tasks", target=Target.SYSTEM)
 def task_send_email_notifications() -> StepList:
     """Gather all failed tasks, and send an email notification if needed."""
     tasks_have_failed = conditional(lambda state: len(state["failed_tasks"]) > 0)
+    prefix_tasks_have_failed = conditional(lambda state: len(state["failed_prefix_list_checks"]) > 0)
 
-    return init >> gather_failed_tasks >> tasks_have_failed(send_email_notifications) >> done
+    return (
+        init
+        >> gather_failed_tasks
+        >> tasks_have_failed(send_email_notification)
+        >> prefix_tasks_have_failed(send_prefix_list_email_notification)
+        >> done
+    )
diff --git a/gso/workflows/vrf/create_vrf.py b/gso/workflows/vrf/create_vrf.py
index 8844ea0c0d3911c406446a25268882f383b2b830..29b46a561e3de85676e6daf4c32600c79e3b4e73 100644
--- a/gso/workflows/vrf/create_vrf.py
+++ b/gso/workflows/vrf/create_vrf.py
@@ -2,11 +2,12 @@
 
 from orchestrator.forms import FormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done, step, workflow
 from orchestrator.workflows.steps import resync, set_status, store_process_subscription
 from orchestrator.workflows.utils import wrap_create_initial_input_form
 from pydantic import ConfigDict
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 from pydantic_forms.validators import ReadOnlyField
 
 from gso.products.product_types.vrf import VRFInactive
diff --git a/gso/workflows/vrf/modify_vrf_router_list.py b/gso/workflows/vrf/modify_vrf_router_list.py
index 200912317a115ede0cd63a56147e3716d9da4cdf..1dde31b7cffb1373c46dd89c2bd8269a06fcaa21 100644
--- a/gso/workflows/vrf/modify_vrf_router_list.py
+++ b/gso/workflows/vrf/modify_vrf_router_list.py
@@ -4,11 +4,11 @@ from typing import Annotated, Any
 
 from orchestrator.forms import SubmitFormPage
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, State, UUIDstr
 from orchestrator.workflow import StepList, begin, done, step, workflow
 from orchestrator.workflows.steps import resync, store_process_subscription, unsync
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
 from pydantic import AfterValidator, BaseModel, ConfigDict, Field
+from pydantic_forms.types import FormGenerator, State, UUIDstr
 from pydantic_forms.validators import validate_unique_list
 
 from gso.products.product_types.router import Router
diff --git a/gso/workflows/vrf/terminate_vrf.py b/gso/workflows/vrf/terminate_vrf.py
index 1b985206b68f788219212ba3676ab245abd6a61d..1b1a6ea7ffd3ba5ce170547f64b7e0788a6b9305 100644
--- a/gso/workflows/vrf/terminate_vrf.py
+++ b/gso/workflows/vrf/terminate_vrf.py
@@ -5,7 +5,7 @@ from typing import Any
 from orchestrator.forms import SubmitFormPage
 from orchestrator.forms.validators import Label
 from orchestrator.targets import Target
-from orchestrator.types import FormGenerator, SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
 from orchestrator.workflow import StepList, begin, done, workflow
 from orchestrator.workflows.steps import (
     resync,
@@ -15,6 +15,7 @@ from orchestrator.workflows.steps import (
 )
 from orchestrator.workflows.utils import wrap_modify_initial_input_form
 from pydantic import model_validator
+from pydantic_forms.types import FormGenerator, UUIDstr
 
 from gso.products.product_types.vrf import VRF
 from gso.utils.types.tt_number import TTNumber
diff --git a/pyproject.toml b/pyproject.toml
index c31bcaefc059e0800ece9d21387068d25f74f887..0a81ec7ba50a8d6bc1baf2bb248900e4488bf312 100644
--- a/pyproject.toml
+++ b/pyproject.toml
@@ -119,6 +119,7 @@ filterwarnings = [
     "ignore",
     "default:::gso",
 ]
+asyncio_default_fixture_loop_scope = "function"
 
 [tool.coverage.run]
 omit = ["gso/migrations/*"]
diff --git a/requirements.txt b/requirements.txt
index a885793c4b4fece3e88a9d00e99129ab331e6719..f625624487ed20b459af5e53bc9c758ceafc7e05 100644
--- a/requirements.txt
+++ b/requirements.txt
@@ -1,30 +1,26 @@
-# Temporary hotfix while version 1.9.1 is still broken
-microsoft-kiota-abstractions==1.9.0
-
-orchestrator-core==2.8.0
+orchestrator-core==3.1.1
+graphql-core==3.2.*  # TODO: this could probably get removed the next time orchestrator-core is upgraded
 requests==2.32.3
-infoblox-client~=0.6.0
-pycountry==23.12.11
-pynetbox==7.3.3
-celery-redbeat==2.2.0
-celery==5.3.6
-azure-identity==1.19.0
-msgraph-sdk==1.2.0
+infoblox-client==0.6.2
+pycountry==24.6.1
+pynetbox==7.4.1
+celery-redbeat==2.3.2
+celery==5.4.0
+azure-identity==1.21.0
+msgraph-sdk==1.24.0
 ping3==4.0.8
 unidecode==1.3.8
 
 # Test and linting dependencies
 celery-stubs==0.1.3
-types-requests==2.31.0.20240406
-types-PyYAML==6.0.12.20240311
-pytest==8.1.1
-faker==24.8.0
-responses==0.25.0
-mypy==1.9.0
+types-requests==2.32.0.20250306
+types-PyYAML==6.0.12.20241230
+pytest==8.3.5
+faker==37.0.0
+responses==0.25.7
+mypy==1.15.0
 ruff==0.3.5
-sphinx==7.2.6
-sphinx-rtd-theme==2.0.0
 urllib3_mock==0.3.3
-pytest-asyncio==0.23.6
-pre-commit~=3.7.0
+pytest-asyncio==0.25.3
+pre-commit==4.1.0
 pytest-xdist==3.6.1
diff --git a/setup.py b/setup.py
index 6815cae22a25215df58cf854c2861bf975d504e1..18d09e620cd17a274e1388c54e7fa9cdfcf9d8f6 100644
--- a/setup.py
+++ b/setup.py
@@ -4,25 +4,25 @@ from setuptools import find_packages, setup
 
 setup(
     name="geant-service-orchestrator",
-    version="2.41",
+    version="2.42",
     author="GÉANT Orchestration and Automation Team",
     author_email="goat@geant.org",
     description="GÉANT Service Orchestrator",
     url="https://gitlab.software.geant.org/goat/gap/geant-service-orchestrator",
     packages=find_packages(),
     install_requires=[
-        "orchestrator-core==2.8.0",
-        "requests==2.31.0",
-        "infoblox-client~=0.6.0",
-        "pycountry==23.12.11",
-        "pynetbox==7.3.3",
-        "celery-redbeat==2.2.0",
-        "celery==5.3.6",
-        "azure-identity==1.16.0",
-        "msgraph-sdk==1.2.0",
+        "orchestrator-core==3.1.1",
+        "graphql-core==3.2.*",  # TODO: this could probably get removed the next time orchestrator-core is upgraded
+        "requests==2.32.3",
+        "infoblox-client==0.6.2",
+        "pycountry==24.6.1",
+        "pynetbox==7.4.1",
+        "celery-redbeat==2.3.2",
+        "celery==5.4.0",
+        "azure-identity==1.21.0",
+        "msgraph-sdk==1.24.0",
         "ping3==4.0.8",
         "unidecode==1.3.8",
-        "microsoft-kiota-abstractions==1.9.0",
     ],
     include_package_data=True,
 )
diff --git a/test/cli/test_imports.py b/test/cli/test_imports.py
index 39c9f31efbdf205afba48cc908096d172a67c4c9..bc882410526e73dde39025e5da0adb91bd8881a5 100644
--- a/test/cli/test_imports.py
+++ b/test/cli/test_imports.py
@@ -554,12 +554,14 @@ def test_import_iptrunk_invalid_router_id_side_a_and_b(mock_start_process, mock_
     import_iptrunks(broken_data["path"])
 
     captured_output, _ = capfd.readouterr()
+    assert "Validation error: 2 validation errors for IptrunkImportModel" in captured_output
+    assert (
+        """side_a_node_id
+  Value error, Router  not found [type=value_error, input_value='', input_type=str]"""
+        in captured_output
+    )
     assert (
-        """Validation error: 2 validation errors for IptrunkImportModel
-side_a_node_id
-  Value error, Router  not found [type=value_error, input_value='', input_type=str]
-    For further information visit https://errors.pydantic.dev/2.7/v/value_error
-side_b_node_id
+        """side_b_node_id
   Value error, Router  not found [type=value_error, input_value='', input_type=str]"""
         in captured_output
     )
diff --git a/test/conftest.py b/test/conftest.py
index 731e0a3c1894d10f73a29cbbc4f6c79ec045108a..233a0921ef67d5b1a58c14619ece9a8b1fb9c129 100644
--- a/test/conftest.py
+++ b/test/conftest.py
@@ -25,7 +25,8 @@ from orchestrator.db import (
 from orchestrator.db.database import ENGINE_ARGUMENTS, SESSION_ARGUMENTS, BaseModel
 from orchestrator.domain import SUBSCRIPTION_MODEL_REGISTRY, SubscriptionModel
 from orchestrator.domain.base import ProductBlockModel
-from orchestrator.types import SubscriptionLifecycle, strEnum
+from orchestrator.types import SubscriptionLifecycle
+from pydantic_forms.types import strEnum
 from sqlalchemy import create_engine, select, text
 from sqlalchemy.engine import make_url
 from sqlalchemy.orm import scoped_session, sessionmaker
@@ -168,9 +169,9 @@ def db_uri():
     database_host = os.getenv("DATABASE_HOST", "localhost")
 
     if worker_id:
-        return f"postgresql://nwa:nwa@{database_host}/gso-test-db_{worker_id}"
+        return f"postgresql+psycopg://nwa:nwa@{database_host}/gso-test-db_{worker_id}"
 
-    return os.environ.get("DATABASE_URI_TEST", f"postgresql://nwa:nwa@{database_host}/gso-test-db")
+    return os.environ.get("DATABASE_URI_TEST", f"postgresql+psycopg://nwa:nwa@{database_host}/gso-test-db")
 
 
 def run_migrations(db_uri: str) -> None:
@@ -211,15 +212,14 @@ def _database(db_uri):
 
     engine = create_engine(url)
     with engine.connect() as conn:
-        conn.execute(text("COMMIT;"))
         conn.execute(
             text("SELECT pg_terminate_backend(pid) FROM pg_stat_activity WHERE datname=:db_name").bindparams(
                 db_name=db_to_create,
             ),
         )
-
-        conn.execute(text(f'DROP DATABASE IF EXISTS "{db_to_create}";'))
-        conn.execute(text("COMMIT;"))
+        conn.commit()
+        conn.execution_options(isolation_level="AUTOCOMMIT").execute(text(f'DROP DATABASE IF EXISTS "{db_to_create}";'))
+        conn.commit()
         conn.execute(text(f'CREATE DATABASE "{db_to_create}";'))
 
     run_migrations(db_uri)
@@ -230,12 +230,13 @@ def _database(db_uri):
     finally:
         db.wrapped_database.engine.dispose()
         with engine.connect() as conn:
-            conn.execute(text("COMMIT;"))
-            # Terminate all connections to the database
             conn.execute(
                 text(f"SELECT pg_terminate_backend(pid) FROM pg_stat_activity WHERE datname='{db_to_create}';"),  # noqa: S608
             )
-            conn.execute(text(f'DROP DATABASE IF EXISTS "{db_to_create}";'))
+            conn.commit()
+            conn.execution_options(isolation_level="AUTOCOMMIT").execute(
+                text(f'DROP DATABASE IF EXISTS "{db_to_create}";')
+            )
 
 
 @pytest.fixture(autouse=True)
diff --git a/test/fixtures.py b/test/fixtures.py
index 4d503bf11c4cb639ba97cf4e0a9a94f8232e2a55..6687d05e1695bfc821cb6a31abb5b331f3a7fad3 100644
--- a/test/fixtures.py
+++ b/test/fixtures.py
@@ -6,9 +6,8 @@ import pytest
 from orchestrator import step, workflow
 from orchestrator.config.assignee import Assignee
 from orchestrator.forms import SubmitFormPage
-from orchestrator.types import UUIDstr
 from orchestrator.workflow import done, init, inputstep
-from pydantic_forms.types import FormGenerator
+from pydantic_forms.types import FormGenerator, UUIDstr
 from pydantic_forms.validators import Choice
 
 from test.workflows import WorkflowInstanceForTests
diff --git a/test/fixtures/lan_switch_interconnect_fixtures.py b/test/fixtures/lan_switch_interconnect_fixtures.py
index 40f95374d3cb04da15995e7ab7601eaadc51a6a4..3879441ee8390cc6d2ee0b7af8a6b11ae8195e5e 100644
--- a/test/fixtures/lan_switch_interconnect_fixtures.py
+++ b/test/fixtures/lan_switch_interconnect_fixtures.py
@@ -3,7 +3,8 @@ from uuid import uuid4
 import pytest
 from orchestrator.db import db
 from orchestrator.domain import SubscriptionModel
-from orchestrator.types import SubscriptionLifecycle, UUIDstr
+from orchestrator.types import SubscriptionLifecycle
+from pydantic_forms.types import UUIDstr
 
 from gso.products import ProductName
 from gso.products.product_blocks.lan_switch_interconnect import (
diff --git a/test/services/subscriptions.py b/test/services/test_subscriptions.py
similarity index 100%
rename from test/services/subscriptions.py
rename to test/services/test_subscriptions.py
diff --git a/test/workflows/__init__.py b/test/workflows/__init__.py
index 4edb847047b22ed4e4201836054a25606cb0f8cc..33a0e3f1a97f07f0c2e9ef27d84951f4fbd7ee8f 100644
--- a/test/workflows/__init__.py
+++ b/test/workflows/__init__.py
@@ -8,12 +8,12 @@ from uuid import uuid4
 import structlog
 from orchestrator.db import ProcessTable, WorkflowTable, db
 from orchestrator.services.processes import StateMerger, _db_create_process
-from orchestrator.types import State
 from orchestrator.utils.json import json_dumps, json_loads
 from orchestrator.workflow import Process, ProcessStat, Step, Success, Workflow, runwf
 from orchestrator.workflow import Process as WFProcess
 from orchestrator.workflows import ALL_WORKFLOWS, LazyWorkflowInstance, get_workflow
 from pydantic_forms.core import post_form
+from pydantic_forms.types import State
 
 from test import LSO_RESULT_FAILURE, LSO_RESULT_SUCCESS, USER_CONFIRM_EMPTY_FORM
 
diff --git a/test/workflows/l3_core_service/test_deploy_prefix_list.py b/test/workflows/l3_core_service/test_deploy_prefix_list.py
new file mode 100644
index 0000000000000000000000000000000000000000..4935a353b1f0b885338d2bc0b8f0f82e8e3e2f87
--- /dev/null
+++ b/test/workflows/l3_core_service/test_deploy_prefix_list.py
@@ -0,0 +1,27 @@
+from unittest.mock import patch
+
+import pytest
+
+from gso.products.product_types.l3_core_service import L3_CORE_SERVICE_TYPES, L3CoreService
+from test.workflows import assert_complete, assert_lso_interaction_success, extract_state, run_workflow
+
+
+@pytest.mark.workflow()
+@patch("gso.services.lso_client._send_request")
+@pytest.mark.parametrize("l3_core_service_type", L3_CORE_SERVICE_TYPES)
+def test_deploy_prefix_list(mock_lso_interaction, l3_core_service_subscription_factory, faker, l3_core_service_type):
+    subscription_id = str(
+        l3_core_service_subscription_factory(l3_core_service_type=l3_core_service_type).subscription_id
+    )
+    initial_l3_core_service_data = [{"subscription_id": subscription_id}]
+    result, process_stat, step_log = run_workflow("deploy_prefix_list", initial_l3_core_service_data)
+    result, step_log = assert_lso_interaction_success(result, process_stat, step_log)
+    result, _ = assert_lso_interaction_success(result, process_stat, step_log)
+    assert_complete(result)
+
+    state = extract_state(result)
+    subscription_id = state["subscription_id"]
+    subscription = L3CoreService.from_subscription(subscription_id)
+    assert subscription.status == "active"
+    assert subscription.insync is True
+    assert mock_lso_interaction.call_count == 2
diff --git a/test/workflows/l3_core_service/test_modify_l3_core_service.py b/test/workflows/l3_core_service/test_modify_l3_core_service.py
index 75cfe87b40114c0554626d6c7682c0a853fda72f..ebcf99339de1391eaaf3f24fc6d90ae74e296756 100644
--- a/test/workflows/l3_core_service/test_modify_l3_core_service.py
+++ b/test/workflows/l3_core_service/test_modify_l3_core_service.py
@@ -70,7 +70,9 @@ def test_modify_l3_core_service_add_new_edge_port_success(
             "gs_id": faker.gs_id(),
             "vlan_id": faker.vlan_id(),
             "ipv4_address": faker.ipv4(),
+            "ipv4_mask": faker.ipv4_netmask(),
             "ipv6_address": faker.ipv6(),
+            "ipv6_mask": faker.ipv6_netmask(),
             "v4_bgp_peer": {
                 "authentication_key": faker.password(),
                 "peer_address": faker.ipv4(),
@@ -91,6 +93,14 @@ def test_modify_l3_core_service_add_new_edge_port_success(
 
     state = extract_state(result)
     subscription = L3CoreService.from_subscription(state["subscription_id"])
+    new_ap = subscription.l3_core_service.ap_list[-1]
+    assert new_ap.ap_type == APType.BACKUP
+    assert new_ap.sbp.gs_id == input_form_data[4]["gs_id"]
+    assert new_ap.sbp.vlan_id == input_form_data[4]["vlan_id"]
+    assert str(new_ap.sbp.ipv4_address) == input_form_data[4]["ipv4_address"]
+    assert new_ap.sbp.ipv4_mask == input_form_data[4]["ipv4_mask"]
+    assert str(new_ap.sbp.ipv6_address) == input_form_data[4]["ipv6_address"]
+    assert new_ap.sbp.ipv6_mask == input_form_data[4]["ipv6_mask"]
     assert len(subscription.l3_core_service.ap_list) == 3
 
 
@@ -102,7 +112,9 @@ def sbp_input_form_data(faker):
             "is_tagged": True,
             "vlan_id": faker.vlan_id(),
             "ipv4_address": faker.ipv4(),
+            "ipv4_mask": faker.ipv4_netmask(),
             "ipv6_address": faker.ipv6(),
+            "ipv6_mask": faker.ipv6_netmask(),
             "custom_firewall_filters": True,
             "v4_bfd_settings": {
                 "bfd_enabled": True,
@@ -175,7 +187,9 @@ def test_modify_l3_core_service_modify_edge_port_success(
         assert subscription.l3_core_service.ap_list[i].sbp.is_tagged == new_sbp_data[i]["is_tagged"]
         assert subscription.l3_core_service.ap_list[i].sbp.vlan_id == new_sbp_data[i]["vlan_id"]
         assert str(subscription.l3_core_service.ap_list[i].sbp.ipv4_address) == new_sbp_data[i]["ipv4_address"]
+        assert subscription.l3_core_service.ap_list[i].sbp.ipv4_mask == new_sbp_data[i]["ipv4_mask"]
         assert str(subscription.l3_core_service.ap_list[i].sbp.ipv6_address) == new_sbp_data[i]["ipv6_address"]
+        assert subscription.l3_core_service.ap_list[i].sbp.ipv6_mask == new_sbp_data[i]["ipv6_mask"]
         assert (
             subscription.l3_core_service.ap_list[i].sbp.custom_firewall_filters
             == new_sbp_data[i]["custom_firewall_filters"]
diff --git a/test/workflows/l3_core_service/test_validate_prefix_list.py b/test/workflows/l3_core_service/test_validate_prefix_list.py
new file mode 100644
index 0000000000000000000000000000000000000000..3e19deee5076c9506082b2e342cc595ae67faff5
--- /dev/null
+++ b/test/workflows/l3_core_service/test_validate_prefix_list.py
@@ -0,0 +1,26 @@
+from unittest.mock import patch
+
+import pytest
+
+from gso.products.product_types.l3_core_service import L3_CORE_SERVICE_TYPES, L3CoreService
+from test.workflows import assert_complete, assert_lso_success, extract_state, run_workflow
+
+
+@pytest.mark.workflow()
+@patch("gso.services.lso_client._send_request")
+@pytest.mark.parametrize("l3_core_service_type", L3_CORE_SERVICE_TYPES)
+def test_validate_prefix_list(mock_lso_interaction, l3_core_service_subscription_factory, faker, l3_core_service_type):
+    subscription_id = str(
+        l3_core_service_subscription_factory(l3_core_service_type=l3_core_service_type).subscription_id
+    )
+    initial_l3_core_service_data = [{"subscription_id": subscription_id}]
+    result, process_stat, step_log = run_workflow("validate_prefix_list", initial_l3_core_service_data)
+    result, step_log = assert_lso_success(result, process_stat, step_log)
+    assert_complete(result)
+
+    state = extract_state(result)
+    subscription_id = state["subscription_id"]
+    subscription = L3CoreService.from_subscription(subscription_id)
+    assert subscription.status == "active"
+    assert subscription.insync is True
+    assert mock_lso_interaction.call_count == 1
diff --git a/test/workflows/router/test_promote_p_to_pe.py b/test/workflows/router/test_promote_p_to_pe.py
index 71ffd639224094a08815f186bcbedba7a4d309ce..46ab40b7fa7215de2b94bbfd3980c5bea0506268 100644
--- a/test/workflows/router/test_promote_p_to_pe.py
+++ b/test/workflows/router/test_promote_p_to_pe.py
@@ -92,7 +92,7 @@ def test_promote_p_to_pe_missing_tt_number(router_subscription_factory):
     with pytest.raises(FormValidationError) as error:
         run_workflow("promote_p_to_pe", [{"subscription_id": router_id}, {}])
     error = error.value.errors[0]
-    assert error["msg"] == "Field required"
+    assert error["msg"] == "field required"
     assert error["loc"][0] == "tt_number"