PostgreSQL Error 54023 too_many_arguments: Причины и Решение
- Ошибка выполнения DDL:
ERROR: 54023: functions cannot have more than 100 arguments. - Сбой генерации динамических хранимых процедур внешними фреймворками.
- Отказ вызова API функций в интеграционных решениях между 1С и внешними учетными системами.
- Падение компиляции PL/pgSQL функций со слишком большим списком входных параметров.
1. Архитектурное ограничение аргументов функций
В PostgreSQL определен жесткий системный предел: функция или хранимая процедура может принимать не более 100 аргументов (константа INDEX_MAX_KEYS / FUNC_MAX_ARGS в исходном коде).
2. Рефакторинг: Передача параметров через JSON / JSONB
Вместо передачи десятков отдельных аргументов передавайте единый структурированный объект JSONB:
-- ОШИБОЧНЫЙ ПОДХОД (громоздко и ведет к 54023):
CREATE FUNCTION update_client(p1 int, p2 text, ... p105 text) ...
-- ПРАВИЛЬНЫЙ ПОДХОД:
CREATE OR REPLACE FUNCTION update_client_json(payload jsonb)
RETURNS void AS $$
DECLARE
v_client_id int := (payload->>'client_id')::int;
v_name text := payload->>'name';
v_status text := payload->>'status';
BEGIN
UPDATE clients
SET name = v_name,
status = v_status,
updated_at = clock_timestamp()
WHERE id = v_client_id;
END;
$$ LANGUAGE plpgsql;
-- Вызов:
SELECT update_client_json('{"client_id": 42, "name": "ООО Рога и Копыта", "status": "active"}'::jsonb);
3. Использование составных пользовательских типов (Composite Types)
CREATE TYPE client_data_t AS (
client_id int,
name text,
inn varchar(12),
kpp varchar(9),
address text
);
CREATE OR REPLACE FUNCTION register_client(data client_data_t)
RETURNS void AS $$
BEGIN
INSERT INTO clients (id, name, inn) VALUES (data.client_id, data.name, data.inn);
END;
$$ LANGUAGE plpgsql;
4. Использование массивов и вариативных аргументов (VARIADIC)
Если требуется передавать переменное число однотипных параметров, используйте VARIADIC массив:
CREATE OR REPLACE FUNCTION calculate_total(VARIADIC amounts numeric[])
RETURNS numeric AS $$
SELECT sum(x) FROM unnest(amounts) g(x);
$$ LANGUAGE sql;
SELECT calculate_total(10.5, 20.0, 35.1, 40.2);
Частые вопросы (FAQ)
Почему действует ограничение ровно в 100 аргументов?
Константа FUNC_MAX_ARGS = 100 заложена для оптимизации передачи аргументов через стек C-функций ядра и структуры сопоставления типов в системном каталоге pg_proc.
Влияет ли лимит 100 аргументов на количество параметров в запросе (prepared statements $1, $2...)?
Нет. В параметризованных запросах (Prepared Statements) лимит параметров определяется протоколом и составляет 65535 ($1 ... $65535), ошибка 54023 к ним не относится.
Как этот лимит влияет на процедуры интеграции 1С?
Если внешняя обработка 1С вызывает хранимую функцию в PostgreSQL через COM-соединение или ODBC, попытка передать более 100 параметров напрямую завершится фатальной ошибкой 54023.
Теряется ли валидация типов при упаковке аргументов в JSONB?
При использовании JSONB валидацию типов можно выполнять внутри тела функции через проверки jsonb_typeof() либо проверять схему через JSON Schema расширения.