对开发者来说,使用DropWizard有如下好处:
1、和Maven集成良好,也就是说和Gradle集成也很良好;
2、开发迅速,部署简单;
3、代码结构好,可读性高;
4、自动为服务提供OM框架;
5、让开发者自然的把一个应用拆分为一个个的小服务
DropWizard结构的Web服务组成
1、Configuration:用于设置该服务的配置,比方说在服务开放在哪个端口,数据库配置是怎样的等等。
2、Service:该服务的主入口,定义该服务使用哪个配置文件,开放哪些Resource,该服务需要哪些HealthCheck等等。
3、Resource:定义一个资源,包括如何获取该资源,对该资源做Get/Post/Delete/Query时,对应的各种业务逻辑。
4、Representation:定义了一个服务返回值对象,当服务返回该对象时,会自动的把该对象按属性值生成一个Json格式的字符串返回给服务调用者。
5、HealthCheck:在DropWizard为每个服务提供的OM框架中用到,通过它可以随时检测当前服务是否可用。
DropWizard之Hello World
怎样开发一个DropWizard的Web服务呢?首先,在你的项目中引入DropWizard依赖
apply plugin: 'idea' apply plugin: 'maven' apply plugin: 'java' repositories { mavenCentral() } dependencies { compile( 'com.yammer.dropwizard:dropwizard-core:0.6.1' ) }
然后,定义Configuration
public class HelloWorldConfiguration extends Configuration { @NotEmpty //参数检查 @JsonProperty //自动映射配置文件 private String template; @NotEmpty @JsonProperty private String defaultName; public String getTemplate() { return template; } public String getDefaultName() { return defaultName; } }
再接着,定义服务想要开放的Resource,(DropWizard中大量使用了Annotation,大大简化了代码开发)
@Path("/helloWorld") @Produces(MediaType.APPLICATION_JSON) public class HelloWorldResource { private final String template; private final String defaultName; private final AtomicLong counter; public HelloWorldResource(String template, String defaultName) { this.template = template; this.defaultName = defaultName; this.counter = new AtomicLong(); } @GET @Timed public SayingRepresentation sayHello(@QueryParam("name")Optional<String> name){ return new SayingRepresentation(counter.incrementAndGet(),String.format(template,name.or(defaultName))); } }
然后,定义该服务返回值的Representation:
public class SayingRepresentation { private long id; private String content; public SayingRepresentation(long id, String content) { this.id = id; this.content = content; } public long getId() { return id; } public String getContent() { return content; } }
然后,为该服务定义一个HeatlthCheck,这个是可选的,但是,有HealthCheck的web服务让人放心很多:
public class TemplateHealthCheck extends HealthCheck { private final String template; protected TemplateHealthCheck(String template) { super("template"); this.template = template; } @Override protected Result check() throws Exception { final String saying = String.format(template,"TEST"); if(!saying.contains("TEST")){ return Result.unhealthy("template doesn't include a name!"); } return Result.healthy(); } }
最后,把该服务涉及的配置,资源,HealthCheck统一整合到Service主类中:
public class HelloWorldService extends Service<HelloWorldConfiguration> { //服务入口 public static void main(String[] args) throws Exception { new HelloWorldService().run(args); } @Override public void initialize(Bootstrap<HelloWorldConfiguration> bootstrap) { //指定配置文件的名字 bootstrap.setName("helloWorld"); } @Override public void run(HelloWorldConfiguration helloWorldConfiguration, Environment environment) throws Exception { final String template = helloWorldConfiguration.getTemplate(); final String defaultName = helloWorldConfiguration.getDefaultName(); environment.addResource(new HelloWorldResource(template,defaultName)); environment.addHealthCheck(new TemplateHealthCheck(template)); } }
另外配置文件如下:
template: Hello, %s!
defaultName: Stranger
这就是一个完整的REST风格的Web服务代码,另外,DropWizard的部署也非常简单,只需要使用构建脚本把该服务打包,然后使用如下的命令即可运行服务:
java -jar <jar包> server <config_file>
注意:1、在打包的时候一定要把依赖库也打进去
2、配置文件的名字一定要和Service类中设置的一样
最后,前面只是关于DropWizard的最基本的应用,DropWizard开发团队还为开发者考虑了很多贴心的功能,比方说,和Hibernate,Liquidbase的集成等等。更多更详细的信息,请移步:http://dropwizard.codahale.com/manual/
已有 0 人发表留言,猛击->>这里<<-参与讨论
ITeye推荐
- —软件人才免语言低担保 赴美带薪读研!—
V$LATCH
V$LATCH视图在选取X$KSLLT记录时,进行了Group By及SUM运算,从而得出了一个汇总信息,保存了自实例启动后各类栓锁的统计信息。常用于当v$session_wait中发现栓锁竞争时鉴别SGA区中问题所在区域。
v$latch表的每一行包括了对不同类型latch的统计,每一列反映了不同类型的latch请求的活动情况。不同类型的latch请求之间的区别在于,当latch不可立即获得时,请求进程是否继续进行。按此分类,latch请求的类型可分为两类:willing-to-wait和immediate。
Willing-to-wait:是指如果所请求的latch不能立即得到,请求进程将等待一很短的时间后再次发出请求。进程一直重复此过程直到得到latch。
Immediate:是指如果所请求的latch不能立即得到,请求进程就不再等待,而是继续执行下去。
V$LATCH中的常用列:
NAME:latch名称
IMMEDIATE_GETS:以Immediate模式latch请求数
IMMEDIATE_MISSES:IMMEDIATE_GETS的失败数
GETS:以Willing to wait请求模式latch的请求数
MISSES:GETS that did not obtain the latch on first try,Gets 不成功次数
SPIN_GETS:GETS that got the latch within SPIN_GET tries and did not have to sleep 第一次尝试失败,但在以后的轮次中成功
SLEEP1-SLEEP3: GETS that succeeded only after sleeping one to three times
SLEEP4: GETS that only succeeded after sleeping four or more times
WAIT_TIME: Elapsed time spent waiting for this latch ,花费在等待latch的时间
MISSES_WAITLIST: Number of latch misses on the associated wait list latch
SLEEPS_WAITLIST: Number of sleeps while trying to acquire the associated wait list latch
WAIT_TIME_WAITLIST: Wait time for the associated wait list latch
关于latch的统计信息,主要关注以下几部分
misses/gets的比率是多少
获自spinning的misses的百分比是多少
latch请求了多少次
latch休眠了多少次
latch有40余种,但作为DBA关心的主要应有以下几种:
Cache buffers chains latch:当用户进程搜索SGA寻找database cache buffers时需要使用此latch。
Cache buffers LRU chain latch:当用户进程要搜索buffer cache中包括所有 dirty blocks的LRU (least recently used) 链时使用该种latch。
Redo log buffer latch:这种latch控制redo log buffer中每条redo entries的空间分配。
Row cache objects latch:当用户进程访问缓存的数据字典数值时,将使用Row cache objects latch。
V$LATCH_CHILDREN
V$LATCH_CHILDREN是具体每个子LATCH的统计,V$LATCH是每一种LATCH的统计,前者比后者多了一个CHILD#,相同的LATCH#表示同种LATCH,ADDR是子LATCH的地址。V$LATCH_CHILDREN视图和v$Latch视图的差别与v$sql和v$sqlarea的区别相似并不进行汇总运算,所以也就显示了子Latch的相关信息。所谓子Latch就是library cache在系统中包含了多少个具体的物理数量的library cache,他们的分配原则是这样的。v$latch_children内容的条数一般都是v$latch cpu+1倍,例如:从v$latch查询出有1个library cache latches,系统cpu个数为2,则v$latch_children中library cache latches的子latch个数应该为3。
v$latch_children除了比v$latch多了child#其他列都一样,这里不再赘述。
V$LATCHHOLDER
通过v$latchholder可以查看当前持有latch的会话和进程。由于LATCH的等待时间都很短,该视图多用于查看长时间等待LATCH的SESSION
PID:进程标识,用于和v$process关联
SID: 会话标识,用于和V$SESSION关联
LADDR: Latch address V$LATCH_CHILDRN
NAME: Name of the latch being held V$LATCH / V$LATCHNAME / V$LATCH_CHILDRN
GETS:NUMBER Number of times that the latch was obtained in either wait mode or no-wait mode
V$LATCHNAME
显示了v$latch中latch的名称,和v$latch中的信息一一对应
LATCH#:Latch number
NAME:Latch name
HASH:Latch hash
常用SQL
查看持有latch的sql信息和会话信息
SELECT s.sql_hash_value,s.sql_id,s.sid l.name
FROM V$SESSION s, V$LATCHHOLDER l
WHERE s.sid = l.sid;
根据latch名称显示对latch的统计信息
select c.name,a.addr,a.gets,a.misses,a.sleeps,
a.immediate_gets,a.immediate_misses,b.pid
from v$latch a, v$latchholder b, v$latchname c
where a.addr = b.laddr(+) and a.latch# = c.latch#
and c.name like '&latch_name%' order by a.latch#;
# 查看latch的命中率
SQL>SELECT name, gets, misses, sleeps,
immediate_gets, immediate_misses
FROM v$latch
WHERE name = 'cache buffers chains';
#
如果在Top 5中发现latch free热点块事件时,可以从V$latch_children中查询具体的子Latch信息
SELECT *
FROM (SELECT addr, child#, gets, misses, sleeps, immediate_gets igets,
immediate_misses imiss, spin_gets sgets
FROM v$latch_children
WHERE NAME = 'cache buffers chains'
ORDER BY sleeps DESC)
WHERE ROWNUM < 11;
参考至:http://www.itpub.net/thread-1574165-1-1.html
http://blog.163.com/wghbeyond@126/blog/static/351661812010619073376/
http://grassbell.itpub.net/post/26/1458
http://www.poluoluo.com/jzxy/201010/95955.html
本函数的主要功能就是按指定的长度对utf-8字符集的字符串进行切断,如果字符串的长度大小指定的长度就在尾部加上“...”以表示字符串没有切束。
#对utf-8字符集进行切断处理,返回len个字符,中文和英文字符都当作一个计算。
def sub_utf8 text,len,endss="..."
t=i=max=0
slen=text.length
while t<len
if text[i]<= 0x7f
i=i+1
elsif text[i]<= 0xc0
i=i+2
else
i=i+3
end
if(i>=slen)
max=1
break
end
t=t+1
end
ret=text[0..i-1]
if max==0
ret<<endss
end
#print " slen:#{slen} get:#{i}================ "
return ret
end
已有 0 人发表留言,猛击->>这里<<-参与讨论
ITeye推荐
- —软件人才免语言低担保 赴美带薪读研!—