Hi all

This is a follow-up to a recent question I posted regarding a slow query. I 
thought that the slowness was caused by the number of JOINs in the query, but 
with your assistance I have found the true reason. I said in the previous 
thread that the question had become academic, but now that I understand things 
better, it is no longer academic as it casts doubt on my whole approach.

I have split my AR transaction table into three physical tables – ar_tran_inv, 
ar_tran_crn, ar_tran_rec. I will probably add others at some point, such as 
ar_tran_jnl.

I then create a VIEW to view all transactions combined. The view is created 
like this -

CREATE VIEW ar_trans AS
  SELECT ‘ar_inv’ AS tran_type, row_id AS tran_row_id, tran_number ... FROM 
ar_tran_inv WHERE posted = ‘1’
  UNION ALL
  SELECT ‘ar_crn’ AS tran_type, row_id AS tran_row_id, tran_number ... FROM 
ar_tran_crn WHERE posted = ‘1’
  UNION ALL
  SELECT ‘ar_rec’ AS tran_type, row_id AS tran_row_id, tran_number ... FROM 
ar_tran_rec WHERE posted = ‘1’

I have another table called ‘ar_trans_due’, to keep track of outstanding 
transactions. All of the three transaction types generate entries into this 
table. To identify the source of the transaction, I have created columns in 
ar_trans_due called ‘tran_type’ and ‘tran_row_id’. After inserting a row into 
‘ar_tran_inv’, I invoke this -

  INSERT INTO ar_trans_due (tran_type, tran_row_id, ...) VALUES (‘ar_inv’, 
ar_tran_inv.row_id, ...), and similar for the other transaction types. It is 
handled by a Python program, and it all happens within a transaction.

When I view a row in ar_trans_due, I want to retrieve data from the source 
transaction, so I have this -

  SELECT * FROM ar_trans_due a
  LEFT JOIN ar_trans b ON b.tran_type = a.tran_type AND b.tran_row_id = 
a.tran_row_id

I understand that PostgreSQL must somehow follow a path from the view 
‘ar_trans’ to the physical table ‘ar_tran_inv’, but I assumed it would execute 
the equivalent of SELECT * FROM ar_tran_inv WHERE row_id = a.tran_row_id AND 
posted = ‘1’.

If this was the case, it would be an indexed read, and very fast. Instead, 
according to EXPLAIN, it performs a sequential scan of the ‘ar_tran_inv’ table.

It also scans ‘ar_tran_crn’ and ‘ar_tran_rec’, but EXPLAIN shows that it uses a 
Bitmap Heap Scan on those. I assume that is because the tables are currently 
empty.

Is this analysis correct?

If so, is there any way to force it to use an indexed read?

Thanks for any pointers.

Frank Millman

Reply via email to