设计模式无处不在,我们可以在各种开源框架中识别到各种设计模式是如何被巧妙地应用的。BlackStar,虽然并不刻意,但也使用到很多设计模式。我们来看看BlackStar的Reporter,看一些常用的设计模式是如何使其更加灵活和可扩展的。
1.什么是Reporter
BlackStar的JVM Monitor会进行JVM监控数据的采集,采集后的数据如何处理呢,就交个Reporter去进行数据的处理。
2.策略模式
数据处理可能记录到文件、也可能调用远端服务器接口进行记录、也可能存储到数据库,对于JVM Monitor来说,不会关心Reporter如何去存储数据,这就是策略模式。
如下上策略接口定义
public interface ResultReporter
{
void report(ReportData data);
}
3.装饰模式
为了不影响JVM Monitor继续后续的工作,对于结果记录我们希望采用异步的方式去处理,然而如果每种策略实现者都需要自己去处理异步,当然是一个很冗余乏味的工作,我们使用装饰模式来处理
下面是异步Reporter的实现(代码做了裁减)
public class AysnResultReporter implements ResultReporter
{
private final static Log LOGGER = LogFactory.getLog(AysnResultReporter.class);
private ResultReporter targetResultReporter;
private ExecutorService executorService;
public AysnResultReporter(ResultReporter targetResultReporter,
ExecutorService executorService)
{
super();
this.targetResultReporter = targetResultReporter;
this.executorService = executorService;
}
public void report(final ReportData data)
{
this.executorService.execute(new Runnable()
{
public void run()
{
targetResultReporter.report(data);
}
});
}
}
看下面的示例
ResultReporter reporter = new AsynResultReporter(new FileReporter(...), executorService);
//异步、文件Reporter
ResultReporter reporter = new AsynResultReporter(new HessianReporter(...), executorService);
//异步、Hessian Reporter
4.组合模式
我们的目标当然不仅仅这么简单,为了保证采集的数据一定会被记录,我们可能要求首先使用远程模式记录,而远程模式记录错误时,则使用文件记录,或者我们可能要求使用多个Reporter同时记录,我们看看组合模式如何处理的
看看ListResultReporter的实现
public class ListResultReporter implements ResultReporter
{
private final static Log LOGGER = LogFactory
.getLog(ListResultReporter.class);
private boolean isAndMode = true;
private List<ResultReporter> list = new ArrayList<ResultReporter>();
public ListResultReporter()
{
this(true);
}
public ListResultReporter(boolean isAndMode)
{
this.isAndMode = isAndMode;
}
public void addResultReporter(ResultReporter reporter)
{
this.list.add(reporter);
}
public void report(ReportData data)
{
for (ResultReporter reporter : list)
{
if (isAndMode)
{
reporter.report(data);
} else
{
try
{
reporter.report(data);
return;
} catch (Exception e)
{
LOGGER.error("Error When Report[" + reporter + "]", e);
}
}
}
}
}
看看怎么使用
ListResultReporter reporter = new ListResultReporter();
reporter.addResultReporter(new FileReporter(...));
reporter.addResultReporter(new HessianReporter(...));
5.适配器模式
我们知道,对于数据库的写入,一次批量写总是要比多次写要高效地多,因此对于数据库的Reporter,会使用一个BatchResultReporter的接口,而Monitor使用的是ResultReporter接口,因此需要在它们之间做一个适配
BatchResultReporter接口
public interface BatchResultReporter
{
void reportBatch(List<ReportData> datas);
}
适配器
public class BatchReporterAdapter implements ResultReporter
{
private final static Log LOGGER = LogFactory
.getLog(BatchReporterAdapter.class);
private final Object LOCK = new Object();
private BatchResultReporter targetBatchResultReporter;
private long maxBatchSize = 1000L;
private List<ReportData> datas = new ArrayList<ReportData>();
public BatchReporterAdapter(BatchResultReporter batchResultReporter)
{
super();
this.targetBatchResultReporter = batchResultReporter;
}
public void setMaxBatchSize(long maxBatchSize)
{
this.maxBatchSize = maxBatchSize;
}
public void report(ReportData data)
{
List<ReportData> oldDatas = null;
synchronized (LOCK)
{
this.datas.add(data);
if (this.datas.size() >= this.maxBatchSize)
{
oldDatas = this.datas;
this.datas = new ArrayList<ReportData>();
}
}
if (oldDatas != null)
{
commit(oldDatas);
}
}
public void commit()
{
List<ReportData> oldDatas = null;
synchronized (LOCK)
{
oldDatas = this.datas;
this.datas = new ArrayList<ReportData>();
}
commit(oldDatas);
}
protected void commit(List<ReportData> datas)
{
LOGGER.info("commit batch report data[" + datas.size() + "]");
try
{
this.targetBatchResultReporter.reportBatch(datas);
} catch (Exception e)
{
LOGGER.error("Error When commit batch datas", e);
}
LOGGER.info("commit success");
}
}
6.工厂模式
如何将上面这些各种各样的Reporter创建出来呢,我们可以选择使用简单xml配置的方式来管理这些Reporter并创建,我们也可以依赖于其他的创建工厂,譬如Spring,这就是工厂模式
工厂接口如下
public interface ReporterFactory
{
ResultReporter createReporter(String name);
}
分享到:
相关推荐
"black_star"与标题相呼应,再次强调了工具包的品牌。"dax_tools"指的是这些工具专门用于DAX市场。 【压缩包子文件的文件名称列表】仅包含了一个文件:“Black Star Premium_幆ㄡ牠ē.docx”。这很可能是一个文档,...
常规的电磁波无线随钻仪能够传送的信号参数有井斜、方位、工具面、磁场强度、重力和温度等,而美国BlackStar EM-MWD电磁波无线随钻仪除了可以测量上述参数之外,还可以测得高边伽马、低边伽马,这两个值对于判断煤层顶...
【描述】虽然描述内容"LB^2 blackstar"与标题相同,但我们可以推测这可能是一个专为基于位置的应用或网站设计的网页模板,它可能包含了响应式布局、地图集成、定位功能、数据可视化等特性,旨在帮助开发者快速创建出...
BLACK STAR.apk.1
BlackStar电磁波无线随钻测斜仪是一种先进的钻井测量技术,由美国NOV公司研发。该技术在中石化胜利油田钻井工程技术公司的应用中取得了显著成果,尤其在墨西哥EBAN O区块的欠平衡水平井施工中表现出色。相较于传统的...
在这个“java设计模式资料汇总”中,包含两个核心文档:《Java与模式》和《统一建模语言概述》。 首先,我们来探讨《Java与模式》。这本书籍或文档可能会详细讲解21种经典的设计模式,这些模式被分为三大类:创建型...
在编程领域,设计模式是一种被广泛认可的解决特定问题或实现特定目标的代码结构模板。在C#中,设计模式的应用极大地提高了代码的可维护性、可读性和可复用性。本DEMO将深入探讨一些常见的设计模式,并通过实际的C#...
设计模式是软件设计中的一种最佳实践,它们是经过验证的、在特定情况下解决常见问题的模板。在Java中,设计模式被广泛应用于构建可扩展、可维护和高性能的软件系统。 创建型模式主要关注对象的创建,它们包括抽象...
黑星BlackStar是Roblox的所有标志和检查的一系列绕过步骤,以及详细而严格的解释,以帮助学习而不是用勺子喂食。 计划进行绕过的步骤包括memcheck,retcheck,hookcheck,FindWindowA,禁用日志,心跳和VEH。 Black...
《JAVA多线程设计模式》中包含JAVA线程的介绍导读,12个重要的线程设计模式和全书总结以及丰富的附录内容。每一章相关线程设计模式的介绍,都举一反三使读者学习更有效率。最后附上练习问题,让读者可以温故而知新,...
(修改消息中key为temp的值为15.36),点击勾进行保存节点修改后,必须点击右下角勾进行规则链的保存节点删除点击面板中的节点消息变换,点击节点右上角x按钮
### JAVA设计模式之创造型模式介绍 #### 一、工厂方法模式 **定义:** 工厂方法模式定义了一个创建对象的接口,但允许子类决定实例化哪个类。工厂方法让类的实例化推迟到子类。 **适用场景:** 1. 当一个类不知道...
本文档将详细介绍C++递归与分治算法在解决Red and Black问题、Fractal问题、Rank the Languages问题中的应用,包括问题描述、算法设计、代码实现和实例分析。 递归算法 递归算法是一种常用的算法设计模式,它通过...
BlackICE
"基于Linux嵌入式平台BeagleBone Black的EtherCAT主站设计" 该资源主要介绍了基于Linux嵌入式平台BeagleBone Black的EtherCAT主站设计,旨在提高工业控制系统的实时性。下面是从该资源中提取的知识点: 1. ...
在本课程设计中,我们将深入探讨如何使用C++编程语言实现经典的21点游戏,也称为Blackjack。这个项目不仅提供了实践经验,而且有助于巩固和提升C++编程技能,特别是面向对象编程、游戏逻辑以及随机数生成等核心概念...