Как исправить генерацию правильного типа значения для параметра INPUT в jOOQ для сгенерированной пользовательской функции PL/pgSQL с использованием тега ‹forcedType›?


У меня возникла проблема с решением проблемы с <forcedType> для хранимой функции, написанной на PL/pgSQL, в моих сгенерированных подпрограммах. Этот вопрос более специфичен для решения проблемы, которую я уже задавал в этот вопрос и ответ частично представлены в этом Вопросы и ответы.

Это ОДНА из моих пользовательских функций в PL/pgSQL, с которой у меня возникли проблемы (я показываю только одну, так как обе функции имеют одинаковый RETURN TYPE и < strong>ВВОДНОЙ параметр):

create or replace function public.get_order_by_order_id(o_id bigint) returns json as
$BODY$
DECLARE
   finalJson json;
BEGIN
   return finalJson;
END;
&BODY&
LANGUAGE 'plpgsql';

Поскольку я использую Maven, это мои принудительные типы pom.xml, которые я использовал для выполнения преобразования (например, в приведенных выше связанных вопросах и ответах):

<forcedType>
    <userType>java.lang.String</userType>
    <converter>
        org.jooq.Converter.ofNullable(org.jooq.JSON.class, String.class, Object::toString, org.jooq.JSON::valueOf)
    </converter>
    <includeExpression>(?i:get_book_by_book_id|return_value)</includeExpression>
</forcedType>
<forcedType>
    <userType>java.lang.Long</userType>
    <converter>
        org.jooq.Converter.ofNullable(Long.class, String.class, Object::toString, java.lang.Long::valueOf)
    </converter>
    <includeExpression>(?i:get_book_by_book_id\.b_id)</includeExpression>
</forcedType>
<forcedType>
    <userType>java.lang.String</userType>
    <converter>
        org.jooq.Converter.ofNullable(org.jooq.JSON.class, String.class, Object::toString, org.jooq.JSON::valueOf)
    </converter>
    <includeExpression>(?i:get_order_by_order_id|return_value)</includeExpression>
</forcedType>
<forcedType>
    <userType>java.lang.Long</userType>
    <converter>
        org.jooq.Converter.ofNullable(Long.class, String.class, Object::toString, java.lang.Long::valueOf)
    </converter>
    <includeExpression>(?i:get_order_by_order_id\.o_id)</includeExpression>
</forcedType>

Когда я щелкаю правой кнопкой мыши свой проект в Project Exporer›Maven›Обновить проект и устанавливаю флажок «Принудительно обновить…», я получаю две следующие ошибки:

Несоответствие типов: невозможно преобразовать параметр ‹ String › в параметр ‹ Long ›

...и вот как выглядит сгенерированный код класса GetBookByBookId.java:

// This class is generated by jOOQ.
@SuppressWarnings({ "all", "unchecked", "rawtypes" })
public class GetBookByBookId extends AbstractRoutine<String> {  
    private static final long serialVersionUID = 1276724822;

    // The parameter <code>public.get_book_by_book_id.RETURN_VALUE</code>.
    public static final Parameter<String> RETURN_VALUE = Internal.createParameter("RETURN_VALUE", org.jooq.impl.SQLDataType.JSON, false, false, org.jooq.Converter.ofNullable(org.jooq.JSON.class, String.class, Object::toString, org.jooq.JSON::valueOf));

     // The parameter <code>public.get_book_by_book_id.b_id</code>.
    // Error is occuring AT NEXT LINE of code for value of "B_ID" variable !!!!!!!!!!
    public static final Parameter<Long> B_ID = Internal.createParameter("b_id", org.jooq.impl.SQLDataType.BIGINT, false, false, org.jooq.Converter.ofNullable(Long.class, String.class, Object::toString, java.lang.Long::valueOf));

    // Create a new routine call instance
    public GetBookByBookId() {
        super("get_book_by_book_id", Public.PUBLIC, org.jooq.impl.SQLDataType.JSON, org.jooq.Converter.ofNullable(org.jooq.JSON.class, String.class, Object::toString, org.jooq.JSON::valueOf));

        setReturnParameter(RETURN_VALUE);
        addInParameter(B_ID);
    }

    // Set the <code>b_id</code> parameter IN value to the routine
    public void setBId(Long value) {
        setValue(B_ID, value);
    }

    // Set the <code>b_id</code> parameter to the function to be used with a {@link org.jooq.Select} statement
    public GetBookByBookId setBId(Field<Long> field) {
        setField(B_ID, field);
        return this;
    }
}

Передача строкового значения strParam в Long.valueOf(strParam) должна работать, но здесь, в jOOQ, это почему-то не работает. Разве компилятор Java не должен сделать вывод из кода org.jooq.Converter.ofNullable(Long.class, String.class, Object::toString, java.lang.Long::valueOf), переданного в <converter>... есть ли что-то, что мне не хватает, и что именно?
Мы очень признательны за любую помощь или предложение.


person NikolaS    schedule 26.06.2020    source источник


Ответы (1)


Вы сделали это дважды:

<forcedType>
    <userType>java.lang.Long</userType>
    <converter>
        org.jooq.Converter.ofNullable(
            Long.class, String.class, Object::toString, java.lang.Long::valueOf
        )
    </converter>
    <includeExpression>...</includeExpression>
</forcedType>

Посмотрите на подпись Converter.ofNullable(). Его:

static <T, U> Converter<T, U> ofNullable(
    Class<T> fromType,
    Class<U> toType,
    Function<? super T, ? extends U> from,
    Function<? super U, ? extends T> to
) { ... }

Где <T> — тип базы данных/JDBC, а <U> — тип пользователя. Вы просто смешиваете два типа. Параметр уже имеет тип Long, и вы пытаетесь преобразовать его в String. Итак, объявите String своим типом пользователя:

<forcedType>
    <userType>java.lang.String</userType>
    ...
</forcedType>
person Lukas Eder    schedule 29.06.2020
comment
Меня смутило, что BIGINT — это <T> тип базы данных, и поэтому я подумал, что Long — это мой пользовательский тип в моем случае, но на самом деле это тип базы данных, а НЕ BIGINT. Поэтому String - мой тип пользователя... глупая ошибка, сделанная часами экспериментов. Лукас еще раз спасибо :) - person NikolaS; 29.06.2020