SSRS order by multiple criteria dropdown - sql

Sorry for being a noob, but I believe this is the right place for the help I need.
I just started working on SSRS reports (2005) and I would like to find out how I can add a filter dropdown with multiple options that execute a sort. I have imported a list into my table and have the apropriate fields needed for this sort.
IE. I would like to have a dropdown box named "Sort By" with the available selections:
CustomerName
ZipCode, SIC
SIC, City
Each one of those performs the specific order by function that is selected when viewing the report.
I played around and was able to set datasets and add filters, but that isn't optimal because (for instance) you would have to know the exact ZipCode and SIC match to return any results.
There has to be an easy way to return this select statement with multiple order by criteria based on the selection of the dropdown list, but I can't find it if there is.
Any assistance would be greatly appreciated!

I can think of a couple of options. In both cases I've assumed a parameter SortOrder which contains the following values:
CustomerName
ZipCode, SIC
SIC, City
Apply sort expressions to Table based on Parameter
I've applied to sorting expressions to the Table:
First sort:
=Switch(Parameters!SortOrder.Value = "CustomerName", Fields!CustomerName.Value
, Parameters!SortOrder.Value = "ZipCode, SIC", Fields!ZIP.Value
, Parameters!SortOrder.Value = "SIC, City", Fields!SIC.Value)
Second sort:
=Switch(Parameters!SortOrder.Value = "CustomerName", Fields!CustomerName.Value
, Parameters!SortOrder.Value = "ZipCode, SIC", Fields!SIC.Value
, Parameters!SortOrder.Value = "SIC, City", Fields!City.Value)
Apply sort in query
You can add an order by to your Dataset query based on the parameter to perform the same operation:
...
order by case #SortOrder when 'CustomerName' then CustomerName
when 'ZipCode, SIC' then ZIP
when 'SIC, City' then SIC
end
, case #SortOrder when 'CustomerName' then CustomerName
when 'ZipCode, SIC' then SIC
when 'SIC, City' then City
end
In both cases you get a parameter-based sort:

Related

Make an MS Access Report label visible based on data in the report's record source query

