Какие инструменты C # существуют для запуска, постановки в очередь, определения приоритетов зависимых задач - PullRequest
10 голосов
/ 03 февраля 2012

У меня есть приложение-служба C #, которое взаимодействует с базой данных. Недавно он был перенесен с .NET 2.0 на .NET 4.0, поэтому мы можем использовать множество новых инструментов.

Я ищу указатели на подходы к программированию или инструменты / библиотеки для обработки определения задач, настройки задач, от которых они зависят, постановки в очередь, определения приоритетов, отмены и т. Д.

Существуют различные виды услуг:

  • Данные (для получения и обновления)
  • Расчет (заполните некоторую таблицу с результатами расчета по данным)
  • Отчетность

Эти службы часто зависят друг от друга и запускаются по требованию, т. Е. Задача Отчетность , вероятно, будет содержать код, такой как

if (IsSomeDependentCalculationRequired())
    PerformDependentCalculation();  // which may trigger further calculations
GenerateRequestedReport();

Кроме того, любая модификация Data может устанавливать флаг Required для некоторых служб Calculation или Reporting (так что отчет может быть устарела, пока не закончила генерировать). Продолжительность задач варьируется от нескольких секунд до пары минут и выполняется внутри транзакций.

До сих пор это работало нормально, но плохо масштабируется. Существуют фундаментальные проблемы проектирования, и я хочу переписать эту часть кода. Например, если два пользователя запрашивают один и тот же отчет в одинаковое время, зависимые задачи будут выполнены дважды. Кроме того, в настоящее время нет способа отменить выполняемую задачу. Трудно поддерживать зависимые задачи и т. Д.

Я НЕ ищу предложений по внедрению исправления. Скорее я ищу указатели на то, какие инструменты / библиотеки я бы использовал для такого рода требований, если бы я начинал с .NET 4 с нуля. Будет ли это хорошим кандидатом для Windows Workflow ? Для этого Фьючерсы ? Есть ли какие-либо другие библиотеки, на которые мне следует обратить внимание, книги или публикации в блогах, которые я должен прочитать?

Редактировать: А как насчет Rx Reactive Extensions ?

Ответы [ 6 ]

4 голосов
/ 06 февраля 2012

Я бы попытался использовать пакет конечного автомата без состояний для моделирования рабочего процесса. Использование пакета обеспечит согласованный способ улучшения состояния рабочего процесса между различными службами. Каждый из ваших сервисов будет содержать внутреннюю реализацию машины состояний и предоставлять методы для ее продвижения. Без сохранения состояния будет ответственным за инициирование действий, основанных на состоянии рабочего процесса, и заставит вас явно настроить различные состояния, в которых он может находиться - это будет особенно полезно для обслуживания и, вероятно, поможет вам лучше понять домен. 1003 *

4 голосов
/ 06 февраля 2012

Я не думаю, что ваши требования вписываются ни в одну из встроенных вещей. Ваши требования слишком специфичны для этого.

Я бы порекомендовал вам построить инфраструктуру очередей задач вокруг базы данных SQL. Ваши задачи выполняются довольно долго (в секундах), поэтому вам не требуется особенно высокая пропускная способность в планировщике задач. Это означает, что вы не столкнетесь с проблемами производительности. На самом деле это будет довольно управляемая задача с точки зрения программирования.

Вероятно, вам следует создать службу Windows или какой-либо другой процесс, который постоянно опрашивает базу данных на предмет новых задач или запросов. Этот сервис может затем применять произвольные правила для запрошенных задач. Например, он может обнаружить, что задача отчетности уже запущена, и не запланировать новое вычисление.

Мое главное - ваши требования настолько специфичны, что вам нужно использовать код C # для их кодирования. Вы не можете сделать существующий инструмент соответствующим вашим потребностям. Вам нужна полнота Тьюринга языка программирования, чтобы сделать это самостоятельно.

Редактировать: Вам, вероятно, следует отделить запрос-задачу от выполнения-задачи. Это позволяет нескольким сторонам запрашивать обновление некоторых отчетов, в то же время выполняется только одно фактическое вычисление. Как только это единственное вычисление завершено, все задачи-задачи помечаются как выполненные. Когда запрос отменен, выполнение не должно быть отменено. Только когда последний запрос отменен, выполнение задачи также отменяется.

Редактировать 2: я не думаю, что рабочие процессы являются решением. Рабочие процессы обычно работают отдельно друг от друга. Но ты не хочешь этого. Вы хотите иметь правила, которые охватывают несколько задач / рабочих процессов. Вы будете работать против системы с моделью, основанной на рабочем процессе.

Редактировать 3: Несколько слов о TPL (Task Parallel Library). Вы упомянули это («Фьючерс»). Если вы хотите получить вдохновение о том, как задачи могут работать вместе, как могут создаваться зависимости и как составляются задачи, посмотрите на библиотеку параллельных задач (в частности, классы Task и TaskFactory). Вы найдете несколько хороших шаблонов дизайна, потому что он очень хорошо разработан. Вот как вы моделируете последовательность задач: Вы вызываете Task.ContinueWith, который зарегистрирует функцию продолжения как новую задачу. Вот как вы моделируете зависимости: TaskFactory.WhenAll (Task []) запускает задачу, которая запускается только после завершения всех входных задач.

