При попытке выполнить запрос вставки в MySql с помощью Task.Run () выдается следующее исключение: «Не удается подключиться к любому из указанных хостов MySQL». - PullRequest
0 голосов
/ 11 ноября 2018

Вот код:

static void Client_MqttMsgPublishReceived(object sender, MqttMsgPublishEventArgs e) //Event Handler
{
   Time timeToSend = JsonConvert.DeserializeObject<Time>(Encoding.UTF8.GetString(e.Message));

   Task.Run(async () => await SendToMySql(timeToSend));            
}

В методе SendToMySql это в основном вставка, как показано ниже:

private static async Task SendToMySql(Time timeToSend)
{
        try
        {
            var connection = new MySqlConnection(string.Format(configuration["MySql:ConnectionString"], configuration["MySql:DataBaseName"]));
            await connection.OpenAsync();
            string query = "insert into resource_log (resource_value_log, creation_date) values ('" + timeToSend.Message + "',STR_TO_DATE( '" + DateTime.Now + "', '%d/%m/%Y %H:%i:%s'))";
            var cmd = new MySqlCommand(query, connection);
            await cmd.ExecuteReaderAsync();
            await connection.CloseAsync();
        }
        catch (Exception ex)
        {
            Console.WriteLine(ex.Message.ToString());
        }
 } 

Я вызвал этот метод с помощью Task.Run (), потому что я хотел, чтобы он тоже запускался асинхронно при необходимости. Но он выдает следующее исключение:

"Невозможно подключиться к любому из указанных хостов MySQL."

Вот внутреннее исключение:

Истекло время ожидания. Время ожидания истекло до завершения операции или сервер не отвечает.

Некоторые данные фактически были вставлены в MySql.

Я новичок в асинхронном и параллельном программировании, и я написал этот код, но мне интересно, правильно ли это делать асинхронный запрос в MySql. Я сделал это так же, как это, но с MongoDb, и он работал нормально. Надеюсь, вы, ребята, можете мне помочь. Спасибо.

1 Ответ

0 голосов
/ 12 ноября 2018

В Connector / NET (MySql.Data) существует давняя ошибка, из-за которой ни один из Async методов фактически не выполняется асинхронно: ошибка 70111 .

Чтобы исправить это, вы можете переключиться на альтернативную библиотеку ADO.NET MySQL, которая на 100% асинхронна: MySqlConnector на GitHub и NuGet .

Хотя MySqlConnector реализует метод CloseAsync, реализация по умолчанию синхронно возвращает открытое соединение в пул соединений, поэтому я бы рекомендовал пропустить вызов CloseAsync и просто использовать блок using для Dispose соединения когда вы закончите с этим:

using (var connection = new MySqlConnection(string.Format(configuration["MySql:ConnectionString"], configuration["MySql:DataBaseName"])))
{
    await connection.OpenAsync();
    var query = "...";
    using (var cmd = new MySqlCommand(query, connection))
        await cmd.ExecuteReaderAsync();
}
...