TimesTen数据交换技术提供在Oracle数据库和TimesTen数据管理器之间进行连接和双向数据传送。数据交换技术也使得能够方便的捕获和处理进入到TimesTen数据管理器的大流量事件流,而且能进行并发传送数据到Oracle数据库。
TimesTen同意通过创建cache group来快速缓存Oracle数据,以在TimesTen中映射一个或多个Oracle表。
同意快速缓存Oracle数据的TimesTen联合特征就作为Cache Connect to Oracle。
一个cache group就是描写叙述被快速缓存到TimesTen数据存储中的Oracle数据。快速缓存集合能够创建来快速缓存一个单表的全部或部分数据,或一个相关的Oracle数据表集。
快速缓存集合能够使用CREATE CACHE GROUP SQL语句或基于浏览器的Cache Administrator(Chapter 6, “CacheAdministrator.”)来创建。
图 1.1 显示名为target_customers快速缓存集合缓存Oracle表table customer。快速缓存集合中的数据是存储在Oracle数据库中全部用户的大数据集的一个子集。
图 1.1 快速缓存一个表
假设定义一个root table和多个child tables,则能够在同一个快速缓存集合中缓存多个Oracle表。在一个快速缓存集合中仅仅能有一个root table。
在拥有多个表的快速缓存集合中,每一个子表必须通过一个外键约束连接到快速缓存集合中的根表或还有一个子表。虽然TimesTen中缓存的表必须使用外键连接约束,但这些表在Oracle实例中不一定必须有连接。缓存集合中的根表不能通过外键约束来引用缓存集合中的不论什么其他表。全部缓存集合中的其他表都是子表
从Oracle载入到TimesTen缓存集合中的基本单位是cache instance,用来描写叙述通过外键与根表特定行相关联的行集。缓存集合中每一个表中粗体显示的是由根表中主键为122标识的缓存实例。此cache instance key确定根表中的行和引用此行的子表中全部的行。
图 1.2显示缓存集合target_customers中的表。根表是customer,orders和order_item是子表。
图 1.2 快速缓存多个表
如图 1.3所看到的,flush或propagate表示从TimesTen缓存拷贝表数据到Oracle,load或refresh表示从Oracle拷贝数据到TimesTen缓存。
图 1.3 在TimesTen和Oracle之间交换数据
至于如何将缓存集合中的数据传送到Oracle和从Oracle刷新数据,将依据所选择的缓存集合的类型。
缓存集合的基本类型为:
• READONLY缓存集合。
READONLY缓存集合通过AUTOREFRESH机制来将Oracle表中的更新进行强制缓存以应用到TimesTen。
• SYNCHRONOUS WRITETHROUGH (SWT) 缓存集合。
SYNCHRONOUS WRITETHROUGH (SWT)缓存集合将强制把集合中的缓存数据更新至TimesTen,而且发送到Oracle。SWT缓存集合的更新将被进行同步提交(Oracle)。
• ASYNCHRONOUS WRITETHROUGH (AWT)缓存集合。
ASYNCHROUNOUS WRITETHROUGH (AWT)缓存集合将强制把集合中的缓存数据更新至TimesTen,而且发送到Oracle。AWT缓存集合的更新将被进行异步提交(Oracle)。
• USERMANAGED缓存集合。
USERMANAGED缓存集合能够进行自己定义。比如,USERMANAGED缓存集合中的表能够拥有READONLY或PROPAGATE属性。
这章将讨论如何使用SQL语句来创建并管理简单的缓存集合。也可使用基于浏览器的Cache Administrator来创建缓存集合。
在能够创建缓存集合之前,必须安装TimesTen和Oracle环境。完毕以下任务:
1. 在TimesTen主机上安装Oracle Client。
2. 创建必需的Oracle帐号。
3. 创建一个TimesTen帐号。
4. 创建TimesTen DSN。
Cache Connect to Oracle特性使用Oracle共享库来与Oracle数据库进行通信。能够通过在安装了TimesTen的机器上安装Oracle Client来安装这些库文件。安装Oracle 9i Client或Oracle Database 10g。Oracleclient的版本号不必与Oracleserver端的版本号同样。Cache Connect支持以下的Oracleclient和server端的版本号:
• Oracle 10g Release 2 (Oracle 10.2.0.1.0 或之后)
• Oracle 10g Release 1 (Oracle 10.1.0.5.0或之后)
• Oracle 9i Release 2 (Oracle 9.2.0.8.0或之后)
安装Oracle Client时,选择Application User Installation Type。不必专门配置一个服务文件夹来用于Cache Connect to Oracle,所以能够跳过安装过程的这一步。
安装Oracle Client以后,安装TimesTen。
注意:假设在安装Oracle Client之前安装了TimesTen,必须又一次启动操作系统(Windows)或TimesTen(UNIX)。
在能够使用Cache Connect to Oracle之前,必须从数据库管理员处获得一个Oracle帐号。假设操作者实际拥有数据库管理权限,则在Oracleserver上打开命令窗体并启动SQL*Plus,以系统管理员身份登录:
sqlplus system/password@Oracle_Service_Name
比如,为了在由连接串、system1确定的Oracle数据库上给testuser创建一个新Oracle帐号,操作例如以下:
sqlplus system/manager@system1
SQL> CREATE USER testuser IDENTIFIED BY 11;
SQL> GRANT connect, resource, create any trigger TO cddbo;
SQL> COMMIT;
SQL> EXIT
为了与本章余下的部分讨论的一些演示样例缓存集合操作保持一致,Oracle用户为cddbo,口令为11,而且是system1中的一个Oracle帐号。
作为实例管理者,使用ttIsql工具来连接到数据存储TT_tt70_32.。数据存储实例由TimesTen在安装时定义,用来使实例管理者能够运行数据存储连接管理任务。
然后使用CREATE USER和GRANT语句来创建一个名为cddbo的用户,拥有ADMIN和DDL权限:
ttIsql TT_tt70_32.
Command> CREATE USER pgmrnew IDENTIFIED BY 'pgmrnew';
Command> GRANT ADMIN, DDL TO pgmrnew;
注意:此帐号必须与Oracle数据库帐号和口令同样。
在Window系统中,创建一简单的TimesTen系统数据存储(System DSN),名称为cddboDSN。
关于cddboDSN,设置例如以下:
• Data Store Path and Name:c:/temp/ cddbods
• Permanent Data Sz (MB):16
• Temporary Data Sz (MB):16
• User ID:pgmrnew(此ID也用作Oracle User ID)
• Oracle ID:orcl
• Oracle Password:pgmrnew
• DatabaseCharacterSet:ZHS16GBK。此数据库字符集必须与Oracle数据库字符集同样。为了得到Oracle数据库字符集信息,在Oracle数据库上输入下列查询:
SELECT value FROM nls_database_parameters
WHERE parameter='NLS_CHARACTERSET';
对于其余设置,使用缺省值。
在已经安装TimesTen和Oracle并进行配置以后,就能够创建缓存集合。
这部分将讨论如何创建一个简单READONLY缓存集合,以缓存Oracle数据库中单一表中的内容。虽然一个缓存集合能够由多个表组成,这里仅仅缓存一个Oracle表以保持演示样例的简单。
图 2.1 显示一个缓存一单个Oracle表的READONLY缓存集合。
图2.1 简单READONLY缓存集合
图 2.2 创建一Oracle表
连接到新帐号并创建一数据表:
sqlplus testuser/mypsswrd@system1
SQL> CREATE TABLE readtab (a NUMBER NOT NULL PRIMARY KEY,
b VARCHAR2(31));
然后插入一些记录并进行提交:
SQL> INSERT INTO readtab VALUES (1, 'hello');
1 row created.
SQL> INSERT INTO readtab VALUES (2, 'world');
1 row created.
SQL> COMMIT;
Commit completed.
图 2.3 创建READONLY缓存集合
使用ttIsql工具来连接cddboDSN数据存储。在命令提示符下,使用ttCacheUidPwdSet程序来传递缓存管理用户ID和口令作为參数。然后调用ttCacheStart程序来为数据存储启动缓存代理。在这个演示样例中,缓存管理用户ID是cddbo,而且口令为11:
> ttIsql cddboDSN
Command> call ttCacheUidPwdSet('pgmrnew','pgmrnew');
Command> call ttCacheStart;
接下来,使用CREATE CACHE GROUP语句来创建名为readcache的READONLY缓存集合,用来在TimesTen中缓存Oracle表tsr20_user的内容:
Command> CREATE READONLY CACHE GROUP readcache
> AUTOREFRESH INTERVAL 5 SECONDS
> FROM tsr20_user
>(code char(5) NOT NULL PRIMARY KEY, name VARCHAR(20) NOT NULL);
载入Oracle表中的内容到缓存集合表中。
Command> LOAD CACHE GROUP readcache COMMIT EVERY 256 ROWS;
185 cache instances affected.
检查tsr20_user表的内容:
Command> SELECT * FROM tsr20_user;
< -000, test >
……………………
< 05999, 系统管理员05999 >
185 rows found
使用ttIsql cachegroups命令来检查READCACHE缓存集合的定义:
Command> cachegroups;
Cache Group TESTUSER.READCACHE:
Cache Group Type: Read Only
Autorefresh: Yes
Autorefresh Mode: Incremental
Autorefresh State: On
Autorefresh Interval: 5 Seconds
Root Table: PGMRNEW.TSR20_USER
Table Type: Read Only
1 cache group found.
图 2.4 使用Oracle更新自己主动刷新TimesTen
使用SQL*Plus,插入多行到READTAB并提交事务:
SQL> INSERT INTO readtab VALUES (3, 'Hello');
1 row created.
SQL> INSERT INTO readtab VALUES (4, 'Again');
1 row created.
SQL> COMMIT;
Commit completed.
5秒之后,TimesTen将从Oracle自己主动刷新缓存数据。在ttIsql中检查READTAB表的内容:
Command> SELECT * FROM readtab;
< 1, hello >
< 2, world >
< 3, Hello >
< 4, Again >
4 rows found
在TimesTen窗体中,使用DROP CACHE GROUP语句从TimesTen数据存储中删除缓存集合:
Command> DROP CACHE GROUP readcache;
调用ttCacheStop程序停止数据存储的缓存代理:
Command> call ttCacheStop;
这部分将讨论如何在DSN中设置PassThrough属性来命令TimesTen通过SQL定向到Oracle。
图 2.5 显示从一个应用将SQL传递到Oracle表。缓存表通过自己主动刷新机制从Oracle接收更新。
图 2.5 从Cache Group to Oracle传递SQL
在Window系统中,创建一新的TimesTen系统数据源(System DSN),名称为cddboPT,使用与指定给cddboDSN的同样的属性。另外,设置PassThrough属性值为‘2’,以直接传递不在缓存集合中的Oracle表的查询和程序调用到Oracle。
对于cddboPT,设置例如以下:
• Data Store Path and Name: c:/temp/cgPT2d
• Permanent Data Sz (MB): 16
• Temporary Data Sz (MB): 16
• User ID: pgmrnew (此ID也用作Oracle User ID)
• Oracle ID: orcl
• Oracle Password: pgmrnew
• PassThrough: 2
• DatabaseCharacterSet: ZHS16GBK。此数据库字符集必须与Oracle数据库字符集同样。为了得到Oracle数据库字符集信息,在Oracle数据库上输入下列查询:
SELECT value FROM nls_database_parameters
WHERE parameter='NLS_CHARACTERSET';
对于其余设置,使用缺省值。
图 2.6 创建READONLY缓相聚集合
在TimesTen窗体中,连接到DSN cddboPT,设置缓存管理用户ID和口令,启动缓存代理,并创建READONLY缓存集合:
ttIsql cgPT2
Command> call ttCacheUidPwdSet('pgmrnew','pgmrnew');
Command> call ttCacheStart;
Command> CREATE READONLY CACHE GROUP readcache
> AUTOREFRESH INTERVAL 5 SECONDS
> FROM tsr20_user
> (code char(5) NOT NULL PRIMARY KEY, name VARCHAR(20) NOT NULL);
载入Oracle表的内容到缓存集合表中。
Command> LOAD CACHE GROUP readcache COMMIT EVERY 256 ROWS;
4 cache instances affected.
图 2.7 更新TimesTen缓存集合表
使用ttIsql,插入一些行到tsr20_user:
Command> INSERT INTO tsr20_user VALUES ('0001','Just','00000', 'dd','0000','1',NULL);
1 row inserted.
Command> INSERT INTO tsr20_user VALUES ('0002',' Passing ','00000', 'dd','0000','1',NULL);
1 row inserted.
Command> INSERT INTO tsr20_user VALUES ('0002',' Through ','00000', 'dd','0000','1',NULL);
1 row inserted.
使用SQL*Plus检查 check the contents of the readtab table on Oracle:
SQL> SELECT * FROM tsr20_user;
CODE NAME
---------- -------------------------------
-000 test
……………………
05999 系统管理员05999
187 rows selected.
然后使用ttIsql检查TimesTen中表tsr20_user的内容:
Command> SELECT * FROM tsr20_user;
< -000, test >
……………………
< 05999, 系统管理员05999 >
187 rows found
使用ttIsql,输入DROP CACHE GROUP语句来从TimesTen数据存储中删除缓存集合:
Command> DROP CACHE GROUP readcache;
调用ttCacheStop程序来停止数据存储的缓存代理:
Command> call ttCacheStop;
表 2.1 创建缓存集合任务列表
任务序号 |
任 务 |
1 |
确保已经安装Cache Connect to Oracle。使用ttIsql来验证: connect “uid=myuid;pwd=mypwd;OraclePWD=mypwd;passthrough=3”; SELECT COUNT(*) FROM DUAL; exit 此查询应该返回1。假设不是,则检查以下内容: • 设置以下环境变更:ORACLE_HOME、LD_LIBRARY_PATH、SHLIB_PATH • 缓存管理用户ID和口令,以及Oracle ID • Oracleserver的状态 |
2 |
对全部要创建的缓存集合设计缓存集合计划。可能使用Cache Administrator。 |
3 |
确保有足够的资源来载入全部的缓存集合。 设置First Connection属性: • PermSize – 能够首先创建缓存集合,然后使用ttSize工具来估算PermSize属性的值。必须估算要使用ttSize工具进行缓存的行数。 • TempSize – 没有必要的意义。 • DatabaseCharacterSet – 确保它与Oracle数据库字符集相匹配。 文件系统大小推荐: • 数据存储文件夹应足够大以处理两个检查点文件。每一个检查点文件的最大值为20 MB + PermSize。 • 日志文件夹应足够大以处理积累在检查点之间的日志文件。注意,假设在自己主动刷新间隔期间Oracle表中有大量的更新,自己主动刷新事务可能相当大。 一个对于日志文件夹大小的处理规则是使它等于数据存储的大小加上3倍的LogFileSize的3倍。 • 暂时文件夹应放在快速文件系统中,以提高运行大事务的速度。能够通过设置TMPDIR环境变量(UNIX)或TEMP环境变更(Window)来指定暂时文件夹用于自己主动刷新操作。在环境变量设置之后,又一次启动TimesTen Daemon(UNIX)或机器(Window)。一个非常大自己主动刷新事务在暂时文件夹中要求非常大空间。 |
4 |
假设缓存集合是自己主动刷新或异步写方式,要设置缓存管理用户ID和口令。缓存管理用户ID必须是一个Oracle用户,而且必须有对应的权限。 |
5 |
启动缓存代理。假设计划使用非日志模式(參阅第7步),则跳过此步。 |
6 |
创建并提交全部的缓存集合。 |
7 |
(选项)使用非日志模式载入缓存集合。 为了更快运行和减少资源使用,能够在非日志模式中载入缓存集合。非日志模式的缺点是: • 全部到TimesTen数据存储已存在的连接必须停止。 • 载入操作不能进行复制。 运行下列任务来使用非日志模式载入缓存集合: a. 假设正在运行的话,停止缓存代理、复制代理以及TimesTen服务。 b. 断开全部连接到TimesTen数据存储的应用。 c. 使用First Connection attributes Logging=0、DurableCommits=0、LockLevel=1属性连接到数据存储。. d. 为每一个集合发送下列SQL语句:LOAD CACHE GROUP cache_group_name COMMIT EVERY 0 ROWS。 e. 在载入每一个缓存集合之后,提交事务并发送一个检查点。 f. 使用日志又一次将应用连接到TimesTen数据存储。 g. 启动缓存代理。 |
8 |
假设须要复制,则在缓存集合表上创建TimesTen复制计划。 |
9 |
假设要复制缓存集合表或缓存集合是异步写(AWT)方式,则启动复制代理。
注意:当复制代理正在运行时,不能创建或删除AWT缓存集合。 |
10 |
载入缓存集合并提交(假设不运行第7步)。使用LOAD CACHE GROUP cache_group_name COMMIT EVERY n ROWS。对于n的推荐值为256。 |
这章将讨论不同的缓存集合类型以及如何进行定义。
能够使用CREATE CACHE GROUP语句来创建一个缓存集合定义,包括为每一个将被缓存的Oracle表分别定义缓存表。
表 3.1 显示一个简单缓存集合定义的组成。缓存集合定义的每一个部分将在以下部分讨论。
表 3.1 缓存集合定义的组成
组 成 |
CREATE type CACHE GROUP |
owner.name |
Cache group and table attributes |
FROM table definition |
[WHERE ...] |
[AGING ...] |
也能够使用Web浏览器通过Cache Administrator来创建缓存集合。
在CREATE CACHE GROUP语句中,缓存集合的名称标识使用例如以下形式:
owner.name
假设在缓存集合的名称中不指定owner,则ID或当前会话用户将作为owner。
缓存集合类型能够是系统管理或用户管理。系统管理缓存集合强制指定数据操作,而用户管理缓存集合的数据操作能够自己定义。系统管理缓存集合包括:
• READONLY cache groups
• SYNCHRONOUS WRITETHROUGH (SWT) cache groups
• ASYNCHRONOUS WRITETHROUGH (AWT) cache groups
A READONLY缓存集合通过AUTOREFRESH机制进行强制缓存操作,将Oracle表中的更新应用到TimesTen。此缓存不能进行直接更新。
图 3.1 显示一个READONLY缓存集合
图 3.1 READONLY缓存集合
使用CREATE READONLY CACHE GROUP语句来创建READONLY缓存集合。缺省的:
• AUTOREFRESH缓存集合属性被设置为INCREMENTAL模式。
• AUTOREFRESH INTERVAL值为5 MINUTES。
• AUTOREFRESH STATE为PAUSED。
能够使用ALTER CACHE GROUP语句来改变不论什么AUTOREFRESH缓存集合属性的缺省设置或全然阻止Oracle表中的更新应用到缓存中。
在创建READONLY缓存集合之前,通过使用ttCacheUidPwdSet内部程序来设置缓存管理用户ID和口令或使用带有-cacheUidPwdSet选项的ttAdmin工具。缓存管理用户将在Oracle上创建一个触发器,所以它必须拥有显示在表 4.1中关于CREATE READONLY CACHE GROUP的Oracle权限。
对于每一个数据存储,缓存管理用户ID和口令仅仅需设置一次。假设数据存储被重写或破坏,则须要又一次设置缓存管理用户ID和口令。
试图在READONLY缓存集合中更新缓存的表,将导致TimesTen错误8225 “Table is read only”。可是,假设PassThrough属性被设置为2或3,DML语句也能够通过缓存传递到Oracle,并通过AUTOREFRESH再从Oracle传回到缓存集合中。在READONLY缓存集合中的passed-through语句的效果不会在包括此语句的事务中产生。仅仅有在此事务被提交到Oracle,然后在下一次缓存的AUTOREFRESH完毕时才会体现。
当使用READONLY缓存集合时,有下列限制:
• READONLY缓存集合中的表不能直接更新。
• 缓存集合和当中的表能够使用下列属性:
– AUTOREFRESH
– UNIQUE HASH ON
– ON DELETE CASCADE
• 不同意使用手动FLUSH操作。
• TRUNCATE TABLE语句不能自己主动刷新。
• 当使用LOAD CACHE GROUP语句时缓存集合必须为空。
• 当使用LOAD CACHE GROUP或REFRESH CACHE GROUP语句时,AUTOREFRESH STATE必须为PAUSED。
• WHERE子句中的全部字段(列和表)的引用必须全然合法。比如:user.table 和 user.table.column。
• LOAD CACHE GROUP和REFRESH CACHE GROUP语句不能包括WHERE子句。
• 不能指定Least recently used (LRU)老化。
此例创建一个包括customer和ordertab表的READONLY缓存集合,名为customer_orders:
CREATE READONLY CACHE GROUP customer_orders
FROM
user1.customer (custid INTEGER NOT NULL,
name VARCHAR2(100) NOT NULL,
addr VARCHAR2(100),
zip VARCHAR2(10),
region VARCHAR2(10),
PRIMARY KEY(custid)),
user1.ordertab (orderid NUMBER NOT NULL,
custid INTEGER NOT NULL,
PRIMARY KEY (orderid),
FOREIGN KEY (custid) REFERENCES CUSTOMER(custid));
SYNCHRONOUS WRITETHROUGH (SWT)缓存集合将进行强制运行:把TimesTen中被更新的缓存数据传送到Oracle。当使用CREATE SYNCHRONOUS WRITETHROUGH CACHE GROUP语句创建SWT缓存集合时,在创建缓存集合之后,缓存集合中的内容必须手动从Oracle表载入。SWT缓存集合的内容能够在须要时进行手动载入、卸载或刷新。
对SWT缓存集合的更新将被同步提交。当应用提交一个事务时,在它提交到TimesTen之前先被提交到Oracle。应用将被锁定,而且表中的行也同进被锁定,直到事务完毕到TimesTen的提交。
假设到Oracle的事务提交失败,则到TimesTen的事务提交必须被回滚。假设Oracle事务成功但TimesTen事务失败,则缓存集合的数据将与Oracle数据不同步。假设产生这样的情况,必须手动将缓存集合与Oracle重同步。这可能通过调用ttCachePropagateFlagSet程序先停止到Oracle的数据传递,然后又一次应用此事务到TimesTen缓存集合。作为还有一选择,也能够又一次从Oracle载入数据。
图 3.2 显示一个SYNCHRONOUS WRITETHROUGH缓存集合。
图 3.2 SYNCHRONOUS WRITETHROUGH缓存集合
当使用SWT缓存集合时,有例如以下限期完毕:
• 缓存集合和当中的表属性中,能够使用UNIQUE HASH ON和ON DELETE CASCADE属性。
• 不同意使用手动FLUSH操作。
• 在此类型的缓存集合定义中不能显示使用WHERE子句。
• TRUNCATE TABLE语句不能应用到缓存集合的表中。
此演示样例为一单独Oracle表vendor创建一个SYNCHRONOUS WRITETHROUGH缓存集合,名为vendors。在缓存集合中的vendor表的更新将自己主动传送到Oracle。
CREATE SYNCHRONOUS WRITETHROUGH CACHE GROUP vendors
FROM
user1.vendor (vendor_id INTEGER NOT NULL,
vendor_name VARCHAR2(100) NOT NULL,
contact_name VARCHAR2(100) NOT NULL,
phone VARCHAR2(15),
street VARCHAR2(100),
city VARCHAR2(30),
state VARCHAR2(30),
zip VARCHAR2(10),
PRIMARY KEY(vendor_id));
ASYNCHRONOUS WRITETHROUGH (AWT)缓存集合与SWT缓耻集合一样强制运行同样的操作:更新TimesTen中的缓存数据,并传送到Oracle。AWT缓存集合能够提供比SWT缓存集合理快的时间响应,由于TimesTen提交的产生与Oracle的提交不同步。这就同意应用持续运行,而不必等待Oracle事务的提交完毕。而且也可在Oracle数据库关闭后更新AWT缓存集合。当Oracle数据库返回到操作时,此更新将被应用到Oracle数据库。
图 3.3 显示TimesTen缓存集合的更新被异步拷贝到Oracle。
图 3.3 ASYNCHRONOUS WRITETHROUGH缓存集合
AWT缓存集合要求包括此缓存集合的数据存储的缓存代理和复制代理都要启动。缓存代理可能载入和刷新缓存内容。缓存代理不必运行卸载此缓存。
AWT缓存集合通过CREATE ASYNCHRONOUS WRITETHROUGH CACHE GROUP语句创建。
为了使用AWT缓存集合,必须有对应的Oracle权限,并在启动缓存代理和复制代理之前使用ttCacheUidPwdSet程序设置缓存管理用户ID和口令。
当使用AWT缓存集合时,提交到TimesTen和Oracle的事务是异步的。所以当更新提交到Oracle时,应用不一定可靠。
AWT缓存集合能够例如以下保证:
• 不会由于TimesTen和Oracle这间的通信失败而丢失事务。
– 假设复制代理丢失到Oracle的连接,则在代理可能连接到Oracle之后,AWT将又一次启动。
– 假设数据存储上的复制代理与缓存集合一起关闭,则代理将从备份又一次開始并再次启动事务。
• 对于一个单独TimesTen数据存储被提交的事务被提交到Oracle的顺序与被提交到TimesTen的顺序同样。
• 假设到Oracle的事务失败,则失败将被报告在dataStoreName.awterr错误文件里。
AWT缓存集合不能保证:
• 全部在TimesTen中运行的事务都将被应用到Oracle。Oracle上运行错误将引起整个事务被回滚。比如,可能由于违反唯一约束而引起Oracle上的插入失败。产生运行错误的事务将不会再试。
• 要绝对保证Oracle的更新顺序,由于AWT不能解决更新冲突。这儿有一些样例:
– 一行首先被更新到一个AWT表并被提交。然后一些被更新的行通过Oracle传送操作并提交。AWT代理最后应用到此行的第一次更新并又一次覆盖传送操作。
– 在两个独立的数据存储中(DS1, DS2),都有一个拥有同样Oracle基表的AWT表。一行在DS1中被更新并提交。一行在DS2中被更新并提交。由于缓存集合的动作是异步的,DS2中的更新或许先于DS1中的更新应用到Oracle数据库,结果是DS1中的更新覆盖DS2中的更新。
关于SWT缓存集合的限制讨论也适用于AWT缓存集合:
• 缓存集合和表的属性能够使用UNIQUE HASH ON和ON DELETE CASCADE属性。
• 不同意使用手动FLUSH操作。
• WHERE子句不能出如今此类型的缓存集合的表定义中。
• TRUNCATE TABLE语句不能应用于缓存集合的表中。
• AWT缓存表中的VARCHAR2、NVARCHAR2、VARBINARY和TT_VARCHAR列必须限制为256K字节。
以下是仅仅对AWT缓存集合适用的另外限制:
• 在AWT缓存集合中数据存储路径名的最大长度不能超过248字符。
• 在传送更新到Oracle的过程中产生的错误和警告,将记录在一个特殊的错误文件里,而且在提交到TimesTen以后都能够一直报告。
• AWT缓存集合不同意使用在日志被关闭的数据存储中(Logging=0)。
• 在创建或删除AWT缓存集合之前,必须停止复制代理。
• 在复制代理启动之前,更新将不会从TimesTen传送到Oracle。
• 在Oracle上的更新冲突将不会被发觉并解决。当从TimesTen传送更新时将覆盖直接到Oracle基表的更新。
• 与单一条相关的SQL语句的约束检查将马上进行。比如,假设在一个AWT表中有一个唯一索引integer字段。有10条记录,而且此字段的值的范围是从1到10。公布一条添加此字段的更新语句。此语句在TimesTen中成功,但当应用到Oracle时非常可能失败。原因就是TimesTen在语句结束之后检查此唯一索引约束,但当更新应用到Oracle时,此约束是在每一行都被更新之后进行检查。所以当值为1的记录被设置为2时,它将与此字段已经为2的其他行发生冲突。
• 在一个返回twosafe服务的复制计划中不能包括AWT缓存集合。
此演示样例为一单独表customer创建一个ASYNCHRONOUS WRITETHROUGH缓存集合,名为customers。
CREATE ASYNCHRONOUS WRITETHROUGH CACHE GROUP customers
FROM
user1.customer (custid INTEGER NOT NULL,
name VARCHAR2(100) NOT NULL,
addr VARCHAR2(100),
zip VARCHAR2(10),
PRIMARY KEY(custid));
TimesTen须要在Oracle中创建一个状态表来支持AWT。此表用来跟踪状态和近期应用到Oracle的事务。此表由CREATE ASYNCHRONOUS WRITETHROUGH CACHE GROUP语句自己主动创建。作为选择,也能够在创建AWT缓存集合之前,手工创建此Oracle表。
当设置AWT缓存集合时,运行下列任务:
1. 设置缓存管理用户ID和口令。
通过使用ttCacheUidPwdSet内部程序或使用带有-cacheUidPwdSet选项的ttAdmin工具来设置缓存管理用户ID和口令。
缓存管理用户将应用更新到Oracle。所以缓存管理用户帐号必须拥有对应的Oracle权限。
对于每一个数据存储,缓存管理用户ID和口令仅仅需设置一次。假设数据存储被覆盖或被破坏,则必须又一次设置缓存管理用户ID和口令。
2. 创建AWT缓存集合。
使用CREATE ASYNCHRONOUS WRITETHROUGH CACHE GROUP SQL语句。
3. 启动缓存代理。
4. 启动复制代理。
创建AWT缓存集合时将自己主动创建复制计划以同意数据存储与Oracle数据库进行通信。此复制计划全然由TimesTen管理,并不须要用户干涉。当使用DROP CACHE GROUP来删除AWT缓存集合时,此复制计划也将被删除。
在载入缓存集合之前,不必启动复制代理,可是假设复制代理已经首先启动,最好让它运行完毕。
5. 载入缓存集合。
使用LOAD CACHE GROUP语句。
假设系统管理缓存集合(READONLY、AWT和SWT)不适合工作须要,能够使用CREATE USERMANAGED CACHE GROUP语句来创建缓存集合以实现自己定义缓存操作:
• 能够通过设置AUTOREFRESH和PROPAGATE属性来定义USERMANAGED缓存集合在Oracle和TimesTen之间进行自己主动刷新和传送更新。两个属性同一时候设置以激活双向传送,这样就能够在两者之间通过互相传送即能够更新TimesTen,又可更新Oracle。
• 能够使用SQL语句来控制Oracle和TimesTen之间的数据传送。比如,能够:
– 在应用中使用FLUSH CACHE GROUP SQL语句来将TimesTen缓存集合中的更新发送至Oracle。
– 使用LOAD CACHE GROUP或REFRESH CACHE GROUP语句来将Oracle中的更新载入或刷新到TimesTen缓存中。
• 可能通过使用UNLOAD CACHE GROUP语句从用户管理缓存集合中删除全部数据或选择的数据。
• 能够在用户管理缓存集合中为每一个表指定PROPAGATE或READONLY属性,以在表级上定义可写或仅仅读操作。
这部分显示使用EATE USERMANAGED CACHE GROUP语句创建自己定义缓存集合的一些演示样例。
例 3.1 此例为一单独表customer创建一个USERMANAGED缓存集合,名为update_anywhere_customers。customer表中的更新通过“双向”彼此传送来更新TimesTen或Oracle。图 3.4 显示update_anywhere_customers USERMANAGED缓存集合。
图 3.4 简单USERMANAGED缓存集合
在此例中,设置了AUTOREFRESH属性,以使此缓存集合能够每隔30秒从Oracle进行增量更新。用户是user1。表中描写叙述的PROPAGATE属性显示TimesTen缓存中的customer表的更新将被传送到Oracle:
CREATE USERMANAGED CACHE GROUP update_anywhere_customers
AUTOREFRESH
MODE INCREMENTAL
INTERVAL 30 SECONDS
FROM
user1.customer (custid INTEGER NOT NULL,
name VARCHAR2(100) NOT NULL,
addr VARCHAR2(100),
zip VARCHAR2(10),
PRIMARY KEY(custid),
PROPAGATE);
例 3.2 此例创建一个USERMANAGED缓存集合,名为western_customers,包括四个相关联的表:customer、ordertab、order_details和cust_interest。图 3.5 显示此缓存集合和它的表。
图 3.5 复杂USERMANAGED缓存集合
western_customers缓存集合中的每一个表都有一个主键。缓存集合中的表通过关联的外键相互连接。customer表为根表,所以在缓存集合它不能引用其他表。根表包括一条WHERE子句以限制缓存中表的行数。
指定了PROPAGATE属性,以使缓存中表的不论什么变化在提交时将被自己主动传送到对应的Oracle表。
CREATE USERMANAGED CACHE GROUP western_customers
FROM
user1.customer (custid INTEGER NOT NULL,
name VARCHAR2(100) NOT NULL,
addr VARCHAR2(100),
zip VARCHAR2(10),
region VARCHAR2(10),
PRIMARY KEY(custid),
PROPAGATE)
WHERE (customer.region = 'Western'),
user1.ordertab(orderid NUMBER NOT NULL,
custid INTEGER NOT NULL,
PRIMARY KEY (orderid),
FOREIGN KEY (custid) REFERENCES customer(custid),
PROPAGATE),
user1.order_details(orderid NUMBER NOT NULL,
itemit NUMBER NOT NULL,
quantity NUMBER NOT NULL,
PRIMARY KEY (orderid, itemid),
FOREIGN KEY (orderid) REFERENCES ordertab(orderid),
PROPAGATE),
user1.cust_interest(custid INTEGER NOT NULL,
interest VARCHAR2(10) NOT NULL,
PRIMARY KEY (custid, interest),
FOREIGN KEY (custid) REFERENCES customer(custid),
PROPAGATE);
下表总结可用于CREATE CACHE GROUP语句的属性。
表 3.2 总结AUTOREFRESH缓存集合属性。
表 3.3 列出了可应用于缓存集合中单个表定义的属性。
表 3.2 完整缓存集合的属性
缓存集合属性 |
描 述 |
AUTOREFRESH |
将Oracle表中产生的更新变化自己主动应用到TimesTen缓存。此属性能够在READONLY和USERMANAGED缓存集合中设置。 |
表 3.3 缓存集合中表的属性
缓存表属性 |
描 述 |
UNIQUE HASH ON |
为被创建的表指定一个哈希索引。能够为不论什么类型缓存集合中的表进行设置。 |
PROPAGATE |
在提交时自己主动地将缓存表中的更新传送到对应的Oracle表。仅仅能为USERMANAGED缓存类型中的表进行设置。 |
READONLY |
指定缓存集合中的表不能更新到TimesTen。仅仅能为USERMANAGED缓存集合中的表进行设置。 |
ON DELETE CASCADE |
指定当包括被引用键的值从父表中删除时,子表中依靠外键连接的行也要被删除。能够为不论什么类型的缓存集合中的表进行设置。限制: • 使用PROPAGATE属性的缓存集合表。 • SWT和AWT缓存集合表。 |
AUTOREFRESH属性是READONLY和USERMANAGED缓存集合的一个选项属性。
AUTOREFRESH自己主动将Oracle表中的变化应用到TimesTen缓存。
TimesTen支持两种AUTOREFRESH模式:
• FULL:通过卸载内容然后再从Oracle表又一次载入来刷新整个缓存集合。
• INCREMENTAL:Oracle跟踪更新情况并周期性地仅仅更新Oracle中已经变化行到缓存集合中。此模式将使用Oracle中的专用对象来跟踪变化情况。
缺省值:
• AUTOREFRESH MODE了为 INCREMENTAL。
• AUTOREFRESH STATE 为 PAUSED。
• AUTOREFRESH INTERVAL 值为5 MINUTES。
缓存集合使用同样的自己主动刷新间隔在同样的时间被刷新。
AUTOREFRESH 以 INCREMENTAL模式对于Oracle中的每一个更新将产生一些额外的花销来刷新缓存集合。而使用AUTOREFRESH 和 FULL模式时则没有额外的花销。
在使用AUTOREFRESH属性创建缓存集合之前,要使用ttCacheUidPwdSet内部程序或带有-cacheUidPwdSet选项的ttAdmin工具来设置缓存管理用户ID和口令。缓存管理用户将在Oracle上创建一触发器,所以它必须拥有使用AUTOREFRESH属性的READONLY缓存集合和USERMANAGED缓存集合对应的Oracle权限。
对于每一个数据存储,缓存管理用户ID和口令仅仅须要设置一次。假设数据存储被覆盖或破坏,则必须又一次设置缓存管理用户ID和口令。
当使用CREATE CACHE GROUP语句创建缓存集合时,能够指定AUTOREFRESH。在创建缓存集合之后,能够使用ALTER CACHE GROUP来改变MODE、STATE和INTERVAL的设置。ALTER CACHE GROUP语句不能用于没有使用AUTOREFRESH 属性创建的缓存集合。
AUTOREFRESH产生的频率将取决于INTERVAL值。能够使用CREATE CACHE GROUP 或ALTER CACHE GROUP语句来设置AUTOREFRESH STATE为ON、OFF或PAUSED。当提交STATE设置为ON的事务时,AUTOREFRESH将由TimesTen管理。
当STATE被设置为OFF时,到Oracle表的更新将不会被捕获或记录。当状态为PAUSED时,Oracle表中的更新将被捕获并记录在Oracle中,但不会应用到TimesTen缓存集合的表中。
当一个AUTOREFRESH操作在处理中,而且试图将STATE改变为OFF或删除缓存集合时:
• 假设LockWait普通连接属性大于0,则AUTOREFRESH操作将停止。ALTER CACHE GROUP SET AUTOREFRESH STATE OFF 和 DROP CACHE GROUP 语句将优先于AUTOREFRESH操作。
• 假设LockWait普通连接属性为0,则AUTOREFRESH操作将继续。ALTER CACHE GROUP SET AUTOREFRESH STATE OFF 和 DROP CACHE GROUP 语句将失败,并产生一个锁定终止错误。
当以INCREMENTAL模式使用AUTOREFRESH时,在Oracle中发生的变化将在change log table中进行维护。在确定的环境下,在应用到TimesTen缓存集合之前,事务中的一些记录可能将从更新日志表中被清除。假设发生这样的情况,Cache Connect to Oracle启动缓存集合的全然自己主动更新。
当使用AUTOREFRESH时有例如以下限制:
• 假设在Oracle基表上使用了TRUNCATE TABLE语句,则增量AUTOREFRESH将不会工作。假设Oracle基表上使用了TRUNCATE,则必须又一次设置AUTOREFRESH。使用ALTER CACHE GROUP语句来将AUTOREFRESH STATE设置为PAUSED,然后手工刷新缓存集合。再发送还有一条ALTER CACHE GROUP来将AUTOREFRESH STATE又一次设置为ON。
• 为了使用AUTOREFRESH特性,缓存集合中的全部表必须指定为PROPAGATE或READONLY。不能使用NOT PROPAGATE属性指定AUTOREFRESH。
• 当手工载入或刷新缓存集合时,AUTOREFRESH STATE必须为PAUSED。
• 当使用LOAD CACHE GROUP语句时,缓存集合必须为空。
• WHERE 子句中引用的全部字段(列和表)必须全然合法。比如:user.table 和 user.table.column。
• 对于AUTOREFRESH的缓存集合的LOAD CACHE GROUP和REFRESH CACHE GROUP语句不能包括WHERE子句。
• 不能在AUTOREFRESH缓存集合中实现LRU老化。
这部分包括下列缓存表属性:
• PROPAGATE
• READONLY
• ON DELETE CASCADE
• UNIQUE HASH ON
PROPAGATE属性仅仅能为USERMANAGED缓存集合中的表进行指定。可是,这里讨论的传送操作与同步写(SWT)缓存集合类似。
PROPAGATE指定在提交时TimesTen缓存集合中表的不论什么变化将被自己主动传送到对应的Oracle表。NOT PROPAGATE将取传送能力。
假设缓存表使用PROPAGATE属性定义,到缓存表中的更新在TimesTen提交过程中将被传送回Oracle。是以同步的方式:
1. 提交首先尝试到Oracle。假设向Oracle提交失败,则不会再向TimesTen提交,而且TimesTen事务被作上须要回滚的标记。这样的方式,Oracle数据库不会遗失数据更新。
2. 假设向Oracle提交成功,将尝试向TimesTen提交。假设向TimesTen提交失败,将收到一条说明失败原因的TimesTen错误信息。
用户的操作通过连接到Oracle的应用进行提交。对于用户的登录和口令必须指定在DSN中或到TimesTen的连接串中的UID和OraclePWD属性中。
关于传送提交到Oracle,必需满足下列要求:
• 被缓存在TimesTen中的Oracle表的列必须包括此Oracle表中至少一个唯一键或主键中的全部列。组成唯一键或主键的列在Oracle必须为非NULL值的列,而且在TimesTen缓存集合中它们必须申明为主键。
这个要求的目的就是要确保在TimesTen中被更新的行之间和Oracle中原来的数据保持一对一的映射关系。确定此一对一的映射,就不会操心应用的更新会受到非缓存行的影响。
• 表的缓存版本号必须有一个主键申明。
缺省地,缓存表使用NOT PROPAGATE属性被创建,以使表中的更新不会传送到Oracle。当PROPAGATE被激活时,应用有时候偶尔须要更新缓存表,但不向Oracle提交。使用ttCachePropagateFlagSet内部程序来取消它,然后又一次激活传送。
当传送被取消时,能够使用FLUSH CACHE GROUP语句来选择传送插入并更新到Oracle。
当使用PROPAGATE时有例如以下限制:
• 假设使用PROPAGATE,它必须为缓存集合中的全部表进行指定。
• 在同一个缓存集合中,不能同一时候使用PROPAGATE和READONLY缓存表。
• TimesTen不会检查冲突以防止覆盖多个当前到Oracle更新的操作。基于这个原因,更新将分别在TimesTen缓存或Oracle中进行,但不是同一时候。
• 假设缓存集合的AUTOREFRESH被激活或在AUTOREFRESH缓存集合的拷贝中,不能为表设置NOT PROPAGATE。
• 在缓存集合被指定为PROPAGATE之后,就不能再改变此属性。
注意:对于表使用PROPAGATE属性的缓存集合,TimesTen将不会检查向表的插入和更新是否与定义缓存集合时的WHERE子句有无约束。因此不会阻止插入和更新,而且将传送到Oracle。
READONLY表属性仅仅能为USERMANAGED缓存集合中的表进行指定。
注意:不要混淆READONLY表属性和READONLY缓存集合类型。READONLY缓存集合类型包括仅仅读表,但READONLY表仅仅能显示地为USERMANAGED缓存集合指定。
能够为每一个缓存集合表指定READONLY表属性,以禁止TimesTen应用更新这些表。
以下是使用READONLY表属性时的限制:
• 假设使用READONLY,它必须为缓存集合中的全部表进行指定。
• 不能与PROPAGATE表属性一起指定READONLY表属性。
当创建缓存集合时,ON DELETE CASCADE表属性能够为全部缓存集合类型的表进行指定。也能够为不在缓存集合中后进行指定。
ON DELETE CASCADE表属性指定当从父表中删除包括引用键值的行时,通过外键相关联的子表中插也将被删除。根表是缓存集合中全部其他表的父表。
全部从父表到子表的方式必须是要么是“删除”或要么是“不删除”。不能父表到子表一些是删除,而还有一些是不删除。对于子表的删除方式是指定ON DELETE CASCADE。
以下是使用ON DELETE CASCADE的限制:
• 对于AWT和SWT缓存集合和使用PROPAGATE属性的缓存集合表,有ON DELETE CASCADE属性的TimesTen表的外键必须是Oracle中有ON DELETE CASCADE属性的表中的外键相的对应的一个子集。在Oracle表上的ON DELETE CASCADE动作应用到TimesTen时将作为单独的删除动作。TimesTen中的ON DELETE CASCADE动作应用到Oracle时将作为一个级联操作。
• TimesTen和Oracle之间的外键匹配仅仅是在创建缓存集合时强制进行。假设Oracle上的外键后来进行过改动,ON DELETE CASCADE将不会正常的工作。
UNIQUE HASH ON属性能够为全部缓存集合类型中的表进行指定。也能够为不在缓存集合中的表进行指定。
UNIQUE HASH ON指定在缓存集合中的一个表上创建一个哈希索引。指定在哈希索引中的列必须同样是主键中的列。
绝大多数缓存集合的基本类型是在TimesTen中缓存一个单一的Oracle表。在一个缓存集合中缓存多个表复杂的多,并要求理解另外的Cache Connect to Oracle概念。
通常情况下,每一个被缓存的Oracle表至少有一个主键或非空值的唯一索引。另外,在TimesTen缓存集合表中定义的主键和唯一索引将与那些Oracle表中的相匹配。比如,假设Oracle表有主键或唯一索引列C1、C2和C3,则对应的TimesTen缓存表中的主键也应该有列C1、C2和C3。
能够为TimesTen缓存表创建随意多个非唯一索引。添加缓存表的索引将提高同样查询非缓存TimesTen表的SQL速度。不要创建与Oracle表不匹配唯一索引,由于将起唯一约束失败。
注意:Oracle暂时表不能被缓存。
例如以下创建一个简单缓存集合定义来缓存一单一表:
CREATE TYPE CACHE GROUP owner.name
FROM
owner.root_table(column_list,
PRIMARY KEY(primary_key_column_list));
说明:
• owner.root_table 是Oracle表或一个Oracle表私有同义词的拥有者和表名。
• column_list 是一个被缓存的表的列清单和它们的数据类型。
• primary_key_column_list 是一个组成主键的列的清单。
当为列选择数据类型时,要考虑Oracle列中的数据类型并为缓存集合中的表选择对应的数据类型映射。
例 3.3 图 3.6 显示一个单表READONLY缓存集合,名为target_customers,缓存Oracle表customer。TimesTen缓存集合中的数据是一个更大的存储在Oracle数据中全部用户数据集的子集。
图 3.6 在TimesTen中缓存单个Oracle表
使用CREATE READONLY CACHE GROUP语句来创建单表缓存集合target_customers:
CREATE READONLY CACHE GROUP target_customers
FROM
user1.customer (cust_num NUMBER NOT NULL PRIMARY KEY,
region VARCHAR2(5) NOT NULL,
name VARCHAR2(80),
address VARCHAR2(255) NOT NULL);
假设多个Oracle表被缓存在同一个缓存集合中,必须定义一个根表和多个子表。在一个缓存集合中仅仅能有一个根表。
在有多表的缓存集合中,缓存集合中的每一个子表必须通过外键约束与缓存集合中的根表或还有一个子表相关联。虽然在TimesTen中缓存集合中的表必须通过外键约束关联,但在Oracle实例中,这些表不一定要关联起来。缓存集合中的根表不能通过外键约束引用缓存集合中另外的不论什么表。缓存集合中另外全部表都是子表。
每一个表的定义必须包括一个主键。每一个子表也必须包括一个引用到它父表主键的外键。缓存集合中表层次能够指定子表到父表或其他子表,但缓存集合中的表不能是一个在此缓存集合中有多个父表的子表。參阅图 3.7 关于一个正确缓存集合表配置的演示样例。图 3.8 显示一个不对的表配置,图 3.9 显示如何工作来解决这个问题。
必须在缓存集合中为每一个将被包括在缓存中的Oracle表创建单独的表定义。定义在缓存集合中的表的全部者和名称必须与Oracle表的全部者和名称相匹配。能够创建一个表定义来缓存Oracle表中列的全部数据或它的一个子集。
注意:每一个Oracle表能够仅仅被定义在一个缓存集合中。不能创建多个缓存集合来缓存同样的Oracle表。
例 3.4 创建一简单缓存集合定义来缓存一个根表和一个子表例如以下:
CREATE TYPE CACHE GROUP owner.name
FROM
owner.root_table(column_list,
PRIMARY KEY(primary_key_column_list)),
owner.child_table(column_list,
PRIMARY KEY(primary_key_column_list),
FOREIGN KEY(reference_column_list)
REFERENCES owner.root_table(primary_key_column_list));
说明:
• owner.root_table 是Oracle表或Oracle表的私有同义词的全部者和表名。
• owner.child_table 是Oracle表或Oracle表的私有同义词的全部者和表名。
• column_list 是一个被缓存表中的列清单。
• primary_key_column_list 是一个组成主键的列的清单。
• reference_column_list 是一个child_table中引用一个外键的列的清单。
图 3.7 显示先前显示在图 3.6中的target_customers缓存集合的多表版本号。
图 3.7 多表缓存集合
在此例中,缓存集合被扩展到缓存三个Oracle表:customer、orders和order_item。缓存集合中的数据是一个更大的存储在Oracle数据库中全部用户数据集的一个子集。target_customers缓存集合中的每一个父表有一个主键(显示为粗体),通过一个相关的外键(显示为箭头)被子表引用。表customer是根表,它不能缓存集合中不论什么另外的表。customer表的主键是对于target_customers缓存集合的主键。orders和order_item表是子表。
例 3.5 使用CREATE READONLY CACHE GROUP语句来创建target_customers多表缓存集合:
CREATE READONLY CACHE GROUP target_customers
FROM
user1.customer (cust_num NUMBER NOT NULL PRIMARY KEY,
region VARCHAR2(10) NOT NULL,
name VARCHAR2(80),
address VARCHAR2(255) NOT NULL),
user1.orders (ord_num NUMBER NOT NULL PRIMARY KEY,
cust_num NUMBER NOT NULL,
when_placed TIMESTAMP NOT NULL,
when_shipped TIMESTAMP,
FOREIGN KEY (cust_num) REFERENCES user1.customer (cust_num)),
user1.order_item (ord_num NUMBER NOT NULL,
prod_num NUMBER NOT NULL,
quantity NUMBER NOT NULL,
PRIMARY KEY (ord_num, prod_num),
FOREIGN KEY (ord_num) REFERENCES user1.orders (ord_num));
图igure 3.8 显示缓存集合中不对的表配置。
图 3.8 问题:两个根表
不能在拥有customer、orders和order_item表的同一个缓存集合中定义products和inventory表。这是由于products表没有引用(直接或间接)到根表customer的外键。这就意谓着products表也被觉得是一个根表,由于一个缓存集合不能同一时候拥有多个根表,因此无效。
为了缓存全部表,能够为products和inventory表创建第二个缓存集合,如图 3.9所看到的。
图 3.9 解决:两个独立的缓存集合
当缓存常规Oracle表时,能够在缓存集合中依据规则规定定义Oracle分区表。比如,在仅仅读缓存集合中的分区表在Oracle中必须有一个对应的唯一非NULL值索引。用于缓存集合的分区表能够是不论什么样式(哈希、列表、排列或合成)的分区或子分区表。
以下是缓存Oracle分区表时的限制:
• 除非有数据丢失,在分区上的DDL操作不会影响缓存集合。比如,假设一个分区的数据被截短,AUTOREFRESH不会从对应的缓存表中删除数据。
• 缓存集合中的WHERE子句操作不引用单独的分区或子分区。比如,试图定义下列分区表user1.partitioned_table,将返回一个错误:
CREATE READONLY CACHE GROUP badcachegroup
FROM
user1.partitioned_table(ii NUMBER NOT NULL PRIMARY KEY, jj NUMBER)
WHERE ii IN (SELECT ii
FROM user1.partitioned_table PARTITION(F200402));
注意:在离线分区上试图缓存操作(如LOAD CACHE GROUP、UNLOAD
CACHE GROUP或REFRESH CACHE GROUP)将导致ORA-00376或ORA-01110错误。可是,假设分区将离线(如在一个备份操作期间),则不会产生错误,除非这时试图訪问分区。
一个定义在缓存集合中的表能够引用Oracle其表的私有的Oracle同义词。实际的Oracle基表能够存在于还有一个Oracle帐号中,并有一个不同的名称,但作为同义词它必须驻留在同一个Oracleserver上。缓存集合中的表名必须是私有同义词名称,但同义词能够指向还有一个公有或私有的同义词。同义词终于必须指向(直接或间接)一个表、分区表或物化视图。
包括为Oracle同义词的表定义的缓存集合能够是一个USERMANAGED、SWT或AWT缓存集合。USERMANAGED缓存集合支持LOAD CACHE GROUP、UNLOAD CACHE GROUP、REFRESH CACHE GROUP和FLUSH CACHE GROUP 操作,但不能使用AUTOREFRESH或READONLY属性配置此缓存集合。不能在READONLY缓存集合中为Oracle同义词定义表。
在使用CREATE CACHE GROUP语句为用户管理和READONLY缓存集合中的表的定义能够包括一条WHERE子句来指定搜索条件来将Oracle数据拷贝到缓存中。
另外,能够在LOAD CACHE GROUP、UNLOAD CACHE GROUP、MERGE和FLUSH CACHE GROUP语句中指定WHERE子句。一些语句,如LOAD CACHE GROUP和REFRESH CACHE GROUP,将导致连接的WHERE子句中缓存集合中的WHERE子句将先于语句中的WHERE进行计算。全部的WHERE子句将通过TimesTen解析。不要使用TimesTen不支持的Oracle SQL语法。
例 3.6 此例创建一个名为western_customers的缓存集合,指定一条WHERE子句来从Oracle表customer中仅仅缓存那些西部地区中有邮政编码的用户的相关数据:
CREATE USERMANAGED CACHE GROUP western_customers
FROM
user1.customer (custid INTEGER NOT NULL,
name VARCHAR(2100) NOT NULL,
addr VARCHAR2(100),
zip VARCHAR2(10),
region VARCHAR2(10),
PRIMARY KEY(custid),PROPAGATE)
WHERE (user1.customer.region = 'Western');
然后在LOAD CACHE GROUP语句中指定另外一条WHERE子句来仅仅缓存来自西部地区的ID小于或等于100的用户:
LOAD CACHE GROUP western_customers WHERE (custid <= 100)
COMMIT EVERY 256 ROWS;
CREATE CACHE GROUP和LOAD CACHE GROUP 语句中的WHERE子句,在数据被载入到缓存集合之前,在Oracle上进行计算。
表 3.4 显示LOAD CACHE GROUP, UNLOAD CACHE GROUP、REFRESH CACHE GROUP和FLUSH CACHE GROUP语句的WHERE子句是否在TimesTen、Oracle或两者上都要计算。假设CREATE CACHE GROUP语句也包括一条WHERE子句,此表显示在Oracle上计算的另外的WHERE子句。
表 3.4 WHERE子句的计算
SQL语句 |
语句的WHERE子句的计算处... |
CREATE CACHE GROUP WHERE 子句计算处... |
LOAD |
Oracle |
Oracle |
UNLOAD |
TimesTen |
- |
REFRESH |
TimesTen和Oracle |
Oracle |
FLUSH |
TimesTen |
- |
表 3.5 显示对每一条SQL语句的WHERE子句是否仅仅由TimesTen或同一时候由TimesTen和Oracle解析。
表 3.5 WHERE子句解析
SQL语句 |
由TimesTen解析 |
由Oracle解析 |
LOAD |
Yes |
Yes |
UNLOAD |
Yes |
No |
REFRESH |
Yes |
Yes |
FLUSH |
Yes |
No |
CREATE |
Yes |
Yes |
与具体日志一起,全部面对Oracle运行的SQL语句将记录在Oracleserver日志中。查看此日志以更好的理解缓存集合操作的机制和运行。
以下是Cache Connect to Oracle使用WHERE子句的限制:
• CREATE CACHE GROUP语句中的WHERE子句不能指定子查询,所以它们不能引用不论什么当前的其他表。LOAD CACHE GROUP, UNLOAD CACHE GROUP、REFRESH CACHE GROUP和FLUSH CACHE GROUP语句中的WHERE子句能够指定子查询。
• WHERE子句不能包括Oracle PARTITION扩展名。
• LOAD CACHE GROUP、REFRESH CACHE GROUP、FLUSH CACHE GROUP语句(表和同义词)中的WHERE子句仅仅能够引用根表,除非WHERE子句包括一个子查询。
• 当创建一个多表缓存集合时,全部WHERE子句中的列名必须合法,如:user.table.column。
在缓存集合和Oracle Database之间的操作将继承此会话中使用的TimesTen全球支持的连接属性值。这些操作包括传送、载入、刷新、更新和同步写。
不直接与指定用户会话相关联的缓存集合操作将缺省使用全球支持的连接属性设置。这些操作包括自己主动刷新、老化和异步写。比如,这此操作使用BINARY作为NLS_SORT的值。
假设缓存集合操作使用了与全球支持的连接属性不同的值,将产生矛盾。比如,考虑以下的语句:
CREATE CACHE GROUP cachegroup1 FROM table1(
column1 NUMBER NOT NULL PRIMARY KEY,
column2 NCHAR(30))
WHERE column2 < 'string';
WHERE子句中的字符串将使用这些字符的二进制值来进行比較。这将在基于本地组装缓存集合表时,可能导致非预期结果。
为了保证WHERE子句中的字符串使用它们语言学的值来进行比較,使用CREATE CACHE GROUP语句时使用一条与面类似的WHERE子句:
CREATE CACHE GROUP cachegroup1 FROM table1(
column1 NUMBER NOT NULL PRIMARY KEY,
column2 NCHAR(30))
WHERE
NLSSORT(column2,'NLS_SORT=TCHINESE_RADICAL')
< NLSSORT('string','NLS_SORT=TCHINESE_RADICAL');
能够为缓存集合中的根表定义一个老化性质。老化性质引用老化类型和老化属性,也就是老化状态(ON或OFF)。能够指定下列之中的一个的老化类型:基于使用或基于时间。基于使用老化将删除指定数据存储使用范围内近期使用过(LRU)的数据。基于时间老化将依据指定的数据生存期和老化处理频率来删除数据。在同样的数据存储中,能够在同一个数据存储定义基于使用和基于时间的老化,但在指定的缓存集合或表中仅仅能定义一种老化类型。
CREATE CACHE GROUP语句中使用表定义来为新缓存集合的根表指定一个老化性质。假设表中未定义老化性质,能够使用ALTER TABLE语句来为已存在的缓存集合中的根表添加老化性质。能够通过先删除老化性质然后再加入老化性质来改变老化性质。
老化性质仅仅能定义在缓存集合的根表上,由于老化是基于缓存实例的。
能够为那些没在缓存集合中的表定义老化性质。
基于使用老化将保证在指定的极限范围内通过删除近期使用过(LRU)的数据来保持数据存储中可使用内存的大小。LRU老化可用于除了使用AUTOREFRESH属性的缓存集合以外的全部类型的缓存集合。
通过在CREATE CACHE GROUP语句中的表定义中使用AGING LRU子句来为一个缓存集合定义LRU老化。假设状态是ON,老化将自己主动開始。假设根表是数据存储中第一个拥有LRU老化性质定义的表,老化将马上開始。否则,老化将在已有LRU老化性质定义的表上发生老化时在根表上同一时候发生。
使用ttAgingLRUConfig内部程序来为数据存储中的全部表指定LRU老化属性。此属性将应用到有LRU老化性质的数据存储中全部的表。假设不调用ttAgingLRUConfig内部程序,则将使用属性的缺省值。
下表总结LRU老化属性:
LRU老化属性 |
描写叙述 |
LowUsageThreshhold |
LRU老化被解除时数据存储PermSize的百分比。 |
HighUsageThreshhold |
LRU老化激活时数据存储PermSize的百分比。 |
AgingCycle |
在两个老化周期之间的分钟数。 |
在定义LRU老化性质之后,假设为AgingCycle设置了一个新值,老化的产生将基于当前时间和新的周期。比如,假设原来的周期是15分钟,而且LRU在10分钟之前已经产生,则老化估计将在5分钟之后再次发生。可是,假设将AgingCycle參数改变为30分钟,则老化将从使用新的AgingCycle值调用ttAgingLRUConfig程序之时起30分钟后发生。
假设自从上一次老化周期后一行被訪问或引用,它就不符合LRU老化的条件。假设下列之中的一个为真时,行就觉得被訪问或引用过:
• 行被用来建立一条SELECT语句的结果集。
• 行已经作上被更新或删除的标记。
• 行被用来建立一条INSERT SELECT语句的结果集。
使用ALTER TABLE语句来运行下列任务:
• 通过在缓存集合的根表上使用带有SET AGING {ON|OFF}子句的ALTER TABLE语句来激活或非激活老化状态。
• 通过使用带有ADD AGING LRU [ON|OFF]子句的ALTER TABLE语句来在为已存在的根表添加一LRU老化性质。
• 通过使用带有DROP AGING子句的ALTER TABLE语句来删除根表上的老化。
使用ttAgingScheduleNow内部程序来确定老化的開始。
为了将缓存集合的老化从LRU改变为基于时间,首先使用带有DROP AGING子句的ALTER TABLE语句来删除根表上的老化。然后通过使用带有ADD AGING USE子句的ALTER TABLE语句来为根表添加基于时间的老化。
基于时间老化将依据指定的数据生存期和老化处理频率从缓存集合的根表中删除数据。在CREATE CACHE GROUP语句的表定义中的AGING USE子句中定义基于时间的老化。使用带有AGING USE子句的ALTER TABLE语句来为已存在缓存集合中的根表添加一基于时间的老化性质。
AGING USE子句有一个ColumnName參数。ColumnName是用于基于时间老化的列的名称。作为简化,称呼此列为timestamp列。timestamp列必须定义例如以下:
• TIMESTAMP或DATE数据类型
• NOT NULL
应用将更新timestamp列的值。假设此列的值对于某些行来说是未知的,而且不想这些行被老化,则使用一个较大的缺省值来定义此例。能够在timestamp列上创建一个索引,以提高老化处理的运行速度。
注意:不能在已存在的表中添加或改动一个列,然后将它用作timestamp列,由于不能添加或改动一个列并定义它为NOT NULL。
不能从已经有基于时间老化性质的表中删除timestamp列。
在CREATE CACHE GROUP语句中的LIFETIME子句中以days、hours或minutes指定生存期。
timestamp列中的值将从SYSDATE中被减去。被截短的结果使用指定单位(minute、hour、day),并与指定的LIFETIME值进行比較。假设结果大于LIFETIME值,则行将成为老化的候选行。
使用CYCLE子句来指定系统检查行的周期以删除超过指定的生存期的数据。假设没有指定CYCLE,则每隔五分钟产生一次老化。假设指定CYCLE为0,则老化将持续产生。假设状态为ON,老化将自己主动開始。
使用ALTER TABLE语句来运行下列任务:
•通过使用SET AGING {ON|OFF}子句来在使用基于时间老化性质的根表上激活或非激活老化状态。
• 通过使用SET AGING CYCLE子句来在使用基于时间老化性质的根表上改变老化周期。
• 通过使用SET AGING LIFETIME子句来改变根表中生存期。
• 通过使用ADD AGING USE子句来为没有老化性质的已存在的根表添加基于时间老化。
• 通过使用DROP AGING子句来删除根表上的老化。
当老化開始时使用ttAgingScheduleNow内部程序来安排时序。
为了将缓存集合的老化从基于时间改为LRU,首先删除根表上的老化。然后使用带有ADD AGING LRU子句的ALTER TABLE语句来为根表添加LRU老化。
注意:假设要改变AUTOREFRESH缓存集合根表的属性,必须停止缓存代理。在AUTOREFRESH 缓存集合中添加、改变或删除老化之前,停止缓存代理。
通过外键关联的表必须拥有同样的老化性质。
假设LRU老化在起作用过程中而且子表中的行近期被訪问过,则无论是父表还是子表中的行都将被删除。
假设基于时间老化在起作用过程中而且父表中的行已成为老化候选行,则父行和它全部的子行都将被删除。
假设表的ON DELETE CASCADE被激活,则将忽略此设置。
使用ttAgingScheduleNow内部程序来安排老化过程的时序。一旦调用内部程序老化过程就马上開始,除非已经有一个老化过程正在进行中,这样的情况下,当进行中的老化完毕时,新的老化才干開始。
当调用ttAgingScheduleNow时,老化过程将启动,而无论状态是否是ON或OFF。当调用ttAgingScheduleNow时要指定根表的名称。否则ttAgingScheduleNow将在数据存储中有老化定义的全部表上启动或又一次启动老化,而不仅仅是缓存集合的根表。
老化过程的启动仅仅是作为调用ttAgingScheduleNow的结果。调用ttAgingScheduleNow不会改变老化的状态。当调用ttAgingScheduleNow时假设老化的状态是OFF,则老化过程将開始,但在过程完毕后它不会持续。为了继续老化,必须再次调用ttAgingScheduleNow或将老化状态改为ON。
假设老化状态已经设置为ON,则ttAgingScheduleNow将依据调用ttAgingScheduleNow的时间来又一次设置老化周期。
能够控制老化行为。首先通过使用带有SET AGING OFF子句的ALTER TABLE语句来非激活老化。然后在期望的时间使用ttAgingScheduleNow来启动老化。
调用程序时,能够使用ttAgingScheduleNow并通过通过指定表名来为单一表启动或重新启动老化。假设不指定表名,则ttAgingScheduleNow将启动或重新启动有老化定义的数据存储中全部表的老化。
能够使用ttTraceMon工具来监视老化。
能够使用基于时间老化来完毕缓存集合数据变化窗体。在带有变化窗体的缓存集合中,依照时序规则加入新数据和删除老数据,以使缓存仅仅保留满足指定的时间间隔的数据。
能够通过使用增量AUTOREFRESH属性来为缓存集合数据配置一变化窗体,并指定基于时间老化性质。AUTOREFRESH操作将在Oracle中检查timestamp以决定是否将新数据刷新到缓存表中。Oracle和TimesTen的SYSDATE和时区必须一致。
不能为通过手工载入、显示载入、刷新或插入数据的其他类型的缓存集合配置变化窗体来将新数据更新到缓存集合表中。
例 3.7 以下的语句使用变化窗体属性创建一个缓存集合。
CREATE READONLY CACHE GROUP cg1
AUTOREFRESH STATE ON INTERVAL 1 MINUTES
FROM t1(i NUMBER NOT NULL PRIMARY KEY,
ts TIMESTAMP NOT NULL,
c VARCHAR2(50))
AGING USE ts LIFETIME 3 HOURS CYCLE 10 MINUTES;
cg1缓存集合有1分钟的自己主动刷新间隔。每一分钟都会将Oracle表中的新数据更新到缓存集合中。
老化将每10分钟检查一次老数据。老化将删除大于3小时的老数据(ts < SYSDATE - 3 HOURS)。
为AUTOREFRESH间隔和LIFETIME间隔设置的參数将决定数据将在缓存中保存多长时间。小于完整生存期间隔的数据也可能被老化出缓存。比如,假设AUTOREFRESH间隔是3天,而且LIFETIME间隔为30天,当数据进入缓存时可能已经存在3天了。因此数据在27天后将从缓存中被删除。这样的情况发生是由于老化是基于Oracle timestamp而不是基于TimesTen timestamp。
假设使用Oracle TimesTen In-Memory Database的Cache Connect特性,必须使用Oracle类型模式(TypeMode=0),即使缓存集合是被7.0曾经的版本号所定义。
假设缓存集合是被7.0曾经的版本号所定义,使用带有-convertCGTypes选项的ttMigrate工具来映射数据类型到用于7.0或此后的版本号的数据类型。
注意假设应用使用的是本地整数数据类型,并要继续使用它们,在调用ttMigrate之前,必须改变应用为指定的TT_INTEGER、TT_SMALLINT、TT_TINYINT和TT_BIGINT。
BINARY_FLOAT和BINARY_DOUBLE被传入到Oracle Database 10g Release 1。Cache Connect支持从Oracle9i到Oracle Database 10g的Oracleclient和server端。
假设须要使用BINARY_FLOAT或BINARY_DOUBLE数据类型,TimesTen推荐例如以下配置:
• 使用Oracle Database 10gclient和server
• 将TimesTen中的BINARY_FLOAT数据映射为Oracle中BINARY_FLOAT数据
• 将TimesTen中的BINARY_DOUBLE数据映射为Oracle中的BINARY_DOUBLE数据
能够在Oracle9i和Oracle Database 10g中使用FLOAT(n)。
假设在映射TT_BINARY_FLOAT数据类型为Oracle的FLOAT(n)时,须要保持内存或提高运行速度,TimesTen推荐Oracleclient的版本号要与serverOracle的版本号同样或较低。虽然作为推荐,也会发生下列情况:
• 在从FLOAT(n) 转换到BINARY_FLOAT和BINARY_DOUBLE时,会有数据精度的丢擒失。
• 在缓存中当Inf和NaN被定义为BINARY_FLOAT和BINARY_DOUBLE数据类型时,Inf可能被转换溢出,NaN可能被转换为0。
当为缓存集合表的列选择数据类型时,要考虑Oracle列的数据类型,并为缓存集合表中的列选择等价的数据类型。
主键和外键列级别要高于非键列。对于缓存集合表中的键列同意的数据类型映射显示在表 3.6中。
表 3.6 键列中同意的数据类型映射
Oracle数据类型 |
TimesTen数据类型 |
NUMBER(p,s) |
NUMBER(p,s) 注意:也能够使用DECIMAL(p,s)或NUMERIC(p,s)。它们是NUMBER(p,s)的别名。 |
NUMBER(p,0) INTEGER |
TT_TINYINT TT_SMALLINT TT_INTEGER TT_BIGINT INTEGER NUMBER(p,0) |
NUMBER |
TT_TINYINT TT_SMALLINT TT_INTEGER TT_BIGINT NUMBER |
CHAR(m) |
CHAR(m) |
VARCHAR2(m) |
VARCHAR2(m) |
RAW(m) |
VARBINARY(m) |
TIMESTAMP(m) |
TIMESTAMP(m) |
DATE |
DATE |
NCHAR(m) |
NCHAR(m) |
NVARCHAR2(m) |
NVARCHAR2(m) |
表 3.7 显示关于缓存集合中非键列映射的数据类型。
表 3.7 关于非键列同意的数据类型映射
Oracle数据类型 |
TimesTen数据类型 |
NUMBER(p,s) |
NUMBER(p,s) REAL FLOAT BINARY_FLOAT DOUBLE BINARY_DOUBLE |
NUMBER(p,0) INTEGER |
TT_TINYINT TT_SMALLINT TT_INTEGER TT_BIGINT INTEGER NUMBER(p,0) FLOAT BINARY_FLOAT DOUBLE BINARY_DOUBLE |
NUMBER |
TT_TINYINT TT_SMALLINT TT_INTEGER TT_BIGINT NUMBER REAL FLOAT BINARY_FLOAT DOUBLE BINARY_DOUBLE |
CHAR(m) |
CHAR(m) |
VARCHAR2(m) |
VARCHAR2(m) |
RAW(m) |
VARBINARY(m) |
LONG |
VARCHAR2(m) 注意:m能够是为此数据类型定义的范围内的不论什么有效值。 |
LONG RAW |
VARBINARY(m) 注意:m能够是为此数据类型定义的范围内的不论什么有效值。 |
TIMESTAMP(m) |
TIMESTAMP(m) |
DATE |
DATE TIMESTAMP(0) |
FLOAT(n) 注意:包括DOUBLE PRECISION和FLOAT,等于 FLOAT(126)。也包括REAL,等于FLOAT(63)。 |
FLOAT(n) BINARY_DOUBLE 注意:FLOAT(126)能够声明为DOUBLE PRECISION。FLOAT(63)能够声明为REAL。 |
BINARY_FLOAT |
BINARY_FLOAT |
BINARY_DOUBLE |
BINARY_DOUBLE |
NCHAR(m) |
NCHAR(m) |
NVARCHAR2(m) |
NVARCHAR2(m) |
这部分总结将TimesTen主机配置为Oracle Client并使用Cache Connect to Oracle特性来操作远程Oracleserver的指定步骤。
1.在TimesTen主机上安装Oracleclient或Oracle数据库。Oracleclient或数据库必须在安装TimesTen之前装以防止使用Cache Connect特性时会出现故障。
2. 为特定的操作系统配置环境变更。
3. 安装TimesTen。
4. 假设打算使用基于Web的Cache Administrator,配置内植的webserver。
5. 假设在TNSNAMES.ORA文件里定义Oracle Service Names,要使用系统级TNSNAMES.ORA文件。TimesTen的主守护程序、缓存代理、webserver和复制代理将使用系统级TNSNAMES.ORA文件里提供的信息。不要使用不同的TNSNAMES.ORA文件来配置Oracleclient。
注意:TimesTen不支持Oracle Name Server for Windows clients。
为TimesTen用户环境和启动TimesTen守护程序(根)的用户环境环境变量设置:
• 设置ORACLE_HOME环境变量为Oracle Client安装文件夹的路径。比如:
$ORACLE_HOME = /oracle/ora10g
• 对于32-位和64-位Oracle/TimesTen安装应该包括LD_LIBRARY_PATH或SHLIB_PATH环境变更:
$ORACLE_HOME/lib
$ORACLE_HOME/network/lib
install_dir/lib
比如:
LD_LIBRARY_PATH = $ORACLE_HOME/lib:$ORACLE_HOME/network/lib:
/timesten/myinstance/lib
注意:假设使用32-位TimesTen安装而配置64-位Oracleserver,则库路径是$ORACLE_HOME/lib32。
• PATH环境变量应该包括:
$ORACLE_HOME/bin
install_dir/bin
比如:
PATH = $ORACLE_HOME/bin:/timesten/myinstance/bin
必须设置PATH系统环境变量包括:
Oracle_install_dir/bin
install_dir/lib
install_dir/bin
比如:
PATH = C:/Oracle/Ora10g/bin;C:/timesten/myinstance/lib;
C:/timesten/myinstance/bin;
这部分将讨论操作Oracle DBA必须使用system帐号在Oracle数据库上运行。
必须指定一个Oracle用户和口令以訪问Oracle表和创建缓存集合。全部Oracle用户帐号必须授予CREATE SESSION权限,以使用Cache Connect to Oracle。一些Cache Connect to Oracle操作要求另外的Oracle用户权限。
一些Cache Connect to Oracle操作要求一个使用另外Oracle权限的独立的用户。由于可能要求仅仅授予另外缓存管理用户权限来选择用户,所以Cache Connect to Oracle同意创建一个独立的缓存管理用户帐号。
关于用于每一个Cache Connect to Oracle操作的Oracle用户和缓存管理用户最小权限显示在表 4.1中。对一每一个缓存管理用户的权限必须包括全部Oracle表能够被缓存到数据存储中,同一时候Oracle用户也须要特定的指定在由用户创建的缓存集合中的Oracle表的权限。參阅例 4.1。
表 4.1 对于缓存集合操作的Oracle权限要求
缓存集合操作 |
授予Cache Connect to Oracle用户的最小权限 |
授予缓存管理用户的最小权限 |
全部操作 |
• 在Oracle数据库上CREATE SESSION • SELECT TABLE |
一个也不须要 |
CREATE READONLY CACHE GROUP |
• 在Oracle数据库上CREATE SESSION • SELECT TABLE |
• 在Oracle数据库上CREATE SESSION • SELECT TABLE • UNLIMITED TABLESPACE (或在表空间上适当的空间引用 ) • CREATE TABLE① • CREATE ANY TRIGGER① |
CREATE SYNCHRONOUS WRITETHROUGH CACHE GROUP |
• 在Oracle数据库上CREATE SESSION • SELECT TABLE • INSERT • UPDATE • DELETE |
一个也不须要 |
CREATE ASYNCHRONOUS WRITETHROUGH CACHE GROUP |
• 在Oracle数据库上CREATE SESSION • SELECT TABLE • INSERT② • UPDATE② • DELETE ② • QUERY REWRITE③ |
• 在Oracle数据库上CREATE SESSION • SELECT TABLE • INSERT • UPDATE • DELETE • UNLIMITED TABLESPACE (或在表空间上适当的空间引用 ) • CREATE TABLE① |
CREATE USERMANAGED CACHE GROUP(參阅并发行中的变量) |
• 在Oracle数据库上CREATE SESSION • SELECT TABLE |
一个也不须要 |
CREATE USERMANAGED CACHE GROUP .....加上 PROPAGATE |
• 在Oracle数据库上CREATE SESSION • SELECT TABLE • INSERT • UPDATE • DELETE |
一个也不须要 |
CREATE USERMANAGED CACHE GROUP .....加上 AUTOREFRESH INCREMENTAL |
• 在Oracle数据库上CREATE SESSION • SELECT TABLE • QUERY REWRITE ③ |
• 在Oracle数据库上CREATE SESSION • SELECT TABLE • UNLIMITED TABLESPACE (或在表空间上适当的空间引用 ) • CREATE TABLE① • CREATE ANY TRIGGER① |
LOAD CACHE GROUP |
• 在Oracle数据库上CREATE SESSION • SELECT TABLE |
• 在Oracle数据库上CREATE SESSION • SELECT TABLE |
REFRESH CACHE GROUP |
• 在Oracle数据库上CREATE SESSION • SELECT TABLE |
• 在Oracle数据库上CREATE SESSION • SELECT TABLE |
FLUSH CACHE GROUP |
• 在Oracle数据库上CREATE SESSION • SELECT TABLE • INSERT TABLE • UPDATE TABLE |
- |
使用Real Application Clusters 进行配置的全部操作 |
• 在Oracle数据库上CREATE SESSION • SELECT TABLE |
在Oracle GV$SESSION上SELECT动态性能视图 |
① 假设Oracle对象是手工安装的,不要求创建缓存集合
② 不强从TimesTen运行
③ 仅仅对于Oracle server version 9.2才要求
例 4.1 须要为两个用户Sam和John设立权限,使每一个用户能够发送一条CREATE READONLY CACHE GROUP语句来各自创建仅仅读缓存集合。Sam创建一个缓存Oracle表TTUSER.TABLEA的缓存集合,John创建还有一个缓存Oracle TTUSER.TABLEB的缓存集合。
为了提供Sam和John充足的Oracle权限来CREATE READONLY CACHE GROUP,须要创建两个Oracle用户帐号,而且当中一个缓存管理用户帐号将拥有扩展的权限。缓存管理用户的名称为User2:
• oracleUID = Sam
• oracleUID = John
• cacheUid = User2
在Oracle上创建帐号:
SQL> CREATE USER Sam IDENTIFIED BY Samspwd DEFAULT TABLESPACE users;
SQL> CREATE USER John IDENTIFIED BY Johnspwd DEFAULT TABLESPACE users;
SQL> CREATE USER User2 IDENTIFIED BY User2pwd DEFAULT TABLESPACE users;
然后为每一个用户分配下列权限:
SQL> GRANT CREATE SESSION, SELECT ON TTUSER.TABLEA TO Sam;
SQL> GRANT CREATE SESSION, SELECT ON TTUSER.TABLEB TO John;
SQL> GRANT
> CREATE SESSION,
> SELECT ON TTUSER.TABLEA, TTUSER.TABLEB,
> UNLIMITED TABLESPACE,
> CREATE TABLE,
> CREATE ANY TRIGGER
> TO User2;
SQL>
TimesTen强烈推荐为缓存管理用户创建一个独立的表空间。此表空间用作缓存管理用户的缺省表空间。此表空间包括有每一个Oracle表的自己主动刷新触发器、变化日志表和其他对于每一个缓存集合用户TimesTen须要的对象。假设不指定一个独立的表空间,这些对象将放在Oracle system表空间中。
当在Oracle上创建缓存管理用户时,要指定表空间。也能够创建用户之后使用Oracle ALTER USER语句的DEFAULT TABLESPACE子句来指定表空间。
例 4.2 例 4.1 显示如何创建并授权给缓存管理用户User2。为了给User2指定一个名为cacheuser的独立表空间,在Oracle中输入下列语句:
SQL> ALTER USER User2 IDENTIFIED BY User2pwd
DEFAULT TABLESPACE cacheuser;
每一个缓存的Oracle表的变化日志表驻留在缓存管理用户表空间中。对于Oracle表上每次更新,将为此Oracle表向变化日志表插入一行(一条变化记录)。变化日志记录的字节大小例如以下:
变化日志记录的大小 = Oracle表上主键的大小 + 250
变化日志表中的记录数将依赖于Oracle表的更新率和TimesTen上的自己主动刷新间隔。每隔20秒,TimesTen将删除已经应用到缓存相关Oracle表的数据存储的变化日志记录。
当缓存管理用户表空间变写满时,自己主动刷新触发器将通过删除已存在的变化日志记录来为新变化日志记录产生空间。这将引起一些TimesTen数据存储上一些表的全然自己主动刷新。
假设表空间写满,检查例如以下内容:
• 是否正在创建一个缓存集合或正在复制一个数据存储?这些暂时操作将停止变化日志表上的清除操作。
• TimesTen数据存储上的缓存代理是否正在运行?假设缓存代理没有运行,变化日志记录将堆积。
• 在数据存储中是否没有通过删除自己主动刷新缓存集合而抛弃的数据存储?在这样的情况下,变化日志记录也将堆积。
缓存Oracle数据的数据存储必须定义为系统DSN,不能作为User DSN,假设TimesTen缓存不定义为System DSN,则TimesTen Cache Administrator就不能进行工作,而且ttAdmin也不能启动TimesTen缓存代理。
DSN路径必须是一个绝对值。
当为了缓存Oracle表创建DSN时,DSN的属性必须例如以下设置:
• Logging 必须激活为disk-based。
• LockLevel 必须激活row-level locking。(Cache Connect to Oracle不支持database-level locking。)
• Isolation 能够是不论什么isolation模式。
• OracleID 必须设置为Oracle Service Name for Oracle 9i和以后的Oracle版本号。
• PassThrough 能够设置来控制程序和SQL语句是在本地的TimesTen缓存中运行或是传递到Oracle。
• DatabaseCharacterSet 必须与Oracle数据库字符集同样。
• TypeMode 必须设置为0(Oracle)。
下列属性能够指定为DSN属性或作为连接属性:
• Oracle User ID指定Oracle用户ID。此字符串通过设置UID连接属性来间接指定。对应的UNIX平台上的DSN属性是UID。在Window系统中,对应的DSN属性是User ID。
• OraclePWD 为Oracle用户指定口令。
用来连接到Oracle的username和口令将从DSN定义的属性中或ODBC连接串中取出。在连接串中给出的值将覆盖指定DSN中的值。
比如,能够在ttIsql连接串中指定Oracle UID和OraclePWD:
ttIsql -connStr "DSN=cgDSN; UID=testuser; OraclePWD=mypsswrd"
假设通过ODBC应用发送更新并提交,必须在连接串中指定username和口令。比如:
SQLDriverConnect(hdbc, ..., "DSN=cgDSN; UID=testuser;
OraclePWD=mypsswrd", ...);
在UNIX平台上 比如,为UNIX平台上的myOraCache定义就例如以下形式:
[myOraCache]
DataStore=/users/OracleCache/hotData
Authenticate=0
Logging=1
LockLevel=0
PermSize=40
TypeMode=0
DurableCommits=1
OracleID=system1
UID=testuser
OraclePWD=mypsswrd
DatabaseCharacterSet=WE8ISO1559P1
在Windowt系统中 在ODBC TimesTen Setup dialog的Oracle Data Loading窗体中指定OracleID。
一个TimesTen进程调用一缓存代理来运行异步缓存操作,如载入或刷新缓存集合。很多Cache Connect to Oracle操作能够直接通过TimesTen进行,而不须要缓存代理的协助。
假设下列之中的一个或多个情形为真,则必须为每一个包括缓存集合的数据存储启动一个独立的缓存代理:
• 缓存集合为READONLY。
• 缓存集合为USERMANAGED而且包括一条AUTOREFRESH子句。
• 应用载入或刷新缓存集合。
能够从命令行或一个程序来为一个DSN启动缓存代理。
也可从基于浏览器的Cache Administrator来启动缓存代理。
注意:假设安装TimesTen时激活了Access Control,必须拥有数据存储的ADMIN权限来启动或停止缓存代理。另外,TimesTenusername必须与Oracleusername相匹配(应用到内部和外部的username)。
使用ttAdmin工具来从命令行控制缓存代理。能够使用ttAdmin来:
• 从命令行设置缓存管理用户ID和口令
• 从命令行启动缓存代理
• 从命令行停止缓存代理
• 从命令行设置代理启动性质
假设使用下列之中的一个的缓存集合类型,则必须有一个拥有对应Oracle权限的缓存管理用户帐号:
• ASYNCHRONOUS WRITETHROUGH缓存集合
• READONLY缓存集合
• 使用AUTOREFRESH属性的USERMANAGED缓存集合
缓存管理用户ID必须遵守下列规则:
• 长度为1到30字节。
• 必须以字母开头。
• 仅仅能包括ASCII字母、下划线(_)、美元符号($)和英镑符号(#)。
缓存管理口令必须遵守下列规则:
• 长度为1到30字节。
• 能够包括除了分号(;)外的不论什么ASCII字符。
在启动缓存代理之前设置缓存管理用户ID和口令。使用例如以下语法:
ttAdmin -cacheUidPwdSet -cacheUid cacheUid -cachePwd cachePwd DSN
注意:假设数据存储中有自己主动刷新或AWT缓存集合,则缓存管理用户ID和口令不能进行又一次设置。在又一次设置缓存管理用户ID和口令之前,必须删除那些缓存集合。
例 4.3 ttAdmin -cacheUidPwdSet -cacheUid testuser -cachePwd mypass myOraCache
假设改变了缓存管理用户ID或口令,则必须又一次启动缓存代理。
注意:假设在数据存储中没有缓存集合,则不要设置缓存管理用户ID和口令。假设没有缓存集合时设置了它们,将不会使用缓存管理用户ID和口令,并校验到Oracle数据库。
为了人命令行启动缓存代理,使用例如以下语法:
ttAdmin -cacheStart DSN
例 4.4 ttAdmin -cacheStart myOraCache
假设试图为在DSN中使用相关路径标识的数据存储启动缓存代理,TimesTen将搜索TimesTen运行和失败的相关数据存储。比如,在Window系统中,假设在DSN中为数据存储指定路径为DataStore=./dsn1,而且试图使用以下命令启动缓存代理:
ttAdmin -cacheStart dsn1
缓存代理在install_dir/srv/dsn1中搜索数据存储。将不能在此位置找到数据存储,也不能启动缓存代理。对于UNIX,缓存代理将查找:
/var/TimesTen/ttversion/bits
为了停止代理,使用例如以下语法:
ttAdmin -cacheStop DSN
例 4.5 ttAdmin -cacheStop myOraCache
注意:使用AUTOREFRESH特性时,在删除或改变缓存集合之后,不要马上停止缓存代理。应该至少等待2分钟。缓存代理须要这个时间来清除AUTOREFRESH使用的Oracle对象。
能够通过调用ttCachePolicySet程序来设置缓存代理启动性质。使用ttCachePolicyGet程序来返回当前的性质。
缺省的缓存代理启动性质是manual。假设要在TimesTen守护程序又一次启动时将缓存代理自己主动又一次启动,则设置缓存代理性质为always。一旦设置性质为always,缓存代理将马上启动。
例 4.6 设置缓存代理性质为always:
CALL ttCachePolicySet ('always');
为了从程序中控制数据存储的缓存代理,首先连接到数据存储。使用ttCacheUidPwdSet、ttCacheStart、ttCacheStop或ttCachePolicySet程序来运行下列任务:
• 从程序设置缓存管理用户ID和口令
• 从程序启动缓存代理
• 从程序停止缓存代理
• 从程序设置缓存代理性质
注意:假设Access Control被激活,则须要ADMIN权限来为缓存代理和复制代理进行启动、停止和设置性质。也须要ADMIN权限来设置缓存管理用户ID和口令。
假设使用下列类型之中的一个的缓存集合,必须有一个拥有对应Oracle权限的缓存管理用户帐号:
• ASYNCHRONOUS WRITETHROUGH缓存集合
• READONLY缓存集合
• 使用AUTOREFRESH属性的USERMANAGED缓存集合
缓存管理用户ID必须遵守下列规则:
• 长度为1到30字节。
• 必须以字母开头。
• 仅仅能包括ASCII字母、下划线(_)、美元符号($)和英镑符号(#)。
缓存管理口令必须遵守下列规则:
• 长度为1到30字节。
• 能够包括除了分号(;)外的不论什么ASCII字符。
在启动缓存代理之前设置缓存管理用户ID和口令。使用ttCacheUidPwdSet程序。
例 4.7 在此例中,通过连接句柄hdbc指定数据存储。缓存管理用户ID为testuser,而且缓存管理用户口令为mypass。
sprintf( stmt, "CALL ttCacheUidPwdSet('testuser','mypass')");
rc = SQLAllocStmt( hdbc, &hstmt );
rc = SQLExecDirect( hstmt, (SQLCHAR *) stmt, SQL_NTS );
sprintf( stmt, "CALL ttCacheStart()" );
rc = SQLAllocStmt( hdbc, &hstmt2 );
rc = SQLExecDirect( hstmt2, (SQLCHAR *) stmt, SQL_NTS );
使用ttCacheStart程序来启动缓存代理。
例 4.8 在此例中,通过连接句柄hdbc指定数据存储。
sprintf( stmt, "CALL ttCacheStart()" );
rc = SQLAllocStmt( hdbc, &hstmt );
rc = SQLExecDirect( hstmt, (SQLCHAR *) stmt, SQL_NTS );
注意:假设自己主动提交非激活,则必须在提交之前和之后调用ttCacheStart。
使用ttCacheStop程序来停止缓存代理。
例 4.9 sprintf( stmt, "CALL ttCacheStop()" );
rc = SQLAllocStmt( hdbc, &hstmt );
rc = SQLExecDirect( hstmt, (SQLCHAR *) stmt, SQL_NTS );
ttCacheStop程序有一个选项參数stopTimeout,用来指定TimesTen守护程序要等多长时间才停止缓存代理。假设缓存代理在指定的时间内没有停止,则TimesTen守护程序将停止缓存代理。stopTimeout的缺省值是100秒。0值指定永远等待下去。
例 4.10 为了停止缓存代理,并设置stopTimeout为160秒:
sprintf( stmt, "CALL ttCacheStop(160)" );
rc = SQLAllocStmt( hdbc, &hstmt );
rc = SQLExecDirect( hstmt, (SQLCHAR *) stmt, SQL_NTS );
能够通过调用ttCachePolicySet程序来设置缓存代理启动性质。使用ttCachePolicyGet程序来返回当前的性质。
缺省的缓存代理启动性质是manual。假设要在TimesTen守护程序又一次启动时将缓存代理自己主动又一次启动,则设置缓存代理性质为always。一旦设置性质为always,缓存代理将马上启动。
例 4.11 设置由hdbc连接句柄指定数据存储的缓存代理启动性质为always:
sprintf( stmt, "CALL ttCachePolicySet ('always')");
rc = SQLAllocStmt( hdbc, &hstmt );
rc = SQLExecDirect( hstmt, (SQLCHAR *) stmt, SQL_NTS );
能够使用ttStatus工具或ttDataStoreStatus程序来检查正在运行的TimesTen缓存代理。
例 4.12 为了使用ttStatus工具来确认位于c:/temp/cgds的数据存储的缓存代理正在运行,输入:
C:/>ttStatus
TimesTen status report as of Wed Apr 07 15:04:45 2004
Daemon pid 484 port 15000 instance MYCOMPUTER
No TimesTen server running
--------------------------------------------------------------
Data store c:/temp/cgds
There are 4 connections to the data store
Data store is in shared mode
Shared Memory KEY Global/DBI3cd02077.0.SHM.26 HANDLE 0x380
Subdaemon pid 964 context 0x5d82d0 connected (KEY
Global/DBI3cd02077.0.SHM.26)
Process pid 2040 context 0x97b200 connected (KEY
Global/DBI3cd02077.0.SHM.26)
Process pid 2040 context 0x1427c70 connected (KEY
Global/DBI3cd02077.0.SHM.26)
Process pid 2040 context 0x144bd70 connected (KEY
Global/DBI3cd02077.0.SHM.26)
TimesTen's cache agent is running for this data store
cache agent restart policy: manual
能够使用带有-query选项的ttAdmin工具来确觉得数据存储设置的性质,包括缓存代理的重新启动性质。
例 4.13
C:/>ttAdmin -query cgDSN
RAM Residence Policy : inUse
Replication Agent Policy : manual
Replication Manually Started : False
cache agent Policy : manual
cache agent Manually Started : True
例 4.14 假设已经创建了一个AWT缓存集合,而且数据存储已经启动复制代理,则ttStatus工具也报告Oracle和复制代理的状态。在此例中,复制和缓存代理正在运行。
C:/> ttStatus
TimesTen status report as of Wed May 4 13:44:30 2005
Daemon pid 25337 port 16000 instance -
No TimesTen server running
No TimesTen webserver running
-----------------------------------------------------------------
------- Data store /datastore/cache There are 15 connections to
the data store Data store is in shared mode Shared Memory KEY
0x260e30c2 ID 521502725
Cache agent pid 25545 context 0x82fd820 name timestenorad
connid 2 connected (KEY 0x260e30c2)
Cache agent pid 25545 context 0x832d798 name timestenorad
connid 4 connected (KEY 0x260e30c2)
Cache agent pid 25545 context 0x8335198 name timestenorad
connid 3 connected (KEY 0x260e30c2)
Cache agent pid 25545 context 0xaf27ad08 name timestenorad
connid 6 connected (KEY 0x260e30c2)
Process pid 25485 context 0x80bd8b0 name cache connid 8
connected (KEY 0x260e30c2)
Replication pid 25559 context 0x8193110 name connid 7
connected (KEY 0x260e30c2)
Replication pid 25559 context 0x81bddb0 name connid 9
connected (KEY 0x260e30c2)
Replication pid 25559 context 0x81e53f8 name connid 12
connected (KEY 0x260e30c2)
Replication pid 25559 context 0x82040d8 name connid 5
connected (KEY 0x260e30c2)
Replication pid 25559 context 0x8229148 name connid 10
connected (KEY 0x260e30c2)
Replication pid 25559 context 0x824e1b8 name connid 11
connected (KEY 0x260e30c2)
Subdaemon pid 25350 context 0x8092960 name Worker connid
2044 connected (KEY 0x260e30c2)
Subdaemon pid 25350 context 0x8110140 name Flusher connid
2045 connected (KEY 0x260e30c2)
Subdaemon pid 25350 context 0x813a838 name Checkpoint
connid 2047 connected (KEY 0x260e30c2)
Subdaemon pid 25350 context 0x81608f8 name Monitor connid
2046 connected (KEY 0x260e30c2)
Replication policy : Manual
Replication agent is running.
Cache agent policy : Manual
TimesTen's Cache agent is running for this data store
假设使用异步写(AWT)缓存集合,必须启动复制代理。
CREATE ASYNCHRONOUS WRITETHROUGH CACHE GROUP 语句将创建一个复制计划以激活数据存储与Oracle数据库之间的通信。复制计划全然由TimesTen管理,不须要用户介入。使用DROP CACHE GROUP语句删除AWT缓存集合时,复制计划也将被删除。
可能通过使用带有-repStart选项的ttAdmin工具从命令行启动复制代理。
例 4.15 为AWTdsn数据存储启动复制代理。
ttAdmin -repStart AWTdsn
也能够通过使用ttRepStart程序从程序启动复制代理。
例 4.16 一个缓存管理用户的ID为testuser,口令为mypass,能够使用:
• ttCacheUidPwdSet 程序来设置缓存管理用户ID和口令
• ttCacheStart 程序来启动缓存代理
• ttRepStart 程序来为AWTdsn数据存储启动复制代理
sprintf( stmt, "CALL ttCacheUidPwdSet('testuser','mypass')");
rc = SQLAllocStmt( hdbc, &hstmt );
rc = SQLExecDirect( hstmt, (SQLCHAR *) stmt, SQL_NTS );
sprintf( stmt, "CALL ttCacheStart()" );
rc = SQLAllocStmt( hdbc, &hstmt2 );
rc = SQLExecDirect( hstmt2, (SQLCHAR *) stmt, SQL_NTS );
sprintf( stmt, "CALL ttRepStart()" );
rc = SQLAllocStmt( hdbc, &hstmt3 );
rc = SQLExecDirect( hstmt3, (SQLCHAR *) stmt, SQL_NTS );
注意:在为AWT缓存集合发送一条CREATE ASYNCHRONOUS WRITETHROUGH CACHE GROUP或DROP CACHE GROUP语句之前,要停止复制代理(如ttAdmin -repStop DSN)。
假设有定义缓存集合的SQL文件,就能够在TimesTen数据存储上使用带有-f选项的ttIsql工具来运行此SQL。语法是::
ttIsql -f file.sql DSN
例 4.17 假设缓存集合在名为CG1.sql的文件里定义,能够在名为cgDSN的DSN上运行此文件,输入:
C:/> ttIsql -f CG1.sql cgDSN
也能够从ttIsql命令行运行包括缓存集合定义的SQL文件。比如:
Command> run CG1.sql
应用通过TimesTen连接能够发送SQL语句到TimesTen或Oracle。
SQL是否被直接传送到TimesTen或Oracle将依赖于SQL语句的组成和PassThrough连接属性的设置。能够设置PassThrough属性来定义SQL语句的类型:是由本地的TimesTen处理,还是重定向到Oracle。
比如,能够设置PassThrough=0(缺省值)来指定全部SQL都在TimesTen中运行或PassThrough=3来指定全部SQL被传送到Oracle去运行。
如图 4.1显示,能够设置PassThrough=1来为一个不在TimesTen中的目标表或在TimesTen中产生的一条语法错误传送SQL。比如,一条到缓存表(Table A)的UPDATE 在TimesTen缓存中被处理,同一时候一条到在TimesTen中找不到的表(Table G)的UPDATE被传送到Oracle。同样地,TimesTen的设置程序如ttCacheStart或ttCkpt,由TimesTen处理,同一时候不支持的过程将传送到Oracle。
图 4.1 PassThrough=1
对于PassThrough=1的设置,没有DDL语句会传送到Oracle。TimesTen中不存在的过程将被传送到Oracle:假设对于缓存集合表DML语句包括错误语法,就不会发送到Oracle。可是,全部包括错误语法的SELECT语句将被发送到Oracle。
对于全部的passthrough级别,假设事务有不论什么DDL或DML语句传送到Oracle,则提交和回滚将在Oracle和TimesTen中都要运行。否则,将仅仅在TimesTen中运行。
READONLY缓存集合禁止在缓存集合中使用DML语句的更新。假设计划使用READONLY缓存集合,能够设置PassThrough=2来直接将缓存集合中全部表的DML语句定向到Oracle。否则,此设置将于PassThrough=1时一样,因此全部DDL语句、兼容的非DML语句及过程将直接到TimesTen。同样的passthrough情形也应用到USERMANAGED缓存集合中的READONLY表。比如,考虑如图4.1所看到的的缓存集合演示样例。假设在Table A上设置了READONLY属性,而且PassThrough = 2,一条到Table A的UPDATE将被传送到Oracle。
在AWT和SWT缓存集合的表DML操作不推荐使用passthrough特性。在被定义为异步的AWT集合中通过缓存进行的更新,passthrough将同步实施,可能将产生非预期结果。假设运用passthrough特性,SWT缓存集合中的更新可能导致自死锁。
确保应用为传送语句提供正确的SQL数据类型。ODBC驱动器将转换C和SQL类型,并向TimesTen传送转换的数据和SQL类型码。TimesTen传递此信息到Oracle。
TimesTen处理passthrough语句的參数与在TimesTen中它自己运行语句中的參数不同。TimesTen查询优化将为TimesTen语句的參数分配数据类型。应用将获得分配的数据类型来使用SQLDescribeParam ODBC函数。与此相比,passthrough语句的參数将不会为它们分配数据类型。TimesTen将报告passthrough语句的參数的数据类型为VARCHAR2(4000)。此数据类型仅仅是一个占位符。它不意谓着TimesTen期望作为VARCHAR2数据来接收此參数值。作为替代,当应用调用SQLBindParameter ODBC函数时,必须通知TimesTen关于passthrough语句參数的数据类型。SQLBindParameter的fSqlType參数指定參数的SQL数据类型。假设使用,cbColDef和ibScale參数指定精度和比例。
比如,为了绑定一个SQL数据类型INTEGER的參数为NUMBER(3)參数,使用下列參数调用SQLBindParameter ODBC函数:
fCType=SQL_C_SLONG
fSqlType=SQL_DECIMAL
cbColDef=3
ibScale=0
二选其一,也能够使用下列參数:
fCType=SQL_C_SLONG
fSqlType=SQL_INTEGER
cbColDef=0
ibScale=0
对于SQL_INTEGER,cbColDef和ibScale參数将被忽略。
能够在ttIsql会话中使用passthrough命令来覆盖DSN中PassThrough的设置。也能够为指定的事务通过调用ttOptSetFlag程序并指定‘passthrough’作为optflag參数和新的passthrough设置作为optval參数来又一次设置passthrough。新的passthrough设置将马上产生影响。在事务的最后,passthrough将被重置为原来指定在PassThrough属性中的值。
注意:PassThrough的行为如同不论什么其他的优化标志。当运行语句时准备的语句是使用的级别时,将建立PassThrough级别。假设在准许语句和运行它之间改变了PassThrough级别,则在运行中将使用原来的PassThrough级别。
以下部分将讨论如何得到缓存集合的配置信息和如何监视缓存集合的状态。
能够通过使用ttIsql cachegroup命令来获得关于数据存储中当前使用中的缓存集合的信息,如以下例4.18所看到的。
例 4.18
Command> cachegroup;
Cache Group TESTUSER.CUSTOMERORDERS:
AutoRefresh Mode: Incremental
AutoRefresh State: On
AutoRefresh Interval: 5 Minutes
Root Table: TESTUSER.CUSTOMER
Where Clause: (none)
Type: Read Only
Child Table: TESTUSER.ORDERTAB
Where Clause: (none)
Type: Read Only
Cache Group TESTUSER.TABCACHE:
Root Table: TESTUSER.TAB3
Where Clause: (none)
Type: Propagate
2 cache groups found.
TimesTen提供下列工具来监视自己主动刷新缓存集合:
• ttCacheAutorefreshStatsGet内部程序
• 支持日志中的信息
• 一个能够在Oracle数据库中运行的SQL脚本来显示关于变化日志表的信息
• ttTraceMon工具的AUTOREFRESH组成
• SNMP陷阱
READONLY缓存集合和一些USERMANAGED缓存集合使用AUTOREFRESH特性来自己主动将Oracle更新刷新到TimesTen缓存中。
能够为缓存集合建立全然或增量自己主动刷新模式。当配置为增量自己主动刷新时,TimesTen将为缓存集合中的每一个Oracle基表要求创建一个触发器、日志表和其他对象。每次在Oracle基表上的插入、更新和删除操作将启动触器。触发器将在日志表中记录更新记录的主键。TimesTen缓存代理将定期搜索日志表中的更新键和关联的被更新的Oracle基表以得到近期更新的快照。
使用AUTOREFRESH INCREMENTAL属性创建缓存集合时,自己主动刷新的要求的Oracle对象将被自己主动安装。二选其一,能够手工安装Oracle对象,以同意用户使用较小的Oracle权限来创建要使用触发器的缓存集合。
在安装Oracle对象之前,必须:
• 有一个授予了额外的缓存管理用户权限的缓存管理用户帐号。
• 使用ttCacheUidPwdSet设置缓存管理用户ID和口令。
• 启动缓存代理。
对于每一个缓存管理用户,TimesTen将创建下列各表,version是一个内部TimesTen版本号号:
• TT_version_USER_COUNT
• TT_version_AGENT_STATUS
• TT_version_SYNC_OBJS
对于缓存集合中的每一个表,TimesTen将创建下列对象,number是原Oracle表的对象ID,version是一个内部TimesTen版本号号。
对象 |
描写叙述 |
TT_version_number_L |
为记录到Oracle表的变化变化日志表。 |
TT_version_number_T |
在变化日志表记录变化的触发器。当在缓存表中有插入、删除和更新时被触发。 |
AWT缓存集合请求一个额外的Oracle对象。将在Oracle上创建一个名为TT_version_REPPPEERS的表用来跟踪状态和近期应用到Oracle的语句。此表将由CREATE ASYNCHRONOUS WRITETHROUGH CACHE GROUP语句自己主动创建。二选其一,能够创建AWT缓存集合之前手工创建此Oracle表。
假设AWT缓存集合是一个活动的复制计划备用对的一部分,则当创建活动的备用对时,一个名为TT_version_REPACTIVESTANDBY将在Oracle上被自己主动创建。
TimesTen将下列表的SELECT、INSERT、UPDATE和DELETE的权限授予给user PUBLIC:
• TT_version_number_L
• TT_version_USER_COUNT
• TT_version_REPPEERS (为AWT缓存集合创建)
• TT_version_REPACTIVESTANDBY (为活动的备用复制计划中的AWT缓存集合创建)
为了直接使TimesTen自己主动安装Oracle对象,确保缓存管理用户拥有全部要求的自己主动创建Oracle对象的权限。当以PAUSED或ON状态创建缓存集合或缓存集合状态被改为PAUSED或ON时,将自己主动创建Oracle对象。
例 4.19 显示如何直接使TimesTen为READONLY缓存集合自己主动安装Oracle对象。
1. 使用ttIsql来连接到cgDSN数据存储。
2. 调用ttCacheUidPwdSet程序来为数据存储设置缓存管理用户ID(testuser)和口令。
3. 调用ttCacheStart程序来启动缓存代理。
4. 使用CREATE READONLY CACHE GROUP来创建一个READONLY缓存集合,此集合有AUTOREFRESH INCREMENTAL值,而且STATE被设置为缺省值PAUSED。
例 4.19
> ttIsql cgDSN
Command> call ttCacheUidPwdSet('testuser','mypsswrd');
Command> call ttCacheStart();
Command> CREATE READONLY CACHE GROUP readcache
FROM
user1.readtab
(a NUMBER NOT NULL PRIMARY KEY, b VARCHAR2(31));
例 4.20 显示如何直接使TimesTen为AWT缓存集合自己主动安装Oracle对象。
例 4.20
> ttIsql cgDSN
Command> call ttCacheUidPwdSet('testuser','mypsswrd');
Command> call ttCacheStart();
Command> CREATE ASYNCHRONOUS WRITETHROUGH CACHE GROUP writecache
FROM user1.writetab (a NUMBER NOT NULL PRIMARY KEY,b VARCHAR2(31));
假设不须要授予用户全然自己主动安装Oracle对象的CREATE权限设置,能够手工安装Oracle对象,并同意用户使用较少的权限来创建AWT缓存集合和使用AUTOREFRESH INCREMENTAL属性的缓存集合。
对象的安装必须授予与选择自己主动安装选项的用户同样的Oracle权限。
获得SQL码须要通过下方式之中的一个从TimesTen创建Oracle对象:
• 从ttIsql提示符,输入一条带有INSTALL标志的cachesqlget命令。
• 从一个程序中,调用ttCacheSqlGet内部程序并指定參数install_flag为‘1’。
注意:当获得SQL码来安装Oracle对象时,也应该产生一个来获得SQL码的脚本并保存它以在以后用来删除对象。
在已经获得SQL码以后,就能够通过在Oracle主机上启动SQL*Plus来手工创建Oracle对象,登录例如以下:
sqlplus cacheUid/cachePwd@machine_name
在SQL>提示符,输入SQL码来创建对象。
例 4.21 使用ttIsql来连接到数据存储。然后调用ttCacheStart程序来为数据存储启动缓存代理。缓存管理用户ID是testuser,口令为mypsswrd。下一步,使用CREATE CACHE GROUP来创建一个READONLY缓存集合,AUTOREFRESH STATE设置为OFF,并运行cachesqlget命令来获取必须的SQL来安装Oracle对象:
> ttIsql cgDSN
Command> call ttCacheUidPwdSet('testuser', 'mypsswrd');
Command> call ttCacheStart();
Command> CREATE READONLY CACHE GROUP readcache
AUTOREFRESH
MODE INCREMENTAL
INTERVAL 30 SECONDS
STATE OFF
FROM user1.readtab
(a NUMBER NOT NULL PRIMARY KEY, b VARCHAR2(31));
Command> cachesqlget readcache install;
从cachesqlget的输出类似例如以下:
CREATE TABLE system.tt_version_user_count(tableName VARCHAR2(65),
userCount
.... more code .....
END;
.
RUN;
能够从TimesTen剪贴和粘贴此SQL到Oracle上的SQL*Plus提示符:
SQL> CREATE TABLE system.tt_version_user_count(tableName
VARCHAR2(65), userCount
.... more code .....
END;
.
RUN;
二选其一,能够请求ttIsql将cachesqlget输出到一个在命令行中提供的输出文件名的一个文件将其保存。然后能够拷贝此文件到Oracle系统并运行此文件来安装Oracle对象。
注意:假设手工安装Oracle对象,必须要手工删除它们。
当手工为AWT缓存集合安装Oracle对象时,必须在为Oracle实例创建AWT缓存集合之前安装。对于每一个Oracle实例和缓存管理用户ID和口令,对象仅仅须要安装一次。
运行下列任务来为一个AWT缓存集合安装Oracle对象:
1. 在ttIsql会话中使用ttCacheUidGet程序来检查是否已经设置缓存管理用户ID和口令。在此例中,DSN为cgDSN。NULL结果表示还没有为cgDSN设置缓存管理用户ID和口令。
> ttIsql cgDSN
Command> call ttCacheUidGet();
<
1 row found.
2. 通过使用ttCacheUidPwdSet(uid,pwd)来设置缓存管理用户ID和口令。以下的样例在ttIsql会话中设置缓存管理用户ID为testuser,口令为mypsswrd,然后验证它已经被设置。
Command> call ttCacheUidPwdSet('testuser','mypsswrd');
Command> call ttCacheUidGet();
< testuser >
3. 通过使用ASYNCHRONOUS_WRITETHROUGH和INSTALL标志的ttIsql cachesqlget命令来获取SQL以安装对象。
Command> cachesqlget ASYNCHRONOUS_WRITETHROUGH INSTALL;
输出类似例如以下:
CREATE TABLE testuser.TT_03_RepPeers(
replication_name CHAR(31) NOT NULL,
replication_owner CHAR(31) NOT NULL,
tt_store_id NUMBER(19,0) NOT NULL,
subscriber_id NUMBER(19,0) NOT NULL,
commit_timestamp NUMBER(19,0),
commit_seqnum NUMBER(19,0),
timerecv NUMBER(10,0),
protocol NUMBER(10,0),
PRIMARY KEY(tt_store_id));
GRANT INSERT, UPDATE, DELETE, SELECT
ON testuser.TT_03_RepPeers TO PUBLIC;
CREATE TABLE testuser.TT_03_RepActiveStandby(
tt_store_pair INTEGER NOT NULL,
tt_store_id1 NUMBER(19,0) NOT NULL,
tt_store_id2 NUMBER(19,0) NOT NULL,
ts1 NUMBER(19,0),
ts2 NUMBER(19,0),
role1 CHAR(1),
role2 CHAR(1),
state NUMBER(10,0),
rep_checksum NUMBER(19,0),
PRIMARY KEY(tt_store_pair));
CREATE INDEX testuser.TT_03_RepActiveStandby_ix
ON testuser.TT_03_RepActiveStandby
( tt_store_id1, tt_store_id2 );
GRANT INSERT, UPDATE, DELETE, SELECT
ON testuser.TT_03_RepActiveStandby TO PUBLIC;
4. 剪切并粘贴SQL码到SQL*Plus会话以创建TT_version_REPPEERS。二选其一,能够从一个PassThrough属性被设置为3进行连接的TimesTen中的ODBC或JDBC程序中运行此代码。
假设AWT缓存集合是活动的备用对中的副本,还要创建TT_version_REPACTIVESTANDBY和TT_version_REPACTIVESTANDBY_IX。
为了确定安装在Oracle中的对象,登录Oracle帐号并从Oracle SQL *Plus命令提示符运行下列查询:
SQL> select owner, object_name, object_type from all_objects where
object_name like 'TT/___/_%' escape '/';
输出应该包括对象,类似例如以下:
OWNER OBJECT_NAME OBJECT_TYPE
------------- ------------------------------ ------------------
TESTUSER TT_03_34520_L TABLE
TESTUSER TT_03_34520_T TRIGGER
TESTUSER TT_03_USER_COUNT TABLE
TESTUSER TT_03_REPPEERS TABLE
假设Oracle对象由Cache Connect to Oracle自己主动安装,则当设置AUTOREFRESH为OFF或使用DROP CACHE GROUP来删除缓存集合时,将自己主动删除。
假设手工安装Oracle对象,能够通过在Oracle系统中运行代码来卸载它们来删除对象。为了从TimesTen获得卸载代码,使用下列方式之中的一个:
• 从ttIsql提示符,输入一条cachesqlget命令,指定uninstall。
• 从一个程序,调用ttCacheSqlGet程序并设置install_flag为0。
注意:假设在删除或改变自己主动刷新缓存集合之后马上关闭缓存代理,则它可能不会卸载Oracle对象。当重新启动缓存代理时,它将卸载删除或改变自己主动刷新缓存集合时留下的Oracle对象。
在从全部使用一个Oracle实例的数据存储中删除全部的AWT缓存集合之后,要为AWT缓存集合删除Oracle对象。
1. 从ttIsql会话,运行cachesqlget命令来获取SQL来删除对象。在此例中,DSN为cgDSN,而且用户是testuser。
> ttIsql cgDSN
Command> cachesqlget ASYNCHRONOUS_WRITETHROUGH UNINSTALL;
输出类似例如以下:
DROP TABLE testuser.TT_03_RepPeers;
DROP TABLE testuser.TT_03_RepActiveStandby;
2. 剪切并粘贴此SQL到SQL*Plus会话来删除对象。二选其一,能够从使用PassThrough属性被设置为3的TimesTen连接中的ODBC或JDBC程序中运行此代码。
这章将讨论如何使用缓存集合。
使用ALTER CACHE GROUP语句来改变AUTOREFRESH STATE、INTERVAL和MODE的设置。不论什么通过ALTER CACHE GROUP设置的值或状态都是永久的;它们保存在数据存储中,并在TimesTen守护程序和缓存代理又一次启动时生存。
注意:假设TimesTen安装时Access Control被激活,则必须拥有DDL权限来在数据存储中使用ALTER CACHE GROUP语句。
当一个AUTOREFRESH操作正在进行中而且将STATE改为OFF:
• 假设LockWait普通连接属性大于0,则AUTOREFRESH操作将停止。ALTER CACHE GROUP SET AUTOREFRESH STATE OFF语句优先于AUTOREFRESH操作。
• 假设LockWait普通连接属性为0,则AUTOREFRESH操作将继续。ALTER CACHE GROUP SET AUTOREFRESH STATE OFF语句将失败,产生一个锁定终止错误。
例 5.1 此例通过将状态改为ON来激活AutorefreshCustomers缓存集合的AUTOREFRESH:
ALTER CACHE GROUP AutorefreshCustomers
SET AUTOREFRESH STATE ON;
使用DROP CACHE GROUP SQL语句来从TimesTen中删除缓存集合和它全部相关的表。
注意:假设TimesTen安装时Access Control被激活,则必须拥有DDL权限来在数据存储中使用DROP CACHE GROUP语句。
假设删除使用了以INCREMENTAL模式的AUTOREFRESH并在Oracle进行手工安装对象的READONLY缓存集合或USERMANAGED缓存集合,则在删除缓存集合之前,必须手工删除Oracle对象。
当一个AUTOREFRESH操作正在进行时,假设输入一条DROP CACHE GROUP语句:
• 假设LockWait普通连接属性大于0,则AUTOREFRESH操作将停止。DROP CACHE GROUP语句优先于AUTOREFRESH操作。
• 假设LockWait普通连接属性为0,则AUTOREFRESH操作将继续。DROP CACHE GROUP语句将失败,产生一个锁定终止错误。
为了删除WesternCustomers缓存集合:
DROP CACHE GROUP WesternCustomers
全部WesternCustomers缓存中表将马上从TimesTen中被删除,而且缓存集合的定义也将从TimesTen系统表中被删除。
注意:全部AWT设置都将保持有效,直到DROP CACHE GROUP事务被提交。假设缓存集合是AWT,在删除缓存集合之前,确保全部绑定的更新都已经应用到Oracle。使用ttRepSubscriberWait程序。
TimesTen多个机制来从Oracle拷贝数据到TimesTen和从TimesTen拷贝数据到Oracle。
一个应用能够使用下列SQL语句来在Oracle和缓存集合之间拷贝数据:
SQL语句 |
描写叙述 |
LOAD CACHE GROUP |
从Oracle 数据中载入还没有在缓存中的缓存实例。 |
REFRESH CACHE GROUP |
使用当前的Oracle数据替换缓存实例。 |
FLUSH CACHE GROUP |
从缓存集合表中拷贝数据到Oracle表。缓存集合必须是PROPAGATE没有激活的USERMANAGED。 |
PROPAGATE被激活的SWT缓存集合、AWT缓存集合和USERMANAGED缓存集合提供了自己主动方式来将缓存集合中的更新应用到Oracle表。
AUTOREFRESH缓存集合属性可用于READONLY和USERMANAGED缓存集合中来自己主动将Oracle表中变化应用到缓存集合中。
当一条SELECT查询在缓存集合表中没有找到数据时,能够使用事务载入特性来将Oracle表中的数据载入到缓存集合表中。能够对除了使用AUTOREFRESH属性以外的全部缓存集合使用事务载入。
AUTOREFRESH是一个缓存集合定义的一部分。在已经定义缓存集合并按需调用之后,事务载入就能够实现。事务载入与AUTOREFRESH缓存集合相比較,前者在缓存集合上的限制较少。
AUTOREFRESH适用于与静态数据相关的如产品文件夹或飞行航班表。事务载入在动态缓存内容方面更实用。应用能够使用事务载入特性来载入数据到缓存中,并使TimesTen代理自己主动删除长时间没有使用的数据。
能够使用一条LOAD CACHE GROUP或REFRESH CACHE GROUP语句来将数据从Oracle载入到缓存集合中。两种从Oracle拷贝数据到缓存集合的SQL语句都能够含或不含WHERE子句或WITH ID子句。载入和刷新的有例如以下不同:
• LOAD CACHE GROUP 不更新已经出如今缓存集合中的实例。
• REFRESH CACHE GROUP 使用近期的Oracle数据替换缓存集合中全部或指定的实例,即使实例已经出如今缓集合中。自己主动刷新操作相当于一条UNLOAD CACHE GROUP 语句后跟一条LOAD CACHE GROUP 语句。全部到Oracle数据的变化,包括根表和子表中的插入、更新和删除,将在刷新操作后反映到缓存中。
例 5.2 为了从Oracle载入数据到WesternCustomers缓存集合:
LOAD CACHE GROUP WesternCustomers
COMMIT EVERY 256 ROWS;
例 5.3 为了仅仅从Oracle中载入Zip Code 94022中的用户的缓存集合实例到WesternCustomers 缓存集合:
LOAD CACHE GROUP WesternCustomers
WHERE (user1.customer.zip = 94022)
COMMIT EVERY 256 ROWS;
例 5.4 为了从Oracle表中刷新整个WesternCustomers 缓存集合:
REFRESH CACHE GROUP WesternCustomers
COMMIT EVERY 256 ROWS;
例 5.5 为了仅仅刷新与合同号2353相关的缓存集合实例:
REFRESH CACHE GROUP WesternCustomers
WHERE (user1.orderdetails.itemid = 2353)
COMMIT EVERY 256 ROWS;
载入和刷新AUTOREFRESH和READONLY缓存集合有例如以下限制:
• 载入一个AUTOREFRESH呀READONLY缓存集合时,缓存集合必须为空。
• AUTOREFRESH状态必须是PAUSED。
• LOAD或REFRESH语句不能包括WHERE子句或WITH ID子句。
运行下列任务来载入一个AUTOREFRESH缓民集合:
1. 设置AUTOREFRESH状态为PAUSED。
ALTER CACHE GROUP testcache SET AUTOREFRESH STATE PAUSED;
COMMIT;
2. 卸载缓存集合。
UNLOAD CACHE GROUP testcache;
COMMIT;
3. 载入缓存集合。
LOAD CACHE GROUP testcache COMMIT EVERY 256 ROWS;
COMMIT;
4. 设置AUTOREFRESH状态为ON。
ALTER CACHE GROUP testcache SET AUTOREFRESH STATE ON;
COMMIT;
WITH ID子句能够依据主键的值而不须要WHERE子句来载入或刷新一个缓存集合。能够以字段名或绑定參数来描写叙述主键值。使用WITH ID子句将比使用等价的WHERE子句速度要快。假设失败,也能够回滚载入的事务。
WITH ID子句不能用于AUTOREFRESH或READONLY缓存集合。
WITH ID子句同意每次载入一个缓存实例。假设有一个orders表,其主键为order_id。假设用户调用一指定的合同,则能够通过为指定的order_id载入缓存实例载入相关信息。
例 5.6 在Oracle中,创建一名为sample的表:
CREATE TABLE sample (a NUMBER, b NUMBER, c NUMBER,
PRIMARY KEY (a,b));
缓装此表以使它包括以下行:
A B C
---------- ---------- ----------
1 2 3
4 5 6
7 8 9
在TimesTen上创建缓存集合:
CREATE SYNCHRONOUS WRITETHROUGH CACHE GROUP testcache
FROM sample
(a NUMBER, b NUMBER, c NUMBER, PRIMARY KEY (a,b));
使用主键有值(1,2)的行载入缓存集合:
LOAD CACHE GROUP testcache WITH ID (1,2);
1 cache instance affected.
SELECT * FROM sample;
< 1, 2, 3>
1 row found.
例 5.7 使用主键有值(4,5)的行刷新testcache缓存集合:
REFRESH CACHE GROUP testcache WITH ID (4,5);
1 cache instance affected.
SELECT * FROM sample;
< 1, 2, 3 >
< 4, 5, 6 >
2 rows found.
假设缓存集合包括多个表,而且Oracle当前正在更新被载入或刷新的表,在提交LOAD CACHE GROUP或REFRESH CACHE GROUP语句之前,能够设置TimesTen isolation级别为SERIALIZABLE。这将使TimesTen以连接的方式来查询Oracle表,并保证载入的数据与事务一致。在已经载入或刷新缓存集合之后,能够为更好的并发又一次设置isolation级别为READ_COMMITTED。
例 5.8 在一个ttIsql会话中,在载入缓存集合之前能够又一次设置isolation级别。当要载入或刷新缓存集合时,这个将应用到非日志模式。
Command> isolation SERIALIZABLE;
Command> LOAD CACHE GROUP WesternCustomers
>COMMIT EVERY 1000 ROWS;
Command> isolation READ_COMMITTED;
能够通过使用LOAD CACHE GROUP或REFRESH CACHEGROUP语句的PARALLEL子句来改善载入或刷新大表的运行速度。指定要使用的线程号。一个线程从Oracle中取出行,而且另外一个线程插入数据到缓存集合中。不要指定大于CPU能够载入的线程数量。
例 5.9
REFRESH CACHE GROUP WesterCustomers
COMMIT EVERY 256 ROWS
PARALLEL 2;
当一条SELECT查询在缓存集合中没有查找到数据时,能够配置TimesTen来自己主动从Oracle表中载入数据到缓存集合表中。当运行SELECT语句时,被选择的和相关的行被载入到缓存集合的根表中,而且关联和被选择的行也被载入到子表中。仅仅有那些满足缓存集合定义的行被载入。假设缓存集合有基于时间的老化性质定义,这些行也必须满足此老化性质。
能够为全部的类型的缓存集合配置透明载入,除了使用AUTOREFRESH属性的READONLY缓存集合和USERMANAGED缓存集合。
当缓存内容是动态的情况下,透明载入特别实用。比如,能够使用它来载入已经被老化删除的数据。
透明载入可用于下列类型的SELECT语句:
• SELECT在单表的主键上使用了一个等价的条件。此等价条件必须包括一个常量或參数。比如:
SELECT * FROM table1 WHERE primkey=1;
假设主键是复合键,则SELECT语句必须包括全部主键列的等价条件。比如:
SELECT * FROM table2 WHERE pkcol1=10 AND pkcol2=10;
• SELECT在单表的外键上使用了一个等价的条件。此等价条件必须包括一个常量或參数。比如:
SELECT * FROM table2 WHERE foreignkey=1;
假设外键是复合键,则SELECT语句必须包括全部外键列的等价条件。比如:
SELECT * FROM table2 WHERE fkcol1=10 AND fkcol2=10;
• 使用一个等价的条件选择缓存集合实例中的一个子树。比如:
SELECT * FROM table1,table2 where table1.primkey=1 and
table2.foreignkey=table1.primkey;
SELECT查询必须满足下列条件:
• SELECT查询必须是语句中最外层的查询。
• SELECT查询不能包括UNION、INTERSECT或MINUS结果集操作。
• 仅仅有一个缓存集合中的表能够指定在最外层的SELECT查询中,但其他没有在缓存集合中的表能够指定在语句中。
当SELECT查询返回选择的行时,整个缓存实例都要被载入,以保持主键和外键之间的关联。.
为了透明载入数据,设置TransparentLoad Cache Connect属性为1。这将使一条SELECT语句在Oracle表上被运行。数据结果将被载入到缓存集合表中。然后此数据通过在缓存集合表中运行原来的SELECT语句被透明返回。
下表总结关于TransparentLoad的设置:
设置 |
描写叙述 |
0 |
不使用透明载入。(缺省) |
1 |
在TimesTen中不发送错误信息或警告信息的运行SELECT语句。 |
2 |
假设SELECT操作不能使用透明载入,将返回一个错误。将依据TimesTen中可用的数据来运行SELECT操作。 |
二选其一,为了能够使用透明载入,能够使用SQLSetConnectOption ODBC函数来设置TT_TRANSPARENT_LOAD ODBC连接选项。此设置将应用到整个连接。
能够通过使用ttOptSetFlag内部程序的TransparentLoad标志来覆盖指定事务的TransparentLoad属性或TT_TRANSPARENT_LOAD ODBC选项。当语句准备时,TransparentLoad标志值就将产生影响,而且在运行时不能进行改变。在事务被提交或回滚时之后,此连接属性将又一次产生影响。
FLUSH CACHE GROUP语句将USERMANAGED缓存集合中的插入和更新冲洗到Oracle。不冲洗删除。指定为READONLY或PROPAGATE的表中的记录也不会冲洗到Oracle。
当从TimesTen到Oracle的数据提交被关闭时,使用FLUSH CACHE GROUP。相比每次事务提交更新数据,在更新被传送到Oracle之前,很多事务能够在TimesTen中被提交会更好。对于每一个实例,假设缓存实例在Oracle中存在,则Oracle中操作将由一个更新构成。假设缓存实例在Oracle不存在,则TimesTen将插入它。
FLUSH CACHE GROUP语句能够使用WHERE或WITH ID子句指定以控制冲洗到Oracle的数据。
例 5.10 为了将WesternCustomers缓存集合中的变化冲洗到Oracle:
FLUSH CACHE GROUP WesternCustomers;
能够使用UNLOAD CACHE GROUP SQL语句来删除缓存集合中一些或全部的实例。与DROP CACHE GROUP语句不同,它们中的表不会被删除。
对于使用AUTOREFRESH属性的缓存集合要小心使用UNLOAD CACHE GROUP语句。假设行或它的子行在Oracle中被更新,作为自己主动刷新的结果,被卸载的行有可能再次出如今缓存集合中。
例 5.11 为了从WesternCustomers缓存中删除全部实例:
UNLOAD CACHE GROUP WesternCustomers;
为了从WesternCustomers缓存中删除CustId = 1的用户:
UNLOAD CACHE GROUP WesternCustomers WITH ID(1);
或
UNLOAD CACHE GROUP WesternCustomers
WHERE (User1.Customer.CustId = 1);
能够从一个数据存储中复制缓存集合表到还有一个数据存储中的缓存集合表中或还有一个数据存储的标准TimesTen表中。主数据存储中的缓存集合类型必须与子数据存储中的缓存集合类型同样。比如,READONLY缓存集合中的表可仅仅能被拷贝到还有一个数据存储中的READONLY缓存集合的表中或还有一个数据存储的标准TimesTen表中。
缓存集合中的全部表都必须包括在复制计划中。
能够为下列类型的缓存集合通过配置一个名为active standby pair的复制计划来实现高效的缓存实例:
• READONLY缓存集合
• ASYNCHRONOUS WRITETHROUGH缓存集合
一个复制这些类型之中的一个的缓存集合活动备用对能够自己主动地改变缓存集合的角色作为失败和使用最小数据丢失进行恢复的一部分。缓存集合给自己提供来自于Oracle数据库的弹性,进一步巩固系统的可靠性。
也能够配置缓存集合表的复制来实现工作量的平衡。以下的配置是一个演示样例:
• 载入平衡 — 配置从使用AUTOREFRESH属性的缓存集合中的表到标准表中的单向复制。Oracle上的更新将自己主动刷新到TimesTen缓存集合。此更新然后被拷贝到TimesTen表。
• 分隔工作量 — 在不同的数据存储的WRITETHROUGH缓存集合中的表之间配置双向复制。设计应用以使事务为了一个特定用途(比如,一个地理区域)仅仅更新特定的缓存数据表,而且同样的缓存集合表不能在两个存储中都直接被更新。在一个存储中被更新的缓存集合表被拷贝到还有一个数据存储中对应的缓存集合表中。更新将直接通过应用传送到Oracle,但不进行复制更新。
不要使用活动active/活动配置,特别是复制缓存集合时。这样的配置的非预期结果包括不可解的死锁、缓存集合内容的冲突和恢复问题。
Cache Connect to Oracle没有机制来发现Oracle数据库由际操作如CREATE、DROP或ALTER引起的规划改变。假设须要改变Oracle规划,则要运行下列任务:
1. 使用DROP CACHE GROUP来删除全部缓存Oracle被改变表的缓存集合。
2. 停止缓存代理。
3. 对Oracle进行期望的改变。
4. 使用CREATE CACHE GROUP来又一次创建缓存集合。
假设在Oracle数据库中规划被改动之前不删除缓存集合,则在原来缓存集合中的操作,包括AUTOREFRESH,可能成功,也可能失败而产生错误。
增量AUTOREFRESH不能发现一人Oracle表的截短。假设要截短一个Oracle基表,则要运行下列任务:
1. 使用ALTER CACHE GROUP语句来设置AUTOREFRESH STATE为PAUSED。
2. 截短Oracle基表。
3. 通过使用不带有WHERE或WITH ID子句的REFRESH CACHE GROUP语句刷新缓存集合。
在刷新缓存集合之后,自己主动刷新操作将又一次開始。
注意:在缓存集合中不同意截短TimesTen表。
注意:假设缓存集合是AWT,在删除缓存集合之前,确保全部绑定的更新已经应用到Oracle。使用ttRepSubscriberWait程序。
TimesTen提供了一个基于浏览器名为Cache Administrator的工具创建缓存集合定义和工作。Cache Administrator能够使用管理员使用位于与安装TimesTen同样的机器上的Web浏览器通过操纵Oracle规划来定义一个或多个缓存集合。能够设置Webserver以使能够訪问Cache Connect to Oracle。
下列Web浏览器支持Cache Administrator:
• Internet Explorer 6.0
• Firefox 1.5和以后的版本号
缓存集合定义保存在守护程序文件夹中的ws/cgi-bin/cache/cachedata文件里。能够通过输入ttVersion –m命令来获得守护程序文件夹。
缓存集合定义既包括查询和索引又包括连接信息的定义。假设Access Control被激活,连接信息也包括Oracle用户和TimesTen用户。
Oracle用户帐号必须拥有下列权限:
• CREATE SESSION
• 需为为每一个缓存集合创建须要訪问的表的SELECT
当Access Control为TimesTen实例激活时,用户必须是一个内部TimesTen用户。TimesTen用户必须有下列权限:
• DDL
• SELECT
当Access Control被激活时,TimesTen用户必须拥有ADMIN权限,以使它能够从命令行启动和停止缓存代理。
在启动Cache Administrator之前,确保:
• Oracleclient已经安装到要启动Cache Administrator的机器上。
• 要正确设置ORACLE_HOME环境变量。在启动TimesTen守护程序之前,必须进行设置。
• UNIX上的LD_LIBRARY_PATH或Window上的PATH要设置正确。
• Cache Connect to Oracle已经安装成功。
• TimesTen守护程序正在运行。
• Webserver正在运行。能够通过使用ttStatus来验证。实例管理员能够通过使用带有-startwebserver选项的ttDaemonAdmin工具来启动它。
通过在浏览器中输入下列URL来启动Cache Administrator:
http://localhost:port/cache
本地主机仅仅支持能够启动Web服务的位置。这就意谓着Cache Administrator必须运行在安装TimesTen的机器上。试图从其他机器上查看Cache Administrator将会失败。
port是守护程序Webserver的端口号。端口号在安装时指定。假设不知道此端口号,查看守护程序文件夹中守护程序的Web服务日志webserver.log。
在Window平台上,能够从Start >Programs > TimesTen菜单来启动Cache Administrator。
在为数据存储启动缓存代理之后,选择Login来连接到数据存储。图 6.1 显示假设在数据存储上没有激活Access Control时的Connect to a Data Store 屏幕。
图 6.1 不使用Access Control连接到数据存储
下字段必须完毕:
• TimesTen DSN — 指定用于缓存的TimesTen数据存储。能够输入一简单串(DSN的名称)或完整连接串。
简单串是一个在Window系统中ODBC面板或UNIX平台上SYS.ODBC.INI文件里已经创建的DSN的名称。
以下是一个完整连接串的演示样例:DSN=CacheData;DurableCommits=0;DatabaseCharacterSet=US7ASCII;
• Oracle username — Oracle数据库上的一个用户帐号。它获取关于保存在Oracle上的表和索引信息。
• Oracle password — 指定Oracle用户的口令。
• TimesTen password — 假设数据存储上的Access Control被激活,也必须输入TimesTen Password,如图 6.2所看到的。Password输入是大写和小写敏感的。
图 6.2 使用激活的Access Control连接到数据存储
在完毕输入后,单击Log in。
当成功连接到数据存储时,Cache Administrator选项将显示如图 6.3所看到的。
图 6.3 欢迎页和完整菜单
能够使用Cache Administrator来运行下列任务:
• 管理缓存集合定义(创建、拷贝、改动和删除)。
• 查看描写叙述缓存集合的SQL语句。
• 为创建缓存集合生成必须的SQL语句,并发送信息到到创建它的数据存储。
• 创建缓存集合。
• 管理缓存代理(启动、停止、状态)。
Cache Administrator的在线帮助将说明如何运行这些任务。
这章将讨论如何在RAC环境中实现Cache Connect to Oracle。
Oracle Real Application Clusters (RAC)能够使多个Oracle实例使用共享资源訪问一个数据库,共享资源包括驻留在簇共享磁盘上全部的数据文件、控制文件、PFILE和重做日志文件。在提供高性能的同一时候,RAC处理连续的读/写和载入平衡。
Fast Application Notification (FAN)是一个与Oracle Call Interface (OCI) in Oracle Database 10g Release 2结合使用的RAC特性。FAN公布关于簇上变化的信息给订阅FAN事件的应用。FAN将排除例如以下的减少效率的行为:
• 当服务被关闭时的试图连接
• 当服务被关闭时的试图完毕事务的进程
• 等待TCP/IP终止
不使用FAN,Cache Connec可能要花费数分钟来接收一个Oracle失败的通知。
Transparent application failover (TAF)是一个Oracle Net Services的特性,以使能够指定失败以后须要应用如何进行又一次连接。Cache Connect将OCI结合FAN使用来接收Oracle事件的通知。OCI应用能够使用下列类型之中的一个的Oracle Net失败功能:
• 会话:假设一用户的连接丢失,一个新的会话将自己主动为用户创建。此失败的类型不会试图恢复选择。
• 选择:此失败的类型能够使用户在失败以后使用打开游标来继续在里面取值。
• 无:这是缺省值。不使用失败功能。也能够显式指定来防止失败的产生。
Cache Connect能够非常快地从Oracle失败中恢复过来,而不须要用户的干预。Cache Connect能够与Oracle Database 10g Release 2 server一起用于RAC环境。Oracleclient能够是Oracle9i Release 2或Oracle Database 10g Release 2。
Cache Connect的行为将依赖于TAF的动作和TAF是如何配置的。RACCallback Cache Connect属性缺省地注冊TAF和FAN回叫。假设不须要TAF和FAN可用,则在连接串中设置RACCallback为0。
表 7.1 显示在使用不同的TAF失败类型的RAC环境中Cache Connect特性和操作的行为。这些行为与Oracle9i Release 2和Oracle Database 10g Release 2client一样,除了当Oracle Database 10g Release 2中FAN被激活时,Cache Connect将马上接收到节点失败的通知。
表 7.1 在RAC环境中Cache Connect特性和操作的行为
特性或操作 |
TAF失败类型 |
在连接到Oracle数据库失败后Cache Connect的行为 |
Autorefresh |
无 |
缓存代理将自己主动关闭、重新启动和等待,直到能够建立到Oracle服务的连接。此行为与Cache Connect to Oracle release 6.0.1和非RAC环境中的Cache Connect中的一样。 |
Autorefresh |
Session |
将发生下列情形之中的一个: • 全部失败的连接将恢复。正在进行中的Autorefresh操作将被回滚并重试。 • 假设TAF时间已到或不能恢复连接,则缓存代理将自己主动关闭、重新启动和等待,直到能够建立到Oracle服务的连接。此行为与Cache Connect to Oracle release 6.0.1和非RAC环境中的Cache Connect中的一样。 |
Autorefresh |
Select |
将发生下列情形之中的一个: • Autorefresh将从连接失败点继续又一次開始。 • 正在进行中的Autorefresh操作将被回滚并重试。 •假设TAF时间已到或不能恢复连接,则缓存代理将自己主动关闭、重新启动和等待,直到能够建立到Oracle服务的连接。此行为与Cache Connect to Oracle release 6.0.1中的一样。 |
Passthrough、 SWT、propagate和flush |
无 |
通知应用连接丢失并必须回滚TimesTen连接。在下一次passthrough操作期间,Cache Connect试图又一次连接到Oracle数据库。全部被改动的会话属性会丢失。此行为与Cache Connect to Oracle release 6.0.1和非RAC环境中Cache Connect中的一样。 |
Passthrough、 SWT、propagate和flush |
Session |
将发生下列情形之中的一个: • 将恢复到Oracle数据库的连接。假设在丢失的连接上有打开的游标、DML或锁定操作,则会产生一个错误,而且用户必须回滚事务。否则用户能够继续而不使用回滚。 • 假设TAF时间到或不能恢复连接,通知应用连接丢失并必须回滚TimesTen连接。在下一次passthrough操作期间,Cache Connect试图又一次连接到Oracle数据库。全部被改动的会话属性会丢失。此行为与Cache Connect to Oracle release 6.0.1和非RAC环境中Cache Connect中的一样。 |
Passthrough |
Select |
将恢复到Oracle数据库的连接。假设在丢失的连接上有打开的游标、DML或锁定操作,则会产生一个错误,而且用户必须回滚事务。否则用户能够继续而不使用回滚。 |
SWT、 Propagate、 和flush |
Select |
将发生下列情形之中的一个: • 将恢复到Oracle数据库的连接。假设在丢失的连接上有DML或锁定操作,则会产生一个错误,而且用户必须回滚事务。否则用户能够继续而不使用回滚。 • 假设TAF时间到或不能恢复连接,通知应用连接丢失并必须回滚TimesTen连接。在下一次passthrough操作期间,Cache Connect试图又一次连接到Oracle数据库。全部被改动的会话属性会丢失。此行为与Cache Connect to Oracle release 6.0.1和非RAC环境中Cache Connect中的一样。 |
Load和 refresh |
无 |
应用将收到一个连接丢失的错误。 |
Load和 refresh |
Session |
将发生下列情形之中的一个: • 载入成功。 • 返回一个错误,报告Oracle取值不能运行。 |
Load和 refresh |
Select |
将发生下列情形之中的一个: • 假设Oracle游标被打开,而且游标被恢复或Oracle游标没有被打开,则载入成功。 • 假设TAF不能恢复会话或打开Oracle游标,则返回一个错误。 注意:返回错误的可能性小于TAF失败类型是Session。 |
AWT |
无 |
AWT的复制接收线程存在。产生一个新线程并试图连接到Oracle数据库。 |
AWT |
Session、 select |
将发生下列情形之中的一个: • 假设连接被恢复而且在连接上有未提交的DML操作,则批量操作或事务将被回滚并又一次运行。 • 假设连接被恢复而且在连接上无未提交的DML操作,则工作继续。 |
能够为下列Oracleclient和server的版本号在RAC环境中使用Cache Connect to Oracle:
• Oracle Database 10g Release 2。假设client和server的版本号都是Oracle Database 10g Release 2,则仅仅能使用FAN。
• Oracle Database 10g Release 1
• Oracle9i Release 9.2
对于每一个版本号,要使用Oracleclient近期的版本号。
Cache Connect支持的RAC有下列限制:
• Cache Connect的行为被限制为使用RAC、FAN和TAF的能力。比如,假设服务全部的节点失败,服务将不会重新启动。Cache Connect将等待用户来又一次启动服务。
• TAF不会恢复ALTER SESSION操作。由用户负责在失败之后恢复改变了的会话属性。
• Cache Connect结合FAN事件使用Oracle Client Interface (OCI)。此接口自己主动产生一个线程来等待一个Oracle事件。在一个直接连接的TimesTen应用中产生一个线程仅仅是TimesTen的特性。建改动ODBC应用以解决此线程的创建。假设不须要额外的线程,设置RACCallback Cache Connect属性为0。则将不会使用TAF和FAN。
安装Cache Connect和RAC。确保缓存管理用户在s Oracle GV$SESSION动态运行视图上有SELECT权限。
有两个TimesTen环境变量控制TAF超时设置:
• TT_ORA_FAILOVER_TIMEOUT:TAF以分钟数为用户应用(SWT缓存集合、使用propagate选项的缓存集合和使用passthrough特性的缓存集合)进行超时设置。缺省值是5分钟。
• TT_AGENT_ORA_FAILOVER_TIMEOUT:TAF以分钟数为复制代理(对于AWT缓存集合)进行超时设置。缺省值为5小是。
下列Oracle组件也必须启动:
• Oracle实例
• Oracle监听器
• 将用于Cache Connect的Oracle服务
然后运行下列任务:
1. 核实RACCallback连接属性被设置为1(缺省值)。
2. 使用DBMS_SERVICE.MODIFY_SERVICE Oracle PL/SQL包或Oracle Enterprise Manager以使能够进行FAN事件的公布。这将改变Oracle ALL_SERVICES视图的AQ_HA_NOTIFICATIONS列为YES。(这将应用到Oracle Database 10g Release 2client。)
3. 通过下列方式之中的一个使得在服务上能够使用TAF:
• 在Oracle tnsnames.ora文件里使用下列字符为Cache Connect创建一个服务:
– LOAD_BALANCE=ON (选项)
– FAILOVER_MODE=(TYPE=SELECT)或FAILOVER_MODE=(TYPE=SESSION)
• 使用DBMS_SERVICE.MODIFY_SERVICE来设置TAF失败类型。
4. 假设应用是一个ODBC直接连接应用,使用一个线程库进行连接,以使它能够接收FAN通知。FAN将产生一个线程来监视失败。(这将应用到Oracle Database 10g Release 2client。)
这章将列出TimesTen和Oracle之间的兼容性问题。此列表不完整,但它包括须要特别注意的地方。
注意:TimesTen不支持Oracle Call Interface (OCI)。
考虑以下TimesTen和Oracle之间的不同:
• TimesTen和Oracle数据库的元数据保存不同。
• TimesTen和Oracle有不同的事务隔绝模式。
• TimesTen和Oracle有不同的连接和语句属性。比如,timesTen不支持文件夹名、滚动游标或更新游标。
• 对于ROWID,TimesTen和Oracle不同的类型和长度。TimesTen 不支持Oracle ROWID数据类型。
• Sequence不会被缓存,而且在缓存和Oracle数据库之间不同步。
• 触发器和过程的作用不会传送到缓存中,直到一个AUTOREFRESH操作或手工REFRESH CACHE GROUP操作之后。
• 在缓存集合中不支持XA和JTA API。
Cache Connect to Oracle不防碍全部支持的Oracleclient/server相互联合协调工作的配置。比如,在TimesTen服务的机器上Cache Connect使用9.2.0.8 Oracleclient安装并连接到不同server上的10.2.0.3 Oracle数据库是被支持的。用户应该检查Metalink Documentation Note 207303.1、“Client/Server/Interoperability Support Between Different Oracle Versions”中关于当前Oracleclient/server支持的配置信息。用户也应该检查关于交互问题的Oracle和TimesTen版本号注意事项。
TimesTen和Oracle的事务意义的不同例如以下:
• Oracle连接的事务在提交时可能失败,由于事务不能被连续化。而TimesTen将使用锁来强制进行连续的事务。
• Oracle用户能够通过显式的SQL来锁定表。此锁定特征在TimesTen中不支持。
• Oracle支持保存点。而TimesTen不支持。
• 在Oracle中,事务能够被设置为仅仅读或读/写。这在TimesTen中也是不支持的。
应用到JDBC的兼容性问题包括例如以下:
• JDBC数据库元数据函数返回TimesTen元数据。假设须要Oracle元数据,能够使用带有PassThrough属性的Cache Connect或直接连接到Oracle数据库。
• 设置/得到连接和语句属性将在TimesTen上。
• 全部Oracle java.sql.ResultSet元数据(长度、类型、标签)将以TimesTen数据类型长度返回。返回的列标签也是TimesTen列标签。
• 对于java.sql.CallableStatement方法的输出參数(OUT和INOUT),在TimesTen中不被支持。
• 不支持Oracle扩展(oracle.sql和oracle.jdbc包)。
• 在TimesTen中不支持Java存储过程。
注意:TimesTen不支持语句的异步运行,也不支持从一个不同的线程取消一条运行语句。
以下的Connection方法没有兼容性问题:
close
commit
createStatement
setAutoCommit
prepareCall
prepareStatement
rollback
以下的方法在本地TimesTen中被运行:
getCatalog
getMetaData
get/setTransactionIsolation
isReadOnly
isClosed – 仅仅返回TimesTen连接状态
nativeSQL
setCatalog
setReadOnly
以下的Statement方法有兼容性问题:
close
execute
executeUpdate
executeQuery
getResultSet
getUpdateCount
getWarnings
executeBatch
clearBatch
addBatch
以下的方法在本地的TimesTen中运行:
get/setMaxFieldSize
get/setMaxRows
get/setQueryTimeout
getMoreResults
setEscapeProcessing
setCursorName
cancel
以下的ResultSet方法没有兼容性问题:
close
findColumn(int) 和 findColumn(string)
getXXX(number) 和 getXXX(name)
getXXXStream(int) 和 getXXXStream(string)
getMetaData
以下的PreparedStatement方法没有兼容性问题:
execute
executeUpdate
executeQuery
setXXX
setXXXStream
close
getResultSet
getUpdateCount
addBatch
以下的方法在本地TimesTen中运行:
get/setMaxFieldSize
get/setMaxRows
get/setQueryTimeout
getMoreResults
setEscapeProccessing
setCursorName
cancel
与显示在java.sql.Statement和应用到CallableStatement的java.sql.PreparedStatement接口有同样的限制。另外,使用不论什么输出形态的CallableStatement都不被支持。全部參数都被作为输入參数。没有输出參数的Callablestatement可能在准备时返回一个错误,通过registerOutparameter返回错误或应用可能得到非预期的结果。
• 在一个WRITETHROUGH缓存集合中,假设PassThrough=1,则隐藏在存储过程中或通过触发器产生的间接DML操作可能被传送,但没有被Cache Connect to Oracle发现。
• 从READONLY缓存集合进行更新的、插入或删除的存储过程将在还有一个异步方式的事务中被自己主动刷新。因此在存储过程被运行的同样事务中将不会出现变化,而且在自己主动刷新到缓存表之前,会有一段时间间隔。
以下ResultSetMetadata方法没有兼容性问题:
getColumnCount
getColumnType
getColumnLabel
getColumnName
getTableName
isNullable
以下的方法在本地的TimesTen中运行:
getSchemaName
getCatalogName
getColumnDisplaySize
getColumnType
getColumnTypeName
getPrecision
getScale
isAutoIncrement
isCaseSensitive
isCurrency
isDefinitelyWritable
isReadOnly
isSearchable
isSigned
isWritable
兼容性问题相关的流是:
• JDBC驱动器在调用executeQuery或next方法时将数据全然取出并放入到内存缓冲区。getXXXStream条目指针返回从此缓冲区读数据的流。
• Oracle支持最大到2GB的long或long raw数据。
• Oracle总是long/long raw数据流,即使应用没有调用getXXXStream。
• TimesTen没有close方法。当它移动到下一行时,将使stream流无效。当移动到下一列时,Oracle将关闭流。
• TimesTen不支持mark、markSupported和reset方法。
下表列出ODBC 2.5 API调用和指出函数是否有兼容性问题。
函数 |
兼容性 |
SQLAllocConnect |
- |
SQLAllocEnv |
- |
SQLAllocStmt |
- |
SQLBindCol |
- |
SQLBindParameter |
当一条SQL语句有同样的參数名时,TimesTen觉得它们是同样參数的多次出现,不同意它们分别绑定。Oracle觉得它们是不同的參数,并同意它们分别绑定。 |
SQLBrowseConnect |
不支持 |
SQLCancel |
TimesTen不支持语句的异步运行,而且不支持从一不同的线程来取消一条运行语句。 |
SQLColAttributes |
- |
SQLColumnPrivileges |
不支持 |
SQLColumns |
元数据函数从TimesTen表返回元数据。 |
SQLConnect |
- |
SQLDataSource |
- |
SQLDescribeCol |
- |
SQLDescribeParam |
- |
SQLDisconnect |
- |
SQLDriverConnect |
- |
SQLDrivers |
- |
SQLError |
是TimesTen错误的本地错误码。用户能够接收到一般错误如“execution at Oracle failed, Oracle error code nnn.”。 |
SQLExecDirect |
- |
SQLExecute |
- |
SQLExtendedFetch |
不支持 |
SQLFetch |
- |
SQLForeignKeys |
元数据函数从TimesTen表返回元数据。 |
SQLFreeConnect |
- |
SQLFreeEnv |
- |
SQLFreeStmt |
- |
SQLGetConnectOption |
- |
SQLGetCursorName |
TimesTen支持get/set游标名,但不支持游标delete/update语句。 |
SQLGetData |
- |
SQLGetFunctions |
- |
SQLGetInfo |
- |
SQLGetStmtOption |
- |
SQLGetTypeInfo |
元数据函数从TimesTen表返回元数据。 |
SQLMoreResults |
不支持 |
SQLNativeSql |
- |
SQLNumParams |
- |
SQLNumResultCols |
- |
SQLParamData |
- |
SQLParamOptions |
- |
SQLPrepare |
- |
SQLPrimaryKeys |
元数据函数从TimesTen表返回元数据。 |
SQLProcedureColumns |
元数据函数从TimesTen表返回元数据。 |
SQLProcedures |
元数据函数从TimesTen表返回元数据。 |
SQLPutData |
- |
SQLRowCount |
- |
SQLSetConnectOption |
设置函数设置TimesTen选项或元数据。 |
SQLSetCursorName |
设置函数设置TimesTen选项或元数据。 |
SQLSetPos |
不支持 |
SQLSetScrollOptions |
不支持 |
SQLSetStmtOption |
设置函数设置TimesTen选项或元数据。 |
SQLSpecialColumns |
元数据函数从TimesTen表返回元数据。 |
SQLStatistics |
元数据函数从TimesTen表返回元数据。 |
SQLTablePrivileges |
不支持 |
SQLTables |
元数据函数从TimesTen表返回元数据。 |
SQLTransact |
- |
这部分比較TimesTen的SQL与Oracle的SQL的运行。目的是提供用户一个在TimesTen中不支持或使用不同意义支持的Oracle SQL特性的列表。这部分比較Oracle Database 10g Release 2和Oracle TimesTen In-Memory Database 7.0.0.0.0。
TimesTen不承认一些Oracle中支持的计划对象。当语句操作或使用这些对象并传送到Oracle时,TimesTen将返回一个语法错误。不支持的对象是:
• 与存储过程相关的对象
– 存储过程
– 存储函数
– 包
– 触发器
• 訪问控制对象
– 角色
– 外形
– 上下文
• 存储管理特性
– 簇
– 表空间
–回滚段
– CREATE/DROP DATABASE语句
– 数据库链节
– 文件夹
– 分区
• 扩展特性
– 扩展程序库
– Object表
– Object类型
– Object视图
TimesTen支持视图和物化视图,但不支持缓存Oracle视图。当TimesTen中没有同样的本地对象名时,包括视图和物化视图的语句将传送到Oracle。
一些TimesTen不支持的Oracle特性是:
• ON DELETE SET NULL
• 约束检查
下列Oracle数据类型不被TimesTen支持:
TIMESTAMP WITH TIME ZONE
TIMESTAMP WITH LOCAL TIME ZONE
INTERVAL YEAR TO MONTH
INTERVAL DAY TO SECOND
ROWID
UROWID
CLOB
NCLOB
BLOB
BFILE
REF
“Any”类型
XML类型
Spatial类型
Media类型
下列TimesTen数据类型不被Oracle支持:
TT_TINYINT
TT_SMALLINT
TT_INTEGER
TT_BIGINT
TT_VARBINARY
注意:TimesTen NCHAR/NVARCHAR2数据类型将被编译为UTF-16。Oracle NCHAR/NVARCHR2将被编译为UTF-16或UTF-8。
TimesTen支持这些Oracle操作符和动词:
一元数的 -
+, -, *, /
=, <, >, <=, >=, <>=
| |
IS NULL, IS NOT NULL
LIKE(Oracle LIKE操作符将忽略后面的空格,但TimesTen不会。)
BETWEEN
IN
NOT IN (list)
AND
OR
+(外连接)
ANY、SOME
ALL (list)
EXISTS
UNION
MINUS
INTERSECT
TimesTen支持这些Oracle函数:
ABS
ADD_MONTHS
AVG
CEIL
COALESCE
CONCAT
COUNT
DECODE
EXTRACT
FLOOR
GREATEST
INSTR
LEAST
LENGTH
LPAD
LTRIM
MAX
MIN
MOD
NUMTOYMINTERVAL
NUMTODSINTERVAL
NVL
POWER
ROUND
RPAD
RTRIM
SIGN
SQRT
SUBSTR
SUM
SYSDATE
TO_DATE
TO_CHAR
TO_NUMBER
TRIM
TRUNC
TimesTen支持这些Oracle表达式:
• 列引用
• Sequence
• NULL
• ()
• 绑定參数
• 计算表达式
• CAST
TimesTen支持Oracle子查询:
• IN(子查询)
• >,<,= ANY(子查询)
• >,=,< SOME(子查询)
• EXISTS(子查询)
• >,=,< (分级子查询)
• 在DELETE/UPDATE的WHERE子句中
• 在FROM子句中
注意:一个“单行结果集”的非验证分级子查询直到运行时才干被确认。TimesTen同意在整个查询中至多仅仅能有一个非验证分级子查询,而且子查询不指定在OR表达式中。
TimesTen支持这些查询:
• FOR UPDATE
• ORDER BY
• GROUP BY
• 表别名
• 列别名
Oracle支持闪回查询,以查询数据库一些曾经状态(比如,查询昨天的一个表)。TimesTen不支持闪回查询。
TimesTen支持这些Oracle DML语句:
• INSERT INTO ... VALUES
• INSERT INTO ... SELECT
• UPDATE WHERE expression(expression能够包括子查询)
• DELETE WHERE expression(expression能够包括子查询)
• MERGE(TimesTen不支持ODBC批量运行MERGE语句)
这部分列出Oracle不支持的TimesTen SQL语句和内部程序。使用PassThrough= 3时,这些语句将被传送到Oracle并产生一个错误。
• 全部TimesTen缓存集合DDL和DML语句,包括CREATE CACHE GROUP、DROP CACHE GROUP、ALTER CACHE GROUP、LOAD CACHE GROUP、UNLOAD CACHE GROUP、FLUSH CACHE GROUP和REFRESH CACHE GROUP语句。
• 全部TimesTen复制管理DDL语句,包括CREATE REPLICATION、DROP REPLICATION、ALTER REPLICATION、CREATE ACTIVE STANDBY PAIR、ALTER ACTIVE STANDBY PAIR和DROP ACTIVE STANDBY PAIR语句。
• 全部TimesTen内部程序。
• Oracle ROWID数据类型是假的ROWID。TimesTen的ROWID数据类型是BINARY(16)。它们的长度不同。
• PL/SQL是一种Oracle语言,并不被TimesTen支持。
• Oracle内部优化内含在SQL凝视中。TimesTen使用内部程序来设置内部优化。
• Oracle和TimesTen的系统表不同。
• TimesTen不支持Oracle INSERT、UPDATE和DELETE语句中的RETURNING子句。
• Oracle存储函数可能通过输出參数返回游标引用或返回值。TimesTen不支持这样的特性。
• 当一条SQL语句有同样的名字的參数时,TimesTen觉得它们是同样參数的反复出现,而且不同意对它们进行分别绑定。Oracle则觉得它们是不同的參数并同意分别绑定。
age out
在一个指定的时间周期之后(基于时间)或当数据的使用已经达到指定的水平(基于使用),将从缓存集合中删除缓存实例。
asynchronous writethrough cache group
TimesTen中一个缓存集合中的数据被更新,并异步的传送到Oracle。
autorefresh
Oracle上的更新通过Oracle触发器的手段被自己主动地传送到TimesTen缓存集合。
AWT cache group
同asynchronous writethrough cache group。
bidirectional propagation
为了将Oracle或TimesTen缓存集合中的更新拷贝到还有一方。
cache agent
一个TimesTen进程以保证缓存集合的操作,如AUTOREFRESH和COMMIT EVERY n ROWS。
cache group
将Oracle表中的数据缓存到一个TimesTen数据存储中。缓存集合能够创建来缓存一个单表的全部或部分,或是缓存一个Oracle相关联的表集。假设缓存了多个Oracle表,则缓存集合中的每一个表必须与缓存集合中还有一个表通过一对多相关联。
cache group primary key
缓存集合中根表的主键。
cache instance
由缓存集合根表中的主键指定的数据中一指定的行。假设缓存集合中有多个表,则缓存实例由通过外键与根表中行关联的相关的行集组成。
cache instance key
根表中指定行的主键,用来确定根表的行和缓存集合子表中引用根表此行的全部子表行。
child table
缓存集合中有一个引用根表主键的外键或引用还有一个直接或间接引用根表的子表主键的外键的表。缓存集合中表的层次能够指定子表是另其他子表的父表。缓存集合中不能有多个父表的子表。
flush
为了将缓存集合中的插入或更新从TimesTen拷贝到Oracle。
load
为了从Oracle仅仅拷贝新实例。不会更新或删除缓存中已经存在实例。
propagate
为了在Oracle和TimesTen缓存集合之间拷贝数据。
refresh
为了使用近期的Oracle数据来替换TimesTen缓存集合中全部的缓存实例。
replication
在多个数据存储中保持数据的副本拷贝的过程。
replication agent
通过一个replication agent来控制在每一个主和从数据存储的复制。在主数据存储上的复制代理来从事务日志读记录并向前查找全部改变以拷贝到从数据存储上的复制代理。从数据存储上的复制代理然后将更新应用到它的数据存储中。
root table
缓存集合中的主表不通过外键约束来引用缓存集合中的不论什么其他表。根表的主键就是缓存集合的主键。
synchronous writethrough cache group
一个缓存集合中缓存数据在TimesTen中被更新,而且同步地传送到Oracle。
system-managed cache group
System-managed cache group强制指定行为。系统管理缓存集合是READONLY、SYNCHRONOUS、WRITETHROUGH和ASYNCHRONOUS WRITETHROUGH。
READONLY缓存集合强制地将Oracle表中的更新通过AUTOREFRESH机制应用到TimesTen。不能在READONLY缓存集合中直接更新表。
ASYNCHRONOUS WRITETHROUGH (SWT)缓存集合强制将TimesTen中缓存数据的更新传送到Oracle。当应用提交事务时,在向TimesTen提交之前向Oracle提交。
ASYNCHRONOUS WRITETHROUGH (AWT)缓存集合的强制缓存行为与SWT缓存集合同样,即TimesTen中缓存数据的更新被传送到Oracle,但TimesTen提交的发生与Oracle提交不同步。
user-managed cache group
一个user-managed cache group实现自己定义行为,如双向传送。
unload
为了从缓存集合中删除一此或全部缓存实例。