Michel  Kub

Michel Kub

1603694885

Microservices Architecture From A to Z

This article aims to discuss the microservices architecture from its definition to a concrete example.

Plan:

  1. What is a microservices architecture?
  2. Advantages and disadvantages of a microservices architecture
  3. Orchestration vs Choreography
  4. Advice and good practices
  5. Proof of concept

The following results were produced via various sources: scientific publications, articles, videos, documentations from large companies, etc. These include the website of Martin Fowler, renowned software engineer and author, which contains an extensive documentation on microservices.

1. What is a microservices architecture?

Essentially, microservices architecture is a method of software development that aims to break down an application to isolate key functions, each of these functions is called a “service”. These services are designed to meet a specific and unique business need, for example: user management, payments, sending emails or even notifications. In addition, they are independent and modular, this allows each to be developed and deployed without affecting the others. This type of architecture is intended to be the opposite of monolithic architectures which are built as a single autonomous unit.

This definition may recall another type of architecture quite similar, Service Oriented Architecture (SOA), a software design already well stated.

What makes an SOA architecture different from a microservices architecture?

Let’s start with a clear observation, made by the precursors of microservices: this architecture is an extension of the concept of SOA. Most of the design principles for microservices were already available in the SOA world. Some people claim that “the microservices architecture is a well-designed SOA architecture.” Let’s see the differences between SOA and microservices along several axes:

  • Size: One of the big differences is the size and scope of services. As you can guess from the name, in microservices, the size of each service is much smaller than the one of SOA services. In a microservices architecture, each service has a single responsibility while in the SOA architecture, services can contain many business functions.
  • Reusability: One of the goals of SOA is to reuse components without worrying about coupling while in microservices we try to minimize reuse since this creates dependencies that reduce agility and resiliency. A weak coupling is preferred, even if it means having code duplication.
  • Communication: In SOA, communication between services is usually done synchronously through an enterprise service bus (ESB), this introduces a critical point of failure and latency. In a microservices application, fault tolerance is better thanks to the independence of each service, asynchronous communication is also privileged between services (for example a publish subscribe model can be used to allow a service to stay up to date on changes to another one’s data), enabling high availability.
  • Data duplication: One of the goals of an SOA is to allow all applications to access data synchronously directly at the source. With a microservices architecture, each service has access to all the data it needs locally (ideally) to have maximum performance and agility, even if this means having to duplicate data and therefore add complexity.

Let’s sum it all up with a diagram:

Image for post

2. Advantages and disadvantages of a microservices architecture

Now that we have a better understanding of what a microservices architecture is, let’s see what are the advantages and disadvantages of it compared to a monolith architecture. We’ve seen a number of benefits before, but let’s go over them all:

  • Independent Development: Teams can choose the technologies that best suit each service using various technology stacks and are not limited by the choices made at the start of the project. Additionally, a single development team can build, test, and deploy a service, enabling faster deployment and facilitating continuous innovation. It is also more difficult to make mistakes since there are strong boundaries between the different services.
  • Independent deployment: Microservices are deployed independently. A service can be updated without having to redeploy the entire application, making it easier to manage bug fixes and new features. This simplifies integration and continuous deployment. In many traditional applications, if there is a bug in one part of the application, it can block the entire release process.
  • Independent scaling: Services can scale independently to suit needs, optimizing costs and time since there is no need to scale the entire application as you would with a monolith.
  • Small Targeted Teams: Teams can be targeted to only one service, making code easier to understand and making it easier for new members to join the team, no need to spend weeks figuring out how a complex monolith works. It also promotes flexibility, large teams tend to be less productive because communication is slower, management time increases and agility decreases.
  • Small Code Base: In a monolithic application, code dependencies tend to get mixed up over time. Adding new functionality requires changing the code in a lot of places. In a microservices architecture, which does not share code or database, these dependencies are minimized, which makes it easier to add new features. It also complements the previous point that it makes it easier to understand the code and introduce new members to the team.
  • Data isolation: In a microservices architecture, each service has private access to its database (ideally), we can then perform an update of the database schema without affecting the other services. In a monolithic application, schema updates can become very difficult and risky since multiple parts of the application can use the same data.
  • Resilience: With a microservices architecture, critical points of failure are considerably reduced. When a service goes down, the whole application does not stop functioning as it does with the monolithic model and therefore the risk is also reduced when new features are developed. Errors are also isolated and therefore easier to correct.
  • Technological Advances: Recent advancements in cloud technologies and containerization make setting up a microservices architecture increasingly simple. Every cloud provider has solutions for this type of architecture to make life easier for developers.

