Clickhouse: Want to extract data from Array(Nested) column in Clickhouse - mysql

Query used to create the table:
CREATE TABLE default.ntest2(
job_name String,
list_data Array(Nested(s UInt64, e UInt64, name String))
)
ENGINE = MergeTree
ORDER BY (job_name)
SETTINGS index_granularity = 8192;
Table Data:
job_name
list_data
job1
[[(1,2,'name1')],[(4,5,'name2')]]
job2
[[(22,33,'name3')],[(44,55,'name4')]]
Expected Output:
job_name
list_data.s
list_data.e
list_data.name
job1
1
2
'name1'
job1
4
5
'name2'
job2
22
33
'name3'
job2
44
55
'name4'
How can I achieve this with less query time?

use clickhouse array join
SELECT job_name, element.s, element.e, element.name
FROM default.ntest2
ARRAY JOIN element IN list_data

Related

AWS GLUE SQL join with single row from right table

Im trying to join two datasets in AWS glue
Table 1(alias af):
id
data
created
1
string 1
2020-02-10
2
string 2
2020-02-11
3
string 3
2020-02-12
Table 2 (alias mp):
id
data
data2
created
foreign_key
1
string 1
json string
2020-02-10
2
2
string 2
json string
2020-02-11
3
3
string 3
json string
2020-02-12
3
What i want to do is get all rows from table 1 and select the first row from table 2 that matches the foreign key.
This is what I have currently after going through a few questions i found that i need to wrap the query with an aggregate function to let spark know that only 1 element will match this subquery.
select af.id,af.data
(select first(mp.data)
from mp
where af.id= mp.foreign_key
) as alias1,
(select first(mp.data2)
from mp
where af.id= mp.foreign_key
) as alias2
from af
having alias 1 is not null and alias2 is not null
But this is giving me the following error:
ParseException: mismatched input 'first' expecting {')', ',', '-'}(line 3, pos 15)
Any help will be appreciated!
Ive found a solution that works for my use case. Comment above was right the SQL was funky before.
Select af.*, mp.*
from af join
(select mp.*, row_number() over (partition by mp.fid order by mp.created_at) as seqnum
from mp
) mp
on af.id= mp.fid and seqnum = 1;

SQL: Need to get aggregrated status by priority across related tables in MySQL

I have a Parent table A in MySQL DB 5.5.x with columns
Id(PK) Name Value
1 ABC 0.1
2 XYZ 0.2
3 PQR 0.3
And a related table B which reference Id from parent (FK)
status can have only 3 possible values i.e. pass,warn,error
with error check being higher priority than warn and so on
CheckName CheckStatus Id
L1 pass 1
L2 pass 1
L3 warn 1
L4 error 1
L1 pass 2
L2 warn 2
L3 pass 2
I want to create an SQL statement which can get aggregrate result from parent table A such that
if Id 1 has any errors reported against it I label the finalState for Id 1 as ERROR,
if no errors found check if Id 1 has any warnings reported against it and label the finalState as WARN
finally Mark it as pass.
I am unable to do a simple JOIN or add a case statement in the select claues
as i start getting multiple rows here.
Can I do this without using Stored Procedures ?.
Result Expected based on sample data in final select query is as follows:-
Id Name FinalStatus
1 ABC error
2 XYZ warn
Thanks!
EDIT:
Approach 1 (That I tried here):
select a.Id,
case when b.CheckStatus='error' then 'ERROR'
case when b.CheckStatus='warn' then 'WARN'
case when b.CheckStatus='pass' then 'PASS'
from a join b on
a.Id=b.Id
This is a prioritization query. I am only focusing on b -- you can bring in the columns from a using a simple join.
This works in MySQL 8+:
select b.*
from (select b.*,
row_number() over (partition by id
order by case checkstatus
when 'error' then 1
when 'warn' then 2
when 'pass' then 3
else 4
end
) as seqnum
from b
) b
where seqnum = 1;
In earlier versions, I would go for conditional aggregation:
select b.id,
max(finalstatus = 'error') as is_error,
max(finalstatus = 'warn') as is_warn,
max(finalstatus = 'pass') as is_pass
from b
group by b.id;
You can then get the final status as:
select b.id,
(case when max(checkstatus = 'error') > 0 then 'error'
when max(checkstatus = 'warn') > 0 then 'warn'
when max(checkstatus = 'pass') > 0 then 'pass'
end) as finalstatus
from b
group by b.id;

how can get data of perticular id by using sqlsubqueries(i am using sql subqueries IN)

