text: from abc import ABC
  from enum import Enum, auto
  
  
  class HotDrink(ABC):
      def consume(self):
          pass
  
  
  class Tea(HotDrink):
      def consume(self):
          print('This tea is nice but I\'d prefer it with milk')
  
  
  class Coffee(HotDrink):
      def consume(self):
          print('This coffee is delicious')
  
  
  class HotDrinkFactory(ABC):
      """
      Python does not require this ABC, but it helps as an API
      to know the factories structure.
      """
      def prepare(self, amount):
          pass
  
  
  class TeaFactory(HotDrinkFactory):
      def prepare(self, amount):
          print(f'Put in tea bag, boil water, pour {amount}ml, enjoy!')
          return Tea()
  
  
  class CoffeeFactory(HotDrinkFactory):
      def prepare(self, amount):
          print(f'Grind some beans, boil water, pour {amount}ml, enjoy!')
          return Coffee()
  
  # How to use previous factories
  
  # Option 1. Using a function
  
  def make_drink(type):
      if type == 'tea':
          return TeaFactory().prepare(200)
      elif type == 'coffee':
          return CoffeeFactory().prepare(50)
      else:
          raise ValueError(type)
  
  
  # Option 2. Using a class
  
  class HotDrinkMachine:
      class AvailableDrink(Enum):
          """
          This violates the OCP as it must be modified each time
          a new drink is added.
          """
          COFFEE = auto()
          TEA = auto()
  
      factories = []
      initialized = False
  
      def __init__(self):
          if not self.initialized:
              self.initialized = True
              for d in self.AvailableDrink:
                  name = d.name[0] + d.name[1:].lower()
                  factory_name = name + 'Factory'
                  factory_instance = eval(factory_name)()
                  self.factories.append((name, factory_instance))
  
      def make_drink(self):
          print('Available drinks:')
          for index, factory in enumerate(self.factories):
              print(f"{index}) {factory[0]}")
  
          s = input(f'Please pick drink (0-{len(self.factories)-1}): ')
          idx = int(s)
          s = input(f'Specify amount: ')
          amount = int(s)
          return self.factories[idx][1].prepare(amount)
  
  
  
  if __name__ == '__main__':
      print("Option 1. Using a function")
      entry = input('What kind of drink would you like? (Write the name)')
      drink = make_drink(entry)
      drink.consume()
  
      print("\nOption 2. Using a class")
      hdm = HotDrinkMachine()
      drink = hdm.make_drink()
      drink.consume()
  