All files / src/rules empty_line_in_statement.ts

98.76% Statements 80/81
88.88% Branches 24/27
100% Functions 7/7
98.76% Lines 80/81

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 79 80 811x 1x 1x 1x 1x 1x 1x 1x 1x 1x 18722x 18722x 18722x 18722x 1x 9362x 9362x 9362x 9362x 9362x 27926x 27926x 27926x 27926x 27926x 27926x 27926x 27926x 9362x 9362x 2x 2x 9362x 9362x 8898x 8898x 9362x 9362x 216x 216x 9362x 9362x 243x 243x 243x 243x 12x 12x 231x 243x 1350x 1350x 7x 7x 1350x 224x 224x 243x 5345x 21x 5345x 1228x 1228x 5345x 2x 2x 2x 2x 5345x 1228x 5345x   4096x 4096x 4096x 5345x 224x 224x 224x 9362x 9362x
import {Issue} from "../issue";
import {ABAPRule} from "./_abap_rule";
import {BasicRuleConfig} from "./_basic_rule_config";
import {Punctuation, Comment as CommentToken} from "../abap/1_lexer/tokens";
import {NativeSQL, Unknown} from "../abap/2_statements/statements/_statement";
import {EditHelper} from "../edit_helper";
import {IRuleMetadata, RuleTag} from "./_irule";
import {Position} from "../position";
import {ABAPFile} from "../abap/abap_file";
 
export class EmptyLineinStatementConf extends BasicRuleConfig {
  /** Allow changed empty lines in chanined statements */
  public allowChained: boolean = false;
}
 
export class EmptyLineinStatement extends ABAPRule {
 
  private conf = new EmptyLineinStatementConf();
 
  public getMetadata(): IRuleMetadata {
    return {
      key: "empty_line_in_statement",
      title: "Find empty lines in statements",
      shortDescription: `Checks that statements do not contain empty lines.`,
      extendedInformation: `https://docs.abapopenchecks.org/checks/41/`,
      tags: [RuleTag.Quickfix, RuleTag.Whitespace, RuleTag.SingleFile],
    };
  }
 
  private getMessage(): string {
    return "Remove empty line in statement";
  }
 
  public getConfig() {
    return this.conf;
  }
 
  public setConfig(conf: EmptyLineinStatementConf) {
    this.conf = conf;
  }
 
  public runParsed(file: ABAPFile) {
    const issues: Issue[] = [];
 
    const stru = file.getStructure();
    if (stru === undefined) {
      return [];
    }
 
    for (const s of file.getStatements()) {
      if (s.get() instanceof Unknown
          || s.get() instanceof NativeSQL) {
        return []; // skip the file if there are parser errors or native/sqlscript
      }
    }
 
    let prevLine: number | undefined = undefined;
    for (const t of file.getTokens()) {
      if (prevLine === undefined && t instanceof CommentToken) {
        continue;
      } else if (prevLine === undefined) {
        prevLine = t.getRow();
      }
      if (prevLine && t.getRow() - prevLine >= 2) {
        const fix = EditHelper.deleteRange(file, new Position(prevLine + 1, 1), t.getStart());
        const issue = Issue.atToken(file, t, this.getMessage(), this.getMetadata().key, this.conf.severity, fix);
        issues.push(issue);
      }
      if (t instanceof Punctuation && t.getStr() === ".") {
        prevLine = undefined;
      } else if (this.conf.allowChained === true && t instanceof Punctuation && t.getStr() === ",") {
        prevLine = undefined;
      } else {
        prevLine = t.getRow();
      }
    }
 
    return issues;
  }
 
}