НО: сам TPL, вероятно, не очень подходит для вас, потому что его задача не может быть сохранена на диск. Когда вы перезагружаете свой сервер или внедряете новый код, все существующие задачи отменяются, и процесс прерывается. Это может быть недопустимым. Пожалуйста, просто используйте TPL в качестве вдохновения. Узнайте из этого, что такое «задача / будущее» и как их можно составить. Затем реализуйте свою собственную форму задач.

Помогает ли это?

3 голосов
/ 06 февраля 2012

Если вы хотите решить эту фундаментальную проблему правильно и масштабируемым образом, вы, вероятно, должны выглядеть как стиль архитектуры SOA. Ваши службы будут получать команды и генерировать события, которые вы сможете обработать, чтобы реагировать на факты, происходящие в вашей системе.

И да, для этого есть инструменты. Например, NServiceBus - замечательный инструмент для построения систем SOA.

1 голос
/ 12 февраля 2012

Если я вас правильно понял, вы хотите кешировать сгенерированные отчеты и больше не работать.Как отмечали другие комментаторы, это можно изящно решить с помощью нескольких очередей «производитель / потребитель» и некоторых кэшей.Сначала вы ставите в очередь свой запрос на отчет.Основываясь на параметрах формирования отчета, вы можете сначала проверить кэш, если ранее созданный отчет уже доступен, и просто вернуть его.Если из-за изменений в базе данных отчет устарел, вам нужно позаботиться о том, чтобы кэш был надежно аннулирован.

Теперь, если отчет еще не был сгенерирован, вам нужно запланировать создание отчета.Планировщик отчетов должен проверить, генерируется ли уже тот же отчет.Если да, зарегистрируйте событие, чтобы уведомить вас о его завершении и вернуть отчет после его завершения.Убедитесь, что у вас нет доступа к данным через уровень кэширования, поскольку он может привести к гонкам (создается отчет, данные изменяются, и готовый отчет немедленно удаляется из кэша, оставляя уведомление о возврате).

Или, если вы хотите запретить возвращать устаревшие отчеты, вы можете позволить слою кэширования стать вашим основным поставщиком данных, который будет генерировать столько отчетов, пока не будет создан один отчет за время, которое не устарело.Но имейте в виду, что если у вас есть постоянные изменения в вашей базе данных, вы можете войти в бесконечный цикл, постоянно генерируя недействительные отчеты, если время генерации отчета больше, чем среднее время между изменениями в вашей базе данных.

Как видите, у вас есть множество вариантов, не говоря уже о .NET, TPL, SQL-сервере.Сначала вам нужно установить свои цели, насколько быстрой / масштабируемой и надежной должна быть ваша система, затем вам нужно выбрать подходящую архитектуру, как описано выше для вашей конкретной проблемной области.Я не могу сделать это для вас, потому что у меня нет вашего полного домена, который знает, что приемлемо, а что нет.

Хитрая часть - это часть передачи между различными очередями с надлежащей гарантией надежности и правильности.В зависимости от ваших конкретных требований к генерации отчетов, вы можете поместить эту логику в облако или использовать один поток, помещая всю работу в соответствующие очереди и работая с ними одновременно, один за другим или между ними.

TPL и SQL-сервер могут помочь в этом, но это всего лишь инструменты.При неправильном использовании из-за недостаточного опыта работы с одним или другим может оказаться, что другой подход (например, использование только в очередях памяти и постоянных отчетах в файловой системе) лучше подходит для вашей проблемы.

Исходя из моего нынешнего понимания, я бы не стал использовать сервер SQL для неправильного использования его в качестве кэша, но если вам нужна база данных, я бы использовал что-то вроде RavenDB или RaportDB , которые выглядятстабильный и гораздо более легкий, по сравнению с полноценным SQL-сервером.

Но если у вас уже работает SQL-сервер, продолжайте и используйте его.

1 голос
/ 09 февраля 2012

Вы можете использовать агент данных SQL для запуска запросов SQL через определенный интервал времени. Вы должны написать приложение самостоятельно, как оно выглядит. Напишите, как долго работающая программа, которая проверяет время и что-то делает. Я не думаю, что есть четкие инструменты для того, чтобы делать то, что вы пытаетесь сделать. Do C # приложение, сервис WCF. автоматизация данных может быть выполнена в самом sql.

0 голосов
/ 13 февраля 2012

Я не уверен, правильно ли я вас понял, но вы, возможно, захотите взглянуть на JAMS Scheduler: http://www.jamsscheduler.com/. Это несвободная, но очень хорошая система для планирования зависимых задач и составления отчетов.Я успешно использовал его в моей предыдущей компании.Он написан на .NET, и для него есть .NET API, так что вы можете создавать свои собственные приложения, взаимодействующие с JAMS.Они также имеют очень хорошую поддержку и готовы внедрять новые функции.

...