Files
casadoc-app/README.md
T
2026-08-26 23:01:07 +03:00

179 lines
6.2 KiB
Markdown

# CasaDoc — mobile app
Mobile client for the CasaDoc property-document platform, for iOS and Android
from a single codebase.
**Stack:** Expo SDK 52 · React Native 0.76 · expo-router · TypeScript ·
React Query · expo-secure-store · i18n-js.
The app can run against the PHP backend or against in-memory demo data; the
choice is one constant in `src/api/config.ts`.
---
## Features
**Account**
- Login with email and password, bearer token kept in SecureStore, auto-login
on next launch.
- Registration with e-mail code verification.
- Password recovery (request a code, set a new password) and password change
from inside the app.
- Profile editing, avatar, account deletion.
- Interface in Italian and English, following the device language, with a
manual override in the profile.
**Properties**
- List with cover image, address and document counters.
- Detail screen with document categories as folders and recent documents.
- Create and edit, including a map picker for the address (react-native-maps).
**Documents**
- Per-property list, filtered by category and by status.
- Search across every document of every property.
- Expiry tracking: valid, expiring and expired badges, warning banners, and a
dedicated tab listing everything that needs attention.
- Detail screen with an inline preview for images and a card that hands PDFs to
the phone's own viewer; sharing and deletion.
- Editing of name, category and expiry date.
**Adding a document**
- From the file picker, from the photo library, or with the built-in scanner.
- The scanner uses the native document scanner (ML Kit on Android, VisionKit on
iOS) with edge detection and perspective correction, captures several pages
and combines them into one PDF (`src/scanner/scanToPdf.ts`).
**Offline**
- Responses are cached and persisted, so a previously opened screen still shows
its content without a connection; a banner appears while the device is
offline and the data refreshes as soon as it is back.
---
## Getting started
```bash
npm install
```
The scanner, the maps and the file viewer are native modules, so the app needs
a development build rather than Expo Go:
```bash
npx expo run:ios # or: npx expo run:android
npm start # subsequent runs
```
With EAS instead of a local build:
```bash
npx eas build --profile development --platform ios # or android
```
`npm run prebuild` regenerates the native projects (`expo prebuild --clean`);
`ios/` and `android/` are not kept in the repository because everything native
is declared by config plugins in `app.json`, and `npm install` applies
`patches/` through `patch-package`.
When the phone is connected over USB, `npm run reverse` forwards the Metro and
backend ports to it.
---
## Pointing the app at a backend
Everything goes through `src/api/config.ts`:
```ts
export const USE_MOCK = false; // true -> in-memory demo data, no server
```
- `USE_MOCK = true` uses `src/api/mock.ts`: every flow works offline on demo
data, and any credentials are accepted at login.
- `USE_MOCK = false` uses `src/api/real.ts`, mapped to the endpoints in
`openapi.yaml`.
The address of the server comes from two places: `DEV_HOST` in the same file
for development builds, and `expo.extra.apiUrl` in `app.json` for release
builds. A release build must use `https`, because both platforms block plain
HTTP traffic outside development.
The screens import `api` from `@/api` and never know which of the two is
active.
### How documents map to the backend
The screens work with a flat model: a property owns documents, each with a
category and an optional expiry date. The backend nests the same data one level
deeper, as page (slug) → section → document requirement → uploaded files.
`src/api/real.ts` holds that mapping. Reads flatten the structure for display;
writes stay faithful, because the upload screen has the user pick a real
requirement and sends its id.
Two consequences are worth knowing:
- A property's documents are gathered with one request per category page, since
the endpoint serves a single page at a time. The properties list does not pay
that cost — it uses the counters `homes.php` returns.
- There is no endpoint for a single file's metadata, so document screens read
from the list they were opened from.
---
## Project structure
```
app/ expo-router routes
_layout.tsx providers, auth gate
(auth)/ login, register, verify, forgot, reset
(tabs)/ properties · search · expiring · profile
property/[id].tsx property detail
property/add.tsx new property
property/edit/[id].tsx edit property
property/location.tsx map picker for the address
documents/[propertyId].tsx documents of a property
document/[id].tsx document detail and viewer
document/edit/[id].tsx edit a document
profile/edit.tsx profile
profile/password.tsx change password
upload.tsx add a document: file, gallery or scan
src/
api/ config.ts (backend switch), http.ts, types.ts, mock.ts, real.ts
auth/ AuthContext, token in SecureStore
i18n/ en.ts, it.ts, locale detection and override
scanner/ scanToPdf.ts
theme/ design tokens (colours, spacing, radii, typography)
components/ ui.tsx, domain.tsx, forms, AppBar, PdfView, OfflineBanner
lib/ formatting, permissions, files, network, query client
```
---
## Scripts
| | |
|---|---|
| `npm start` | Metro for a development build |
| `npm run ios` / `npm run android` | build and install on device or simulator |
| `npm run prebuild` | regenerate `ios/` and `android/` |
| `npm run typecheck` | TypeScript, no emit |
| `npm run lint` | ESLint |
| `npm run reverse` | forward ports 8081 and 8080 to a USB-connected Android device |
---
## Notes
- Design tokens live in `src/theme/tokens.ts` and are the single source for
colours, spacing, radii and typography. Typography currently maps to the
system font; loading Space Grotesk and Inter through `expo-font` is a change
in that one file.
- Sharing between owners, ownership transfer and reports exist in the backend
contract but are outside the scope of this app.