The view runs in 22secs and returns 324 rows, but the materialized view based on the query select * from myview doesn't complete after 5 minutes. What could the reason be. Below is the explain plan. I have not included the sql for the view as it is quite long. Can do so if needed.
Related
I am migrating Oracle objects to Snowflake. I have materialized view in Oracle that fetches data from multiple tables but in Snowflake a materialized view can be created on single table only. Can I use Oracle materialized view script and use it as a simple view to load into a temporary table and then use this temporary table to create a materialized view on top of it?
Can I use Oracle materialized view script and use it as a simple view to load into a temporary table and then use this temporary table to create a materialized view on top of it?
No, this won't work. A materialized view in Snowflake cannot be based on another view. But don't despair, just because you needed a materialised view in Oracle does not mean that you will need one in Snowflake ! On the contrary, it is typical in scenarios where a materialized view was needed in traditional RDBMS, that no special handling is required in Snowflake due to it's superior performance. Snowflake recommends the following considerations when deciding to use a materialized or regular view:
Create a materialized view when all of the following are true:
The query results from the view don’t change often. This almost always means that the underlying/base table for the view doesn’t change often, or at least that the subset of base table rows used in the materialized view don’t change often.
The results of the view are used often (typically significantly more often than the query results change).
The query consumes a lot of resources. Typically, this means that the query consumes a lot of processing time or credits, but it could also mean that the query consumes a lot of storage space for intermediate results.
Create a regular view when any of the following are true:
The results of the view change often.
The results are not used often (relative to the rate at which the results change).
The query is not resource intensive so it is not costly to re-run it.
I'm using clickhouse-go, sometimes when I run create multiple materialized view, then query from those materialized view it shows success, but sometimes failed because the materialized view not yet created (table default.the_mv_name doesn't exists)
Is there any workaround so the db.Exec("CREATE MATERIALIZED VIEW .... POPULATE AS SELECT ...") only return when it's successfully created. Something like SELECT ... FROM bla FINAL when querying.
Or there's no workaround, so I have to loop and check system.columns table until it's ready?
for non-replicated engine - there's around 50% chance it's happened, for replicated engine - almost always happened
When materialized views are created in Oracle, do they store indices or do they store actual table values?
I am asking this as creating index on table and using views on that table and using materialized views (created with refresh complete start with (sysdate) next (sysdate+1) with rowid as) on unindexed table gives similar performance.
Where as I would expect materialized views to be far more faster.
Update
I slightly modified the content/title. My current concern after discussion is if materialized views are actual real tables or virtual tables with some optimization.
Materialized views create a copy of the data. To all intents and purposes they are actual tables. In fact we can create a materialized view from an existing table using the PREBUILT clause. The only difference is how the data is mastered - a materialized view doesn't own its data, a table does.
As to your performance conundrum:
When you say "on unindexed table" do you literally mean one table? If so, we wouldn't expect any difference in the time to query a view, a materialized view or the actual data: they all execute a full table scan on the same volume of data.
Consider the case where views have expecting select * from <table> where <condition>.
We would a SELECT against a materialised view built on that query to execute quicker than the same SELECT against the actual table, provided the WHERE clause restricts the data to a significantly smaller subset of the original data. Simply because a full table scan over a small table (materialised view) takes less time than a full table scan over a big table. Same applies if the materialised view's projection has fewer columns than the base table.
Indexing is a different matter. Unless the query selects a very small subset of the data it's not going to be more efficient than a full table scan and a filter.
To sum up: the only universal tuning heuristic is: it takes less time to do less work. Beyond that it is impossible to generalise. We can't discuss some vague "consider the case where views have select * from <table> where <condition>." It's all about the specifics.
Fundamentally, a materialized view is just a table with an associated query to populate it.
Given static data, one would generally expect the performance of a SELECT * from the materialized view (with no WHERE clause) to be at least as fast as running the query that underlies the materialized view, regardless of indexing.
If we add a WHERE clause to a SELECT * against the mview, however, that query could perform significantly slower than running the query that underlies the mview with the same WHERE clause. That's because the tables referenced in the query underlying the mview could have indexes to support the conditions in the WHERE clause, where as the mview might not have such indexes.
I have following query which has select query that returns data in 5sec. But when I add create materialized view command infront it takes ever for the query to create materialized view.
When you create a materialized view, you actually create a copy of the data that Oracle takes care to keep synchronized (and it makes those views somewhat like indexes). If your view operates over a big amount of data or over data from other servers, it's natural that the creating this view can take time.
From docs.oracle.com:
A materialized view is a replica of a target master from a single
point in time.
Just for "yuks", try
create table temp_tab nologging as select ...
I've seen cases where MV creation is long for some reason, probably logging.
Also, query development tools sometimes begin returning the data to the screen right away, but if you "paged" to the last row, you would find out how long it really takes to get all the data.
You should profile the select statement with explain plan and understand the table cardinality, indexes, waits states when running, ... in order to see if the query needs tuning.
I have materialized views that ran in production but hare having problems refreshing. The error message is
ORA-32411: materialized view definition query exceeds the maximum length
The ones that are having the problems are 76kb,70kb,75kb, and 67kb. Is there anything that can be done, besides splitting up the query? The scripts are one long query each so it will be hard to split up.
Recreate your materialized views as just views, and then recompile your materialized view select statement as
select * from your_new_view
I don't believe there is a limit to how long a view can be. I've also found this makes updating the MV query quite simple as you only have to recompile the view instead of dropping and recreating the MV.