SELECT DISTINCT STATEMENT - sql

For some reason, my query is returning dup rows. I am trying to create a SELECT DISTINCT query. Can someone please tell me what is wrong with my query?
SELECT DISTINCT
PT_AGCY_DTL.MLM_AGCY_NBR AS AgencyID
, AGENCY.ORG_NM AS Agency
, AGCY_ADDR.CTY_NM as AgencyCity
, AGCY_ADDR.ST_PRVN_CDE_CID as AgencyST
, AG_AGCY_CNTCT.AGCY_CNTCT_ID as ContactID
, AG_AGCY_CNTCT.CNTCT_DT AS ContactDt
, AG_AGCY_CNTCT.AGCY_RESULTS_TXT AS AgencyResults
, AG_AGCY_CNTCT.GEN_OVERVIEW_TXT AS GeneralOverview
, AG_AGCY_CNTCT.NB_RNWL_BUS_DISCUSSION_TXT AS NewAndRenewalBusinessDiscussions
, AG_AGCY_CNTCT.NB_RNWL_BUS_DISCUSSION_TXT AS NewAndRenewalBusinessDiscussions
, AG_AGCY_CNTCT.MKT_INTELLIGENCE_TXT AS MarketIntelligence
, AG_AGCY_CNTCT.AGCY_PERSONNEL_CHG_TXT AS AgencyPersonnelChanges
, AG_AGCY_CNTCT.MM_ISSUE_TXT AS MyMonitorIssues
, AG_AGCY_CNTCT.UW_CLM_ISSUE_TXT AS UnderwritingClaimIssues
, AG_AGCY_CNTCT.FOLLOW_UP_ITEM_TXT AS FollowUpActionItems
, AG_AGCY_CNTCT.NXT_CNTCT_DT AS NextScheduledVisitDate
, CONTACT_TYPE.CODE_NM AS ContactType
, CONVERT(VARCHAR, AG_AGCY_CNTCT.CNTCT_DT,101) + ' - ' + CONTACT_TYPE.CODE_NM AS ContactDtType
, AG_AGCY_CNTCT.CNTCT_DESC AS ContactDetails
, CASE
WHEN PRODUCER.LST_NM IS NULL THEN ' '
ELSE LTRIM(RTRIM(PRODUCER.FRST_NM)) + ' ' + LTRIM(RTRIM(PRODUCER.LST_NM)) END AS Producers
, CASE
WHEN MLM_EMPL.LST_NM IS NULL THEN ' '
ELSE LTRIM(RTRIM(MLM_EMPL.FRST_NM)) + ' ' + LTRIM(RTRIM(MLM_EMPL.LST_NM)) END AS Employees
, CASE
WHEN PROD_CAT.CODE_NM IS NULL THEN ' '
ELSE LTRIM(RTRIM(PROD_CAT.CODE_NM)) END AS ProductCategory
FROM
AG_AGCY_CNTCT
INNER JOIN PT_AGCY_DTL
ON AG_AGCY_CNTCT.AGCY_PID = PT_AGCY_DTL.PARTY_ID
INNER JOIN PT_PARTY AS AGENCY
ON AGENCY.PARTY_ID = AG_AGCY_CNTCT.AGCY_PID
LEFT OUTER JOIN PT_PARTY_ADDR AS AGCY_ADDR
ON AGCY_ADDR.PARTY_ID = AG_AGCY_CNTCT.AGCY_PID
INNER JOIN CD_CODE AS CONTACT_TYPE
ON CONTACT_TYPE.CODE_ID = AG_AGCY_CNTCT.CNTCT_TYP_CID
LEFT OUTER JOIN AG_AGCY_CNTCT_PRDCR_RLTNSHP
ON AG_AGCY_CNTCT_PRDCR_RLTNSHP.AGCY_CNTCT_ID = AG_AGCY_CNTCT.AGCY_CNTCT_ID
LEFT OUTER JOIN PT_PARTY AS PRODUCER
ON PRODUCER.PARTY_ID = AG_AGCY_CNTCT_PRDCR_RLTNSHP.PRDCR_PID
LEFT OUTER JOIN AG_AGCY_CNTCT_MLM_EMPL_RLTNSHP
ON AG_AGCY_CNTCT_MLM_EMPL_RLTNSHP.AGCY_CNTCT_ID = AG_AGCY_CNTCT.AGCY_CNTCT_ID
LEFT OUTER JOIN PT_PARTY AS MLM_EMPL
ON MLM_EMPL.PARTY_ID = AG_AGCY_CNTCT_MLM_EMPL_RLTNSHP.MLM_EMPL_PID
LEFT OUTER JOIN AG_AGCY_CNTCT_PROD_CAT_TYP_RLTNSHP
ON AG_AGCY_CNTCT_PROD_CAT_TYP_RLTNSHP.AGCY_CNTCT_ID = AG_AGCY_CNTCT.AGCY_CNTCT_ID
LEFT OUTER JOIN CD_CODE AS PROD_CAT
ON PROD_CAT.CODE_ID = AG_AGCY_CNTCT_PROD_CAT_TYP_RLTNSHP.PROD_CAT_TYP_CID
AND AGCY_ADDR.ADDR_TYP_CID = '30' -- business address
AND AGCY_ADDR.REC_STS_TYP_CID = 'A' -- active
WHERE
PT_AGCY_DTL.MLM_AGCY_NBR ='4759' --#AgencyID (this is the FILTER)
ORDER BY ContactDt DESC, ContactID DESC

