groditi is now going to shout at me for making syntax up in 3, 2, 1 ...
Matt S Trout [Wed, 16 Jul 2008 17:13:35 +0000 (17:13 +0000)]
etc/having-cases.sql

index f0a655f..559c8b1 100644 (file)
@@ -8,6 +8,40 @@ SELECT users.name, SUM(commission) AS total
     HAVING total > 500
   ORDER BY total DESC;
 
+order_by { $_->total }
+  select { $_->users->name, [ total => sum($_->aggregates->commission) ] }
+   where { sum($_->aggregates->commission) > 500 }
+group_by { $_->commissions->recipient_id }
+    join { $_->users->id == $_->commissions->recipient_id }
+      [ users => expr { $_->users  } ],
+      [ commission => expr { $_->commissions } ];
+
+my $total = [ -sum => [ -name => 'commission' ] ];
+
+[
+  -select,
+  [
+    -list,
+    [ -name => qw(users name) ],
+    $total
+  [
+    -where,
+    [ '>', $total, [ -value, 500 ] ],
+    [
+      -group_by,
+      [ -name, qw(commissions recipient_id) ],
+      [
+        -where,
+        [ '>', [ -name, qw(commissions entry_date) ], [ -value, '2007-01-01' ] ],
+        [
+          -join,
+          ...
+      ],
+    ],
+  ],
+  ],
+]
+
 -- CASE 2
 SELECT users.name, aggregates.total FROM (
        SELECT recipient_id, SUM(commission) AS total
@@ -19,6 +53,21 @@ SELECT users.name, aggregates.total FROM (
 INNER JOIN users ON(aggregates.recipient_id = users.id)
 ORDER BY aggregates.total DESC;
 
+order_by { $_->aggregates->total }
+  select { $_->users->name, $_->aggregates->total }
+    join { $_->users->id == $_->aggregates->recipient_id }
+      [ users => expr { $_->users  } ],
+      [ aggregates =>
+          expr {
+              select { $_->recipient_id, [ total => sum($_->commission) ] }
+               where { sum($_->commission) > 500 }
+            group_by { $_->recipient_id }
+               where { $_->entry_date > '2007-01-01' }
+                expr { $_->commissions }
+          }
+      ];
+
 -- CASE 3
 SELECT users.name, aggregates.total FROM (
        SELECT recipient_id, SUM(commission) AS total
@@ -29,3 +78,18 @@ SELECT users.name, aggregates.total FROM (
 INNER JOIN users ON(aggregates.recipient_id = users.id)
 WHERE aggregates.total > 500
 ORDER BY aggregates.total DESC
+
+
+order_by { $_->aggregates->total }
+  select { $_->users->name, $_->aggregates->total }
+   where { $_->aggregates->total > 500 }
+    join { $_->users->id == $_->aggregates->recipient_id }
+      [ users => expr { $_->users  } ],
+      [ aggregates =>
+          expr {
+              select { $_->recipient_id, [ total => sum($_->commission) ] }
+            group_by { $_->recipient_id }
+               where { $_->entry_date > '2007-01-01' }
+                expr { $_->commissions }
+          }
+      ];