diet-guard/docs/flutter-rules-language.md
Krzysztof kuhy Rudnicki 17a2c62f26 Automate CLAUDE.md's structural rules, then cut it to 189 lines
CLAUDE.md was 1101 lines and loaded into every session in this repo. Three
passes, in order: automate what a gate can check, rewrite what is left as
instructions rather than rationale, extract what still does not fit.

Automated. Five prohibitions were enforced by nothing but a paragraph asking a
future reader not to do something; they are now repo_invariants_test.dart:

  - no app/linux/ (a GTK embedder target manages ~20fps at 4K)
  - dart:io only in *_io.dart seams and lib/desktop/ -- this one is why the
    test exists at all, since dart:io does not fail a web *compile*. It throws
    at runtime, so a bad import is a blank white window that the widget tests
    happily pass through.
  - no meal builder / repeat-last-meal / reward prompt
  - no image_picker, no CAMERA permission
  - wrapper port 8732 and the diet-guard-desktop Chrome profile, both pinned
    because IndexedDB is keyed by origin and moving either hides the whole
    local food log

Each guard was canary-tested by breaking the invariant and confirming the
suite goes red -- a guard that cannot fail is decoration.

Rules whose behaviour was already covered (budget epoch seeding, sync merge,
food bank) shrink to a pointer at the test that owns them.

Where a rule's entire value was its rationale ("the removal is the feature"),
the why moved into the name and reason string of the gate that now enforces
it, so it lives somewhere executable instead of somewhere quotable.

Extracted. The vendored flutter/flutter rules were 789 of the 1101 lines --
72% of the file, none of it about this repo. Split into five docs/ topic files
under the cap and linked. Verified content-complete: 664 non-blank lines in,
664 out, zero missing.

Python 692 tests / 100% coverage unchanged; Flutter 548 -> 555 (+7 new).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01MK3HCZrM75sRHL1gL8usve
2026-08-15 16:39:57 +02:00

141 lines
7.3 KiB
Markdown