Now that we have a better idea of all the advantages of a microservices architecture, let’s see what the disadvantages and challenges are:

  • Complexity: While each service is simpler, the system as a whole is more complex. Because this is a distributed system, care should be taken to select and set up all services and databases, and then deploy each of these components independently. All the challenges of a distributed system must be taken into account.
  • Testing: Having multitude independent services can make writing tests more complex, especially when there are many dependencies between services. A mock must be used for each dependent service to be able to unit test a service.
  • Data Integrity: Microservices have a distributed database architecture, which is a challenge for data integrity. Some business transactions, which require updating multiple business functions of the application, need to update multiple databases owned by different services. This requires setting up eventual consistency of data, which is obviously more complex and less intuitive for developers.
  • Network latency: Using many small services can result in increased communications between services. Also, if you have a chain of dependency between services to perform a business transaction, the additional latency that results can become a problem. Asynchronous communications should be favored when usage permits, but this once again adds complexity to the system.

According to these advantages and disadvantages it is then more or less relevant to adopt a microservices architecture, there is no universal rule, each project is unique and the motivations towards one architecture or the other depend on the needs and the context of it.

#microservices #javascript #programming #developer

What is GEEK

Buddha Community

Microservices Architecture From A to Z

Serverless Vs Microservices Architecture - A Deep Dive

Companies need to be thinking long-term before even starting a software development project. These needs are solved at the level of architecture: business owners want to assure agility, scalability, and performance.

The top contenders for scalable solutions are serverless and microservices. Both architectures prioritize security but approach it in their own ways. Let’s take a look at how businesses can benefit from the adoption of serverless architecture vs microservices, examine their differences, advantages, and use cases.

#serverless #microservices #architecture #software-architecture #serverless-architecture #microservice-architecture #serverless-vs-microservices #hackernoon-top-story

The Service Mesh in the Microservices World - DZone Microservices

The software industry has come a long journey and throughout this journey, Software Architecture has evolved a lot. Starting with 1-tier (Single-node), 2-tier (Client/ Server), 3-tier, and Distributed are some of the Software Architectural patterns we saw in this journey.

The Problem

The majority of software companies are moving from Monolithic architecture to Microservices architecture, and Microservices architecture is taking over the software industry day-by-day. While monolithic architecture has many benefits, it also has so many shortcomings when catering to modern software development needs. With those shortcomings of monolithic architecture, it is very difficult to meet the demand of the modern-world software requirements and as a result, microservices architecture is taking control of the software development aggressively. The Microservices architecture enables us to deploy our applications more frequently, independently, and reliably meeting modern-day software application development requirements.

#microservice architecture #istio #microservice best practices #linkerd #microservice communication #microservice design #envoy proxy #kubernetes architecture #api gateways #service mesh architecture

Tia  Gottlieb

Tia Gottlieb

1597438200

What Is a Microservice Architecture? Why Is It Important Now?

We have been building software applications for many years using various tools, technologies, architectural patterns and best practices. It is evident that many software applications become large complex monolith over a period for various reasons. A monolith software application is like a large ball of spaghetti with criss-cross dependencies among its constituent modules. It becomes more complex to develop, deploy and maintain monoliths, constraining the agility and competitive advantages of development teams. Also, let us not undermine the challenge of clearing any sort of technical debt monoliths accumulate, as changing part of monolith code may have cascading impact of destabilizing a working software in production.

Over the years, architectural patterns such as Service Oriented Architecture (SOA) and Microservices have emerged as alternatives to Monoliths.

SOA was arguably the first architectural pattern aimed at solving the typical monolith issues by breaking down a large complex software application to sub-systems or “services”. All these services communicate over a common enterprise service bus (ESB). However, these sub-systems or services are actually mid-sized monoliths, as they share the same database. Also, more and more service-aware logic gets added to ESB and it becomes the single point of failure.

Microservice as an architectural pattern has gathered steam due to large scale adoption by companies like Amazon, Netflix, SoundCloud, Spotify etc. It breaks downs a large software application to a number of loosely coupled microservices. Each microservice is responsible for doing specific discrete tasks, can have its own database and can communicate with other microservices through Application Programming Interfaces (APIs) to solve a large complex business problem. Each microservice can be developed, deployed and maintained independently as long as it operates without breaching a well-defined set of APIs called contract to communicate with other microservices.

