/** * Record an observation of an error. If it is the first observation of this error type for a stack trace * then a new entry will be created. For subsequent observations of the same error type and stack trace a * counter and time of last observation will be updated. * * @param observation to be logged as an error observation. * @return true if successfully logged otherwise false if insufficient space remaining in the log. */ public boolean record(final Throwable observation) { final long timestamp = clock.time(); DistinctObservation distinctObservation; synchronized (this) { distinctObservation = find(distinctObservations, observation); if (null == distinctObservation) { distinctObservation = newObservation(timestamp, observation); if (INSUFFICIENT_SPACE == distinctObservation) { return false; } } } final int offset = distinctObservation.offset; buffer.getAndAddInt(offset + OBSERVATION_COUNT_OFFSET, 1); buffer.putLongOrdered(offset + LAST_OBSERVATION_TIMESTAMP_OFFSET, timestamp); return true; }
DistinctObservation existingObservation = find(existingObservations, observation);
private DistinctObservation newObservation( final long timestamp, final DistinctObservation[] existingObservations, final Throwable observation) { DistinctObservation existingObservation = null; if (existingObservations != distinctObservations) { existingObservation = find(distinctObservations, observation); } if (null == existingObservation) { final StringWriter stringWriter = new StringWriter(); observation.printStackTrace(new PrintWriter(stringWriter)); final byte[] encodedError = stringWriter.toString().getBytes(UTF_8); final int length = ENCODED_ERROR_OFFSET + encodedError.length; final int offset = nextOffset; if ((offset + length) > buffer.capacity()) { return INSUFFICIENT_SPACE; } buffer.putBytes(offset + ENCODED_ERROR_OFFSET, encodedError); buffer.putLong(offset + FIRST_OBSERVATION_TIMESTAMP_OFFSET, timestamp); nextOffset = align(offset + length, RECORD_ALIGNMENT); existingObservation = new DistinctObservation(observation, offset); distinctObservations = prepend(distinctObservations, existingObservation); buffer.putIntOrdered(offset + LENGTH_OFFSET, length); } return existingObservation; }
/** * Record an observation of an error. If it is the first observation of this error type for a stack trace * then a new entry will be created. For subsequent observations of the same error type and stack trace a * counter and time of last observation will be updated. * * @param observation to be logged as an error observation. * @return true if successfully logged otherwise false if insufficient space remaining in the log. */ public boolean record(final Throwable observation) { final long timestamp = clock.time(); DistinctObservation distinctObservation; synchronized (this) { distinctObservation = find(distinctObservations, observation); if (null == distinctObservation) { distinctObservation = newObservation(timestamp, observation); if (INSUFFICIENT_SPACE == distinctObservation) { return false; } } } final int offset = distinctObservation.offset; buffer.getAndAddInt(offset + OBSERVATION_COUNT_OFFSET, 1); buffer.putLongOrdered(offset + LAST_OBSERVATION_TIMESTAMP_OFFSET, timestamp); return true; }