CakePHP 3: Truncate a table - orm

How can I truncate a table with CakePHP 3.x
I get the truncate query by this:
$this->Coupons->schema()->truncateSql($this->Coupons->connection());
but what is the best practice to execute it

This code working well, thanks to #ndm for his comment that helped the answer to be better.
//In Coupons Controller
$this->Coupons->connection()->transactional(function ($conn) {
$sqls = $this->Coupons->schema()->truncateSql($this->Coupons->connection());
foreach ($sqls as $sql) {
$this->Coupons->connection()->execute($sql)->execute();
}
});

In CakePHP4 you can use the following code to truncate a table:
$table = $this->Coupons;
$sqls = $table->getSchema()->truncateSql($table->getConnection());
foreach ($sqls as $sql) {
$table->getConnection()->execute($sql)->execute();
}

I tested following and it's worked:
$connection = $this->Coupons->getConnection();
$connection->query('TRUNCATE coupons');
Reference: https://book.cakephp.org/4/en/orm/database-basics.html#executing-queries
Read more here: https://book.cakephp.org/4/en/orm/database-basics.html#using-transactions

Related

Truncate all tables before running seed files with Phinx

So, I have been creating migrations using Phinx. I want to be able to truncate all the tables(148 tables) before running the seed files. I am thinking about just creating a seed file that will be ran first and then it will truncate all the tables. The catch is that I don't want to have to ever change this file if we add more tables. How would I go about doing this. Maybe doing a Show tables and then looping through them, but not exactly sure how to do that. Any help would be great! This is what I have so far.
<?php
use Phinx\Seed\AbstractSeed;
class BonusRuleTypesSeeder extends AbstractSeed
{
public function run()
{
$this->execute('SET foreign_key_checks=0');
// some code here
$this->execute('SET foreign_key_checks=1');
}
}
If you have a migrations table, then this will truncate that table as well. This would work.
$this->execute('SET foreign_key_checks=0');
foreach($tables as $table){
$table = $table["Tables_in_".$database];
if ($table != $config->getProperty(['phinx', 'default_migration_table'])){
$sql = "TRUNCATE TABLE ".$table;
$this->execute($sql);
}
}
Here is the answer
$config = new Config(__DIR__.'/../../config/default.ini',true);
$host = $config->getProperty(['db', 'host']);
$database = $config->getProperty(['db', 'name']);
$username = $config->getProperty(['db', 'username']);
$password = $config->getProperty(['db', 'password']);
$mysqli = new mysqli($host, $username, $password, $database);
$query = "Show tables";
$tables = $mysqli->query($query);
$tables->fetch_all();
$mysqli->close();
$this->execute('SET foreign_key_checks=0');
foreach($tables as $table){
$table = $table["Tables_in_".$database];
$sql = "TRUNCATE TABLE ".$table;
$this->execute($sql);
}
$this->execute('SET foreign_key_checks=1');

Customise zf2 join tables to single table to get arrays

Hi I have a working public function that joins 3 tables to get values for 2 arrays. Now the process only has one table (table2) which contains all the colvalues required for the arrays.
I have tried everything I know to customise this so only table2 is used to get the arrays, but I just get blank results.
Can anyone point to me an example of something similar which takes values from a single table to get 2 separate arrays. I inherited this so I do not know what the thinking behind it was.
thank you in advance.
public function get2ColArray($condition)
{
$sql =new Sql($this->adapter);
$select = $sql->select();
$select->from('table1');
$select->columns(array('colval1'));
$select->join('table2', "table1.colval2 = table2.colval3", array('colval4'), 'inner');
$select->join('table3', "tabl1.colval1= table3.colval1", array('colval5'), 'left');
if(!empty($condition['in']))
foreach ($condition['in'] as $key=>$val) {
$select->where->in($key,$val);
}
if(!empty($condition['where']))
$select->where($condition['where']);
$select->order(array('table2.colval4'=>'ASC'));
$statement = $sql->prepareStatementForSqlObject($select);
$sql_result = $statement->execute();
if ($sql_result->count() > 0) {
$results = new ResultSet();
$data = $results->initialize($sql_result);
}
return $data;
}
Got it, its abit blunt but works, thanks ...
$select->from('table2');
$select->columns(array('colval1','colval_whateveryouwantaslongasitsintable2',));

Codeigniter ActiveRecord update SQL error

I am working on CI 2.1.3 and encountering the following problem. What am I doing wrong here? Is there any reading or knowledge I need to do or know.
Codeigniter ActiveReocrd Update syntax
$data['spun'] = TRUE;
$this->db->update('registered', $data,
"registered_id = $registration['registered_id']");
what I expected
UPDATE `registered` SET `spun` = 1 WHERE `registered_id` = 1
what CI generated
UPDATE `registered` SET `spun` = 1 WHERE `id` = 1
DB table (in bracketing notation)
registered(registered_id, registered_name, ..., spun);
Edit 1
I also tried the following, but CI give the same SQL.
$this->db->update('registered', $data,
array('registered_id' => $registration['registered_id']));
I think the solution is very easy. You can simply do this:
$data['spun'] = TRUE;
$this->db->update('registered', $data,
array('registered_id' => $registration['registered_id']);
Based on Code Igniter documentation:
http://codeigniter.com/user_guide/database/active_record.html#update
you should use:
$data['spun'] = TRUE;
$this->db->where('registered_id', $registration['registered_id']);
$this->db->update('registered', $data);

ZEND_DB_TABLE_ABSTRACT methods SQL INJECTION

Is it possible for to sql inject a ZEND_DB_TABLE_ABSTRACT method?
like for example
$this->insert();
edit for a more clearer explanation
Post values are :
'username' = 'admin';
'password' = '1;Drop table users;'
Here is the insert statement in the controller:
public function InsertAction() {
$postValues = $this->_request->getPost();
$usersTable = new Application_Models_DbTable_Users();
$username = $postValues['username'];
$password = $postValues['password'];
$data = array('username'=>$username,'password'=>$password);
$users->insert($data);
}
Yes, it is possible, but in the usual uses of insert() it's not probable. Unless you are using Zend_Db_Expr, you should be safe, because insert() uses prepared statements.
See this post from Bill Karwin for other methods and details.
Check the manual of Zend Zend_Db_Table
It will show you who you can create your own method.

How do I bulk Insert using SubSonic?

I have something that looks like this
foreach (var user in NewUsers)
{
var dbUser = new User {FirstName = user.FirstName};
dbUser.Save();
}
That is too many inserts into the database. Can I do something like?
User.BulkInsert(NewUsers);
Thanks.
Check out the Batch Query - this should solve the issue
http://www.subsonicproject.com/docs/BatchQuery