sraoss / pgsql-ivm

IVM (Incremental View Maintenance) development for PostgreSQL
Other
127 stars 12 forks source link

Incorrect WHERE condition check for outer-join views #78

Closed yugo-n closed 4 years ago

yugo-n commented 4 years ago
outer=# \d r
                 Table "public.r"
 Column |  Type   | Collation | Nullable | Default 
--------+---------+-----------+----------+---------
 i      | integer |           |          | 

outer=# \d s
                 Table "public.s"
 Column |  Type   | Collation | Nullable | Default 
--------+---------+-----------+----------+---------
 j      | integer |           |          | 

outer=# create incremental materialized view mv_rs as
   select * from r left join s on i=j where i > 0 or j> 0;
ERROR:  WHERE cannot contain non null-rejecting predicates for IVM with outer join

This error is incorrect because "i>0 or j>0" can not be true if i or j is null.

yugo-n commented 4 years ago

This error is incorrect because "i>0 or j>0" can not be true if i or j is null.

Sorry, this statement was not correct. "i>0 or j>0" is not null-rejecting, so this error is right!

p(x1,x2,...,xn) is said null-rejecting if it evaluates to false as soon as one of column xi is null. "i>0 or j>0" is not null-rejecting because even if i is null, if j is not null this can be truth. In other words, simple OR condition in WHERE is not supported with outer-join views!

However, we still need fix because an error is raised even when "is not null" is used for these columns.

create incremental materialized view mv_rs as 
  select * from r left join s on i=j 
  where (i > 0 or j> 0) and i is not null and j is not null;
ERROR:  WHERE cannot contain non null-rejecting predicates for IVM with outer join

Due to IS NULL, if either i or j is null then it evaluates to false, so this predicate is null-rejecting and must be supported. I'll fix this.