将课程解释为文字

时间:2017-11-28 13:13:08

标签: c# .net design-patterns

(长期问题道歉)

您好, 我们有一个运行的服务,每15分钟监视一次我们的队列,并将结果输出到许多东西(公司IM,日志,表存储)。我正在寻找一种很好的方法将数据转换为“智能”文本输出到我们的IM。

服务监视3件事(警报),结果对象看起来像

    public class ServiceMonitorResult 
    {
        public string Name
        public int Count 
        public int Age 
        public int Delta
        // our 3 alerts
        public IAlert CountAlert // can be null 
        public IAlert DeltaAlert // can be null 
        public IAlert AgeAlert   // can be null 


    }  

    public interface IAlert
    {
        AlertStatus Status// enum : New - Continuing - Ended
        ...
        public string MessageText   //  usually like $"{ServiceName (very long)} {alert status} breached  {Alert}  with value X at {DateTime.Now}. Started At {startedAt}"
    }

当这个结果在我们的compay IM上发出时,结果有时会非常冗长。我们有超过200项服务,如果我们平均有10%的违规,那就是20条消息/ 15分钟!

你可以想象,在有多个faulures的时候你会得到多少信息。

我已从IAlert中删除了MessageText,以使另一个类负责根据Alert状态构建消息。原因是这种监控的结果需要以不同的方式显示 - 例如IM中的它需要紧凑和清晰;它在表存储中并不重要,因为它用于分析而不是人类读取

鉴于:

  1. 这些警报可以为空,如果不是,则可以具有“新建”,“继续”或“结束”状态。
  2. 我有兴趣展示至少有一个状态为
  3. 的提醒的服务
  4. 我有兴趣展示至少有一个状态为已结束
  5. 的提醒的服务

    我正在尝试做的是使用某种设计模式/算法而不是嵌套if else语句将变成spagehetti并且维护/理解将无效。 我已经看过解释器模式,但它看起来不像在这里工作。 有什么想法吗?

    监视输入的示例

    ServiceName:CountAlertStatus / AgeAlertSatus / DeltaAlertStatus

    1. service100:N / - / E
    2. Service101:N / N / C
    3. Service102: - / - / -
    4. Service103:C / C / C
    5. Service104:C / E / N
    6. Service105:N / N / N
    7. Service106:的E / E / E
    8. (N:新,C:持续:,E:结束, - :空警报)

      期望的输出

      • service100:违反了计数(X),并且{Now}
      • 不再违反Delta
      • service101:违反了计数(X)和年龄(Y)。在{Now}
      • 仍然违反了Delta(Z)
      • Service104:Delta(X)遭到破坏,Age不再受到攻击。 Count仍在{Now}
      • 突破
      • Service105:在{now}
      • 违反计数(X)年龄(Y)和Delta(Z)
      • 服务106:计数(X)年龄(Y)和Delta(Z)违规结束于{now}

      service102& service103不会显示任何提醒,因为它们为空/继续,因此我们不关心

1 个答案:

答案 0 :(得分:0)

拥有一系列处理程序。每个处理程序都具有以下签名:

bool handle(char countAlertStatus, char ageAlertSatus, char deltaAlertStatus, out string message)
{
   //...
}

如果您可以处理CountAlertStatus / AgeAlertSatus / DeltaAlertStatus的组合,请返回true并设置message,否则返回false

您可以轻松地使用处理程序数组注册新的lambdas。

然后,您只需迭代处理程序,并在返回true时停止。

示例:

using System;
using System.Collections.Generic;

delegate bool MessageHandler(char countAlertStatus, char ageAlertSatus, char deltaAlertStatus, out string message);

class Program
{
    static void Main(string[] args)
    {
        var handlers = new List<MessageHandler>();

        //register lambda with array
        handlers.Add(Handler1);

        foreach (var handler in handlers)
        {
            // some fake input to each handler C/-/-
            if (handler('C', '-', '-', out string message))
            {
                Console.WriteLine("handled: " + message);
            }
        }

        Console.WriteLine("Done...");
        Console.Read();
    }

    static bool Handler1(char countAlertStatus, char ageAlertSatus, char deltaAlertStatus, out string message)
    {
        if (countAlertStatus == 'C')
        {
            message = "Handled";

            return true;
        }
        else
        {
            message = null;

            return false;
        }
    }
}