Update code, add API

This commit is contained in:
2025-10-17 14:20:52 +03:00
parent a90875e774
commit ae70bd5619
15 changed files with 717 additions and 5 deletions

8
.idea/.gitignore generated vendored Normal file
View File

@@ -0,0 +1,8 @@
# Default ignored files
/shelf/
/workspace.xml
# Editor-based HTTP Client requests
/httpRequests/
# Datasource local storage ignored files
/dataSources/
/dataSources.local.xml

13
.idea/compiler.xml generated Normal file
View File

@@ -0,0 +1,13 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="CompilerConfiguration">
<annotationProcessing>
<profile name="Maven default annotation processors profile" enabled="true">
<sourceOutputDir name="target/generated-sources/annotations" />
<sourceTestOutputDir name="target/generated-test-sources/test-annotations" />
<outputRelativeToContentRoot value="true" />
<module name="excel-access-migration" />
</profile>
</annotationProcessing>
</component>
</project>

7
.idea/encodings.xml generated Normal file
View File

@@ -0,0 +1,7 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="Encoding">
<file url="file://$PROJECT_DIR$/src/main/java" charset="UTF-8" />
<file url="file://$PROJECT_DIR$/src/main/resources" charset="UTF-8" />
</component>
</project>

20
.idea/jarRepositories.xml generated Normal file
View File

@@ -0,0 +1,20 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="RemoteRepositoriesConfiguration">
<remote-repository>
<option name="id" value="central" />
<option name="name" value="Central Repository" />
<option name="url" value="https://repo.maven.apache.org/maven2" />
</remote-repository>
<remote-repository>
<option name="id" value="central" />
<option name="name" value="Maven Central repository" />
<option name="url" value="https://repo1.maven.org/maven2" />
</remote-repository>
<remote-repository>
<option name="id" value="jboss.community" />
<option name="name" value="JBoss Community repository" />
<option name="url" value="https://repository.jboss.org/nexus/content/repositories/public/" />
</remote-repository>
</component>
</project>

12
.idea/misc.xml generated Normal file
View File

@@ -0,0 +1,12 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="ExternalStorageConfigurationManager" enabled="true" />
<component name="MavenProjectsManager">
<option name="originalFiles">
<list>
<option value="$PROJECT_DIR$/pom.xml" />
</list>
</option>
</component>
<component name="ProjectRootManager" version="2" languageLevel="JDK_25" project-jdk-name="24" project-jdk-type="JavaSDK" />
</project>

6
.idea/vcs.xml generated Normal file
View File

@@ -0,0 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="VcsDirectoryMappings">
<mapping directory="" vcs="Git" />
</component>
</project>

View File

