/*
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you under the Apache License, Version 2.0 (the
 * "License"); you may not use this file except in compliance
 * with the License.  You may obtain a copy of the License at
 *
 *   http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the License is distributed on an
 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 * KIND, either express or implied.  See the License for the
 * specific language governing permissions and limitations
 * under the License.
 */

drop  dataverse q3_shipping_priority if exists;
create  dataverse q3_shipping_priority;

use q3_shipping_priority;


create type q3_shipping_priority.LineItemType as
 closed {
  l_orderkey : int32,
  l_partkey : int32,
  l_suppkey : int32,
  l_linenumber : int32,
  l_quantity : double,
  l_extendedprice : double,
  l_discount : double,
  l_tax : double,
  l_returnflag : string,
  l_linestatus : string,
  l_shipdate : string,
  l_commitdate : string,
  l_receiptdate : string,
  l_shipinstruct : string,
  l_shipmode : string,
  l_comment : string
}

create type q3_shipping_priority.OrderType as
 closed {
  o_orderkey : int32,
  o_custkey : int32,
  o_orderstatus : string,
  o_totalprice : double,
  o_orderdate : string,
  o_orderpriority : string,
  o_clerk : string,
  o_shippriority : int32,
  o_comment : string
}

create type q3_shipping_priority.CustomerType as
 closed {
  c_custkey : int32,
  c_name : string,
  c_address : string,
  c_nationkey : int32,
  c_phone : string,
  c_acctbal : double,
  c_mktsegment : string,
  c_comment : string
}

create  nodegroup group1 if not exists  on
    asterix_nc1,
    asterix_nc2
;
create  dataset LineItems(LineItemType) primary key l_orderkey,l_linenumber on group1;

create  dataset Orders(OrderType) primary key o_orderkey on group1;

create  dataset Customers(CustomerType) primary key c_custkey on group1;

write output to asterix_nc1:"/tmp/q3_shipping_priority.adm"
select element {'l_orderkey':l_orderkey,'revenue':revenue,'o_orderdate':o_orderdate,'o_shippriority':o_shippriority}
from  Customers as c,
      Orders as o,
      LineItems as l
where (((c.c_mktsegment = 'BUILDING') and (c.c_custkey = o.o_custkey)) and ((l.l_orderkey = o.o_orderkey) and (o.o_orderdate < '1995-03-15') and (l.l_shipdate > '1995-03-15')))
/* +hash */
group by l.l_orderkey as l_orderkey,o.o_orderdate as o_orderdate,o.o_shippriority as o_shippriority
with  revenue as q3_shipping_priority.coll_sum((
      select element (i.l_extendedprice * (1 - i.l_discount))
      from  l as i
  ))
order by revenue desc,o_orderdate
limit 10
;
