here's my query which gives the error "#1054 - Unknown column 'request1.orgname' in 'on clause'":
SELECT request.orgname,
request1.API_name AS 'API name',
SUM(CASE WHEN request.username IS NULL
THEN request.projects_priced_count
else 0
END) AS 'API prices calls',
SUM(request.projects_priced_count) AS 'Total prices calls'
FROM prod_virida_pricing.request
LEFT OUTER JOIN (
SELECT api_key.name AS 'API_name',
api_key.orgname AS 'Organization',
date(expiry_date) AS 'API expiry date',
is_active AS 'Active org'
FROM prod_virida_auth.api_key
INNER JOIN prod_virida_auth.organization ON api_key.orgname = organization.orgname
WHERE api_key.blocked = 0
AND organization.is_active = 1) request1 ON request.orgname = request1.orgname
ORDER BY orgname
;
This will solve the problem
Better to use aliases(table1 & table2 in the e.g.) for different subqueries to reduce confusion for SQL to understand to understand the correct columns.
SELECT request.orgname AS 'Organization',
request1.API_name AS 'API name',
SUM(CASE WHEN request.username IS NULL
THEN request.projects_priced_count
else 0
END) AS 'API prices calls',
SUM(request.projects_priced_count) AS 'Total prices calls'
FROM prod_virida_pricing.request AS table1
LEFT OUTER JOIN (
SELECT api_key.name AS 'API_name',
api_key.orgname AS 'Organization',
date(expiry_date) AS 'API expiry date',
is_active AS 'Active org'
FROM prod_virida_auth.api_key
INNER JOIN prod_virida_auth.organization ON api_key.orgname = organization.orgname
WHERE api_key.blocked = 0
AND organization.is_active = 1) AS table2 ON table1.Organization= table2.Organization
ORDER BY table1.Organization
;
Related
I've got the following query that's finding all subscribers between a certain date:
SELECT s.id as 'Subscription ID', s.customer_id as 'Customer ID', s.start_date as 'Start Date', s.status as 'Current Status', l.date 'Cancellation Date'
FROM subscriptions as s
LEFT JOIN subscriptionlog as l ON s.id=l.subscription_id
WHERE s.start_date >= 1559347200
AND s.start_date <= 1596239999
I've added the last column "Cancellation date" where I want to find the following:
l.event = 'subscription_cancelled'
If that exists for a subscriber can it output l.date but if it can't find it, can the column be left blank for that line? How can I incorporate an IF statement?
This looks like a job for CASE clause. You can put it in your select clause for if-else display issues. You can also put it in your WHERE clause for a more robust filter.
In your case:
SELECT
s.id as 'Subscription ID',
s.customer_id as 'Customer ID',
s.start_date as 'Start Date',
s.status as 'Current Status',
CASE
WHEN l.event = 'subscription_cancelled'
THEN l.date
ELSE NULL
END as 'Cancellation Date'
FROM subscriptions as s
LEFT JOIN subscriptionlog as l ON s.id=l.subscription_id
WHERE s.start_date >= 1559347200
AND s.start_date <= 1596239999
I have this pseudo SQL code for what I want to achieve:
UPDATE orders o
SET o.datePaid = null
WHERE
(
SELECT SUM(amount)
FROM transactions t
WHERE t.orderId = o.id
AND t.status = 'success'
AND t.type = 'refund'
)
>=
(
SELECT SUM(amount)
FROM transactions t
WHERE t.orderId = o.id
AND t.status = 'success'
AND t.type IN ('purchase', 'capture')
)
How would I do this in SQL?
I think your approach is interesting. Here is a more concise method:
UPDATE orders o
SET o.datePaid = null
WHERE (SELECT SUM(CASE WHEN t.type = 'refund' THEN amount
WHEN t.type IN ('purchase', 'capture') THEN -amount
END)
FROM transactions t
WHERE t.orderId = o.id AND
t.status = 'success'
) > 0;
Your query works fine as is. However it can be more optimally written using MySQL multi-table UPDATE syntax:
UPDATE orders o
LEFT JOIN (SELECT orderId,
COALESCE(SUM(CASE WHEN type = 'refund' THEN amount END), 0) AS refunds,
COALESCE(SUM(CASE WHEN type IN ('purchase', 'capture') THEN amount END), 0) AS pc
FROM transactions
WHERE status = 'success'
GROUP BY orderId) t ON t.orderId = o.id
SET o.datePaid = NULL
WHERE t.refunds > t.pc
Demo on dbfiddle (includes your query working as well)
Your code would probably work just as it is. Give it a try.
You could also optimize the query to avoid the need for two subqueries by using a JOIN and conditional aggregation in a single subquery:
UPDATE orders o
INNER JOIN (
SELECT orderId
FROM transactions
WHERE
status = 'success'
AND type IN ('success', 'purchase', 'capture') -- this condition might be superfuous
GROUP BY o.id
HAVING
SUM(CASE WHEN type = 'success' THEN amount ELSE 0 END)
>= SUM(CASE WHEN type IN ('purchase', 'capture') THEN amount ELSE 0 END)
) t ON t.orderId = o.id
SET o.datePaid = null
Note: WHERE condition AND type IN ('success', 'purchase', 'capture') is superfluous if that list of 3 values represents all the possible values.
My query:
`SELECT gft_key,
DonorCustomer.cst_ind_full_name_dn as 'Full Name',
DonorCustomer.cst_ixo_title_dn as 'Job Title',
DonorCustomer.cst_org_name_dn as 'Organization',
DonorCustomer.cst_eml_address_dn as 'Email Address',
apl_code as 'Appeal Code',
cmp_code as 'Campaign Code',
prd_name as 'Product Name',
chp_name as 'Chapter Name',
adr_line1,
adr_line2,
adr_city as 'City',
adr_post_code as 'Zip Code',
adr_country as 'Country',
mem_member_type as 'Member Type',
ivd_amount_cp as 'Gift Amount',
fun_code as 'Purpose Code',
gty_type as 'Gift Type',
gft_date as 'Gift Date',
pay_trx_date,
case
when pay_trx_date is null then 'Not Paid' else 'Paid' end as 'Paid?'
FROM
np_gift
JOIN np_gift_type ON gft_gty_key=gty_key
JOIN np_constituent ON gft_dnr_cst_key=dnr_cst_key
JOIN co_customer DonorCustomer ON dnr_cst_key=DonorCustomer.cst_key
JOIN co_customer_x_address ON cst_cxa_key = cxa_key
JOIN co_address ON cxa_adr_key = adr_key
JOIN oe_product ON gft_fpc_prd_key=prd_key
LEFT JOIN np_purpose ON gft_fun_key=fun_key
LEFT JOIN np_campaign ON gft_cmp_key=cmp_key
LEFT JOIN np_appeal ON gft_apl_key=apl_key
JOIN ac_invoice_detail ON gft_ivd_key=ivd_key and ivd_void_flag=0
left outer join ac_payment_detail on pyd_ivd_key=ivd_key
left outer join ac_payment on pyd_pay_key=pay_key
left outer join ac_payment_info on pay_pin_key=pin_key
LEFT JOIN vw_client_uli_member_type ON dnr_cst_key=mem_cst_key
LEFT JOIN co_customer_x_customer ON cxc_cst_key_1 = DonorCustomer.cst_key and (cxc_end_date is null or datediff(dd,getdate(),cxc_end_date) >=0) and cxc_rlt_code='Chapter Member'
LEFT JOIN co_chapter ON cxc_cst_key_2=chp_cst_key
where (pay_trx_date >= '7/1/2017' or pay_trx_date is null)
order by gft_date`
Sample data that I get by running the query: Gift Date pay_trx_date
2013-11-18 2017-07-12
2013-11-29 NULL
2014-12-15 NULL
2017-06-30 NULL
2015-05-01 2017-07-01
By running the query above I accomplish the above result set. However, I want to exclude rows where the gift date is < '7/1/2017' and pay_trx_date is NULL (Just like the middle rows in my sample data) at the same time though I want to keep rows where the gift date is <= '7/1/2017' and pay_trx_date is not NULL (Just like the first or last row in my sample data)
You can use your current query as inner block and filter one time as per your requirement.
SELECT * FROM (
-- Your Current Query
) Q
WHERE gft_date <= '7/1/2017' AND pay_trx_date IS NOT NULL
I have this query that select records from a table and LEFT JOINS other two tables.
Here's the query
SELECT mainTest.lab_number_auto, mainTest.lab_number,
SUM(CASE WHEN test.lab_number = mainTest.lab_number
THEN test.test_unit_cost ELSE 0 END) cost,
payment.totalPaid
FROM patient_main_test mainTest
LEFT JOIN patient_test test
ON test.lab_number = mainTest.lab_number
LEFT JOIN (
SELECT SUM(CASE WHEN testpayment.lab_number = mainTest.lab_number THEN testpayment.amount_paid ELSE 0 END) totalPaid
FROM patient_test_payment testpayment
GROUP BY testpayment.lab_number
) AS payment
ON payment.lab_number = mainTest.lab_number
WHERE mainTest.lab_number != ''
GROUP BY mainTest.lab_number
On running this query i get this error
MySQL said:
#1054 - Unknown column 'mainTest.lab_number' in 'field list'
Thanks.
Here's a fiddle i created.
http://sqlfiddle.com/#!2/291c4/8
Try this, if im right the issue is that you were trying to treat your derived table in the left join like a co-related sub-query. & thx for the sql fiddle... makes it so much easier to help you.
SELECT mainTest.lab_number_auto, mainTest.lab_number,
SUM(CASE WHEN test.lab_number = mainTest.lab_number
THEN test.test_unit_cost ELSE 0 END) cost,
(
SELECT SUM(CASE WHEN testpayment.lab_number = mainTest.lab_number THEN testpayment.amount_paid ELSE 0 END) totalPaid
FROM patient_test_payment testpayment
Where lab_number = mainTest.lab_number
GROUP BY testpayment.lab_number
) AS totalPaid
FROM patient_main_test mainTest
LEFT JOIN patient_test test
ON test.lab_number = mainTest.lab_number
WHERE mainTest.lab_number != ''
GROUP BY mainTest.lab_number
I have a query that looks like this:
SELECT
app.application_id,
j.job_number,
j.job_id,
j.job_title,
j.job_city,
j.job_state,
p.person_id AS candidate_id,
p.first_name,
p.last_name,
app.start_date,
ope1.percent_complete,
MAX(CASE
WHEN r.role_display_name = 'ENG - Recruiter' THEN
(SELECT CASE WHEN COUNT(last_name) = 0 THEN
'Unassigned'
ELSE
COUNT(last_name)
END AS uname
FROM users
JOIN job_roles ON job_roles.user_id = users.user_id
WHERE job_id = j.job_id
AND role_id = r.role_id
)
ELSE '' END) AS role_3
My problem is that COUNT(last_name) will not return 0, because there are no records returned, so there is no value of NULL. All makes sense, however I have tried wrapping it in IFNULL(), ISNULL() and none of them seem to fix this problem. How can I get it to return 0 when there are no records? Do I need another subquery inside the COUNT() aggregate? I would really like to not use another subquery....
If understand correctly what you want you can try to rewrite it this way
SELECT ...
,MAX(CASE WHEN r.role_display_name = 'ENG - Recruiter'
THEN COALESCE(NULLIF(
(
SELECT COUNT(last_name)
FROM users JOIN job_roles
ON job_roles.user_id = users.user_id
WHERE job_id = j.job_id
AND role_id = r.role_id
), 0), 'Unassigned')
ELSE ''
END) as role_3
...