CQRS для потоковых данных - PullRequest
       75

CQRS для потоковых данных

2 голосов
/ 07 марта 2020

Я использую сегрегацию CQRS и очень хорошо работает для транзакционных команд или запроса-ответа от одного узла к удаленному узлу.

У меня есть вариант использования, когда команда будет выдана удаленному узлу, и это приведет к появлению «потоковых» данных (очень похоже на выполнение удаленной команды, когда сервер будет давать нам обновления в текстовом виде по мере их продвижения):

// this is sent from requesting node to remote node to initiate the stream
public class LongRunningCommand: ICommand 
{
    Guid Session { get; set; } // the session ID to use
    string CommandLine {get; set; } // the command the remote note will run
}

Эти данные затем отправляются в виде нескольких пакетов через период времени от удаленного узла до запрашивающего узла:

// this is sent from remote node to requestor in multiple updates over time
public class UpdateProgress: ICommand
{
    Guid Session { get; set; } // possibility to multiplex sessions
    int Sequence { get; set; } // de-dupe/resequencing out of order packets (lower QOS)
    byte[] Payload { get; set; } // the data to be passed to the application
}

Это не команда и не запрос-ответ (так как имеется несколько ответов) - это длительный сеанс Сортировка, но я не уверен, как это вписывается в CQRS.

Как лучше всего это заказать? Может ли мой запрашивающий узел иметь обработчик команд, подобный приведенному ниже (где UpdateProgress - это обрабатываемая «команда»):

public class UpdateProgressCommandHandler : ICommandHandler<UpdateProgress>
{
   public async Task HandleAsync(UpdateProgress message)
   {
      // resequence in handler or chained infrastructure - omitted for brevity
      var window = GetWindowForSession(message.Session);
      var updateFromServer = System.Text.Encoding.UTF8.GetString(message.Payload);
      await window.WriteLine(updateFromServer);
   }
}

Вышеуказанное работает (и я думаю, довольно хорошо), но терминология выглядит немного funky (имя команды UpdateProgress - больше событие, чем команда).

Или мне лучше отказаться от понятия команд / запросов все вместе, и go полной шины событий, и если я это сделал, как бы я обработал начальный запрос, поскольку это не событие, а скорее команда (что не имеет смысла семантически на шине событий, которая имеет дело с событиями, а не с командами или запросами).

Или я попасться только в соглашение об именах? С тех пор, как вы впервые это делаете, оцените передовой опыт для приведенного выше варианта использования.

1 Ответ

3 голосов
/ 07 марта 2020

Я не уверен, правильно ли я вас понял, Command, где он должен общаться с удаленным узлом, не является частью вашего домена. Это не означает, что это не Command, вы все равно можете определить это как Command, но не в своем Domain IMO. Вы можете посмотреть на события интеграции здесь.

Не имея полного понимания вашего домена, вот как вы можете определить свой процесс:

  • Выполнить команду для изменения вашего домена (что-то вроде Status: Pending)

  • Вызов события интеграции из вашего CommandHandler в отдельную рабочую / служебную шину

  • Отдельный работник завершает процесс и затем вызывает другое событие интеграции

  • Ваш работник подписывается на это событие и обновляет соответствующие части вашего домена (например, Status: Completed).

...