@@ -193,6 +193,7 @@ public class MainController implements Initializable {
// Display INSERT statements for Склад
appendLog("=== ВСТАВКА ДАННЫХ В ТАБЛИЦУ СКЛАД ===");
appendLog("ВНИМАНИЕ: ID товара получается через API запросы к dsol_factory");
for (String statement : sqlResult.getSkladInsertStatements()) {
appendLog(statement);
}

View File

@@ -0,0 +1,56 @@
package com.excelaccess.service;
import com.excelaccess.model.ApiConfig;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
/**
* Отладочный класс для тестирования API с реальными данными
*/
public class ApiDebugTest {
private static final Logger logger = LoggerFactory.getLogger(ApiDebugTest.class);
public static void main(String[] args) {
// Создаем конфигурацию API на основе ваших логов
ApiConfig apiConfig = new ApiConfig();
apiConfig.setBaseUrl("http://dsol-factory.ulan:9000"); // реальный URL
apiConfig.setApiGetLabelId("instruments/api/get_label/");
// Создаем API сервис
ApiService apiService = new ApiService(apiConfig);
// Тестируем с реальными данными из ваших логов
testProduct(apiService, "Заказные интегральные микросхемы в корпусе с кристаллом",
"А6 эт.2", "Заказные интегральные микросхемы в корпусе с кристаллом по договору SBR028-2505220027/024/67 от 06.06.25",
"микросхема", "DS-DD-001197");
testProduct(apiService, "Микросхема 3DV7 512Gbit",
"Сапфир субсидия эт 3 Тех.оснастка", "Микросхема 3DV7 512Gbit",
"Микросхема", "DS-DD-001198");
}
private static void testProduct(ApiService apiService, String name, String nameUpd, String project, String category, String article) {
logger.info("=== TESTING PRODUCT: {} ===", name);
ApiService.ProductSearchData testProduct = new ApiService.ProductSearchData(
name, // name
nameUpd, // name_upd
project, // project
category, // category
article, // article
1, // count
null, // upd
null // date
);
try {
Integer productId = apiService.getProductId(testProduct);
logger.info("RESULT: Product ID = {}", productId);
} catch (Exception e) {
logger.error("ERROR: {}", e.getMessage(), e);
}
logger.info("=== END TEST ===\n");
}
}

View File

@@ -0,0 +1,93 @@
package com.excelaccess.service;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
/**
* Тест парсинга реального ответа API
*/
public class ApiParsingTest {
private static final Logger logger = LoggerFactory.getLogger(ApiParsingTest.class);
public static void main(String[] args) {
// Реальный ответ API из curl запроса
String apiResponse = "{\n" +
" \"state\": 200,\n" +
" \"data\": {\n" +
" \"id\": 34539,\n" +
" \"name_1\": \"Трасса Р110(В)-3-DB9(В)-05\",\n" +
" \"name_2\": \"Трасса Р110(В)-3-DB9(В)-05\",\n" +
" \"cipher\": \"СЧ ОКР МБС Энергия этап 2.1 \",\n" +
" \"type\": \"Кабель\",\n" +
" \"article\": \"DS-CB-000528\",\n" +
" \"count\": 4,\n" +
" \"upd\": \"УПД УТ-1759 08.10.25\",\n" +
" \"date\": \"16.10.2025\",\n" +
" \"cell_num\": null\n" +
" }\n" +
"}";
testParsing(apiResponse);
}
private static void testParsing(String responseBody) {
try {
ObjectMapper objectMapper = new ObjectMapper();
logger.info("Testing API response parsing...");
logger.info("Response: {}", responseBody);
JsonNode rootNode = objectMapper.readTree(responseBody);
logger.info("Parsed JSON structure: {}", rootNode.toPrettyString());
// Ищем ID в различных возможных полях ответа
String[] possibleIdFields = {"id", "product_id", "item_id", "label_id", "ID", "label", "labelId"};
// Сначала проверяем объект data (основной формат API)
if (rootNode.has("data")) {
logger.info("Searching for ID in 'data' object...");
JsonNode dataNode = rootNode.get("data");
if (dataNode.isObject()) {
logger.info("Data is object: {}", dataNode.toPrettyString());
for (String field : possibleIdFields) {
JsonNode node = dataNode.get(field);
logger.info("Checking field '{}' in data object: {}", field, node);
if (node != null && !node.isNull()) {
if (node.isNumber()) {
int id = node.asInt();
logger.info("Found numeric ID {} in data field '{}'", id, field);
if (id > 0) {
logger.info("✅ SUCCESS: Found valid ID {} in data.{}", id, field);
return;
} else {
logger.warn("ID is 0 or negative in data field '{}': {}", field, id);
}
} else if (node.isTextual()) {
try {
int id = Integer.parseInt(node.asText());
logger.info("Found string ID {} in data field '{}'", id, field);
if (id > 0) {
logger.info("✅ SUCCESS: Found valid ID {} in data.{}", id, field);
return;
} else {
logger.warn("ID is 0 or negative in data field '{}': {}", field, id);
}
} catch (NumberFormatException e) {
logger.warn("Не удалось преобразовать ID в число: {}", node.asText());
}
}
}
}
}
}
logger.warn("❌ No valid ID found in response");
} catch (Exception e) {
logger.error("Error parsing API response: {}", e.getMessage(), e);
}
}
}

View File

@@ -0,0 +1,357 @@
package com.excelaccess.service;
import com.excelaccess.model.ApiConfig;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.net.URI;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;
import java.time.Duration;
import java.time.LocalDate;
import java.time.format.DateTimeFormatter;
import java.util.HashMap;
import java.util.Map;
public class ApiService {
private static final Logger logger = LoggerFactory.getLogger(ApiService.class);
private final HttpClient httpClient;
private final ObjectMapper objectMapper;
private final ApiConfig apiConfig;
public ApiService(ApiConfig apiConfig) {
this.apiConfig = apiConfig;
this.httpClient = HttpClient.newBuilder()
.connectTimeout(Duration.ofSeconds(30))
.build();
this.objectMapper = new ObjectMapper();
}
/**
* Получает ID товара через API запрос
*
* @param productData данные товара для поиска
* @return ID товара или null если не найден
*/
public Integer getProductId(ProductSearchData productData) {
if (!isApiConfigured()) {
logger.warn("API не настроен, пропускаем получение ID товара");
return null;
}
try {
logger.debug("Поиск ID товара для: {}", productData.getName());
// Формируем URL для API запроса
String apiUrl = buildApiUrl(productData);
logger.info("API URL: {}", apiUrl);
logger.info("Searching for product with data: {}", productData);
// Формируем данные для POST запроса
String postData = buildPostData(productData);
logger.info("POST data: {}", postData);
logger.info("Equivalent curl command (with swapped name fields):");
logger.info("curl -X POST {} -d \"{}\"", apiUrl, postData.replace("&", "\" -d \""));
logger.info("Note: name and name_upd fields are swapped in API request");
// Создаем HTTP запрос
HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create(apiUrl))
.timeout(Duration.ofSeconds(30))
.header("Content-Type", "application/x-www-form-urlencoded")
.POST(HttpRequest.BodyPublishers.ofString(postData))
.build();
// Выполняем запрос
HttpResponse<String> response = httpClient.send(request,
HttpResponse.BodyHandlers.ofString());
logger.info("API Response status: {}", response.statusCode());
logger.info("API Response body: {}", response.body());
logger.info("API Response headers: {}", response.headers().map());
if (response.statusCode() == 200) {
return parseProductId(response.body());
} else {
logger.warn("API запрос завершился с ошибкой: {} - {}",
response.statusCode(), response.body());
// Проверяем, есть ли ошибка в JSON ответе
try {
JsonNode errorNode = objectMapper.readTree(response.body());
if (errorNode.has("error")) {
logger.error("API Error: {}", errorNode.get("error").asText());
}
if (errorNode.has("state") && errorNode.get("state").asInt() != 200) {
logger.error("API State: {}", errorNode.get("state").asInt());
}
} catch (Exception e) {
logger.debug("Could not parse error response as JSON");
}
return null;
}
} catch (Exception e) {
logger.error("Ошибка при получении ID товара для '{}': {}",
productData.getName(), e.getMessage(), e);
return null;
}
}
/**
* Проверяет, настроен ли API
*/
public boolean isApiConfigured() {
return apiConfig != null
&& apiConfig.getBaseUrl() != null
&& !apiConfig.getBaseUrl().trim().isEmpty()
&& apiConfig.getApiGetLabelId() != null
&& !apiConfig.getApiGetLabelId().trim().isEmpty();
}
/**
* Формирует URL для API запроса (без параметров для POST)
*/
private String buildApiUrl(ProductSearchData productData) {
StringBuilder url = new StringBuilder(apiConfig.getBaseUrl());
// Добавляем endpoint если base_url не заканчивается на /
if (!apiConfig.getBaseUrl().endsWith("/")) {
url.append("/");
}
url.append(apiConfig.getApiGetLabelId());
return url.toString();
}
/**
* Формирует данные для POST запроса
*/
private String buildPostData(ProductSearchData productData) {
Map<String, String> params = new HashMap<>();
// Обязательные поля (всегда отправляем, даже если пустые)
// Поменяли местами: name_upd -> name, name -> name_upd
params.put("name", productData.getNameUpd() != null ? productData.getNameUpd() : "");
params.put("name_upd", productData.getName() != null ? productData.getName() : "");
params.put("project", productData.getProject() != null ? productData.getProject() : "");
params.put("category", productData.getCategory() != null ? productData.getCategory() : "");
params.put("article", productData.getArticle() != null ? productData.getArticle() : "");
params.put("count", String.valueOf(productData.getCount()));
params.put("upd", productData.getUpd() != null ? productData.getUpd() : "");
// Опциональные поля
if (productData.getDate() != null) {
params.put("date", productData.getDate().format(DateTimeFormatter.ofPattern("dd.MM.yyyy")));
}
// Формируем строку для application/x-www-form-urlencoded
StringBuilder postData = new StringBuilder();
boolean first = true;
for (Map.Entry<String, String> entry : params.entrySet()) {
if (!first) {
postData.append("&");
}
postData.append(entry.getKey()).append("=")
.append(java.net.URLEncoder.encode(entry.getValue(), java.nio.charset.StandardCharsets.UTF_8));
first = false;
}
return postData.toString();
}
/**
* Парсит ответ API и извлекает ID товара
*/
private Integer parseProductId(String responseBody) {
try {
logger.info("Parsing API response: {}", responseBody);
JsonNode rootNode = objectMapper.readTree(responseBody);
logger.info("Parsed JSON structure: {}", rootNode.toPrettyString());
// Ищем ID в различных возможных полях ответа
String[] possibleIdFields = {"id", "product_id", "item_id", "label_id", "ID", "label", "labelId"};
// Сначала проверяем объект data (основной формат API)
if (rootNode.has("data")) {
logger.info("Searching for ID in 'data' object...");
JsonNode dataNode = rootNode.get("data");
if (dataNode.isObject()) {
logger.info("Data is object: {}", dataNode.toPrettyString());
for (String field : possibleIdFields) {
JsonNode node = dataNode.get(field);
logger.info("Checking field '{}' in data object: {}", field, node);
if (node != null && !node.isNull()) {
if (node.isNumber()) {
int id = node.asInt();
logger.info("Found numeric ID {} in data field '{}'", id, field);
if (id > 0) {
return id;
} else {
logger.warn("ID is 0 or negative in data field '{}': {}", field, id);
}
} else if (node.isTextual()) {
try {
int id = Integer.parseInt(node.asText());
logger.info("Found string ID {} in data field '{}'", id, field);
if (id > 0) {
return id;
} else {
logger.warn("ID is 0 or negative in data field '{}': {}", field, id);
}
} catch (NumberFormatException e) {
logger.warn("Не удалось преобразовать ID в число: {}", node.asText());
}
}
}
}
} else if (dataNode.isArray() && dataNode.size() > 0) {
logger.info("Data is array with {} elements", dataNode.size());
// Берем первый элемент массива
JsonNode firstItem = dataNode.get(0);
logger.info("First array element: {}", firstItem.toPrettyString());
for (String field : possibleIdFields) {
JsonNode node = firstItem.get(field);
logger.info("Checking field '{}' in array element: {}", field, node);
if (node != null && !node.isNull()) {
if (node.isNumber()) {
int id = node.asInt();
logger.info("Found numeric ID {} in array field '{}'", id, field);
if (id > 0) {
return id;
} else {
logger.warn("ID is 0 or negative in array field '{}': {}", field, id);
}
} else if (node.isTextual()) {
try {
int id = Integer.parseInt(node.asText());
logger.info("Found string ID {} in array field '{}'", id, field);
if (id > 0) {
return id;
} else {
logger.warn("ID is 0 or negative in array field '{}': {}", field, id);
}
} catch (NumberFormatException e) {
logger.warn("Не удалось преобразовать ID в число: {}", node.asText());
}
}
}
}
}
}
// Если ID не найден в data, ищем в корневом объекте
logger.info("Searching for ID in root object...");
for (String field : possibleIdFields) {
JsonNode node = rootNode.get(field);
logger.info("Checking field '{}': {}", field, node);
if (node != null && !node.isNull()) {
if (node.isNumber()) {
int id = node.asInt();
logger.info("Found numeric ID {} in field '{}'", id, field);
if (id > 0) {
return id;
} else {
logger.warn("ID is 0 or negative in field '{}': {}", field, id);
}
} else if (node.isTextual()) {
try {
int id = Integer.parseInt(node.asText());
logger.info("Found string ID {} in field '{}'", id, field);
if (id > 0) {
return id;
} else {
logger.warn("ID is 0 or negative in field '{}': {}", field, id);
}
} catch (NumberFormatException e) {
logger.warn("Не удалось преобразовать ID в число: {}", node.asText());
}
}
}
}
// Проверяем все поля в корневом объекте для отладки
logger.info("All fields in root object:");
rootNode.fieldNames().forEachRemaining(fieldName -> {
JsonNode fieldValue = rootNode.get(fieldName);
logger.info(" {}: {} (type: {})", fieldName, fieldValue, fieldValue.getNodeType());
});
logger.warn("ID товара не найден в ответе API: {}", responseBody);
return null;
} catch (Exception e) {
logger.error("Ошибка при парсинге ответа API: {}", e.getMessage(), e);
return null;
}
}
/**
* Данные товара для поиска через API
*/
public static class ProductSearchData {
private String name;
private String nameUpd;
private String project;
private String category;
private String article;
private Integer count;
private String upd;
private LocalDate date;
// Конструкторы
public ProductSearchData() {}
public ProductSearchData(String name, String nameUpd, String project,
String category, String article, Integer count,
String upd, LocalDate date) {
this.name = name;
this.nameUpd = nameUpd;
this.project = project;
this.category = category;
this.article = article;
this.count = count;
this.upd = upd;
this.date = date;
}
// Getters and Setters
public String getName() { return name; }
public void setName(String name) { this.name = name; }
public String getNameUpd() { return nameUpd; }
public void setNameUpd(String nameUpd) { this.nameUpd = nameUpd; }
public String getProject() { return project; }
public void setProject(String project) { this.project = project; }
public String getCategory() { return category; }
public void setCategory(String category) { this.category = category; }
public String getArticle() { return article; }
public void setArticle(String article) { this.article = article; }
public Integer getCount() { return count; }
public void setCount(Integer count) { this.count = count; }
public String getUpd() { return upd; }
public void setUpd(String upd) { this.upd = upd; }
public LocalDate getDate() { return date; }
public void setDate(LocalDate date) { this.date = date; }
@Override
public String toString() {
return String.format("ProductSearchData{name='%s', nameUpd='%s', project='%s', category='%s', article='%s', count=%d, upd='%s', date=%s}",
name, nameUpd, project, category, article, count, upd, date);
}
}
}