#microservice architecture #microservice #scaling #thought leadership #microservices build #microservice

Dylan  Iqbal

Dylan Iqbal

1630996646

A Look at an ES2022 Feature: Class Static Initialization Blocks

ECMAScript class static initialization blocks

Class static blocks provide a mechanism to perform additional static initialization during class definition evaluation.

This is not intended as a replacement for public fields, as they provide useful information for static analysis tools and are a valid target for decorators. Rather, this is intended to augment existing use cases and enable new use cases not currently handled by that proposal.

Status

Stage: 4
Champion: Ron Buckton (@rbuckton)

For detailed status of this proposal see TODO, below.

Authors

  • Ron Buckton (@rbuckton)

Motivations

The current proposals for static fields and static private fields provide a mechanism to perform per-field initialization of the static-side of a class during ClassDefinitionEvaluation, however there are some cases that cannot be covered easily. For example, if you need to evaluate statements during initialization (such as try..catch), or set two fields from a single value, you have to perform that logic outside of the class definition.

// without static blocks:
class C {
  static x = ...;
  static y;
  static z;
}

try {
  const obj = doSomethingWith(C.x);
  C.y = obj.y
  C.z = obj.z;
}
catch {
  C.y = ...;
  C.z = ...;
}

// with static blocks:
class C {
  static x = ...;
  static y;
  static z;
  static {
    try {
      const obj = doSomethingWith(this.x);
      this.y = obj.y;
      this.z = obj.z;
    }
    catch {
      this.y = ...;
      this.z = ...;
    }
  }
}

In addition, there are cases where information sharing needs to occur between a class with an instance private field and another class or function declared in the same scope.

Static blocks provide an opportunity to evaluate statements in the context of the current class declaration, with privileged access to private state (be they instance-private or static-private):

let getX;

export class C {
  #x
  constructor(x) {
    this.#x = { data: x };
  }

  static {
    // getX has privileged access to #x
    getX = (obj) => obj.#x;
  }
}

export function readXData(obj) {
  return getX(obj).data;
}

Relation to "Private Declarations"

The Private Declarations proposal also intends to address the issue of privileged access between two classes, by lifting the private name out of the class declaration and into the enclosing scope. While there is some overlap in that respect, private declarations do not solve the issue of multi-step static initialization without potentially exposing a private name to the outer scope purely for initialization purposes:

// with private declarations
private #z; // exposed purely for post-declaration initialization
class C {
  static y;
  static outer #z;
}
const obj = ...;
C.y = obj.y;
C.#z = obj.z;

// with static block
class C {
  static y;
  static #z; // not exposed outside of class
  static {
    const obj = ...;
    this.y = obj.y;
    this.#z = obj.z;
  }
}

In addition, Private Declarations expose a private name that potentially allows both read and write access to shared private state when read-only access might be desireable. To work around this with private declarations requires additional complexity (though there is a similar cost for static{} as well):

// with private declarations
private #zRead;
class C {
  #z = ...; // only writable inside of the class
  get #zRead() { return this.#z; } // wrapper needed to ensure read-only access
}

// with static
let zRead;
class C {
  #z = ...; // only writable inside of the class
  static { zRead = obj => obj.#z; } // callback needed to ensure read-only access
}

In the long run, however, there is nothing that prevents these two proposals from working side-by-side:

private #shared;
class C {
  static outer #shared;
  static #local;
  static {
    const obj = ...;
    this.#shared = obj.shared;
    this.#local = obj.local;
  }
}
class D {
  method() {
    C.#shared; // ok
    C.#local; // no access
  }
}

Prior Art

Syntax

class C {
  static {
    // statements
  }
}

Semantics

