Class: Danger::DangerLoggingLint
- Inherits:
-
Plugin
- Object
- Plugin
- Danger::DangerLoggingLint
- Defined in:
- lib/logging_lint/plugin.rb
Overview
This danger plugin can be used to check log lines in modified (added) files. It heavily relies on regex configuration which can be modified to search all kinds of parts of code in the files. Default configuration is set to support Kotlin eMan Logger Library github.com/eManPrague/logger-ktx. Ex: logInfo { “Info message $var” }.
It works in two steps. First it searches for all log lines (multilines) in files. And then it applies line variable regex combined with line remove regex. Check [check_files] function for more information.
Constant Summary collapse
- DEFAULT_LOG_FUNCTIONS =
%w(logInfo).freeze
- DEFAULT_LOG_REGEX =
'[ ]?[{(](?:\n?|.)["]?(?:\n?|.)["]?(?:\n?|.)+(?:[)}][ ]?\n)'- DEFAULT_LINE_VARIABLE_REGEX =
['[{(](\n| |\+)*([^\"]\w[^\"])+', '(\".*\$.*\")'].freeze
- DEFAULT_LINE_REMOVE_REGEX =
['(\+ )?\".*\"'].freeze
- DEFAULT_WARNING_TEXT =
"Does this log comply with security rules?"
Instance Attribute Summary collapse
-
#file_extensions ⇒ Array<String>
File extensions are used to limit the number of files checked based on their extension.
-
#line_index_position ⇒ String
Unfortunately due to line modification in function ‘contains_variable` it is not possible to accurately pinpoint variable in the log.
-
#line_remove_regex ⇒ Array<String>
Gets ‘line_remove_regex` array from configuration or default `DEFAULT_LINE_REMOVE_REGEX` when null or empty.
-
#line_variable_regex ⇒ Array<String>
Gets ‘line_variable_regex` array from configuration or default `DEFAULT_LINE_VARIABLE_REGEX` when null or empty.
-
#log_functions ⇒ Array<String>
Gets ‘log_functions` array from configuration or default `DEFAULT_LOG_FUNCTIONS` when null.
-
#log_regex ⇒ String
Gets ‘log_regex` string from configuration or default `DEFAULT_LOG_REGEX` when null.
-
#warning_description ⇒ String
Warning description can be used to extend warning text.
-
#warning_text ⇒ String
Gets ‘warning_text` string from configuration or default `DEFAULT_WARNING_TEXT` when null.
Instance Method Summary collapse
-
#check_files(files) ⇒ void
Checks all files for log violations based on log regex and log function.
-
#compose_warning_text(warning_text) ⇒ String
Composes warning text.
-
#contains_variable(log) ⇒ Boolean
Checks if log contains variable or not.
-
#line_offset(line) ⇒ Integer
Calculates line offset which is used to identify line to danger.
-
#log_lint ⇒ void
Triggers file linting on specific target files.
Instance Attribute Details
#file_extensions ⇒ Array<String>
File extensions are used to limit the number of files checked based on their extension. For example for Kotlin language we want to check only .kt files and no other.
This variable is optional. When it is not set the plugin will automatically check all files.
58 59 60 |
# File 'lib/logging_lint/plugin.rb', line 58 def file_extensions @file_extensions end |
#line_index_position ⇒ String
Unfortunately due to line modification in function ‘contains_variable` it is not possible to accurately pinpoint variable in the log. That is why there are three options for the offset to identity the line.
Options are (set by ‘line_index_position`):
-
“start” which means 0 offset and start of the log,
-
“middle” which means length of the log divided by two,
-
else (“end”) which means length - 1 and end of the log. Used by default.
79 80 81 |
# File 'lib/logging_lint/plugin.rb', line 79 def line_index_position @line_index_position end |
#line_remove_regex ⇒ Array<String>
Gets ‘line_remove_regex` array from configuration or default `DEFAULT_LINE_REMOVE_REGEX` when null or empty.
174 175 176 177 178 |
# File 'lib/logging_lint/plugin.rb', line 174 def line_remove_regex return DEFAULT_LINE_REMOVE_REGEX if @line_remove_regex.nil? @line_remove_regex end |
#line_variable_regex ⇒ Array<String>
Gets ‘line_variable_regex` array from configuration or default `DEFAULT_LINE_VARIABLE_REGEX` when null or empty.
153 154 155 156 157 |
# File 'lib/logging_lint/plugin.rb', line 153 def line_variable_regex return DEFAULT_LINE_VARIABLE_REGEX if @line_variable_regex.nil? || @line_variable_regex.size <= 0 @line_variable_regex end |
#log_functions ⇒ Array<String>
Gets ‘log_functions` array from configuration or default `DEFAULT_LOG_FUNCTIONS` when null.
94 95 96 97 98 |
# File 'lib/logging_lint/plugin.rb', line 94 def log_functions return DEFAULT_LOG_FUNCTIONS if @log_functions.nil? @log_functions end |
#log_regex ⇒ String
Gets ‘log_regex` string from configuration or default `DEFAULT_LOG_REGEX` when null.
132 133 134 135 136 |
# File 'lib/logging_lint/plugin.rb', line 132 def log_regex return DEFAULT_LOG_REGEX if @log_regex.nil? @log_regex end |
#warning_description ⇒ String
Warning description can be used to extend warning text. It can be used to provide more context for the log warning such as more description, link with security rules and other.
66 67 68 |
# File 'lib/logging_lint/plugin.rb', line 66 def warning_description @warning_description end |
#warning_text ⇒ String
Gets ‘warning_text` string from configuration or default `DEFAULT_WARNING_TEXT` when null.
113 114 115 116 117 |
# File 'lib/logging_lint/plugin.rb', line 113 def warning_text return DEFAULT_WARNING_TEXT if @warning_text.nil? @warning_text end |
Instance Method Details
#check_files(files) ⇒ void
This method returns an undefined value.
Checks all files for log violations based on log regex and log function. Each log function id extended by log regex and searched for (format: #log_function#log_regex). Each of such found line is then checked if it contains a variable. If it does it is warned with a specific line index and warning text. Uses Danger warn level with sticky option.
224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 |
# File 'lib/logging_lint/plugin.rb', line 224 def check_files(files) raw_file = "" files.each do |filename| raw_file = File.read(filename) log_functions.each do |log_function| raw_file.scan(/#{log_function}#{log_regex}/m) do |c| if contains_variable(c) char_index = $~.offset(0)[0] + line_offset(c) line_index = raw_file[0..char_index].lines.count warn(compose_warning_text(warning_text), true, filename, line_index) end end end end end |
#compose_warning_text(warning_text) ⇒ String
Composes warning text. If ‘warning_description` is defined it will return a combination with `warning_text` else it will return only `warning_text`.
291 292 293 294 295 |
# File 'lib/logging_lint/plugin.rb', line 291 def compose_warning_text(warning_text) return warning_text if warning_description.nil? "#{warning_text} Check: #{warning_description}" end |
#contains_variable(log) ⇒ Boolean
Checks if log contains variable or not. Requires ‘line_variable_regex` variable to be configured. For each of this regex is searches value in `line_remove_regex`. If it is found then it is used to replace parts of the log using `gsub` function. It makes sure variable regex can be used on complex logs like `logInfo(n“TEST”n+ messagen)`. After cleaning it will try to match the variable regex in modified log.
248 249 250 251 252 253 254 255 256 257 258 259 260 |
# File 'lib/logging_lint/plugin.rb', line 248 def contains_variable(log) line_variable_regex.each_with_index do |regex, index| next if regex.nil? log_temp = log remove_regex = line_remove_regex[index] unless remove_regex.nil? log_temp = log.gsub(/#{remove_regex}/, "") end return true if log_temp.match?(regex) end false end |
#line_offset(line) ⇒ Integer
Calculates line offset which is used to identify line to danger. Unfortunately due to line modification in ‘contains_variable` it is not possible to accurately pinpoint variable in the log. That is why there are three options for the offset to identity the line.
Options are (set by ‘line_index_position`):
-
“start” which means 0 offset and start of the log,
-
“middle” which means length of the log divided by two,
-
else (“end”) which means length - 1 and end of the log.
274 275 276 277 278 279 280 281 282 283 |
# File 'lib/logging_lint/plugin.rb', line 274 def line_offset(line) case line_index_position when "start" 0 when "middle" (line.length - 1) / 1 else line.length - 1 end end |
#log_lint ⇒ void
This method returns an undefined value.
Triggers file linting on specific target files. But first it does few checks if it actually needs to run. 1) Checks if ‘log_functions` have size at least 1. If they are not then this script send Danger fail and cancels. 2) Checks if `line_variable_regex` have size at least 1. If they are not then this script send Danger fail and cancels. 3) Filters target files based on `file_extensions` and if there are no files to check it will send Danger message and cancels.
If all of these checks pass then it will trigger linter on target files (filtered) using ‘check_files`.
192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 |
# File 'lib/logging_lint/plugin.rb', line 192 def log_lint if log_functions.nil? || log_functions.size <= 0 self.fail("No log functions are defined. Please check your Danger file.") return end if line_variable_regex.nil? || line_variable_regex.size <= 0 ("At least one variable index must be defined (using default). Please check your Danger file.") end target_files = (git.modified_files - git.deleted_files) + git.added_files if !file_extensions.nil? && file_extensions.size >= 0 file_extensions_regex = "(.#{file_extensions.join('|.')})" target_files = target_files.grep(/#{file_extensions_regex}/) end if target_files.empty? ("No files to check.") return end check_files(target_files) end |