<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: divya-mohan0209</title>
    <description>The latest articles on DEV Community by divya-mohan0209 (@divyamohan0209).</description>
    <link>https://dev.to/divyamohan0209</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F310715%2Ff35b0d7d-ba20-410b-ac04-f6a272fd8730.jpeg</url>
      <title>DEV Community: divya-mohan0209</title>
      <link>https://dev.to/divyamohan0209</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/divyamohan0209"/>
    <language>en</language>
    <item>
      <title>How KubeSlice implements multi-tenancy in Kubernetes</title>
      <dc:creator>divya-mohan0209</dc:creator>
      <pubDate>Mon, 25 Jul 2022 05:00:00 +0000</pubDate>
      <link>https://dev.to/divyamohan0209/how-kubeslice-implements-multi-tenancy-in-kubernetes-3b03</link>
      <guid>https://dev.to/divyamohan0209/how-kubeslice-implements-multi-tenancy-in-kubernetes-3b03</guid>
      <description>&lt;p&gt;_This is an article originally co-authored by &lt;a href="https://www.linkedin.com/in/olyviar" rel="noopener noreferrer"&gt;Olyvia Rakshit&lt;/a&gt; &amp;amp; I for the Avesha blog. You can find it by following &lt;a href="https://avesha.io/blogs/how-kubeslice-implements-multi-tenancy/" rel="noopener noreferrer"&gt;this link&lt;/a&gt;.&lt;br&gt;
_&lt;/p&gt;
&lt;h2&gt;
  
  
  What is Multi-tenancy in Kubernetes?
&lt;/h2&gt;

&lt;p&gt;Multi-tenancy in &lt;a href="https://kubernetes.io" rel="noopener noreferrer"&gt;Kubernetes&lt;/a&gt; is a way to deploy multiple workloads in a shared cluster with isolated network traffic, resources, user access, and last but not least control plane access. Such tenancy is needed &lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;by SaaS providers for their customers who orchestrate containers using Kubernetes, &lt;/li&gt;
&lt;li&gt;by teams in an enterprise who have different functions or &lt;/li&gt;
&lt;li&gt;by applications which have specific compliance or performance requirements.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Similar to virtualization in the compute world, multi-tenancy in Kubernetes is a form of virtual cluster on a physical cluster.&lt;/p&gt;

&lt;p&gt;Or to look at it from a different perspective, multi-tenancy in Kubernetes is very similar to multiple tenants in real estate such as in an apartment complex or shared office centers.&lt;/p&gt;
&lt;h2&gt;
  
  
  The use case for multi-tenancy
&lt;/h2&gt;

&lt;p&gt;When we talk about multi-tenancy in the real world, it is not difficult to picture why it is required. Let’s take the example of an apartment complex where several isolated apartments are leased out to several customers sharing the same resources. Contrast this with a single family purchasing the same real estate and building a single house.&lt;/p&gt;

&lt;p&gt;More individuals and families can be accommodated within a complex. An equitable sharing of resources like electricity, water etc in an isolated manner can be achieved among people living in different apartments. In case of a single tenant building a house on the same plot of land, there’d be limited sharing capabilities – whether it be in the case of real estate or resources. Therefore from the perspective of making a profit during a sale and ensuring efficient occupancy, it can be argued the first option is definitely better.&lt;/p&gt;

&lt;p&gt;In the case of application deployments, going by the analogy above, it’s always efficient to pack multiple tenants in the same infrastructure.&lt;/p&gt;

&lt;p&gt;Moving over to the Kubernetes world, due to efficiencies gained by Kubernetes, organizations are rapidly transitioning their application architectures from monoliths to microservices.. Kubernetes clusters, with release 1.24, can have upto 5000 nodes, 110 pods per node, and 150000 total pods.&lt;/p&gt;

&lt;p&gt;With multiple teams needing to have a dedicated cluster or set of clusters, platform teams managing the clusters have to deal with increased costs of running a farm of clusters, copies of tooling associated with operating clusters, and optimizing unused capacity in clusters. Add to it the fact that the Kubernetes control plane (master node) is required to scale horizontally along with the increase in workloads and we know why having multiple tenants or “multi-tenancy” would make more sense in the context of Kubernetes clusters.&lt;/p&gt;
&lt;h2&gt;
  
  
  Benefits of a multi-tenant approach
&lt;/h2&gt;

&lt;p&gt;Multi-tenancy in Kubernetes helps bring cost savings by reducing the footprint of the control plane and by optimizing node capacity across multiple teams or multiple customers. It can be achieved by either using a shared node pool across teams (compute is cheaper at scale) or&lt;br&gt;
dedicating some set of nodes to a tenant when needed. If you consider an on-prem deployment, dedicating servers to a tenant will increase costs and will not take optimal advantage of the Kubernetes scheduler bin packing algorithm for optimal workload placement.&lt;/p&gt;

&lt;p&gt;Multi-tenancy also brings operational cost savings by consolidating different tools sets for managing, visibility and operating clusters. Optimizing a single cluster is complex. If one deploys a cluster per tenant, operating and optimizing will be difficult and increases the operational burden by many folds.&lt;/p&gt;

&lt;p&gt;Multi-tenancy helps spin up new customers or new teams instantly and easily along with the associated tooling. This means you don’t have to bring all new infrastructure for each tenant! It also helps reduce complexity of configuration maintenance and security validation for multiple clusters.&lt;/p&gt;

&lt;p&gt;In summary by implementing multi-tenancy in Kubernetes clusters you gain:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Cost savings&lt;/li&gt;
&lt;li&gt;Reduce operational overhead&lt;/li&gt;
&lt;li&gt;Improves continuous delivery at scale&lt;/li&gt;
&lt;/ul&gt;
&lt;h2&gt;
  
  
  Enter KubeSlice!
&lt;/h2&gt;

&lt;p&gt;&lt;a href="https://kubeslice.io" rel="noopener noreferrer"&gt;‘KubeSlice’&lt;/a&gt; combines network, application, and deployment services in a framework to create tenancy in a Kubernetes cluster and extends it to multi-cluster.&lt;/p&gt;

