在建立对远程数据库上数据的访问时,首选视图还是同义词?
When establishing access to data on a remote database, are views or synonyms preferred?
考虑一个场景,您有两个数据库:在数据库 A 上,您需要访问数据库 B 上的数据。
您可以在数据库 A 上创建一个视图,该视图从数据库 B 上的 table 中进行选择。
CREATE OR REPLACE VIEW Demographics.Employees(
employee_id, employee_dept
)
AS
SELECT employee_id, employee_dept
FROM Employee@DB_B;
/
或者,您可以在数据库 A 上创建一个指向数据库 B 上的 table 的同义词。
CREATE OR REPLACE SYNONYM Demographics.Employees FOR Employee@DB_B;
跨数据库使用视图 link 与跨数据库使用同义词 link 的优点和缺点是什么?
如果数据库位于 Exadata 平台内,这会改变建议吗?
就我个人而言,我更喜欢同义词。这就是同义词的作用,为您提供访问对象的更短语法。视图更多用于保存特定查询以供以后重用。现在,如果您想限制源 table 或其他内容上的可用列,那就是您使用视图的时候。
为简单起见,使用同义词。
如果本地数据库应该看到来自远程数据库的所有行和列,那么您定义的视图是不必要的复杂化。它增加了复杂性,因为视图中 可能 存在一些额外的逻辑。寻求了解系统的人将需要花时间检查视图定义并理解它。
也许该视图使 Oracle 优化器的事情变得更加复杂。
有一些正当的理由来观看:
- 您想限制可见的列
- 如果新列添加到远程 table,您不希望它们显示在本地
- 您想限制可见的行,加入其他 table 等
- 如果在远程站点进行更改(例如删除列)而不是在应用程序运行时发现,您希望视图无效
创建视图的时间就是具备这些条件的时候。即便如此,我也会从同义词select 中创建视图。
当您在数据库 link 上创建视图时,您是在本地数据库上创建一个对象。这意味着您在本地拥有关于远程对象的字典信息。
而同义词只是指向远程对象的指针。所以你所拥有的只是同义词定义。
create database link loopback
using 'localhost/pdb1';
create table t (
c1 int
);
create or replace synonym s
for t@loopback;
create or replace view v as
select * from t@loopback;
select table_name, column_name, data_type
from user_tab_cols
where table_name in ( 'S', 'V' )
order by table_name, column_name ;
TABLE_NAME COLUMN_NAME DATA_TYPE
V C1 NUMBER
因此,如果您有检查 table 结构(列、数据类型等)的工具,那么使用视图会很方便。
另一方面,因为视图是本地对象,所以对远程 table 的更改不会自动传播:
alter table t
add ( c2 date );
info s
TABLE: T
LAST ANALYZED:
ROWS :
SAMPLE SIZE :
INMEMORY :DISABLED
COMMENTS :
Columns
NAME DATA TYPE NULL DEFAULT COMMENTS
C1 NUMBER(38,0) Yes
C2 DATE Yes
info v
Columns
NAME DATA TYPE NULL DEFAULT COMMENTS
C1 NUMBER(38,0) Yes
因此您需要重新创建视图才能看到更改。另一方面,如果您不希望远程 DDL 更改立即显示在本地数据库中,这可能是一个优势。
请注意,本地视图和远程视图之间没有依赖关系 table。因此中断更改(例如删除列)不会使视图无效。你只有在查询时才会发现它:
alter table t
drop ( c1 );
select status from user_objects
where object_name = 'V';
STATUS
VALID
select * from v;
ORA-00904: "C1": invalid identifier
select * from s;
no rows selected
同义词只是指向对象的指针。如果要求只是访问对象而无需每次都放入数据库 link/owner 的麻烦,那么它们是最好的方法(考虑到您不想限制列访问)。
视图基本上是对底层对象数据的 window。您可以在列访问中有选择(同义词不可能),并且由于视图基于 SQL 查询,您可以使用 sql 函数对数据进行各种在线操作,例如更改日期格式(upper, lower, nvl 等..),同义词也是不可能的。如果将来需要,您还可以选择修改 SQL 语句以包含更复杂的 SQL 语句。
如果你只想执行抓取和显示,视图是好的,如果你想在其他查询中使用它,建议使用同义词,因为没有中间 SQL 层,因此数据访问速度更快。
这一切都归结为您的要求和对象的使用方式。
考虑一个场景,您有两个数据库:在数据库 A 上,您需要访问数据库 B 上的数据。
您可以在数据库 A 上创建一个视图,该视图从数据库 B 上的 table 中进行选择。
CREATE OR REPLACE VIEW Demographics.Employees(
employee_id, employee_dept
)
AS
SELECT employee_id, employee_dept
FROM Employee@DB_B;
/
或者,您可以在数据库 A 上创建一个指向数据库 B 上的 table 的同义词。
CREATE OR REPLACE SYNONYM Demographics.Employees FOR Employee@DB_B;
跨数据库使用视图 link 与跨数据库使用同义词 link 的优点和缺点是什么?
如果数据库位于 Exadata 平台内,这会改变建议吗?
就我个人而言,我更喜欢同义词。这就是同义词的作用,为您提供访问对象的更短语法。视图更多用于保存特定查询以供以后重用。现在,如果您想限制源 table 或其他内容上的可用列,那就是您使用视图的时候。
为简单起见,使用同义词。
如果本地数据库应该看到来自远程数据库的所有行和列,那么您定义的视图是不必要的复杂化。它增加了复杂性,因为视图中 可能 存在一些额外的逻辑。寻求了解系统的人将需要花时间检查视图定义并理解它。
也许该视图使 Oracle 优化器的事情变得更加复杂。
有一些正当的理由来观看:
- 您想限制可见的列
- 如果新列添加到远程 table,您不希望它们显示在本地
- 您想限制可见的行,加入其他 table 等
- 如果在远程站点进行更改(例如删除列)而不是在应用程序运行时发现,您希望视图无效
创建视图的时间就是具备这些条件的时候。即便如此,我也会从同义词select 中创建视图。
当您在数据库 link 上创建视图时,您是在本地数据库上创建一个对象。这意味着您在本地拥有关于远程对象的字典信息。
而同义词只是指向远程对象的指针。所以你所拥有的只是同义词定义。
create database link loopback
using 'localhost/pdb1';
create table t (
c1 int
);
create or replace synonym s
for t@loopback;
create or replace view v as
select * from t@loopback;
select table_name, column_name, data_type
from user_tab_cols
where table_name in ( 'S', 'V' )
order by table_name, column_name ;
TABLE_NAME COLUMN_NAME DATA_TYPE
V C1 NUMBER
因此,如果您有检查 table 结构(列、数据类型等)的工具,那么使用视图会很方便。
另一方面,因为视图是本地对象,所以对远程 table 的更改不会自动传播:
alter table t
add ( c2 date );
info s
TABLE: T
LAST ANALYZED:
ROWS :
SAMPLE SIZE :
INMEMORY :DISABLED
COMMENTS :
Columns
NAME DATA TYPE NULL DEFAULT COMMENTS
C1 NUMBER(38,0) Yes
C2 DATE Yes
info v
Columns
NAME DATA TYPE NULL DEFAULT COMMENTS
C1 NUMBER(38,0) Yes
因此您需要重新创建视图才能看到更改。另一方面,如果您不希望远程 DDL 更改立即显示在本地数据库中,这可能是一个优势。
请注意,本地视图和远程视图之间没有依赖关系 table。因此中断更改(例如删除列)不会使视图无效。你只有在查询时才会发现它:
alter table t
drop ( c1 );
select status from user_objects
where object_name = 'V';
STATUS
VALID
select * from v;
ORA-00904: "C1": invalid identifier
select * from s;
no rows selected
同义词只是指向对象的指针。如果要求只是访问对象而无需每次都放入数据库 link/owner 的麻烦,那么它们是最好的方法(考虑到您不想限制列访问)。
视图基本上是对底层对象数据的 window。您可以在列访问中有选择(同义词不可能),并且由于视图基于 SQL 查询,您可以使用 sql 函数对数据进行各种在线操作,例如更改日期格式(upper, lower, nvl 等..),同义词也是不可能的。如果将来需要,您还可以选择修改 SQL 语句以包含更复杂的 SQL 语句。
如果你只想执行抓取和显示,视图是好的,如果你想在其他查询中使用它,建议使用同义词,因为没有中间 SQL 层,因此数据访问速度更快。
这一切都归结为您的要求和对象的使用方式。