[Yandex Cloud documentation](../../../../index.md) > [Tutorials](../../../index.md) > [Security](../../index.md) > [Migrating services from an NLB to an L7 ALB to enable Smart Web Security protection](../index.md) > [NLB with a Managed Service for Kubernetes cluster as a target](index.md) > Management console

# Migrating services from an NLB with a Yandex Managed Service for Kubernetes cluster as a target to an L7 ALB using the management console

# Migrating services from an NLB with a Yandex Managed Service for Kubernetes cluster as a target to an L7 ALB using the management console


To migrate a service from a network load balancer to an L7 load balancer:

1. [See the service migration recommendations](#recommendations).
1. [Create a migration infrastructure](#before-you-begin).
1. [Create a Smart Web Security profile](#create-profile-sws).
1. [Install an Application Load Balancer ingress controller and create resources in your Managed Service for Kubernetes cluster](#install-ingress-nginx). At this step, you will associate your Smart Web Security profile with the L7 load balancer.
1. [Test the L7 load balancer](#test).
1. [Migrate user traffic from the network load balancer to the L7 load balancer](#migration-nlb-to-alb).

## Service migration recommendations {#recommendations}

1. Optionally, enable L3-L4 DDoS protection (the [OSI model](https://en.wikipedia.org/wiki/OSI_model)). It will enhance the L7 protection provided by [Yandex Smart Web Security](../../../../smartwebsecurity/index.md) after migration.

    To enable L3-L4 protection:

    1. Before the migration, [reserve a public static IP address with DDoS protection](../../../../vpc/operations/enable-ddos-protection.md#enable-on-reservation) and use this address for the L7 load balancer's listener. If you already have a protected public IP address for the load balancer, you can keep this address during migration. Otherwise, you will have to change the IP address to a protected one.

    1. Configure a trigger threshold for the protection mechanisms, consistent with the amount of legitimate traffic to the protected resource. To set up this threshold, contact [support](https://center.yandex.cloud/support).

    1. [Set](../../../../vpc/operations/adjust-mtu-ddos-protection.md) the MTU value to `1450` for the targets downstream of the load balancer. For more information, see [MTU and TCP MSS](../../../../vpc/concepts/mtu-mss.md).

1. Perform migration during the hours when the user load is at its lowest. If you decided to keep your public IP address, your service will be unavailable during the migration while this IP address is moved from the load balancer to the L7 load balancer. This usually takes a few minutes.

1. When using an L7 load balancer, requests to backends come with the source IP address from the range of internal IP addresses of the subnets specified when creating the L7 load balancer. The original IP address of the request source (user) is specified in the `X-Forwarded-For` header. If you want to log public IP addresses of users on the web server, reconfigure it.

1. Before the migration, define the minimum number of resource units for the [autoscaling](../../../../application-load-balancer/concepts/application-load-balancer.md#lcu-scaling) settings in the L7 load balancer:

    Select the number of resource units based on the analysis of your service load expressed in:

    * Number of requests per second (RPS).
    * Number of concurrent active connections.
    * Number of new connections per second.
    * Traffic processed per second.

1. The features of the Application Load Balancer load balancer may differ from those of your load balancer deployed in the Managed Service for Kubernetes cluster. See [Application Load Balancer](../../../../application-load-balancer/tools/k8s-ingress-controller/index.md) ingress controller description and [operating principles](../../../../application-load-balancer/tools/k8s-ingress-controller/principles.md).

1. Set up backend health checks on your Application Load Balancer. With health checks, the load balancer timely spots unavailable backends and reroutes traffic to healthy backends. Once the application is updated, traffic will again be distributed across all backends.

    For more information, see [Tips for configuring Yandex Application Load Balancer health checks](../../../../application-load-balancer/concepts/best-practices.md) and [Annotations (metadata.annotations)](../../../../application-load-balancer/k8s-ref/service-for-ingress.md#annotations).

## Create the infrastructure {#before-you-begin}

1. [Create subnets](../../../../vpc/operations/subnet-create.md) in three availability zones for the L7 load balancer.

1. Create [security groups](../../../../application-load-balancer/tools/k8s-ingress-controller/security-groups.md) that allow the L7 load balancer to receive inbound traffic and send it to the targets and allow the targets to receive inbound traffic from the load balancer.

1. When using HTTPS, [add the TLS certificate](../../../../certificate-manager/operations/import/cert-create.md#create-certificate) of your service to [Yandex Certificate Manager](../../../../certificate-manager/index.md).

1. Optionally, [reserve an L3-L4 DDoS-protected static public IP address](../../../../vpc/operations/get-static-ip.md) for the L7 load balancer.

1. The Managed Service for Kubernetes services used as backends must be of the `NodePort` type. If your service type is different, change it to `NodePort`. For more about this type, see [this Kubernetes guide](https://kubernetes.io/docs/concepts/services-networking/service/#type-nodeport).

## Create a Smart Web Security profile {#create-profile-sws}

[Create a Smart Web Security profile](../../../../smartwebsecurity/operations/profile-create.md) by selecting **From a preset template**.

Use these settings when creating the profile:

* In the **Action for the default base rule** field, select `Allow`.
* For the **Smart Protection** rule, enable **Only logging (dry run)**.

These settings enable logging of traffic information, but no actions will be applied to the traffic. This will reduce the risk of disconnecting users due to profile configuration issues. Further on, you will have the option to disable **Only logging (dry run)** and configure deny rules for your use case in the security profile.

## Install an Application Load Balancer ingress controller and create resources in your Managed Service for Kubernetes cluster {#install-ingress-nginx}

{% note tip %}

We recommend using the new [Yandex Cloud Gwin](../../../../application-load-balancer/tools/gwin/index.md) controller instead of an ALB Ingress controller and Gateway API.

{% endnote %}

1. [Install the Yandex Application Load Balancer](../../../../managed-kubernetes/operations/applications/alb-ingress-controller.md) ingress controller.

1. Create an [IngressClass](../../../../application-load-balancer/k8s-ref/ingress-class.md) resource for the L7 load balancer's Ingress controller:

    1. Create a YAML file and describe the `IngressClass` resource in it.

        `IngressClass` resource example:

        ```yaml
        apiVersion: networking.k8s.io/v1
        kind: IngressClass
        metadata:
          labels:
            app.kubernetes.io/component: controller
          name: ingress-alb
        spec:
          controller: ingress.alb.yc.io/yc-alb-ingress-controller
        ```

    1. Use the following command to create the `IngressClass` resource:

        ```bash
        kubectl apply -f <IngressClass_resource_file>
        ```

1. Create an `Ingress` resource:

    1. Read the descriptions of the [`Ingress`](../../../../managed-kubernetes/alb-ref/ingress.md) resource fields and annotations and see [the example](../../../../managed-kubernetes/tutorials/alb-ingress-controller.md#create-ingress-and-apps).

    1. Create a YAML file and describe the `Ingress` resource in it:

        1. Complete the [annotations](../../../../managed-kubernetes/alb-ref/ingress.md#annotations) section for the L7 load balancer settings:

            * `ingress.alb.yc.io/subnets`: IDs of the subnets in the three availability zones for the L7 load balancer nodes. Specify the IDs separated by commas with no spaces.
            * `ingress.alb.yc.io/security-groups`: ID of one or more security groups for the L7 load balancer. For multiple groups, specify their IDs separated by commas with no spaces.
            * `ingress.alb.yc.io/external-ipv4-address`: Previously reserved static public IP address.
            * `ingress.alb.yc.io/group-name`: Name of the `Ingress` resource group. `Ingress` resources are grouped together, each group served by a separate Application Load Balancer instance with a dedicated public IP address.
            * `ingress.alb.yc.io/security-profile-id`: ID of the previously created Smart Web Security security profile.

                {% note warning %}

                The security profile will be linked to the virtual host of the L7 load balancer. Smart Web Security cannot be made operational without linking a security profile to the L7 load balancer's virtual host.

                {% endnote %}

            * `ingress.alb.yc.io/autoscale-min-zone-size`: [Minimum number of resource units](../../../../application-load-balancer/concepts/application-load-balancer.md#lcu-scaling-settings) per availability zone, based on expected load.

        1. For the `ingressClassName` field, enter the name of the `IngressClass` resource you created earlier.

        1. When using HTTPS, complete the [tls](../../../../managed-kubernetes/alb-ref/ingress.md#tls) section:

            * `hosts`: Your service domain name the TLS certificate corresponds to.
            * `secretName`: TLS certificate of your service in Yandex Certificate Manager, in `yc-certmgr-cert-id-<certificate_ID>` format.

        1. Complete the [rules](../../../../managed-kubernetes/alb-ref/ingress.md#rule) section in line with your rules for distribution of incoming traffic among backends depending on the domain name (`host` field) and requested resource (`http.paths` field).

            * `host`: Your service domain name.
            * `pathType`: Type of reference to the requested resource:

                * `Exact`: Request URI path must match the `path` field value.
                * `Prefix`: Request URI path must start with the `path` field value.

            * `path`: Incoming request URI path (if `Exact`) or its prefix (if `Prefix`).
            * `backend`: Reference to a [backend or group of backends](../../../../managed-kubernetes/alb-ref/ingress.md#backend) to process the requests with the specified domain name and URI path. Specify either a service backend (`service`) or a backend group (`resource`) but not both.

                * `service`: Managed Service for Kubernetes backend service for processing requests:

                    * `name`: Managed Service for Kubernetes service name. The `Service` resource this field refers to must be described in line with [this configuration](../../../../application-load-balancer/k8s-ref/service-for-ingress.md).
                    * `port`: Service port `Ingress` is going to address. For the service port, specify either a number (`number`) or a name (`name`) but not both.

                    {% note warning %}

                    The Managed Service for Kubernetes services used as backends must be of the `NodePort` type.

                    {% endnote %}

                * `resource`: Reference to the `HttpBackendGroup` group of backends to process the requests. A backend group can route traffic to either Managed Service for Kubernetes services or [Yandex Object Storage buckets](../../../../storage/concepts/bucket.md). When using a backend group, advanced Application Load Balancer functionality is available. You can also specify relative backend weights to allocate traffic to them in proportion.

                    * `kind`: `HttpBackendGroup`
                    * `name`: Backend group name. The name must match the value specified in the `metadata.name` field of the `HttpBackendGroup` resource. The `HttpBackendGroup` resource this field refers to must be described in line with [this configuration](../../../../application-load-balancer/k8s-ref/http-backend-group.md).
                    * `apiGroup`: `alb.yc.io`

        `Ingress` resource example:

        ```yaml
        apiVersion: networking.k8s.io/v1
        kind: Ingress
        metadata:
          name: <resource_name>
          annotations:
            ingress.alb.yc.io/subnets: <IDs_of_subnets_in_three_availability_zones>
            ingress.alb.yc.io/security-groups: <L7_load_balancer_security_group_ID>
            ingress.alb.yc.io/external-ipv4-address: <static_public_IP_address>
            ingress.alb.yc.io/group-name: <resource_group_name>
            ingress.alb.yc.io/security-profile-id: <Smart_Web_Security_security_profile_ID>
            ingress.alb.yc.io/autoscale-min-zone-size: <minimum_number_of_L7_load_balancer_resource_units_per_zone>
        spec:
          ingressClassName: <IngressClass_resource_name>
          tls:
            - hosts:
                - <service_domain_name>
              secretName: yc-certmgr-cert-id-<certificate_ID>
          rules:
            - host: <service_domain_name>
              http:
                paths:
                - path: /
                  pathType: Prefix
                  backend:
                    service:
                      name: <Kubernetes_service_name>
                      port:
                        number: <443_or_another_port_number>
        ```

    1. Use the following command to create the `Ingress` resource:

        ```bash
        kubectl apply -f <Ingress_resource_file>
        ```

1. An L7 load balancer will be deployed based on the `Ingress` resource configuration. Wait until its creation is complete and `Ingress` has a public IP address linked. You will need this IP address to check requests. You can view resource info using this command:

    ```bash
    kubectl get ingress <Ingress_resource_name> -w
    ```

## Test the L7 load balancer {#test}

Run a test request to the service through the L7 load balancer, for example, using one of these methods:

* Add this record to the `hosts` file on your workstation: `<L7_load_balancer_public_IP_address> <service_domain_name>`. Delete the record after the test.
* Execute the request using [cURL](https://curl.se/) depending on the protocol type:

    ```bash
    curl http://<service_domain_name> \
        --resolve <service_domain_name>:<service_port>:<public_IP_address_of_L7_load_balancer>
    ```

    ```bash
    curl https://<service_domain_name> \
        --resolve <service_domain_name>:<service_port>:<public_IP_address_of_L7_load_balancer>
    ```

## Migrate user traffic from the network load balancer to the L7 load balancer {#migration-nlb-to-alb}

Select one of these migration options:

* [Keep the public IP address for your service](#save-public-ip).
* [Do not keep the public IP address for your service](#not-save-public-ip).

### Keep the public IP address for your service {#save-public-ip}

1. If your external network load balancer uses a dynamic public IP address, [convert it to a static one](../../../../vpc/operations/set-static-ip.md).

1. [Delete all listeners](../../../../network-load-balancer/operations/listener-remove.md) in the network load balancer to release the static public IP address. This will make your service unavailable through the network load balancer.

1. In the L7 load balancer, assign to the listener the public IP address previously used by the network load balancer:

    1. Open the YAML file that describes the `Ingress` resource.
    1. Under `annotations`, in the `ingress.alb.yc.io/external-ipv4-address` field, specify the public IP address previously assigned to the network load balancer.
    1. Apply the changes using this command:

        ```bash
        kubectl apply -f <Ingress_resource_file>
        ```

1. Wait for the `Ingress` resource to finish switching its public IP address. You can view resource information using this command:

    ```bash
    kubectl get ingress <Ingress_resource_name> -w
    ```

    After the IP address changes, your service will again be available through the L7 load balancer.

1. Navigate to the L7 load balancer:

    1. In the [management console](https://console.yandex.cloud), navigate to the folder with the Managed Service for Kubernetes cluster.
    1. Navigate to **Managed Service for&nbsp;Kubernetes**.
    1. Select the cluster.
    1. Select ![image](../../../../_assets/console-icons/timestamps.svg) **Services and Ingresses** on the left and then the **Ingresses** tab on the right. For your `Ingress` resource, follow the L7 load balancer link in the **Load balancer** column.
    1. Monitor the L7 load balancer's user traffic on the [load balancer statistics](../../../../application-load-balancer/operations/application-load-balancer-get-stats.md) charts.

1. Delete the released static public IP address previously reserved for the L7 load balancer.

1. Optionally, [delete the network load balancer](../../../../network-load-balancer/operations/load-balancer-delete.md) after migrating user traffic to the L7 load balancer.

### Do not keep the public IP address for your service {#not-save-public-ip}

1. To migrate user traffic from a network load balancer to an L7 load balancer, in your domain's public zone DNS service, change the A record for the service domain name to the L7 load balancer's public IP address. If the public domain zone was created in [Yandex Cloud DNS](../../../../dns/index.md), update the record using [this guide](../../../../dns/operations/resource-record-update.md).

    {% note info %}

    The migration may take a while because the propagation of DNS record's updates depends on its time-to-live (TTL) and the number of links in the DNS request chain.

    {% endnote %}

1. As the DNS record updates propagate, monitor the increase in requests to the L7 load balancer.

    1. In the [management console](https://console.yandex.cloud), navigate to the folder with the Managed Service for Kubernetes cluster.
    1. Navigate to **Managed Service for&nbsp;Kubernetes**.
    1. Select the cluster.
    1. Select ![image](../../../../_assets/console-icons/timestamps.svg) **Services and Ingresses** on the left and then the **Ingresses** tab on the right. For your `Ingress` resource, follow the L7 load balancer link in the **Load balancer** column.
    1. Monitor the L7 load balancer's user traffic on the [load balancer statistics](../../../../application-load-balancer/operations/application-load-balancer-get-stats.md) charts.

1. Monitor the decrease in traffic on the network load balancer using the `processed_bytes` and `processed_packets` [load balancer metrics](../../../../monitoring/metrics-ref/network-load-balancer-ref.md). You can [create a dashboard](../../../../monitoring/operations/dashboard/create.md) to visualize these metrics. If there is no load on the network load balancer for a long time, the migration to the L7 load balancer is complete.

1. Optionally, [delete the network load balancer](../../../../network-load-balancer/operations/load-balancer-delete.md) after migrating user traffic to the L7 load balancer.