App Factory & Config

The application factory is a function that builds and returns a configured Flask app on demand, instead of creating one global app at import time — making your project easier to test, configure, and scale.

Learn App Factory & Config in our free Flask course — a beginner-friendly interactive lesson with worked examples, a practice exercise and a quick reference.

Part of the free Flask course at LearnCodingFast — hands-on lessons with examples you run in your browser, plus practice exercises and a quick quiz.

In this lesson you'll write a create_app() factory, organize settings into configuration classes, and load secrets from environment variables.

In small examples you create the app once at the top of app.py . That global app is fine for a demo, but it hard-codes one configuration and makes testing awkward because there is no clean way to build a fresh app with different settings.

The application factory solves this by moving app creation into a function. Each call to create_app() returns a brand-new, fully configured app — ideal for production, development, and tests side by side.

A config class is a plain Python class whose attributes become Flask settings. Put shared values in a base Config class, then subclass it for each environment. Read anything sensitive from an environment variable.

The factory creates the app, loads a config object with app.config.from_object , attaches each extension with init_app , registers routes, and returns the finished app. Extensions are defined once at module level so they can be shared.

When you run flask run , Flask looks for a create_app or make_app factory automatically. You can also choose a config by passing a different class name, like create_app("config.ProductionConfig") .

Complete the factory below. Replace each ___ so it creates the app, loads the config, and binds the database.

❌ RuntimeError: Working outside of application context

You used db or current_app before an app existed. Inside the factory, wrap setup code in with app.app_context(): when you need it.

❌ ImportError: cannot import name 'app' (circular import)

This happens when modules import a global app . The fix is the factory pattern: create extensions without an app and bind them with init_app inside create_app() .

Make your factory accept a config so a test can build an app with an in-memory database.

Lesson 19 complete — your app is structured to scale!

You can now build apps with a create_app() factory, organize settings into config classes, and read secrets from the environment. This is how professional Flask projects are laid out.

🚀 Up next: Testing Flask Apps — use the test client and pytest to prove your routes work before you ship.

Practice quiz

What is the application factory pattern?

  • A global app created at import time
  • A class that subclasses Flask
  • A function that builds and returns a configured app
  • A config file format

Answer: A function that builds and returns a configured app. create_app() builds and returns a configured Flask app on demand.

What is the conventional name for the factory function?

  • create_app
  • make_flask
  • build
  • init_app

Answer: create_app. The factory is usually named create_app().

Which method loads settings from a config class?

  • app.config.from_mapping
  • app.config.from_object
  • app.config.load_class
  • app.config.import_object

Answer: app.config.from_object. app.config.from_object(config_object) loads settings from a class.

How do you bind an extension like SQLAlchemy inside the factory?

  • SQLAlchemy(app) at import
  • db.bind(app)
  • db.attach(app)
  • db.init_app(app)

Answer: db.init_app(app). Create the extension without an app, then call db.init_app(app) inside create_app().

Why create extensions at module level without an app?

  • To avoid circular imports and share them across apps
  • To make them run faster
  • Because Flask requires it
  • To skip configuration

Answer: To avoid circular imports and share them across apps. Creating extensions without an app avoids circular imports and lets apps share them.

Where should secrets like SECRET_KEY come from?

  • Hard-coded in config.py
  • Environment variables via os.environ
  • The HTML template
  • The URL query string

Answer: Environment variables via os.environ. Read secrets from environment variables so they stay out of source code.

Why does the factory pattern make testing easier?

  • It disables routes
  • It removes the need for a database
  • It builds a fresh app with a test config per run
  • It runs tests automatically

Answer: It builds a fresh app with a test config per run. Each create_app() call builds a separate app with whatever config you pass.

What does flask run look for to start the app?

  • A run.py script only
  • A global variable named server
  • An app.run() call
  • A create_app or make_app factory automatically

Answer: A create_app or make_app factory automatically. flask run finds a create_app or make_app factory automatically.

How do you choose a different config when calling the factory?

  • create_app('config.ProductionConfig')
  • create_app(production=True)
  • create_app().use_prod()
  • set FLASK_PROD=1 only

Answer: create_app('config.ProductionConfig'). Pass the config object path, like create_app('config.ProductionConfig').

What does app.config behave like?

  • A read-only tuple
  • A frozen set
  • A dictionary-like object
  • A function

Answer: A dictionary-like object. app.config is a dictionary-like object of settings.