You don't specify, but I suspect you are under the impression that the following rows are duplicate:
t1.col1 | t1.col2 | t2.col1
--------------------------------
1 | 1 | 1
1 | 1 | 2
This is not the case. As was mentioned in the comments, DISTINCT is applied to all columns you are selecting. You can see there are two different combinations of values, hence two rows will be returned. Some people will use an aggregate function and a group by to get around this. Example:
SELECT t1.col1, t1.col2, MAX(t2.col1)
FROM table1 t1
INNER JOIN table2 t2
on t1.whatever = t2.whatever
GROUP BY t1.col1, t1.col2
This would only return the second row. If you are doing this be sure that you understand that you are excluding information in order to force the appearance of a distinct set of records.

Related

Which query is faster to execute

Following are two options to query CTE and NFSE data. Pls advise !
A similar approach may have to be used in many places.
I would like you to verify them and suggest, if there are better options.
Option 1: Query CTE with all necessary joins UNION with query on NFSe with all necessary joins
SELECT DISTINCT 'CTE' as docTypeID
, cte.isqn_mstr_cd as ctePk
, cte.ct_e_cd
, cter.stat_desc
, awb.CREATE_DT
, awb.AWB_NBR
, awb.SHPR_NM
, awbs.DEST_LOC_CD
, nfe.NT_FSCL_CD
, nfe.FSCL_DOC_NBR
FROM cte_identity_master cte
INNER JOIN cte_response_detail cter ON (cte.isqn_mstr_cd = cter.isqn_mstr_cd)
LEFT JOIN match_ref_awb mawb ON (cte.isqn_ref_cd = mawb.isqn_mstr_cd)
LEFT JOIN awb_cust_master awb ON (mawb.awb_nbr = awb.awb_nbr)
LEFT JOIN awb_shipment_detail awbs ON (awb.awb_nbr = awbs.awb_nbr)
LEFT JOIN match_ref_nfe mnfe ON (cte.isqn_ref_cd = mnfe.isqn_mstr_cd)
LEFT JOIN nfe_identity_master nfe ON (mnfe.nt_fscl_cd = nfe.nt_fscl_cd)
UNION
SELECT DISTINCT 'NFSE' as docTypeID
, nfse.isqn_mstr_cd as nfsePk
, nfse.rp_s_id
, nfser.stat_desc
, awb.CREATE_DT
, awb.AWB_NBR
, awb.SHPR_NM
, awbs.DEST_LOC_CD
, nfe.NT_FSCL_CD
, nfe.FSCL_DOC_NBR
FROM nfse_request_detail nfse
INNER JOIN nfse_response_detail nfser ON (nfse.isqn_mstr_cd = nfser.isqn_mstr_cd)
LEFT JOIN match_ref_awb mawb ON (nfse.isqn_ref_cd = mawb.isqn_mstr_cd)
LEFT JOIN awb_cust_master awb ON (mawb.awb_nbr = awb.awb_nbr)
LEFT JOIN awb_shipment_detail awbs ON (awb.awb_nbr = awbs.awb_nbr)
LEFT JOIN match_ref_nfe mnfe ON (nfse.isqn_ref_cd = mnfe.isqn_mstr_cd)
LEFT JOIN nfe_identity_master nfe ON (mnfe.nt_fscl_cd = nfe.nt_fscl_cd)
;
Option 2: Use Union of CTe and NFSe first and then apply joins with other tables
SELECT ctnf.*
, awb.CREATE_DT
, awb.AWB_NBR
, awb.SHPR_NM
, awbs.DEST_LOC_CD
, nfe.NT_FSCL_CD
, nfe.FSCL_DOC_NBR
FROM (
SELECT DISTINCT 'CTE' as docTypeID
, cte.isqn_mstr_cd as docPk
, cte.ct_e_cd as docNbr
, cter.stat_desc as docStat
, cte.isqn_ref_cd as matchRef
FROM cte_identity_master cte
INNER JOIN cte_response_detail cter ON (cte.isqn_mstr_cd = cter.isqn_mstr_cd)
UNION
SELECT DISTINCT 'NFSE' as docTypeID
, nfse.isqn_mstr_cd as nfsePk
, nfse.rp_s_id
, nfser.stat_desc
, nfse.isqn_ref_cd
FROM nfse_request_detail nfse
INNER JOIN nfse_response_detail nfser ON (nfse.isqn_mstr_cd = nfser.isqn_mstr_cd)
) ctnf
LEFT JOIN match_ref_awb mawb ON (ctnf.matchRef = mawb.isqn_mstr_cd)
LEFT JOIN awb_cust_master awb ON (mawb.awb_nbr = awb.awb_nbr)
LEFT JOIN awb_shipment_detail awbs ON (awb.awb_nbr = awbs.awb_nbr)
LEFT JOIN match_ref_nfe mnfe ON (ctnf.matchRef = mnfe.isqn_mstr_cd)
LEFT JOIN nfe_identity_master nfe ON (mnfe.nt_fscl_cd = nfe.nt_fscl_cd)
;
Both approaches of the above will have following Where Clause:
WHERE lower(cte.sttn_cd) = lower(:stationId)
and (:documentType is null or lower(:documentType) = 'cte')
and (:shipperName is null or lower(awb.shipperNm) like lower(concat(concat('%',:shipperName),'%')))
and (:awbCreated is null or to_char(awb.createDt, 'MM-DD-YYYY') = :awbCreated)
and (:awbNumber is null or m2.awbNbr like concat(concat('%',:awbNumber),'%'))
and (:serviceType = 0 or awbs.baseServiceCd = :serviceType)
and (:commitmentDate is null or awbs.commitmentDate = :commitmentDate)
and (:ursa is null or lower(awbs.ursaCd) like lower(concat(concat('%',:ursa),'%')))
and (:destLocationId is null or lower(awbs.destLocCd) like lower(concat(concat('%',:destLocationId),'%')))
and (:nfeNumber is null or nfe.fiscalDocumentNumber like concat(concat('%',:nfeNumber),'%'))
PLEASE SUGGEST - Output of these two approaches to get data which one will be better to fix at Java End to retrieve the data.
Any help will be greatly appreciated. Also suggest if there is any other better query apart from these two!