In MS Access, I have a report based on a query that presents a summary of a medical checkup. I would like labels for each test to be visible ONLY when those tests were performed. For example, if Glucose was performed on a patient, then the label "lblGlucose" should appear in the report, next to the result. The results currently are present in the report, the problem is when a test is not performed the label is always present. This gives the patient a feeling that the testing was not performed correctly.
To hide the labels I have tried the following approaches:
Private Sub Report_Load()
'1st approach: Lookup column [GLUCOSE] from query qrySummary if not null then set visible property of label lblGLUCOSE to True, else set property to False
IIF(IsNotNull(DLookup("[GLUCOSE]", "qrySummary")),Me!lblGLUCOSE.Visible = True,Me!lblGLUCOSE.Visible = False)
'2nd approach: If value of field [GLUCOSE_RSLT] from table tblResults make textbox txtGlucose visible. FYI: Table tblResults is the table that holds all the results of all the test performed. The query qrySummary derives from this table.
Me!txtGlucose.Visible = Not IsNull([tblResults]![GLUCOSE_RSLT])
'3rd approach: Count column [GLUCOSE], from query qrySummary and if greater than 0 then label lblBHClbl visible
End Sub
I'm still coding the 3rd approach but I'm pretty much running out of ideas and getting nowhere. For first two approaches I get field or expression not found. I don't need for all approaches to work, just one, -in fact, I'm open to other ideas on how I can accomplish the above task.
Any help would be ENORMOUSLY appreciated! Thanks a million!
I'm sharing my DB structure for better understanding
The SQL statement for the summary report is:
PARAMETERS [Forms]![frmIngresoEmpleados]![IDChequeo] Long;
SELECT TblClienteCorp.NombreEmpresa, TblClienteCorp.Direccion, tblChequeo.IDChequeo, tblChequeo.FechaMuestreo, tblChequeo.ChequeoPeriodico, qryCountGenero.*, tblEmpleadosClienteCorp.Genero, tblResultados.Aud_RSLT, tblResultados.Otos_RSLT, tblResultados.AV_RSLT, tblResultados.EKG_RSLT, tblResultados.FR_RSLT, tblResultados.TGP_RSLT, tblResultados.TGO_RSLT, tblResultados.CS_RSLT, tblResultados.ESP_RSLT, tblResultados.PB_RSLT, tblResultados.BHC_RSLT, tblResultados.Plaquetas_RSLT, tblResultados.EGO_RSLT, tblResultados.EGH_RSLT, tblResultados.VDRL_RSLT, tblResultados.Gluc_RSLT, tblResultados.Col_RSLT, tblResultados.EFEC_RSLT, tblResultados.PL_RSLT, tblResultados.Derm_RSLT, tblResultados.Isop_RSLT, tblResultados.BAAR_RSLT, tblResultados.ExFarin_RSLT, tblResultados.Lep_RSLT, tblResultados.Copro_RSLT, tblResultados.Osteo_RSLT, tblResultados.RX_RSLT, tblResultados.US_RSLT
FROM TblClienteCorp INNER JOIN ((tblChequeo INNER JOIN (tblEmpleadosClienteCorp INNER JOIN qryCountGenero ON tblEmpleadosClienteCorp.IDEmpleado = qryCountGenero.IDEmpleado) ON tblChequeo.IDChequeo = tblEmpleadosClienteCorp.IDChequeo) INNER JOIN tblResultados ON tblEmpleadosClienteCorp.IDEmpleado = tblResultados.IDEmpleados) ON TblClienteCorp.IDClienteCorp = tblChequeo.IDClienteCorp
WHERE (((tblChequeo.IDChequeo)=[Forms]![frmIngresoEmpleados]![IDChequeo]));
Within the report that is one query per test, which is:
PARAMETERS [Forms]![frmIngresoEmpleados]![IDChequeo] Long;
SELECT Count(tblResultados.IDEmpleados) AS CuentaDeIDEmpleados, tblResultados.Gluc_RSLT, tblEmpleadosClienteCorp.IDChequeo
FROM tblEmpleadosClienteCorp INNER JOIN tblResultados ON tblEmpleadosClienteCorp.IDEmpleado = tblResultados.IDEmpleados
GROUP BY tblResultados.Gluc_RSLT, tblEmpleadosClienteCorp.IDChequeo
HAVING (((tblResultados.Gluc_RSLT)="P") AND ((tblEmpleadosClienteCorp.IDChequeo)=[Forms]![frmIngresoEmpleados]![IDChequeo]));
If qrySummary has multiple patient records, need WHERE CONDITION criteria:
Me.lblGlucose.Visible = Not IsNull(DLookup("[GLUCOSE]", "qrySummary", "PatientID=" & Me!PatientID))
However, VBA is not necessary. Calculate in textbox (or in query and bind textbox to calculated field) and set control with transparent BorderStyle. Options:
show "None" text when no data:
=Nz(DLookup("[GLUCOSE]", "qrySummary", "PatientID=" & Me!PatientID), "None").
instead of label, use a textbox with expression:
=IIf(IsNull(DLookup("[GLUCOSE]", "qrySummary", "PatientID=" & Me!PatientID)), "", "Glucose")

Access Query parameter that uses a separate table to eliminate or include records

