Introduction
In this article, we will cover the Abstract Factory Design Pattern.
So, Let's get started.
Please refer to my previous article,
What is Abstract Factory?
The Abstract Factory is a creational design pattern that provides an interface for creating families of related objects without specifying their concrete classes. Think of it as a super factory that delegates object creation to specialized sub-factories based on your needs.
How do we implement the Abstract Factory Design Pattern in C#?
We must use the following components to Implement the Abstract Factory Design Pattern in C#.
- Abstract Product: These are going to be interfaces for creating abstract products. Here, we need to define the Operations a Product should have.
- Concrete Product: These are the classes that implement the Abstract Product interface.
- Abstract Factory: This will be an interface for operations that will create Abstract Product objects.
- Concrete Factory: These classes implement the Abstract Factory interface and provide implementations for the interface methods. We can use these concrete classes to create concrete product objects.
- Client: This class will use our Abstract Factory and Abstract Product interfaces to create a family of products.
Real-World Example. Payment Gateways in E-commerce
Let’s consider a scenario where financial software needs to process payments using different methods, such as “Credit Card” and “GPay”. The Abstract Factory pattern can help create families of related objects to process payments with each method, considering operations like payment authorization and transfer. Let us see how we can implement the above example using the Abstract Factory Design Pattern in C#:
public interface IPaymentAuthorization
{
bool AuthorizePayment(decimal amount);
}
public interface IPaymentTransfer
{
bool Transfer(decimal amount);
}
// Concrete Products for Credit Card
public class CreditCardAuthorization : IPaymentAuthorization
{
public bool AuthorizePayment(decimal amount)
{
Console.WriteLine($"Authorizing payment of {amount} via Credit Card...");
return true; // Mocked success
}
}
public class CreditCardTransfer : IPaymentTransfer
{
public bool Transfer(decimal amount)
{
Console.WriteLine($"Transferring payment of {amount} via Credit Card...");
return true; // Mocked success
}
}
// Concrete Products for GPay
public class GPayAuthorization : IPaymentAuthorization
{
public bool AuthorizePayment(decimal amount)
{
Console.WriteLine($"Authorizing payment of {amount} via GPay...");
return true; // Mocked success
}
}
public class GPayTransfer : IPaymentTransfer
{
public bool Transfer(decimal amount)
{
Console.WriteLine($"Transferring payment of {amount} via GPay...");
return true; // Mocked success
}
}
// Abstract Factory
public interface IPaymentFactory
{
IPaymentAuthorization CreateAuthorization();
IPaymentTransfer CreateTransfer();
}
// Concrete Factories
public class CreditCardPaymentFactory : IPaymentFactory
{
public IPaymentAuthorization CreateAuthorization() => new CreditCardAuthorization();
public IPaymentTransfer CreateTransfer() => new CreditCardTransfer();
}
public class GPayPaymentFactory : IPaymentFactory
{
public IPaymentAuthorization CreateAuthorization() => new GPayAuthorization();
public IPaymentTransfer CreateTransfer() => new GPayTransfer();
}
// Client Code
public class PaymentProcessor
{
private readonly IPaymentAuthorization _authorization;
private readonly IPaymentTransfer _transfer;
public PaymentProcessor(IPaymentFactory factory)
{
_authorization = factory.CreateAuthorization();
_transfer = factory.CreateTransfer();
}
public bool ProcessPayment(decimal amount)
{
if (_authorization.AuthorizePayment(amount))
{
return _transfer.Transfer(amount);
}
return false;
}
}
// Testing the Abstract Factory Design Pattern
public class Program
{
public static void Main()
{
Console.WriteLine("Processing payment using Credit Card:");
var creditCardFactory = new CreditCardPaymentFactory();
var creditCardProcessor = new PaymentProcessor(creditCardFactory);
creditCardProcessor.ProcessPayment(100.00M);
Console.WriteLine("\nProcessing payment using GPay:");
var gPayFactory = new GPayPaymentFactory();
var gPayProcessor = new PaymentProcessor(gPayFactory);
gPayProcessor.ProcessPayment(100.00M);
Console.ReadKey();
}
}
Summary
In this article, I have tried to cover Abstract Factory Design Patterns.