|
| 1 | +# AGENTS.md |
| 2 | + |
| 3 | +This file provides guidance to AI agents and developers when working with code in this repository. |
| 4 | + |
| 5 | +## Project Overview |
| 6 | + |
| 7 | +pdfrx is a monorepo containing two packages: |
| 8 | + |
| 9 | +1. **pdfrx_engine** (`packages/pdfrx_engine/`) - A platform-agnostic PDF rendering API built on top of PDFium |
| 10 | + - Pure Dart package with no Flutter dependencies |
| 11 | + - Provides core PDF document API and PDFium bindings |
| 12 | + - Can be used independently for non-Flutter Dart applications |
| 13 | + |
| 14 | +2. **pdfrx** (`packages/pdfrx/`) - A cross-platform PDF viewer plugin for Flutter |
| 15 | + - Depends on pdfrx_engine for PDF rendering functionality |
| 16 | + - Provides Flutter widgets and UI components |
| 17 | + - Supports iOS, Android, Windows, macOS, Linux, and Web |
| 18 | + - Uses PDFium for native platforms and PDFium WASM for web platforms |
| 19 | + |
| 20 | +## Development Commands |
| 21 | + |
| 22 | +### Monorepo Management |
| 23 | + |
| 24 | +This project uses pub workspace for managing the multi-package repository. All you have to do is to run `dart pub get` on somewhere in the repo directory. |
| 25 | + |
| 26 | +### Basic Flutter Commands |
| 27 | + |
| 28 | +```bash |
| 29 | +# For the main pdfrx package |
| 30 | +cd packages/pdfrx |
| 31 | +flutter pub get # Install dependencies |
| 32 | +flutter analyze # Run static analysis |
| 33 | +flutter test # Run all tests |
| 34 | +flutter format . # Format code (120 char line width) |
| 35 | + |
| 36 | +# For the pdfrx_engine package |
| 37 | +cd packages/pdfrx_engine |
| 38 | +dart pub get # Install dependencies |
| 39 | +dart analyze # Run static analysis |
| 40 | +dart test # Run all tests |
| 41 | +dart format . # Format code (120 char line width) |
| 42 | +``` |
| 43 | + |
| 44 | +### Platform-Specific Builds |
| 45 | + |
| 46 | +```bash |
| 47 | +# Example app |
| 48 | +cd packages/pdfrx/example/viewer |
| 49 | +flutter run # Run on connected device/emulator |
| 50 | +flutter build appbundle # Build Android App Bundle |
| 51 | +flutter build ios # Build iOS (requires macOS) |
| 52 | +flutter build web --wasm # Build for web |
| 53 | +flutter build linux # Build for Linux |
| 54 | +flutter build windows # Build for Windows |
| 55 | +flutter build macos # Build for macOS |
| 56 | +``` |
| 57 | + |
| 58 | +### FFI Bindings Generation (pdfrx_engine) |
| 59 | + |
| 60 | +- FFI bindings for PDFium are generated using `ffigen` in the pdfrx_engine package. |
| 61 | +- FFI bindings depends on the Pdfium headers which are downloaded during `dart test` on pdfrx_engine (Linux only). |
| 62 | + |
| 63 | +```bash |
| 64 | +# Run on Linux |
| 65 | +cd packages/pdfrx_engine |
| 66 | +dart test |
| 67 | +dart run ffigen # Regenerate PDFium FFI bindings |
| 68 | +``` |
| 69 | + |
| 70 | +## Release Process |
| 71 | + |
| 72 | +Both packages may need to be released when changes are made: |
| 73 | + |
| 74 | +### For pdfrx_engine package updates |
| 75 | + |
| 76 | +1. Update version in `packages/pdfrx_engine/pubspec.yaml` |
| 77 | + - Basically, if the changes are not breaking (or relatively small breaking changes), increment the patch version (X.Y.Z -> X.Y.Z+1) |
| 78 | + - If there are breaking changes, increment the minor version (X.Y.Z -> X.Y+1.0) |
| 79 | + - If there are major changes, increment the major version (X.Y.Z -> X+1.0.0) |
| 80 | +2. Update `packages/pdfrx_engine/CHANGELOG.md` with changes |
| 81 | + - Don't mention CI/CD changes and `CLAUDE.md`/`AGENTS.md` related changes (unless they are significant) |
| 82 | +3. Update `packages/pdfrx_engine/README.md` if needed |
| 83 | +4. Update `README.md` on the repo root if needed |
| 84 | +5. Run `dart pub publish` in `packages/pdfrx_engine/` |
| 85 | + |
| 86 | +### For pdfrx package updates |
| 87 | + |
| 88 | +1. Update version in `packages/pdfrx/pubspec.yaml` |
| 89 | + - If pdfrx_engine was updated, update the dependency version |
| 90 | +2. Update `packages/pdfrx/CHANGELOG.md` with changes |
| 91 | +3. Update `packages/pdfrx/README.md` with new version information |
| 92 | + - Changes version in example fragments |
| 93 | + - Consider to add notes for new features or breaking changes |
| 94 | + - Notify the owner if you find any issues with the example app or documentation |
| 95 | +4. Update `README.md` on the repo root if needed |
| 96 | +5. Run `dart pub get` to update all dependencies |
| 97 | +6. Run tests to ensure everything works |
| 98 | + - Run `dart test` in `packages/pdfrx_engine/` |
| 99 | + - Run `flutter test` in `packages/pdfrx/` |
| 100 | +7. Ensure the example app builds correctly |
| 101 | + - Run `flutter build web --wasm` in `packages/pdfrx/example/viewer` to test the example app |
| 102 | +8. Commit changes with message "Release pdfrx vX.Y.Z" or "Release pdfrx_engine vX.Y.Z" |
| 103 | +9. Tag the commit with `git tag pdfrx-vX.Y.Z` or `git tag pdfrx_engine-vX.Y.Z` |
| 104 | +10. Push changes and tags to remote |
| 105 | +11. Run `flutter pub publish` in `packages/pdfrx/` |
| 106 | +12. If the changes reference GitHub issues or PRs, add comments on them notifying about the new release |
| 107 | + - Use `gh issue comment` or `gh pr comment` to notify that the issue/PR has been addressed in the new release |
| 108 | + - If the PR references issues, please also comment on the issues |
| 109 | + - Follow the template below for comments (but modify it as needed): |
| 110 | + |
| 111 | + ```md |
| 112 | + The FIX|UPDATE|SOMETHING for this issue has been released in v[x.y.z](https://pub.dev/packages/pdfrx/versions/x.y.z). |
| 113 | + |
| 114 | + ...Fix/update summary... |
| 115 | + |
| 116 | + Written by [AGENT SIGNATURE] |
| 117 | + ``` |
| 118 | + |
| 119 | + - Focus on the release notes and what was fixed/changed rather than upgrade instructions |
| 120 | + - Include a link to the changelog for the specific version |
| 121 | + |
| 122 | +## Architecture Overview |
| 123 | + |
| 124 | +### Package Architecture |
| 125 | + |
| 126 | +The project is split into two packages with clear separation of concerns: |
| 127 | + |
| 128 | +#### pdfrx_engine (`packages/pdfrx_engine/`) |
| 129 | + |
| 130 | +- Platform-agnostic PDF rendering engine |
| 131 | +- Conditional imports to support different platforms: |
| 132 | + - `lib/src/native/` - Native platform implementation using PDFium via FFI |
| 133 | + - `lib/src/web/` - Web implementation using PDFium WASM |
| 134 | + - Platform-specific code determined at import time based on `dart:library.io` availability |
| 135 | +- Main exports: |
| 136 | + - `pdf_api.dart` - Core PDF document interfaces |
| 137 | + |
| 138 | +#### pdfrx (`packages/pdfrx/`) |
| 139 | + |
| 140 | +- Flutter plugin built on top of pdfrx_engine |
| 141 | +- Contains all Flutter-specific code: |
| 142 | + - Widget layer |
| 143 | + - Platform channel implementations |
| 144 | + - UI components and overlays |
| 145 | + |
| 146 | +### Core Components |
| 147 | + |
| 148 | +1. **Document API** (in `packages/pdfrx_engine/lib/src/pdf_api.dart`) |
| 149 | + - `PdfDocument` - Main document interface |
| 150 | + - `PdfPage` - Page representation |
| 151 | + - `PdfDocumentRef` - Reference counting for document lifecycle |
| 152 | + - Platform-agnostic interfaces implemented differently per platform |
| 153 | + |
| 154 | +2. **Widget Layer** (in `packages/pdfrx/lib/src/widgets/`) |
| 155 | + - `PdfViewer` - Main viewer widget with multiple constructors |
| 156 | + - `PdfPageView` - Single page display |
| 157 | + - `PdfDocumentViewBuilder` - Safe document loading pattern |
| 158 | + - Overlay widgets for text selection, links, search |
| 159 | + |
| 160 | +3. **Native Integration** |
| 161 | + - pdfrx_engine uses Dart FFI for PDFium integration |
| 162 | + - Native code in `packages/pdfrx_engine/src/pdfium_interop.cpp` |
| 163 | + - Platform folders in `packages/pdfrx/` contain Flutter plugin build configurations |
| 164 | + |
| 165 | +### Key Patterns |
| 166 | + |
| 167 | +- **Factory Pattern**: `PdfDocumentFactory` creates platform-specific implementations |
| 168 | +- **Builder Pattern**: `PdfDocumentViewBuilder` for safe async document loading |
| 169 | +- **Overlay System**: Composable overlays for text, links, annotations |
| 170 | +- **Conditional Imports**: Web vs native determined at compile time |
| 171 | + |
| 172 | +## Testing |
| 173 | + |
| 174 | +Tests download PDFium binaries automatically for supported platforms. Run tests with: |
| 175 | + |
| 176 | +```bash |
| 177 | +# Test pdfrx_engine |
| 178 | +cd packages/pdfrx_engine |
| 179 | +dart test |
| 180 | + |
| 181 | +# Test pdfrx Flutter plugin |
| 182 | +cd packages/pdfrx |
| 183 | +flutter test |
| 184 | +``` |
| 185 | + |
| 186 | +## Platform-Specific Notes |
| 187 | + |
| 188 | +### iOS/macOS |
| 189 | + |
| 190 | +- Uses pre-built PDFium binaries from [GitHub releases](https://github.com/espresso3389/pdfrx/releases) |
| 191 | +- CocoaPods integration via `packages/pdfrx/darwin/pdfrx.podspec` |
| 192 | +- Binaries downloaded during pod install (Or you can use Swift Package Manager if you like) |
| 193 | + |
| 194 | +### Android |
| 195 | + |
| 196 | +- Uses CMake for native build |
| 197 | +- Requires Android NDK |
| 198 | +- Downloads PDFium binaries during build |
| 199 | + |
| 200 | +### Web |
| 201 | + |
| 202 | +- `packages/pdfrx/assets/pdfium.wasm` is prebuilt PDFium WASM binary |
| 203 | +- `packages/pdfrx/assets/pdfium_worker.js` is the worker script that contains Pdfium WASM's shim |
| 204 | +- `packages/pdfrx/assets/pdfium_client.js` is the code that launches the worker and provides the API, which is used by pdfrx_engine's web implementation |
| 205 | + |
| 206 | +### Windows/Linux |
| 207 | + |
| 208 | +- CMake-based build |
| 209 | +- Downloads PDFium binaries during build |
| 210 | + |
| 211 | +## Code Style |
| 212 | + |
| 213 | +- Single quotes for strings |
| 214 | +- 120 character line width |
| 215 | +- Relative imports within lib/ |
| 216 | +- Follow flutter_lints with custom rules in analysis_options.yaml |
| 217 | + |
| 218 | +## Dependency Version Policy |
| 219 | + |
| 220 | +### pdfrx_engine |
| 221 | + |
| 222 | +This package follows standard Dart package versioning practices. |
| 223 | + |
| 224 | +### pdfrx |
| 225 | + |
| 226 | +This package intentionally does NOT specify version constraints for core Flutter-managed packages (collection, ffi, http, path, rxdart). This design decision allows: |
| 227 | + |
| 228 | +- Flutter SDK to manage these dependencies based on the user's Flutter version |
| 229 | +- Broader compatibility across different Flutter stable versions |
| 230 | +- Avoiding version conflicts for users on older Flutter stable releases |
| 231 | + |
| 232 | +When running `flutter pub publish`, warnings about missing version constraints for these packages can be safely ignored. Only packages that are not managed by Flutter SDK should have explicit version constraints. |
| 233 | + |
| 234 | +## Documentation Guidelines |
| 235 | + |
| 236 | +The following guidelines should be followed when writing documentation including comments, `README.md`, and other markdown files: |
| 237 | + |
| 238 | +- Use proper grammar and spelling |
| 239 | +- Use clear and concise language |
| 240 | +- Use consistent terminology |
| 241 | +- Use proper headings for sections |
| 242 | +- Use code blocks for code snippets |
| 243 | +- Use bullet points for lists |
| 244 | +- Use link to relevant issues/PRs when applicable |
| 245 | +- Use backticks (`` ` ``) for code references and file/directory/path names in documentation |
| 246 | + |
| 247 | +### Commenting Guidelines |
| 248 | + |
| 249 | +- Use reference links for classes, enums, and functions in documentation |
| 250 | +- Use `///` (dartdoc comments) for public API comments (and even for important private APIs) |
| 251 | + |
| 252 | +### Markdown Documentation Guidelines |
| 253 | + |
| 254 | +- Include links to issues/PRs when relevant; `#NNN` -> `[#NNN](https://github.com/espresso3389/pdfrx/issues/NNN)` |
| 255 | +- Use link to [API reference](https://pub.dev/documentation/pdfrx/latest/pdfrx/) for public APIs if possible |
| 256 | +- `README.md` should provide an overview of the project, how to use it, and any important notes |
| 257 | +- `CHANGELOG.md` should follow the [Keep a Changelog](https://keepachangelog.com/en/1.0.0/) principles |
| 258 | + - Be careful not to include implementation details in the changelog |
| 259 | + - Focus on user-facing changes, new features, bug fixes, and breaking changes |
| 260 | + - Use sections for different versions |
| 261 | + - Use bullet points for changes |
| 262 | + |
| 263 | +## Command Execution Guidelines |
| 264 | + |
| 265 | +- Run commands directly in the repository environment; do not rely on any agent sandbox when executing them. |
| 266 | +- If a command cannot be executed without sandboxing, pause and coordinate with the user so it runs on their machine as needed. |
| 267 | +- On Windows, use `pwsh.exe -Command ...` to run any commands to reduce issues caused by missing .bat/.cmd and shebang on shell-scripts |
| 268 | + |
| 269 | +## Special Notes |
| 270 | + |
| 271 | +- `CHANGELOG.md` is not an implementation node. So it should be updated only on releasing a new version |
0 commit comments