<!--
Vendored from flutter/flutter docs/rules/rules.md, split across five files
so each stays under this repo's 250-line cap. Upstream content: edit it here
only to re-sync with upstream, not to record decisions about this repo --
those belong in CLAUDE.md.
-->
# Language, style and architecture
_Vendored Flutter/Dart AI rules. See [CLAUDE.md](../CLAUDE.md)._
### Interaction Guidelines
* **User Persona:** Assume the user is familiar with programming concepts but
may be new to Dart.
* **Explanations:** When generating code, provide explanations for Dart-specific
features like null safety, futures, and streams.
* **Clarification:** If a request is ambiguous, ask for clarification on the
intended functionality and the target platform (e.g., command-line, web,
server).
* **Dependencies:** When suggesting new dependencies from `pub.dev`, explain
their benefits.
* **Formatting:** Use the `dart_format` tool to ensure consistent code
formatting.
* **Fixes:** Use the `dart_fix` tool to automatically fix many common errors,
and to help code conform to configured analysis options.
* **Linting:** Use the Dart linter with a recommended set of rules to catch
common issues. Use the `analyze_files` tool to run the linter.
### Project Structure
* **Standard Structure:** Assumes a standard Flutter project structure with
`lib/main.dart` as the primary application entry point.
### Flutter style guide
* **SOLID Principles:** Apply SOLID principles throughout the codebase.
* **Concise and Declarative:** Write concise, modern, technical Dart code.
Prefer functional and declarative patterns.
* **Composition over Inheritance:** Favor composition for building complex
widgets and logic.
* **Immutability:** Prefer immutable data structures. Widgets (especially
`StatelessWidget`) should be immutable.
* **State Management:** Separate ephemeral state and app state. Use a state
management solution for app state to handle the separation of concerns.
* **Widgets are for UI:** Everything in Flutter's UI is a widget. Compose
complex UIs from smaller, reusable widgets.
* **Navigation:** Use a modern routing package like `auto_route` or `go_router`.
For more guidelines around navigation, see the section on [routing](#routing).
### Package Management
* **Pub Tool:** To manage packages, use the `pub` tool, if available.
* **External Packages:** If a new feature requires an external package, use the
`pub_dev_search` tool, if it is available. Otherwise, identify the most
suitable and stable package from pub.dev.
* **Adding Dependencies:** To add a regular dependency, use the `pub` tool, if
it is available. Otherwise, run `flutter pub add <package_name>`.
* **Adding Dev Dependencies:** To add a development dependency, use the `pub`
tool, if it is available, with `dev:<package name>`. Otherwise, run `flutter
pub add dev:<package_name>`.
* **Dependency Overrides:** To add a dependency override, use the `pub` tool, if
it is available, with `override:<package name>:1.0.0`. Otherwise, run `flutter
pub add override:<package_name>:1.0.0`.
* **Removing Dependencies:** To remove a dependency, use the `pub` tool, if it
is available. Otherwise, run `dart pub remove <package_name>`.
### Code Quality
* **Code structure:** Adhere to maintainable code structure and separation of
concerns (e.g., UI logic separate from business logic).
* **Naming conventions:** Avoid abbreviations and use meaningful, consistent,
descriptive names for variables, functions, and classes.
* **Conciseness:** Write code that is as short as it can be while remaining
clear.
* **Simplicity:** Write straightforward code. Code that is clever or
obscure is difficult to maintain.
* **Error Handling:** Anticipate and handle potential errors. Don't let your
code fail silently.
* **Styling:**
* Line length: Lines should be 80 characters or fewer.
* Use `PascalCase` for classes, `camelCase` for
members/variables/functions/enums, and `snake_case` for files.
* **Functions:**
* Keep functions short and with a single purpose.
Strive for less than 20 lines.
* **Testing:** Write code with testing in mind. Use the `file`, `process`, and
`platform` packages, if appropriate, so you can inject in-memory and fake
versions of the objects.
* **Logging:** Use the `logging` package instead of `print`.
### Dart Best Practices
* **Effective Dart:** Follow the official Effective Dart guidelines
(https://dart.dev/effective-dart)
* **Class Organization:** Define related classes within the same library file.
For large libraries, export smaller, private libraries from a single top-level
library.
* **Library Organization:** Group related libraries in the same folder.
* **API Documentation:** Add documentation comments to all public APIs,
including classes, constructors, methods, and top-level functions.
* **Comments:** Write clear comments for complex or non-obvious code. Avoid
over-commenting.
* **Trailing Comments:** Don't add trailing comments.
* **Async/Await:** Ensure proper use of `async`/`await` for asynchronous
operations with robust error handling.
* Use `Future`s, `async`, and `await` for asynchronous operations.
* Use `Stream`s for sequences of asynchronous events.
* **Null Safety:** Write code that is soundly null-safe. Leverage Dart's null
safety features. Avoid `!` unless the value is guaranteed to be non-null.
* **Pattern Matching:** Use pattern matching features where they simplify the
code.
* **Records:** Use records to return multiple types in situations where defining
an entire class is cumbersome.
* **Switch Statements:** Prefer using exhaustive `switch` statements or
expressions, which don't require `break` statements.
* **Exception Handling:** Use `try-catch` blocks for handling exceptions, and
use exceptions appropriate for the type of exception. Use custom exceptions
for situations specific to your code.
* **Arrow Functions:** Use arrow syntax for simple one-line functions.
### Flutter Best Practices
* **Immutability:** Widgets (especially `StatelessWidget`) are immutable; when
the UI needs to change, Flutter rebuilds the widget tree.
* **Composition:** Prefer composing smaller widgets over extending existing
ones. Use this to avoid deep widget nesting.
* **Private Widgets:** Use small, private `Widget` classes instead of private
helper methods that return a `Widget`.
* **Build Methods:** Break down large `build()` methods into smaller, reusable
private Widget classes.
* **List Performance:** Use `ListView.builder` or `SliverList` for long lists to
create lazy-loaded lists for performance.
* **Isolates:** Use `compute()` to run expensive calculations in a separate
isolate to avoid blocking the UI thread, such as JSON parsing.
* **Const Constructors:** Use `const` constructors for widgets and in `build()`
methods whenever possible to reduce rebuilds.
* **Build Method Performance:** Avoid performing expensive operations, like
network calls or complex computations, directly within `build()` methods.
### API Design Principles
When building reusable APIs, such as a library, follow these principles.
* **Consider the User:** Design APIs from the perspective of the person who will
be using them. The API should be intuitive and easy to use correctly.
* **Documentation is Essential:** Good documentation is a part of good API
design. It should be clear, concise, and provide examples.