2015-01-12 7 views
6

Ich habe ein Haupt-Python-Skript, das eine Verbindung zu einer MySQL-Datenbank herstellt und einige Datensätze daraus herauszieht. Basierend auf dem zurückgegebenen Ergebnis werden so viele Threads (Klasseninstanzen) gestartet wie viele Datensätze erfasst werden. Jeder Thread sollte zurück zur Datenbank gehen und eine andere Tabelle aktualisieren, indem ein Status-Flag auf einen anderen Status gesetzt wird ("Prozess gestartet").Wie man MySQL-Verbindung (en) mit Python Multithreading behandelt

das ich versucht zu erreichen:

1.) Führen Sie die Datenbankverbindung zu allen Threads 2.) Öffnen Sie eine neue Datenbankverbindung von jedem Thread

aber keiner von ihnen arbeiteten.

Ich konnte mein Update ohne Probleme in beiden Fällen mit try/except ausführen, aber die MySQL-Tabelle wurde nicht aktualisiert, und kein Fehler wurde generiert. Ich habe in beiden Fällen Commit gemacht.

Meine Frage wäre, wie MySQL-Verbindung (en) in einem solchen Fall zu behandeln?

aktualisiert basierend auf den ersten paar Bemerkungen:

MAIN SCRIPT 
----------- 

#Connecting to DB 
db = MySQLdb.connect(host = db_host, 
         db = db_db, 
         port = db_port, 
         user = db_user, 
         passwd = db_password, 
         charset='utf8') 

# Initiating database cursor 
cur = db.cursor() 

# Fetching records for which I need to initiate a class instance 

cur.execute('SELECT ...') 

for row in cur.fetchall() : 
    # Initiating new instance, appending it to a list and 
    # starting all of them 



CLASS WHICH IS INSTANTIATED 
--------------------------- 

# Connecting to DB again. I also tried to pass connection 
# which has been opened in the main script but it did not 
# work either. 

db = MySQLdb.connect(host = db_host, 
         db = db_db, 
         port = db_port, 
         user = db_user, 
         passwd = db_password, 
         charset='utf8') 

# Initiating database cursor 
cur_class = db.cursor() 
cur.execute('UPDATE ...') 
db.commit() 
+0

schwierig, etwas zu sagen, ohne zu wissen, wie Sie zu Ihrer DB verbinden und wie implementieren Sie das Updates. – Ashalynd

+0

Ich verstehe Ihre Frage nicht vollständig. Arbeitet der einfachste Fall, wie Single-Thread-Python mit mysql verbinden und eine Tabelle aktualisieren? – qqibrow

+0

@Ashalynd Danke, dass du dir die Zeit genommen hast! Und tut mir leid, aber ich war AFK. Ich habe meine Frage mit einem Code-Snipet aus meinen Haupt- und Klassencodes aktualisiert. Auf diese Weise initiiere ich Instanzen und öffne Datenbankverbindungen. Ich habe versucht, Fehler beim Öffnen der Verbindung und Ausführen der Abfrage von Instanz mit try/except ohne Glück zu fangen. – g0m3z

Antwort

3

Es scheint, dass es kein Problem mit meinem Code aber mit meiner MySQL-Version gibt. Ich verwende MySQL Standard Community Edition und auf der Grundlage der offiziellen Dokumentation here:

Der Thread-Pool-Plugin ist eine kommerzielle Funktion. Es ist nicht in MySQL-Community-Distributionen enthalten.

Ich bin dabei, auf MariaDB zu aktualisieren, um dieses Problem zu lösen.

9

Hier ist ein Beispiel in Python mit Multithreading Deal mysql, ich weiß nicht, Tisch und Daten, so, nur den Code ändern kann hilfe:

import threading 
import time 
import MySQLdb 

Num_Of_threads = 5 

class myThread(threading.Thread): 

    def __init__(self, conn, cur, data_to_deal): 
     threading.Thread.__init__(self) 
     self.threadID = threadID 
     self.conn = conn 
     self.cur = cur 
     self.data_to_deal 

    def run(self): 

     # add your sql 
     sql = 'insert into table id values ({0});' 
     for i in self.data_to_deal: 
      self.cur.execute(sql.format(i)) 
      self.conn.commit() 

threads = [] 
data_list = [1,2,3,4,5] 

for i in range(Num_Of_threads): 
    conn = MySQLdb.connect(host='localhost',user='root',passwd='',db='') 
    cur = conn.cursor() 
    new_thread = myThread(conn, cur, data_list[i]) 

for th in threads: 
    th.start() 

for t in threads: 
    t.join() 
+0

Entschuldigung für meine späte Antwort. In Ihrem obigen Beispiel habe ich meine Klasse und mein Hauptscript in zwei verschiedenen Dateien. Das sollte kein Problem sein, denke ich. Eine andere Sache, die ich anders mache, ist, dass ich meine data_list nicht an meinen Thread weitergebe, weil ich meinen Thread brauche, um die Daten aus meiner Datenbank im laufenden Betrieb abzufragen. Also was ich mache ist: 1.) Öffnen Sie eine Datenbankverbindung (Hauptskript) 2.) Abfragen Sie Datensätze (Hauptskript) 3.) Initiieren Sie so viele Klasseninstanzen wie viele Datensätze, die ich habe (Hauptskript) 4.) Versuchen Sie, einen Tabellendatensatz in der DB von jeder Instanz (Klasseninstanz) zu aktualisieren. – g0m3z

1

Sieht aus wie mysql 5.7 Multithreading unterstützt.

Wie Sie zuvor versucht haben - unbedingt sicherstellen, dass die Verbindung innerhalb des def Worker() übergeben wird. die Verbindungen definiert, wurde global mein Fehler

Beispielcode Hier ist die 10 Datensätze über 5 Fäden druckt, 5-mal

import MySQLdb 
import threading 


def write_good_proxies():  
    local_db = MySQLdb.connect("localhost","username","PassW","DB", port=3306) 
    local_cursor = local_db.cursor (MySQLdb.cursors.DictCursor) 
    sql_select = 'select http from zproxies where update_time is null order by rand() limit 10' 
    local_cursor.execute(sql_select) 
    records = local_cursor.fetchall() 
    id_list = [f['http'] for f in records] 
    print id_list 
def worker(): 
    x=0 
    while x< 5: 
     x = x+1 
     write_good_proxies() 

threads = [] 


for i in range(5): 
    print i 
    t = threading.Thread(target=worker) 
    threads.append(t) 
    t.start() 
Verwandte Themen