복붙노트

[SPRING] jpa 쿼리에서 사용자 지정 함수를 사용하는 방법?

SPRING

jpa 쿼리에서 사용자 지정 함수를 사용하는 방법?

나는 Spring Jpa와 Hibernate에 익숙하지 않다. Oracle 데이터베이스에서 사용자 지정 함수를 사용하여 데이터를 가져 오려고합니다. 관련 서비스, 구현 및 저장소와 함께 엔티티를 정의 할 수 있습니다. 또한 아래에서 볼 수 있듯이 registerFunction을 사용하여 새로운 사용자 정의 오라클 dialect를 만들었습니다.

그래서 두 가지 질문이 있습니다.

1) 내 오라클 db에서 함수는 다른 스키마 아래에 앉는다. 스키마를 지정해야합니까? 그렇다면 어떻게? 아니면 자동으로 최대 절전 모드로 전환합니까?

내 전체 stacktrace를 제공 ​​한 후이 게시물의 끝에 두 번째 질문을 물어볼 것입니다 ...

다음은 전체 스택 추적입니다.

Oracle10gDialect

package blog;

import org.hibernate.dialect.Oracle10gDialect;
import org.hibernate.dialect.function.StandardSQLFunction;


public class MyOracle10gDialect extends Oracle10gDialect {

    public MyOracle10gDialect() {
        super();
        registerFunction("my_function", new StandardSQLFunction("my_function"));
    }

}

application.properties

...
spring.jpa.database-platform=blog.MyOracle10gDialect
...

실재:

package blog.models;

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.Id;
import javax.persistence.Table;

@Entity
@Table(name = "item", schema = "WOS_SOURCE")
public class WosItem {

    @Id
    @Column(nullable = false)
    private String UT;

    @Column(nullable = false)
    private String TI;

    public String getUT() {
        return UT;
    }

    public void setUT(String UT) {
        this.UT = UT;
    }

    public String getTI() {
        return TI;
    }

    public void setTI(String TI) {
        this.TI = TI;
    }

    public WosItem(String UT, String TI) {
        this.UT = UT;
        this.TI = TI;
    }

    public WosItem() { }

    @Override
    public String toString() {
        return "WosItem{" +
                "UT='" + UT + '\'' +
                ", TI='" + TI + '\'' +
                '}';
    }
}

서비스:

package blog.services;

import blog.models.WosItem;
import org.springframework.stereotype.Service;

import java.util.List;

@Service
public interface WosItemService {

    List<WosItem> findAll();
    WosItem findById(String id);
    String find_ut(Long ut_seq);
}

이행:

package blog.services;

import blog.models.WosItem;
import blog.repositories.WosItemRepository;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.List;

@Service
public class WosItemServiceJpaImpl implements WosItemService {

    @Autowired
    private WosItemRepository wosItemRepository;

    @Override
    public List<WosItem> findAll() {
        return this.wosItemRepository.findAll();
    }

    @Override
    public WosItem findById(String id) {
        return this.wosItemRepository.findOne(id);
    }

    @Override
    public String find_ut(Long ut_seq) {
        return this.wosItemRepository.find_ut();
    }
}

저장소:

package blog.repositories;

import blog.models.WosItem;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.Query;
import org.springframework.stereotype.Repository;


@Repository
public interface WosItemRepository extends JpaRepository<WosItem, String> {
    @Query("SELECT function('my_function', input) FROM WosItem wos");
    String find_ut();
}

그래서 내 Oracle 데이터베이스에서 나는 아래와 같이이 함수를 사용할 수있다.

select other_schema.my_function(aa.input) from my_schema.TABLE aa;

예를 들어. aa.input이 332708100009라고 말하면 000332708100009를 반환합니다.

내 두 번째 질문에 관해서는 :

2) 어떻게이 과정을 일본에서 할 수 있습니까? 내 저장소가 정확하지 않다는 것을 알고 있습니다. '특수 효과는 허용되지 않습니다.'와 같은 오류가 발생합니다. 이 문제를 해결할 방법을 찾지 못했습니다.

미리 감사드립니다.

예외적으로 편집 :

Caused by: java.lang.IllegalStateException: No data type for node: org.hibernate.hql.internal.ast.tree.MethodNode 
 \-[METHOD_CALL] MethodNode: 'function (my_function)'
    +-[METHOD_NAME] IdentNode: 'my_function' {originalText=my_function}
    \-[EXPR_LIST] SqlNode: 'exprList'
       \-[NAMED_PARAM] ParameterNode: '?' {name=ut_seq, expectedType=null}

해결법

  1. ==============================

    1.아쉽게도 Select 문에서 사용자 정의 함수 호출의 JPA 2.1 기능을 사용하려면 사용하기 전에 몇 가지 추가 작업을 수행해야합니다.

    아쉽게도 Select 문에서 사용자 정의 함수 호출의 JPA 2.1 기능을 사용하려면 사용하기 전에 몇 가지 추가 작업을 수행해야합니다.

    where 문에서 사용할 때 추가 작업 없이도 작동하지만 선택 작업 내에서 내 프로젝트 중 하나에 사용하려면 다음과 같이해야합니다.

    1) 최대 절전 모드를 확장하고 함수를 등록하십시오 :

    package com.mypkg.dialect;
    
    import org.hibernate.dialect.Oracle10gDialect;
    import org.hibernate.dialect.function.StandardSQLFunction;
    import org.hibernate.type.StringType;
    
    public class CustomOracle10gDialect extends Oracle10gDialect {
    
        public CustomOracle10gDialect() {
            super();
            registerFunction("my_function"
               , new StandardSQLFunction("my_function", new StringType()));
        }
    }
    

    2) 사용자 정의 구현을 가리 키도록 세션 팩토리의 hibernate.dialect 특성을 편집하십시오.

    <property name="hibernate.dialect" value="com.mypkg.dialect.CustomOracle10gDialect"/>
    

    최신 정보

    특정 스키마에서 함수를 호출해야하는 경우 다음을 제안합니다.

    registerFunction("my_function"
               , new StandardSQLFunction("schema.my_function", new StringType()));
    

    더 읽기 -> 네이티브 함수 호출

  2. from https://stackoverflow.com/questions/42484199/how-to-use-a-custom-function-in-a-jpa-query by cc-by-sa and MIT license