A user opens the app, types a departure station, and sees the ticket price for tomorrow. One click — a car diagram with occupied seats. Another click — a PDF ticket with a QR code that works offline. That's what a mobile app for railway tickets looks like, and we develop such solutions. With 30+ projects and experience working with transport APIs: Tutu.ru, UFS, Express-3. Here's how to do it right.
What Problems We Solve
Integration with monolithic APIs. Express-3 is a legacy system from Russian Railways with SOAP/XML; it's slow under peak loads. Aggregators like Tutu.ru provide JSON in ~200 ms but require caching and error handling. We build a middleware layer: retries with exponential backoff, fallback to UFS on timeouts.
Seat selection in a car. Compartment, open-plan, SV — each has its own layout. Data arrives as an array of seats with coordinates. Deserialization of heavy responses (up to 500 KB) is a bottleneck. On iOS we use DispatchQueue.global(qos: .userInitiated), on Android Dispatchers.IO.
Offline access to tickets. After payment, the QR code of the itinerary receipt is stored locally. On iOS — PDFKit, on Android — PdfRenderer. Push notifications via FCM/APNs handle schedule changes.
How We Develop a Railway Ticket App
The process — from analysis to deployment. We use a modern stack: Swift 5.9 + SwiftUI (iOS) / Kotlin + Jetpack Compose (Android) or Flutter 3.x for cross-platform.
- Analysis and prototype. We define the API (Tutu.ru / UFS / Ticketcloud), draw screens. We document refund logic and dynamic pricing.
- Design. We develop data schemas, routing, error handling. We configure code signing and provisioning profiles.
- Implementation. We write modules: search, seat selection, payment (StoreKit 2 / Google Billing 6), ticket storage. We embed deep linking (Universal Links / App Links) for transitioning from push notifications.
- Testing. TestFlight / Firebase App Distribution. We test scenarios: interrupted payment, refund, weak signal.
- Deployment. We publish to App Store and Google Play. We comply with App Store Review Guidelines and Google Play Policy.
Case in point: for one client, integration with Tutu.ru API took 2 weeks. The issue was that their endpoint didn't support batch requests. We parallelized calls using Combine (iOS) and coroutines (Android). Response time for 10 stations — 800 ms instead of 2 seconds.
Why Is Offline Ticket Access Critical?
The app must work in metro, tunnels, and areas with poor coverage. The QR code of the itinerary receipt is generated on the server but stored locally in PDF. For rendering, we use PDFKit on iOS and PdfRenderer on Android. This ensures the conductor can scan the ticket even without internet. Additionally, we sign the code via push notifications: when the schedule changes, FCM/APNs deliver a short signal, and the app updates cached data on the next connection.
Comparison of Aggregator APIs
| API | Format | Speed | Refunds | Dynamic Pricing |
|---|---|---|---|---|
| Tutu.ru | JSON | ~200 ms | No direct support | Yes |
| UFS | XML | ~400 ms | Yes | Yes |
| Ticketcloud | JSON | ~300 ms | Yes, 2% commission | No |
Tutu.ru is 2x faster — critical for searches with 10+ requests.
Which Payment Methods Are Supported?
SBP (instant, no commission), YooKassa, PSB. Apple Pay via PKPaymentRequest, Google Pay via PaymentsClient. Without these, conversion drops by 20%. The choice of payment provider affects confirmation speed: SBP credits funds in seconds, while card transactions can take up to 3 minutes.
Comparison of Payment Methods
| Method | User Commission | Speed | Notes |
|---|---|---|---|
| SBP | 0% | Instant | No amount limit |
| YooKassa | 0-2% | Up to 1 minute | Supports cards and SBP |
| Apple Pay | 0% | 1-2 seconds | Requires Face ID / Touch ID |
| Google Pay | 0% | 1-2 seconds | Requires biometrics |
How Does Dynamic Pricing Work?
In Express-3, the price rises as seats decrease. We show the dynamics in the train card: if seats are below a certain threshold, we highlight the price. For accurate calculation, we use Tutu.ru or UFS API with 5-minute caching.
And Ticket Refund — How Does It Work?
Refund is a separate API call. Penalties: up to 8 hours before departure — full refund minus fee; less than 8 hours — 50% of the price. We do not implement calculation logic on the client side.
What Is Included in Turnkey Development
- Integration documentation with the chosen API
- Source code of the app (iOS/Android)
- Build and publication to App Store and Google Play
- Test access via TestFlight/Firebase
- Client team training (2 hours online)
- 1 month post-release support
Why Choose Us
Experience with transport APIs for many years, completed 30+ projects. Certified iOS and Android developers. We guarantee compliance with App Store Review Guidelines and Google Play Policy.
Timeframes and Cost
6–8 weeks for an app with search, seat selection, payment, refund, and trip history via an aggregator API. Under tight deadlines, we can deliver in 5 weeks if the API is already chosen. Cost is calculated individually. Get a consultation — we'll evaluate your project within 1 day. Contact us to discuss details.