&lt;p&gt;KubeSlice creates logical application boundaries known as “slices” that allow pods and services to communicate seamlessly across clusters, clouds, edges, and data centers regardless of their physical location. Each slice is assigned its own set of namespaces, resource quotas, traffic profiles that creates an “isolated virtual network” for each tenant (a team or a customer) in a single cluster or multiple clusters.&lt;/p&gt;

&lt;p&gt;KubeSlice drives provisioning and management of tenants via a Controller which is isolated functionally from workloads deployed by product teams via a worker cluster. As Kubernetes defines a control plane for orchestrating containers in worker nodes, KubeSlice’s control plane is defined as ‘Controller’.&lt;/p&gt;
&lt;h2&gt;
  
  
  KubeSlice in action
&lt;/h2&gt;

&lt;p&gt;Installing KubeSlice on any distribution of Kubernetes is done via Helm charts. Tenancy driven by KubeSlice can be attained in a few simple steps after the initial installation of the ‘Controller’ subsystem.&lt;/p&gt;

&lt;p&gt;KubeSlice is divided into two components: A control cluster and a group of worker clusters. The control cluster is the control plane managing worker clusters either in public clouds (multi cloud support) or clusters on-prem. The controllers job is to manage tenancy creation, establishment of isolation, creation of overlay network across worker clusters for a tenant, RBAC functionality for a tenant, resource allocation to a tenant and much more.&lt;/p&gt;
&lt;h2&gt;
  
  
  Steps for Establishing Tenancy
&lt;/h2&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fd9pocz583wdfbtmifzh0.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fd9pocz583wdfbtmifzh0.png" alt="A multi-cluster multi-tenant model showing Team Athena Slice and Team Zeus Slice"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;em&gt;&lt;p&gt;A multi-cluster multi-tenant model showing Team Athena Slice and Team Zeus Slice&lt;/p&gt;&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;1) Register cluster or set of clusters&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;This step defines Kubernetes clusters to be managed by Controller for creation of tenancy / Isolation for teams or customers.&lt;/p&gt;

&lt;p&gt;First step is to register the clusters with the Controller.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="s"&gt;—------&lt;/span&gt;
&lt;span class="na"&gt;Cluster 1&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;aws-us-east-prod-cluster&lt;/span&gt;
&lt;span class="s"&gt;—-------&lt;/span&gt;
&lt;span class="na"&gt;apiVersion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;controller.kubeslice.io/v1alpha1&lt;/span&gt;
&lt;span class="na"&gt;kind&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Cluster&lt;/span&gt;
&lt;span class="na"&gt;metadata&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;

&lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;aws-us-east-prod-cluster&lt;/span&gt;
&lt;span class="na"&gt;namespace&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;kubeslice-acme&lt;/span&gt;
&lt;span class="na"&gt;spec&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;networkInterface&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;eth0&lt;/span&gt;
&lt;span class="na"&gt;clusterProperty&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;telemetry&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;enabled&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;
&lt;span class="na"&gt;telemetryProvider&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;prometheus"&lt;/span&gt;
&lt;span class="na"&gt;endpoint&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;http://30.2.44.110:32700"&lt;/span&gt; &lt;span class="c1"&gt;## For example: "http://extrenal IP:32700"&lt;/span&gt;
&lt;span class="na"&gt;geoLocation&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;cloudProvider&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;AWS"&lt;/span&gt;
&lt;span class="na"&gt;cloudRegion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;us-east-1a"&lt;/span&gt;
&lt;span class="s"&gt;—-----&lt;/span&gt;
&lt;span class="na"&gt;Cluster 2&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;gcp-us-east-prod-cluster&lt;/span&gt;
&lt;span class="s"&gt;—-------&lt;/span&gt;
&lt;span class="na"&gt;apiVersion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;controller.kubeslice.io/v1alpha1&lt;/span&gt;
&lt;span class="na"&gt;kind&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Cluster&lt;/span&gt;
&lt;span class="na"&gt;metadata&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;gcp-us-east-prod-cluster&lt;/span&gt;
&lt;span class="na"&gt;namespace&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;kubeslice-acme&lt;/span&gt;
&lt;span class="na"&gt;spec&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;networkInterface&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;eth0&lt;/span&gt;
&lt;span class="na"&gt;clusterProperty&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;telemetry&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;enabled&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;
&lt;span class="na"&gt;telemetryProvider&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;prometheus"&lt;/span&gt;
&lt;span class="na"&gt;endpoint&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;http://25.4.32.210:32700"&lt;/span&gt; &lt;span class="c1"&gt;## For example: "http://extrenal IP:32700"&lt;/span&gt;
&lt;span class="na"&gt;geoLocation&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;cloudProvider&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;GCP"&lt;/span&gt;
&lt;span class="na"&gt;cloudRegion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;us-east"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Command Execution&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;kubectl apply &lt;span class="nt"&gt;-f&lt;/span&gt; &amp;lt;cluster registration&amp;gt;.yaml &lt;span class="nt"&gt;-n&lt;/span&gt; kubeslice-&amp;lt;project namespace&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;2) Install KubeSlice operator in above registered clusters&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Edit below YAML file with information&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="c1"&gt;## Base64 encoded secret values from controller cluster&lt;/span&gt;
&lt;span class="na"&gt;controllerSecret&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;namespace&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;&amp;lt;namespace&amp;gt;&lt;/span&gt;
&lt;span class="na"&gt;endpoint&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;base64 value of the &amp;lt;controller endpoint&amp;gt;&lt;/span&gt;
&lt;span class="na"&gt;ca.crt&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;&amp;lt;ca-cert&amp;gt;&lt;/span&gt;