I have one table, Main, which is the main accounting table with all the transactions. I have a second table, Payments, which i keep track of payments and specifically which invoice a given payment has paid off.
I need a report that will be dynamic and flexible; really my accounting workhorse. The report i need will search between dates, customer Id's, record status, account1, account2, and pay status.
So i have a form built out to handle these inputs, but i am having trouble with "pay status" as in, how to form a parameter with it. My current code,
SELECT Main.Invo, Main.InvoDate, Main.Amt, Main.PartyId, Main.TboInvoRloc, Main.TboDocNo, Main.TboPax
FROM Main
WHERE Main.RecSrce<>"Accounts"
AND Main.InvoDate BETWEEN [Forms]![GeneralReport]![startDate] AND [Forms]![GeneralReport]![endDate]
AND Main.PartyId =IIF([Forms]![GeneralReport]![PartyID] IS NULL, PartyID, [Forms]![GeneralReport]![PartyID])
AND Main.Status = IIF([Forms]![GeneralReport]![Status] IS NULL, Status, [Forms]![GeneralReport]![Status])
AND Main.Ac1 = IIF([Forms]![GeneralReport]![Ac1] IS NULL, Ac1, [Forms]![GeneralReport]![Ac1])
AND Main.Ac2 = IIF([Forms]![GeneralReport]![Ac2] IS NULL, Ac2, [Forms]![GeneralReport]![Ac2])
;
covers everything but the "pay status." I wanted to do something like
If checkbox=true, then include paid items, else exclude items where Main.Invo = Payments.DueInvo
My other thought was to exclude the paid items in the initial query, and then include them in a subsequent union query if the checkbox is checked. Any help or thoughts would be appreciated.
Set unbound checkbox for TripleState Yes. Or use a combobox with 3 options (Paid, Unpaid, All) because users might be confused by a triple state checkbox.
Build an aggregate query on Payments table that totals the payments by invoice. Join that query to Main (this assumes invoice is unique in Main).
Calculate a field and set a parameter under that field.
If using checkbox:
IsNotPaid: Amt <> Nz(SumOfPayments,0)
LIKE Forms![GeneralReport]!checkboxname & "*"
If using combobox:
PaidStatus: IIf(Amt = Nz(SumOfPayments,0), "Paid", "Unpaid")
LIKE IIf(Forms![GeneralReport]!comboboxname = "All", "*", Forms![GeneralReport]!comboboxname)
An alternative to aggregate query is DSum() domain aggregate function but that will probably perform slower.
Consider setting payment detail columns to NULL depending on checkbox. Specifically, join the Payments table and run a logical condition on fields in SELECT assigning NULL or not.
SELECT m.Invo, m.InvoDate, m.Amt,
m.PartyId, m.TboInvoRloc,
m.TboDocNo, m.TboPax,
IIF(Forms]![GeneralReport]![myCheckBox] = True,
p.PaymentDetailColumn1, NULL) AS PayColumn1,
IIF(Forms]![GeneralReport]![myCheckBox] = True,
p.PaymentDetailColumn2, NULL) AS PayColumn2,
IIF(Forms]![GeneralReport]![myCheckBox] = True,
p.PaymentDetailColumne, NULL) AS PayColumn3
...
FROM Main m
LEFT JOIN Payments p ON m.Invo = p.DueInvo
WHERE m.RecSrce <> 'Accounts'
AND m.InvoDate BETWEEN [Forms]![GeneralReport]![startDate]
AND [Forms]![GeneralReport]![endDate]
AND m.PartyId = NZ([Forms]![GeneralReport]![PartyID], m.PartyID)
AND m.Status = NZ([Forms]![GeneralReport]![Status], m.Status)
AND m.Ac1 = NZ([Forms]![GeneralReport]![Ac1], m.Ac1)
AND m.Ac2 = NZ([Forms]![GeneralReport]![Ac2], m.Ac2);
If you want dynamic columns (i.e., payment details) to appear or not depending on condition, this cannot come directly from SQL but some connecting app layer code (VBA, Python, etc.) to building dynamic queries. Recall SQL is a declarative language and once identifiers are assigned they are immutable. However, if using reports, you do want all columns explicitly defined from recordsource query.

Test Function Against Every Table Value SQL

I have two tables:
FINAL_VIEW:
and tblUnits:
I need to check that every Value in FINAL_VIEW, if present in Units or if LIKE any field in Correct_Unit, is a case sensitive match for that Correct_Unit(presumably using strComp(Value,Correct_Unit,0)). I'm using this as a criteria for selection.
For instance, if Value was BarG it would be LIKE barg but would then evaluate to false on the strComp().
The stage after this is to return the relevant Correct_Unit (in this case barg) in another field.
I have tried using a subquery within the strComp() but that doesn't work and I have no idea where ot go from here. Any help would be appreciated!
My question can't have been particularly clear but I worked out a solution for both parts.
The key was to link Value with Unit and then perform the query, whilst having my subStr() in the WHERE clause and selecting the Correct_Unit.
Essentially, the linking did the work.
Here's my query for reference:
INSERT INTO tbluoms
SELECT final_view.controller AS Controller,
final_view.compound AS Compound,
final_view.contained_name AS contained_name,
final_view.strategytagname AS StrategyTagname,
final_view.tagname AS Tagname,
final_view.block_cont_name AS Block_Cont_Name,
final_view.name AS Name,
Cstr(final_view.value) AS [Value],
tblunits.[correct unit] AS Correct_Value
FROM tblunits
INNER JOIN final_view
ON tblunits.unit = Cstr(final_view.value)
WHERE NOT (( [value] = [correct unit] ))
OR Strcomp([value], [correct unit], 0)
AND tagname NOT IN (SELECT [tagname]
FROM [tbluoms])
AND name LIKE "ei*"
AND controller IS NOT NULL
AND compound IS NOT NULL;

