use crate::components::*;
use leptos::*;
use leptos_meta::*;

#[component]
pub fn Blog(cx: Scope) -> impl IntoView {
    let es_health_green_short = [
        "$ kubectl exec -n <namespace> <elasticsearch-pod> -it -- curl localhost:9200/_cluster/health?pretty | grep status",
        r#"  "status" : "green", # <<<<< Make sure this is green <<<<<"#,
    ].join("\n");

    let es_health_green = [
        "$ kubectl exec -n <namespace> <elasticsearch-pod> -it -- curl localhost:9200/_cluster/health?pretty",
        "{",
        r#"  "cluster_name" : "elastic","#,
        r#"  "status" : "green", # <<<<< Make sure this is green <<<<<"#,
        r#"  "timed_out" : false,"#,
        r#"  "number_of_nodes" : 7,"#,
        r#"  "number_of_data_nodes" : 2,"#,
        r#"  "active_primary_shards" : 202,"#,
        r#"  "active_shards" : 404,"#,
        r#"  "relocating_shards" : 0,"#,
        r#"  "initializing_shards" : 0,"#,
        r#"  "unassigned_shards" : 0,"#,
        r#"  "delayed_unassigned_shards" : 0,"#,
        r#"  "number_of_pending_tasks" : 0,"#,
        r#"  "number_of_in_flight_fetch" : 0,"#,
        r#"  "task_max_waiting_in_queue_millis" : 0,"#,
        r#"  "active_shards_percent_as_number" : 100.0"#,
        "}",
    ].join("\n");
    view! { cx,
        <Title text="Blog - NationTech - Unconventional team for extraordinary challenges"/>
        <div>
        <div class="flex space-y-4 flex-col max-w-3xl container mx-auto">
            <h1 class="text-6xl text-orange-400 font-extrabold pt-12">"Blog"</h1>
            <h2 class="text-3xl">"Modifying storageClass of kubernetes bitnami ElasticSearch cluster without downtime"</h2>
            <p class="">"Thanks Percona for this excellent article "
                <a class="text-orange-400" href="https://www.percona.com/blog/change-storage-class-on-kubernetes-on-the-fly/">"Change Storage Class on Kubernetes on the Fly."</a>
            </p>
            <p class="">"It inspired most of this procedure. Here it is : "</p>
            <h4 class="text-2xl pb-2">"Make sure  your cluster is green "</h4>
            <p>
                "This is obviously the first step, and one we will repeat many times throughout the upgrade procedure."
            </p>
                <CodeBlock>{es_health_green}</CodeBlock>
            <p>
                "If your cluster is not green, refer to "<a class="text-orange-400" href="https://www.elastic.co/guide/en/elasticsearch/reference/current/red-yellow-cluster-status.html">"Elastic's documentation."</a>
            </p>
            <h4 class="text-2xl">"Delete the statefulset with "<Code>"--cascade=orphan"</Code></h4>
            <p>
                "This is where things get interesting. We are combining strengths of K8s and  Helm here. By using the "<Code>"Orphan"</Code>" flag, we are telling K8s to leave the running pods alone. This way we are working around the limitation that prevents us from directly editing the PVC definition within the StatefulSet."
            </p>
            <CodeBlock>"kubectl delete -n <namespace> statefulset --cascade=orphan <statefulset_name>"</CodeBlock>
            <p>
                "See the documentation excerpt for the "
                <Code>"orphan"</Code>
                " option."
            </p>
            <blockquote class="border-l-2 border-white px-4 py-2 mx-4">"By default, when you tell Kubernetes to delete an object, the controller also deletes dependent objects. You can make Kubernetes orphan these dependents using kubectl or the Kubernetes API, depending on the Kubernetes version your cluster runs. To check the version, enter kubectl version."
            <br/>
            <br/>
            <a class="text-orange-400" href="https://kubernetes.io/docs/tasks/administer-cluster/use-cascading-deletion/#set-orphan-deletion-policy">"https://kubernetes.io/docs/tasks/administer-cluster/use-cascading-deletion/#set-orphan-deletion-policy"</a>
            </blockquote>
            <h4 class="text-2xl">"Change the storage class in the helm chart to the new one"</h4>
            <p>
                "In my case, this simply means setting "<Code>"global.storageClass: ceph-block"</Code>
                " on line 19 of my values file. If you have defined the storage class for more specific values in the chart you may have to modify those instead."
            </p>
            <h4 class="text-2xl">"Upgrade the deployment with "<Code>"helm upgrade"</Code></h4>
            <p>
                "This will create a new StatefulSet to replace the old one that has been deleted previously. We are now leveraging the "
                <a class="text-orange-400" href="https://kubernetes.io/docs/concepts/workloads/controllers/statefulset/#stable-network-id">"idempotency of a StatefulSet's pod names"</a>
                ". This will allow the StatefulSet to take ownership of the exact same pod as the previous StatefulSet. That is, unless you changed its name in the chart's configuration, which would break more than only this."
            </p>
            <p>
                "However, since the underlying components (Pods/ReplicaSets) do not support an update to the "
                <Code>"...volumeClaimTemplates[].spec.storageClassName"</Code>
                "Nothing more will be done"
            </p>
            <h4 class="text-2xl">"Delete pods and PVCs"</h4>
            <p>
                "Now the scary part : deleting."
            </p>
            <p>
            "These steps must be done carefully for each pod in the Elastic cluster."
            </p>
            <ol class="list-decimal list-inside">
            <li>"Find the PVC name for the pod to be deleted with "<Code>"kubectl get -n <namespace> pvc"</Code></li>
            <li>"Delete the PVC with "<Code>"kubectl delete -n [namespace] pvc [pvc]"</Code>"This command may hang until the pod is deleted to allow the PVC to be deleted"</li>
            <li>"Validate that the PVC is being deleted "<Code>"kubectl get -n [namespace] pvc [pvc]"</Code></li>
            <li>"Delete the pod associated with the PVC. "<Code>"kubectl delete -n namespace pod [pod]"</Code>" At this point, the StatefulSet will detect that one of his pods is missing and will recreate it with the new spec, that has the new storageClass setting."</li>
            <li>"Now wait until your Elastic cluster comes back to "<Code>"green"</Code>" status"</li>
            </ol>
            <p>
                <Code>"...volumeClaimTemplates[].spec.storageClassName"</Code>
                "Nothing more will be done"
            </p>
        </div>
        </div>
    }
}