My query doesn't get the right value

My query doesn't give the right output.
I tried with different way such as with CTE as well but nothing help.
I'm trying to write View to display available products with quantity but as some data is not available in StockCloseInventory table it displaying me 0 even though records are available for some products.
Here is my query:
SELECT TOP (100) PERCENT
SOI.InStockPrdID
, SOI.ProdName
, SOI.TradeDrugId
, ISNULL(SOI.Quantity, 0) AS INQTY
, ISNULL(SCI.QuantitySold, 0) AS OUTQTY
, ISNULL(SOI.Quantity, 0) - ISNULL(SCI.QuantitySold, 0) AS AQTY
, SOI.UnitPrice
FROM dbo.StockInventory AS SOI
LEFT OUTER JOIN dbo.StockCloseInventory AS SCI
ON SOI.InStockPrdID = SCI.InStockPrdID
AND SOI.SoldOut <> 1
LEFT OUTER JOIN dbo.vwTradeDrug AS VTD
ON SOI.TradeDrugId = VTD.TradeDrugId
ORDER BY SOI.ProdName
And this is the output of my View:
And here is my Tables
Table: StockInventory
Table: StockCloseInventory
vwTradeDrug view:
CREATE VIEW [dbo].[vwTradeDrug]
AS
SELECT
T.TradeDrugId
, T.GenericDrugId
, T.TradeName
, G.GenericProprietaryName
, G.DosageType
, G.Strength
, T.TradeName + ',' + G.GenericProprietaryName + ',' + G.DosageType
+ ',' + G.Strength AS TradeFullName
FROM dbo.TradeDrug AS T
INNER JOIN Inventory.GenericDrug AS G
ON T.GenericDrugId = G.GenericId
GO
The problem is with SOI.SoldOut <> 1
First, as Pouya Kamyar pointed out, it is more conventional to include this in a WHERE clause than in a JOIN.
However, the issue is that the value of this field is mostly NULL.
What you want is something more like this:
WHERE SOI.SoldOut IS NULL
OR SOI.SoldOut <> 1
I Suggest bring "AND SOI.SoldOut <> 1" in WHERE clause not in join terms
Either change the null data in sold out to be 0 or 1 OR...
handle the nulls so that the boolean compare results in a true or false instead of "NULL" as below.
SELECT TOP (100) PERCENT
SOI.InStockPrdID
, SOI.ProdName
, SOI.TradeDrugId
, ISNULL(SOI.Quantity, 0) AS INQTY
, ISNULL(SCI.QuantitySold, 0) AS OUTQTY
, ISNULL(SOI.Quantity, 0) - ISNULL(SCI.QuantitySold, 0) AS AQTY
, SOI.UnitPrice
FROM dbo.StockInventory AS SOI
LEFT OUTER JOIN dbo.StockCloseInventory AS SCI
ON SOI.InStockPrdID = SCI.InStockPrdID
AND ISNULL(SOI.SoldOut,0) <> 1 -- this should do the trick
LEFT OUTER JOIN dbo.vwTradeDrug AS VTD
ON SOI.TradeDrugId = VTD.TradeDrugId
ORDER BY SOI.ProdName
Remember Boolean compares on Null values result in NULL (a third value in a Boolean compare!) so SOI.SoldOut <> 1 when SOI.SoldOut is null will result in NULL instead of a true/false you're expecting.