&lt;span class="na"&gt;token&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;&amp;lt;token&amp;gt;&lt;/span&gt;
&lt;span class="na"&gt;cluster&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;&amp;lt;worker cluster&amp;gt;&lt;/span&gt;
&lt;span class="na"&gt;endpoint&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;&amp;lt;endpoint of control plane of the worker cluster&amp;gt;&lt;/span&gt;
&lt;span class="c1"&gt;# Provide your username, password &amp;amp; email values under imagePullSecrets to create a&lt;/span&gt;
&lt;span class="s"&gt;secret&lt;/span&gt;
&lt;span class="na"&gt;imagePullSecrets&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;repository&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;https://index.docker.io/v1/&lt;/span&gt;
&lt;span class="na"&gt;username&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;&amp;lt;username&amp;gt;&lt;/span&gt;
&lt;span class="na"&gt;password&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;&amp;lt;accesstoken of the user&amp;gt;&lt;/span&gt;
&lt;span class="na"&gt;email&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;&amp;lt;email ID&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Command Execution&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;helm &lt;span class="nb"&gt;install &lt;/span&gt;kubeslice-worker kubeslice/kubeslice-worker &lt;span class="nt"&gt;-f&lt;/span&gt; &amp;lt;values&amp;gt;.yaml &lt;span class="nt"&gt;--&lt;/span&gt;
namespace kubeslice-system &lt;span class="nt"&gt;--create-namespace&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;3) Install Slice on the two clusters&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;After registering the cluster or a set of clusters by following the step above, one is ready to create a slice on a cluster or a set of clusters. By adding more than one cluster KubeSlice will automatically establish connectivity across clusters.&lt;/p&gt;

&lt;p&gt;The YAML file below helps to create two tenants for two teams in the clusters registered. The teams ‘Team Athena’ &amp;amp; ‘Team Zeus’ will share the clusters in AWS and GCP.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="s"&gt;—-----&lt;/span&gt;
&lt;span class="na"&gt;Slice 1&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;team-athena&lt;/span&gt;
&lt;span class="s"&gt;—-------&lt;/span&gt;
&lt;span class="na"&gt;apiVersion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;controller.kubeslice.io/v1alpha1&lt;/span&gt;
&lt;span class="na"&gt;kind&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;SliceConfig&lt;/span&gt;
&lt;span class="na"&gt;metadata&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;team-athena&lt;/span&gt;
&lt;span class="na"&gt;namespace&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;kubeslice-acme&lt;/span&gt;
&lt;span class="na"&gt;spec&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;sliceSubnet&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;“192.168.0.0/16”&lt;/span&gt;
&lt;span class="na"&gt;sliceType&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Application&lt;/span&gt;
&lt;span class="na"&gt;sliceGatewayProvider&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;sliceGatewayType&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;OpenVPN&lt;/span&gt;
&lt;span class="na"&gt;sliceCaType&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Local&lt;/span&gt;
&lt;span class="na"&gt;sliceIpamType&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Local&lt;/span&gt;
&lt;span class="na"&gt;clusters&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;

&lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s"&gt;aws-us-east-prod-cluster&lt;/span&gt;
&lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s"&gt;gcp-us-east-prod-cluster&lt;/span&gt;
&lt;span class="na"&gt;qosProfileDetails&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;queueType&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;HTB&lt;/span&gt;
&lt;span class="na"&gt;priority&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1&lt;/span&gt; &lt;span class="c1"&gt;#keep integer values from 0 to 3&lt;/span&gt;
&lt;span class="na"&gt;tcType&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;BANDWIDTH_CONTROL&lt;/span&gt;
&lt;span class="na"&gt;bandwidthCeilingKbps&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;5120&lt;/span&gt;
&lt;span class="na"&gt;bandwidthGuaranteedKbps&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;2560&lt;/span&gt;
&lt;span class="na"&gt;dscpClass&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;AF11&lt;/span&gt;
&lt;span class="na"&gt;namespaceIsolationProfile&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;applicationNamespaces&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;namespace&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;identity-application&lt;/span&gt;
&lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;namespace&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;identity-db-cache&lt;/span&gt;
&lt;span class="na"&gt;clusters&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s1"&gt;'&lt;/span&gt;&lt;span class="s"&gt;*'&lt;/span&gt;
&lt;span class="na"&gt;isolationEnabled&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;#make this true in case you want to enable isolation&lt;/span&gt;
&lt;span class="na"&gt;allowedNamespaces&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;namespace&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;kube-system&lt;/span&gt;
&lt;span class="na"&gt;clusters&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s1"&gt;'&lt;/span&gt;&lt;span class="s"&gt;*'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;A second slice for a different team who needs infrastructure but would like to not have any linkage with teams in the same organization. A cost effective way of sharing resources and still maintaining strict isolation from network, access, and resources can be achieved by creating a slice (tenant) on the same clusters.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="s"&gt;—-----&lt;/span&gt;
&lt;span class="na"&gt;Slice 2&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;team-zeus&lt;/span&gt;
&lt;span class="s"&gt;—-------&lt;/span&gt;
&lt;span class="na"&gt;apiVersion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;controller.kubeslice.io/v1alpha1&lt;/span&gt;
&lt;span class="na"&gt;kind&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;SliceConfig&lt;/span&gt;
&lt;span class="na"&gt;metadata&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;team-zeus&lt;/span&gt;
&lt;span class="na"&gt;namespace&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;kubeslice-acme&lt;/span&gt;
&lt;span class="na"&gt;spec&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;sliceSubnet&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;“192.168.0.0/16”&lt;/span&gt;
&lt;span class="na"&gt;sliceType&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Application&lt;/span&gt;
&lt;span class="na"&gt;sliceGatewayProvider&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;sliceGatewayType&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;OpenVPN&lt;/span&gt;
&lt;span class="na"&gt;sliceCaType&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Local&lt;/span&gt;
&lt;span class="na"&gt;sliceIpamType&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Local&lt;/span&gt;
&lt;span class="na"&gt;clusters&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s"&gt;aws-us-east-prod-cluster&lt;/span&gt;

&lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s"&gt;gcp-us-east-prod-cluster&lt;/span&gt;
&lt;span class="na"&gt;qosProfileDetails&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;queueType&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;HTB&lt;/span&gt;
&lt;span class="na"&gt;priority&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;2&lt;/span&gt; &lt;span class="c1"&gt;#keep integer values from 0 to 3&lt;/span&gt;
&lt;span class="na"&gt;tcType&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;BANDWIDTH_CONTROL&lt;/span&gt;
&lt;span class="na"&gt;bandwidthCeilingKbps&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;5120&lt;/span&gt;
&lt;span class="na"&gt;bandwidthGuaranteedKbps&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;2560&lt;/span&gt;
&lt;span class="na"&gt;dscpClass&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;AF11&lt;/span&gt;
&lt;span class="na"&gt;namespaceIsolationProfile&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="na"&gt;applicationNamespaces&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;namespace&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;analytics-application&lt;/span&gt;
&lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;namespace&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;analytics-db&lt;/span&gt;
&lt;span class="na"&gt;clusters&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s1"&gt;'&lt;/span&gt;&lt;span class="s"&gt;*'&lt;/span&gt;
&lt;span class="na"&gt;isolationEnabled&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;#make this true in case you want to enable isolation&lt;/span&gt;
&lt;span class="na"&gt;allowedNamespaces&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;namespace&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;kube-system&lt;/span&gt;
&lt;span class="na"&gt;clusters&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
&lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s1"&gt;'&lt;/span&gt;&lt;span class="s"&gt;*'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;With the actions above, we have created TWO TENANTS (&lt;strong&gt;team-athena&lt;/strong&gt;, &lt;strong&gt;team-zeus&lt;/strong&gt;) across &lt;strong&gt;TWO CLUSTERS&lt;/strong&gt; based on two different cloud providers. (&lt;strong&gt;aws-us-east-prod-clust&lt;/strong&gt;, &lt;strong&gt;gcp-us-east-prod-cluster&lt;/strong&gt;)&lt;/p&gt;

&lt;p&gt;We’d love for you to &lt;a href="https://github.com/kubeslice/examples" rel="noopener noreferrer"&gt;try out KubeSlice&lt;/a&gt; and provide us feedback! If you run into any issues, we hang out in the #kubeslice channel on the &lt;a href="https://slack.k8s.io" rel="noopener noreferrer"&gt;Kubernetes&lt;/a&gt; slack. To keep up with the latest updates on KubeSlice, follow us on &lt;a href="https://twitter.com/kubeslice" rel="noopener noreferrer"&gt;Twitter&lt;/a&gt; and &lt;a href="https://reddit.com/user/kubeslice" rel="noopener noreferrer"&gt;Reddit&lt;/a&gt;.&lt;/p&gt;

</description>
      <category>kubernetes</category>
      <category>kubeslice</category>
      <category>multitenancy</category>
      <category>cloud</category>
    </item>
    <item>
      <title>A primer on WebAssembly</title>
      <dc:creator>divya-mohan0209</dc:creator>
      <pubDate>Thu, 06 Jan 2022 04:43:19 +0000</pubDate>
      <link>https://dev.to/divyamohan0209/a-primer-on-webassembly-36dj</link>
      <guid>https://dev.to/divyamohan0209/a-primer-on-webassembly-36dj</guid>
      <description>&lt;p&gt;&lt;em&gt;This first appeared on &lt;a href="https://divya-mohan0209.medium.com/a-primer-on-webassembly-834150fdd7ae"&gt;my Medium blog&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;As detailed in this &lt;a href="https://www.linkedin.com/posts/divya-mohan0209_why-wait-for-2022-to-set-goals-when-you-can-activity-6877972221831327744-46gt"&gt;LinkedIn post&lt;/a&gt;, 2022 is going to be my year of diving into the world of WebAssembly and Rust. With an overwhelming amount of people opting for blog content over other media, here’s the first one in, what I hope will be, a series of posts covering the aforementioned topics.&lt;/p&gt;

&lt;p&gt;Although this has been covered in various formats across the internet, I believe any content about a new technology or tool should start with the motivations behind its inception. To understand why there was a requirement for WebAssembly, let’s take a not-so-quick stroll down memory lane.&lt;/p&gt;

&lt;h2&gt;
  
  
  History of the WWW
&lt;/h2&gt;

&lt;p&gt;The world wide web, as we know it today, started off as a single page project on a NeXT computer at CERN. You can still view it &lt;a href="http://info.cern.ch/hypertext/WWW/TheProject.html"&gt;here&lt;/a&gt;. The page was a simple static page written in HTML and contained links to the project and a few other technical details. The motivation behind this project was to enable information sharing between academics via a document exchange network.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--XGEVeGWI--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/xx5g40swp1ezf4g1934o.jpg" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--XGEVeGWI--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/xx5g40swp1ezf4g1934o.jpg" alt="The very first webpage, CREDIT: CERN" width="880" height="654"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;As you probably noticed above, the very first browser wasn’t radically different from the browsers we use today. However, the interactive nature of web content has definitely seen a drastic change ever since. With its ubiquity and maturation, there was a requirement for the content being made available to be more sophisticated and for it to be rendered on different operating systems &amp;amp; devices. This obviously meant interacting with and accessing various elements within the HTML document and one of the frontrunners in this space was JavaScript.&lt;/p&gt;

&lt;h2&gt;
  
  
  Enter.. JavaScript
&lt;/h2&gt;

&lt;p&gt;Created in 1995 with a name aimed to capitalize on the widespread adoption of Java, JavaScript had a very low barrier to entry. This meant that even someone who was fairly non-technical could use it to introduce interactivity into their webpage. This contributed to its prominence and rise as a de facto compilation target against competitors like ActiveX, Adobe Flash, JavaBeans etc.&lt;/p&gt;

&lt;p&gt;But with this uninhibited rise, there were several challenges as well. JavaScript is an interpreted language. In simple terms, the functions you write are bundled and minified into a source file. Sent as plain text to the Client’s browser, this needs to be parsed into &lt;a href="https://en.wikipedia.org/wiki/Abstract_syntax_tree"&gt;Abstract Syntax Trees&lt;/a&gt;, compiled into bytecode and then executed by the interpreter. The browser’s &lt;a href="https://en.wikipedia.org/wiki/JavaScript_engine"&gt;JavaScript engine&lt;/a&gt; then spots any potential optimizations via methods such as JIT Compilation allowing for eventual optimization. Keyword here being eventual since it’s a long drawn process with speed as an end goal.&lt;br&gt;
However, the concerns with speed were not only limited to the convoluted process to get there. For more challenging applications where performance is a critical factor, the lack of consistency/predictability in the levels of performance was a significant obstacle.&lt;/p&gt;

