Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/hibernate/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java Hibernate:通过注释使用动态表名的数据对象_Java_Hibernate_Annotations - Fatal编程技术网

Java Hibernate:通过注释使用动态表名的数据对象

Java Hibernate:通过注释使用动态表名的数据对象,java,hibernate,annotations,Java,Hibernate,Annotations,我有一个与表关联的Hibernate数据类;想象实体人是这样的: @Entity @org.hibernate.annotations.Proxy(lazy=false) @Table(name="Person", schema="MySchema") @Inheritance(strategy=InheritanceType.SINGLE_TABLE) public class ProfileData implements Serializable { private st

我有一个与表关联的Hibernate数据类;想象实体人是这样的:

 @Entity
 @org.hibernate.annotations.Proxy(lazy=false)
 @Table(name="Person", schema="MySchema")
 @Inheritance(strategy=InheritanceType.SINGLE_TABLE)
 public class ProfileData implements Serializable {

    private static final long serialVersionUID = -844564646821609090L;

    public PersonData() {
    }

    @Column(name="idPerson", nullable=false, unique=true)   
    @Id 
    ...
我需要按此表格的年份创建历史表格:Person2010、Person2011、Person2012。。。是否可以不创建新的数据对象?也许是一个参数。。。?我不知道


实体类是相同的,更改了表名和构造函数。

您应该尝试查找历史数据。

在Hibernate中,您将一个类映射到一个表。不能重用同一实体动态映射多个表


对于历史数据来说,这是一个非常好的解决方案,但您仍然无法完成您尝试的操作(动态增加表的数量,而不涉及映射器实体)。

多亏了@CodeBrickie和@edutesoy,我找到了Envers

我使用AUD后缀配置hibernate配置文件,并每年使用年份后缀创建新的hibernate配置文件(hibernate.cfg.2009.xml、hibernate.cfg.2010.xml、hibernate.cfg.2011.xml…)

保存数据时,始终在AUD表中审核。在1月1日,自动:

  • _AUD表重命名为“过去年份表”
  • 将创建一个新的_AUD表
  • 将使用新后缀创建一个新的hibernate.cfg.pass_year.xml
当我需要获取数据时,我加载相应的hibernate配置文件


希望这对其他人有所帮助:)

另一种架构,更复杂但优雅:

,您可以使用NamingStrategies更改表名:

而且,当您想使用_year表时,必须创建一个具有Hibernate的会话,该会话覆盖表名:

  SessionFactory sessionFactory;
  Configuration config = new AnnotationConfiguration()
                         .configure("hibernate.cfg.xml")
                         .setNamingStrategy( new MyNamingStrategy () );
  sessionFactory = config.buildSessionFactory();
  session = sessionFactory.openSession();
对于我的架构,我每年创建一个会话,并将其存储到应用程序映射中,以便在需要时进行访问

谢谢

@Table(name="emd_employee_1001")
例如,在上面的注释中,文件名可以作为参数传递

x=1001 
@Table(name="emd_employee_+x+")
在运行时修改(我认为这是最好的方法):


谢谢你。我将为我的应用程序研究它。如果它解决了我的问题,我会将你的答案设置为正确:)Envers很简单,也许是解决方案,但。。。如何动态设置审核表后缀?我需要将数据按年份分开,因为每个表有数百万个数据,我需要搜索。谢谢你为什么不能只搜索一张桌子?一个好的数据库管理系统应该能够处理这个问题。我不能。我需要按年份将数据存储在表中。它的效率更高。我将尝试每年使用不同的hibernate配置创建一个会话…为什么您如此确信使用单独的表更有效?谢谢。我将为我的应用程序研究它。如果它解决了我的问题,我会将你的答案设置为正确:)Envers很简单,也许是解决方案,但。。。如何动态设置审核表后缀?我需要将数据按年份分开,因为每个表有数百万个数据,我需要搜索。谢谢你不能。ORMs并没有为您提供那么高的灵活性,如果您真的想采用您提出的糟糕设计,那么您将不得不放弃Hibernate和Envers并使用直接SQL。好吧,不知道整个设计的糟糕设计有点傲慢。根据我选择的年份,我可以完成加载hibernate配置文件所需的操作。是的,好的,但一旦数据对象初始化,我就无法更改名称。这是一个SQL查询。这在多个数据库(Oracle DB、Microsoft SQL Server、Sybase)上无法正常工作。编写不在多个数据库上工作的SQL代码非常容易。
x=1001 
@Table(name="emd_employee_+x+")
Session session = super.getSession();
    SQLQuery query = session.createSQLQuery("raw sql");
    query.setParameter(":abc", "value");
    query.addEntity(Some.class);
    return query.list();