`
iamlotus
  • 浏览: 108520 次
  • 性别: Icon_minigender_1
  • 来自: 上海
文章分类
社区版块
存档分类
最新评论

在toplink中映射nested table

阅读更多

nested table是Oracle所特有的一种实现,作为被Oracle收购了的OR-Mapping工具Toplink,自然也应该对其提供支持。但是在寻找这个的过程中,又一次深深体会到了Toplink文档的稀少(OTN,也只有OTN)以及语焉不详(我就不信有人看着官方文档能调出来的)。为以后起见,这里记录一下吧。

 

假设有以下的nested table:

 

CREATE OR REPLACE TYPE STUDENT_TYPE AS OBJECT
(
  STUDENT_ID   NUMBER(4),
  STUDENT_NAME VARCHAR2(10)
);

CREATE OR REPLACE TYPE STUDENT_LIST IS TABLE OF STUDENT_TYPE;

CREATE TABLE SCHOOL(SCHOOL_ID NUMBER(2) primary key, SCHOOL_NAME VARCHAR2(14),
 STUDENTS STUDENT_LIST) NESTED TABLE STUDENTS store AS STUDENTS_TAB;


ALTER TABLE STUDENTS_TAB add CONSTRAINT UK_STUDENTS_TAB UNIQUE(STUDENT_ID);

 

和以下的JO

public class School {
    private int id;

    private String name;

    private List<Student> students;

    //skip  getter, setter
}

 

public class Student {
    private int id;
    private String name;

    // skip getter,setter
    
    
    
}

 

那么相应的Descriptor应该这么写

 

 

 public ClassDescriptor buildSchoolDescriptor() {

        ObjectRelationalDescriptor descriptor = new ObjectRelationalDescriptor();
        descriptor.setJavaClass(School.class);
        descriptor.addTableName("SCHOOL");
        descriptor.addPrimaryKeyFieldName("SCHOOL.SCHOOL_ID");

        DirectToFieldMapping idMapping = new DirectToFieldMapping();
        idMapping.setAttributeName("id");
        idMapping.setFieldName("SCHOOL_ID");
        descriptor.addMapping(idMapping);

        DirectToFieldMapping nameMapping = new DirectToFieldMapping();
        nameMapping.setAttributeName("name");
        nameMapping.setFieldName("SCHOOL.SCHOOL_NAME");
        descriptor.addMapping(nameMapping);

        ObjectArrayMapping studentsMapping = new ObjectArrayMapping();
        studentsMapping.setReferenceClass(Student.class);
        studentsMapping.setAttributeName("students");
        studentsMapping.setFieldName("STUDENTS");
        studentsMapping.setStructureName("STUDENT_LIST");
        descriptor.addMapping(studentsMapping);

        return descriptor;

    }

 

 public ClassDescriptor buildStudentDescriptor() {

        ObjectRelationalDescriptor descriptor = new ObjectRelationalDescriptor();
        descriptor.setJavaClass(Student.class);
        descriptor.descriptorIsAggregate();
        descriptor.setStructureName("STUDENT_TYPE");
        descriptor.addPrimaryKeyFieldName("id");
        descriptor.addFieldOrdering("id");
        descriptor.addFieldOrdering("name");

        descriptor.addDirectMapping("id", "id");
        descriptor.addDirectMapping("name", "name");

        return descriptor;

    }

 

相应的测试代码如下

 Server server = project.createServerSession();
        server.login();
        UnitOfWork uow = server.acquireUnitOfWork();
        ClientSession cs = server.acquireClientSession();

        server.shouldLogMessages();
        uow.shouldLogMessages();
        uow.setLogLevel(1);

        School school = new School();
        school.setId(1);
        school=(School)uow.readObject(school);
        System.out.println(school.getStudents().get(0).getId());
        school.getStudents().get(0).setName("NN");
        uow.commit();

 

 

在这个问题上我花了一整天时间,主要是在官方文档这里 完全没有把和核心讲出来。

1,正如论坛 jsuther 所言,

 

In TopLink if the nested table is of refs, then you use the NestedTableMapping (target class is not aggregate), if it is a nested table or varray of object types, then you use the ObjectArrayMapping (target class is aggregate).

也就是说,所谓的NestedTableMapping,居然只对ref nested table有效,普通的nested table应该用ObjectArrayMapping, 这是何等跳跃的思维啊!

 

2 在Student Descriptor中,一定要有以下两句,不然会报ora-17049 "Inconsistent java and sql object types"

descriptor.addFieldOrdering("id");
descriptor.addFieldOrdering("name");

 

3.还是在Student Descriptor中,添加DirectMapping时一定要写成以下方式,

 descriptor.addDirectMapping("id", "id");
 descriptor.addDirectMapping("name", "name");

    切忌写成以下这样

descriptor.addDirectMapping("id", "STUDENT_ID");

   这里我没有去看源码,既然addDirectMapping添加的是一个哑元(不要求指定数据库Column name) 又要求指定fieldOrdering,估计在组装对象时是按顺序来的,也就是把STUDENT_TYPE中出现的属性依照addFieldOrdering依次塞给Student上的属性。为了验证这个猜想,把addFieldOrdering的顺序颠倒一下变成

descriptor.addFieldOrdering("name");
descriptor.addFieldOrdering("id");

 

果然报了java.lang.NumberFormatException: For input string: "NN",验证了我的猜想

1
1
分享到:
评论

相关推荐

    toplink-api.jar,toplink-essentials.jar

    在Java开发领域,依赖管理是项目构建中的关键环节,而`toplink-api.jar`和`toplink-essentials.jar`是两个重要的库文件,尤其对于处理对象关系映射(ORM)的问题至关重要。这两个JAR文件属于Oracle TopLink框架,一...

    Oracle TopLink Getting Started 10.1.3

    在使用TopLink之前,首先需要正确安装和配置相关的环境。这通常涉及到以下几个步骤: 1. **下载并安装**:从Oracle官方网站下载TopLink安装包,并按照指示完成安装。 2. **配置开发环境**:将TopLink的JAR文件添加...

    TopLink 教程

    TopLink,全称为Oracle TopLink,是Oracle公司的一款对象关系映射(ORM)框架,它允许开发者在Java应用程序中通过对象模型来操作数据库,从而降低了数据访问层的复杂性。作为Java持久化解决方案的一部分,TopLink...

    oracle toplink lib

    在ORM领域,TopLink扮演着一个桥梁的角色,它消除了Java对象与SQL数据库之间的语义差异,使开发者可以使用面向对象的方式来处理数据库操作。Oracle TopLink的核心功能包括: 1. **对象关系映射**:TopLink提供了一...

    toplink 文档学习

    Toplink作为一款成熟稳定的Java持久化框架,在企业级应用中扮演着重要的角色。通过理解其基本概念和掌握高级特性,开发者可以更高效地利用Toplink来处理复杂的数据库操作,从而提高应用程序的整体性能。在未来的发展...

    TopLink_Mysql例子

    toplink mysql5 开发工具:Eclipse3.3 for J2ee 简要过程(先导好mysqlJDBC包和toplink包,进mysql建好数据库), 1.新建pojo类,加入...2.在src目录下建META-INF目录,写好persistence.xml文件 3.写测试类 自动完成建表

    jpa toplink相关jar包,完整版。

    在Java EE环境中使用JPA TopLink,你需要包含相关的jar包以支持TopLink作为JPA的提供者。这些jar包通常包含了TopLink的实体管理器工厂、持久化单元配置、查询API以及其他必要的组件。"jpa_toplink"这个压缩包很可能...

    toplink-essentials.jar

    toplink-essentials.jar toplink-essentials.jar

    Oracle Toplink JPA

    Oracle Toplink JPA

    toplink-api.jar

    toplink-api.jar、 toplink-api.jar

    Oracle Toplink Grid

    首先,软件需求包括Oracle TopLink 11g版本11.1.1.0.0,该版本集成了EclipseLink,以及Coherence 3.4,这两者都可在Oracle Technology Network (OTN)上获取。这样的组合使得JPA应用能够利用Coherence的数据网格功能...

    Toplink_JPA注解参考

    **Toplink JPA注解参考** Toplink JPA(Java Persistence API)是Oracle公司提供的一种对象关系映射(ORM)框架,它允许开发者使用Java对象来操作数据库,而无需直接编写SQL语句。JPA提供了丰富的注解,使得在Java...

    spring-toplink-2.0-rc1.jar

    toplink 和spring 集成包

    TopLink Getting Started Guide

    2. **Session**:在TopLink中,Session代表了与数据库的一次会话,它是所有数据交互的基础。一个Session实例负责管理持久化对象的生命周期,并且执行对这些对象的查询和更新操作。 3. **Descriptor**:Descriptor是...

    JPA教程,包括TOPLink JPA,Hibernate JPA,Open Jpa,jpa批注

    **Java Persistence API (JPA)** 是...在实际开发中,根据项目的具体需求,可以选择适合的JPA实现,例如,对于性能要求高的场景,可能选择TOPLink JPA;而对于需要强大ORM特性的项目,Hibernate JPA可能是更好的选择。

    toplink

    不用说了吧 大家都知道

    toplink-essentials-agent.jar

    toplink-essentials-agent.jar

    Oracle TopLink Developer's Guide.PDF

    - **继承映射**:在具有继承关系的对象之间建立映射,可以采用不同的策略如Table per Class、Table per Subclass等。 #### 2. **TopLink的特性** - **高效性能**:TopLink优化了数据加载和更新过程,减少了与...

    Oracle Fusion Middleware Developer's Guide for Oracle TopLink

    - **事务管理**:阐述了TopLink在事务处理方面的支持,包括本地事务和分布式事务的概念及实现。 - **并发控制**:介绍了TopLink提供的不同类型的并发控制机制,如乐观锁、悲观锁等,并探讨了其应用场景。 ##### 5...

Global site tag (gtag.js) - Google Analytics