Loading...
Loading...
Anders & A-Cube S.r.l. / 15 juillet 2025 • 3 min read
Pempel Dashboard est une application mobile production-ready pour la gestion de reçus électroniques, construite sur Expo 53 et React Native 0.79. Elle fournit une expérience offline-first transparente avec authentification mTLS sécurisée, internationalisation complète et standards de qualité code enterprise-grade.
Expo Router (file-based) gère navigation avec app/(tabs)/* et app/modal/*. Couche état Zustand pour Reçus, Auth, UI, Sync et Paramètres. Couche données avec E-Receipt SDK, SQLite et AsyncStorage. Couche sécurité avec expo-mutual-tls, Secure Store et Keychain/Keystore.
Écosystème Expo:
Stack React Native:
Gestion État & Données:
Liste Reçus avec virtualisation:
import { FlashList } from '@shopify/flash-list'
import { useReceiptsStore } from '@/store/receipts'
export default function ReceiptsScreen() {
const { receipts, loading, fetchReceipts } = useReceiptsStore()
return (
<FlashList
data={receipts}
estimatedItemSize={120}
renderItem={({ item }) => <ReceiptCard receipt={item} />}
onRefresh={fetchReceipts}
refreshing={loading}
/>
)
Détails Reçu avec visualisation PDF: Récupération reçu via ID avec possibilité téléchargement et partage PDF. Intégration expo-file-system pour gestion fichiers locale et expo-sharing pour partage multi-app.
Configuration Certificat:
import ExpoMutualTls from '@a-cube-io/expo-mutual-tls'
import * as SecureStore from 'expo-secure-store'
export const setupMTLS = async (credentials: Credentials) => {
try {
// Configure module mTLS
await ExpoMutualTls.configureP12('pempel-app', true)
// Stocke certificat de manière sécurisée
const certificateData = await fetchUserCertificate(credentials)
await ExpoMutualTls.storeP12(
certificateData.p12Base64,
certificateData.password
)
// Stocke metadata dans secure storage
Appels API Authentifiés: SDK EReceipts utilise automatiquement mTLS pour toutes les requêtes avec configuration timeout 30s et gestion erreurs complète.
Stratégie Sync:
export const useSyncManager = () => {
const { lastSync, isSyncing, setLastSync } = useSyncStore()
const syncReceipts = async () => {
const netInfo = await NetInfo.fetch()
if (!netInfo.isConnected) {
return { success: false, reason: 'offline' }
}
setIsSyncing(true)
try {
// Récupère derniers reçus du serveur
const serverReceipts = await receiptsSDK
Configuration Traductions:
import i18n from 'i18next'
import { initReactI18next } from 'react-i18next'
import * as Localization from 'expo-localization'
i18n
.use(initReactI18next)
.init({
compatibilityJSON: 'v3',
resources: {
en: { translation: require('./locales/en.json') },
it: { translation: require('./locales/it.json') },
fr: { translation: require('./locales/fr.json') }
},
lng: Localization.locale.split(
Tooling Qualité Complet:
lint: Linting complet codelint:fix: Fix automatique problèmeslint:check: Linting avec zéro warninglint:unused: Suppression imports inutilisésformat: Formatage Prettiertype:check: Vérification TypeScriptquality:check: Contrôles qualité completsquality:fix: Fix automatique tous problèmesquality:full: Fix et vérification completsRègles Linting Complètes:
Quality Gates Pré-commit:
{
"lint-staged": {
"*.{ts,tsx,js,jsx}": [
"eslint --fix",
"prettier --write",
"tsc-files --noEmit"
]
}
}Remplacement FlatList avec FlashList pour rendu 10x plus rapide. Avant (FlatList): ~16ms par frame pour 1000 items. Après (FlashList): ~2ms par frame pour 1000 items.
Gestion efficace grands datasets avec @tanstack/react-virtual. Rendu uniquement éléments visibles avec overscan 5 items. Calcul dynamique positions éléments avec estimateSize.
Stratégie Mémoïsation:
import { memo, useMemo, useCallback } from 'react'
const ReceiptCard = memo(({ receipt, onPress }) => {
const formattedDate = useMemo(
() => formatDate(receipt.date),
[receipt.date]
)
const handlePress = useCallback(() => {
onPress(receipt.id)
}, [receipt.id, onPress])
return (
<Pressable onPress=
Pempel Dashboard démontre développement mobile production-ready avec Expo et React Native, atteignant qualité enterprise-grade grâce à tooling complet et best practices. Le projet équilibre avec succès performances, sécurité et expérience développeur.
Licence: Propriétaire (A-Cube S.r.l.)