fixed a bunch of bugs
This commit is contained in:
parent
1699e76dcc
commit
ed9e568d7d
|
|
@ -555,8 +555,6 @@ function generateReportFieldsFunction(report_fields) {
|
|||
window.notifiedAboutRubIl = false;
|
||||
async function getReportFieldValue(frm, reportName, filters, fieldName, aggregation = 'sum') {
|
||||
try {
|
||||
// Отладочное сообщение о начальных фильтрах
|
||||
console.log(\`Запуск отчета \${reportName} с начальными фильтрами:\`, JSON.stringify(filters));
|
||||
|
||||
// Проверка необходимости полей сразу для всех фильтров
|
||||
if (Object.values(filters).some(v => v === "$AyIlSpecial")) {
|
||||
|
|
@ -726,9 +724,6 @@ async function getReportFieldValue(frm, reportName, filters, fieldName, aggregat
|
|||
processedFilters[key] = value;
|
||||
}
|
||||
|
||||
// Отладочное сообщение об обработанных фильтрах
|
||||
console.log(\`ОТЧЕТ API - запуск отчета \${reportName} с фильтрами\`, JSON.stringify(processedFilters));
|
||||
|
||||
// Проверяем кеш для экономии запросов
|
||||
if (!window.reportCache) window.reportCache = {};
|
||||
|
||||
|
|
@ -756,7 +751,6 @@ async function getReportFieldValue(frm, reportName, filters, fieldName, aggregat
|
|||
// Проверяем результат
|
||||
if (result && result.message) {
|
||||
if (result.message.error) {
|
||||
console.log(\`Ошибка при получении данных отчета: \${result.message.error}\`);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
@ -764,8 +758,6 @@ async function getReportFieldValue(frm, reportName, filters, fieldName, aggregat
|
|||
let value = parseFloat(result.message);
|
||||
if (isNaN(value)) value = 0;
|
||||
|
||||
console.log(\`Результат отчета \${reportName}: \${value}\`);
|
||||
|
||||
// Сохраняем в кеш
|
||||
window.reportCache[cacheKey] = {
|
||||
value: value,
|
||||
|
|
@ -775,12 +767,10 @@ async function getReportFieldValue(frm, reportName, filters, fieldName, aggregat
|
|||
return value;
|
||||
}
|
||||
} catch (err) {
|
||||
console.error(\`Ошибка при вызове отчета \${reportName}:\`, err);
|
||||
}
|
||||
|
||||
return 0;
|
||||
} catch (error) {
|
||||
console.error(\`Общая ошибка в getReportFieldValue:\`, error);
|
||||
return 0;
|
||||
}
|
||||
}`;
|
||||
|
|
@ -1262,7 +1252,7 @@ function generateTransformExpressionFunction(universal_fields, report_fields) {
|
|||
let reportCalls = [];
|
||||
|
||||
// === Обработка report(...) ===
|
||||
const reportRegex = /report\\(([^)]+)\\)/g;\n
|
||||
const reportRegex = /report\\\\(([^)]+)\\\\)/g;
|
||||
let match;
|
||||
|
||||
// Находим все вызовы report() в выражении
|
||||
|
|
@ -1340,38 +1330,35 @@ function generateTransformExpressionFunction(universal_fields, report_fields) {
|
|||
${Object.keys(universal_fields).map(fieldId => {
|
||||
const field = universal_fields[fieldId];
|
||||
if (!field || !field.name) return '';
|
||||
return `transformed = transformed.replace(/univ\\(${field.name}\\)/g, "(frm.doc.__universalFields && frm.doc.__universalFields['${fieldId}'] || 0)");`;
|
||||
return `transformed = transformed.replace(/univ\\\\(${field.name}\\\\)/g, "(frm.doc.__universalFields && frm.doc.__universalFields['${fieldId}'] || 0)");`;
|
||||
}).filter(Boolean).join('\n')}
|
||||
|
||||
// === Обработка val() и row() ===
|
||||
const tablePrefixes = ${JSON.stringify([
|
||||
"items", "taxes", "packed_items", "payments", "advances", "timesheets",
|
||||
"payment_schedule", "sales_team", "aksiz_test_table"
|
||||
])};
|
||||
|
||||
for (const prefix of tablePrefixes) {
|
||||
const sumPattern = new RegExp(\`sum\\\\(\${prefix}_([^)]+)\\\\)\`, 'g');
|
||||
const sumPattern = new RegExp(\`sum\\\\\\\\(\${prefix}_([^)]+)\\\\\\\\)\`, 'g');
|
||||
transformed = transformed.replace(sumPattern, (m, f) =>
|
||||
\`(frm.doc["\${prefix}"] && frm.doc["\${prefix}"].reduce((s, r) => s + (parseFloat(r["\${f}"]) || 0), 0) || 0)\`
|
||||
);
|
||||
|
||||
const valPattern = new RegExp(\`val\\\\(\${prefix}_([^)]+)\\\\)\`, 'g');
|
||||
const valPattern = new RegExp(\`val\\\\\\\\(\${prefix}_([^)]+)\\\\\\\\)\`, 'g');
|
||||
transformed = transformed.replace(valPattern, (m, f) =>
|
||||
\`(frm.doc["\${prefix}"] && frm.doc["\${prefix}"].reduce((s, r) => s + (parseFloat(r["\${f}"]) || 0), 0) || 0)\`
|
||||
);
|
||||
}
|
||||
|
||||
if (for_child_table) {
|
||||
// ИСПРАВЛЕНО: корректная обработка row() в контексте табличной части
|
||||
transformed = transformed.replace(/row\\\\(([^)]+)\\\\)/g, (m, f) =>
|
||||
\`(parseFloat(row["\${f}"]) || 0)\`
|
||||
);
|
||||
|
||||
transformed = transformed.replace(/val\\\\(([^)]+)\\\\)/g, (m, f) => {
|
||||
if (f.startsWith(table_name + '_')) {
|
||||
return \`(parseFloat(row["\${f.slice(table_name.length + 1)}"]) || 0)\`;
|
||||
}
|
||||
return \`(parseFloat(frm.doc["\${f}"]) || 0)\`;
|
||||
});
|
||||
|
||||
transformed = transformed.replace(/row\\\\(([^)]+)\\\\)/g, (m, f) =>
|
||||
\`(parseFloat(row["\${f}"]) || 0)\`
|
||||
);
|
||||
} else {
|
||||
transformed = transformed.replace(/val\\\\(([^)]+)\\\\)/g, (m, f) =>
|
||||
\`(parseFloat(frm.doc["\${f}"]) || 0)\`
|
||||
|
|
@ -5757,6 +5744,11 @@ function openTableRowFormulaModal(frm, formulaId = null) {
|
|||
$triggerContainer.empty();
|
||||
$modal.find(".field-groups-container").empty();
|
||||
|
||||
// ИСПРАВЛЕНИЕ: явно очищаем ID формулы, если это новая формула
|
||||
if (!formulaId) {
|
||||
$modal.removeData("formula-id");
|
||||
}
|
||||
|
||||
// Показываем модальное окно с блокировкой контента
|
||||
$modal.find(".modal-content").append('<div class="modal-overlay" style="position:absolute;top:0;left:0;right:0;bottom:0;background:rgba(255,255,255,0.8);z-index:1000;display:flex;align-items:center;justify-content:center;"><div class="text-center"><div class="spinner-border text-primary" role="status"></div><div class="mt-2">Загрузка данных...</div></div></div>');
|
||||
$modal.modal('show');
|
||||
|
|
@ -5894,6 +5886,11 @@ function openTableRowFormulaModal(frm, formulaId = null) {
|
|||
initTriggerDragAndDrop($modal, $triggerContainer);
|
||||
setupTriggerEditableContainer($triggerContainer);
|
||||
|
||||
// ИСПРАВЛЕНИЕ: Добавляем обработчик закрытия модального окна для очистки данных
|
||||
$modal.off('hidden.bs.modal').on('hidden.bs.modal', function() {
|
||||
$modal.removeData("formula-id");
|
||||
});
|
||||
|
||||
// Удаляем блокирующий оверлей
|
||||
$modal.find(".modal-overlay").remove();
|
||||
})
|
||||
|
|
@ -6946,7 +6943,6 @@ function generateTableRowFormulasHandlers(table_row_formulas, functions, target_
|
|||
try {
|
||||
await calculate_table_row_field(frm, tableName, rowIdx, formula.field_name, formula.formula, "refresh");
|
||||
} catch (asyncError) {
|
||||
console.error("Ошибка при асинхронном расчете формулы (порядок " + (formula.order || 10) + "):", asyncError);
|
||||
}
|
||||
})();
|
||||
} else {
|
||||
|
|
@ -6954,13 +6950,11 @@ function generateTableRowFormulasHandlers(table_row_formulas, functions, target_
|
|||
calculate_table_row_field(frm, tableName, rowIdx, formula.field_name, formula.formula, "refresh");
|
||||
}
|
||||
} catch (error) {
|
||||
console.error("Ошибка расчета формулы для " + tableName + "[" + rowIdx + "]." + formula.field_name + " (порядок " + (formula.order || 10) + "):", error);
|
||||
}
|
||||
}
|
||||
});
|
||||
});
|
||||
} catch (error) {
|
||||
console.error("Ошибка инициализации формул строк табличных частей:", error);
|
||||
}
|
||||
}`;
|
||||
|
||||
|
|
@ -6971,6 +6965,7 @@ function generateTableRowFormulasHandlers(table_row_formulas, functions, target_
|
|||
// Функция для расчета значения поля в строке табличной части
|
||||
async function calculate_table_row_field(frm, tableName, rowIndex, fieldName, formula, triggerField) {
|
||||
try {
|
||||
|
||||
if (!frm.doc[tableName] || !frm.doc[tableName][rowIndex]) {
|
||||
return;
|
||||
}
|
||||
|
|
@ -6979,39 +6974,105 @@ async function calculate_table_row_field(frm, tableName, rowIndex, fieldName, fo
|
|||
const cdt = frm.fields_dict[tableName].grid.doctype;
|
||||
const cdn = row.name;
|
||||
|
||||
const { transformed, needsAsync, reportCalls } = transform_expression(formula, true, tableName);
|
||||
// === Обработка report() ===
|
||||
let processedFormula = formula;
|
||||
if (formula.includes("report(")) {
|
||||
// Регулярное выражение для поиска вызовов report()
|
||||
const reportRegex = /report\\(([^)]+)\\)/g;
|
||||
let match;
|
||||
const reportPromises = [];
|
||||
const reportPlaceholders = [];
|
||||
|
||||
let finalExpression = transformed;
|
||||
// Находим все вызовы report() и заменяем их на плейсхолдеры
|
||||
while ((match = reportRegex.exec(formula)) !== null) {
|
||||
const fullMatch = match[0]; // report(fieldName)
|
||||
const fieldName = match[1]; // fieldName
|
||||
|
||||
// Загрузка универсальных полей при необходимости
|
||||
if (formula.includes("univ(") && !frm.doc.__universalFields) {
|
||||
await calculate_universal_fields(frm);
|
||||
// Создаем уникальный плейсхолдер
|
||||
const placeholder = \`__REPORT_PLACEHOLDER_\${reportPromises.length}__\`;
|
||||
|
||||
// Ищем данные отчета в хранилище или используем предопределенный отчет
|
||||
let reportName, reportFilters, reportField, reportAggregation;
|
||||
|
||||
if (fieldName === "testt") {
|
||||
reportName = "General Ledger";
|
||||
reportFilters = {"company":"$DefaultCompany","from_date":"$AyIlSpecial","to_date":"$AyIlSpecial"};
|
||||
reportField = "debit";
|
||||
reportAggregation = "sum";
|
||||
} else {
|
||||
// Ищем в хранилище полей отчетов
|
||||
const reportFields = JSON.parse(frm.doc.report_fields_storage || "{}");
|
||||
const reportObj = Object.values(reportFields).find(f => f.name === fieldName);
|
||||
|
||||
if (reportObj) {
|
||||
reportName = reportObj.report;
|
||||
reportFilters = JSON.parse(reportObj.filters_json || "{}");
|
||||
reportField = reportObj.field_name;
|
||||
reportAggregation = reportObj.aggregation || 'sum';
|
||||
} else {
|
||||
processedFormula = processedFormula.replace(fullMatch, "0");
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
// Обработка вызовов report()
|
||||
if (reportCalls && reportCalls.length > 0) {
|
||||
const reportResults = [];
|
||||
|
||||
for (const call of reportCalls) {
|
||||
const result = await getReportFieldValue(
|
||||
// Добавляем промис запроса к отчету
|
||||
reportPromises.push(
|
||||
getReportFieldValue(
|
||||
frm,
|
||||
call.reportName,
|
||||
call.filters,
|
||||
call.fieldName,
|
||||
call.aggregation
|
||||
reportName,
|
||||
reportFilters,
|
||||
reportField,
|
||||
reportAggregation
|
||||
)
|
||||
);
|
||||
reportResults.push({ placeholder: call.placeholder, value: result });
|
||||
|
||||
// Запоминаем соответствие плейсхолдера и вызова
|
||||
reportPlaceholders.push({
|
||||
placeholder: placeholder,
|
||||
original: fullMatch
|
||||
});
|
||||
|
||||
// Заменяем вызов отчета на плейсхолдер
|
||||
processedFormula = processedFormula.replace(fullMatch, placeholder);
|
||||
}
|
||||
|
||||
for (const result of reportResults) {
|
||||
finalExpression = finalExpression.replace(result.placeholder, result.value);
|
||||
// Если нашли вызовы отчетов, ждем выполнения всех запросов
|
||||
if (reportPromises.length > 0) {
|
||||
const reportResults = await Promise.all(reportPromises);
|
||||
|
||||
// Заменяем плейсхолдеры на результаты
|
||||
for (let i = 0; i < reportPlaceholders.length; i++) {
|
||||
// Убедимся, что результат - числовое значение
|
||||
const reportValue = reportResults[i] !== undefined ? Number(reportResults[i]) : 0;
|
||||
processedFormula = processedFormula.replace(
|
||||
reportPlaceholders[i].placeholder,
|
||||
reportValue
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Вычисление выражения
|
||||
// === Обработка row() ===
|
||||
// Заменяем все вызовы row() на доступ к полям текущей строки
|
||||
let finalFormula = processedFormula;
|
||||
const rowRegex = /row\\(([^)]+)\\)/g;
|
||||
finalFormula = finalFormula.replace(rowRegex, (match, fieldName) => {
|
||||
return \`(parseFloat(row["\${fieldName}"]) || 0)\`;
|
||||
});
|
||||
|
||||
// === Обработка val() ===
|
||||
// Заменяем все вызовы val() на доступ к полям документа
|
||||
const valRegex = /val\\(([^)]+)\\)/g;
|
||||
finalFormula = finalFormula.replace(valRegex, (match, fieldName) => {
|
||||
return \`(parseFloat(frm.doc["\${fieldName}"]) || 0)\`;
|
||||
});
|
||||
|
||||
// Вычисление выражения с доступом к объекту row
|
||||
let result = 0;
|
||||
try {
|
||||
result = eval(finalExpression);
|
||||
// Создаем функцию с доступом к контексту row и frm
|
||||
const evalFunc = new Function('row', 'frm', \`return \${finalFormula};\`);
|
||||
result = evalFunc(row, frm);
|
||||
} catch (e) {
|
||||
}
|
||||
|
||||
|
|
@ -7019,14 +7080,14 @@ async function calculate_table_row_field(frm, tableName, rowIndex, fieldName, fo
|
|||
result = 0;
|
||||
}
|
||||
|
||||
// Устанавливаем вычисленное значение
|
||||
frappe.model.set_value(cdt, cdn, fieldName, result);
|
||||
|
||||
// Обновляем таблицу
|
||||
frm.refresh_field(tableName);
|
||||
} catch (err) {
|
||||
}
|
||||
}
|
||||
`;
|
||||
}`;
|
||||
|
||||
|
||||
functions.push(calculateFunction);
|
||||
|
|
@ -7429,7 +7490,6 @@ async function handle_predefined_events(frm) {
|
|||
}
|
||||
}).join('')}
|
||||
} catch (error) {
|
||||
console.error("Error in predefined events handler:", error);
|
||||
}
|
||||
}`;
|
||||
|
||||
|
|
@ -8300,7 +8360,6 @@ function restoreSpecialDateValues(d, current_filters) {
|
|||
}
|
||||
});
|
||||
} catch (e) {
|
||||
console.error("Error restoring special date values:", e);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -9030,7 +9089,6 @@ function editReportField(frm, fieldId) {
|
|||
fieldCopy.filters_json = JSON.stringify(processedFilters);
|
||||
fieldCopy.__has_special_dates = true; // Маркер для последующего восстановления
|
||||
} catch (e) {
|
||||
console.error("Error processing filters:", e);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -9132,7 +9190,6 @@ function processTableRowFormulas(table_row_formulas, table_doctypes) {
|
|||
|
||||
${usesUniversal || usesReports ? 'await ' : ''}calculate_table_row_field(frm, "${tableName}", rowIndex, "${formula.field_name}", formula, "${trigger}");
|
||||
} catch (error) {
|
||||
console.error("Ошибка вычисления формулы для ${tableName}[${rowIndex - 1}].${formula.field_name}:", error);
|
||||
}
|
||||
}`;
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue