Generating a select query from a generalized and specialized tables - php

So I have a generalised table called beneficiaries which gives the specialised table parent and child. So parent and child table reference a beneficiary id. However, child table references a parent beneficiary id. Now my struggle is I want to write a query which returns the name of the child from the beneficiary and the name of the parent from the beneficiary while showing which parent a child belongs to. I wrote this query:
select * from beneficiaries
inner join child on beneficiaries.bene_id = child.ParentBene_id
inner join parent on beneficiaries.bene_id = parent.parentBene_id;
But the results I get is just the parent name and the id for the child.
Structure of Tables
Beneficiaries table
Child Table
Parent Table

Your query looks great. I created some tables with sample data and this is my result.
Maybe you forgot to declare the foreigns keys when creating the tables?
Here is the commands I used to create your tables in MySQL:
Beneficiaries table:
CREATE TABLE `beneficiaries` (
`bene_id` int(11) NOT NULL,
`kayacare_id` int(11) DEFAULT NULL,
`fname` tinytext,
`mname` tinytext,
`lname` tinytext,
`location` tinytext,
`dob` tinytext,
`sex` varchar(1) DEFAULT NULL,
PRIMARY KEY (`bene_id`)
)
Child table:
CREATE TABLE `child` (
`bene_id` int(11) DEFAULT NULL,
`parentBene_id` int(11) DEFAULT NULL,
`healthWorker_id` int(11) DEFAULT NULL,
`careGiver_id` int(11) DEFAULT NULL,
KEY `parentBene_id` (`parentBene_id`),
FOREIGN KEY (parentBene_id) REFERENCES beneficiaries(bene_id)
)
Parents table:
CREATE TABLE `parent` (
`parentBene_id` int(11) DEFAULT NULL,
`phone` int(11) DEFAULT NULL,
KEY `parentBene_id` (`parentBene_id`),
FOREIGN KEY (parentBene_id) REFERENCES beneficiaries(bene_id)
)
Here you can see how to edit a foreign key in MySQL.

To get the results I wanted I used this query:
select * from child
right join beneficiaries on child.bene_id = beneficiaries.bene_id
inner join (select parentBene_id,fname as pfname, mname as pmname, lname as plname, phone from
parent inner join beneficiaries on parent.parentBene_id = beneficiaries.bene_id)
parent on child.parentBene_id = parent.parentBene_id;

Related

How can i combine these queries into single query with where clause from another parent table?

How can I combine these queries into a single query with where clause from another parent table? Please consider my SQL code and suggest a better method to work with
//look my code
CREATE TABLE IF NOT EXISTS first (
fid int(11) NOT NULL PRIMARY KEY AUTO_INCREMENT,
p_name varchar(60) NOT NULL
);
CREATE TABLE IF NOT EXISTS second (
sed int(11) NOT NULL PRIMARY KEY AUTO_INCREMENT,
firstname varchar(20) NOT NULL,
fid int(11) NOT NULL,
FOREIGN KEY (fid) REFERENCES first(fid)
);
CREATE TABLE IF NOT EXISTS third (
thid int(11) NOT NULL PRIMARY KEY AUTO_INCREMENT,
start_date date NOT NULL,
end_date date NOT NULL,
sed int(11) NOT NULL,
FOREIGN KEY (sed) REFERENCES second(sed),
fid int(11) NOT NULL,
FOREIGN KEY (fid) REFERENCES first(fid)
);
CREATE TABLE IF NOT EXISTS fourth (
fid int(11) NOT NULL PRIMARY KEY AUTO_INCREMENT,
start_date date NOT NULL,
end_date date NOT NULL,
sed int(11) NOT NULL,
FOREIGN KEY (sed) REFERENCES second(sed),
fid int(11) NOT NULL,
FOREIGN KEY (fid) REFERENCES first(fid)
);
CREATE TABLE IF NOT EXISTS fifth (
fiid int(11) NOT NULL PRIMARY KEY AUTO_INCREMENT,
start_date date NOT NULL,
end_date date NOT NULL,
sed int(11) NOT NULL,
FOREIGN KEY (sed) REFERENCES second(sed),
fid int(11) NOT NULL,
FOREIGN KEY (fid) REFERENCES first(fid)
);
CREATE TABLE IF NOT EXISTS sixth (
sid int(11) NOT NULL PRIMARY KEY AUTO_INCREMENT,
start_date date NOT NULL,
end_date date NOT NULL,
sed int(11) NOT NULL,
FOREIGN KEY (sed) REFERENCES second(sed),
fid int(11) NOT NULL,
FOREIGN KEY (fid) REFERENCES first(fid)
);
//As you can see above, I want to create a single query to query all data at the samee time i.e
//All table from third table depend on first and second table, but the second table have column firstname and the first table has the p_name column
//I want
SELECT second.*, third.* FROM second INNER JOIN third ON third.sed = second.sed
SELECT second.*, fourth.* FROM second INNER JOIN fourth ON fourth.sed = second.sed
SELECT second.*, fifth.* FROM second INNER JOIN fifth ON fifth.sed = second.sed
SELECT second.*, sixth.* FROM second INNER JOIN sixth ON sixth.sed = second.sed
....WHERE fid = 1;
I want to combine these queries into a single query ie, $newqueries = '.....';
The concept
The second table is used to carry all details, ie student details, but the third to sixth tables are tables with few different details but they took all other details from the second table, ie a student can be a chairman, secretary and vice secretary but not all students so that I classified them in third to sixth table. The first table used to keep few info about i.e classes so I want to differentiate chairman etc base on class tables but all of them are students
In short
A chairman, secretary and vice secretary are students but not all students have these role in a class but we have more than one classes, how to differentiate these leaders based on class
in a single query
You can use left join
SELECT second.*, third.*,fourth.*,fifth.*,sixth.* FROM second
LEFT JOIN third ON third.sed = second.sed
LEFT JOIN fourth ON fourth.sed = second.sed
LEFT JOIN fifth ON fifth.sed = second.sed
LEFT JOIN sixth ON sixth.sed = second.sed
WHERE second.fid = 1;
I assume that if student is chairman then there will be an entry of that student in third table. Above query will return null if the student is normal student. You can use CASE Statement if you want role as well. For example,
CASE WHEN third.startdate IS NULL THEN '' ELSE 'Chairman' END