View File

@@ -0,0 +1,59 @@
package com.excelaccess.service;
import com.excelaccess.model.ApiConfig;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
/**
* Тестовый класс для проверки API интеграции
* Этот класс можно использовать для тестирования API запросов
*/
public class ApiServiceTest {
private static final Logger logger = LoggerFactory.getLogger(ApiServiceTest.class);
public static void main(String[] args) {
// Создаем тестовую конфигурацию API
ApiConfig apiConfig = new ApiConfig();
apiConfig.setBaseUrl("https://api.example.com");
apiConfig.setApiGetLabelId("products/search");
// Создаем API сервис
ApiService apiService = new ApiService(apiConfig);
// Проверяем конфигурацию
if (apiService.isApiConfigured()) {
logger.info("API service is properly configured");
} else {
logger.warn("API service is not configured");
}
// Создаем тестовые данные товара
ApiService.ProductSearchData testProduct = new ApiService.ProductSearchData(
"Тестовый товар", // name
"Поставщик товара", // name_upd
"Тестовый проект", // project
"Категория", // category
"ART-001", // article
10, // count
"INV-12345", // upd
java.time.LocalDate.now() // date
);
logger.info("Testing API request with product data: {}", testProduct);
try {
// Выполняем тестовый запрос
Integer productId = apiService.getProductId(testProduct);
if (productId != null) {
logger.info("Successfully retrieved product ID: {}", productId);
} else {
logger.warn("Product ID not found for test product");
}
} catch (Exception e) {
logger.error("Error during API test: {}", e.getMessage(), e);
}
}
}

