docs: def create_app_factory(app_name, config_loader=None,
                         extension_entry_points=None, extensions=None,
                         blueprint_entry_points=None, blueprints=None,
                         converter_entry_points=None, converters=None,
                         wsgi_factory=None, **app_kwargs):
      """Create a Flask application factory.
  
      The application factory will load Flask extensions and blueprints specified
      using both entry points and directly in the arguments. Loading order of
      entry points are not guaranteed and can happen in any order.
  
      :param app_name: Flask application name.
      :param config_loader: Callable which will be invoked on application
          creation in order to load the Flask configuration. See example below.
      :param extension_entry_points: List of entry points, which specifies Flask
          extensions that will be initialized only by passing in the Flask
          application object
      :param extensions: List of Flask extensions that can be initialized only by
          passing in the Flask application object.
      :param blueprint_entry_points: List of entry points, which specifies
          Blueprints that will be registered on the Flask application.
      :param blueprints: List of Blueprints that will be registered on the
          Flask application.
      :param converter_entry_points: List of entry points, which specifies
          Werkzeug URL map converters that will be added to
          ``app.url_map.converters``.
      :param converters: Map of Werkzeug URL map converter classes that will
          be added to ``app.url_map.converters``.
      :param wsgi_factory: A callable that will be passed the Flask application
          object in order to overwrite the default WSGI application (e.g. to
          install ``DispatcherMiddleware``).
      :param app_kwargs: Keyword arguments passed to :py:meth:`base_app`.
      :returns: Flask application factory.
  
      Example of a configuration loader:
  
      .. code-block:: python
  
         def my_config_loader(app, **kwargs):
             app.config.from_module('mysite.config')
             app.config.update(**kwargs)
  
      .. note::
  
         `Invenio-Config <https://pythonhosted.org/invenio-config>`_ provides a
         factory creating default configuration loader (see
         :func:`invenio_config.utils.create_config_loader`) which is sufficient
         for most cases.
  
      Example of a WSGI factory:
  
      .. code-block:: python
  
         def my_wsgi_factory(app):
             return DispatcherMiddleware(app.wsgi_app, {'/api': api_app})
  
      .. versionadded: 1.0.0
      """
      def _create_app(**kwargs):
          app = base_app(app_name, **app_kwargs)
          app_created.send(_create_app, app=app)
  
          debug = kwargs.get('debug')
          if debug is not None:
              app.debug = debug
  
          # Load configuration
          if config_loader:
              config_loader(app, **kwargs)
  
          # Load URL converters.
          converter_loader(
              app,
              entry_points=converter_entry_points,
              modules=converters,
          )
  
          # Load application based on entrypoints.
          app_loader(
              app,
              entry_points=extension_entry_points,
              modules=extensions,
          )
  
          # Load blueprints
          blueprint_loader(
              app,
              entry_points=blueprint_entry_points,
              modules=blueprints,
          )
  
          app_loaded.send(_create_app, app=app)
  
          # Replace WSGI application using factory if provided (e.g. to install
          # WSGI middleware).
          if wsgi_factory:
              app.wsgi_app = wsgi_factory(app, **kwargs)
  
          return app
  
      return _create_app