What sql statement can I write to get all the linking tracks to an album

I'm trying to think of an SQL statement I can write up in MySQL in which I can get all the tracks included inside an album. The way I have it set up is Album_id which is the primary key to my album table is linked inside the tracks table in the form of a foreign key. That way each track row is linked to an album in the album table.
I'll further detail below the layout of my tables:
tbl_Albums
As you can see I have the Album_id as the primary key and it's auto_incremented so the id will automatically update when a new row is entered.
CREATE TABLE `tbl_Albums` (
`Album_id` int(11) NOT NULL auto_increment,
`Album_Name` varchar(32) NOT NULL,
`Number_Of_Tracks` int(11) NOT NULL,
`Genre` varchar(32) NOT NULL,
`Artist_id` int(11) NOT NULL,
PRIMARY KEY (`Album_id`),
KEY `Artist_id` (`Artist_id`),
CONSTRAINT `tbl_Albums_ibfk_2`
FOREIGN KEY (`Artist_id`) REFERENCES `tbl_Artist` (`Artist_id`))
tbl_Tracks
Inside the tracks table I set a foreign key with album_id, so I link the tracks to a specific album.
CREATE TABLE `tbl_Tracks` (
`Track_id` int(11) NOT NULL auto_increment,
`Track_Name` varchar(32) NOT NULL,
`Length` time NOT NULL,
`Artist_id` int(11) NOT NULL,
`Album_id` int(11) NOT NULL,
PRIMARY KEY (`Track_id`),
KEY `Artist_id` (`Artist_id`),
KEY `Album_id` (`Album_id`),
CONSTRAINT `tbl_Tracks_ibfk_1`
FOREIGN KEY (`Artist_id`) REFERENCES `tbl_Artist` (`Artist_id`),
CONSTRAINT `tbl_Tracks_ibfk_2`
FOREIGN KEY (`Album_id`) REFERENCES `tbl_Albums` (`Album_id`))
I have the tables linked properly, but I'm trying to think of an MySQL statement that can allow me to show all the tracks linked to a specific album and have come up empty so far. I'm then trying to implement the code into a php form for a user to use to list out the tracks
Any help would be greatly appreciated.
SELECT tbl_Albums.Album_id, tbl_Albums.Album_Name, tbl_Tracks.Track_id, tbl_Tracks.Track_Name, tbl_Tracks.Album_id
FROM tbl_Albums
INNER JOIN tbl_Tracks ON tbl_Albums.Album_id = tbl_Tracks.Album_id WHERE
`tbl_Albums`.`Album_Name`='Your album name'
ORDER BY
`tbl_Tracks`.`Track_id`;
SELECT
`t2`.*
FROM
`tbl_Albums` `t1`
INNER JOIN
`tbl_Tracks` `t2`
ON
`t2`.`Album_id`=`t1`.`Album_id`
WHERE
`t1`.`Album_Name`='Name of Your album'
ORDER BY
`t2`.`Track_id`;
I don't know if I understand your question correct, but a simple select should do the trick?
If you know the album id, for instance 5:
SELECT * FROM `tbl_Tracks` WHERE `Album_id` = 5;
If you know the album name:
SELECT `t`.* FROM `tbl_Tracks` AS `t`
LEFT JOIN `tbl_Albums` AS `a` ON `a`.`Album_id` = `t`.`Album_id`
WHERE `a`.`Album_Name` = 'Thriller';

