-
Notifications
You must be signed in to change notification settings - Fork 15
chore: Add agents.md #2849
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Open
FabianDevel
wants to merge
6
commits into
main
Choose a base branch
from
add-agents.md
base: main
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Open
chore: Add agents.md #2849
Changes from all commits
Commits
Show all changes
6 commits
Select commit
Hold shift + click to select a range
db1c0de
chore(Agents): Add AGENTS.md
FabianDevel 204a3b3
chore(Agents): Add some learned preferences
FabianDevel 5b91a32
chore(Agents): Add core agents.md
FabianDevel abd6eb8
chore(Agents): Replace hardcoded SDK versions with build.gradle.kts r…
Copilot f04033a
chore: Bump core
FabianDevel 53ecc5a
chore(Agents): Fix incorrect init references and Gradle task paths in…
Copilot File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,73 @@ | ||
| # AGENTS.md - Infomaniak Mail (Top Level) | ||
|
|
||
| > **Navigation Guide**: This file describes the composite structure. For app-specific norms, see `app/AGENTS.md`. For Core library norms, see `Core/AGENTS.md`. | ||
|
|
||
| ## Repository Structure | ||
|
|
||
| This is a **composite Gradle build** with two main components: | ||
|
|
||
| ``` | ||
| android-kMail/ | ||
| ├── Core/ # Git submodule - shared library (see Core/AGENTS.md) | ||
| │ ├── Auth/ # OAuth2, account management | ||
| │ ├── Network/ # Ktor HTTP client | ||
| │ ├── Ui/ # Compose + XML components | ||
| │ ├── Common/ # Shared utilities | ||
| │ └── ... (30+ modules) | ||
| ├── app/ # Main Mail application (see app/AGENTS.md) | ||
| │ ├── src/main/java/... # Mail app source code | ||
| │ ├── src/main/res/ # Android resources | ||
| │ ├── src/test/ # Unit tests | ||
| │ └── src/androidTest/ # UI tests | ||
| ├── EmojiComponents/ # Custom emoji picker | ||
| ├── HtmlCleaner/ # HTML sanitization | ||
| └── AGENTS.md # This file (top-level overview) | ||
| ``` | ||
|
|
||
| ## Quick Summary | ||
|
|
||
| | Component | Location | AGENTS.md | Purpose | | ||
| |-----------|----------|-----------|---------| | ||
| | **Core** | `Core/` | `Core/AGENTS.md` | Reusable library for all Infomaniak apps | | ||
| | **App** | `app/` | `app/AGENTS.md` | Mail app-specific code and norms | | ||
| | **Root** | `./` | `AGENTS.md` | This file - composite build overview | | ||
|
|
||
| ## Composite Build Explained | ||
|
|
||
| - **Core is a Git submodule**: Changes in `Core/` are tracked separately and shared with other Infomaniak apps | ||
| - **Immediate resolution**: App uses `com.infomaniak.core:<module>` which resolves locally (no Maven publishing needed) | ||
| - **Impact**: Changes to Core affect ALL Infomaniak apps - be careful! | ||
|
|
||
| ## Key Integration Points | ||
|
|
||
| - **Authentication**: App uses `Core:Auth` for OAuth2 (tokens, account management) | ||
| - **Networking**: App uses `Core:Network` with `HttpClientProvider` from `Core:Common` | ||
| - **UI Components**: App uses `Core:Ui:Compose` and `Core:Ui:View` components | ||
| - **Initialization**: `MainApplication.kt` initializes Core via `NetworkConfiguration.init()` and `AuthConfiguration.init()` inside `configureInfomaniakCore()` | ||
|
|
||
| ## Quick Commands | ||
|
|
||
| ```bash | ||
| # Build Mail app | ||
| ./gradlew :app:assembleStandardDebug | ||
|
|
||
| # Build included Core modules | ||
| ./gradlew :Core:Legacy:assemble :Core:Legacy:Confetti:assemble | ||
|
|
||
| # Run all tests | ||
| ./gradlew :app:testStandardDebugUnitTest && ./gradlew :Core:Legacy:test :Core:Legacy:Confetti:test | ||
|
|
||
| # Lint included Core modules (uses ktlint) | ||
| ./gradlew :Core:Legacy:ktlintCheck :Core:Legacy:Confetti:ktlintCheck | ||
| ``` | ||
|
|
||
| ## Important Rules | ||
|
|
||
| 1. **Editing Core**: Core changes affect ALL apps - consider impact carefully | ||
| 2. **Norm separation**: | ||
| - App norms → `app/AGENTS.md` | ||
| - Core norms → `Core/AGENTS.md` | ||
| - Composite structure → this file | ||
| 3. **When working on:** | ||
| - `app/src/...` → read `app/AGENTS.md` | ||
| - `Core/` → read `Core/AGENTS.md` | ||
Submodule Core
updated
12 files
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,205 @@ | ||
| # AGENTS.md - Infomaniak Mail App | ||
|
|
||
| > For the Core library, see `Core/AGENTS.md`. For composite build overview, see root `AGENTS.md`. | ||
|
|
||
| ## Project Summary | ||
|
|
||
| **Infomaniak Mail** is an Android email client application built by Infomaniak Network SA, featuring a modern UI with Jetpack | ||
| Compose, Realm database, and multi-account support. | ||
|
|
||
| ### High-Level Tech Stack | ||
|
|
||
| - **Language**: Kotlin — JVM target set via `javaVersion` in `build.gradle.kts` | ||
| - **Platform**: Android — SDK versions (`appMinSdk`, `appTargetSdk`, `appCompileSdk`) set in `build.gradle.kts` | ||
| - **Build System**: Gradle with Kotlin DSL | ||
| - **Architecture**: MVVM with Repository pattern | ||
| - **Dependency Injection**: Dagger Hilt | ||
| - **Database**: Realm (RealmObject for models) | ||
| - **UI Framework**: Hybrid - Jetpack Compose + XML Views with ViewBinding | ||
| - **Network**: Ktor with Kotlin Serialization | ||
| - **Navigation**: Android Navigation Component with Safe Args | ||
| - **Crash Reporting**: Sentry | ||
| - **Analytics**: Matomo | ||
|
|
||
| ## Context Map | ||
|
|
||
| ``` | ||
| app/src/main/java/com/infomaniak/mail/ | ||
| ├── MainApplication.kt # Entry point, configures core via configureInfomaniakCore() (NetworkConfiguration.init() / AuthConfiguration.init()) | ||
| ├── MainActivity.kt # Main coordinator (682 lines - keep focused) | ||
| ├── data/ # Data layer | ||
| │ ├── cache/ # Realm controllers (ThreadController, etc.) | ||
| │ ├── models/ # Realm entities (Message, Thread, Draft, Mailbox, etc.) | ||
| │ └── api/ # API service interfaces | ||
| ├── di/ # Hilt modules | ||
| ├── ui/ # UI layer | ||
| │ ├── main/ # Inbox, thread list, settings | ||
| │ ├── newMessage/ # Compose new email flow | ||
| │ ├── login/ # Authentication flows | ||
| │ └── alertDialogs/ # Custom dialogs | ||
| ├── utils/ # Utilities and extensions | ||
| ├── workers/ # WorkManager background tasks | ||
| └── receivers/ # BroadcastReceivers (notifications) | ||
|
|
||
| app/src/main/res/ | ||
| ├── layout/ # XML layouts (ViewBinding) | ||
| ├── navigation/ # Navigation graphs | ||
| ├── drawable/ # Vector drawables | ||
| └── ... # Other resources | ||
|
|
||
| app/src/test/ # JUnit unit tests | ||
| app/src/androidTest/ # Espresso UI tests | ||
| ``` | ||
|
|
||
| ## Local Norms | ||
|
|
||
| ### Architecture & Design | ||
|
|
||
| - **MVVM**: Fragment/Activity + ViewModel per screen | ||
| - **Repository**: Data access via controllers (`ThreadController`, `DraftController`) | ||
| - **DI**: Use Hilt `@Inject` constructor | ||
| - **Database**: Models extend `RealmObject` or `EmbeddedRealmObject` | ||
| - **SOLID/KISS**: Keep classes focused; prefer multiple smaller classes over one large class | ||
|
|
||
| ### Commands | ||
|
|
||
| ```bash | ||
| # Build debug | ||
| ./gradlew :app:assembleStandardDebug | ||
|
|
||
| # Build release (requires env.properties with sentryAuthToken) | ||
| ./gradlew :app:assembleStandardRelease | ||
|
|
||
| # Run tests | ||
| ./gradlew :app:testStandardDebugUnitTest | ||
| ./gradlew :app:connectedStandardDebugAndroidTest # UI tests need device | ||
|
|
||
| # Clean | ||
| ./gradlew clean | ||
| ``` | ||
|
|
||
| ### Code Style | ||
|
|
||
| **Line Length:** | ||
|
|
||
| - Maximum **130 characters** per line for Kotlin files | ||
| - Exceptions: single-line comments, import statements, hardcoded strings | ||
|
|
||
| **Blank Lines:** | ||
|
|
||
| - Never use more than 1 consecutive blank line | ||
| - Always add 1 blank line after early return statements/blocks | ||
|
|
||
| **Copyright Headers:** | ||
|
|
||
| - Required in ALL files (including resources) | ||
| - Format: `Copyright (C) YYYY` or `Copyright (C) startYear-endYear` | ||
| - Example: `(C) 2022-2026 Infomaniak Network SA` | ||
| - **No blank line between copyright and package declaration** | ||
|
|
||
| **Naming:** | ||
|
|
||
| - Classes: PascalCase (`MainActivity`, `ThreadController`) | ||
| - Functions/Properties: camelCase (`getThreads()`, `isEmpty`) | ||
| - Packages: lowercase (`com.infomaniak.mail.ui.main`) | ||
| - **New enums**: PascalCase entries (`Active`, `Inactive`) | ||
| - **Old enums**: DO NOT rename (stored in sharedPrefs/Realm - would break) | ||
|
|
||
| **Control Flow:** | ||
|
|
||
| ```kotlin | ||
| // Trivial statements: prefer one-line (under 130 chars) | ||
| if (condition) return result | ||
|
|
||
| // Trivial if/else: prefer one-line | ||
| val color = if (isDark) darkColor else lightColor | ||
|
|
||
| // Non-trivial: always use braces + newlines | ||
| if (condition) { | ||
| doSomething() | ||
| doAnotherThing() | ||
| } | ||
| ``` | ||
|
|
||
| **Jetpack Compose:** | ||
|
|
||
| ```kotlin | ||
| // One parameter: one line (if under 130 chars) | ||
| @Composable | ||
| fun MyButton(onClick: () -> Unit) { | ||
| Text("Click") | ||
| } | ||
|
|
||
| // Multiple parameters: standard formatting with proper indent | ||
| @Composable | ||
| fun MyButton( | ||
| onClick: () -> Unit, | ||
| modifier: Modifier = Modifier | ||
| ) { | ||
| // implementation | ||
| } | ||
| ``` | ||
|
|
||
| **Resources (XML):** | ||
|
|
||
| - Remove `fillColor="#00000000"` (invisible colors auto-added by Figma) | ||
| - Follow Android Studio formatting conventions | ||
| - Use Android Studio's Reformat Code on drawable/ files | ||
|
|
||
| **Kotlin Files:** | ||
|
|
||
| - Follow official Kotlin code style (`kotlin.code.style=official` in gradle.properties) | ||
| - GPL license headers required | ||
|
|
||
| ### UI Development | ||
|
|
||
| - **Hybrid Approach**: Compose for new screens, XML with ViewBinding for existing | ||
| - **Compose**: Material3 components, place in `ui.components.compose` | ||
| - **XML**: ViewBinding with property access syntax, place in `views` | ||
| - **Navigation**: Use Safe Args plugin for type-safe navigation | ||
|
|
||
| ### Testing | ||
|
|
||
| - **Unit Tests**: `app/src/test/java/` | ||
| - JUnit 4 + MockK for mocking | ||
| - Use dummy datasets in `dataset/` package for database tests | ||
| - **UI Tests**: `app/src/androidTest/java/` | ||
| - Espresso for view interactions | ||
| - Pattern: `*ActivityTest.kt` or `*Test.kt` | ||
|
|
||
| ### Product Flavors | ||
|
|
||
| | Flavor | Description | Dependencies | | ||
| |--------------|---------------------------------------------------------|--------------------------| | ||
| | **standard** | Full features, Google Play Services, push notifications | `standardImplementation` | | ||
| | **fdroid** | FOSS variant, no proprietary dependencies | `fdroidImplementation` | | ||
|
|
||
| ### Environment | ||
|
|
||
| - `env.properties`: Required for release builds (sentryAuthToken) | ||
| - `local.properties`: Local SDK paths (auto-generated) | ||
| - Never commit `env.properties` or `local.properties` (see .gitignore) | ||
|
|
||
| ## Learned Preferences | ||
|
|
||
| *Add project-specific corrections here as they occur.* | ||
|
|
||
| **Kotlin Control Flow:** | ||
|
|
||
| - Prefer one-line if/else for trivial statements under 130 chars | ||
| - Always use braces + newlines for non-trivial statements | ||
|
|
||
| **Jetpack Compose:** | ||
|
|
||
| - One-line composables with single parameter (within line limit) | ||
|
|
||
| **Resources (XML):** | ||
|
|
||
| - Remove fillColor="#00000000" (invisible colors from Figma imports) | ||
| - Follow Android Studio formatting on PRs if formatting is off | ||
|
|
||
| ## Self-correction | ||
|
|
||
| 1. **Stale Map**: Update when you encounter new files/folders not listed | ||
| 2. **New Norms**: Add user corrections to "Learned Preferences" immediately | ||
| 3. **Reference Core**: When editing Core imports, check `Core/AGENTS.md` for Core-specific norms |
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@copilot We use composite build, you should put a reference to the :build-logic that is also needed to build core