SQL Server 2012 : Multiple Queries in One Stored Procedure

How do I create Stored Procedure on these queries and he output should show which check the anomaly was captured from, along with all the relevant data.
SELECT cm.Cust_id, cm.cust_ref_id4, cm.cust_ref_id3, cm.plan_group, cm.Company_name, cm.Cust_firstname, cm.Cust_lastname
COALESCE(c.pkCustomerID, c2.fkCustomerID, c3.pkCustomerID, c4.pkCustomerID) AS pkCustomerID, c3.CompanyName FROM PRODUCTIONSQL.[SigmaPaTri].[dbo].[CUSTOMER_MASTER] cm
LEFT JOIN PHOENIX.CORE.dbo.Customers AS c ON cust_ref_id4 = c.pkCustomerID AND cm.cust_ref_id3 = c.pkCustomerID AND cm.cust_ref_id3 >= 1000000 AND cm.Cust_firstname + ' ' + cm.Cust_lastname = c.CompanyName
LEFT JOIN PHOENIX.CORE.dbo.Contracts AS c2 ON cm.cust_ref_id3 = c2.ConfirmationNumber
WHERE cm.cust_status IN ('A','P','R','G') AND COALESCE(c.pkCustomerID, c2.fkCustomerID) IS NULL ORDER BY cust_ref_id4;
and
SELECT [pkCustomerID],b.[pkContractID],[pkCustomerTypeID],[CustomerType],b.[ContractType] AS Contractype1,c.[ContractType]
AS Contractype2 FROM [CORE].[dbo].[Customers] a
JOIN [CORE].[dbo].[CustomerTypes] ON [pkCustomerTypeID] = [fkCustomerTypeID]
LEFT JOIN (SELECT [pkContractID],[ContractType],[fkCustomerID] FROM [CORE].[dbo].[Contracts]
JOIN [CORE].[dbo].[ContractTypes] ON [fkContractTypeID] = [pkContractTypeID] WHERE [ContractType] NOT LIKE 'Holdover%')b ON a.pkCustomerID=b.fkCustomerID
LEFT JOIN (SELECT [pkContractID],[fkCustomerID],[ContractType] FROM [CORE].[dbo].[Contracts]
JOIN [CORE].[dbo].[ContractTypes] ON [fkContractTypeID] = [pkContractTypeID] WHERE ContractType LIKE 'Holdover%')c ON b.fkCustomerID=c.fkCustomerID WHERE [CustomerType] IN ('Customer','Former Customer') AND (b.ContractType IS NULL OR c.ContractType IS NULL)
You question is lacking a very important piece of information, the explanation of what you are trying to do. I took a shot in the dark here as a guess to what you might be looking for. BTW, I ran this through a formatter so it was legible.
SELECT 'Found in query1'
,cm.Cust_id
,cm.cust_ref_id4
,cm.cust_ref_id3
,cm.plan_group
,cm.Company_name
,cm.Cust_firstname
,cm.Cust_lastname
,COALESCE(c.pkCustomerID, c2.fkCustomerID, c3.pkCustomerID, c4.pkCustomerID) AS pkCustomerID
,c3.CompanyName
FROM PRODUCTIONSQL.[SigmaPaTri].[dbo].[CUSTOMER_MASTER] cm
LEFT JOIN PHOENIX.CORE.dbo.Customers AS c ON cust_ref_id4 = c.pkCustomerID
AND cm.cust_ref_id3 = c.pkCustomerID
AND cm.cust_ref_id3 >= 1000000
AND cm.Cust_firstname + ' ' + cm.Cust_lastname = c.CompanyName
LEFT JOIN PHOENIX.CORE.dbo.Contracts AS c2 ON cm.cust_ref_id3 = c2.ConfirmationNumber
WHERE cm.cust_status IN (
'A'
,'P'
,'R'
,'G'
)
AND COALESCE(c.pkCustomerID, c2.fkCustomerID) IS NULL
SELECT 'Found in query 2'
,[pkCustomerID]
,b.[pkContractID]
,[pkCustomerTypeID]
,[CustomerType]
,b.[ContractType] AS Contractype1
,c.[ContractType] AS Contractype2
FROM [CORE].[dbo].[Customers] a
INNER JOIN [CORE].[dbo].[CustomerTypes] ON [pkCustomerTypeID] = [fkCustomerTypeID]
LEFT JOIN (
SELECT [pkContractID]
,[ContractType]
,[fkCustomerID]
FROM [CORE].[dbo].[Contracts]
INNER JOIN [CORE].[dbo].[ContractTypes] ON [fkContractTypeID] = [pkContractTypeID]
WHERE [ContractType] NOT LIKE 'Holdover%'
) b ON a.pkCustomerID = b.fkCustomerID
LEFT JOIN (
SELECT [pkContractID]
,[fkCustomerID]
,[ContractType]
FROM [CORE].[dbo].[Contracts]
INNER JOIN [CORE].[dbo].[ContractTypes] ON [fkContractTypeID] = [pkContractTypeID]
WHERE ContractType LIKE 'Holdover%'
) c ON b.fkCustomerID = c.fkCustomerID
WHERE [CustomerType] IN (
'Customer'
,'Former Customer'
)
AND (
b.ContractType IS NULL
OR c.ContractType IS NULL
)

