From 806497b24d43f730e0fa0d7bce924ea52115563b Mon Sep 17 00:00:00 2001 From: luklpz Date: Thu, 14 May 2026 21:04:09 +0200 Subject: [PATCH] fix: fetch all Dolibarr products without tms sqlfilter Incremental sync via t.tms filter breaks when products were created before the service started running: their tms is older than lastSyncStart so they are never returned. Since the sync is idempotent (ProductMapping handles create-vs-update), always fetching all products is safe and simpler. Co-Authored-By: Claude Sonnet 4.6 --- .../integration/dolibarr/DolibarrClient.java | 23 +++++-------------- .../sync_service/sync/ProductSyncService.java | 12 +++------- 2 files changed, 9 insertions(+), 26 deletions(-) diff --git a/sync-service/src/main/java/com/teterialosjuanjos/tfg/sync_service/integration/dolibarr/DolibarrClient.java b/sync-service/src/main/java/com/teterialosjuanjos/tfg/sync_service/integration/dolibarr/DolibarrClient.java index 03a3243..308cc10 100644 --- a/sync-service/src/main/java/com/teterialosjuanjos/tfg/sync_service/integration/dolibarr/DolibarrClient.java +++ b/sync-service/src/main/java/com/teterialosjuanjos/tfg/sync_service/integration/dolibarr/DolibarrClient.java @@ -7,9 +7,6 @@ import org.springframework.core.ParameterizedTypeReference; import org.springframework.stereotype.Component; import org.springframework.web.client.RestClient; -import java.time.Instant; -import java.time.ZoneOffset; -import java.time.format.DateTimeFormatter; import java.util.List; import java.util.Map; @@ -24,9 +21,6 @@ import java.util.Map; @Component public class DolibarrClient { - private static final DateTimeFormatter DOLIBARR_DATE_FORMAT = - DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss").withZone(ZoneOffset.UTC); - private final RestClient restClient; public DolibarrClient(@Qualifier("dolibarrRestClient") RestClient restClient) { @@ -36,20 +30,15 @@ public class DolibarrClient { // ── Products ────────────────────────────────────────────────────────── /** - * Returns all products, optionally filtered by last modification date. + * Returns all active products (up to 500). * - * @param modifiedSince if non-null, only products with {@code tms >= modifiedSince} are returned + *

Full fetch on every run keeps sync idempotent and avoids timezone issues + * with Dolibarr's {@code tms} column filter. The service handles create-vs-update + * via {@code ProductMapping}, so re-processing unchanged products is safe.

*/ - public List getProducts(Instant modifiedSince) { + public List getProducts() { return restClient.get() - .uri(u -> { - u.path("/products").queryParam("limit", 500); - if (modifiedSince != null) { - u.queryParam("sqlfilters", - "(t.tms:>=:'%s')".formatted(DOLIBARR_DATE_FORMAT.format(modifiedSince))); - } - return u.build(); - }) + .uri(u -> u.path("/products").queryParam("limit", 500).build()) .retrieve() .body(new ParameterizedTypeReference>() {}); } diff --git a/sync-service/src/main/java/com/teterialosjuanjos/tfg/sync_service/sync/ProductSyncService.java b/sync-service/src/main/java/com/teterialosjuanjos/tfg/sync_service/sync/ProductSyncService.java index 17908e8..0e0404f 100644 --- a/sync-service/src/main/java/com/teterialosjuanjos/tfg/sync_service/sync/ProductSyncService.java +++ b/sync-service/src/main/java/com/teterialosjuanjos/tfg/sync_service/sync/ProductSyncService.java @@ -40,15 +40,9 @@ public class ProductSyncService { private final IntegrationProperties integrationProperties; /** - * Executes a full incremental product push and returns a summary. + * Fetches all Dolibarr products and pushes them to PrestaShop (create or update by SKU). */ public SyncResult synchronize() { - // Determine cutoff BEFORE saving current log to avoid self-reference - Instant lastSyncStart = syncLogRepository - .findFirstBySyncTypeOrderByStartedAtDesc(SyncType.PRODUCT_PUSH) - .map(SyncLog::getStartedAt) - .orElse(null); - SyncLog syncLog = syncLogRepository.save(SyncLog.builder() .syncType(SyncType.PRODUCT_PUSH) .startedAt(Instant.now()) @@ -59,8 +53,8 @@ public class ProductSyncService { List errors = new ArrayList<>(); try { - List products = dolibarrClient.getProducts(lastSyncStart); - log.info("ProductSync: {} products to process (since {})", products.size(), lastSyncStart); + List products = dolibarrClient.getProducts(); + log.info("ProductSync: {} products to process", products.size()); for (DolibarrProductDto product : products) { if (product.ref() == null || product.ref().isBlank()) {