View File

@@ -127,6 +127,16 @@ public class MigrationService {
// Generate SQL statements
SqlGeneratorService sqlGeneratorService = new SqlGeneratorService();
sqlGeneratorService.setIdCurator(config.getSettings().getIdCurator());
// Настраиваем API сервис если он доступен
if (config.getDsolFactory() != null) {
ApiService apiService = new ApiService(config.getDsolFactory());
sqlGeneratorService.setApiService(apiService);
logger.info("API service configured for product ID lookup");
} else {
logger.warn("API configuration not found, product IDs will be NULL");
}
SqlGeneratorService.SqlGenerationResult sqlResult = sqlGeneratorService.generateSqlQueries(
analysisResult.getProductCards(), analysisResult.getTransactions());

View File

@@ -14,11 +14,16 @@ public class SqlGeneratorService {
private static final Logger logger = LoggerFactory.getLogger(SqlGeneratorService.class);
private int idCurator = 1; // Default value
private ApiService apiService;
public void setIdCurator(int idCurator) {
this.idCurator = idCurator;
}
public void setApiService(ApiService apiService) {
this.apiService = apiService;
}
public SqlGenerationResult generateSqlQueries(List<ProductCard> productCards, List<Transaction> transactions) {
logger.info("Generating SQL queries for {} product cards and {} transactions",
productCards.size(), transactions.size());
@@ -42,6 +47,7 @@ public class SqlGeneratorService {
List<String> statements = new ArrayList<>();
statements.add("-- Вставка данных в таблицу Склад");
statements.add("-- Получение ID товара через API запросы");
for (int i = 0; i < productCards.size(); i++) {
ProductCard card = productCards.get(i);
@@ -52,10 +58,23 @@ public class SqlGeneratorService {
logger.debug("Generating SQL for product card {}: {}", i, card.getName());
// Получаем ID товара через API
Integer productId = getProductIdFromApi(card);
StringBuilder sql = new StringBuilder();
sql.append("INSERT INTO Склад ([Наименование], [Наименование у поставщика], [Проект], [Местоположение], [Категория], [Артикул], [Примечание]) VALUES (");
sql.append(escapeString(truncateString(card.getName(), 255))).append(", ");
sql.append("INSERT INTO Склад ([ID Товара], [Наименование], [Наименование у поставщика], [Проект], [Местоположение], [Категория], [Артикул], [Примечание]) VALUES (");
if (productId != null) {
sql.append(productId).append(", ");
logger.debug("Using API product ID {} for product: {}", productId, card.getName());
} else {
sql.append("NULL, ");
logger.warn("Product ID not found via API for: {}", card.getName());
}
// Поменяли местами: Наименование и Наименование у поставщика
sql.append(escapeString(truncateString(card.getSupplierName(), 255))).append(", ");
sql.append(escapeString(truncateString(card.getName(), 255))).append(", ");
sql.append(escapeString(truncateString(card.getProject(), 255))).append(", ");
sql.append(escapeString(truncateString(card.getLocation(), 255))).append(", ");
sql.append(escapeString(truncateString(card.getCategory(), 255))).append(", ");
@@ -67,7 +86,6 @@ public class SqlGeneratorService {
logger.debug("Added SQL statement for product card: {}", card.getName());
}
return statements;
}
@@ -161,6 +179,53 @@ public class SqlGeneratorService {
return str.substring(0, maxLength);
}
/**
* Получает ID товара через API запрос
*/
private Integer getProductIdFromApi(ProductCard card) {
if (apiService == null || !apiService.isApiConfigured()) {
logger.warn("API service not configured, skipping product ID lookup for: {}", card.getName());
return null;
}
try {
logger.info("=== API LOOKUP START ===");
logger.info("Product name: {}", card.getName());
logger.info("Supplier name: {}", card.getSupplierName());
logger.info("Project: {}", card.getProject());
logger.info("Category: {}", card.getCategory());
logger.info("Article: {}", card.getArticleNumbers());
// Создаем данные для поиска товара
ApiService.ProductSearchData searchData = new ApiService.ProductSearchData(
card.getName(), // name
card.getSupplierName(), // name_upd
card.getProject(), // project
card.getCategory(), // category
card.getArticleNumbers(), // article
1, // count (по умолчанию 1, так как в карточке товара нет количества)
"", // upd (пустая строка вместо null)
null // date (дата - нет в карточке товара)
);
logger.info("Searching for product ID with data: {}", searchData);
Integer productId = apiService.getProductId(searchData);
if (productId != null && productId > 0) {
logger.info("✅ Found product ID {} for: {}", productId, card.getName());
} else {
logger.warn("❌ Product ID not found or is 0 for: {} (returned: {})", card.getName(), productId);
}
logger.info("=== API LOOKUP END ===");
return productId;
} catch (Exception e) {
logger.error("❌ Error getting product ID for '{}': {}", card.getName(), e.getMessage(), e);
return null;
}
}
public static class SqlGenerationResult {
private List<String> skladInsertStatements;
private List<String> transactionsInsertStatements;

View File

@@ -22,6 +22,11 @@
<appender-ref ref="FILE" />
</logger>
<logger name="com.excelaccess.service.ApiService" level="INFO" additivity="false">
<appender-ref ref="CONSOLE" />
<appender-ref ref="FILE" />
</logger>
<logger name="net.ucanaccess" level="WARN" additivity="false">
<appender-ref ref="CONSOLE" />
<appender-ref ref="FILE" />

View File

@@ -99,7 +99,7 @@
"id_curator": 1
},
"dsol_factory": {
"base_url": "",
"api_get_label_id": ""
"base_url": "http://dsol-factory.ulan:9000",
"api_get_label_id": "instruments/api/get_label/"
}
}