Habit Tracker with SQLite
A streak is a claim about consecutive days, and the boundary cases are where every naive counter breaks.
- Flutter
- Dart
- SQLite
About this project
Add habits, check them off daily, and see a current streak, an all-time best, and a calendar heatmap per habit — backed by real SQLite via sqflite_common_ffi, the project’s one justified dependency.
The idea it is built around is that a streak is a specific claim — consecutive days, ending at today or yesterday — and getting the boundary cases right is where every naive counter breaks. What happens the moment you check in today. What a missed day does (resets to zero, not to one). Why the all-time best is stored separately rather than recomputed by eyeballing history, and what happens to it when you undo today’s check-in right after it sets a new record. Fifty tests cover this directly against a real database, not a mock.
The project ships as Dart source only — lib/, test/, pubspec.yaml — deliberately without the hundreds of lines of generated Android and Windows platform boilerplate flutter create would normally add. One documented command regenerates both, verified in the README to leave the real source untouched.
What you will learn
- Get the streak boundary cases right: today, a missed day, the all-time best, and why they need separate storage
- Use real SQLite via sqflite_common_ffi on desktop, justified as the project’s one dependency
- Understand why a query surface — "every habit with a streak over 7" — is the reason to reach for SQL at all
- Read and write tests that assert against a real database, not just an in-memory fake
- See a const constructor stop a rebuild, and confirm it by counting builds rather than assuming
Before you start
- Some Flutter — widgets, state, a list view
- Flutter 3.19+ and Dart. The project ships as Dart source only; the README gives the one command that regenerates the platform folders.
Academic integrity notice
These projects are provided for learning, experimentation and reference. Understand the code, modify it for your own requirements, and acknowledge external work according to your institution’s academic policies. Priodemy does not supply work to be submitted as your own.
Features
- Real SQLite via sqflite_common_ffi, with the dependency choice justified rather than assumed
- Correct streak logic at every boundary: today, a missed day, the all-time best going stale and recomputing
- A calendar heatmap per habit, built from real check-in history
- Fifty tests, eighteen of them against the streak algorithm alone, fifteen against a real database
- SQL query-surface examples — "every habit with a current streak over 7" — in one query, not a loop
- Ships as source only; the README’s one command regenerates the platform folders without touching your code
Technology stack
Track: Mobile · Level: Mini project
What is included
- lib/, test/ and pubspec.yaml — commented throughout
- A README on streak boundaries, SQLite on desktop, and why the platform folders are not shipped
- Suggested extensions, including habit categories and a weekly summary notification
Delivered as a 69 KB ZIP. SHA-256 published under Changelog so you can verify it.
System requirements
- Operating system
- Windows, macOS or Linux for desktop; Android also supported
- Runtime
- Flutter 3.19+. flutter create --platforms=windows,android . to add the platform folders, then flutter run.
Licence
Learn from it, change it, and use it in your own coursework and personal projects. Do not resell it or pass it off as your own original work.
- Personal and educational use
- Modifying the code however you like
- Using it as the basis of your own coursework, with honest acknowledgement
- Putting your modified version in a portfolio or on your own GitHub
- Reselling or redistributing the project, modified or not
- Presenting it as your own original work
- Commercial deployment — see the Commercial licence
Support window: 6 months from download.
Frequently asked
Why is there no android/ or windows/ folder in the download?
Because they are hundreds of lines of generated CMake, Gradle and manifest code with nothing hand-written in them, and shipping them would bury the project’s actual content. One documented command regenerates both in place, verified not to touch your source.
Why SQLite instead of the JSON approach other projects in this catalogue use?
Because the query surface is real here — "every habit with a streak over 7", "my longest-ever streak" are natural SQL and get slower by hand as history grows, the same lesson the Python expense manager project teaches with GROUP BY.
Does it run on the web?
No, on purpose. sqflite has no clean web story without a second, heavier plugin, which would break the project’s one-dependency budget. The README explains the trade-off rather than silently picking a worse database for web’s sake.
Changelog
- First release
SHA-256c418e6dc04840b83be67bed2c4f4e30138c6e72e8fe9d10c2992510d2311dddd