Syntax Error in CASE STATEMENT

Here is my select statement. What I'm trying to do is if an account has more than one ID, I want the phone number to be NULL, ELSE I want the phone number to = phone_number_formatted:
SELECT
v_returned_inventory.order_id,
v_live_inventory.inet_event_description,
v_live_inventory.event_time,
v_cust_phone.phone_number_formatted,
v_live_inventory.event_date,
v_returned_inventory.section_name,
v_returned_inventory.add_usr,
v_live_inventory.num_seats,
v_returned_inventory.acct_id,
v_live_inventory.class_name,
AT_trans_for_emailTrigger.email_addr,
AT_trans_for_emailTrigger.cust_name_id,
premclub.name_first + ' ' + premclub.name_last AS name
FROM
v_returned_inventory
INNER JOIN
v_live_inventory
ON
LEFT(v_returned_inventory.event_name, 6) = LEFT(v_live_inventory.event_name, 6)
AND v_returned_inventory.orderNumber = v_live_inventory.other_info_1 INNER JOIN
AT_trans_for_emailTrigger
ON v_returned_inventory.order_id = AT_trans_for_emailTrigger.order_id
LEFT OUTER JOIN
v_cust_phone
on v_cust_phone.acct_id = v_returned_inventory.acct_id
LEFT OUTER JOIN
OPENQUERY(premclub, 'select name_first, name_last, cust_name_id from dba.v_cust_name') AS premclub
ON AT_trans_for_emailTrigger.cust_name_id = premclub.cust_name_id,
**CASE
WHEN (select
count(cust_name_id)
from
v_cust_phone) > 1 then null
else v_cust_phone.phone_number_formatted
END**
You have the CASE statement in the wrong place, it needs to be in the SELECT. Based on what you currently have, it appears that you might be able to do something like this:
SELECT v_returned_inventory.order_id,
v_live_inventory.inet_event_description,
v_live_inventory.event_time,
case when phone.cnt > 1 then null else v_cust_phone.phone_number_formatted end phone_number_formatted,
v_live_inventory.event_date,
v_returned_inventory.section_name,
v_returned_inventory.add_usr,
v_live_inventory.num_seats,
v_returned_inventory.acct_id,
v_live_inventory.class_name,
AT_trans_for_emailTrigger.email_addr,
AT_trans_for_emailTrigger.cust_name_id,
premclub.name_first + ' ' + premclub.name_last AS name
FROM v_returned_inventory
INNER JOIN v_live_inventory
ON LEFT(v_returned_inventory.event_name, 6) = LEFT(v_live_inventory.event_name, 6)
AND v_returned_inventory.orderNumber = v_live_inventory.other_info_1
INNER JOIN AT_trans_for_emailTrigger
ON v_returned_inventory.order_id = AT_trans_for_emailTrigger.order_id
LEFT OUTER JOIN v_cust_phone
on v_cust_phone.acct_id = v_returned_inventory.acct_id
LEFT OUTER JOIN
(
select count(cust_name_id) cnt, cust_name_id
from v_cust_phone
group by cust_name_id
) phone
on v_cust_phone.cust_name_id = phone.cust_name_id
LEFT OUTER JOIN OPENQUERY(premclub, 'select name_first, name_last, cust_name_id from dba.v_cust_name') AS premclub
ON AT_trans_for_emailTrigger.cust_name_id = premclub.cust_name_id

