Pick your appointment date. PaperPath gives you the latest safe day to request each certificate, apostille and sworn translation, so nothing expires before you hand it in.
Moving a life across a border takes six to fifteen documents. Each one has an issuer, a processing time, a cost, a validity window and things it depends on: birth certificate, then the apostille, then the sworn translation, then an apostille on the translation. Ask for a 90-day criminal record too early and it expires while you wait for the apostille; ask too late and you miss the appointment. Government sites publish flat lists and nobody treats this as a scheduling problem. PaperPath does, starting with Albania to Italy, and it is built for the sworn translators and legalisation agencies who answer "what do I need, and in what order?" all day.
- Plans that work back from the appointment. Choose a recipe and the appointment date; each document gets a safe request window (latest day it can be requested, and for expiring papers the earliest day that still leaves it valid), an expected ready range and its slack. The critical path is marked.
- A timeline worth reading. SVG Gantt from today to the appointment: hatched safe windows, processing bars from fastest to slowest, validity lines, today, the appointment and the two-day buffer before it.
- A checklist that moves the plan. Mark a document requested or in hand. The issue date is checked against its validity on the spot ("expires 1 Oct, before the appointment on 12 Oct"), and a new copy restarts everything that was made from the old one.
- Conflicts in plain words, with the first appointment date that would work and a one-click move to it.
- Recipe library of three sample chains, labelled as samples, dated and sourced: an Albanian birth certificate for Italy, Albanian papers for an Italian residence permit, and a power of attorney from Italy for a property matter in Albania. Each has a dependency diagram and a document table (issuer, where, time, cost, validity, source).
- Your own versions. Fork any recipe, correct times, costs, validity and dependencies, and save it as a new version; the corrections against the sample are listed. Plans keep a frozen copy of the recipe, so later edits never change them.
- For agencies: client details on each plan, a client list, the agency's colour and logo on a read-only share link, and a print view that reads like a document.
- WhatsApp reminders every morning: "request it by" two days before and on the last safe day, and a warning when a document in hand will expire before the appointment. They go to the plan's owner and to the client, each in their own language.
- Dashboard with each plan's next action, overdue steps, the next two weeks of reminders and the agency's clients.
- Albanian and English throughout, phone-first where clients read it.
The scheduler (backend/app/Planning) is plain PHP with no framework in it. Days are integers, so it can try hundreds of dates quickly.
- Working days per issuing country. Weekends and national holidays for Albania, Italy, Germany and Greece. Fixed dates plus the ones that move with Easter, computed with
easter_days(): Catholic Easter for Italy and Germany, Orthodox Easter for Greece, both for Albania, where a holiday on a weekend also gives the next Monday off. Documents counted in calendar days (a consulate booking, some couriers) skip no days. - Backward pass, assuming the slowest times. What is handed in must be in hand two working days before the appointment. A document's latest request day is the day it must be in hand minus its longest processing time, and it must be in hand by the latest request day of everything that needs it.
- Validity. A document that must still be valid at the appointment may not be issued before appointment − validity + 1 day, so it may not be requested before that day minus its shortest processing time. The apostille and the translation inherit that floor; they do not restart the certificate's clock.
- Forward pass from today. Each document is requested as soon as it is allowed and what it needs is in hand; that gives the expected ready range. The critical path is the chain with no float against that finish.
- Conflicts. A window that cannot open, a last safe day already past, a request that may arrive too late, or a copy in hand that expires before the appointment. When the date does not work, the scheduler searches forward day by day, up to a year, for the first appointment date that does.
The recipe graph is validated first: unknown documents, a document that needs itself and circular requirements are refused with the circle spelled out.
- Backend: Laravel 12 on PHP 8.2, PostgreSQL, Sanctum cookie sessions, PHPUnit.
- Frontend: Vue 3.5, Vite, TypeScript, Pinia, vue-router, vue-i18n, Phosphor icons, Source Serif 4 and Source Sans 3. The timeline and the diagram are hand-written SVG.
- Messages: WhatsApp Cloud API, or an in-app outbox with click-to-chat links.
You need PHP 8.2 with pdo_pgsql and calendar, Composer, Node 22 and PostgreSQL.
# database (user and password "paperpath")
createuser -P paperpath
createdb -O paperpath paperpath
createdb -O paperpath paperpath_test
# backend, on :8118
cd backend
composer install
cp .env.example .env
php artisan key:generate
php artisan migrate --seed
php artisan serve --port=8118
# frontend, on :5118 (another terminal)
cd frontend
npm ci
PORT=5118 BACKEND_URL=http://127.0.0.1:8118 npm run devOpen http://localhost:5118 and sign in:
| Account | Password | Role |
|---|---|---|
demo@paperpath.test |
demo1234 |
Ina Kola, owner of Studio Përkthimi Ina, a sworn-translation agency in Tirana |
klea@paperpath.test |
demo1234 |
Klea Duka, member of the same agency |
The demo agency has its own corrected recipe and seven client plans dated relative to the day you seed: on track, one whose criminal record expires before the appointment, one almost done, one whose safe window has not opened yet, one with a step due today, one waiting on a consulate appointment, and one finished and archived.
The morning job is php artisan paperpath:reminders; in production run php artisan schedule:run from cron every minute and it fires at 08:00 Europe/Tirane. In demo mode the Messages page has a button that runs it at once.
Everything lives in backend/.env (see .env.example) and backend/config/product.php.
| Variable | What it does | Without it |
|---|---|---|
APP_PUBLIC_URL |
Base of the links in WhatsApp messages and share links | http://localhost:5173 |
APP_DEMO |
Seeds the demo agency and shows the demo tools | true in the example file |
APP_DEFAULT_TIMEZONE |
What "today" is for new organisations and the 08:00 job | Europe/Tirane |
MESSAGING_DRIVER=whatsapp with WHATSAPP_TOKEN, WHATSAPP_PHONE_NUMBER_ID, WHATSAPP_APP_SECRET, WHATSAPP_VERIFY_TOKEN |
Sends reminders through the WhatsApp Cloud API | Messages stay in the in-app outbox, each with an "Open in WhatsApp" link |
WhatsApp only delivers business-initiated messages through approved templates: map each message key (request_soon, client_request_soon, expiry_warning, ...) to its template in config/product.php under messaging.whatsapp.templates. PaperPath needs no AI keys.
cd backend && php artisan test # 76 tests: scheduler, calendars, API, reminders, sharing, tenancy
cd frontend && npm run type-check && npm test && npm run build-only # 38 testsThe scheduler has unit tests for DAG validation, Easter dates on both calendars, the holidays of all four countries, backward and forward passes, validity windows and inherited floors, conflicts and the search for a workable date. Feature tests cover the recipe library and forks, snapshot immutability (editing a recipe leaves existing plans alone), checklist progress, the reminder job, the public share page (no contact details, notes or ids leak) and tenant isolation.
backend/
app/Planning/ the scheduler: Day, Holidays, WorkingCalendar, RecipeGraph, Scheduler
app/Recipes/ recipe content and translations, forking, corrections diff, saving
app/Plans/ making plans, running the engine on them, reminders (planner and sender)
app/Http/Controllers/ JSON API
database/seeders/ sample recipes (Data/SampleRecipes.php) and the demo agency
tests/Unit/Planning/ scheduler and calendar tests
tests/Feature/ API tests
frontend/
src/lib/ gantt.ts, dag.ts, plan.ts (wording), format.ts (dates and money, Albanian included)
src/components/ GanttChart, DependencyDiagram, StepItem, ConflictPanel, PlanRow, ...
src/views/ dashboard, plans, plan, new plan, print, shared plan, recipes, editor, clients, settings
Recipes are samples, not legal advice: every step should be verified with the issuer, and PaperPath plans the timing without guaranteeing an outcome.
MIT, see LICENSE.





