如何在JPA中动态创建序列生成器

4
我想通过动态地将序列名称order_sequence传递给这个类来重用计数器,如何实现呢?
public class Counter  {
    
    @Id
    @GeneratedValue(generator = "sequence-generator")
    @GenericGenerator(name = "sequence-generator", strategy = "org.hibernate.id.enhanced.SequenceStyleGenerator", parameters = {
            @Parameter(name = "sequence_name", value = "order_sequence"),
            @Parameter(name = "initial_value", value = "1"), @Parameter(name = "increment_size", value = "1") })
    private Long counter;

}

“重用”是什么意思?您是否想在MappedSuperClass中定义JPA注释,并在子类中定义特定序列? - Andrey B. Panfilov
是的,我想要重用Counter定义,但从扩展的子类中将变量sequence_name和其他值作为动态参数传递。 - user352290
你使用哪种数据库引擎,Oracle 还是 MySQL 等等? - shareef
2
为什么你需要这个?在你的数据库和实体内定义静态序列会更容易理解,也更容易实现。我想不出有什么用处可以解决你可能会遇到的问题。并且即使谈论到这一点:不要修复不存在的问题! - Pwnstar
1个回答

1

主要思路是以以下方式覆盖org.hibernate.id.enhanced.SequenceStyleGenerator

@Target(TYPE)
@Retention(RUNTIME)
@Inherited
public @interface EntityAwareGeneratorParams {

    String sequence();

}

public class EntityAwareGenerator extends SequenceStyleGenerator {

    public static final String NAME = EntityAwareGenerator.class.getName();

    @Override
    public void configure(Type type, Properties params, ServiceRegistry serviceRegistry) throws MappingException {
        String entityName = params.getProperty(ENTITY_NAME);
        if (entityName == null) {
            throw new IllegalStateException("Entity name must not be null");
        }

        Class<?> entityClass = serviceRegistry.requireService(ClassLoaderService.class)
                .classForName(entityName);

        EntityAwareGeneratorParams generatorParams = entityClass.getAnnotation(EntityAwareGeneratorParams.class);
        if (generatorParams == null) {
            throw new IllegalStateException(String.format(
                    "Annotation @%s is not present for class %s",
                    EntityAwareGeneratorParams.class.getName(),
                    entityClass.getName()
            ));
        }

        params.setProperty(SEQUENCE_PARAM, generatorParams.sequence());

        super.configure(type, params, serviceRegistry);
    }

}

MappedSuperClass:

@Id
@GeneratedValue(generator = "entity-aware-generator", strategy = GenerationType.SEQUENCE)
@GenericGenerator(name = "entity-aware-generator", strategy = EntityAwareGenerator.NAME, ...)
private Long id;

子类:

@Entity
@EntityAwareGeneratorParams(sequence="another sequence")

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接