another union all selecting all the rows that have not already been selected

Right now i have 2 select statements that are joined by a union what i was hopping to do was maybe name the first query like query1 and the second one query2 and then in my third query do a where bookno not in query1 or query2.
SELECT distinct t0.BOOKNO, t0.PaxName, t0.Locator, t0.FDATE7,
t0.BOARD, t0.ALIGHT, t0.AIRLINE, t0.FNUMBR, t0.DEP,
t0.ARR, t0.TOUR, t0.ROUTE,
t1.tour, t1.route, t1.sfrom , t1.sto,t1.seq,t0.seq, 'yes'
FROM
( SELECT TOP (100) PERCENT test.dbo.BNAMES.BOOKNO, RTRIM(test.dbo.BNAMES.SRNAME) + '/' + RTRIM(test.dbo.BNAMES.FIRST) + RTRIM(test.dbo.BNAMES.TITLE)
AS PaxName, test.dbo.PNRS.PNR AS Locator, test.dbo.PNRSECTORS.FDATE7, test.dbo.PNRSECTORS.BOARD, test.dbo.PNRSECTORS.ALIGHT,
test.dbo.PNRSECTORS.AIRLINE, test.dbo.PNRSECTORS.FNUMBR, test.dbo.PNRSECTORS.DEP, test.dbo.PNRSECTORS.ARR, test.dbo.BOOKINGS.TOUR,
test.dbo.BOOKINGS.ROUTE, test.dbo.BSTAGES.SEQ,(test.dbo.PNRSECTORS.BOARD + test.dbo.PNRSECTORS.ALIGHT) as both
FROM test.dbo.BOOKINGS LEFT OUTER JOIN
test.dbo.BNAMES ON test.dbo.BOOKINGS.BOOKNO = test.dbo.BNAMES.BOOKNO LEFT OUTER JOIN
test.dbo.BSTAGES ON test.dbo.BNAMES.BOOKNO = test.dbo.BSTAGES.BOOKNO LEFT OUTER JOIN
test.dbo.PNRSECTORS ON test.dbo.BSTAGES.SCODE = test.dbo.PNRSECTORS.SKEY LEFT OUTER JOIN
test.dbo.PNRS ON test.dbo.PNRSECTORS.PNRKEY = test.dbo.PNRS.PNRKEY
WHERE (test.dbo.BSTAGES.STYPE = 3)
ORDER BY test.dbo.BOOKINGS.BOOKNO, test.dbo.BNAMES.SEQ, locator
) t0
INNER JOIN ( SELECT TOUR, ROUTE, OFFSET, SEQ, SCODE, SFROM, STO, (SFROM + STO) AS BOTH
FROM test.dbo.TSTAGES
) t1 ON t1.tour = t0.tour and t1.route = t0.route and (t0.both = t1.both)
union all
SELECT distinct t0.BOOKNO, t0.PaxName, t0.Locator, t0.FDATE7,
t0.BOARD, t0.ALIGHT, t0.AIRLINE, t0.FNUMBR, t0.DEP,
t0.ARR, t0.TOUR, t0.ROUTE,
t1.tour, t1.route, t1.sfrom , t1.sto,t1.seq,t0.seq,'YES'
FROM
( SELECT TOP (100) PERCENT test.dbo.BNAMES.BOOKNO, RTRIM(test.dbo.BNAMES.SRNAME) + '/' + RTRIM(test.dbo.BNAMES.FIRST) + RTRIM(test.dbo.BNAMES.TITLE)
AS PaxName, test.dbo.PNRS.PNR AS Locator, test.dbo.PNRSECTORS.FDATE7, test.dbo.PNRSECTORS.BOARD, test.dbo.PNRSECTORS.ALIGHT,
test.dbo.PNRSECTORS.AIRLINE, test.dbo.PNRSECTORS.FNUMBR, test.dbo.PNRSECTORS.DEP, test.dbo.PNRSECTORS.ARR, test.dbo.BOOKINGS.TOUR,
test.dbo.BOOKINGS.ROUTE, test.dbo.BSTAGES.SEQ,(test.dbo.PNRSECTORS.BOARD + test.dbo.PNRSECTORS.ALIGHT) as both
FROM test.dbo.BOOKINGS LEFT OUTER JOIN
test.dbo.BNAMES ON test.dbo.BOOKINGS.BOOKNO = test.dbo.BNAMES.BOOKNO LEFT OUTER JOIN
test.dbo.BSTAGES ON test.dbo.BNAMES.BOOKNO = test.dbo.BSTAGES.BOOKNO LEFT OUTER JOIN
test.dbo.PNRSECTORS ON test.dbo.BSTAGES.SCODE = test.dbo.PNRSECTORS.SKEY LEFT OUTER JOIN
test.dbo.PNRS ON test.dbo.PNRSECTORS.PNRKEY = test.dbo.PNRS.PNRKEY
WHERE (test.dbo.BSTAGES.STYPE = 1)
ORDER BY test.dbo.BOOKINGS.BOOKNO, test.dbo.BNAMES.SEQ, locator
) t0
INNER JOIN ( SELECT TOUR, ROUTE, OFFSET, SEQ, SCODE, SFROM, STO, (SFROM + STO) AS BOTH
FROM test.dbo.TSTAGES
) t1 ON t1.tour = t0.tour and t1.route = t0.route and t1.seq = t0.seq and (t0.both = t1.both)
order by bookno
END
How about using WITH? You can declare you queries, join them with UNION and them search for the ones not there.
Take a look here: Multiple Select Statements using SQL Server 2005 "WITH" Statement . It should help you get started.
By using WITH statement, you will isolate logic of your queries, making your overall query more understandable.
just wrap your logic around what you wrote:
select bookno
where key not in (
your big select statement...
)