问题
I have the following tables:
Series One Tables:
create table tbl1
(
id int,
name varchar(100)
);
insert into tbl1 values(1,'tbl1');
create table tbl2
(
id int,
name varchar(100)
);
insert into tbl2 values(1,'tbl2');
create table tbl3
(
id int,
name varchar(100)
);
insert into tbl3 values(1,'tbl3');
create table tbl4
(
id int,
name varchar(100)
);
insert into tbl4 values(1,'tbl4');
Series Double Tables:
create table tbl11
(
id int,
name varchar(100)
);
insert into tbl11 values(1,'tbl11');
create table tbl22
(
id int,
name varchar(100)
);
insert into tbl22 values(1,'tb22');
create table tbl33
(
id int,
name varchar(100)
);
insert into tbl33 values(1,'tbl33');
create table tbl44
(
id int,
name varchar(100)
);
insert into tbl44 values(1,'tbl44');
Now I want to create VIEW of each series tables:
Series One View:
create view View_tbl_one_series as
select * from tbl1
union all
select * from tbl2
union all
select * from tbl3
union all
select * from tbl4
Series Double View:
create view View_tbl_double_series as
select * from tbl11
union all
select * from tbl22
union all
select * from tbl33
union all
select * from tbl44
After that I DROP TABLE tbl1 for some reason and creating another VIEW which contains the definition of two series views.
VIEW ALL:
create view All_VIEW AS
select * from View_tbl_one_series
union all
select * from View_tbl_double_series
Getting an error:
Msg 208, Level 16, State 1, Procedure View_tbl_one_series, Line 2 Invalid object name 'tbl1'.
Try:
exec sp_refreshview View_tbl_one_series
but still getting same error.
Note: I have many tables and views in the database system, and creating view all is the last procedure, and between that have to drop some tables for some reason.
回答1:
A non materialized view in SQL Server can be thought of as just a thin wrapper on top of the underlying tables which appear in that view. If you drop one or more of the tables involved in the view, it won't work, because the table can no longer be queried. There are a number of workarounds here, one of which would be to just create an indexed (materialized) view:
CREATE VIEW View_tbl_one_series
WITH SCHEMABINDING
AS
SELECT * from tbl1
UNION ALL
SELECT * from tbl2
UNION ALL
SELECT * from tbl3
UNION ALL
SELECT * from tbl4
GO
CREATE UNIQUE CLUSTERED INDEX idx ON View_tbl_one_series (id);
Other options would include using a temporary table for the same purpose, or maybe even a bona fide regular table.
Note that in general doing SELECT * in a union query is not ideal, because it leaves open the possibility that the columns/column types may not line up properly between the two tables involved in the union.
来源:https://stackoverflow.com/questions/56249310/refresh-view-after-table-drop