Repository: linkml/linkml

Issue:
linkml-lint command should have a verbose flag
The `linkml-link` command should have a verbose flag. If provided it should list all the files checked, even if they have no issues.


Discussion:

Patch:
diff --git a/linkml/linter/cli.py b/linkml/linter/cli.py
index 07483e43..1d9718b4 100644
--- a/linkml/linter/cli.py
+++ b/linkml/linter/cli.py
@@ -51,6 +51,7 @@ def get_yaml_files(root: Path) -> Iterable[str]:
     help="Report format.",
     show_default=True,
 )
+@click.option("-v", "--verbose", is_flag=True)
 @click.option(
     "-o", "--output", type=click.File("w"), default="-", help="Report file name."
 )
@@ -76,6 +77,7 @@ def main(
     output,
     ignore_warnings: bool,
     max_warnings: int,
+    verbose: bool
 ):
     """Run linter on SCHEMA.
 
@@ -99,7 +101,7 @@ def main(
 
     linter = Linter(config_dict)
     if format == "terminal":
-        formatter = TerminalFormatter(output)
+        formatter = TerminalFormatter(output, verbose)
     elif format == "markdown":
         formatter = MarkdownFormatter(output)
     elif format == "json":
diff --git a/linkml/linter/formatters/terminal_formatter.py b/linkml/linter/formatters/terminal_formatter.py
index 4dac4ebf..1c284c9f 100644
--- a/linkml/linter/formatters/terminal_formatter.py
+++ b/linkml/linter/formatters/terminal_formatter.py
@@ -14,17 +14,20 @@ def plural(word: str, count: int):
 
 
 class TerminalFormatter(Formatter):
-    def __init__(self, file: Optional[IO[Any]] = None) -> None:
+    def __init__(self, file: Optional[IO[Any]] = None, verbose: bool = False) -> None:
         super().__init__(file)
+        self.verbose = verbose
         self.problem_counts = defaultdict(int)
         self.current_schema = None
 
     def start_schema(self, name: str):
         self.current_schema = name
+        if self.verbose:
+            self.write(click.style(name, underline=True))
 
     def handle_problem(self, problem: LinterProblem):
         key = self.current_schema
-        if key not in self.problem_counts:
+        if not self.verbose and key not in self.problem_counts:
             self.write(click.style(key, underline=True))
 
         self.problem_counts[key] += 1
@@ -39,7 +42,7 @@ class TerminalFormatter(Formatter):
         self.write(formatted)
 
     def end_schema(self):
-        if self.current_schema in self.problem_counts:
+        if self.verbose or self.current_schema in self.problem_counts:
             self.write("")
 
     def end_report(self):


Test patch:
diff --git a/tests/test_linter/test_formatters.py b/tests/test_linter/test_formatters.py
index 98376a14..ed9ad92a 100644
--- a/tests/test_linter/test_formatters.py
+++ b/tests/test_linter/test_formatters.py
@@ -31,6 +31,9 @@ def populate_report(formatter):
     )
     formatter.end_schema()
 
+    formatter.start_schema("no_problems.yaml")
+    formatter.end_schema()
+
     formatter.start_schema("b.yaml")
     formatter.handle_problem(
         LinterProblem(
@@ -64,6 +67,26 @@ b.yaml
 """
         self.assertEqual(output.getvalue().strip(), expected.strip())
 
+    def test_terminal_formatter_verbose(self):
+        output = io.StringIO()
+        formatter = TerminalFormatter(file=output, verbose=True)
+        populate_report(formatter)
+        
+        expected = """
+a.yaml
+  error    this is an error  (rule_1)
+  warning  this is a warning  (rule_2)
+
+no_problems.yaml
+
+b.yaml
+  error    this is another error  (rule_3)
+
+✖ Found 3 problems in 2 schemas
+"""
+        self.assertEqual(output.getvalue().strip(), expected.strip())
+
+
     def test_markdown_formatter(self):
         output = io.StringIO()
         formatter = MarkdownFormatter(file=output)
@@ -74,7 +97,7 @@ b.yaml
 
 |                      | Count |
 |----------------------|-------|
-| Schemas Checked      | 2 |
+| Schemas Checked      | 3 |
 | Schemas with Error   | 2 |
 | Schemas with Warning | 1 |
 | Total Errors         | 2 |