Hi all am using sql sub queries IN for two sql queries .am getting data of all id's but i need to get data of of perticualar id how can i write below is my query
SELECT g.title
FROM`object_reference` b, object_data a,`object_reference` d,
`tree` e,`object_reference` f,`object_data` g,`tree` c
WHERE a.`obj_id` = b.`obj_id`
AND b.`ref_id` = c.`parent`
AND c.`child` = d.`ref_id`
AND d.`ref_id` = e.`parent`
AND e.`child` = f.`ref_id`
AND f.`obj_id` = g.`obj_id`
AND a.type='tst' IN(
SELECT c.child
FROM object_data a,`object_reference` b,`tree` c
WHERE a.`obj_id` = b.`obj_id`
AND b.`ref_id` = c.`parent`
AND a.obj_id=3217)
Here is some sample data:
table object_data:
obj_id | type | title
-------+------+------
3217 |crs |it
3221 |grp |xyz
3228 |tst |test
3264 |tst |test3
table object_reference:
ref_id | obj_id
-------+---------
337 |3217
338 |3221
343 |3228
371 |3264
table tree:
tree | child | parent
-----+-------+------
1 |338 |337
2 |343 |338
3 |371 |337
And here is the expected result for the sample data:
obj_id|title
------+-----
3228 |test
3264 |test3
Try this query:
SELECT A.obj_id, A.title
FROM object_data A JOIN object_reference B
ON A.obj_id=B.obj_id
JOIN (SELECT C.child FROM tree C
WHERE NOT EXISTS (SELECT null
FROM. tree D
WHERE D.parent=C.child)) E
ON B.ref_id=E.child;

MySQL result combination

I am fairly new to MySQL and I am having a bit of a problem trying to combine a few queries into a single one. Basically I have two tables:
I need to get:
ALL IDJobs where StaffID is NOT Part of it
ALL IDJobs where StaffID is part of it AND has a Status 1 or 6
.
Jobs
------------------
IDJob - The PKey
JobInfo - Some Data
JobPosition
------------------
PositionID - Each Job can have multiple positions
JobID - Value from Jobs Table
StaffID - Value from Staffs Table
Status - Status of Staff for the Job
I am trying to get all IDJobs WHERE
(
SELECT JobID AS IDJob
FROM SelectedStaff
WHERE StaffID <>10
)
UNION
(
SELECT IDJob
FROM Jobs
WHERE IDJob
IN (
SELECT JobID
FROM SelectedStaff
WHERE SelectStatus
IN ( 1, 6 )
AND StaffID =10
)
)
But the result is not returning for me the Job IDs where the Staff is not part of it. That would be the bigger list, and then filtering it with the smaller query.
Any help would be appreciated.
EDIT:
Sample data would be:
Jobs Table
IDJob JobInfo
1 Job1
2 Job2
3 Job3
.
JobPosition
PositionID JobID StaffID Status
1 2 10 0
2 2 10 6
3 3 10 0
This should result:
IDJob
1
2
Is this what you want?
select jp.JobId
from JobPosition jp
group by jp.JobId
having sum(StaffId = 10) = 0 or -- Staff10 is not part of the job
sum(StaffId = 10 and status in (1, 6)) > 0
This uses conditional aggregation in the where clause to count the number of rows that match each of your conditions.
So here is the solution that finally worked for me. I don't know if I am making it too complicated, but it is the right result:
(
SELECT IDJob
FROM Jobs
WHERE IDJob
NOT IN (
SELECT JobID AS IDJob
FROM JobPosition
WHERE StaffID = 10
)
)
UNION
(
SELECT IDJob
FROM Jobs
WHERE IDJob
IN (
SELECT JobID
FROM SelectedStaff
WHERE JobPosition IN (1,6)
AND StaffID=10
)
)

sql query for filtering data with where multiple criteria on same column of table

I have following Sample table.
table having combination of name and key column unique records
ID name key key_type
-----------------------------------
118 ab 12 aw1
119 fb 13 1Y2
120 cb 14 qw3
121 ab 15 4123
122 cs 12 23d2
select * from Sample where name ='ab' and key= '12'
select * from Sample where name ='fb' and key= '13'
how to write single query for both record ?
Easiest way would be union all
select * from Sample where name ='ab' and key= '12'
union all
select * from Sample where name ='fb' and key= '13'
Easiest way would be
select *
from Sample
where (name = 'ab' and `key` = '12')
or (name = 'fb' and `key` = '13')
Demo here: http://sqlfiddle.com/#!9/3eabc/3
Throw an index on (name, key) for good measure.
create index name_key on sample(name, `key`);