The cloud is a godsend for the vast majority of software developers. It offers resources right at their fingertips, along with lower costs than traditional setups and a reasonable learning curve. However, this convenience creates challenges for developers who must learn to manage local development environments that differ from their organizations' cloud environments.
Ideally, development environments should run locally without any external dependencies, since development teams are more productive when they have to deal with fewer external resources.
However, this isn't always possible when there are cloud dependencies. The more tightly coupled a development environment is with the outside world, the more likely developer productivity will be hindered by poor Wi-Fi reception or an internet outage. It's developers' desire to forgo those dependencies locally that can create discrepancies between the two environments.
Take an offline mindset
The ubiquity of the cloud has made it more difficult to develop applications without an active internet connection. Whether an application relies on proprietary, cloud-based database technologies or a third-party API, these external dependencies can quickly become bottlenecks in a world where rapid iteration can make or break an organization.
Designing a development environment with an offline-first mindset establishes a foundation for environment parity from the beginning. Look-alike and mock services are great ways to create an offline-first environment that reduces the number of local hardware resources required to power an application.
Adopt mock services
Many programming languages use duck typing to define objects. Rather than explicitly define an object as an integer or a string -- like statically typed languages -- duck typing infers variable types based on properties. In other words, if it walks like a duck and it quacks like a duck, it must be a duck.
To achieve parity between development environments, treat dependent services as ducks. This mindset enables users to swap out third-party dependencies for compatible mock services without fundamentally changing their application configuration. These duck services can reduce unnecessary overhead by decreasing both the minimum hardware requirements and the number of third-party services that need to run locally.
One example is Minio, an open source cloud storage platform with an Amazon Simple Storage Service (S3)-compatible API. Typically, applications that rely on Amazon S3 for object storage also rely on an active internet connection for production. With Minio, enterprises can communicate with a locally hosted service with the same library they already use to communicate with Amazon S3. Without this mock service, developers would have to get numerous services to achieve the same result.
Sometimes, there is no appropriate proxy for a given cloud-based dependency. While some users are tempted to sign up for the latest offering from their cloud provider, the service might be too nascent to have a viable proxy, which could negatively impact future parity possibilities. The popularity and age of a cloud-native service are generally the deciding factor here, so take a closer look at open source and third-party options before risking lock-in.
Get the parity users need
As software applications grow in size and scale, so too do dependencies. From a local development perspective, this can be a monumental challenge when developers can't rely on the one tool they generally use in cloud and are instead forced to install elements such as Redis, Postgres, Minio, PHP and Nginx just to run one microservice locally. This process is not scalable or sustainable without automation, and when more than one engineer is introduced into the process, it can lead to a loss of parity between individual developers' environments.
Vagrant by HashiCorp -- an open source tool used to build and distribute development environments -- is often the go-to tool to automate the provisioning and management of local development environments. However, many organizations are outgrowing it as they move toward cloud orchestration platforms, such as Kubernetes, which don't always play nice with Vagrant's VM-driven workflow. In order to truly achieve parity, enterprises need to deploy and manage local development environments in the same way as production infrastructure -- albeit at a much smaller scale.
For example, rather than spin up every dependency directly on the local development machine, enterprises can use the built-in Kubernetes functionality of Docker Desktop to ensure that the development environments align from both a dependency and infrastructure standpoint. In keeping with the DevOps tradition, the same scripts used to provision the production environment can be written and tested much earlier in the process, before the cloud ever comes into the picture.