001/* 002 * (C) Copyright 2017 Nuxeo (http://nuxeo.com/) and others. 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 * 016 */ 017package org.nuxeo.ecm.core.cache; 018 019import java.io.Serializable; 020 021import org.nuxeo.runtime.metrics.MetricsService; 022 023import com.codahale.metrics.Counter; 024import com.codahale.metrics.Gauge; 025import com.codahale.metrics.MetricRegistry; 026import com.codahale.metrics.RatioGauge; 027import com.codahale.metrics.SharedMetricRegistries; 028 029public class CacheMetrics extends CacheWrapper { 030 031 protected MetricRegistry registry; 032 033 protected Counter read; 034 035 protected Counter read_hit; 036 037 protected Counter read_miss; 038 039 protected RatioGauge read_hit_ratio; 040 041 protected Counter write; 042 043 protected Counter invalidation; 044 045 protected Gauge<Long> size; 046 047 protected final String READ_HIT_NAME = nameOf("read-hit-counter"); 048 049 protected final String READ_HIT_RATIO_NAME = nameOf("read-hit-ratio"); 050 051 protected final String READ_MISS_NAME = nameOf("read-miss-counter"); 052 053 protected final String READ_NAME = nameOf("read-counter"); 054 055 protected final String WRITE_NAME = nameOf("write-counter"); 056 057 protected final String INVALIDATE_ALL_NAME = nameOf("invalidate-all-counter"); 058 059 protected final String SIZE_NAME = nameOf("size"); 060 061 protected String nameOf(String name) { 062 return MetricRegistry.name("nuxeo", "cache", getName(), name); 063 } 064 065 public CacheMetrics(CacheManagement cache) { 066 super(cache); 067 } 068 069 @Override 070 public void start() { 071 registry = SharedMetricRegistries.getOrCreate(MetricsService.class.getName()); 072 read = registry.counter(READ_NAME); 073 read_hit = registry.counter(READ_HIT_NAME); 074 read_miss = registry.counter(READ_MISS_NAME); 075 registry.register(READ_HIT_RATIO_NAME, read_hit_ratio = new RatioGauge() { 076 077 @Override 078 protected Ratio getRatio() { 079 Ratio ratio = Ratio.of(read_hit.getCount(), read.getCount()); 080 return ratio; 081 } 082 }); 083 write = registry.counter(WRITE_NAME); 084 invalidation = registry.counter(INVALIDATE_ALL_NAME); 085 registry.register(SIZE_NAME, size = new Gauge<Long>() { 086 087 @Override 088 public Long getValue() { 089 return Long.valueOf(getSize()); 090 } 091 }); 092 } 093 094 @Override 095 public void stop() { 096 registry.remove(READ_NAME); 097 registry.remove(READ_HIT_NAME); 098 registry.remove(READ_MISS_NAME); 099 registry.remove(READ_HIT_RATIO_NAME); 100 registry.remove(WRITE_NAME); 101 registry.remove(INVALIDATE_ALL_NAME); 102 registry.remove(SIZE_NAME); 103 } 104 105 @Override 106 public Serializable get(String key) { 107 Serializable value = super.get(key); 108 read.inc(); 109 if (value != null || super.hasEntry(key)) { 110 read_hit.inc(); 111 } else { 112 read_miss.inc(); 113 } 114 return value; 115 } 116 117 @Override 118 public void put(String key, Serializable value) { 119 try { 120 super.put(key, value); 121 } finally { 122 write.inc(); 123 } 124 } 125 126 @Override 127 public void invalidateAll() { 128 try { 129 super.invalidateAll(); 130 } finally { 131 invalidation.inc(); 132 } 133 } 134 135}