001 /* 002 * Sonar, open source software quality management tool. 003 * Copyright (C) 2008-2011 SonarSource 004 * mailto:contact AT sonarsource DOT com 005 * 006 * Sonar is free software; you can redistribute it and/or 007 * modify it under the terms of the GNU Lesser General Public 008 * License as published by the Free Software Foundation; either 009 * version 3 of the License, or (at your option) any later version. 010 * 011 * Sonar is distributed in the hope that it will be useful, 012 * but WITHOUT ANY WARRANTY; without even the implied warranty of 013 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 014 * Lesser General Public License for more details. 015 * 016 * You should have received a copy of the GNU Lesser General Public 017 * License along with Sonar; if not, write to the Free Software 018 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02 019 */ 020 package org.sonar.api.measures; 021 022 import com.google.common.collect.Lists; 023 import org.apache.commons.lang.StringUtils; 024 import org.sonar.api.resources.Scopes; 025 import org.sonar.api.utils.SonarException; 026 027 import java.lang.reflect.Field; 028 import java.util.List; 029 030 /** 031 * @since 1.10 032 */ 033 public final class CoreMetrics { 034 035 private CoreMetrics() { 036 // only static stuff 037 } 038 039 public static final String DOMAIN_SIZE = "Size"; 040 public static final String DOMAIN_TESTS = "Tests"; 041 public static final String DOMAIN_INTEGRATION_TESTS = "Integration Tests"; 042 public static final String DOMAIN_COMPLEXITY = "Complexity"; 043 public static final String DOMAIN_DOCUMENTATION = "Documentation"; 044 public static final String DOMAIN_RULES = "Rules"; 045 public static final String DOMAIN_SCM = "SCM"; 046 047 /** 048 * @deprecated since 2.5 See http://jira.codehaus.org/browse/SONAR-2007 049 */ 050 @Deprecated 051 public static final String DOMAIN_RULE_CATEGORIES = "Rule categories"; 052 053 public static final String DOMAIN_GENERAL = "General"; 054 public static final String DOMAIN_DUPLICATION = "Duplication"; 055 public static final String DOMAIN_DESIGN = "Design"; 056 057 public static final String LINES_KEY = "lines"; 058 public static final Metric LINES = new Metric.Builder(LINES_KEY, "Lines", Metric.ValueType.INT) 059 .setDescription("Lines") 060 .setDirection(Metric.DIRECTION_WORST) 061 .setQualitative(false) 062 .setDomain(DOMAIN_SIZE) 063 .setFormula(new SumChildValuesFormula(false)) 064 .create(); 065 066 public static final String GENERATED_LINES_KEY = "generated_lines"; 067 public static final Metric GENERATED_LINES = new Metric.Builder(GENERATED_LINES_KEY, "Generated Lines", Metric.ValueType.INT) 068 .setDescription("Number of generated lines") 069 .setDirection(Metric.DIRECTION_WORST) 070 .setQualitative(false) 071 .setDomain(DOMAIN_SIZE) 072 .setBestValue(0.0) 073 .setOptimizedBestValue(true) 074 .setFormula(new SumChildValuesFormula(false)) 075 .create(); 076 077 public static final String NCLOC_KEY = "ncloc"; 078 public static final Metric NCLOC = new Metric.Builder(NCLOC_KEY, "Lines of code", Metric.ValueType.INT) 079 .setDescription("Non Commenting Lines of Code") 080 .setDirection(Metric.DIRECTION_WORST) 081 .setQualitative(false) 082 .setDomain(DOMAIN_SIZE) 083 .setFormula(new SumChildValuesFormula(false)) 084 .create(); 085 086 public static final String GENERATED_NCLOC_KEY = "generated_ncloc"; 087 public static final Metric GENERATED_NCLOC = new Metric.Builder(GENERATED_NCLOC_KEY, "Generated lines of code", Metric.ValueType.INT) 088 .setDescription("Generated non Commenting Lines of Code") 089 .setDirection(Metric.DIRECTION_WORST) 090 .setQualitative(false) 091 .setDomain(DOMAIN_SIZE) 092 .setBestValue(0.0) 093 .setOptimizedBestValue(true) 094 .setFormula(new SumChildValuesFormula(false)) 095 .create(); 096 097 public static final String CLASSES_KEY = "classes"; 098 public static final Metric CLASSES = new Metric.Builder(CLASSES_KEY, "Classes", Metric.ValueType.INT) 099 .setDescription("Classes") 100 .setDirection(Metric.DIRECTION_WORST) 101 .setQualitative(false) 102 .setDomain(DOMAIN_SIZE) 103 .setFormula(new SumChildValuesFormula(false)) 104 .create(); 105 106 public static final String FILES_KEY = "files"; 107 public static final Metric FILES = new Metric.Builder(FILES_KEY, "Files", Metric.ValueType.INT) 108 .setDescription("Number of files") 109 .setDirection(Metric.DIRECTION_WORST) 110 .setQualitative(false) 111 .setDomain(DOMAIN_SIZE) 112 .create(); 113 114 public static final String DIRECTORIES_KEY = "directories"; 115 public static final Metric DIRECTORIES = new Metric.Builder(DIRECTORIES_KEY, "Directories", Metric.ValueType.INT) 116 .setDescription("Directories") 117 .setDirection(Metric.DIRECTION_WORST) 118 .setQualitative(false) 119 .setDomain(DOMAIN_SIZE) 120 .create(); 121 122 public static final String PACKAGES_KEY = "packages"; 123 public static final Metric PACKAGES = new Metric.Builder(PACKAGES_KEY, "Packages", Metric.ValueType.INT) 124 .setDescription("Packages") 125 .setDirection(Metric.DIRECTION_WORST) 126 .setQualitative(false) 127 .setDomain(DOMAIN_SIZE) 128 .setFormula(new SumChildValuesFormula(false)) 129 .create(); 130 131 public static final String FUNCTIONS_KEY = "functions"; 132 public static final Metric FUNCTIONS = new Metric.Builder(FUNCTIONS_KEY, "Methods", Metric.ValueType.INT) 133 .setDescription("Methods") 134 .setDirection(Metric.DIRECTION_WORST) 135 .setQualitative(false) 136 .setDomain(DOMAIN_SIZE) 137 .setFormula(new SumChildValuesFormula(false)) 138 .create(); 139 140 public static final String ACCESSORS_KEY = "accessors"; 141 public static final Metric ACCESSORS = new Metric.Builder(ACCESSORS_KEY, "Accessors", Metric.ValueType.INT) 142 .setDescription("Accessors") 143 .setDirection(Metric.DIRECTION_WORST) 144 .setQualitative(false) 145 .setDomain(DOMAIN_SIZE) 146 .setFormula(new SumChildValuesFormula(false)) 147 .create(); 148 149 public static final String PARAGRAPHS_KEY = "paragraphs"; 150 public static final Metric PARAGRAPHS = new Metric.Builder(PARAGRAPHS_KEY, "Paragraphs", Metric.ValueType.INT) 151 .setDescription("Number of paragraphs") 152 .setDirection(Metric.DIRECTION_WORST) 153 .setQualitative(false) 154 .setDomain(DOMAIN_SIZE) 155 .setFormula(new SumChildValuesFormula(false)) 156 .create(); 157 158 public static final String STATEMENTS_KEY = "statements"; 159 public static final Metric STATEMENTS = new Metric.Builder(STATEMENTS_KEY, "Statements", Metric.ValueType.INT) 160 .setDescription("Number of statements") 161 .setDirection(Metric.DIRECTION_WORST) 162 .setQualitative(false) 163 .setDomain(DOMAIN_SIZE) 164 .setFormula(new SumChildValuesFormula(false)) 165 .create(); 166 167 public static final String PUBLIC_API_KEY = "public_api"; 168 public static final Metric PUBLIC_API = new Metric.Builder(PUBLIC_API_KEY, "Public API", Metric.ValueType.INT) 169 .setDescription("Public API") 170 .setDirection(Metric.DIRECTION_WORST) 171 .setQualitative(false) 172 .setDomain(DOMAIN_SIZE) 173 .setFormula(new SumChildValuesFormula(false)) 174 .create(); 175 176 177 //-------------------------------------------------------------------------------------------------------------------- 178 // 179 // DOCUMENTATION 180 // 181 //-------------------------------------------------------------------------------------------------------------------- 182 183 public static final String COMMENT_LINES_KEY = "comment_lines"; 184 public static final Metric COMMENT_LINES = new Metric.Builder(COMMENT_LINES_KEY, "Comment lines", Metric.ValueType.INT) 185 .setDescription("Number of comment lines") 186 .setDirection(Metric.DIRECTION_BETTER) 187 .setQualitative(false) 188 .setDomain(DOMAIN_DOCUMENTATION) 189 .setFormula(new SumChildValuesFormula(false)) 190 .create(); 191 192 public static final String COMMENT_LINES_DENSITY_KEY = "comment_lines_density"; 193 public static final Metric COMMENT_LINES_DENSITY = new Metric.Builder(COMMENT_LINES_DENSITY_KEY, "Comments (%)", Metric.ValueType.PERCENT) 194 .setDescription("Comments balanced by ncloc + comment lines") 195 .setDirection(Metric.DIRECTION_BETTER) 196 .setQualitative(true) 197 .setDomain(DOMAIN_DOCUMENTATION) 198 .create(); 199 200 public static final String COMMENT_BLANK_LINES_KEY = "comment_blank_lines"; 201 public static final Metric COMMENT_BLANK_LINES = new Metric.Builder(COMMENT_BLANK_LINES_KEY, "Blank comments", Metric.ValueType.INT) 202 .setDescription("Comments that do not contain comments") 203 .setDirection(Metric.DIRECTION_WORST) 204 .setQualitative(false) 205 .setDomain(DOMAIN_DOCUMENTATION) 206 .setFormula(new SumChildValuesFormula(false)) 207 .setBestValue(0.0) 208 .setOptimizedBestValue(true) 209 .create(); 210 211 public static final String PUBLIC_DOCUMENTED_API_DENSITY_KEY = "public_documented_api_density"; 212 public static final Metric PUBLIC_DOCUMENTED_API_DENSITY = new Metric.Builder(PUBLIC_DOCUMENTED_API_DENSITY_KEY, "Public documented API (%)", Metric.ValueType.PERCENT) 213 .setDescription("Public documented classes and methods balanced by ncloc") 214 .setDirection(Metric.DIRECTION_BETTER) 215 .setQualitative(true) 216 .setDomain(DOMAIN_DOCUMENTATION) 217 .setWorstValue(0.0) 218 .setBestValue(100.0) 219 .setOptimizedBestValue(true) 220 .create(); 221 222 public static final String PUBLIC_UNDOCUMENTED_API_KEY = "public_undocumented_api"; 223 public static final Metric PUBLIC_UNDOCUMENTED_API = new Metric.Builder(PUBLIC_UNDOCUMENTED_API_KEY, "Public undocumented API", Metric.ValueType.INT) 224 .setDescription("Public undocumented classes, methods and variables") 225 .setDirection(Metric.DIRECTION_WORST) 226 .setQualitative(true) 227 .setDomain(DOMAIN_DOCUMENTATION) 228 .setBestValue(0.0) 229 .setDirection(Metric.DIRECTION_WORST) 230 .setOptimizedBestValue(true) 231 .setFormula(new SumChildValuesFormula(false)) 232 .create(); 233 234 public static final String COMMENTED_OUT_CODE_LINES_KEY = "commented_out_code_lines"; 235 public static final Metric COMMENTED_OUT_CODE_LINES = new Metric.Builder(COMMENTED_OUT_CODE_LINES_KEY, "Commented-out LOC", Metric.ValueType.INT) 236 .setDescription("Commented lines of code") 237 .setDirection(Metric.DIRECTION_WORST) 238 .setQualitative(true) 239 .setDomain(DOMAIN_DOCUMENTATION) 240 .setFormula(new SumChildValuesFormula(false)) 241 .setBestValue(0.0) 242 .setOptimizedBestValue(true) 243 .create(); 244 245 246 //-------------------------------------------------------------------------------------------------------------------- 247 // 248 // COMPLEXITY 249 // 250 //-------------------------------------------------------------------------------------------------------------------- 251 252 public static final String COMPLEXITY_KEY = "complexity"; 253 public static final Metric COMPLEXITY = new Metric.Builder(COMPLEXITY_KEY, "Complexity", Metric.ValueType.INT) 254 .setDescription("Cyclomatic complexity") 255 .setDirection(Metric.DIRECTION_WORST) 256 .setQualitative(false) 257 .setDomain(DOMAIN_COMPLEXITY) 258 .setFormula(new SumChildValuesFormula(false)) 259 .create(); 260 261 public static final String CLASS_COMPLEXITY_KEY = "class_complexity"; 262 public static final Metric CLASS_COMPLEXITY = new Metric.Builder(CLASS_COMPLEXITY_KEY, "Complexity /class", Metric.ValueType.FLOAT) 263 .setDescription("Complexity average by class") 264 .setDirection(Metric.DIRECTION_WORST) 265 .setQualitative(true) 266 .setDomain(DOMAIN_COMPLEXITY) 267 .setFormula(new AverageComplexityFormula(CoreMetrics.CLASSES)) 268 .create(); 269 270 public static final String FUNCTION_COMPLEXITY_KEY = "function_complexity"; 271 public static final Metric FUNCTION_COMPLEXITY = new Metric.Builder(FUNCTION_COMPLEXITY_KEY, "Complexity /method", Metric.ValueType.FLOAT) 272 .setDescription("Complexity average by method") 273 .setDirection(Metric.DIRECTION_WORST) 274 .setQualitative(true) 275 .setDomain(DOMAIN_COMPLEXITY) 276 .setFormula(new AverageComplexityFormula(CoreMetrics.FUNCTIONS)) 277 .create(); 278 279 public static final String FILE_COMPLEXITY_KEY = "file_complexity"; 280 public static final Metric FILE_COMPLEXITY = new Metric.Builder(FILE_COMPLEXITY_KEY, "Complexity /file", Metric.ValueType.FLOAT) 281 .setDescription("Complexity average by file") 282 .setDirection(Metric.DIRECTION_WORST) 283 .setQualitative(true) 284 .setDomain(DOMAIN_COMPLEXITY) 285 .setFormula(new AverageComplexityFormula(CoreMetrics.FILES)) 286 .create(); 287 288 public static final String PARAGRAPH_COMPLEXITY_KEY = "paragraph_complexity"; 289 public static final Metric PARAGRAPH_COMPLEXITY = new Metric.Builder(PARAGRAPH_COMPLEXITY_KEY, "Complexity /paragraph", Metric.ValueType.FLOAT) 290 .setDescription("Complexity average by paragraph") 291 .setDirection(Metric.DIRECTION_WORST) 292 .setQualitative(true) 293 .setDomain(DOMAIN_COMPLEXITY) 294 .setFormula(new AverageComplexityFormula(CoreMetrics.PARAGRAPHS)) 295 .create(); 296 297 public static final String CLASS_COMPLEXITY_DISTRIBUTION_KEY = "class_complexity_distribution"; 298 public static final Metric CLASS_COMPLEXITY_DISTRIBUTION = new Metric.Builder(CLASS_COMPLEXITY_DISTRIBUTION_KEY, "Classes distribution /complexity", Metric.ValueType.DISTRIB) 299 .setDescription("Classes distribution /complexity") 300 .setDirection(Metric.DIRECTION_NONE) 301 .setQualitative(true) 302 .setDomain(DOMAIN_COMPLEXITY) 303 .setFormula(new SumChildDistributionFormula().setMinimumScopeToPersist(Scopes.DIRECTORY)) 304 .create(); 305 306 public static final String FUNCTION_COMPLEXITY_DISTRIBUTION_KEY = "function_complexity_distribution"; 307 public static final Metric FUNCTION_COMPLEXITY_DISTRIBUTION = new Metric.Builder(FUNCTION_COMPLEXITY_DISTRIBUTION_KEY, "Functions distribution /complexity", Metric.ValueType.DISTRIB) 308 .setDescription("Functions distribution /complexity") 309 .setDirection(Metric.DIRECTION_NONE) 310 .setQualitative(true) 311 .setDomain(DOMAIN_COMPLEXITY) 312 .setFormula(new SumChildDistributionFormula().setMinimumScopeToPersist(Scopes.DIRECTORY)) 313 .create(); 314 315 public static final String FILE_COMPLEXITY_DISTRIBUTION_KEY = "file_complexity_distribution"; 316 public static final Metric FILE_COMPLEXITY_DISTRIBUTION = new Metric.Builder(FILE_COMPLEXITY_DISTRIBUTION_KEY, "Files distribution /complexity", Metric.ValueType.DISTRIB) 317 .setDescription("Files distribution /complexity") 318 .setDirection(Metric.DIRECTION_NONE) 319 .setQualitative(true) 320 .setDomain(DOMAIN_COMPLEXITY) 321 .setFormula(new SumChildDistributionFormula().setMinimumScopeToPersist(Scopes.DIRECTORY)) 322 .create(); 323 324 public static final String PARAGRAPH_COMPLEXITY_DISTRIBUTION_KEY = "paragraph_complexity_distribution"; 325 public static final Metric PARAGRAPH_COMPLEXITY_DISTRIBUTION = new Metric.Builder(PARAGRAPH_COMPLEXITY_DISTRIBUTION_KEY, "Paragraph distribution /complexity", Metric.ValueType.DISTRIB) 326 .setDescription("Paragraph distribution /complexity") 327 .setDirection(Metric.DIRECTION_NONE) 328 .setQualitative(true) 329 .setDomain(DOMAIN_COMPLEXITY) 330 .setFormula(new SumChildDistributionFormula().setMinimumScopeToPersist(Scopes.DIRECTORY)) 331 .create(); 332 333 //-------------------------------------------------------------------------------------------------------------------- 334 // 335 // UNIT TESTS 336 // 337 //-------------------------------------------------------------------------------------------------------------------- 338 339 public static final String TESTS_KEY = "tests"; 340 341 /** 342 * Value of measure for this metric can be saved from Sensor, taking into account following rules: 343 * <ul> 344 * <li>If tool (like Maven Surefire Plugin) has not been activated to run unit tests, then Sensor should not save anything. For example there is no such tool for COBOL.</li> 345 * <li>If tool has been activated, but there was no unit tests to run, then zero value should be saved for project.</li> 346 * <li>Non-zero value should be saved for resources representing tests. And Sonar provides default Decorator, which will decorate parent resources.</li> 347 * <li>Should include {@link #TEST_FAILURES} and {@link #TEST_ERRORS}, but should not include {@link #SKIPPED_TESTS}.</li> 348 * </ul> 349 */ 350 public static final Metric TESTS = new Metric.Builder(TESTS_KEY, "Unit tests", Metric.ValueType.INT) 351 .setDescription("Number of unit tests") 352 .setDirection(Metric.DIRECTION_WORST) 353 .setQualitative(false) 354 .setDomain(DOMAIN_TESTS) 355 .create(); 356 357 public static final String TEST_EXECUTION_TIME_KEY = "test_execution_time"; 358 public static final Metric TEST_EXECUTION_TIME = new Metric.Builder(TEST_EXECUTION_TIME_KEY, "Unit tests duration", Metric.ValueType.MILLISEC) 359 .setDescription("Execution duration of unit tests") 360 .setDirection(Metric.DIRECTION_WORST) 361 .setQualitative(false) 362 .setDomain(DOMAIN_TESTS) 363 .create(); 364 365 public static final String TEST_ERRORS_KEY = "test_errors"; 366 public static final Metric TEST_ERRORS = new Metric.Builder(TEST_ERRORS_KEY, "Unit test errors", Metric.ValueType.INT) 367 .setDescription("Number of unit test errors") 368 .setDirection(Metric.DIRECTION_WORST) 369 .setQualitative(false) 370 .setDomain(DOMAIN_TESTS) 371 .setBestValue(0.0) 372 .setOptimizedBestValue(true) 373 .create(); 374 375 public static final String SKIPPED_TESTS_KEY = "skipped_tests"; 376 public static final Metric SKIPPED_TESTS = new Metric.Builder(SKIPPED_TESTS_KEY, "Skipped unit tests", Metric.ValueType.INT) 377 .setDescription("Number of skipped unit tests") 378 .setDirection(Metric.DIRECTION_WORST) 379 .setQualitative(false) 380 .setDomain(DOMAIN_TESTS) 381 .setBestValue(0.0) 382 .setOptimizedBestValue(true) 383 .create(); 384 385 public static final String TEST_FAILURES_KEY = "test_failures"; 386 public static final Metric TEST_FAILURES = new Metric.Builder(TEST_FAILURES_KEY, "Unit test failures", Metric.ValueType.INT) 387 .setDescription("Number of unit test failures") 388 .setDirection(Metric.DIRECTION_WORST) 389 .setQualitative(false) 390 .setDomain(DOMAIN_TESTS) 391 .setBestValue(0.0) 392 .setOptimizedBestValue(true) 393 .create(); 394 395 public static final String TEST_SUCCESS_DENSITY_KEY = "test_success_density"; 396 public static final Metric TEST_SUCCESS_DENSITY = new Metric.Builder(TEST_SUCCESS_DENSITY_KEY, "Unit test success (%)", Metric.ValueType.PERCENT) 397 .setDescription("Density of successful unit tests") 398 .setDirection(Metric.DIRECTION_BETTER) 399 .setQualitative(true) 400 .setDomain(DOMAIN_TESTS) 401 .setWorstValue(0.0) 402 .setBestValue(100.0) 403 .setOptimizedBestValue(true) 404 .create(); 405 406 public static final String TEST_DATA_KEY = "test_data"; 407 public static final Metric TEST_DATA = new Metric.Builder(TEST_DATA_KEY, "Unit tests details", Metric.ValueType.DATA) 408 .setDescription("Unit tests details") 409 .setDirection(Metric.DIRECTION_WORST) 410 .setDomain(DOMAIN_TESTS) 411 .create(); 412 413 public static final String COVERAGE_KEY = "coverage"; 414 public static final Metric COVERAGE = new Metric.Builder(COVERAGE_KEY, "Coverage", Metric.ValueType.PERCENT) 415 .setDescription("Coverage by unit tests") 416 .setDirection(Metric.DIRECTION_BETTER) 417 .setQualitative(true) 418 .setDomain(DOMAIN_TESTS) 419 .setWorstValue(0.0) 420 .setBestValue(100.0) 421 .create(); 422 423 public static final String NEW_COVERAGE_KEY = "new_coverage"; 424 public static final Metric NEW_COVERAGE = new Metric.Builder(NEW_COVERAGE_KEY, "New coverage", Metric.ValueType.PERCENT) 425 .setDescription("Coverage of new/changed code") 426 .setDirection(Metric.DIRECTION_BETTER) 427 .setQualitative(true) 428 .setDomain(DOMAIN_TESTS) 429 .setWorstValue(0.0) 430 .setBestValue(100.0) 431 .create(); 432 433 public static final String LINES_TO_COVER_KEY = "lines_to_cover"; 434 435 /** 436 * Use {@link CoverageMeasuresBuilder} to build measure for this metric. 437 */ 438 public static final Metric LINES_TO_COVER = new Metric.Builder(LINES_TO_COVER_KEY, "Lines to cover", Metric.ValueType.INT) 439 .setDescription("Lines to cover") 440 .setDirection(Metric.DIRECTION_BETTER) 441 .setQualitative(false) 442 .setDomain(DOMAIN_TESTS) 443 .setFormula(new SumChildValuesFormula(false)) 444 .setHidden(true) 445 .create(); 446 447 public static final String NEW_LINES_TO_COVER_KEY = "new_lines_to_cover"; 448 public static final Metric NEW_LINES_TO_COVER = new Metric.Builder(NEW_LINES_TO_COVER_KEY, "New lines to cover", Metric.ValueType.INT) 449 .setDescription("New lines to cover") 450 .setDirection(Metric.DIRECTION_WORST) 451 .setQualitative(false) 452 .setDomain(DOMAIN_TESTS) 453 .setFormula(new SumChildValuesFormula(false)) 454 .create(); 455 456 public static final String UNCOVERED_LINES_KEY = "uncovered_lines"; 457 458 /** 459 * Use {@link CoverageMeasuresBuilder} to build measure for this metric. 460 */ 461 public static final Metric UNCOVERED_LINES = new Metric.Builder(UNCOVERED_LINES_KEY, "Uncovered lines", Metric.ValueType.INT) 462 .setDescription("Uncovered lines") 463 .setDirection(Metric.DIRECTION_WORST) 464 .setDomain(DOMAIN_TESTS) 465 .setFormula(new SumChildValuesFormula(false)) 466 .setBestValue(0.0) 467 .create(); 468 469 public static final String NEW_UNCOVERED_LINES_KEY = "new_uncovered_lines"; 470 public static final Metric NEW_UNCOVERED_LINES = new Metric.Builder(NEW_UNCOVERED_LINES_KEY, "New uncovered lines", Metric.ValueType.INT) 471 .setDescription("New uncovered lines") 472 .setDirection(Metric.DIRECTION_WORST) 473 .setDomain(DOMAIN_TESTS) 474 .setFormula(new SumChildValuesFormula(false)) 475 .setBestValue(0.0) 476 .create(); 477 478 public static final String LINE_COVERAGE_KEY = "line_coverage"; 479 public static final Metric LINE_COVERAGE = new Metric.Builder(LINE_COVERAGE_KEY, "Line coverage", Metric.ValueType.PERCENT) 480 .setDescription("Line coverage") 481 .setDirection(Metric.DIRECTION_BETTER) 482 .setQualitative(true) 483 .setDomain(DOMAIN_TESTS) 484 .setWorstValue(0.0) 485 .setBestValue(100.0) 486 .create(); 487 488 public static final String NEW_LINE_COVERAGE_KEY = "new_line_coverage"; 489 public static final Metric NEW_LINE_COVERAGE = new Metric.Builder(NEW_LINE_COVERAGE_KEY, "New line coverage", Metric.ValueType.PERCENT) 490 .setDescription("Line coverage of added/changed code") 491 .setDirection(Metric.DIRECTION_BETTER) 492 .setQualitative(true) 493 .setWorstValue(0.0) 494 .setBestValue(100.0) 495 .setDomain(DOMAIN_TESTS) 496 .create(); 497 498 public static final String COVERAGE_LINE_HITS_DATA_KEY = "coverage_line_hits_data"; 499 500 /** 501 * Use {@link CoverageMeasuresBuilder} to build measure for this metric. 502 */ 503 public static final Metric COVERAGE_LINE_HITS_DATA = new Metric.Builder(COVERAGE_LINE_HITS_DATA_KEY, "Coverage hits by line", Metric.ValueType.DATA) 504 .setDomain(DOMAIN_TESTS) 505 .create(); 506 507 public static final String CONDITIONS_TO_COVER_KEY = "conditions_to_cover"; 508 509 /** 510 * Use {@link CoverageMeasuresBuilder} to build measure for this metric. 511 */ 512 public static final Metric CONDITIONS_TO_COVER = new Metric.Builder(CONDITIONS_TO_COVER_KEY, "Conditions to cover", Metric.ValueType.INT) 513 .setDescription("Conditions to cover") 514 .setDomain(DOMAIN_TESTS) 515 .setFormula(new SumChildValuesFormula(false)) 516 .setHidden(true) 517 .create(); 518 519 public static final String NEW_CONDITIONS_TO_COVER_KEY = "new_conditions_to_cover"; 520 public static final Metric NEW_CONDITIONS_TO_COVER = new Metric.Builder(NEW_CONDITIONS_TO_COVER_KEY, "New conditions to cover", Metric.ValueType.INT) 521 .setDescription("New conditions to cover") 522 .setDomain(DOMAIN_TESTS) 523 .setFormula(new SumChildValuesFormula(false)) 524 .create(); 525 526 public static final String UNCOVERED_CONDITIONS_KEY = "uncovered_conditions"; 527 528 /** 529 * Use {@link CoverageMeasuresBuilder} to build measure for this metric. 530 */ 531 public static final Metric UNCOVERED_CONDITIONS = new Metric.Builder(UNCOVERED_CONDITIONS_KEY, "Uncovered conditions", Metric.ValueType.INT) 532 .setDescription("Uncovered conditions") 533 .setDirection(Metric.DIRECTION_WORST) 534 .setDomain(DOMAIN_TESTS) 535 .setFormula(new SumChildValuesFormula(false)) 536 .setBestValue(0.0) 537 .create(); 538 539 public static final String NEW_UNCOVERED_CONDITIONS_KEY = "new_uncovered_conditions"; 540 public static final Metric NEW_UNCOVERED_CONDITIONS = new Metric.Builder(NEW_UNCOVERED_CONDITIONS_KEY, "New uncovered conditions", Metric.ValueType.INT) 541 .setDescription("New uncovered conditions") 542 .setDirection(Metric.DIRECTION_WORST) 543 .setDomain(DOMAIN_TESTS) 544 .setFormula(new SumChildValuesFormula(false)) 545 .setBestValue(0.0) 546 .create(); 547 548 public static final String BRANCH_COVERAGE_KEY = "branch_coverage"; 549 public static final Metric BRANCH_COVERAGE = new Metric.Builder(BRANCH_COVERAGE_KEY, "Branch coverage", Metric.ValueType.PERCENT) 550 .setDescription("Branch coverage") 551 .setDirection(Metric.DIRECTION_BETTER) 552 .setQualitative(true) 553 .setDomain(DOMAIN_TESTS) 554 .setWorstValue(0.0) 555 .setBestValue(100.0) 556 .create(); 557 558 public static final String NEW_BRANCH_COVERAGE_KEY = "new_branch_coverage"; 559 public static final Metric NEW_BRANCH_COVERAGE = new Metric.Builder(NEW_BRANCH_COVERAGE_KEY, "New branch coverage", Metric.ValueType.PERCENT) 560 .setDescription("Branch coverage of new/changed code") 561 .setDirection(Metric.DIRECTION_BETTER) 562 .setQualitative(true) 563 .setDomain(DOMAIN_TESTS) 564 .setWorstValue(0.0) 565 .setBestValue(100.0) 566 .create(); 567 568 /** 569 * @deprecated in 2.7. Replaced by {@link #CONDITIONS_BY_LINE_KEY} and {@link #COVERED_CONDITIONS_BY_LINE_KEY} 570 */ 571 @Deprecated 572 public static final String BRANCH_COVERAGE_HITS_DATA_KEY = "branch_coverage_hits_data"; 573 574 /** 575 * @deprecated in 2.7. Replaced by metrics {@link #CONDITIONS_BY_LINE} and {@link #COVERED_CONDITIONS_BY_LINE} 576 */ 577 @Deprecated 578 public static final Metric BRANCH_COVERAGE_HITS_DATA = new Metric.Builder(BRANCH_COVERAGE_HITS_DATA_KEY, "Branch coverage hits", Metric.ValueType.DATA) 579 .setDomain(DOMAIN_TESTS) 580 .create(); 581 582 public static final String CONDITIONS_BY_LINE_KEY = "conditions_by_line"; 583 584 /** 585 * Use {@link CoverageMeasuresBuilder} to build measure for this metric. 586 * 587 * @since 2.7 588 */ 589 public static final Metric CONDITIONS_BY_LINE = new Metric.Builder(CONDITIONS_BY_LINE_KEY, "Conditions by line", Metric.ValueType.DATA) 590 .setDomain(DOMAIN_TESTS) 591 .create(); 592 593 public static final String COVERED_CONDITIONS_BY_LINE_KEY = "covered_conditions_by_line"; 594 595 /** 596 * Use {@link CoverageMeasuresBuilder} to build measure for this metric. 597 * 598 * @since 2.7 599 */ 600 public static final Metric COVERED_CONDITIONS_BY_LINE = new Metric.Builder(COVERED_CONDITIONS_BY_LINE_KEY, "Covered conditions by line", Metric.ValueType.DATA) 601 .setDomain(DOMAIN_TESTS) 602 .create(); 603 604 605 //-------------------------------------------------------------------------------------------------------------------- 606 // 607 // INTEGRATION TESTS 608 // 609 //-------------------------------------------------------------------------------------------------------------------- 610 611 /** 612 * @since 2.12 613 */ 614 public static final String IT_COVERAGE_KEY = "it_coverage"; 615 616 /** 617 * @since 2.12 618 */ 619 public static final Metric IT_COVERAGE = new Metric.Builder(IT_COVERAGE_KEY, "IT Coverage", Metric.ValueType.PERCENT) 620 .setDescription("Coverage by integration tests") 621 .setDirection(Metric.DIRECTION_BETTER) 622 .setQualitative(true) 623 .setDomain(DOMAIN_INTEGRATION_TESTS) 624 .setWorstValue(0.0) 625 .setBestValue(100.0) 626 .create(); 627 628 /** 629 * @since 2.12 630 */ 631 public static final String NEW_IT_COVERAGE_KEY = "new_it_coverage"; 632 633 /** 634 * @since 2.12 635 */ 636 public static final Metric NEW_IT_COVERAGE = new Metric.Builder(NEW_IT_COVERAGE_KEY, "New Coverage by IT", Metric.ValueType.PERCENT) 637 .setDescription("Integration Tests Coverage of new/changed code") 638 .setDirection(Metric.DIRECTION_BETTER) 639 .setQualitative(true) 640 .setDomain(DOMAIN_INTEGRATION_TESTS) 641 .setWorstValue(0.0) 642 .setBestValue(100.0) 643 .create(); 644 645 /** 646 * @since 2.12 647 */ 648 public static final String IT_LINES_TO_COVER_KEY = "it_lines_to_cover"; 649 650 /** 651 * @since 2.12 652 */ 653 public static final Metric IT_LINES_TO_COVER = new Metric.Builder(IT_LINES_TO_COVER_KEY, "IT Lines to Cover", Metric.ValueType.INT) 654 .setDescription("Lines to cover by Integration Tests") 655 .setDirection(Metric.DIRECTION_BETTER) 656 .setDomain(DOMAIN_INTEGRATION_TESTS) 657 .setQualitative(false) 658 .setFormula(new SumChildValuesFormula(false)) 659 .setHidden(true) 660 .create(); 661 662 /** 663 * @since 2.12 664 */ 665 public static final String NEW_IT_LINES_TO_COVER_KEY = "new_it_lines_to_cover"; 666 667 /** 668 * @since 2.12 669 */ 670 public static final Metric NEW_IT_LINES_TO_COVER = new Metric.Builder(NEW_IT_LINES_TO_COVER_KEY, "New Lines to Cover by IT", Metric.ValueType.INT) 671 .setDescription("New lines to cover by Integration Tests") 672 .setDirection(Metric.DIRECTION_WORST) 673 .setQualitative(false) 674 .setDomain(DOMAIN_INTEGRATION_TESTS) 675 .setFormula(new SumChildValuesFormula(false)) 676 .create(); 677 678 /** 679 * @since 2.12 680 */ 681 public static final String IT_UNCOVERED_LINES_KEY = "it_uncovered_lines"; 682 683 /** 684 * @since 2.12 685 */ 686 public static final Metric IT_UNCOVERED_LINES = new Metric.Builder(IT_UNCOVERED_LINES_KEY, "IT Uncovered Lines", Metric.ValueType.INT) 687 .setDescription("IT uncovered lines") 688 .setDirection(Metric.DIRECTION_WORST) 689 .setQualitative(false) 690 .setDomain(DOMAIN_INTEGRATION_TESTS) 691 .setFormula(new SumChildValuesFormula(false)) 692 .create(); 693 694 /** 695 * @since 2.12 696 */ 697 public static final String NEW_IT_UNCOVERED_LINES_KEY = "new_it_uncovered_lines"; 698 699 /** 700 * @since 2.12 701 */ 702 public static final Metric NEW_IT_UNCOVERED_LINES = new Metric.Builder(NEW_IT_UNCOVERED_LINES_KEY, "New Uncovered Lines by IT", Metric.ValueType.INT) 703 .setDescription("New uncovered lines by Integration Tests") 704 .setDirection(Metric.DIRECTION_WORST) 705 .setDomain(DOMAIN_INTEGRATION_TESTS) 706 .setFormula(new SumChildValuesFormula(false)) 707 .setBestValue(0.0) 708 .create(); 709 710 /** 711 * @since 2.12 712 */ 713 public static final String IT_LINE_COVERAGE_KEY = "it_line_coverage"; 714 715 /** 716 * @since 2.12 717 */ 718 public static final Metric IT_LINE_COVERAGE = new Metric.Builder(IT_LINE_COVERAGE_KEY, "IT Line coverage", Metric.ValueType.PERCENT) 719 .setDescription("IT line coverage") 720 .setDirection(Metric.DIRECTION_BETTER) 721 .setQualitative(true) 722 .setDomain(DOMAIN_INTEGRATION_TESTS) 723 .create(); 724 725 /** 726 * @since 2.12 727 */ 728 public static final String NEW_IT_LINE_COVERAGE_KEY = "new_it_line_coverage"; 729 730 /** 731 * @since 2.12 732 */ 733 public static final Metric NEW_IT_LINE_COVERAGE = new Metric.Builder(NEW_IT_LINE_COVERAGE_KEY, "New Line Coverage by IT", Metric.ValueType.PERCENT) 734 .setDescription("Line Coverage by Integration Tests of added/changed code") 735 .setDirection(Metric.DIRECTION_BETTER) 736 .setQualitative(true) 737 .setWorstValue(0.0) 738 .setBestValue(100.0) 739 .setDomain(DOMAIN_INTEGRATION_TESTS) 740 .create(); 741 742 /** 743 * @since 2.12 744 */ 745 public static final String IT_COVERAGE_LINE_HITS_DATA_KEY = "it_coverage_line_hits_data"; 746 747 /** 748 * @since 2.12 749 */ 750 public static final Metric IT_COVERAGE_LINE_HITS_DATA = new Metric.Builder(IT_COVERAGE_LINE_HITS_DATA_KEY, "IT Coverage Hits Data", Metric.ValueType.DATA) 751 .setDescription("IT Code coverage line hits data") 752 .setDirection(Metric.DIRECTION_NONE) 753 .setQualitative(false) 754 .setDomain(DOMAIN_INTEGRATION_TESTS) 755 .create(); 756 757 /** 758 * @since 2.12 759 */ 760 public static final String IT_CONDITIONS_TO_COVER_KEY = "it_conditions_to_cover"; 761 762 /** 763 * @since 2.12 764 */ 765 public static final Metric IT_CONDITIONS_TO_COVER = new Metric.Builder(IT_CONDITIONS_TO_COVER_KEY, "IT Branches to Cover", Metric.ValueType.INT) 766 .setDescription("IT Conditions to cover") 767 .setDirection(Metric.DIRECTION_BETTER) 768 .setQualitative(false) 769 .setDomain(DOMAIN_INTEGRATION_TESTS) 770 .setFormula(new SumChildValuesFormula(false)) 771 .setHidden(true) 772 .create(); 773 774 /** 775 * @since 2.12 776 */ 777 public static final String NEW_IT_CONDITIONS_TO_COVER_KEY = "new_it_conditions_to_cover"; 778 779 /** 780 * @since 2.12 781 */ 782 public static final Metric NEW_IT_CONDITIONS_TO_COVER = new Metric.Builder(NEW_IT_CONDITIONS_TO_COVER_KEY, "New Conditions to Cover by IT", Metric.ValueType.INT) 783 .setDescription("New conditions to cover by Integration Tests") 784 .setDomain(DOMAIN_INTEGRATION_TESTS) 785 .setFormula(new SumChildValuesFormula(false)) 786 .create(); 787 788 /** 789 * @since 2.12 790 */ 791 public static final String IT_UNCOVERED_CONDITIONS_KEY = "it_uncovered_conditions"; 792 793 /** 794 * @since 2.12 795 */ 796 public static final Metric IT_UNCOVERED_CONDITIONS = new Metric.Builder(IT_UNCOVERED_CONDITIONS_KEY, "IT Uncovered Branches", Metric.ValueType.INT) 797 .setDescription("IT Uncovered conditions") 798 .setDirection(Metric.DIRECTION_WORST) 799 .setDomain(DOMAIN_INTEGRATION_TESTS) 800 .setFormula(new SumChildValuesFormula(false)) 801 .create(); 802 803 /** 804 * @since 2.12 805 */ 806 public static final String NEW_IT_UNCOVERED_CONDITIONS_KEY = "new_it_uncovered_conditions"; 807 808 /** 809 * @since 2.12 810 */ 811 public static final Metric NEW_IT_UNCOVERED_CONDITIONS = new Metric.Builder(NEW_IT_UNCOVERED_CONDITIONS_KEY, "New Uncovered Conditions by IT", Metric.ValueType.INT) 812 .setDescription("New uncovered conditions by Integration Tests") 813 .setDirection(Metric.DIRECTION_WORST) 814 .setDomain(DOMAIN_INTEGRATION_TESTS) 815 .setFormula(new SumChildValuesFormula(false)) 816 .setBestValue(0.0) 817 .create(); 818 819 /** 820 * @since 2.12 821 */ 822 public static final String IT_BRANCH_COVERAGE_KEY = "it_branch_coverage"; 823 824 /** 825 * @since 2.12 826 */ 827 public static final Metric IT_BRANCH_COVERAGE = new Metric.Builder(IT_BRANCH_COVERAGE_KEY, "IT Branch Coverage", Metric.ValueType.PERCENT) 828 .setDescription("IT Branch coverage") 829 .setDirection(Metric.DIRECTION_BETTER) 830 .setQualitative(true) 831 .setDomain(DOMAIN_INTEGRATION_TESTS) 832 .setWorstValue(0.0) 833 .setBestValue(100.0) 834 .create(); 835 836 /** 837 * @since 2.12 838 */ 839 public static final String NEW_IT_BRANCH_COVERAGE_KEY = "new_it_branch_coverage"; 840 841 /** 842 * @since 2.12 843 */ 844 public static final Metric NEW_IT_BRANCH_COVERAGE = new Metric.Builder(NEW_IT_BRANCH_COVERAGE_KEY, "New Branch Coverage by IT", Metric.ValueType.PERCENT) 845 .setDescription("Branch coverage by Integration Tests of new/changed code") 846 .setDirection(Metric.DIRECTION_BETTER) 847 .setQualitative(true) 848 .setDomain(DOMAIN_INTEGRATION_TESTS) 849 .setWorstValue(0.0) 850 .setBestValue(100.0) 851 .create(); 852 853 /** 854 * @since 2.12 855 */ 856 public static final String IT_CONDITIONS_BY_LINE_KEY = "it_conditions_by_line"; 857 858 /** 859 * @since 2.12 860 */ 861 public static final Metric IT_CONDITIONS_BY_LINE = new Metric.Builder(IT_CONDITIONS_BY_LINE_KEY, "IT Branches by Line", Metric.ValueType.DATA) 862 .setDomain(DOMAIN_INTEGRATION_TESTS) 863 .create(); 864 865 /** 866 * @since 2.12 867 */ 868 public static final String IT_COVERED_CONDITIONS_BY_LINE_KEY = "it_covered_conditions_by_line"; 869 870 /** 871 * @since 2.12 872 */ 873 public static final Metric IT_COVERED_CONDITIONS_BY_LINE = new Metric.Builder(IT_COVERED_CONDITIONS_BY_LINE_KEY, "IT Covered Branches by Line", Metric.ValueType.DATA) 874 .setDomain(DOMAIN_INTEGRATION_TESTS) 875 .create(); 876 877 878 //-------------------------------------------------------------------------------------------------------------------- 879 // 880 // DUPLICATIONS 881 // 882 //-------------------------------------------------------------------------------------------------------------------- 883 884 public static final String DUPLICATED_LINES_KEY = "duplicated_lines"; 885 public static final Metric DUPLICATED_LINES = new Metric.Builder(DUPLICATED_LINES_KEY, "Duplicated lines", Metric.ValueType.INT) 886 .setDescription("Duplicated lines") 887 .setDirection(Metric.DIRECTION_WORST) 888 .setQualitative(true) 889 .setDomain(DOMAIN_DUPLICATION) 890 .setBestValue(0.0) 891 .setOptimizedBestValue(true) 892 .create(); 893 894 public static final String DUPLICATED_BLOCKS_KEY = "duplicated_blocks"; 895 public static final Metric DUPLICATED_BLOCKS = new Metric.Builder(DUPLICATED_BLOCKS_KEY, "Duplicated blocks", Metric.ValueType.INT) 896 .setDescription("Duplicated blocks") 897 .setDirection(Metric.DIRECTION_WORST) 898 .setQualitative(true) 899 .setDomain(DOMAIN_DUPLICATION) 900 .setBestValue(0.0) 901 .setOptimizedBestValue(true) 902 .create(); 903 904 public static final String DUPLICATED_FILES_KEY = "duplicated_files"; 905 public static final Metric DUPLICATED_FILES = new Metric.Builder(DUPLICATED_FILES_KEY, "Duplicated files", Metric.ValueType.INT) 906 .setDescription("Duplicated files") 907 .setDirection(Metric.DIRECTION_WORST) 908 .setQualitative(true) 909 .setDomain(DOMAIN_DUPLICATION) 910 .setBestValue(0.0) 911 .setOptimizedBestValue(true) 912 .create(); 913 914 public static final String DUPLICATED_LINES_DENSITY_KEY = "duplicated_lines_density"; 915 public static final Metric DUPLICATED_LINES_DENSITY = new Metric.Builder(DUPLICATED_LINES_DENSITY_KEY, "Duplicated lines (%)", Metric.ValueType.PERCENT) 916 .setDescription("Duplicated lines balanced by statements") 917 .setDirection(Metric.DIRECTION_WORST) 918 .setQualitative(true) 919 .setDomain(DOMAIN_DUPLICATION) 920 .setWorstValue(50.0) 921 .setBestValue(0.0) 922 .setOptimizedBestValue(true) 923 .create(); 924 925 public static final String DUPLICATIONS_DATA_KEY = "duplications_data"; 926 public static final Metric DUPLICATIONS_DATA = new Metric.Builder(DUPLICATIONS_DATA_KEY, "Duplications details", Metric.ValueType.DATA) 927 .setDescription("Duplications details") 928 .setDirection(Metric.DIRECTION_NONE) 929 .setQualitative(false) 930 .setDomain(DOMAIN_DUPLICATION) 931 .create(); 932 933 934 //-------------------------------------------------------------------------------------------------------------------- 935 // 936 // CODING RULES 937 // 938 //-------------------------------------------------------------------------------------------------------------------- 939 /** 940 * @deprecated since 2.5 See http://jira.codehaus.org/browse/SONAR-2007 941 */ 942 @Deprecated 943 public static final String USABILITY_KEY = "usability"; 944 945 /** 946 * @deprecated since 2.5 See http://jira.codehaus.org/browse/SONAR-2007 947 */ 948 @Deprecated 949 public static final Metric USABILITY = new Metric(USABILITY_KEY, "Usability", "Usability", Metric.ValueType.PERCENT, 950 Metric.DIRECTION_BETTER, true, DOMAIN_RULE_CATEGORIES).setBestValue(100.0).setOptimizedBestValue(true); 951 952 /** 953 * @deprecated since 2.5 See http://jira.codehaus.org/browse/SONAR-2007 954 */ 955 @Deprecated 956 public static final String RELIABILITY_KEY = "reliability"; 957 958 /** 959 * @deprecated since 2.5 See http://jira.codehaus.org/browse/SONAR-2007 960 */ 961 @Deprecated 962 public static final Metric RELIABILITY = new Metric(RELIABILITY_KEY, "Reliability", "Reliability", Metric.ValueType.PERCENT, 963 Metric.DIRECTION_BETTER, true, DOMAIN_RULE_CATEGORIES).setBestValue(100.0).setOptimizedBestValue(true); 964 965 /** 966 * @deprecated since 2.5 See http://jira.codehaus.org/browse/SONAR-2007 967 */ 968 @Deprecated 969 public static final String EFFICIENCY_KEY = "efficiency"; 970 971 /** 972 * @deprecated since 2.5 See http://jira.codehaus.org/browse/SONAR-2007 973 */ 974 @Deprecated 975 public static final Metric EFFICIENCY = new Metric(EFFICIENCY_KEY, "Efficiency", "Efficiency", Metric.ValueType.PERCENT, 976 Metric.DIRECTION_BETTER, true, DOMAIN_RULE_CATEGORIES).setBestValue(100.0).setOptimizedBestValue(true); 977 978 /** 979 * @deprecated since 2.5 See http://jira.codehaus.org/browse/SONAR-2007 980 */ 981 @Deprecated 982 public static final String PORTABILITY_KEY = "portability"; 983 984 /** 985 * @deprecated since 2.5 See http://jira.codehaus.org/browse/SONAR-2007 986 */ 987 @Deprecated 988 public static final Metric PORTABILITY = new Metric(PORTABILITY_KEY, "Portability", "Portability", Metric.ValueType.PERCENT, 989 Metric.DIRECTION_BETTER, true, DOMAIN_RULE_CATEGORIES).setBestValue(100.0).setOptimizedBestValue(true); 990 991 /** 992 * @deprecated since 2.5 See http://jira.codehaus.org/browse/SONAR-2007 993 */ 994 @Deprecated 995 public static final String MAINTAINABILITY_KEY = "maintainability"; 996 997 /** 998 * @deprecated since 2.5 See http://jira.codehaus.org/browse/SONAR-2007 999 */ 1000 @Deprecated 1001 public static final Metric MAINTAINABILITY = new Metric.Builder(MAINTAINABILITY_KEY, "Maintainability", Metric.ValueType.PERCENT) 1002 .setDescription("Maintainability") 1003 .setDirection(Metric.DIRECTION_BETTER) 1004 .setQualitative(true) 1005 .setDomain(DOMAIN_RULE_CATEGORIES) 1006 .setBestValue(100.0) 1007 .setOptimizedBestValue(true) 1008 .create(); 1009 1010 public static final String WEIGHTED_VIOLATIONS_KEY = "weighted_violations"; 1011 public static final Metric WEIGHTED_VIOLATIONS = new Metric.Builder(WEIGHTED_VIOLATIONS_KEY, "Weighted violations", Metric.ValueType.INT) 1012 .setDescription("Weighted Violations") 1013 .setDirection(Metric.DIRECTION_WORST) 1014 .setQualitative(true) 1015 .setDomain(DOMAIN_RULES) 1016 .create(); 1017 1018 public static final String VIOLATIONS_DENSITY_KEY = "violations_density"; 1019 public static final Metric VIOLATIONS_DENSITY = new Metric.Builder(VIOLATIONS_DENSITY_KEY, "Rules compliance", Metric.ValueType.PERCENT) 1020 .setDescription("Rules compliance") 1021 .setDirection(Metric.DIRECTION_BETTER) 1022 .setQualitative(true) 1023 .setDomain(DOMAIN_RULES) 1024 .create(); 1025 1026 public static final String VIOLATIONS_KEY = "violations"; 1027 public static final Metric VIOLATIONS = new Metric.Builder(VIOLATIONS_KEY, "Violations", Metric.ValueType.INT) 1028 .setDescription("Violations") 1029 .setDirection(Metric.DIRECTION_WORST) 1030 .setQualitative(true) 1031 .setDomain(DOMAIN_RULES) 1032 .setBestValue(0.0) 1033 .setOptimizedBestValue(true) 1034 .create(); 1035 1036 public static final String BLOCKER_VIOLATIONS_KEY = "blocker_violations"; 1037 public static final Metric BLOCKER_VIOLATIONS = new Metric.Builder(BLOCKER_VIOLATIONS_KEY, "Blocker violations", Metric.ValueType.INT) 1038 .setDescription("Blocker violations") 1039 .setDirection(Metric.DIRECTION_WORST) 1040 .setQualitative(true) 1041 .setDomain(DOMAIN_RULES) 1042 .setBestValue(0.0) 1043 .setOptimizedBestValue(true) 1044 .create(); 1045 1046 public static final String CRITICAL_VIOLATIONS_KEY = "critical_violations"; 1047 public static final Metric CRITICAL_VIOLATIONS = new Metric.Builder(CRITICAL_VIOLATIONS_KEY, "Critical violations", Metric.ValueType.INT) 1048 .setDescription("Critical violations") 1049 .setDirection(Metric.DIRECTION_WORST) 1050 .setQualitative(true) 1051 .setDomain(DOMAIN_RULES) 1052 .setBestValue(0.0) 1053 .setOptimizedBestValue(true) 1054 .create(); 1055 1056 public static final String MAJOR_VIOLATIONS_KEY = "major_violations"; 1057 public static final Metric MAJOR_VIOLATIONS = new Metric.Builder(MAJOR_VIOLATIONS_KEY, "Major violations", Metric.ValueType.INT) 1058 .setDescription("Major violations") 1059 .setDirection(Metric.DIRECTION_WORST) 1060 .setQualitative(true) 1061 .setDomain(DOMAIN_RULES) 1062 .setBestValue(0.0) 1063 .setOptimizedBestValue(true) 1064 .create(); 1065 1066 public static final String MINOR_VIOLATIONS_KEY = "minor_violations"; 1067 public static final Metric MINOR_VIOLATIONS = new Metric.Builder(MINOR_VIOLATIONS_KEY, "Minor violations", Metric.ValueType.INT) 1068 .setDescription("Minor violations") 1069 .setDirection(Metric.DIRECTION_WORST) 1070 .setQualitative(true) 1071 .setDomain(DOMAIN_RULES) 1072 .setBestValue(0.0) 1073 .setOptimizedBestValue(true) 1074 .create(); 1075 1076 public static final String INFO_VIOLATIONS_KEY = "info_violations"; 1077 public static final Metric INFO_VIOLATIONS = new Metric.Builder(INFO_VIOLATIONS_KEY, "Info violations", Metric.ValueType.INT) 1078 .setDescription("Info violations") 1079 .setDirection(Metric.DIRECTION_WORST) 1080 .setQualitative(true) 1081 .setDomain(DOMAIN_RULES) 1082 .setBestValue(0.0) 1083 .setOptimizedBestValue(true) 1084 .create(); 1085 1086 public static final String NEW_VIOLATIONS_KEY = "new_violations"; 1087 public static final Metric NEW_VIOLATIONS = new Metric.Builder(NEW_VIOLATIONS_KEY, "New Violations", Metric.ValueType.INT) 1088 .setDescription("New Violations") 1089 .setDirection(Metric.DIRECTION_WORST) 1090 .setQualitative(true) 1091 .setDomain(DOMAIN_RULES) 1092 .setBestValue(0.0) 1093 .setOptimizedBestValue(true) 1094 .create(); 1095 1096 public static final String NEW_BLOCKER_VIOLATIONS_KEY = "new_blocker_violations"; 1097 public static final Metric NEW_BLOCKER_VIOLATIONS = new Metric.Builder(NEW_BLOCKER_VIOLATIONS_KEY, "New Blocker violations", Metric.ValueType.INT) 1098 .setDescription("New Blocker violations") 1099 .setDirection(Metric.DIRECTION_WORST) 1100 .setQualitative(true) 1101 .setDomain(DOMAIN_RULES) 1102 .setBestValue(0.0) 1103 .setOptimizedBestValue(true) 1104 .create(); 1105 1106 public static final String NEW_CRITICAL_VIOLATIONS_KEY = "new_critical_violations"; 1107 public static final Metric NEW_CRITICAL_VIOLATIONS = new Metric.Builder(NEW_CRITICAL_VIOLATIONS_KEY, "New Critical violations", Metric.ValueType.INT) 1108 .setDescription("New Critical violations") 1109 .setDirection(Metric.DIRECTION_WORST) 1110 .setQualitative(true) 1111 .setDomain(DOMAIN_RULES) 1112 .setBestValue(0.0) 1113 .setOptimizedBestValue(true) 1114 .create(); 1115 1116 public static final String NEW_MAJOR_VIOLATIONS_KEY = "new_major_violations"; 1117 public static final Metric NEW_MAJOR_VIOLATIONS = new Metric.Builder(NEW_MAJOR_VIOLATIONS_KEY, "New Major violations", Metric.ValueType.INT) 1118 .setDescription("New Major violations") 1119 .setDirection(Metric.DIRECTION_WORST) 1120 .setQualitative(true) 1121 .setDomain(DOMAIN_RULES) 1122 .setBestValue(0.0) 1123 .setOptimizedBestValue(true) 1124 .create(); 1125 1126 public static final String NEW_MINOR_VIOLATIONS_KEY = "new_minor_violations"; 1127 public static final Metric NEW_MINOR_VIOLATIONS = new Metric.Builder(NEW_MINOR_VIOLATIONS_KEY, "New Minor violations", Metric.ValueType.INT) 1128 .setDescription("New Minor violations") 1129 .setDirection(Metric.DIRECTION_WORST) 1130 .setQualitative(true) 1131 .setDomain(DOMAIN_RULES) 1132 .setBestValue(0.0) 1133 .setOptimizedBestValue(true) 1134 .create(); 1135 1136 public static final String NEW_INFO_VIOLATIONS_KEY = "new_info_violations"; 1137 public static final Metric NEW_INFO_VIOLATIONS = new Metric.Builder(NEW_INFO_VIOLATIONS_KEY, "New Info violations", Metric.ValueType.INT) 1138 .setDescription("New Info violations") 1139 .setDirection(Metric.DIRECTION_WORST) 1140 .setQualitative(true) 1141 .setDomain(DOMAIN_RULES) 1142 .setBestValue(0.0) 1143 .setOptimizedBestValue(true) 1144 .create(); 1145 1146 1147 //-------------------------------------------------------------------------------------------------------------------- 1148 // 1149 // DESIGN 1150 // 1151 //-------------------------------------------------------------------------------------------------------------------- 1152 1153 public static final String ABSTRACTNESS_KEY = "abstractness"; 1154 public static final Metric ABSTRACTNESS = new Metric.Builder(ABSTRACTNESS_KEY, "Abstractness", Metric.ValueType.PERCENT) 1155 .setDescription("Abstractness") 1156 .setDirection(Metric.DIRECTION_NONE) 1157 .setQualitative(false) 1158 .setDomain(DOMAIN_DESIGN) 1159 .create(); 1160 1161 public static final String INSTABILITY_KEY = "instability"; 1162 public static final Metric INSTABILITY = new Metric.Builder(INSTABILITY_KEY, "Instability", Metric.ValueType.PERCENT) 1163 .setDescription("Instability") 1164 .setDirection(Metric.DIRECTION_NONE) 1165 .setQualitative(false) 1166 .setDomain(DOMAIN_DESIGN) 1167 .create(); 1168 1169 public static final String DISTANCE_KEY = "distance"; 1170 public static final Metric DISTANCE = new Metric.Builder(DISTANCE_KEY, "Distance", Metric.ValueType.FLOAT) 1171 .setDescription("Distance") 1172 .setDirection(Metric.DIRECTION_NONE) 1173 .setQualitative(false) 1174 .setDomain(DOMAIN_DESIGN) 1175 .create(); 1176 1177 public static final String DEPTH_IN_TREE_KEY = "dit"; 1178 public static final Metric DEPTH_IN_TREE = new Metric.Builder(DEPTH_IN_TREE_KEY, "Depth in Tree", Metric.ValueType.INT) 1179 .setDescription("Depth in Inheritance Tree") 1180 .setDirection(Metric.DIRECTION_NONE) 1181 .setQualitative(false) 1182 .setDomain(DOMAIN_DESIGN) 1183 .create(); 1184 1185 public static final String NUMBER_OF_CHILDREN_KEY = "noc"; 1186 public static final Metric NUMBER_OF_CHILDREN = new Metric.Builder(NUMBER_OF_CHILDREN_KEY, "Number of Children", Metric.ValueType.INT) 1187 .setDescription("Number of Children") 1188 .setDirection(Metric.DIRECTION_NONE) 1189 .setQualitative(false) 1190 .setDomain(DOMAIN_DESIGN) 1191 .create(); 1192 1193 public static final String RFC_KEY = "rfc"; 1194 public static final Metric RFC = new Metric.Builder(RFC_KEY, "RFC", Metric.ValueType.INT) 1195 .setDescription("Response for Class") 1196 .setDirection(Metric.DIRECTION_WORST) 1197 .setQualitative(false) 1198 .setDomain(DOMAIN_DESIGN) 1199 .setFormula(new WeightedMeanAggregationFormula(CoreMetrics.FILES, false)) 1200 .create(); 1201 1202 public static final String RFC_DISTRIBUTION_KEY = "rfc_distribution"; 1203 public static final Metric RFC_DISTRIBUTION = new Metric.Builder(RFC_DISTRIBUTION_KEY, "Class distribution /RFC", Metric.ValueType.DISTRIB) 1204 .setDescription("Class distribution /RFC") 1205 .setDirection(Metric.DIRECTION_NONE) 1206 .setQualitative(true) 1207 .setDomain(DOMAIN_DESIGN) 1208 .setFormula(new SumChildDistributionFormula().setMinimumScopeToPersist(Scopes.DIRECTORY)) 1209 .create(); 1210 1211 public static final String LCOM4_KEY = "lcom4"; 1212 public static final Metric LCOM4 = new Metric.Builder(LCOM4_KEY, "LCOM4", Metric.ValueType.FLOAT) 1213 .setDescription("Lack of Cohesion of Methods") 1214 .setDirection(Metric.DIRECTION_WORST) 1215 .setQualitative(true) 1216 .setDomain(DOMAIN_DESIGN) 1217 .setBestValue(1.0) 1218 .setFormula(new WeightedMeanAggregationFormula(CoreMetrics.FILES, false)) 1219 .create(); 1220 1221 public static final String LCOM4_BLOCKS_KEY = "lcom4_blocks"; 1222 public static final Metric LCOM4_BLOCKS = new Metric.Builder(LCOM4_BLOCKS_KEY, "LCOM4 blocks", Metric.ValueType.DATA) 1223 .setDescription("LCOM4 blocks") 1224 .setDirection(Metric.DIRECTION_NONE) 1225 .setQualitative(false) 1226 .setDomain(DOMAIN_DESIGN) 1227 .setHidden(true) 1228 .create(); 1229 1230 public static final String LCOM4_DISTRIBUTION_KEY = "lcom4_distribution"; 1231 public static final Metric LCOM4_DISTRIBUTION = new Metric.Builder(LCOM4_DISTRIBUTION_KEY, "Class distribution /LCOM4", Metric.ValueType.DISTRIB) 1232 .setDescription("Class distribution /LCOM4") 1233 .setDirection(Metric.DIRECTION_NONE) 1234 .setQualitative(true) 1235 .setDomain(DOMAIN_DESIGN) 1236 .setFormula(new SumChildDistributionFormula().setMinimumScopeToPersist(Scopes.DIRECTORY)) 1237 .create(); 1238 1239 public static final String SUSPECT_LCOM4_DENSITY_KEY = "suspect_lcom4_density"; 1240 public static final Metric SUSPECT_LCOM4_DENSITY = new Metric.Builder(SUSPECT_LCOM4_DENSITY_KEY, "Suspect LCOM4 density", Metric.ValueType.PERCENT) 1241 .setDescription("Density of classes having LCOM4>1") 1242 .setDirection(Metric.DIRECTION_WORST) 1243 .setQualitative(true) 1244 .setDomain(DOMAIN_DESIGN) 1245 .create(); 1246 1247 public static final String AFFERENT_COUPLINGS_KEY = "ca"; 1248 public static final Metric AFFERENT_COUPLINGS = new Metric.Builder(AFFERENT_COUPLINGS_KEY, "Afferent couplings", Metric.ValueType.INT) 1249 .setDescription("Afferent couplings") 1250 .setDirection(Metric.DIRECTION_WORST) 1251 .setQualitative(false) 1252 .setDomain(DOMAIN_DESIGN) 1253 .create(); 1254 1255 public static final String EFFERENT_COUPLINGS_KEY = "ce"; 1256 public static final Metric EFFERENT_COUPLINGS = new Metric.Builder(EFFERENT_COUPLINGS_KEY, "Efferent couplings", Metric.ValueType.INT) 1257 .setDescription("Efferent couplings") 1258 .setDirection(Metric.DIRECTION_WORST) 1259 .setQualitative(false) 1260 .setDomain(DOMAIN_DESIGN) 1261 .create(); 1262 1263 public static final String DEPENDENCY_MATRIX_KEY = "dsm"; 1264 public static final Metric DEPENDENCY_MATRIX = new Metric.Builder(DEPENDENCY_MATRIX_KEY, "Dependency Matrix", Metric.ValueType.DATA) 1265 .setDescription("Dependency Matrix") 1266 .setDirection(Metric.DIRECTION_NONE) 1267 .setQualitative(false) 1268 .setDomain(DOMAIN_DESIGN) 1269 .create(); 1270 1271 public static final String PACKAGE_CYCLES_KEY = "package_cycles"; 1272 public static final Metric PACKAGE_CYCLES = new Metric.Builder(PACKAGE_CYCLES_KEY, "Package cycles", Metric.ValueType.INT) 1273 .setDescription("Package cycles") 1274 .setDirection(Metric.DIRECTION_WORST) 1275 .setQualitative(true) 1276 .setDomain(DOMAIN_DESIGN) 1277 .setFormula(new SumChildValuesFormula(false)) 1278 .create(); 1279 1280 public static final String PACKAGE_TANGLE_INDEX_KEY = "package_tangle_index"; 1281 public static final Metric PACKAGE_TANGLE_INDEX = new Metric.Builder(PACKAGE_TANGLE_INDEX_KEY, "Package tangle index", Metric.ValueType.PERCENT) 1282 .setDescription("Package tangle index") 1283 .setDirection(Metric.DIRECTION_WORST) 1284 .setQualitative(true) 1285 .setDomain(DOMAIN_DESIGN) 1286 .create(); 1287 1288 public static final String PACKAGE_TANGLES_KEY = "package_tangles"; 1289 public static final Metric PACKAGE_TANGLES = new Metric.Builder(PACKAGE_TANGLES_KEY, "File dependencies to cut", Metric.ValueType.INT) 1290 .setDescription("File dependencies to cut") 1291 .setDirection(Metric.DIRECTION_WORST) 1292 .setQualitative(false) 1293 .setDomain(DOMAIN_DESIGN) 1294 .setFormula(new SumChildValuesFormula(false)) 1295 .create(); 1296 1297 public static final String PACKAGE_FEEDBACK_EDGES_KEY = "package_feedback_edges"; 1298 public static final Metric PACKAGE_FEEDBACK_EDGES = new Metric.Builder(PACKAGE_FEEDBACK_EDGES_KEY, "Package dependencies to cut", Metric.ValueType.INT) 1299 .setDescription("Package dependencies to cut") 1300 .setDirection(Metric.DIRECTION_WORST) 1301 .setQualitative(false) 1302 .setDomain(DOMAIN_DESIGN) 1303 .setFormula(new SumChildValuesFormula(false)) 1304 .create(); 1305 1306 public static final String PACKAGE_EDGES_WEIGHT_KEY = "package_edges_weight"; 1307 public static final Metric PACKAGE_EDGES_WEIGHT = new Metric.Builder(PACKAGE_EDGES_WEIGHT_KEY, "Package edges weight", Metric.ValueType.INT) 1308 .setDescription("Package edges weight") 1309 .setDirection(Metric.DIRECTION_BETTER) 1310 .setQualitative(false) 1311 .setDomain(DOMAIN_DESIGN) 1312 .setFormula(new SumChildValuesFormula(false)) 1313 .setHidden(true) 1314 .create(); 1315 1316 public static final String FILE_CYCLES_KEY = "file_cycles"; 1317 public static final Metric FILE_CYCLES = new Metric.Builder(FILE_CYCLES_KEY, "File cycles", Metric.ValueType.INT) 1318 .setDescription("File cycles") 1319 .setDirection(Metric.DIRECTION_WORST) 1320 .setQualitative(true) 1321 .setDomain(DOMAIN_DESIGN) 1322 .setHidden(true) 1323 .create(); 1324 1325 public static final String FILE_TANGLE_INDEX_KEY = "file_tangle_index"; 1326 public static final Metric FILE_TANGLE_INDEX = new Metric.Builder(FILE_TANGLE_INDEX_KEY, "File tangle index", Metric.ValueType.PERCENT) 1327 .setDescription("File tangle index") 1328 .setDirection(Metric.DIRECTION_WORST) 1329 .setQualitative(true) 1330 .setDomain(DOMAIN_DESIGN) 1331 .setHidden(true) 1332 .create(); 1333 1334 public static final String FILE_TANGLES_KEY = "file_tangles"; 1335 public static final Metric FILE_TANGLES = new Metric.Builder(FILE_TANGLES_KEY, "File tangles", Metric.ValueType.INT) 1336 .setDescription("Files tangles") 1337 .setDirection(Metric.DIRECTION_WORST) 1338 .setQualitative(false) 1339 .setDomain(DOMAIN_DESIGN) 1340 .setHidden(true) 1341 .create(); 1342 1343 public static final String FILE_FEEDBACK_EDGES_KEY = "file_feedback_edges"; 1344 public static final Metric FILE_FEEDBACK_EDGES = new Metric.Builder(FILE_FEEDBACK_EDGES_KEY, "Suspect file dependencies", Metric.ValueType.INT) 1345 .setDescription("Suspect file dependencies") 1346 .setDirection(Metric.DIRECTION_WORST) 1347 .setQualitative(false) 1348 .setDomain(DOMAIN_DESIGN) 1349 .setHidden(true) 1350 .create(); 1351 1352 public static final String FILE_EDGES_WEIGHT_KEY = "file_edges_weight"; 1353 public static final Metric FILE_EDGES_WEIGHT = new Metric.Builder(FILE_EDGES_WEIGHT_KEY, "File edges weight", Metric.ValueType.INT) 1354 .setDescription("File edges weight") 1355 .setDirection(Metric.DIRECTION_BETTER) 1356 .setQualitative(false) 1357 .setDomain(DOMAIN_DESIGN) 1358 .setHidden(true) 1359 .create(); 1360 1361 1362 //-------------------------------------------------------------------------------------------------------------------- 1363 // 1364 // SCM 1365 // These metrics are computed by the SCM Activity plugin, since version 1.2. 1366 // 1367 //-------------------------------------------------------------------------------------------------------------------- 1368 1369 public static final String SCM_COMMITS_KEY = "commits"; 1370 public static final Metric SCM_COMMITS = new Metric.Builder(SCM_COMMITS_KEY, "Commits", Metric.ValueType.INT) 1371 .setDomain(DOMAIN_SCM) 1372 .create(); 1373 1374 public static final String SCM_LAST_COMMIT_DATE_KEY = "last_commit_date"; 1375 public static final Metric SCM_LAST_COMMIT_DATE = new Metric.Builder(SCM_LAST_COMMIT_DATE_KEY, "Last commit", Metric.ValueType.STRING /* TODO: move to date */) 1376 .setDomain(DOMAIN_SCM) 1377 .create(); 1378 1379 public static final String SCM_REVISION_KEY = "revision"; 1380 public static final Metric SCM_REVISION = new Metric.Builder(SCM_REVISION_KEY, "Revision", Metric.ValueType.STRING) 1381 .setDomain(DOMAIN_SCM) 1382 .setHidden(true) 1383 .create(); 1384 1385 public static final String SCM_AUTHORS_BY_LINE_KEY = "authors_by_line"; 1386 public static final Metric SCM_AUTHORS_BY_LINE = new Metric.Builder(SCM_AUTHORS_BY_LINE_KEY, "Authors by line", Metric.ValueType.DATA) 1387 .setDomain(DOMAIN_SCM) 1388 .create(); 1389 1390 public static final String SCM_REVISIONS_BY_LINE_KEY = "revisions_by_line"; 1391 public static final Metric SCM_REVISIONS_BY_LINE = new Metric.Builder(SCM_REVISIONS_BY_LINE_KEY, "Revisions by line", Metric.ValueType.DATA) 1392 .setDomain(DOMAIN_SCM) 1393 .create(); 1394 1395 public static final String SCM_LAST_COMMIT_DATETIMES_BY_LINE_KEY = "last_commit_datetimes_by_line"; 1396 public static final Metric SCM_LAST_COMMIT_DATETIMES_BY_LINE = new Metric.Builder(SCM_LAST_COMMIT_DATETIMES_BY_LINE_KEY, "Last commit dates by line", Metric.ValueType.DATA) 1397 .setDomain(DOMAIN_SCM) 1398 .create(); 1399 1400 1401 //-------------------------------------------------------------------------------------------------------------------- 1402 // 1403 // OTHERS 1404 // 1405 //-------------------------------------------------------------------------------------------------------------------- 1406 public static final String ALERT_STATUS_KEY = "alert_status"; 1407 public static final Metric ALERT_STATUS = new Metric.Builder(ALERT_STATUS_KEY, "Alert", Metric.ValueType.LEVEL) 1408 .setDescription("Alert") 1409 .setDirection(Metric.DIRECTION_BETTER) 1410 .setQualitative(true) 1411 .setDomain(DOMAIN_GENERAL) 1412 .create(); 1413 1414 1415 public static final String PROFILE_KEY = "profile"; 1416 public static final Metric PROFILE = new Metric.Builder(PROFILE_KEY, "Profile", Metric.ValueType.DATA) 1417 .setDescription("Selected quality profile") 1418 .setDomain(DOMAIN_GENERAL) 1419 .create(); 1420 1421 public static final String PROFILE_VERSION_KEY = "profile_version"; 1422 public static final Metric PROFILE_VERSION = new Metric.Builder(PROFILE_VERSION_KEY, "Profile version", Metric.ValueType.INT) 1423 .setDescription("Selected quality profile version") 1424 .setQualitative(false) 1425 .setDomain(DOMAIN_GENERAL) 1426 .create(); 1427 1428 private static final List<Metric> METRICS; 1429 1430 static { 1431 METRICS = Lists.newLinkedList(); 1432 for (Field field : CoreMetrics.class.getFields()) { 1433 if (Metric.class.isAssignableFrom(field.getType())) { 1434 try { 1435 Metric metric = (Metric) field.get(null); 1436 if (!StringUtils.equals(metric.getDomain(), DOMAIN_RULE_CATEGORIES)) { 1437 METRICS.add(metric); 1438 } 1439 } catch (IllegalAccessException e) { 1440 throw new SonarException("can not introspect " + CoreMetrics.class + " to get metrics", e); 1441 } 1442 } 1443 } 1444 } 1445 1446 1447 public static List<Metric> getMetrics() { 1448 return METRICS; 1449 } 1450 }