observation.h 9.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274
  1. // Copyright (C) 2015 Internet Systems Consortium, Inc. ("ISC")
  2. //
  3. // Permission to use, copy, modify, and/or distribute this software for any
  4. // purpose with or without fee is hereby granted, provided that the above
  5. // copyright notice and this permission notice appear in all copies.
  6. //
  7. // THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
  8. // REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
  9. // AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
  10. // INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
  11. // LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
  12. // OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
  13. // PERFORMANCE OF THIS SOFTWARE.
  14. #ifndef OBSERVATION_H
  15. #define OBSERVATION_H
  16. #include <cc/data.h>
  17. #include <exceptions/exceptions.h>
  18. #include <boost/shared_ptr.hpp>
  19. #include <boost/date_time/time_duration.hpp>
  20. #include <boost/date_time/posix_time/posix_time_types.hpp>
  21. #include <list>
  22. #include <stdint.h>
  23. namespace isc {
  24. namespace stats {
  25. /// @brief Exception thrown if invalid statistic type is used
  26. ///
  27. /// For example statistic is of type duration, but methods using
  28. /// it as integer are called.
  29. class InvalidStatType : public Exception {
  30. public:
  31. InvalidStatType(const char* file, size_t line, const char* what) :
  32. isc::Exception(file, line, what) {}
  33. };
  34. /// @brief Defines duration resolution
  35. ///
  36. typedef boost::posix_time::time_duration StatsDuration;
  37. /// @defgroup stat_samples Specifies supported observation types.
  38. ///
  39. /// @brief The list covers all supported types of observations.
  40. ///
  41. /// @{
  42. /// @brief Integer (implemented as signed 64-bit integer)
  43. typedef std::pair<int64_t, boost::posix_time::ptime> IntegerSample;
  44. /// @brief Float (implemented as double precision)
  45. typedef std::pair<double, boost::posix_time::ptime> FloatSample;
  46. /// @brief Time Duration
  47. typedef std::pair<StatsDuration, boost::posix_time::ptime> DurationSample;
  48. /// @brief String
  49. typedef std::pair<std::string, boost::posix_time::ptime> StringSample;
  50. /// @}
  51. /// @brief Represents a single observable characteristic (a 'statistic')
  52. ///
  53. /// Currently it supports one of four types: integer (implemented as signed 64
  54. /// bit integer), float (implemented as double), time duration (implemented with
  55. /// millisecond precision) and string. Absolute (setValue) and
  56. /// incremental (addValue) modes are supported. Statistic type is determined
  57. /// during its first use. Once type is set, any additional observations recorded
  58. /// must be of the same type. Attempting to set or extract information about
  59. /// other types will result in InvalidStateType exception.
  60. ///
  61. /// Observation can be retrieved in one of @ref getInteger, @ref getFloat,
  62. /// @ref getDuration, @ref getString (appropriate type must be used) or
  63. /// @ref getJSON, which is generic and can be used for all types.
  64. ///
  65. /// @todo: Eventually it will be possible to retain multiple samples for the same
  66. /// observation, but that is outside of scope for 0.9.2.
  67. class Observation {
  68. public:
  69. /// @brief Type of available statistics
  70. ///
  71. /// Note that those will later be exposed using control socket. Therefore
  72. /// an easy to understand names were chosen (integer instead of uint64).
  73. /// To avoid confusion, we will support only one type of integer and only
  74. /// one type of floating points. Initially, these are represented by
  75. /// int64_t and double. If convincing use cases appear to change them
  76. /// to something else, we may change the underlying type.
  77. enum Type {
  78. STAT_INTEGER, ///< this statistic is unsinged 64-bit integer value
  79. STAT_FLOAT, ///< this statistic is a floating point value
  80. STAT_DURATION,///< this statistic represents time duration
  81. STAT_STRING ///< this statistic represents a string
  82. };
  83. /// @brief Constructor for integer observations
  84. ///
  85. /// @param name observation name
  86. /// @param value integer value observed.
  87. Observation(const std::string& name, const int64_t value);
  88. /// @brief Constructor for floating point observations
  89. ///
  90. /// @param name observation name
  91. /// @param value floating point value observed.
  92. Observation(const std::string& name, const double value);
  93. /// @brief Constructor for duration observations
  94. ///
  95. /// @param name observation name
  96. /// @param value duration observed.
  97. Observation(const std::string& name, const StatsDuration& value);
  98. /// @brief Constructor for string observations
  99. ///
  100. /// @param name observation name
  101. /// @param value string observed.
  102. Observation(const std::string& name, const std::string& value);
  103. /// @brief Records absolute integer observation
  104. ///
  105. /// @param value integer value observed
  106. /// @throw InvalidStatType if statistic is not integer
  107. void setValue(const int64_t value);
  108. /// @brief Records absolute floating point observation
  109. ///
  110. /// @param value floating point value observed
  111. /// @throw InvalidStatType if statistic is not fp
  112. void setValue(const double value);
  113. /// @brief Records absolute duration observation
  114. ///
  115. /// @param value duration value observed
  116. /// @throw InvalidStatType if statistic is not time duration
  117. void setValue(const StatsDuration& value);
  118. /// @brief Records absolute string observation
  119. ///
  120. /// @param value string value observed
  121. /// @throw InvalidStatType if statistic is not a string
  122. void setValue(const std::string& value);
  123. /// @brief Records incremental integer observation
  124. ///
  125. /// @param value integer value observed
  126. /// @throw InvalidStatType if statistic is not integer
  127. void addValue(const int64_t value);
  128. /// @brief Records incremental floating point observation
  129. ///
  130. /// @param value floating point value observed
  131. /// @throw InvalidStatType if statistic is not fp
  132. void addValue(const double value);
  133. /// @brief Records incremental duration observation
  134. ///
  135. /// @param value duration value observed
  136. /// @throw InvalidStatType if statistic is not time duration
  137. void addValue(const StatsDuration& value);
  138. /// @brief Records incremental string observation.
  139. ///
  140. /// @param value string value observed
  141. /// @throw InvalidStatType if statistic is not a string
  142. void addValue(const std::string& value);
  143. /// @brief Resets statistic.
  144. ///
  145. /// Sets statistic to a neutral (0, 0.0 or "") value.
  146. void reset();
  147. /// @brief Returns statistic type
  148. /// @return statistic type
  149. Type getType() const {
  150. return (type_);
  151. }
  152. /// @brief Returns observed integer sample
  153. /// @return observed sample (value + timestamp)
  154. /// @throw InvalidStatType if statistic is not integer
  155. IntegerSample getInteger() const;
  156. /// @brief Returns observed float sample
  157. /// @return observed sample (value + timestamp)
  158. /// @throw InvalidStatType if statistic is not fp
  159. FloatSample getFloat() const;
  160. /// @brief Returns observed duration sample
  161. /// @return observed sample (value + timestamp)
  162. /// @throw InvalidStatType if statistic is not time duration
  163. DurationSample getDuration() const;
  164. /// @brief Returns observed string sample
  165. /// @return observed sample (value + timestamp)
  166. /// @throw InvalidStatType if statistic is not a string
  167. StringSample getString() const;
  168. /// @brief Returns as a JSON structure
  169. /// @return JSON structures representing all observations
  170. isc::data::ConstElementPtr getJSON() const;
  171. /// @brief Converts statistic type to string
  172. /// @return textual name of statistic type
  173. static std::string typeToText(Type type);
  174. /// @brief Returns observation name
  175. std::string getName() const {
  176. return (name_);
  177. }
  178. private:
  179. /// @brief Records absolute sample (internal version)
  180. ///
  181. /// This method records an absolute value of an observation.
  182. /// It is used by public methods to add sample to one of
  183. /// available storages.
  184. ///
  185. /// @tparam SampleType type of sample (e.g. IntegerSample)
  186. /// @tparam StorageType type of storage (e.g. list<IntegerSample>)
  187. /// @param value observation to be recorded
  188. /// @param storage observation will be stored here
  189. /// @param exp_type expected observation type (used for sanity checking)
  190. /// @throw InvalidStatType if observation type mismatches
  191. template<typename SampleType, typename StorageType>
  192. void setValueInternal(SampleType value, StorageType& storage,
  193. Type exp_type);
  194. /// @brief Returns a sample (internal version)
  195. ///
  196. /// @tparam SampleType type of sample (e.g. IntegerSample)
  197. /// @tparam StorageType type of storage (e.g. list<IntegerSample>)
  198. /// @param observation storage
  199. /// @param exp_type expected observation type (used for sanity checking)
  200. /// @throw InvalidStatType if observation type mismatches
  201. /// @return Observed sample
  202. template<typename SampleType, typename Storage>
  203. SampleType getValueInternal(Storage& storage, Type exp_type) const;
  204. /// @brief Observation (statistic) name
  205. std::string name_;
  206. /// @brief Observation (statistic) type)
  207. Type type_;
  208. /// @defgroup samples_storage Storage for supported observations
  209. ///
  210. /// @brief The following containers serve as a storage for all supported
  211. /// observation types.
  212. ///
  213. /// @{
  214. /// @brief Storage for integer samples
  215. std::list<IntegerSample> integer_samples_;
  216. /// @brief Storage for floating point samples
  217. std::list<FloatSample> float_samples_;
  218. /// @brief Storage for time duration samples
  219. std::list<DurationSample> duration_samples_;
  220. /// @brief Storage for string samples
  221. std::list<StringSample> string_samples_;
  222. /// @}
  223. };
  224. /// @brief Observation pointer
  225. typedef boost::shared_ptr<Observation> ObservationPtr;
  226. };
  227. };
  228. #endif // OBSERVATION_H