&lt;p&gt;Additionally, with the popularity of the web, there has been an even greater rush to bring more sophisticated languages into the fray. In the absence of plugins, using JavaScript as a compilation target was the only option. Being an interpreted language itself, the above operations were made complicated due to the amount of efforts required if they were to be achieved efficiently.&lt;/p&gt;

&lt;h2&gt;
  
  
  asm.js
&lt;/h2&gt;

&lt;p&gt;Introduced as a subset of JavaScript, the &lt;a href="http://asmjs.org/spec/latest/"&gt;asm.js specification&lt;/a&gt; aimed at describing a sandboxed virtual machine for memory-unsafe languages like C or C++ and provide a low-level, efficient target language for compilers. Implemented first by the Mozilla Firefox browser, this spec introduced performance improvements via employment of ahead-of-time optimizing compilation strategy for valid asm.js code by the JavaScript engines.&lt;/p&gt;

&lt;p&gt;Quoting &lt;a href="https://developer.mozilla.org/en-US/docs/Games/Tools/asm.js?source=post_page"&gt;Mozilla docs&lt;/a&gt;,&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;It is a very small, strict subset of JavaScript that only allows things like &lt;code&gt;while&lt;/code&gt;, &lt;code&gt;if&lt;/code&gt;, numbers, top-level named functions, and other simple constructs. It does not allow objects, strings, closures, and basically anything that requires heap allocation. Asm.js code resembles C in many ways, but it’s still completely valid JavaScript that will run in all current engines&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;While asm.js was an improvement on the performance front, it was still limited to the things that were expressible in JavaScript. Being an informal spec of JavaScript and not an actual standard, every vendor optimized it in a way they saw fit. Although it did lead to &lt;a href="https://hacks.mozilla.org/2015/03/asm-speedups-everywhere/"&gt;an eventual convergence&lt;/a&gt;, there definitely was room for improvement with respect to standardization.&lt;/p&gt;

&lt;h2&gt;
  
  
  Enter… WebAssembly
&lt;/h2&gt;

&lt;p&gt;Building upon the experience from asm.js, all major browsers worked towards designing a new format for the Web with one of the end goals being speed and efficiency.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;WebAssembly, abbreviated Wasm, was designed to be a portable compilation target for programming languages, enabling deployment on the web for client and server applications.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;So what exactly is &lt;a href="https://webassembly.org/"&gt;WebAssembly&lt;/a&gt;? It is a binary instruction format for stack based machines. Here’s a partial snippet of how a simple “Hello world” program looks like in Wasm.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--17xdQcpI--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/iyph6v4g15ftufl9rs5p.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--17xdQcpI--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/iyph6v4g15ftufl9rs5p.png" alt="Hello, World in WASM" width="880" height="402"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;As is evident in the above snippet, this is closer to machine code than either asm.js or JavaScript. Therefore, it is a no-brainer that decoding, compiling, fetching, and optimizing WebAssembly code takes lesser time. Why?&lt;/p&gt;

&lt;p&gt;The typical amount of time a JavaScript Engine takes during startup for an application today is depicted below.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--NlqkMxHG--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/xrl6kc85tka5kwr9it60.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--NlqkMxHG--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/xrl6kc85tka5kwr9it60.png" alt="Startup performance of JS engine" width="880" height="201"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Although the tasks have been separated above for pictorial depiction, in reality they weave into each other and are not discrete. With larger JavaScript applications, of course the overhead of monitoring and compiling the code increases.&lt;/p&gt;

&lt;p&gt;Contrast that with how a typical WebAssembly flow looks like.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--0lq834-A--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/0bry00c7agcdu0a1xpx7.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--0lq834-A--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/0bry00c7agcdu0a1xpx7.png" alt="WebAssembly Startup flow" width="694" height="193"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;There’s not only a marked difference in the amount of time being spent on account of it being closer to the machine code, but there is also an elimination of certain steps altogether. This obviously leads to better performances in comparison for most cases but not all, since WebAssembly is still in its nascent stages (the MVP was completed in 2017).&lt;/p&gt;

&lt;p&gt;But wait.. does that mean developers will now be expected to write entire codebases in WebAssembly instead of JavaScript? Since this is a like-to-like comparison, the obvious answer to this question would have been a yes. But that is not the case! It is expected that a majority of Wasm developers will continue to code in languages like Rust, C, etc. and then compile to WebAssembly so that users can reap its performance benefits.&lt;/p&gt;

&lt;p&gt;So that’s it for this post! Here’s a list of resources that helped me along the way while learning,&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://hacks.mozilla.org/"&gt;The Mozilla Hacks blog&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://learning.edx.org/course/course-v1:LinuxFoundationX+LFD133x+1T2021/home"&gt;This free course&lt;/a&gt; by The Linux Foundation on edX&lt;/li&gt;
&lt;li&gt;&lt;a href="https://blog.sessionstack.com/"&gt;The sessionstack blog&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://home.cern/science/computing/birth-web/short-history-web"&gt;CERN webpage&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://developer.mozilla.org/en-US/docs/WebAssembly"&gt;MDN Web Docs&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;To stay updated with my latest tech shenanigans, do follow me on &lt;a href="https://twitter.com/Divya_Mohan02"&gt;Twitter&lt;/a&gt; and &lt;a href="https://www.linkedin.com/in/divya-mohan0209/"&gt;LinkedIn&lt;/a&gt;.&lt;/p&gt;

