运行查询foreach数据库(mysql)

Won*_*and 7 mysql

我正在寻找一种直接的方式来运行我的mysql服务器上托管的所有数据库的查询.

我有一堆Magento安装,我想在所有数据库上截断所有Magento日志表:

  • log_customer
  • log_visitor
  • log_visitor_info
  • log_url
  • log_url_info
  • log_quote
  • report_viewed_product_index
  • report_compared_product_index
  • report_event
  • catalog_compare_item

我觉得在mysql中很容易实现,但我找不到直接的答案/解决方案.

*更新*
根据@Ollie Jones,如果没有商店程序或服务器端语言(PHP或其他),则无法执行此操作

更新1
我选择遵循PHP方法(@samitha)有两个原因:

  1. 商店程序看起来更复杂
  2. 对'information_schema'表的查询非常慢(至少如果你有很多DB/TABLES)

O. *_*nes 12

  SELECT DISTINCT SCHEMA_NAME AS `database`
    FROM information_schema.SCHEMATA
   WHERE  SCHEMA_NAME NOT IN ('information_schema', 'performance_schema', 'mysql')
   ORDER BY SCHEMA_NAME
Run Code Online (Sandbox Code Playgroud)

获取系统中所有非MYSQL数据库的列表.

  SELECT TABLE_SCHEMA AS `database`,
         TABLE_NAME AS `table`
    FROM information_schema.TABLES
   WHERE TABLE_TYPE = 'BASE TABLE'
   ORDER BY TABLE_SCHEMA, TABLE_NAME
Run Code Online (Sandbox Code Playgroud)

获取所有数据库中所有实际表(不包括SYSTEM VIEW,如TABLES表和用户定义的视图)的列表.

然后,您应该在程序中实现逻辑,以确保在截断某些表之前,对于每个数据库,它确实是一个Magento数据库.否则,你可能会成为同事中的一个被鄙视的人.:-)

编辑

这是一个存储过程.

您需要对其进行编辑以完成您需要它做的事情; 特别是,它计算行而不是截断表,并且它不包含正确的日志表列表.(对我来说,发布这样一个极具破坏性的存储过程是不负责任的;你应该自己编辑它来做破坏性的部分.)

DELIMITER $$
DROP PROCEDURE IF EXISTS `zap_magento_logs`$$

CREATE PROCEDURE `zap_magento_logs`()
BEGIN

    -- declare variables for database and table names
    DECLARE dbname VARCHAR(128) DEFAULT '';
    DECLARE tbname VARCHAR(128) DEFAULT '';

    DECLARE done INTEGER DEFAULT 0;

    -- declare cursor for list of log tables
    DECLARE log_table_list CURSOR FOR 
      SELECT TABLE_SCHEMA AS `database`,
             TABLE_NAME AS `table`
        FROM `information_schema`.TABLES
       WHERE TABLE_TYPE = 'BASE TABLE'
         AND TABLE_NAME IN 
         (
            'log_customer',
        'log_visitor',
        'log_visitor_info',
        'log_url',
        'log_url_info',
        'log_quote'
         )
       ORDER BY TABLE_SCHEMA, TABLE_NAME;

    -- declare NOT FOUND handler
        DECLARE CONTINUE HANDLER 
        FOR NOT FOUND SET done = 1;

    OPEN log_table_list;

    log_table: LOOP

        FETCH log_table_list INTO dbname, tbname;

        IF done = 1 THEN
        LEAVE log_table;
        END IF;

        -- create an appropriate text string for a DDL or other SQL statement
        SET @s = CONCAT('SELECT COUNT(*) AS num FROM  ',dbname,'.',tbname);
        PREPARE stmt FROM @s;
        EXECUTE stmt;
        DEALLOCATE PREPARE stmt; 
    END LOOP    log_table;
    CLOSE log_table_list;

END$$

DELIMITER ;
Run Code Online (Sandbox Code Playgroud)

您可以通过发出SQL命令来运行它

  CALL zap_magento_logs();
Run Code Online (Sandbox Code Playgroud)

  • 好吧,这是一个存储过程。我犹豫是否要给你这个,因为它包含你可能不熟悉的多个级别的 MySQL 概念,而且我不相信简单地教人们“魔法咒语”。 (2认同)

Rya*_*ton 7

我不想编写代码来解决这个问题,所以我找到了不同的解决方案。我编写了 SQL 来生成我需要的 SQL。因此,我将以下内容保存到名为 createSomeSQL.sql 的文件中:

SET sql_mode='PIPES_AS_CONCAT';

select 
'truncate table ' || dbs.database || '.someLogTable;'
 as ''
from  (SELECT DISTINCT SCHEMA_NAME AS `database`
         FROM information_schema.SCHEMATA
        WHERE SCHEMA_NAME NOT IN ('information_schema', 'performance_schema', 'mysql', 'test')
        ORDER BY SCHEMA_NAME) as dbs;
Run Code Online (Sandbox Code Playgroud)

您可以将第 4 行中的 SQL 替换为您想要的任何内容。然后我运行此命令来生成我需要的 SQL:

mysql -u root -p < createSomeSQL.sql > sqlToExecute.sql
Run Code Online (Sandbox Code Playgroud)

当然,将“root”替换为您的用户名。现在,文件 sqlToExecute.sql 包含一个脚本,您可以运行它来针对所有数据库执行该 SQL。


und*_*ore 6

PHP的方法是:

$tables = array(
    'log_customer',
    'log_visitor',
    'log_visitor_info',
    'log_url',
    'log_url_info',
    'log_quote',
    'report_viewed_product_index',
    'report_compared_product_index',
    'report_event',
    'catalog_compare_item',
);

$dbh = new PDO('mysql:host=localhost;', 'USERNAME', 'PASSWORD', array(
    PDO::ATTR_PERSISTENT => true
));


$sql = $dbh->query('SHOW DATABASES');
$getAllDbs = $sql->fetchALL(PDO::FETCH_ASSOC);

foreach ($getAllDbs as $DB) {  

        foreach ($tables as $table) {
            $dbh->query('TRUNCATE TABLE ' . $DB['Database'] . '.' . $table);

    };
};
Run Code Online (Sandbox Code Playgroud)