delete in adjacency table

I have an adjacency table with parent and child elements and when I delete my parent element I would like to delete all his child.
My table:
id name parent
1 Name1 null
2 SubName1 1
When I'm trying to delete row with id=1 I would like to delete and id=2
How can I do this?
My table:
CREATE TABLE IF NOT EXISTS `cats` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(255) NOT NULL,
`parent` int(11) DEFAULT NULL,
PRIMARY KEY (`id`),
KEY `parent` (`parent`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=1;
Foreign keys could be the solution.
How you create them is dependent on your used Database.
At foreign keys there is a primary key defined which is like a "parent", if the parent gets deleted the childs get deleted to if you define it.

Selecting data and joining fields

I have two tables, one is "categories" and "foods".
The categories table has two main filds:
category_id
category_slug
The "category_slug" is the value for friendly urls.
The foods table I have a field called "category_id" which is filled with the category id.
What happens is that, as I'm working with friendly urls, I don't have the id of the category, I only have the slug.
What I need to do is: Convert "slug" by "id" and look at the table foods and get all the food in that category.
It's a little hard to explain, but I think you understood.
CREATE TABLE IF NOT EXISTS `categories` (
`category_id` int(11) NOT NULL AUTO_INCREMENT,
`category_name` varchar(255) NOT NULL,
`category_slug` varchar(255) NOT NULL,
PRIMARY KEY (`category_id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=1;
CREATE TABLE IF NOT EXISTS `foods` (
`food_id` int(11) NOT NULL AUTO_INCREMENT,
`food_name` varchar(255) NOT NULL,
`category_id` int(11) NOT NULL,
PRIMARY KEY (`food_id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=1 ;
It's a simple inner join:
SELECT food_name
FROM foods
JOIN categories
USING (category_id)
WHERE category_slug = :slug

Finds related data from mysql table

These are the two table structure of my db
-- Table structure for table `gf_actor`
CREATE TABLE IF NOT EXISTS `gf_actor` (
`actor_id` bigint(20) NOT NULL auto_increment,
`actor_name` varchar(100) default NULL,
PRIMARY KEY (`actor_id`),
UNIQUE KEY `actor_name` (`actor_name`)
) ENGINE=MyISAM;
-- Table structure for table `gf_film_actor`
CREATE TABLE IF NOT EXISTS `gf_film_actor` (
`film_id` int(20) NOT NULL,
`actor_id` int(20) NOT NULL,
KEY `film_id` (`film_id`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1;
So i need a query which fetches five related actors name and id from gf_actor table who is having acted in movies which was performed by the actor_id lets say actor_id=1 and movies must be different that means five related actors must be acted in different movies with the actor_id=1
Try this
select ga.actor_id, actor_name from gf_actor ga inner join gf_film_actor gf on ga.actor_id = gf.actor_id where gf.film_id in (select gf1.film_id from gf_film_actor gf1 where gf1.actor_id=1) AND gf.actor_id != 1 LIMIT 5
You have wrong table structure. It should be like:
CREATE TABLE IF NOT EXISTS `gf_actor` (
`actor_id` bigint(20) NOT NULL auto_increment,
`actor_name` varchar(100) default NULL,
PRIMARY KEY (`actor_id`),
UNIQUE KEY `actor_name` (`actor_name`)
) ENGINE=MyISAM;
CREATE TABLE IF NOT EXISTS `gf_film` (
`film_id` int(20) NOT NULL,
`performed_by_actor_id` bigint(20) NOT NULL,
KEY `film_id` (`film_id`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1;
CREATE TABLE IF NOT EXISTS `gf_film_actor` (
`film_id` int(20) NOT NULL,
`actor_id` bigint(20) NOT NULL,
KEY `film_actor_id` (`film_id`, `actor_id`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1;
And now you can create your query like this:
SELECT a.*
FROM `gf_film` AS f
LEFT JOIN `gf_film_actor` AS fa ON f.`film_id` = fa.`film_id`
LEFT JOIN `gf_actor` AS a ON fa.`actor_id` = a.`actor_id`
WHERE f.`performed_by_actor_id` = 1
LIMIT 0, 5;

Categories