0
這裏是'backstory':我有一個mysql存儲過程,最終創建表,然後它應該在proc結束時銷燬表。我這樣做的原因是因爲我想確保如果proc失敗,我不會最終堆疊我創建的這些「臨時」表(他們確實不是臨時表,但我只是打電話他們,因爲他們應該被刪除,當我完成了過程)。無論如何,我的proc的前20行是在下面。mysql stored proc truncate table
-- build dynamic sql to drop any tables that have been around for longer than 30 seconds
SELECT CONCAT('DROP TABLE IF EXISTS ',GROUP_CONCAT(TableName),';')
INTO @dropcmd FROM TempTableTracker WHERE TIMESTAMPDIFF(SECOND, Created, NOW()) > 30;
-- execute dynamic sql
PREPARE dropcmd FROM @dropcmd;
EXECUTE dropcmd;
DEALLOCATE PREPARE dropcmd;
DELETE FROM TempTableTracker WHERE TIMESTAMPDIFF(SECOND, Created, NOW()) > 30;
SET @nextOutTable = concat('Insert into TempTableTracker (Created, TableName) values (NOW(),''',tableName,''')');
PREPARE nextOutTable FROM @nextOutTable;
EXECUTE nextOutTable;
DEALLOCATE PREPARE nextOutTable;
我們把proc目前扔,說 錯誤「不是唯一的表/別名:‘HelperTable088747200147510875390’」 如果我註釋掉下面這段代碼,然後將PROC工作
PREPARE dropcmd FROM @dropcmd;
EXECUTE dropcmd;
DEALLOCATE PREPARE dropcmd;
對我來說真的沒什麼意義。如果我運行了我從sql編輯器中手動註釋掉的代碼(加上select concat語句...不在proc中),那麼它也可以工作。有關可能會發生什麼的任何想法?
這裏是整個PROC - >
DELIMITER ;;
CREATE PROCEDURE "usergroupCalcs"(IN sqlstatement TEXT, IN tableName VARCHAR(1000), IN topLevelParentID INT)
BEGIN
-- build dynamic sql (DROP TABLE tbl1, tbl2...;)
SELECT CONCAT('DROP TABLE IF EXISTS ',GROUP_CONCAT(TableName),';')
INTO @dropcmd FROM TempTableTracker WHERE TIMESTAMPDIFF(SECOND, Created, NOW()) > 30;
-- execute dynamic sql
PREPARE dropcmd FROM @dropcmd;
EXECUTE dropcmd;
DEALLOCATE PREPARE dropcmd;
DELETE FROM TempTableTracker WHERE TIMESTAMPDIFF(SECOND, Created, NOW()) > 30;
SET @nextOutTable = concat('Insert into TempTableTracker (Created, TableName) values (NOW(),''',tableName,''')');
PREPARE nextOutTable FROM @nextOutTable;
EXECUTE nextOutTable;
DEALLOCATE PREPARE nextOutTable;
SET @dropTable = concat('Drop table if exists ',tableName);
PREPARE dropTable FROM @dropTable;
EXECUTE dropTable;
DEALLOCATE PREPARE dropTable;
SET @createTable = concat('CREATE TABLE ',tableName,' (usergroupID INT, storeID INT, parentID INT, INDEX ug (`usergroupID`), INDEX st (`storeID`), INDEX pim (`parentID`)) ENGINE=MEMORY');
PREPARE createTable FROM @createTable;
EXECUTE createTable;
DEALLOCATE PREPARE createTable;
SET @insertIntoTable = concat('INSERT INTO ',tableName, ' ',sqlstatement);
PREPARE insertIntoTable FROM @insertIntoTable;
EXECUTE insertIntoTable;
DEALLOCATE PREPARE insertIntoTable;
SET @repeatStatement = concat('DELETE entry.* FROM ',tableName,' entry LEFT JOIN ',tableName,' parent ON entry.parentID = parent.usergroupID AND entry.storeID = parent.storeID WHERE parent.usergroupID IS NULL AND entry.parentID NOT IN (',topLevelParentID,')');
PREPARE repeatStatement FROM @repeatStatement;
REPEAT
EXECUTE repeatStatement;
UNTIL row_count() = 0 END REPEAT;
DEALLOCATE PREPARE repeatStatement;
SET @dropTempTable = concat('DROP TEMPORARY TABLE IF EXISTS ',tableName,'_out');
PREPARE dropTempTable FROM @dropTempTable;
EXECUTE dropTempTable;
DEALLOCATE PREPARE dropTempTable;
SET @createTempTable = concat('CREATE TEMPORARY TABLE ',tableName,'_out (usergroupID INT, storeID INT, parentID INT, INDEX ug (`usergroupID`), INDEX st (`storeID`), INDEX pim (`parentID`)) ENGINE=MEMORY COLLATE ''utf8_general_ci'' as select * from ',tableName);
PREPARE createTempTable FROM @createTempTable;
EXECUTE createTempTable;
DEALLOCATE PREPARE createTempTable;
SET @dropTempTableTwo = concat('DROP TABLE IF EXISTS ',tableName);
PREPARE dropTempTableTwo FROM @dropTempTableTwo;
EXECUTE dropTempTableTwo;
DEALLOCATE PREPARE dropTempTableTwo;
END;;
DELIMITER ;
你爲什麼不使用'CREATE TEMPORARY TABLE'。當你關閉數據庫連接時,它們會自動被刪除。 – Barmar
DROP TABLE IF EXISTS'爲任何不存在的表生成警告。這聽起來像是把警告轉化爲錯誤。 – Barmar
顯示如何調用存儲過程並顯示create proc行。當然,你將rem的東西做得很好,因爲那是執行字符串的部分。如果您希望我知道您希望我解決問題,請執行「hey @drew there is the edit」...做一個[編輯] – Drew