Question

I have following tables:

 TABLE NAME    FIELD NAMES
 t1            id,group1,group2,itemname
 t2            group1id,name
 t3            group2id,name

Sample data:

t2

   group1id      name
   1             Aa
   2             AA
   3             1AC

t3

   group2id       name
   1              BB
   2              CC

t1

   id    group1    group2    itemname
   1     1         1         Abc
   2     2         1         Bca
   3     3         2         DEC

I want get the itemname based on group1,group2. I want to

Show the group name's with hyphon after that show itemname which are under comes that groups.

So I tried like this:

select g1.name||'-'||g2.name grp, g1.name || ' - ' || g2.name as name from 
t2 as g1,t3 as g2,t1 i where i.group1=g1.group1id and i.group2=g2.group2id

union all

select g1.name||'-'||g2.name||'-'||itemname grp, itemname as name from 
t2 as g1,t3 as g2,t1 i where i.group1=g1.group1id and i.group2=g2.group2id
order by grp

It shows output like:

grp          Name

1AC-CC       1AC - CC
1AC-CC-dex   dex
Aa-BB        Aa - BB
AA-BB        AA - BB
AA-BB-Abc    Abc
Aa-BB-Bca    Bca

But I want:

grp          Name

1AC-CC       1AC - CC
1AC-CC-dex   dex
Aa-BB        Aa - BB
Aa-BB-Bca    Bca
AA-BB        AA - BB
AA-BB-Abc    Abc

How to change my ordering?. grp is used for order purpose only.

Am using PostgreSQL 9.1.

Was it helpful?

Solution

In a UNION query you can only sort by columns in the result. You need to sort by columns from the base tables, though.

Include the needed columns for sorting and drop them in a final outer SELECT. Added some other improvements while being at it.

SELECT grp, name
FROM  (
   SELECT g1.group1 || '-'   || g2.group2 AS grp
        , g1.group1 || ' - ' || g2.group2 AS name
        , g1.group1 , g2.group2  -- for sortting only
   FROM   group1 g1
   JOIN   items  i  USING (group1id)
   JOIN   group2 g2 USING (group2id)

   UNION ALL
   SELECT g1.group1 || '-' || g2.group2 || '-' || item AS grp
        , item AS name
        , g1.group1 , g2.group2  -- for sortting only
   FROM   group1 g1
   JOIN   items  i  USING (group1id)
   JOIN   group2 g2 USING (group2id)
   ) sub
ORDER  BY group1, group2;

Since grp is used for order purpose only, you can further simplify:

SELECT name
FROM  (
   SELECT  g1.group1 || ' - ' || g2.group2 AS name
         , g1.group1 , g2.group2
   FROM   group1 g1
   JOIN   items  i  USING (group1id)
   JOIN   group2 g2 USING (group2id)

   UNION ALL
   SELECT item AS name
        , g1.group1 , g2.group2
   FROM   group1 g1
   JOIN   items  i  USING (group1id)
   JOIN   group2 g2 USING (group2id)
   ) sub
ORDER  BY group1, group2

SQL Fiddle.

OTHER TIPS

You should order by the original columns:

ORDER BY t2.name, t3.name, t1.itemname

But clean up your question. You mix table names and aliases and it is all quite difficult to read. A bit of proper formatting would certainly help to make sense of your query.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top