All files / src/rules local_testclass_consistency.ts

91.13% Statements 72/79
88.88% Branches 24/27
100% Functions 5/5
91.13% Lines 72/79

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 791x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 11714x 11714x 11714x 11714x 11714x 34998x 34998x 34998x 34998x 34998x 34998x 34998x 11714x 11714x 11175x 11175x 11714x 11714x 253x 253x 11714x 11714x 275x 275x 275x       275x 275x 214x 214x 61x 275x 56x         56x 61x 61x 275x 275x 1x 1x 1x 1x 1x 1x 1x 61x 275x 275x 275x 1x 1x 1x 1x 1x 1x 1x 61x 61x 61x 11714x 11714x
import {Issue} from "../issue";
import {ABAPRule} from "./_abap_rule";
import {BasicRuleConfig} from "./_basic_rule_config";
import {Class} from "../objects";
import {IObject} from "../objects/_iobject";
import {IRuleMetadata, RuleTag} from "./_irule";
import {ABAPFile} from "../abap/abap_file";
import {Release} from "../version";
 
export class LocalTestclassConsistencyConf extends BasicRuleConfig {
}
 
export class LocalTestclassConsistency extends ABAPRule {
 
  private conf = new LocalTestclassConsistencyConf();
 
  public getMetadata(): IRuleMetadata {
    return {
      key: "local_testclass_consistency",
      title: "Local testclass consistency",
      shortDescription: `Checks that local test classes are placed in the test include, and class unit test flag is set`,
      tags: [RuleTag.Syntax],
    };
  }
 
  public getConfig() {
    return this.conf;
  }
 
  public setConfig(conf: LocalTestclassConsistencyConf) {
    this.conf = conf;
  }
 
  public runParsed(file: ABAPFile, obj: IObject) {
    const issues: Issue[] = [];
 
    if (this.reg.getConfig().getRelease() === Release.v700) {
      // 700 does not have testclass includes
      return [];
    }
 
    if (!(obj instanceof Class)) {
      return [];
    }
 
    for (const c of file.getInfo().listClassDefinitions()) {
      if (c.isLocal && c.isForTesting && !file.getFilename().includes(".testclasses.abap")) {
        const message = "Place local testclass \"" + c.name + "\" in the testclass include";
        const issue = Issue.atIdentifier(c.identifier, message, this.getMetadata().key, this.conf.severity);
        issues.push(issue);
      }
    }
 
    if (file.getFilename().includes(".testclasses.") === true
        && obj.getTestclassFile() !== undefined
        && obj.getXML()?.includes("<WITH_UNIT_TESTS>X</WITH_UNIT_TESTS>") === false) {
      const id = obj.getIdentifier();
      if (id) {
        const message = "Has testclass, but XML does not set <WITH_UNIT_TESTS>";
        const issue = Issue.atIdentifier(id, message, this.getMetadata().key, this.conf.severity);
        issues.push(issue);
      }
    }
 
    if (file.getFilename() === obj.getMainABAPFile()?.getFilename()
        && obj.getTestclassFile() === undefined
        && obj.getXML()?.includes("<WITH_UNIT_TESTS>X</WITH_UNIT_TESTS>") === true) {
      const id = obj.getIdentifier();
      if (id) {
        const message = "Has <WITH_UNIT_TESTS> set in XML, but no testclasses";
        const issue = Issue.atIdentifier(id, message, this.getMetadata().key, this.conf.severity);
        issues.push(issue);
      }
    }
 
    return issues;
  }
 
}