Improve error handling

This commit is contained in:
Dominic Ferrando
2026-06-23 19:49:26 -04:00
parent 1ca0fe308d
commit 449b08971f
5 changed files with 116 additions and 137 deletions
+21 -37
View File
@@ -1,5 +1,5 @@
import type { Printful, Webflow } from "./util/types";
import { FetchError, formatSlug, type DeepPartial } from "./util/misc";
import { formatSlug, type DeepPartial } from "./util/misc";
import { WebflowClient } from "./webflow";
import { PrintfulClient } from "./printful";
import { redis } from "bun";
@@ -31,12 +31,12 @@ export class ProductSyncer {
) { }
async sync(printfulProductId?: number) {
await this.setState({ isSyncing: true, syncingIds: [] });
// Populate products
const mainPrintfulProducts: MainProduct[] = [];
const webflowProducts: Webflow.Products.ProductAndSkus[] = [];
try {
await this.setState({ isSyncing: true, syncingIds: [] });
// Populate products
const mainPrintfulProducts: MainProduct[] = [];
const webflowProducts: Webflow.Products.ProductAndSkus[] = [];
let printfulProducts = await this.printful.Products.getAll();
if (printfulProductId) {
const printfulProduct = printfulProducts.find(
@@ -82,17 +82,12 @@ export class ProductSyncer {
});
mainPrintfulProduct.colors.add(productColor);
}
} catch (error) {
await this.setState({ isSyncing: false, syncingIds: [] });
throw error;
}
// TODO: Validate main printful products
// TODO: Validate main printful products
// Sync the main printful products
console.log("Syncing main products...");
for (const mainPrintfulProduct of mainPrintfulProducts) {
try {
// Sync the main printful products
console.log("Syncing main products...");
for (const mainPrintfulProduct of mainPrintfulProducts) {
await this.setState({
isSyncing: true,
syncingIds: mainPrintfulProduct.variants.map(
@@ -161,9 +156,8 @@ export class ProductSyncer {
const webflowProductId =
mainPrintfulProduct.externalId.split("-")[0];
if (!webflowProductId) {
if (!webflowProductId)
throw new Error("Malformed printful product ID");
}
await this.webflow.Products.update(webflowProductId, {
product: {
fieldData: {
@@ -254,10 +248,8 @@ export class ProductSyncer {
);
existingWebflowProduct = await this.webflow.Products.get(webflowProductId);
if (!existingWebflowProduct) {
console.error("Missing webflow product");
throw new Error("Failed to create Webflow product");
}
if (!existingWebflowProduct)
throw new Error("Webflow product missing after create");
for (const specialVariant of mainPrintfulProduct.variants) {
const newPrintfulVariants: DeepPartial<Printful.Products.SyncVariant>[] =
@@ -289,14 +281,16 @@ export class ProductSyncer {
);
}
}
} catch (err) {
if (err instanceof FetchError) {
console.error(err.message, err.payload);
}
}
console.log("Done");
}
finally {
try {
await this.setState({ isSyncing: false, syncingIds: [] });
} catch {
console.error("Failed to reset sync state");
}
}
await this.setState({ isSyncing: false, syncingIds: [] });
console.log("Done");
}
async setState(state: SyncState) {
@@ -323,14 +317,4 @@ export class ProductSyncer {
return productName;
}
}
private async getProductImageUrls(slug: string): Promise<string[]> {
const res = await fetch(`${R2_WORKER_URL}/product-images/${slug}`);
if (!res.ok) {
console.error("Failed to get product image keys:", await res.json());
throw new Error("Failed to get product image keys");
}
const productImageKeys: string[] = (await res.json()) as string[];
return productImageKeys.map((key) => `${WEBSITE_MEDIA_URL}/${key}`);
}
}