Type conversion failure in update query

I'm fairly new to Access so this is driving me a little crazy.
I'm creating an inventory database and want to count the number of items in stock to update an ordering form. Received items are assigned an order code, and I want to count the number of instances of each order code found within the master table. I have a make table query which does this just fine:
SELECT PrimerList.PrimerName
, First(Primer_Master.FR) AS FR
, Primer_Master.OrderCode
, Count(Primer_Master.OrderCode) AS InStock
INTO PrimerOrder
FROM PrimerList
LEFT JOIN Primer_Master ON PrimerList.ID = Primer_Master.PrimerName
GROUP BY PrimerList.PrimerName
, Primer_Master.OrderCode
, Primer_Master.PrimerName
, Primer_Master.FR
, Primer_Master.Finished
HAVING ((([Primer_Master]![Finished])=No));
I want to use PrimerOrder to update an order list table PrimerOrderList which has all of the different possible order codes, updating the InStock value for records with matching OrderCode:
UPDATE PrimerOrderList
SET PrimerOrderList.InStock = PrimerOrder.InStock
WHERE (((PrimerOrderList.OrderCode)=[PrimerOrder].[OrderCode]));
However, when I try to run it I get parameter boxes which pop-up asking for PrimerOrder.OrderCode and PrimerOrderList.OrderCode. Even if I put in a valid value for each, I get a type conversion failure. I've checked the data types for both tables and don't see how there could be a type conversion failure - both are set to text.
Any insight would be greatly appreciated! Thanks in advance!
You haven't included the PrimerOrder table in your query. Should be:
UPDATE PrimerOrderList INNER JOIN PrimerOrder
ON PrimerOrderList.OrderCode = PrimerOrder.OrderCode
PrimerOrderList.InStock = PrimerOrder.InStock

How do I return distinct records in Teradata SQL when joining tables that have two entries per record?

Title is a bit of a mouthful, but essentially I have two tables, one with incident data, say, incident_data that contains things like the Incident ID, date, time, and other structured fields. The other incident_text contains the description, resolution, and other freeform text fields.
I want to search both the description and resolution fields in incident_text and join that with incident_data to get more details. They are joined by incidentno, and each incident can have two entries in incident_text, one for the description, the other for resolution.
Say this is my query:
SELECT
DISTINCT INCIDENTNO as "Incident Number",
SOME_OTHER_FIELDS ETC..,
TEXTFIELD AS "Text"
TEXTFIELDTYPE AS "Text Type"
FROM INCIDENT_DATA
INNER JOIN INCIDENT_TEXT
ON INCIDENT_DATA.INCIDENTNO=INCIDENT_TEXT.INCIDENTNO
WHERE TEXT LIKE ANY ('%THIS THING%', '%THAT THING%')
Which gives me a table like so, despite using DISTINCT
INCIDENT-1 ... FORGOT MY PASSWORD TO THIS THING ... DESCRIPTION
INCIDENT-1 ... PASSWORD RESET TO THAT THING.... RESOLUTION
If I add AND TEXTFIELDTYPE = 'DESCRIPTION' I no longer get duplicates, but I also stop searching the resolution fields, which I'd like to still do.
What I am looking for is one line per incident, with the description of the incident, while searching in both the description and resolution fields.
You're pretty close - mostly it comes down to telling SQL to treat description and resolution rows separately.
SELECT Incident_Data.incidentNo as "Incident Number",
some_other_fields etc..,
d.textField AS "Text", d.textFieldType AS "Text Type"
FROM Incident_Data
INNER JOIN Incident_Text d
ON d.incidentNo = Incident_Data.incidentNo
AND d.textFieldType = 'Description'
LEFT JOIN Incident_Text r
ON r.incidentNo = Incident_Data.incidentNo
AND r.textFieldType = 'Resolution'
AND r.textField LIKE ANY ('%THIS THING%', '%THAT THING%')
WHERE d.textField LIKE ANY ('%THIS THING%', '%THAT THING%')
OR r.incidentNo IS NOT NULL
(Not tested, please verify)
- One note - you don't use UPPER() (or LOWER(), or similar); are you certain that that casing is being used?
This is also one of the times that a WHERE clause condition can't be moved up into an INNER JOIN, as we need the rows even if the description doesn't contain the search text.