</description>
      <category>webassembly</category>
      <category>webdev</category>
      <category>javascript</category>
      <category>beginners</category>
    </item>
    <item>
      <title>Signing your git commits (for Windows users)</title>
      <dc:creator>divya-mohan0209</dc:creator>
      <pubDate>Thu, 09 Dec 2021 13:33:49 +0000</pubDate>
      <link>https://dev.to/divyamohan0209/signing-your-git-commits-for-windows-users-3k5k</link>
      <guid>https://dev.to/divyamohan0209/signing-your-git-commits-for-windows-users-3k5k</guid>
      <description>&lt;p&gt;We may not have the blue tick mark against our Twitter handles, but that should not stop us from verifying our commits on GitHub. After all, a verified account somewhere is better than none at all!&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--I-KJAQq5--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/yjj5k9f22r2qm9bn4glu.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--I-KJAQq5--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/yjj5k9f22r2qm9bn4glu.png" alt="Look ma, GitHub verified me!" width="831" height="49"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Why do I need to sign my commits?
&lt;/h2&gt;

&lt;p&gt;There are tons of great articles on the internet, especially &lt;a href="https://www.freecodecamp.org/news/what-is-commit-signing-in-git/"&gt;this one at freeCodeCamp&lt;/a&gt; by &lt;a href="https://www.freecodecamp.org/news/author/seth/"&gt;Seth Falco&lt;/a&gt; where the author explains it better than I ever can. &lt;/p&gt;

&lt;h2&gt;
  
  
  So why is this targeted at Windows users specifically?
&lt;/h2&gt;

&lt;p&gt;Good question.&lt;/p&gt;

&lt;p&gt;Reason #1: I use Windows. &lt;/p&gt;

&lt;p&gt;Reason #2: Everything is 100 times more complicated with Windows, IMHO, because there'll never be enough &lt;a href="https://stackoverflow.com/"&gt;stackoverflow&lt;/a&gt; posts covering it.&lt;/p&gt;

&lt;h2&gt;
  
  
  Fair enough, how do I get started?
&lt;/h2&gt;

&lt;p&gt;Please note as of writing, GitHub Desktop &lt;strong&gt;DOES NOT&lt;/strong&gt; support signing commits per &lt;a href="https://docs.github.com/en/authentication/managing-commit-signature-verification/signing-commits"&gt;their official documentation&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Step #1: Download &lt;a href="https://www.gpg4win.org/"&gt;gpg4win&lt;/a&gt;. &lt;br&gt;
Step #2: After running the exe file, this is one of the very first pages of setup that you will come across. Please ensure that Kleopatra is selected during this step. We will need it later.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--dHDlcQA3--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/imtp3yiv3tnvyaze2wee.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--dHDlcQA3--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/imtp3yiv3tnvyaze2wee.png" alt="Setup Kleopatra" width="742" height="574"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Step #3: Click install &amp;amp; finish the installation. You should see a Kleopatra icon on your desktop as shown below.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--KfEk_EWn--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/2dsms6j2ndubra77xv88.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--KfEk_EWn--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/2dsms6j2ndubra77xv88.png" alt="Kleopatra icon" width="187" height="138"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Step #4: Open the Kleopatra management tool &amp;amp; create your very first key pair by clicking File -&amp;gt; New Key Pair. Select the personal OpenPGP key pair in the dialog box that pops up.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--k9JLTuQk--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/w7z64y41y9wq1q8nkj7u.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--k9JLTuQk--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/w7z64y41y9wq1q8nkj7u.png" alt="OpenPGP key pair" width="880" height="378"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Step #5: When you click Next, you'll be asked to enter some details. In the section against Name, I recommend entering your GitHub ID. In the email section, it's obviously a no-brainer at this point that you need to enter the one that is registered with GitHub.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--vm70uzjP--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/q5v5f5po330vhrx5j7kj.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--vm70uzjP--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/q5v5f5po330vhrx5j7kj.png" alt="Details" width="880" height="514"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Step #6: This step is optional, however you can change the validity period of the key you create. Default setting as of writing this is two years. &lt;/p&gt;

&lt;p&gt;Step #7: Click create. You'll get a dialog box where the fingerprint of the key you just created will be made visible to you.&lt;/p&gt;

&lt;p&gt;Step #8: This is one of the most important steps. So please ensure you follow it closely. On the Kleopatra console, you should now see the key you just created. Right click on it and select export. Save it &amp;amp; open it with a editor of your choice. I used Notepad because of its ease. Copy the contents of the file and navigate to your GitHub account.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--ppEBqoiJ--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/jpatyfedq9cwv3eikit7.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--ppEBqoiJ--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/jpatyfedq9cwv3eikit7.png" alt="Very important!" width="540" height="579"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Step #9: Under Settings -&amp;gt; SSH and GPG keys, click Add New GPG key &amp;amp; paste the contents from the file you just copied.&lt;/p&gt;

&lt;p&gt;Step #10: Time to setup your CLI! You can use Git Bash or command prompt. I use the latter out of habit. On the prompt window, copy &amp;amp; paste the below command as is.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git config commit.gpgsign &lt;span class="nb"&gt;true&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Step #11: If you want to enable the same keypair for signing any local repository on your machine, copy &amp;amp; paste the below command as is.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git config &lt;span class="nt"&gt;--global&lt;/span&gt; commit.gpgsign &lt;span class="nb"&gt;true&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Step #12: So Windows is a tricky operating system and even if you follow all of the above steps, you still might not end up being able to sign your commits properly. This typically happens because git is not able to find the key you just generated. So, firstly let's list the keys you generated with gpg.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;gpg &lt;span class="nt"&gt;--list-secret-keys&lt;/span&gt; &lt;span class="nt"&gt;--keyid-format&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;long
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Next up, we will need to copy the listed public key and specify that Git needs to use that specific key with the below command.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git config &lt;span class="nt"&gt;--global&lt;/span&gt; user.signingkey your_key_here
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Step #13 You should be all set to sign your commits now by appending an extra -S to your git commit command!&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git commit &lt;span class="nt"&gt;-S&lt;/span&gt; &lt;span class="nt"&gt;-m&lt;/span&gt; &lt;span class="s2"&gt;"your_commit_message"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's it! Once you push the commit to the repo, you should be able to see a green tick mark against your commit verifying that it came from you.&lt;/p&gt;

&lt;p&gt;Hope this was useful!&lt;/p&gt;

