Découvrez comment le passage à une application Web progressive a aidé MishiPay.
MishiPay permet aux clients de scanner et de payer leurs achats avec leur smartphone, au lieu de perdre du temps à faire la queue à la caisse. Grâce à la technologie Scan & Go de MishiPay, les clients peuvent utiliser leur propre téléphone pour scanner le code-barres des articles et les payer, puis simplement quitter le magasin. Des études révèlent que les files d'attente en magasin coûtent environ 200 milliards de dollars par an au secteur du commerce mondial.
Notre technologie repose sur les fonctionnalités matérielles de l'appareil, telles que les capteurs GPS et les caméras, qui permettent aux utilisateurs de localiser les magasins compatibles avec MishiPay, de scanner les codes-barres des articles dans le magasin physique, puis de payer avec le mode de paiement numérique de leur choix. Les versions initiales de notre technologie Scan &Go étaient des applications iOS et Android spécifiques à la plate-forme, et les utilisateurs de la première heure ont adoré cette technologie. Poursuivez votre lecture pour découvrir comment le passage à une PWA a permis de multiplier le nombre de transactions par 10 et d'économiser 2,5 années de mise en file d'attente.
10×
Augmentation du nombre de transactions
2 ans et demi
Mise en file d'attente enregistrée
Défi
Les utilisateurs trouvent notre technologie extrêmement utile lorsqu'ils font la queue ou attendent à la caisse, car elle leur permet de passer devant la file d'attente et de profiter d'une expérience fluide en magasin. Mais la complexité du téléchargement d'une application Android ou iOS a empêché les utilisateurs de choisir notre technologie, malgré son intérêt. C'était un défi croissant pour MishiPay, et nous devions accroître l'adoption par les utilisateurs en réduisant les barrières à l'entrée.
Solution
Nos efforts de création et de lancement de la PWA nous ont permis de supprimer les tracas liés à l'installation et d'encourager les nouveaux utilisateurs à essayer notre technologie dans un magasin physique, à passer devant la file d'attente et à bénéficier d'une expérience d'achat fluide. Depuis le lancement, nous avons constaté un pic d'adoption par les utilisateurs avec notre PWA par rapport à nos applications spécifiques à la plate-forme.
Présentation détaillée technique
Trouver des magasins compatibles avec MishiPay
Pour activer cette fonctionnalité, nous nous appuyons sur l'API getCurrentPosition()
ainsi qu'une solution de remplacement basée sur l'adresse IP.
const geoOptions = {
timeout: 10 * 1000,
enableHighAccuracy: true,
maximumAge: 0,
};
window.navigator.geolocation.getCurrentPosition(
(position) => {
const cords = position.coords;
console.log(`Latitude : ${cords.latitude}`);
console.log(`Longitude : ${cords.longitude}`);
},
(error) => {
console.debug(`Error: ${error.code}:${error.message}`);
/**
* Invoke the IP based location services
* to fetch the latitude and longitude of the user.
*/
},
geoOptions,
);
Cette approche a bien fonctionné dans les versions précédentes de l'application, mais s'est révélée par la suite très problématique pour les utilisateurs de MishiPay, pour les raisons suivantes:
- Inexactitudes de localisation dans les solutions de remplacement basées sur l'adresse IP.
- La liste croissante des magasins compatibles avec MishiPay par région oblige les utilisateurs à faire défiler une liste et à identifier le bon magasin.
- Il arrive que les utilisateurs choisissent accidentellement le mauvais magasin, ce qui entraîne l'enregistrement incorrect des achats.
Pour résoudre ces problèmes, nous avons intégré des codes QR géolocalisés uniques sur les écrans en magasin de chaque magasin. Cela a permis d'accélérer l'intégration. Pour accéder à l'application Web Scan & Go, les utilisateurs doivent simplement scanner les codes QR géolocalisés imprimés sur les supports marketing présents dans les magasins.
Ils peuvent ainsi éviter de saisir l'adresse Web mishipay.shop
pour accéder au service.
Scanner des produits
L'une des fonctionnalités essentielles de l'application MishiPay est la lecture des codes-barres, car elle permet à nos utilisateurs de scanner leurs propres achats et de voir le total cumulé avant même qu'ils n'aient atteint la caisse enregistreuse.
Pour créer une expérience d'analyse sur le Web, nous avons identifié trois couches principales.
Flux vidéo
La méthode getUserMedia()
nous permet d'accéder à la caméra de vue arrière de l'utilisateur avec les contraintes indiquées ci-dessous. L'appel de la méthode déclenche automatiquement une invite invitant les utilisateurs à accepter ou à refuser l'accès à leur caméra. Une fois que nous avons accès au flux vidéo, nous pouvons le transmettre à un élément vidéo, comme illustré ci-dessous :
/**
* Video Stream Layer
* https://developer.mozilla.org/docs/Web/API/MediaDevices/getUserMedia
*/
const canvasEle = document.getElementById('canvas');
const videoEle = document.getElementById('videoElement');
const canvasCtx = canvasEle.getContext('2d');
fetchVideoStream();
function fetchVideoStream() {
let constraints = { video: { facingMode: 'environment' } };
if (navigator.mediaDevices !== undefined) {
navigator.mediaDevices
.getUserMedia(constraints)
.then((stream) => {
videoEle.srcObject = stream;
videoStream = stream;
videoEle.play();
// Initiate frame capture - Processing Layer.
})
.catch((error) => {
console.debug(error);
console.warn(`Failed to access the stream:${error.name}`);
});
} else {
console.warn(`getUserMedia API not supported!!`);
}
}
Couche de traitement
Pour détecter un code-barres dans un flux vidéo donné, nous devons capturer régulièrement des images et les transférer vers la couche décodeur. Pour capturer un frame, nous dessinons simplement les flux de VideoElement
sur un HTMLCanvasElement
à l'aide de la méthode drawImage()
de l'API Canvas.
/**
* Processing Layer - Frame Capture
* https://developer.mozilla.org/en-US/docs/Web/API/Canvas_API/Manipulating_video_using_canvas
*/
async function captureFrames() {
if (videoEle.readyState === videoEle.HAVE_ENOUGH_DATA) {
const canvasHeight = (canvasEle.height = videoEle.videoHeight);
const canvasWidth = (canvasEle.width = videoEle.videoWidth);
canvasCtx.drawImage(videoEle, 0, 0, canvasWidth, canvasHeight);
// Transfer the `canvasEle` to the decoder for barcode detection.
const result = await decodeBarcode(canvasEle);
} else {
console.log('Video feed not available yet');
}
}
Pour les cas d'utilisation avancés, cette couche effectue également certaines tâches de prétraitement telles que le recadrage, la rotation ou la conversion en niveaux de gris. Ces tâches peuvent être gourmandes en ressources processeur et entraîner l'absence de réponse de l'application, car la lecture de codes-barres est une opération de longue durée. Grâce à l'API OffscreenCanvas, nous pouvons transférer la tâche intensive de processeur à un worker Web. Sur les appareils compatibles avec l'accélération graphique matérielle, l'API WebGL et son WebGL2RenderingContext
peuvent optimiser les gains sur les tâches de prétraitement qui sollicitent fortement le processeur.
Couche du décodeur
La dernière couche est la couche décodeur, qui est chargée de décoder les codes-barres à partir des images capturées par la couche de traitement. Grâce à l'API Shape Detection (qui n'est pas encore disponible sur tous les navigateurs), le navigateur décode lui-même le code-barres d'un élément ImageBitmapSource
, qui peut être un élément img
, un élément SVG image
, un élément video
, un élément canvas
, un objet Blob
, un objet ImageData
ou un objet ImageBitmap
.
/**
* Barcode Decoder with Shape Detection API
* https://web.dev/shape-detection/
*/
async function decodeBarcode(canvas) {
const formats = [
'aztec',
'code_128',
'code_39',
'code_93',
'codabar',
'data_matrix',
'ean_13',
'ean_8',
'itf',
'pdf417',
'qr_code',
'upc_a',
'upc_e',
];
const barcodeDetector = new window.BarcodeDetector({
formats,
});
try {
const barcodes = await barcodeDetector.detect(canvas);
console.log(barcodes);
return barcodes.length > 0 ? barcodes[0]['rawValue'] : undefined;
} catch (e) {
throw e;
}
}
Pour les appareils qui ne sont pas encore compatibles avec l'API Shape Detection, nous avons besoin d'une solution de remplacement pour décoder les codes-barres. L'API Shape Detection expose une méthode getSupportedFormats()
qui permet de basculer entre l'API Shape Detection et la solution de remplacement.
// Feature detection.
if (!('BarceodeDetector' in window)) {
return;
}
// Check supported barcode formats.
BarcodeDetector.getSupportedFormats()
.then((supportedFormats) => {
supportedFormats.forEach((format) => console.log(format));
});
Solution de remplacement
Plusieurs bibliothèques d'analyse Open Source et d'entreprise sont disponibles et peuvent être facilement intégrées à n'importe quelle application Web pour implémenter l'analyse. Voici quelques-unes des bibliothèques recommandées par MishiPay.
Toutes les bibliothèques ci-dessus sont des SDK complets qui composent toutes les couches décrites ci-dessus. Ils exposent également des interfaces pour prendre en charge diverses opérations de numérisation. En fonction des formats de codes-barres et de la vitesse de détection requise pour le cas d'utilisation, vous pouvez choisir entre des solutions Wasm et non Wasm. Malgré la surcharge liée à la nécessité d'une ressource supplémentaire (Wasm) pour décoder le code-barres, les solutions Wasm surpassent la solution non Wasm en termes de précision.
Scandit était notre premier choix. Elle est compatible avec tous les formats de code-barres requis pour nos cas d'utilisation professionnels et surpasse toutes les bibliothèques Open Source disponibles en termes de vitesse d'exploration.
L'avenir de la numérisation
Une fois que l'API de détection de forme sera entièrement compatible avec tous les principaux navigateurs, nous pourrons peut-être disposer d'un nouvel élément HTML <scanner>
doté des fonctionnalités requises pour un lecteur de codes-barres. L'équipe d'ingénieurs de MishiPay estime qu'il existe un cas d'utilisation solide pour que la fonctionnalité de lecture de codes-barres devienne un nouvel élément HTML, en raison du nombre croissant de bibliothèques Open Source et sous licence qui permettent des expériences telles que le scan and go et bien d'autres.
Conclusion
La fatigue liée aux applications est un problème auquel les développeurs sont confrontés lorsque leurs produits arrivent sur le marché. Les utilisateurs veulent souvent comprendre la valeur d'une application avant de la télécharger. Dans un magasin, où MishiPay fait gagner du temps aux clients et améliore leur expérience, il est contre-intuitif d'attendre un téléchargement avant de pouvoir utiliser une application. C'est là que notre PWA est utile. En éliminant cette barrière, nous avons multiplié nos transactions par 10 et permis à nos utilisateurs d'économiser 2,5 ans d'attente dans la file d'attente.
Remerciements
Cet article a été relu par Joe Medley.