Test-app/app/models/QRCode.server.js
Albez0-An7h 49d55588b0 feat: QR redirection app
- Scanning the QR code app redicts to page
- Option to chose if we want to redirect to page or checkout
2026-03-04 13:36:11 +05:30

105 lines
2.5 KiB
JavaScript

import qrcode from "qrcode";
import invariant from "tiny-invariant";
import db from "../db.server";
export async function getQRCode(id, graphql) {
const qrCode = await db.qRCode.findFirst({ where: { id } });
if (!qrCode) {
return null;
}
return supplementQRCode(qrCode, graphql);
}
export async function getQRCodes(shop, graphql) {
const qrCodes = await db.qRCode.findMany({
where: { shop },
orderBy: { id: "desc" },
});
if (qrCodes.length === 0) return [];
return Promise.all(
qrCodes.map((qrCode) => supplementQRCode(qrCode, graphql))
);
}
export function getQRCodeImage(id) {
const url = new URL(`/qrcodes/${id}/scan`, process.env.SHOPIFY_APP_URL);
return qrcode.toDataURL(url.href);
}
export function getDestinationUrl(qrCode) {
if (qrCode.destination === "product") {
return `https://${qrCode.shop}/products/${qrCode.productHandle}`;
}
const match = /gid:\/\/shopify\/ProductVariant\/([0-9]+)/.exec(qrCode.productVariantId);
invariant(match, "Unrecognized product variant ID");
return `https://${qrCode.shop}/cart/${match[1]}:1`;
}
async function supplementQRCode(qrCode, graphql) {
const qrCodeImagePromise = getQRCodeImage(qrCode.id);
const response = await graphql(
`
query supplementQRCode($id: ID!) {
product(id: $id) {
title
media(first: 1) {
nodes {
preview {
image {
altText
url
}
}
}
}
}
}
`,
{
variables: {
id: qrCode.productId,
},
}
);
const {
data: { product },
} = await response.json();
return {
...qrCode,
productDeleted: !product?.title,
productTitle: product?.title,
productImage: product?.media?.nodes[0]?.preview?.image?.url,
productAlt: product?.media?.nodes[0]?.preview?.image?.altText,
destinationUrl: getDestinationUrl(qrCode),
image: await qrCodeImagePromise,
};
}
export function validateQRCode(data) {
const errors = {};
if (!data.title) {
errors.title = "Title is required";
}
if (!data.productId) {
errors.productId = "Product is required";
}
if (!data.destination) {
errors.destination = "Destination is required";
}
if (Object.keys(errors).length) {
return errors;
}
}