Announcement

Collapse
No announcement yet.

MySql Connection Pooling

Collapse
X
  • Filter
  • Time
  • Show
Clear All
new posts

  • MySql Connection Pooling

    Hallo zusammen,

    ich habe ein Problem mit dem ConnectionPooling für MySql. In mehreren unterschiedlichen Threads werden Datenbanktransaktionen durchgeführt. Da aber, wie in ADO.NET üblich, die Verbindungen immer wieder geöffnet und geschlossen werden (sollen), bekomme ich immer eine InvalidOperationException "connection is already open".

    Durch das Pooling hoffe ich dieses Problem zu umgehen.

    Ich habe mal einen kleinen Beispielcode geschrieben, der das Problem verdeutlicht. Gestartet wird die Methode MySqlPoolingTest.

    Code:
    class ThreadTest
            {
    
                public void MySqlPoolingTest()
                {
                    var factory = DbProviderFactories.GetFactory("MySql.Data.MySqlClient");
                    var connection = factory.CreateConnection();
    
                    connection.ConnectionString = "server=localhost;database=test;user id=root;password=;pooling=true;min pool size=3;max pool size=100";
                    connection.Open();
                    connection.Close();
    
                    List<BackgroundWorker> lobw = new List<BackgroundWorker>();
    
                    for (int i = 0; i <= 100; i++)
                    {
                        var bw = new BackgroundWorker();
                        bw.DoWork += new DoWorkEventHandler(bw_DoWork);
                        bw.RunWorkerAsync(connection);
                        lobw.Add(bw);
                    }
    
                    while (1 == 1)
                    {
                        System.Threading.Thread.Sleep(1000);
                    }
    
                }
    
                public void bw_DoWork(object sender, DoWorkEventArgs e)
                {
                    Console.WriteLine("Durchlaufen...");
                    for (int i = 0; i <= 50000; i++)
                    {
    
                        var connection = (DbConnection)e.Argument;
                        connection.Open();
    
                        var command = connection.CreateCommand();
                        var param = command.CreateParameter();
    
                        param.DbType = DbType.String;
                        param.Value = DateTime.UtcNow.ToShortTimeString();
                        param.ParameterName = "p_value";
    
                        command.CommandText = "insert into test(t_value) values(@p_value)";
                        command.Parameters.Add(param);
    
                        command.ExecuteNonQuery();
    
                        System.Threading.Thread.Sleep(100);
    
                        connection.Close();
                        connection.Dispose();
    
                    }
    
                }
    
            }
    Kann sich/mir jemand erklären wieso es trotz der pooling Eigenschaft im Connection String weiterhin zu diesem Fehler kommt?

    Dies sind die Seiten, auf denen ich bereits (ohne Erfolg) nach dem Problem recherchiert habe:
    http://dev.mysql.com/doc/refman/5.0/...n-pooling.html
    http://www.codeproject.com/KB/dotnet...onPooling.aspx

    Vielen Dank schonmal für die Hilfe.

    Gruß

    JenneB
    Zuletzt editiert von JenneB; 20.06.2011, 09:51.

  • #2
    bw.RunWorkerAsync(connection);
    Du verteilst die selbe Connection an n Threads. Somit könnte theoretisch die selbe Connection gleichzeitig verwendet werden. Das ist ein nogo. Die Connection Objekte sind nicht Threadsafe. Erzeuge in jedem Thread ein eigenes Connection Object. Wenn du in jedem Thread dann den gleichen Connectionstring für die Connection Objekte verwendest sollten diese Connections aus dem Pool kommen.

    Comment


    • #3
      Hi,
      vielen Dank für die schnelle Antwort.

      Bedeutet das dann, dass der Connection Pool gar nicht intern von der Connection verwaltet wird, sondern ich mich selbst um das erstellen einer immer neuen Verbindung kümmern muss? In diesem Beispiel sollte ich dann nur den ConnectionString an den Thread übergeben und hier eine neue Verbindung erstellen!?

      Gruß

      JenneB

      Comment


      • #4
        , sondern ich mich selbst um das erstellen einer immer neuen Verbindung kümmern muss?
        Du öffnest und schließt selbst explizit die Verbindung mit Open Close des Connection Objects ja. Besser wäre wenn du gleich einen using Block verwendest um das schließen zu garantieren.

        Pooling heißt nur das durch öffnen versucht wird eine noch vorhandene Verbindung aus dem Pool wiederzuverwenden und nicht zwangsweise eine neue zur Datenbank erzeugt wird. Dem entsprechend bedeutet schließen das zurücklegen der Verbindung in den Pool.

        Das Verteilen des Connectionstrings an die Threads wäre definitiv geschickter

        Comment


        • #5
          Super, vielen Dank! Ich glaub jetzt kann ich das Problem lösen.

          Comment

          Working...
          X