001 /** 002 * 003 * Copyright 2004 Protique Ltd 004 * 005 * Licensed under the Apache License, Version 2.0 (the "License"); 006 * you may not use this file except in compliance with the License. 007 * You may obtain a copy of the License at 008 * 009 * http://www.apache.org/licenses/LICENSE-2.0 010 * 011 * Unless required by applicable law or agreed to in writing, software 012 * distributed under the License is distributed on an "AS IS" BASIS, 013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 014 * See the License for the specific language governing permissions and 015 * limitations under the License. 016 * 017 **/ 018 019 package org.activemq.capacity; 020 import java.util.Iterator; 021 import EDU.oswego.cs.dl.util.concurrent.CopyOnWriteArrayList; 022 023 /** 024 * BasicCapacityMonitor implementation 025 * @version $Revision: 1.1.1.1 $ 026 */ 027 public class BasicCapacityMonitor implements CapacityMonitor { 028 private String name; 029 private long valueLimit; 030 private long currentValue = 0; 031 private int currentCapacity = 100; 032 private int roundedCapacity = 100; 033 private int roundingFactor = 10; 034 private CopyOnWriteArrayList listeners = new CopyOnWriteArrayList(); 035 036 /** 037 * Construct a CapacityMonitor 038 * 039 * @param name 040 * @param valueLimit 041 */ 042 public BasicCapacityMonitor(String name, long valueLimit) { 043 this.name = name; 044 this.valueLimit = valueLimit; 045 } 046 047 /** 048 * Get the name of the CapacityMonitor 049 * 050 * @return 051 */ 052 public String getName() { 053 return name; 054 } 055 056 /** 057 * @param newName 058 */ 059 public void setName(String newName){ 060 name = newName; 061 } 062 063 /** 064 * Get the rounding factor - default is 10 065 * @return the rounding factor 066 */ 067 public int getRoundingFactor(){ 068 return roundingFactor; 069 } 070 071 /** 072 * Set the rounding factor (between 1-100) 073 * @param newRoundingFactor 074 */ 075 public void setRoundingFactor(int newRoundingFactor){ 076 if (newRoundingFactor < 1 || newRoundingFactor > 100){ 077 throw new IllegalArgumentException("invalid roundingFactor: " + newRoundingFactor); 078 } 079 roundingFactor = newRoundingFactor; 080 } 081 082 /** 083 * Add a CapacityMonitorEventListener 084 * 085 * @param l 086 */ 087 public void addCapacityEventListener(CapacityMonitorEventListener l) { 088 listeners.add(l); 089 } 090 091 /** 092 * Remove a CapacityMonitorEventListener 093 * 094 * @param l 095 */ 096 public void removeCapacityEventListener(CapacityMonitorEventListener l) { 097 listeners.remove(l); 098 } 099 100 /** 101 * Get the current capscity of the service as a percentage 102 * 103 * @return 104 */ 105 public int getCurrentCapacity() { 106 return currentCapacity; 107 } 108 109 /** 110 * Calculates the capacity rounded down to the rounding factor 111 * @return 112 */ 113 public int getRoundedCapacity(){ 114 return roundedCapacity; 115 } 116 117 /** 118 * Get the current value of the CapacityMonitor 119 * 120 * @return 121 */ 122 public long getCurrentValue() { 123 return currentValue; 124 } 125 126 /** 127 * set the current value of the capacity 128 * 129 * @param newCurrentValue 130 */ 131 public void setCurrentValue(long newCurrentValue) { 132 currentValue = newCurrentValue; 133 int newCapacity = calculateCapacity(); 134 int newRoundedCapacity = newCapacity > 0 ? (newCapacity/roundingFactor)*roundingFactor : 0; 135 updateCapacityChanged(newRoundedCapacity); 136 currentCapacity = newCapacity; 137 roundedCapacity = newRoundedCapacity; 138 } 139 140 /** 141 * @return The upper limit of the value of the CapacityMonitor 142 */ 143 public long getValueLimit() { 144 return valueLimit; 145 } 146 147 /** 148 * set a new value limit for the CapacityMonitor 149 * 150 * @param newValueLimit 151 */ 152 public void setValueLimit(long newValueLimit) { 153 valueLimit = newValueLimit; 154 //this could have changed the capacity 155 setCurrentValue(currentValue); 156 157 } 158 159 /** 160 * @return a CapacityMontorEvent for the currentCapacity 161 */ 162 public CapacityMonitorEvent generateCapacityMonitorEvent(){ 163 CapacityMonitorEvent event = new CapacityMonitorEvent(name, roundedCapacity); 164 return event; 165 } 166 167 private void updateCapacityChanged(int newRoundedCapacity) { 168 if (listeners.size() > 0 && newRoundedCapacity != roundedCapacity) { 169 CapacityMonitorEvent event = new CapacityMonitorEvent(name, newRoundedCapacity); 170 for (Iterator i = listeners.iterator();i.hasNext();) { 171 CapacityMonitorEventListener listener = (CapacityMonitorEventListener) i.next(); 172 listener.capacityChanged(event); 173 } 174 } 175 176 } 177 178 private int calculateCapacity() { 179 int result = 100; 180 if (currentValue != 0){ 181 result = (int) (100-(currentValue * 100)/valueLimit); 182 } 183 return result; 184 } 185 }