0

I have 3 tables (all simplified here)

job (id int, type char(1))
data (job_id int, owner int, creator int, value int)
user (id int)

My query is

select user.id, job.id, sum(data.value)
from job
join data on job.id = data.job_id
join user on case job.type when 'O' then data.owner else data.creator end = user.id
group by user.id, job.id

How do I create an index in Postgres which caters for the case statement in the join?

Job would have maybe a dozen rows, users 1000s and data millions.

Thanks

6
  • 2
    The condition needs values from two different tables. There is no way you can create an index for that. An index can only be defined on expressions using columns from the table you define the index for. Commented Jan 27, 2021 at 10:33
  • Btw: it's CASE expression not a statement. Commented Jan 27, 2021 at 10:34
  • Was afraid that was the case.. back to the drawing board then. Thanks anyway. Commented Jan 27, 2021 at 10:38
  • What's the execution plan from your query? Commented Jan 27, 2021 at 11:03
  • 1
    Change that to two queries with a UNION ALL. Commented Jan 27, 2021 at 12:17

2 Answers 2

1

In your example, you don't need the table "user" to get the results:

SELECT 
    CASE 
        WHEN job.type = '0' THEN DATA.OWNER
        ELSE DATA.creator
    END AS user_id,
    job.ID,
    DATA.VALUE
FROM
    job
    JOIN DATA ON job.ID = DATA.job_id -- indexes on the id's
GROUP BY 1,2;

Edit: Assumption: There is a foreign key between "data" and "user" that checks if a user exists.

Sign up to request clarification or add additional context in comments.

1 Comment

Alas, there is no key between them. Data actually just contains the emails of the users which I need to join on to get the ids.
0

Seems this isn't possible. Solved my issue by refactoring code to add a row into data for each type, along with a new "type" column and then indexed against this.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.