package hudson.plugins.coverage.model;
import hudson.plugins.coverage.model.measurements.BranchCoverage;
import hudson.plugins.coverage.model.measurements.LineCoverage;
import java.io.ObjectStreamException;
import java.util.Collections;
import java.util.HashSet;
import java.util.Set;
import java.util.concurrent.CopyOnWriteArraySet;
/**
* Represents a source code metric.
*
* @author Stephen Connolly
* @since 26-Jun-2008 17:04:11
*/
public final class Metric implements Comparable<Metric> {
// ------------------------------ FIELDS ------------------------------
/**
* Standard metric for line coverage.
*/
public static final Metric LINE_COVERAGE = Metric.newMetric("line", LineCoverage.class);
/**
* Standard metric for branch coverage.
*/
public static final Metric BRANCH_COVERAGE = Metric.newMetric("branch", BranchCoverage.class);
/**
* The name of this metric.
*/
private final String name;
/**
* The type of measurement.
*/
private final Class<? extends Measurement> clazz;
// -------------------------- STATIC METHODS --------------------------
/**
* Creates a new source code metric.
*
* @param name The name of the metric.
* @param clazz The measurement class.
* @return The new metric.
*/
public static Metric newMetric(String name, Class<? extends Measurement> clazz) {
Metric result = new Metric(name, clazz);
SingletonHolder.ALL_METRICS.add(result);
return result;
}
/**
* Returns all the metrics.
*
* @return a read-only copy of all the metrics.
*/
public static Set<Metric> values() {
return Collections.unmodifiableSet(new HashSet<Metric>(SingletonHolder.ALL_METRICS));
}
// --------------------------- CONSTRUCTORS ---------------------------
/**
* Constructor for a child element.
*
* @param name The name.
* @param clazz The measurement class.
*/
private Metric(String name, Class<? extends Measurement> clazz) {
name.getClass(); // throw NPE if null
clazz.getClass();
this.name = name;
this.clazz = clazz;
}
// --------------------- GETTER / SETTER METHODS ---------------------
/**
* Getter for property 'clazz'.
*
* @return Value for property 'clazz'.
*/
public Class<? extends Measurement> getClazz() {
return clazz;
}
/**
* Getter for property 'name'.
*
* @return Value for property 'name'.
*/
public String getName() {
return name;
}
// ------------------------ CANONICAL METHODS ------------------------
/**
* {@inheritDoc}
*/
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
Metric element = (Metric) o;
return name.equals(element.name);
}
/**
* {@inheritDoc}
*/
public int hashCode() {
return name.hashCode();
}
// ------------------------ INTERFACE METHODS ------------------------
// --------------------- Interface Comparable ---------------------
/**
* {@inheritDoc}
*/
public int compareTo(Metric that) {
return name.compareTo(that.name);
}
// -------------------------- OTHER METHODS --------------------------
/**
* Ensure that instances are deserialized correctly.
*
* @return The deserialized instance.
* @throws ObjectStreamException never.
*/
private Object readResolve() throws ObjectStreamException {
for (Metric alternatives : SingletonHolder.ALL_METRICS) {
if (alternatives.name.equals(name)) {
return alternatives;
}
}
SingletonHolder.ALL_METRICS.add(this);
return this;
}
// -------------------------- INNER CLASSES --------------------------
/**
* Holds the metrics collection singleton.
*/
private static final class SingletonHolder {
// ------------------------------ FIELDS ------------------------------
/**
* The collection of metrics.
*/
private static final Set<Metric> ALL_METRICS = new CopyOnWriteArraySet<Metric>();
// --------------------------- CONSTRUCTORS ---------------------------
/**
* Do not instantiate SingletonHolder.
*/
private SingletonHolder() {
}
}
}