  • A static {} initialization block creates a new lexical scope (e.g. var, function, and block-scoped declarations are local to the static {} initialization block. This lexical scope is nested within the lexical scope of the class body (granting privileged access to instance private state for the class).
  • A class may have any number of static {} initialization blocks in its class body.
  • static {} initialization blocks are evaluated in document order interleaved with static field initializers.
  • A static {} initialization block may not have decorators (instead you would decorate the class itself).
  • When evaluated, a static {} initialization block's this receiver is the constructor object of the class (as with static field initializers).
  • It is a Syntax Error to reference arguments from within a static {} initialization block.
  • It is a Syntax Error to include a SuperCall (i.e., super()) from within a static {} initialization block.
  • A static {} initialization block may contain SuperProperty references as a means to access or invoke static members on a base class that may have been overridden by the derived class containing the static {} initialization block.
  • A static {} initialization block should be represented as an independent stack frame in debuggers and exception traces.

Examples

// "friend" access (same module)
let A, B;
{
  let friendA;

  A = class A {
    #x;

    static {
        friendA = {
          getX(obj) { return obj.#x },
          setX(obj, value) { obj.#x = value }
        };
    }
  };

  B = class B {
    constructor(a) {
      const x = friendA.getX(a); // ok
      friendA.setX(a, x); // ok
    }
  };
}

References

TODO

The following is a high-level list of tasks to progress through each stage of the TC39 proposal process:

Stage 1 Entrance Criteria

  • Identified a "champion" who will advance the addition.
  • Prose outlining the problem or need and the general shape of a solution.
  • Illustrative examples of usage.
  • High-level API.

Stage 2 Entrance Criteria

Stage 3 Entrance Criteria

Stage 4 Entrance Criteria

For up-to-date information on Stage 4 criteria, check: #48

  • Test262 acceptance tests have been written for mainline usage scenarios and merged.
  • Two compatible implementations which pass the acceptance tests:
  • A pull request has been sent to tc39/ecma262 with the integrated spec text.
  • The ECMAScript editor has signed off on the pull request.

Download Details:
Author: tc39
The Demo/Documentation: View The Demo/Documentation
Download Link: Download The Source Code
Official Website: https://github.com/tc39/proposal-class-static-block 
License: BSD-3
#javascript #es2022 #ecmascript 

Einar  Hintz

Einar Hintz

1599055326

Testing Microservices Applications

The shift towards microservices and modular applications makes testing more important and more challenging at the same time. You have to make sure that the microservices running in containers perform well and as intended, but you can no longer rely on conventional testing strategies to get the job done.

This is where new testing approaches are needed. Testing your microservices applications require the right approach, a suitable set of tools, and immense attention to details. This article will guide you through the process of testing your microservices and talk about the challenges you will have to overcome along the way. Let’s get started, shall we?

A Brave New World

Traditionally, testing a monolith application meant configuring a test environment and setting up all of the application components in a way that matched the production environment. It took time to set up the testing environment, and there were a lot of complexities around the process.

Testing also requires the application to run in full. It is not possible to test monolith apps on a per-component basis, mainly because there is usually a base code that ties everything together, and the app is designed to run as a complete app to work properly.

Microservices running in containers offer one particular advantage: universal compatibility. You don’t have to match the testing environment with the deployment architecture exactly, and you can get away with testing individual components rather than the full app in some situations.

Of course, you will have to embrace the new cloud-native approach across the pipeline. Rather than creating critical dependencies between microservices, you need to treat each one as a semi-independent module.

The only monolith or centralized portion of the application is the database, but this too is an easy challenge to overcome. As long as you have a persistent database running on your test environment, you can perform tests at any time.

Keep in mind that there are additional things to focus on when testing microservices.

  • Microservices rely on network communications to talk to each other, so network reliability and requirements must be part of the testing.
  • Automation and infrastructure elements are now added as codes, and you have to make sure that they also run properly when microservices are pushed through the pipeline
  • While containerization is universal, you still have to pay attention to specific dependencies and create a testing strategy that allows for those dependencies to be included

Test containers are the method of choice for many developers. Unlike monolith apps, which lets you use stubs and mocks for testing, microservices need to be tested in test containers. Many CI/CD pipelines actually integrate production microservices as part of the testing process.

Contract Testing as an Approach

As mentioned before, there are many ways to test microservices effectively, but the one approach that developers now use reliably is contract testing. Loosely coupled microservices can be tested in an effective and efficient way using contract testing, mainly because this testing approach focuses on contracts; in other words, it focuses on how components or microservices communicate with each other.

Syntax and semantics construct how components communicate with each other. By defining syntax and semantics in a standardized way and testing microservices based on their ability to generate the right message formats and meet behavioral expectations, you can rest assured knowing that the microservices will behave as intended when deployed.

#testing #software testing #test automation #microservice architecture #microservice #test #software test automation #microservice best practices #microservice deployment #microservice components