web-dev-qa-db-fra.com

Comment utiliser DROP TABLE IF EXISTS dans une procédure stockée MySQL

Je veux savoir comment utiliser DROP TABLE IF EXISTS dans une procédure MySQLstored. J'écris une procédure stockée mySQL assez longue qui fera un tas de travail puis chargera une table temporaire avec les résultats. Cependant, j'ai du mal à faire ce travail. 

J'ai vu quelques façons de faire la chose de la table temporaire. Fondamentalement, vous créez la table temporaire, vous travaillez dessus, puis vous la déposez à la fin ... ou vous la supprimez si elle existe, vous la créez, puis vous y effectuez votre travail.

Je préfère la deuxième méthode pour que vous commenciez toujours par un nettoyage, et c'est un contrôle intégré pour l'existence de la table. Cependant, je n'arrive pas à le faire fonctionner:

Voici mes exemples:

Cela marche:

DELIMITER//
    DROP PROCEDURE IF EXISTS pTest//
    CREATE PROCEDURE pTest()
    BEGIN
        CREATE TEMPORARY TABLE tblTest (
            OrderDate varchar(200)
        );
        DROP TEMPORARY TABLE tblTest;
    END//
 DELIMITER ;
CALL pTest();

Cela marche:

DELIMITER//
    DROP PROCEDURE IF EXISTS pTest//
    CREATE PROCEDURE pTest()
    BEGIN
        DROP TEMPORARY TABLE tblTest;
        CREATE TEMPORARY TABLE tblTest (
            OrderDate varchar(200)
        );
    END//
 DELIMITER ;
CALL pTest();

Cela ne veut pas:

DELIMITER//
    DROP PROCEDURE IF EXISTS pTest//
    CREATE PROCEDURE pTest()
    BEGIN
        DROP TEMPORARY TABLE IF EXISTS tblTest;
        CREATE TEMPORARY TABLE tblTest (
            OrderDate varchar(200)
        );
    END//
 DELIMITER ;
CALL pTest();

Les 2 premiers fonctionnent, mais si cette table existe (comme si la procédure ne se terminait pas ou autre), elle se terminerait évidemment par une erreur "La table tblTest n'existe pas". L’exemple qui ne fonctionne pas correspond à ce que je recherche - lâchez la table si elle est là, puis recréez-la afin que je puisse commencer propre.

On a l'impression que c'est le "SI EXISTE" qui fait échouer cette chose J'ai copié du code à partir de toutes sortes de sites qui font des choses très similaires et je ne peux en aucun cas obtenir un "DROP TABLE IF EXISTS ..." pour fonctionner. Déjà.

Serveur de développement: version de mySQL Server: 5.1.47-communityProd Server: version de mySQL Server: 5.0.45-log

Nous ne pouvons pas changer les versions de la base de données (les administrateurs de base de données ne le permettent pas), je suis donc bloqué sur ce que j'ai. Est-ce un bogue dans mySQL ou dans la procédure?

Merci.

15
Coach John

C'est une vieille question, mais elle a été soulevée alors que je cherchais DROP TABLE SI EXISTS.

Votre code non-fonctionnel ne fonctionnait pas sur mon serveur MySQL 5.1.70.

Tout ce que j'avais à faire, c'était d'ajouter un espace entre DELIMITER et // sur la première ligne, et tout s'est bien passé.

Code de travail:

DELIMITER //
    DROP PROCEDURE IF EXISTS pTest//
    CREATE PROCEDURE pTest()
    BEGIN
        DROP TEMPORARY TABLE IF EXISTS tblTest;
        CREATE TEMPORARY TABLE tblTest (
            OrderDate varchar(200)
        );
    END//
DELIMITER ;
16
IvanD

J'ai aussi eu le même problème. Il semble que MySQL n'aime pas vérifier si la table existe sur certaines versions. J'ai d'abord contourné le problème en interrogeant d'abord la base de données et, si j'avais trouvé une table, je l'ai laissée tomber. Utiliser PHP:

$q = @mysql_query("SELECT * FROM `$name`");
if ($q){
    $q = mysql_query("DROP TABLE `$name`");
    if(!$q) die('e: Could not drop the table '.mysql_error());
}

Vous supprimez l'erreur dans la première requête avec le symbole @, vous n'avez donc pas d'erreur d'interférence, puis vous supprimez la table lorsque la requête renvoie false.

2
Abraham Brookes

Je ne sais pas pourquoi cela ne fonctionne pas pour vous, mais vous devriez pouvoir contourner le problème à l'aide d'un gestionnaire de continuation. Si vous mettez l'instruction DROP TABLE dans son propre bloc BEGIN...END, vous pouvez utiliser un gestionnaire de continuation pour ignorer l'erreur si la table n'existe pas.

Essaye ça:

DELIMITER //
    DROP PROCEDURE IF EXISTS pTest //
    CREATE PROCEDURE pTest()
    BEGIN
      BEGIN
        DECLARE CONTINUE HANDLER FOR SQLSTATE '42S02' BEGIN END;
        DROP TEMPORARY TABLE tblTest;
      END;
        CREATE TEMPORARY TABLE tblTest (
            OrderDate varchar(200)
        );
    END //
 DELIMITER ;
CALL pTest();
1
Ike Walker

Je recommande d'ajouter une nouvelle ligne 

SET sql_notes = 0// before DROP PROCEDURE IF EXISTS get_table //

Sinon, l'avertissement sera affiché. PROCEDURE n'existe pas.

0
user5957221