</description>
      <category>github</category>
      <category>git</category>
      <category>tutorial</category>
      <category>beginners</category>
    </item>
    <item>
      <title>From zero to WIP</title>
      <dc:creator>divya-mohan0209</dc:creator>
      <pubDate>Fri, 05 Nov 2021 11:58:11 +0000</pubDate>
      <link>https://dev.to/divyamohan0209/from-zero-to-wip-3i3g</link>
      <guid>https://dev.to/divyamohan0209/from-zero-to-wip-3i3g</guid>
      <description>&lt;h2&gt;
  
  
  How I transitioned from being a sys admin working on legacy middleware to sailing the cloud native seas
&lt;/h2&gt;

&lt;p&gt;&lt;em&gt;This post originally appeared on my &lt;a href="https://medium.com/@divya.mohan0209/from-zero-to-wip-65ca95d8c52a"&gt;Medium&lt;/a&gt; blog&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;At the beginning of the pandemic, with a lot of free time on my hands I decided to invest some of it in learning new things over and above my day job at HSBC. With the ever-changing landscape I felt that my skills required a fair amount of polishing &amp;amp; therefore, I set off in search of places where I could learn and if possible, practise what I learned.&lt;/p&gt;

&lt;p&gt;There are multiple ways you could go about doing this and my route, in no way, is a holy book that you have to follow. By sharing the basic tenets on which my decisions were made, for people stuck in a similar position with zero previous experience in cloud native, I hope, the journey becomes a little less daunting.&lt;/p&gt;

&lt;h3&gt;
  
  
  1. Introspect
&lt;/h3&gt;

&lt;p&gt;This was one of the very steps that I undertook. Introspecting &amp;amp; understanding my end goal was very important for me because learning — be it via MOOCs or any other avenue would be an investment of my time over and above my day job. With the pandemic confining all of us eventually, sure there would be more hours that I could devote to this project. However below were a few questions that helped me narrow down my end goal.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Were my end goals intrinsically motivated? Or were they motivated by external factors such as compensation, recognition, etc?&lt;/li&gt;
&lt;li&gt;What amount of time could I devote on a daily basis towards improvement?&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Both these questions helped define MY baseline of sustainability towards this practice. Again, this is a very subjective result but I wanted to break out of the comfort zone that I had relegated myself to. I also wanted to be able to meet folks outside of my bubble &amp;amp; learn more from them. Since we weren’t in lockdown mode when I started thinking about this, the time commitment was relatively shorter. I could devote, at most, 2 hours per day to this effort. This would, of course, change later on when we all went into one endless lockdown.&lt;/p&gt;

&lt;p&gt;Taking time out to introspect is very important because nobody really knows you better than yourself. Without truly asking yourself why you’re in it, it is also extremely easy to overcommit because you end up saying yes to everything that comes your way.&lt;/p&gt;

&lt;h3&gt;
  
  
  2. Assess
&lt;/h3&gt;

&lt;p&gt;With an end goal in sight, I needed to figure out how to get there with all of the constraints in place. Some of the questions that helped me during this process were,&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;What are some of the avenues that are a great match for the end goal that I have in sight?&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;What are some of the things, technical and non-technical, that I am really good at?&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;What are some skills I could definitely brush up on/learn from scratch?&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Meetup groups and open source communities were easily the best answers for the first question in this section. Meetup groups were slightly more daunting due to the fact that I had to actually meet groups of people I had never interacted with before and put myself out there. Building that muscle was difficult because I did it by learning in public. Most of my technical skills I attributed to my job &amp;amp; hadn’t bothered to upgrade them in years (sad, but true). In an ever-changing landscape, I had not bothered to pull myself up &amp;amp; learn new things. This not only festered dissatisfaction in a job that had all the perks but I ended up hitting “The Wall of Stagnation” as I call it now.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Tip: For a lot of people, meetup groups &amp;amp; open source communities might not be a sustainable option because of the time/effort commitment required. And that’s totally fair! There are other avenues you can pick to start learning, if that’s your end goal and you’ll be just fine.&lt;/em&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  3. Chart
&lt;/h3&gt;

&lt;p&gt;Armed with this information, I charted my course that resembles the below&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;Join open source communities &amp;amp; meetup groups based on the areas I was most interested in&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Figure out where I could contribute based on my skills&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Understand what my aspirational contributor level was.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Develop new skills&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Although I’ve listed this out, it is an endless iterative loop for me. After joining Kubernetes &amp;amp; LitmusChaos based on my interests in 2020, I realized that documentation/non-code contributions were the only place I could contribute effectively because of my skills. I knew the barebones of HTML, CSS, and Javascript and could easily build up on the knowledge I already had. I also built up my documentation prowess by participating in the &lt;a href="https://hepsoftwarefoundation.org/gsdocs/blogs/2020/blog_Rucio_DivyaMohan.html"&gt;Google Season of Docs with CERN&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Over and above this, I also got involved in the &lt;a href="https://www.youtube.com/watch?v=b2lqLgOrNgI&amp;amp;list=PLwbqbiHg4yyizhCc5kHHgaWacXsYggKI2&amp;amp;index=17"&gt;Release Team shadow program&lt;/a&gt; to learn more about the Kubernetes ecosystem from an end-to-end perspective. Of course, during all of this I continued learning (and failing) publicly by &lt;a href="https://github.com/divya-mohan0209/talks"&gt;speaking at various events globally&lt;/a&gt;. This gave me the opportunity to play to my strengths while building muscle for things that I was less skilled in.&lt;/p&gt;

&lt;h3&gt;
  
  
  4. Course correction
&lt;/h3&gt;

&lt;p&gt;I know this seems like a simple start — finish story, but it isn’t. There were multiple times throughout the journey (which is still WIP, btw) when I went completely bonkers by overcommitting &amp;amp; taking on more work than I should have or was skilled for.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Fun fact: I purchased a number of courses on different MOOCs during an impulsive buying spree. I thought I would get to them eventually before starting off this journey. More than half of them will never see completion, unfortunately.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;I am grateful that my journey survived those downfalls because it did teach me a LOT about course correcting. A few questions for when you’ve veered too far away from the road&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;Do I want to achieve something new or am I chasing the next shiny happy thing?&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Is this in alignment with my goal/s?&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;I ask myself these questions every quarter because I have shiny object syndrome. I get distracted very easily &amp;amp; focus is an alien concept. This might not be the case with everyone. But it definitely makes sense to review if what you are doing continues to make sense &amp;amp; if it doesn’t, to reroute yourself by going back to #1 again.&lt;/p&gt;

