Codeigniter delete record where some select query? - php

In codeigniter I want to delete record from a table. But at the same time I want to remove a record from another table which having foreign key to that record.
Is there any possible way to do this using codeigniter?
1st delete query
$this->db->where('id',$id);
$this->db->delete('category_info');
1st table
id | description | image
2nd table
id | category_id | parent_category

Instead of having PHP doing the heavy work, you can do this straight from MYSQL with a trigger. This will trigger after a deletion.
CREATE TRIGGER delete_trigger_tbl_2 AFTER DELETE ON category_info
FOR EACH ROW
BEGIN
DELETE FROM tbl_2
WHERE tbl_2.id = old.id;
-- Or category_id, not clear in your question.
END

Related

PHP add first table column id to another table column id

There are 2 Table in the Database.
tbl_second_category
tbl_third_category
I'm already passing
col_first_category_id
from
table1 tbl_second_category
to
Table2 tbl_third_category col_second_category_id
using select box control
You can see id 13 in both the Tables
when I'm passing above id, at the same time how can I pass col_second_category_id from Table1
tbl_second_category to column col_for_delete_row Table2 tbl_third_category.
Thank you
then use trigger, you may need more then one for update and delete events... for example:
CREATE TRIGGER trigger_name AFTER INSERT ON tbl_second_category
FOR EACH ROW
UPDATE tbl_third_category
SET col_for_delete_row = NEW.col_second_category_id
WHERE col_second_category_id = NEW.col_first_category_id;

Reset id values in existing table (without deleting records)

let me say that I have a table in my phpmyadmin that looks like this:
id | name
1 | John
2 | Dave
5 | Tiffany
As U can see by id - i've deleted 2 records between 'Dave' and 'Tiffany'.
My question:
Is there a way to 'reset' or repopulate the id so that the 'Tiffany' record would have id=3 and so on ?
The only way to start counting id again I've found is a 'TRUNCATE' but it deletes all my records which I dont want
I do this sometimes when I create a new table and want to get 'clean' ids. If there is no reference to / connection with other table, you can do:
SET #var:=0;
UPDATE `table` SET `id`=(#var:=#var+1);
ALTER TABLE `table` AUTO_INCREMENT = 1;
Do not do this for ids already used in other tables!

Simply move row to another table and back

Is there an easy way to SELECT a row and INSERT it into another table that has exactly the same columns? It needs to reserve the id and be able to move it back later on.
STEPS:
Move entire row to an identical temporary table (with a different name of-course) while using the same id.
Delete the row from old table (I know this, dont worry ;))
Move the row back from the temporary table into the original table, while using the same original id.
Delete row from temporary table.
I know how to do this, but there are probably much better, cleaner and faster ways to achieve this in one or two queries. My main concern is that when the table gets refactored, the query should still do its job without skipping newer columns.
I hope someone can come with a good suggestion :)
Assuming the tables have identical columns, you should be able to just do this:
INSERT INTO newtable SELECT * FROM oldtable WHERE id = somevalue
Here are two alternate ideas I can think of:
Add a BIT or BOOL column to the table that can be updated in order to 'flag' the record one way or another so that you can filter on it in your queries.
Create a table that just lists the ID of the record(s) that you want to flag. Enter a new ID into this field when you want it flagged (replaces the act of deleting and moving to the 2nd table) and remove it when you wish to 'unflag' it (replaces the act of deleting it from the 2nd table and re-adding it to the original table.
Aside from the initial schema change required by option 1, both options will work regardless of any changes to the schema of the original table. If you are trying to avoid maintaining the second table, I'd consider these.
If you do wish to copy to the holding table and delete from the original table, and later copy back to the original table, and delete from the holding table, be sure to wrap those operations into a transaction so that you don't end up with duplicated data or data loss in the event of things not going as planned.
You use CREATE TABLE ... SELECT to create a table and then work with it. This will create a table with columns from SELECT in your case the original table. Then you can delete the rows from original table, move the rows back to the original table using INSERT INTO ... SELECT followed by dropping the temporary table. This way you don't need to maintain two tables and the temporary table will always get the latest columns from the original table.
See mysql manual. Following example copied from manual.
mysql> SELECT * FROM foo;
+---+
| n |
+---+
| 1 |
+---+
mysql> CREATE TABLE bar (m INT) SELECT n FROM foo;
Query OK, 1 row affected (0.02 sec)
Records: 1 Duplicates: 0 Warnings: 0
mysql> SELECT * FROM bar;
+------+---+
| m | n |
+------+---+
| NULL | 1 |
+------+---+
1 row in set (0.00 sec)
So you need something like this
CREATE TABLE bar SELECT * FROM foo WHERE fooColumn = 'whatever';
DELETE FROM foo where fooColumn <> 'whatever';
INSERT INTO foo SELECT * FROM bar;
DROP TABLE bar
if you want to avoid creating and dropping tables too often, just create the temporary table once.
INSERT INTO bar SELECT * FROM foo WHERE fooColumn = 'whatever';
DELETE FROM foo where fooColumn <> 'whatever';
INSERT INTO foo SELECT * FROM bar;
But make sure you keep the temporary and the original table in sync all the time i.e. if you add or drop a column in the original table, make sure that is replicated in the temporary table immediately as INSERT INTO ... SELECT only copies data not schema.
You can do this :
INSERT INTO tbltemp (Select * from table1 where someid=somevalue)
Or you could move the entire table into other one :
INSERT INTO tbltemp (select * from table1);
What ever you do, be careful that the record/records which you need to move/copy must not include any primary key values which are already there in target table.

Delete all foreign key data on delete of primary or vice-a-versa

I have table structure like this:
PrimaryTable -> p_id Here p_id is primary
SecondoryTable -> s_id p_id Here p_id is a foreign key
ThirdTable -> t_id s_id Here s_id is foreign key
FourthTable -> f_id t_id Here t_id is foreign key
So I am deleting one of my p_id from PrimaryTable and want that its SecondoryTable data should also get delete AND ThirdTable data should be deleted with reference to SecondoryTable and FourthTable data should be deleted with reference to ThirdTable
I know i can write Delete query from bottom to top, but how to do for so many levels like this??
I found this but not sure on howto: https://stackoverflow.com/a/9847308/1182021
Because its four level hierarchy i am confused.
EDIT1:
What if I want to delete Primary on Delete of Child
Kindly suggest.
As per OP's request, this is an answer for the case when the user wants to delete the row from the parent table when a row is deleted from the child table. The case for recursively deleting all the children when a parent is deleted is working using MySQL ON DELETE CASCADE option.
The 4 tables would be table1, table2, table3 & table4.
If the user wants to delete a row in table2 and also the corresponding row in table1 (parent of table2) then in PHP:
// t2_delete_row_id is the id of the table 2 row to be deleted
// get the the parent of table2
$sql_get_parent = "select p_id from table2 where s_id = 't2_delete_row_id '";
// execute this query using MySQLi/PDO to get id of the parent row to be deleted
// assuming that id is t1_parent_row_id
// now delete the row from table 2:
// note that because of the foreign key constraints,
// corresponding rows from table3 and table4 would also be deleted
$sql_delete_child = "delete from table2 where s_id = 't2_delete_row_id'";
if (mysqli_query($sql_delete_child)){
// delete the parent row
$sql_delete_parent = "delete from table1 where p_id = 't1_parent_row_id'";
}
this logic can be extended so that on deleting table3 row, corresponding parent(table2) and "grand-parent" (table1) rows would be deleted as well. A bit of recursion might be needed for that case. And this will of course delete the child rows in table4 because of the foreign key constraint.
If you are not able to use FOREIGN KEYS (ie using MyISAM tables) I would create a TRIGGER for this. Example for first one below ... you will need to make one for each table that's cascading.
DELIMITER //
CREATE TRIGGER `pDeleteTrigger` BEFORE DELETE ON `PrimaryTable`
FOR EACH ROW BEGIN
DELETE FROM `SecondoryTable` WHERE NEW.`p_id` = `SecondoryTable`.`p_id`
END
//
DELIMITER ;
I have two approachs in my mind (if your language is Tsql)
1.- Store procedure
The idea is have a procedure "spDelete_PrimaryTable", so that you can delete the registers in the four tables by writinf something in tsql like:
exec spDelete_PrimaryTable
#p_id= 25 /* (25 or watever p_id of primary table you want to delete)*/
(yes you can call it from vb.net or watever you want to.)
the code would be something like:
use [your_database]
CREATE PROCEDURE [dbo].[spDelete_PrimaryTable]
#p_id nvarchar(MAX)
AS
begin
SET NOCOUNT ON;
delete from FourthTable where t_id in (
select ThirdTable.t_id
from ThirdTable inner join SecondoryTable on ThirdTable.s_id = SecondoryTable.s_id
where SecondoryTable.p_id = #p_id
)
go
delete from ThirdTable where s_id in (
select SecondoryTable.s_id
where SecondoryTable.p_id = #p_id
)
go
/*Lol, I forgot to eliminate from the "SecondoryTable" */
delete from SecondoryTable.s_id
where SecondoryTable.p_id = #p_id
go
delete from PrimaryTable where p_id = #p_id
go
END
GO
2.- Triggers
seems like "Christopher Morrissey" have already posted that while i was editing this answer XP

MySQL insert to multiple tables (relational)

tbl_product
Name | Creator | UID | Salerank
tbl_price
Supplier | Price | UID
I want to insert a product and then insert multiple prices into a seperate table. How is it possible to ensure that both tables had the same UID ideally an auto increment field? I will be using PHP alongside MySQL.
Thanks,
J
Make UID an auto_increment primary key on the products table, but just a regular primary key on the prices table (no auto_increment). After you insert itnto products, use the PHP command mysql_insert_id(). This will get the ID generated from the last query, which will be your UID generated on the products table. Assign it a variable and use it in your insert statement on the prices table.
http://php.net/manual/en/function.mysql-insert-id.php
Use a GUID for the UID, or better, insert your products and the insert the prices using e.g. the name of the product (assuming unique) to look up the relevant product UID.

Categories