sql - Table-Valued function - Order by is ignored in output -
we moving sql server 2008 sql server 2012 , noticed our table-valued functions no longer deliver temp table contents in correctly sorted order.
code:
insert @customer select customer_id, name, case when expiry_date < getdate() 1 when expired = 1 1 else 0 end customer **order name**
in sql server 2008 function returns customers sorted name. in sql server 2012 returns table unsorted. "order by" ignored in sql 2012.
do have re-write functions include sort_id
, sort them when called in main application or there easy fix??
there 2 things wrong original approach.
- on inserting table never guaranteed
order by
oninsert ... select ... order by
order rows inserted. - on selecting sql server not guarantee
select
withoutorder by
return rows in particular order such insertion order anyway.
in 2012 looks though behaviour has changed respect item 1. ignores order by
on select
statement source insert
declare @t table(number int) insert @t select number master..spt_values order name
2008 plan
2012 plan
the reason change of behaviour in previous versions sql server produced 1 plan shared between executions set rowcount 0
(off) , set rowcount n
. sort operator there ensure correct semantics in case plan run session non 0 rowcount
set. top
operator left of rowcount top
.
sql server 2012 produces separate plans 2 cases there no need add these rowcount 0
version of plan.
a sort may still appear in plan in 2012 if select
has explicit top
defined (other top 100 percent
) still doesn't guarantee actual insertion order of rows, plan might have sort after top n
established rows clustered index order example.
for example in question adjust calling code specify order name
if requires.
regarding sort_id
idea ordering guarantees in sql server guaranteed when inserting table identity
order these allocated per order by
declare @customer table ( sort_id int identity primary key, customer_id int, name int, expired bit ) insert @customer select customer_id, name, case when expiry_date < getdate() 1 when expired = 1 1 else 0 end customer order name
but still need order sort_id
in selecting queries there no guaranteed ordering without (perhaps sort_id
approach might useful in case original columns used ordering aren't being copied table variable)
Comments
Post a Comment