Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Oracle: How do I grab a default value when a more specific value is null from within the same query?

That title is brutal, but I don't know how else to put it.

I have a key value table tied to a user_id that stores user preferences throughout the site. If a user hasn't gone in and updated any of their settings, any time I ask for a key (say "FAVORITE_COLOR" it's going to be null, so I need to pull the default setting that I have tied to the default user, user_id = 0.

I was thinking along the lines of UNION'ing the user_id = 0 results to the bottom of the query, but that'd just lead to duplicates. I'm not sure if it's even possible, but what'd I'd love to be able to say something like:

SELECT val FROM k_v WHERE user_id = 123 AND k = 'FAVORITE_COLOR'
UNION IF val IS NULL
SELECT val FROM k_v WHERE user_id = 0 AND k = 'FAVORITE_COLOR';

Any good way to do this?

Edit: Thanks for all the help on this. If your use case is only grabbing a single value which is what this question is, then NVL from dual is exactly what you want, but if you're planning on returning multiple pairs in the same query, take a look at some of the other answers as they may actually make more sense for implementation.

I wound up going with ZeissS's suggestion below as it's simple, still one query, works with multiple k,v pairs and I don't have a problem doing the possible duplicate filtering client side.

like image 795
user126715 Avatar asked Dec 29 '22 09:12

user126715


1 Answers

Use this,

select
  nvl(
    (SELECT val FROM k_v WHERE user_id = 123 AND k = 'FAVORITE_COLOR'),
    (SELECT val FROM k_v WHERE user_id = 0 AND k = 'FAVORITE_COLOR')
  ) val 
from dual
;

From the Oracle docs,

NVL(expr1, expr2): NVL lets you replace null (returned as a blank) with a string in the results of a query. If expr1 is null, then NVL returns expr2. If expr1 is not null, then NVL returns expr1.

like image 81
Janek Bogucki Avatar answered Dec 30 '22 22:12

Janek Bogucki