2009-02-08 4 views

Répondre

17

Si possible, utilisez le module Ruby DBI, et au lieu d'essayer de citer vos chaînes, utilisez paramétrés préparé les requêtes, comme ceci:

dbh = DBI.connect("DBI:Mysql:test:localhost", "testuser", "testpass") 
sth = dbh.prepare("INSERT INTO people (id, name, height) VALUES(?, ?, ?)") 
File.open("people.txt", "r") do |f| 
    f.each_line do |line| 
    name, height = line.chomp.split("\t") 
    sth.execute(nil, name, height) 
    end 
end 

Citation seront traitées correctement pour vous, et les injections sera chose du passé.

Édition: Notez que cet exemple montre nil étant passé comme premier paramètre à exécuter(). Cela correspond au premier? dans la requête, et est traduit en "NULL" par le module DBI. Les autres paramètres sont également correctement cités et insérés dans la requête.

+0

Pourquoi même insérer un champ id? Avec un design normal, cela serait automatiquement incrémenté. –

+0

Ce n'est qu'un exemple. Mais notez que le premier paramètre à execute() est simplement nul, et le paramètre correspondant dans la requête (le premier point d'interrogation) est pour id. "id" est inséré comme NULL dans cet exemple. – greyfade

+0

Je voulais connaître la même chose que l'OP, mais je voulais juste écrire des instructions SQL dans un fichier, donc je suppose que les instructions préparées sont hors de la table alors? Pourrais-je (ab) utiliser .inspect pour échapper des chaînes? – Jan

3

Vous n'avez pas besoin d'utiliser des rails, vous pouvez juste require 'activerecord' et l'utiliser comme vous le feriez dans les rails (définir les modèles et les utiliser). Ce que vous faites, c'est juste réinventer la roue.

3

Écrivez une fonction wee pour citer des chaînes. Je pense que Rails utilise juste quelque chose comme ceci:

def quote_string(v) 
    v.to_s.gsub(/\\/, '\&\&').gsub(/'/, "''") 
end 
+0

Voir la réponse de greyfade. Ou Andy Lester. C'est juste une mauvaise idée. –

+4

Parfois, vous travaillez sur un script de migration unique et n'avez pas de gemmes supplémentaires installées (pas de rails ou dbi) et quand cela arrive c'est une solution efficace. Dans presque toutes les autres situations, vous devriez utiliser des déclarations préparées bien sûr. –

Questions connexes