&lt;h3&gt;
  
  
  So, what’s next?
&lt;/h3&gt;

&lt;p&gt;I currently co-lead the documentation efforts for &lt;a href="https://github.com/kubernetes/community/tree/master/sig-docs#chairs"&gt;Kubernetes&lt;/a&gt; &amp;amp; &lt;a href="https://github.com/orgs/litmuschaos/teams/sig-documentation/members"&gt;LitmusChaos&lt;/a&gt;, am a &lt;a href="https://www.cncf.io/people/ambassadors/"&gt;CNCF ambassador&lt;/a&gt;, have spoken at global events, and have even &lt;a href="https://github.com/cncf/curriculum/issues/50"&gt;co-led the creation &amp;amp; review&lt;/a&gt; of the &lt;a href="https://training.linuxfoundation.org/certification/kubernetes-cloud-native-associate/?utm_source=tfir&amp;amp;utm_medium=video&amp;amp;utm_campaign=influencer"&gt;KCNA certification&lt;/a&gt;. I intend to continue and plan on writing/speaking more about cloud native &amp;amp; open source. My target is to get myself CKA &amp;amp; CKAD certified by Q1, 2022 &amp;amp; continue exploring other avenues of the projects I can contribute to.&lt;/p&gt;

&lt;p&gt;I will continue to document my journey here and on &lt;a href="https://twitter.com/Divya_Mohan02"&gt;Twitter&lt;/a&gt;. You can follow me on both avenues to stay updated with the latest goss.&lt;/p&gt;

</description>
      <category>opensource</category>
      <category>kubernetes</category>
      <category>cloudnative</category>
      <category>beginners</category>
    </item>
    <item>
      <title>Serverless and the Dreaded CORS</title>
      <dc:creator>divya-mohan0209</dc:creator>
      <pubDate>Sun, 02 Feb 2020 06:42:39 +0000</pubDate>
      <link>https://dev.to/divyamohan0209/serverless-and-the-dreaded-cors-7l0</link>
      <guid>https://dev.to/divyamohan0209/serverless-and-the-dreaded-cors-7l0</guid>
      <description>&lt;p&gt;While venturing farther in the Serverless world, I started making a list of things I encountered on my journey that I would like to delve deeper into; plainly because, I figured learning just enough to make something work was never going to satisfy my voracious appetite. Towards cementing my understanding, I started making unorganized one-liner notes as reference material. This article (&lt;em&gt;and the ones that will follow, hopefully&lt;/em&gt;) are logical extensions of those notepad entries.&lt;/p&gt;

&lt;p&gt;My very first entry on the list, was CORS -  more commonly known as &lt;em&gt;Cross Origin Resource Sharing&lt;/em&gt;. &lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;&lt;p&gt;So what EXACTLY is CORS?&lt;br&gt;
Cross Origin Resource Sharing (&lt;strong&gt;CORS&lt;/strong&gt;) enables a web-app to access resources OUTSIDE of its domain in a controlled manner and offers flexibility + functionality over the default same-origin security policy.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;What is Same-Origin Security Policy?&lt;br&gt;
A policy, under which, a web browser permits web page #1 to access data in web page # 2, ONLY IF both web pages have the same origin i.e. belong to the same domain.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;How is CORS relevant in Serverless?&lt;br&gt;
Web API Backends being a popular use case in serverless, a web page might need to make calls to a backend API that lies on a different domain i.e. of different origin; therefore, requiring the call to be CORS-friendly.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;What is a common error indicating that CORS is NOT enabled?&lt;br&gt;
No 'Access-Control-Allow-Origin' header is present on the requested resource&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;How is CORS implemented?&lt;br&gt;
Two main ways:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Headers

&lt;ul&gt;
&lt;li&gt;Access-Control-Allow-Origin header: Included in the response to specify the origin of where the request originated from as the value for allowing access to the resource's contents.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;Pre-flight requests (&lt;em&gt;&lt;strong&gt;GET, POST, HEAD methods excluded&lt;/strong&gt;&lt;/em&gt;)

&lt;ul&gt;
&lt;li&gt;Browser will send a preflight request to the resource using the OPTIONS method; in response to which, the resource you're requesting will return with methods that are safe to send and may optionally return the headers that are valid to send across.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Ways that CORS can be exploited? (i.e. Poor design practices)&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Allowing access to any domain in the origin field&lt;/li&gt;
&lt;li&gt;Allowing access to all sub-domains (&lt;em&gt;including currently non-existent sub-domains, that could potentially be malicious&lt;/em&gt;)&lt;/li&gt;
&lt;li&gt;Origin header specification supporting the value &lt;strong&gt;null&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;Trusting origins with vulnerabilities to XSS i.e. Cross Site Scripting&lt;/li&gt;
&lt;li&gt;Whitelisting trusted subdomain using HTTP&lt;/li&gt;
&lt;li&gt;Lower security standards for authentication on intranets/internal websites&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Ways to prevent CORS-based attacks?&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Allowing trusted websites ONLY&lt;/li&gt;
&lt;li&gt;Avoid whitelisting null&lt;/li&gt;
&lt;li&gt;Avoid use of wildcards in intranets/internal websites&lt;/li&gt;
&lt;li&gt;Judiciously configure cross-domain requests by correctly specifying origin against Access-Control-Allow-Origin header&lt;/li&gt;
&lt;li&gt;Stringent configuration of server-side security policies.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;&lt;em&gt;&lt;strong&gt;Credits: Major shout-out to Alex DeBrie for his amazing article on Serverless and CORS that helped me a lot while writing this post.&lt;/strong&gt;&lt;/em&gt;&lt;/p&gt;

</description>
      <category>serverless</category>
      <category>webdev</category>
      <category>cors</category>
      <category>design</category>
    </item>
  </channel>
</rss>
