Published on

Factory Pattern

Authors
tailwind-nextjs-banner

Factory Pattern

Factory pattern is a Design principal and part of the Creational Pattern Strategy

Table of Contents

  1. Introduction
  2. Structure
  3. Pseudocode
  4. Supportive class and function
  5. Process Strategy (Creator)
  6. Process Strategies (Concrete Creators)
  7. Product Interface
  8. Run the app
  9. Result
  10. References

Introduction

Factory Pattern is one of the creational design patterns available for software engineers that will help you design a better strategy for software development.

The principle behind this method is to provide a common interface or a class to create objects or an object without exposing the creation logic to the client and allows subclasses to alter the type of objects that will be created. This will provide a better way to create an object and will simplify the expandability of your software in the future.

A Factory has many production lines, each one with its particularities of production and its respective deliverables. However, if the factory decides to increase a new product to its portfolio, the management does not need to build a new factory (sometimes they need it, however, another design pattern could fit better in that situation), but they just increase a new production line.

Structure

structure-img-factory-pattern

Pseudocode

To exemplify the Factory Pattern we will use the example of a Customer Support Center. Imagine that you have a customer support centre that processes the customer open tickets with a specific process strategy, such First-In-First-Out (FIFO strategy) or First-In-Last-Out (FILO strategy). However, due to the market demand, you will need to add more process strategies to your factory to define what is best for your teams and clients.

Will you change all your code?

No, if you have applied the Factory Pattern. With this design pattern, you can add more products (or process strategies) to your factory strategy without changing your code.

Supportive class and function

The Support Tickets class is an engine to create ticket objects that will be consumed in the factory Customer Support. This class is named, the method living inside the factory and its main function is to create ticket objects.

def generate_id(length=8):
    return "".join(random.choices(string.ascii_uppercase, k=length))


class SupportTicket:
    id: str
    customer: str
    issue: str

    def __init__(self, customer: str, issue: str):
        self.id = generate_id()
        self.customer = customer
        self.issue = issue

Process Strategy (Creator)

Creator is an abstract class, inherit from the ABC class and just define abstract processes in the same way they get into the factory CustomerSupport.

class processStrategy(ABC):
    @abstractmethod
    def create_ordering(self, list: List[SupportTicket]) -> List[SupportTicket]:
        pass

Process Strategies (Concrete Creators)

Concrete creators like FIFO strategy and FILO strategy are sub-classes of the ABC class or factory creator called Process Strategy. Each one has its methods to process the objects.

class FIFOStrategy(processStrategy):
    def create_ordering(self, list: List[SupportTicket]) -> List[SupportTicket]:
        return list.copy()


class FILOStrategy(processStrategy):
    def create_ordering(self, list: List[SupportTicket]) -> List[SupportTicket]:
        list_copy = list.copy()
        list_copy.reverse()
        return list_copy

Product Interface

The factory CustomerSupport initiates by creating an empty list of tickets. Additionally, this factory has the following methods:

  1. Creates a ticket object using the SupportTicket() class by passing the issue and customer inputs.

  2. Processes the tickets generated by calling the processTickets() method and providing which process strategy you want to follow. This method calls the individual processTicket() method to each ticket available on the pipeline.

class CustomerSupport:
    def __init__(self):
        self.tickets = []

    def createTicket(self, customer: str, issue: str):
        ticket = SupportTicket(customer, issue)
        return self.tickets.append(ticket)

    def processTicket(self, ticket: SupportTicket):
        print("==================================")
        print(f"Processing ticket id: {ticket.id}")
        print(f"Customer: {ticket.customer}")
        print(f"Issue: {ticket.issue}")
        print("==================================")

    def processTickets(self, processStrategy: processStrategy):
        ticket_list = processStrategy.create_ordering(self.tickets)
        ticket_list = processStrategy.create_ordering(self.tickets)

        if len(ticket_list) == 0:
            print("There are no tickets to process. Well done!")
            return

        for ticket in ticket_list:
            self.processTicket(ticket)

Run the app

  1. To run the app, you first create an instance of the CustomerSupport factory by calling the class CustomerSupport()
  2. Creates different customer tickets of that factory by passing the method to the app created.
  3. Call the process ticket method to process all the tickets in the pipeline as below.
app = CustomerSupport()
app.createTicket("customer 1", "issue 1")
app.createTicket("customer 2", "issue 2")
app.createTicket("customer 3", "issue 3")
app.createTicket("customer 4", "issue 4")

app.processTickets(FIFOStrategy())

Result

The final result is the following

==================================
Processing ticket id: QJLYJAGF
Customer: customer 1
Issue: issue 1
==================================
==================================
Processing ticket id: EONOQTZF
Customer: customer 2
Issue: issue 2
==================================
==================================
Processing ticket id: FSQQLZWZ
Customer: customer 3
Issue: issue 3
==================================
==================================
Processing ticket id: VEJRSPUZ
Customer: customer 4
Issue: issue 4
==================================

References:

  • website refactoring.guru
  • The Factory Pattern in Python // Separate creation from use by ArjanCodes
  • Design Patterns in Python: Factory & Abstract Factory Patterns by Okan Yenigün
  • Factory Method – Python Design Patterns by geeksforgeeks