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.