Class: NdrError::Log
- Inherits:
-
ActiveRecord::Base
- Object
- ActiveRecord::Base
- NdrError::Log
- Includes:
- BacktraceCompression, Fuzzing, UuidBuilder
- Defined in:
- app/models/ndr_error/log.rb
Overview
Stores instances of logs. Child of NdrError::Fingerprint. Log records may be purged, whereas fingerprints are designed to be eternally persisted.
Class Method Summary collapse
- .filter_by_keywords(keywords) ⇒ Object
-
.including_deleted_logs(&block) ⇒ Object
Make explicit when circumventing the default scope.
-
.perform_cleanup! ⇒ Object
Deletes all those errors that have been flagged for deletion and whose soft-delete grace period has ended.
-
.similar_to(error) ⇒ Object
Finds gets all errors that share an MD5 hash (including error).
Instance Method Summary collapse
-
#clock_drift? ⇒ Boolean
Returns true if clock drift of more than 3 seconds was present at the time of the error.
-
#error_string ⇒ Object
Formats error to be like the ruby error.
-
#flag_as_deleted!(time = Time.current) ⇒ Object
Performs a soft-delete of this log.
-
#md5_digest ⇒ Object
Creates (and caches) the md5 of this error, which is used to match to similar errors.
-
#md5_digest=(digest) ⇒ Object
Allow the digest to be set manually if so desired.
-
#next ⇒ Object
Returns the next historical occurence, or nil if there hasn’t been one.
-
#parameters ⇒ Object
Returns the params hash associated with the request.
-
#parameters_yml=(params) ⇒ Object
(also: #set_parameters_yml)
Store as much of ‘params’ as possible in the YAML parameters column.
-
#previous ⇒ Object
Returns the previous historical occurence, or nil if there wasn’t one.
-
#register_exception(exception) ⇒ Object
Copy across attributes from the exception object.
-
#register_request(request) ⇒ Object
Stores parameters from the given request object as YAML.
-
#similar_errors(include_self = false) ⇒ Object
Gets similar errors.
Methods included from UuidBuilder
Methods included from Fuzzing
Methods included from BacktraceCompression
#application_trace, #backtrace, #backtrace=
Class Method Details
.filter_by_keywords(keywords) ⇒ Object
35 36 37 38 39 40 41 |
# File 'app/models/ndr_error/log.rb', line 35 def self.filter_by_keywords(keywords) columns = %w(description error_class) << NdrError.user_column.to_s fragment = columns.map { |column| "lower(#{column}) LIKE lower(:key)" }.join(' OR ') name_match = keywords.map { |part| sanitize_sql([fragment, key: "%#{part}%"]) }.join(' OR ') where(name_match) end |
.including_deleted_logs(&block) ⇒ Object
Make explicit when circumventing the default scope
44 45 46 |
# File 'app/models/ndr_error/log.rb', line 44 def self.including_deleted_logs(&block) unscoped(&block) end |
.perform_cleanup! ⇒ Object
Deletes all those errors that have been flagged for deletion and whose soft-delete grace period has ended.
Returns true if any records were deleted.
52 53 54 55 56 57 58 59 60 61 62 63 |
# File 'app/models/ndr_error/log.rb', line 52 def self.perform_cleanup! records = including_deleted_logs do where("status like 'deleted%'") end destroys = records.map do |record| stamp_string = record.status.sub(/^[^\d]+/, '') record.destroy if Time.zone.parse(stamp_string) < NdrError.log_grace_period.ago end destroys.any? end |
.similar_to(error) ⇒ Object
Finds gets all errors that share an MD5 hash (including error).
67 68 69 |
# File 'app/models/ndr_error/log.rb', line 67 def self.similar_to(error) error.error_fingerprint.error_logs end |
Instance Method Details
#clock_drift? ⇒ Boolean
Returns true if clock drift of more than 3 seconds was present at the time of the error.
153 154 155 |
# File 'app/models/ndr_error/log.rb', line 153 def clock_drift? clock_drift && clock_drift >= 3.0 end |
#error_string ⇒ Object
Formats error to be like the ruby error.
147 148 149 |
# File 'app/models/ndr_error/log.rb', line 147 def error_string [error_class, description].compact.join(': ') end |
#flag_as_deleted!(time = Time.current) ⇒ Object
Performs a soft-delete of this log.
99 100 101 |
# File 'app/models/ndr_error/log.rb', line 99 def flag_as_deleted!(time = Time.current) update_attribute(:status, "deleted at #{time.to_s(:db)}") end |
#md5_digest ⇒ Object
Creates (and caches) the md5 of this error, which is used to match to similar errors.
159 160 161 |
# File 'app/models/ndr_error/log.rb', line 159 def md5_digest @_digest ||= fuzz(description, backtrace) end |
#md5_digest=(digest) ⇒ Object
Allow the digest to be set manually if so desired.
164 165 166 |
# File 'app/models/ndr_error/log.rb', line 164 def md5_digest=(digest) @_digest = digest end |
#next ⇒ Object
Returns the next historical occurence, or nil if there hasn’t been one.
92 93 94 95 96 |
# File 'app/models/ndr_error/log.rb', line 92 def next lookup = similar_errors(true) index = lookup.index(self) lookup[0...index].last end |
#parameters ⇒ Object
Returns the params hash associated with the request.
142 143 144 |
# File 'app/models/ndr_error/log.rb', line 142 def parameters YAML.load(parameters_yml) end |
#parameters_yml=(params) ⇒ Object Also known as: set_parameters_yml
Store as much of ‘params’ as possible in the YAML parameters column.
120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 |
# File 'app/models/ndr_error/log.rb', line 120 def parameters_yml=(params) yml_dump = {}.to_yaml parts = params.sort_by { |_k, v| v.inspect.length } # `parts' was sorted by length so that we # can capture as many different parameters # as possible in the given column space: (1..parts.length).each do |length| sub_hash = Hash[parts.first(length)] sub_yml = sub_hash.to_yaml break if sub_yml.length >= 4000 yml_dump = sub_yml end self[:parameters_yml] = yml_dump end |
#previous ⇒ Object
Returns the previous historical occurence, or nil if there wasn’t one.
84 85 86 87 88 |
# File 'app/models/ndr_error/log.rb', line 84 def previous lookup = similar_errors(true).reverse index = lookup.index(self) lookup[0...index].last end |
#register_exception(exception) ⇒ Object
Copy across attributes from the exception object.
104 105 106 107 108 |
# File 'app/models/ndr_error/log.rb', line 104 def register_exception(exception) self.error_class = exception.class.to_s self.backtrace = exception.backtrace self.description = description_from(exception.) end |
#register_request(request) ⇒ Object
Stores parameters from the given request object as YAML. Will attempt to store as many as possible of the parameters in the available 4000 chars.
113 114 115 116 |
# File 'app/models/ndr_error/log.rb', line 113 def register_request(request) extract_request_params(request) extract_request_attributes(request) end |
#similar_errors(include_self = false) ⇒ Object
Gets similar errors.
72 73 74 75 76 77 78 79 80 |
# File 'app/models/ndr_error/log.rb', line 72 def similar_errors(include_self = false) unless @_similar @_similar = {} @_similar[true] = self.class.similar_to(self) @_similar[false] = @_similar[true] - [self] end @_similar[include_self ? true : false] end |