csharp Неправильнаяреализацияблокировок(черезхелперы)
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了csharp Неправильнаяреализацияблокировок(черезхелперы)相关的知识,希望对你有一定的参考价值。
//Данный сниппет предназначен для демонстрации многопоточной работы с БД (добавьте текущий проект в ZennoPoster и запустите в несколько потоков)
string strDBConnString = project.Variables["cfg_db_connstring"].Value;
int intMaxTasks = Convert.ToInt32(project.Variables["cfg_tasks_per_execution"].Value);
//добавляем несколько "заданий" в таблицу db_jobs (при штатной работе фермы эта информация появлялась бы в таблице в результате других процессов)
string strAddTasksQuery = "INSERT INTO db_tasks (profile_id, task_type, post_text, post_image, object) VALUES (1, 'post', 'this is a texxt', 'image1.jpg', 'http://vk.com/supergruppa');" +
"INSERT INTO db_tasks (profile_id, task_type, object) VALUES (2, 'like', 'https://vk.com/wall-2158488_268002');" +
"INSERT INTO db_tasks (profile_id, task_type, object) VALUES (3, 'invite', 'https://vk.com/id139687748');" +
"INSERT INTO db_tasks (profile_id, task_type, object) VALUES (4, 'like', 'https://vk.com/wall-2158488_636329');" +
"INSERT INTO db_tasks (profile_id, task_type, post_text, post_image, object) VALUES (5, 'post', 'text namba tu', 'image2.jpg', 'http://vk.com/goodgruppa');";
ZennoPoster.Db.ExecuteNonQuery(strAddTasksQuery, null, ZennoLab.InterfacesLibrary.Enums.Db.DbProvider.MySqlClient, strDBConnString);
//получаем свободный профиль (со статусом ready), для которого количество "заданий" больше нуля
//блокируем таблицу db_profiles для записи другими потоками
ZennoPoster.Db.ExecuteNonQuery("LOCK TABLES db_profiles WRITE, db_tasks READ;", null, ZennoLab.InterfacesLibrary.Enums.Db.DbProvider.MySqlClient, strDBConnString);
string strProfileQuery = "SELECT db_profiles.id, login, password, db_profiles.status " +
"FROM db_profiles LEFT JOIN db_tasks ON db_profiles.id = db_tasks.profile_id " +
"WHERE db_tasks.status='wait' " +
"GROUP BY login, password, db_profiles.status " +
"HAVING db_profiles.status='ready' AND COUNT(task_type)>0 " +
"ORDER BY COUNT(db_tasks.task_type) DESC LIMIT 1;";
string strProfileQueryResult = ZennoPoster.Db.ExecuteQuery(strProfileQuery, null, ZennoLab.InterfacesLibrary.Enums.Db.DbProvider.MySqlClient, strDBConnString, "|", Environment.NewLine);
if (String.IsNullOrEmpty(strProfileQueryResult)) {
project.SendInfoToLog("Нет незаблокированных профилей с заданиями. Завершаем работу", true);
goto finish;
}
string[] arrProfileParams = strProfileQueryResult.Split('|'); //обратите внимание: в данных таблицы db_profiles не должно быть символа |
string strCurrProfileID = arrProfileParams[0];
string strLogin = arrProfileParams[1];
string strPassword = arrProfileParams[2];
string strCurrProfileStatus = arrProfileParams[3];
project.SendInfoToLog(String.Format("Получили профиль с id: {0} ({1})", strCurrProfileID, strLogin), true);
//сохраняем id текущего профиля в переменной уровня проекта на случай возникновения ошибки (в этом случае по BadEnd ралочим профиль)
project.Variables["str_current_profile"].Value = strCurrProfileID;
//помечаем профиль как "занятый" (busy)
ZennoPoster.Db.ExecuteNonQuery(String.Format("UPDATE db_profiles SET status='busy', last_used=NOW() WHERE id={0};", strCurrProfileID), null, ZennoLab.InterfacesLibrary.Enums.Db.DbProvider.MySqlClient, strDBConnString);
//снимаем блокировку таблицы db_profiles
ZennoPoster.Db.ExecuteNonQuery("UNLOCK TABLES;", null, ZennoLab.InterfacesLibrary.Enums.Db.DbProvider.MySqlClient, strDBConnString);
//цикл "выполнения заданий"
int intCompletedTasks = 0; //количество выполненных заданий
do {
//получаем задание для выполнения
string strTasksQuery = String.Format("SELECT id, task_type, post_text, post_image, object FROM db_tasks WHERE profile_id={0} AND status='wait' LIMIT 1;", strCurrProfileID);
string strTask = ZennoPoster.Db.ExecuteQuery(strTasksQuery, null, ZennoLab.InterfacesLibrary.Enums.Db.DbProvider.MySqlClient, strDBConnString, "|", Environment.NewLine);
if (strTask.Length==0) {
project.SendInfoToLog(String.Format("Для профиля {0} ({1}) успешно выполнено {2} заданий. Больше в БД заданий нет, завершаем работу.", strCurrProfileID, strLogin, intCompletedTasks), true);
break;
}
string[] arrTask = strTask.Split('|'); //обратите внимание, в данных таблицы db_tasks не должно быть символов |
//получаем параметры текущего задания
string strTaskId = arrTask[0];
string strWhatToDo = arrTask[1];
string strText = arrTask[2];
string strImage = arrTask[3];
string strTaskObject = arrTask[4];
project.SendInfoToLog(String.Format("Выполняем задание id {0} ({1}) для профиля с id {2} ({3})", strTaskId, strWhatToDo, strCurrProfileID, strLogin), true);
//запускаем выполнение задания
string strTaskResultMessage = String.Empty;
switch(strWhatToDo) {
case "post":
strTaskResultMessage = project.Context["fnPost"](strTaskObject, strText, strImage);
break;
case "like":
strTaskResultMessage = project.Context["fnLike"](strTaskObject);
break;
case "invite":
strTaskResultMessage = project.Context["fnInvite"](strTaskObject);
break;
}
//анализируем результат выполнение задания
string strTaskResult = String.Empty;
if (strTaskResultMessage.StartsWith("ok:")){
strTaskResult = "success";
}else{
strTaskResult = "error";
}
//помечаем задачу выполненной, сохраняем результат выполнения
ZennoPoster.Db.ExecuteNonQuery(String.Format("UPDATE db_tasks SET status='{0}', status_message='{1}', change_dt=NOW() WHERE id={2};", strTaskResult, strTaskResultMessage, strTaskId), null, ZennoLab.InterfacesLibrary.Enums.Db.DbProvider.MySqlClient, strDBConnString);
if (strTaskResultMessage.Contains("заблокирован")) {
project.SendErrorToLog(String.Format("Профиль с id {0} ({1}) заблокирован. Завершаем работу", strCurrProfileID, strLogin));
//отменяем все задания в базе для данного профиля (в реальности можно переназначать задания на "любой" профиль)
ZennoPoster.Db.ExecuteNonQuery(String.Format("UPDATE db_tasks SET status='cancelled', status_message='profile blocked', change_dt=NOW() WHERE profile_id={0} AND status='wait';", strCurrProfileID), null, ZennoLab.InterfacesLibrary.Enums.Db.DbProvider.MySqlClient, strDBConnString);
strCurrProfileStatus = "blocked"; //меняем статус профиля в переменной на blocked
break; //прерываем цикл выполнения заданий
}
intCompletedTasks++;
} while (intCompletedTasks<intMaxTasks);
//помечаем профиль как "свободный" (ready). блокировка таблицы при этом не требуется
ZennoPoster.Db.ExecuteNonQuery(String.Format("UPDATE db_profiles SET status='{0}', last_used=NOW() WHERE id={1};", strCurrProfileStatus, strCurrProfileID), null, ZennoLab.InterfacesLibrary.Enums.Db.DbProvider.MySqlClient, strDBConnString);
finish:
return "oki";
//ПРИМЕЧАНИЯ:
//1.
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading;
using System.IO;
using System.Text.RegularExpressions;
using ZennoLab.CommandCenter;
using ZennoLab.InterfacesLibrary;
using ZennoLab.InterfacesLibrary.ProjectModel;
using ZennoLab.InterfacesLibrary.ProjectModel.Collections;
using ZennoLab.InterfacesLibrary.ProjectModel.Enums;
using ZennoLab.Macros;
using Global.ZennoExtensions;
using ZennoLab.Emulation;
namespace ZennoLab.OwnCode
{
/// <summary>
/// A simple class of the common code
/// </summary>
public class CommonCode
{
/// <summary>
/// Lock this object to mark part of code for single thread execution
/// </summary>
public static object SyncObject = new object();
// Insert your code here
}
}
以上是关于csharp Неправильнаяреализацияблокировок(черезхелперы)的主要内容,如果未能解决你的问题,请参考以下文章
sql Задание1.ДолжновыполнятьсясиспользованиемMySQL(иприжеланиисPHP)Преобразоватьданныетаблицытакимоб
php WP is_page - правильноеиспользованиеопределениястраницвfunction.php