diff --git a/pontos/version/commands/_java.py b/pontos/version/commands/_java.py index 926e0594c..379c7e071 100644 --- a/pontos/version/commands/_java.py +++ b/pontos/version/commands/_java.py @@ -15,199 +15,160 @@ # You should have received a copy of the GNU General Public License # along with this program. If not, see . -import logging +import json import re from pathlib import Path -from typing import Literal, Optional, Union - -from lxml import etree +from typing import Literal, Union, Dict, List, Any +from ._command import VersionCommand from ..errors import VersionError -from ..schemes import PEP440VersioningScheme from ..version import Version, VersionUpdate -from ._command import VersionCommand - -TEMPLATE = """# pylint: disable=invalid-name - -# THIS IS AN AUTOGENERATED FILE. DO NOT TOUCH! - -__version__ = "{}"\n""" VERSION_PATTERN = ( - r"([0-9]+\.[0-9]+\.[0-9]+(-?([ab]|rc|alpha|beta)[0-9]+(.dev[0-9]+)?)?)" + r"^(?P
.*[^\d])"
+    r"(?P\d+\.\d+\.\d+"
+    r"(-?([ab]|rc|alpha|beta)\d+(.dev\d+)?)?)"
+    r"(?P.*$)"
 )
 
 
-def find_file(
-    filename: Path, search_path: str, search_glob: str
-) -> Optional[Path]:
-    """Find a file somewhere within an directory tree
-
-    Arg:
-        filename: The file to look up
-        search_path: The path to look for the file
-        search_glob: The glob search pattern
-
-    Returns:
-        The file as Path object, if existing
-    """
-    search_path = Path(search_path).resolve()
-    for file_path in search_path.glob(search_glob):
-        if file_path.is_file() and file_path.name == filename.name:
-            return file_path
-    logging.warning("File %s not found in %s.", filename.name, search_path)
-    return None
-
-
-def replace_string_in_file(
-    file_path: Path, pattern: str, replacement: str
-) -> None:
-    # Read the content of the file
-    content = file_path.read_text(encoding="utf-8")
-
-    # Search for the pattern in the content
-    match = re.search(pattern, content)
-
-    # Replace the matched group (Group 1) with the replacement
-    if match:
-        # Write the updated content back to the file
-        file_path.write_text(
-            content.replace(match.group(1), replacement), encoding="utf-8"
-        )
-    else:
-        logging.warning(
-            "Couldn't match the pattern %s in the content of %s.",
-            pattern,
-            file_path,
-        )
-        logging.warning("Content: %s", content)
-
-
 # This class is used for Java Version command(s)
 class JavaVersionCommand(VersionCommand):
-    project_file_name = "pom.xml"
-    _properties_file_path = Path("src/main/resources/application.properties")
-    _pom_xml: Optional[etree.Element] = None
-
-    def _get_version_from_pom_xml(self) -> Version:
-        """
-        Return the version information from the  tag of the
-        pom.xml file. The version may be in non standardized form.
-        """
-
-        pom_xml: etree.Element = self.pom_xml
-
-        version_element = pom_xml.find("{*}version")
-        if version_element is None:
-            raise VersionError("Version tag missing in pom.xml")
-
-        return PEP440VersioningScheme.parse_version(version_element.text)
-
-    def _update_pom_version(
-        self,
-        new_version: Version,
-    ) -> None:
-        """
-        Update the version in the pom.xml file
-        """
-        pom_xml: etree.Element = self.pom_xml
-
-        version_element = pom_xml.find("{*}version")
-        if version_element is None:
-            raise VersionError("Version tag missing in pom.xml")
-        version_element.text = str(new_version)
-
-        etree.ElementTree(pom_xml).write(
-            self.project_file_path, pretty_print=True, encoding="utf-8"
-        )
+    project_file_name = "upgradeVersion.json"
 
-    def _update_properties_file(
-        self,
-        new_version: Version,
-    ) -> None:
-        # update the java properties file version
-        if not self._properties_file_path.exists():
-            # skip if not existing
-            return
-        pattern = rf"sentry\.release={VERSION_PATTERN}"
-        replace_string_in_file(
-            self._properties_file_path,
-            pattern=pattern,
-            replacement=str(new_version),
-        )
-
-    def _update_swagger_config(
-        self,
-        new_version: Version,
-    ) -> None:
-        # update swagger config file version
-        swagger_config_file = find_file(
-            filename=Path("SwaggerConfig.java"),
-            search_path="src",
-            search_glob="**/config/swagger/*",
-        )
-        if not swagger_config_file:
-            # skip if not existing
-            return
-        pattern = rf'\.version\("{VERSION_PATTERN}"\)'
-        replace_string_in_file(
-            swagger_config_file, pattern=pattern, replacement=str(new_version)
-        )
-
-    @property
-    def pom_xml(self) -> etree.Element:
-        if self._pom_xml is not None:
-            return self._pom_xml
-
-        if not self.project_file_path.exists():
-            raise VersionError("pom.xml file not found.")
-
-        try:
-            pom_xml: etree.ElementTree = etree.parse(self.project_file_path)
-        except etree.XMLSyntaxError as e:
-            raise VersionError(e) from e
+    def get_current_version(self) -> Version:
+        file_versions = self._read_versions_from_files()
 
-        self._pom_xml = pom_xml.getroot()
+        last_version = self._verify_version(file_versions)
 
-        return self._pom_xml
+        if last_version == "":
+            raise VersionError("no version found")
 
-    def get_current_version(self) -> Version:
-        """Get the current version of this project
-        In go the version is only defined within the repository
-        tags, thus we need to check git, what tag is the latest"""
-        return self._get_version_from_pom_xml()
+        return self.versioning_scheme.parse_version(last_version)
 
     def verify_version(
         self, version: Union[Literal["current"], Version, None]
     ) -> None:
-        """Verify the current version of this project"""
-        current_version = self.get_current_version()
+        file_versions = self._read_versions_from_files()
+
+        last_version = self._verify_version(file_versions)
 
-        if current_version != version:
+        if last_version != str(version):
             raise VersionError(
                 f"Provided version {version} does not match the "
-                f"current version {current_version} in "
-                f"{self.project_file_path}."
+                f"current version {last_version} "
+                f"in '{self.project_file_path}'"
             )
 
     def update_version(
         self, new_version: Version, *, force: bool = False
     ) -> VersionUpdate:
         try:
-            package_version = self.get_current_version()
-            if not force and new_version == package_version:
-                return VersionUpdate(previous=package_version, new=new_version)
+            current_version = self.get_current_version()
+            if not force and new_version == current_version:
+                return VersionUpdate(previous=current_version, new=new_version)
         except VersionError:
             # just ignore current version and override it
-            package_version = None
+            current_version = None
 
-        changed_files = [self.project_file_path]
-        self._update_pom_version(new_version=new_version)
-        self._update_properties_file(new_version=new_version)
-        self._update_swagger_config(new_version=new_version)
+        changed_files = self._update_version_files(new_version)
 
         return VersionUpdate(
-            previous=package_version,
+            previous=current_version,
             new=new_version,
             changed_files=changed_files,
         )
+
+    def _update_version_files(self, new_version) -> List[Path]:
+        config = self._load_config()
+
+        changed_files: List[Path] = []
+        for file_config in config["files"]:
+            file_path = file_config["path"]
+            with (Path.cwd() / file_path).open("r") as input_file_handle:
+                lines = input_file_handle.readlines()
+                line_number = file_config["line"]
+                version_line = lines[line_number - 1]
+
+                matches = re.match(VERSION_PATTERN, version_line, re.DOTALL)
+                if matches is None:
+                    raise VersionError(
+                        f"Line has no version, "
+                        f"file:'{file_path}' "
+                        f"lineNo:{line_number} "
+                        f"content:'{version_line}'"
+                    )
+                lines[line_number - 1] = (
+                    matches.group("pre")
+                    + str(new_version)
+                    + matches.group("post")
+                )
+
+                content = "".join(lines)
+                with (Path.cwd() / file_path).open("w") as output_file_handle:
+                    output_file_handle.write(content)
+                changed_files.append(Path(file_config["path"]))
+        return changed_files
+
+    def _load_config(self) -> Dict[str, Any]:
+        version_config_file = Path.cwd() / "upgradeVersion.json"
+        if not version_config_file.exists():
+            raise VersionError(
+                f"No {version_config_file} config file found. "
+                "This file is required for pontos"
+            )
+
+        with version_config_file.open("r") as f:
+            json_string = f.read()
+            config = json.loads(json_string)
+            return config
+
+    def _read_versions_from_files(self) -> Dict[str, str]:
+        config = self._load_config()
+
+        file_versions = {}
+        for file_config in config["files"]:
+            file_path = file_config["path"]
+            file = Path.cwd() / file_path
+            if not file.exists():
+                raise VersionError(f"No {file} file found.")
+
+            with file.open("r") as f:
+                line_number = file_config["line"]
+                readlines = f.readlines()
+                if line_number - 1 > len(readlines):
+                    raise VersionError(
+                        f"Line number:{line_number} "
+                        f"is beyond file lines:{len(readlines) + 1} "
+                        f"file:'{file_path}'"
+                    )
+                version_line = readlines[line_number - 1]
+                matches = re.match(VERSION_PATTERN, version_line, re.DOTALL)
+                if matches is None:
+                    raise VersionError(
+                        f"Line has no version, "
+                        f"file:'{file_path}' "
+                        f"lineNo:{line_number} "
+                        f"content:'{version_line}'"
+                    )
+                file_versions[file_path] = matches.group("version")
+        return file_versions
+
+    def _verify_version(self, file_versions: Dict[str, str]) -> str:
+        last_version = ""
+        last_file_name = ""
+        for file_name, version in file_versions.items():
+            if last_version == "":
+                last_version = version
+                last_file_name = file_name
+                continue
+
+            if last_version != version:
+                raise VersionError(
+                    f"Versions are not the same "
+                    f"last_file_name:'{last_file_name}' "
+                    f"last_version:'{last_version}' "
+                    f"file_name:'{file_name}' "
+                    f"version:'{version}'"
+                )
+        return last_version
diff --git a/tests/version/commands/test_java.py b/tests/version/commands/test_java.py
index 95143aa8c..50f2a8ece 100644
--- a/tests/version/commands/test_java.py
+++ b/tests/version/commands/test_java.py
@@ -14,366 +14,350 @@
 #
 # You should have received a copy of the GNU General Public License
 # along with this program.  If not, see .
-
-# pylint: disable=line-too-long
-# ruff: noqa: E501
-
 import unittest
 from pathlib import Path
-
-from lxml import etree
+from string import Template
 
 from pontos.testing import temp_directory, temp_file
 from pontos.version import VersionError
 from pontos.version.commands import JavaVersionCommand
-from pontos.version.commands._java import (
-    VERSION_PATTERN,
-    find_file,
-    replace_string_in_file,
+from pontos.version.schemes import SemanticVersioningScheme
+
+TEMPLATE_UPGRADE_VERSION_SINGLE_JSON = """{
+  "files": [
+    {
+      "path": "README.md",
+      "line": 3
+    }
+  ]
+}
+"""
+
+TEMPLATE_UPGRADE_VERSION_MULTI_JSON = """{
+  "files": [
+    {
+      "path": "README.md",
+      "line": 3
+    },
+    {
+      "path": "application.properties",
+      "line": 2
+    }
+  ]
+}
+"""
+
+TEMPLATE_UPGRADE_VERSION_WITH_LINE_JSON = Template(
+    """{
+  "files": [
+    {
+      "path": "README.md",
+      "line": ${LINE_NO}
+    }
+  ]
+}
+"""
 )
-from pontos.version.schemes import PEP440VersioningScheme
-
-
-class TestVersionPattern(unittest.TestCase):
-    def test_version_pattern_swagger(self):
-        # Define the test parameters
-        content = """
-@Configuration
-public class SwaggerConfig {{
-
-    @Bean
-    public OpenAPI metaData() {{
-        return new OpenAPI().info(new Info()
-                .title("Api Documentation")
-                .description("Api Documentation for billing service")
-                .version("{}"));
-    }}
-}}
-        """
-        versions = [
-            "2018.0.1",
-            "2023.1.2a1",
-            "2023.3.3-alpha1.dev1",
-            "2023.4.5-rc2",
-            "2023.1.1beta1",
-        ]
-        replacement = "2023.10.10"
-
-        for version in versions:
-            with temp_file(content=content.format(version)) as tmp:
-                replace_string_in_file(tmp, VERSION_PATTERN, replacement)
-
-                updated_content = tmp.read_text(encoding="utf-8")
-
-                # Verify the replacement was performed correctly
-                self.assertNotRegex(
-                    updated_content, version
-                )  # Pattern should not be present
-                self.assertIn(
-                    replacement, updated_content
-                )  # Replacement should be present
-
-    def test_version_pattern_properties(self):
-        # Define the test parameters
-        content = """
-# application
-spring.application.name=boo
-server.port=1elf
-app.stripe.enabled=false
-app.not.for.resale.keys=
-app.gmsp.booking.startOfHistory=2021
-# sentry
+
+TEMPLATE_UPGRADE_VERSION_MARKDOWN = """# Task service
+
+**task service**: Version {}
+
+## starting the local 
+"""
+
+TEMPLATE_UPGRADE_VERSION_WITH_VERSION_PROPERTIES = """# application
 sentry.release={}
-sentry.tags.service_name=boo
-# actuator
-management.health.db.enabled=false
-# spring
-spring.main.allow-bean-definition-overriding=true
-        """
-        versions = [
-            "2018.0.1",
-            "2023.1.2a1",
-            "2023.3.3-alpha1.dev1",
-            "2023.4.5-rc2",
-            "2023.1.1beta1",
-        ]
-        replacement = "2023.10.10"
-
-        for version in versions:
-            with temp_file(content=content.format(version)) as tmp:
-                replace_string_in_file(tmp, VERSION_PATTERN, replacement)
-
-                updated_content = tmp.read_text(encoding="utf-8")
-
-                # Verify the replacement was performed correctly
-                self.assertNotRegex(
-                    updated_content, version
-                )  # Pattern should not be present
-                self.assertIn(
-                    replacement, updated_content
-                )  # Replacement should be present
-
-
-class TestFindFile(unittest.TestCase):
-    def test_file_found(self):
-        with temp_directory() as temp_dir:
-            deep_path = Path(temp_dir / "foo/bat/config/swagger/")
-            deep_path.mkdir(parents=True)
-            Path(deep_path / "SwaggerConfig.java").touch()
-            self.assertTrue(
-                Path(
-                    temp_dir / "foo/bat/config/swagger/SwaggerConfig.java"
-                ).exists()
-            )
-            filename = Path("SwaggerConfig.java")
-            search_path = temp_dir  # Assuming 'config/swagger' is two levels up
-            search_glob = "**/config/swagger/*"
-
-            result = find_file(filename, search_path, search_glob)
-
-            self.assertIsNotNone(result)
-            self.assertEqual(result.name, filename.name)
-
-    def test_file_not_found(self):
-        with temp_directory() as temp_dir:
-            Path(
-                temp_dir / "foo/bat/config/swagger/SwaggerConfig.java",
-                parents=True,
-            )
-            filename = Path("NonExistentFile.java")
-            search_path = temp_dir
-            search_glob = "**/config/swagger/*"
-            with self.assertLogs("root", level="WARNING") as cm:
-                result = find_file(filename, search_path, search_glob)
-                self.assertEqual(
-                    cm.output,
-                    [
-                        (
-                            f"WARNING:root:File {filename.name} not "
-                            f"found in {search_path.resolve()}."
-                        )
-                    ],
-                )
-
-            self.assertIsNone(result)
-
-
-class TestReplaceString(unittest.TestCase):
-    def test_replace_string_in_file(self):
-        # Define the test parameters
-        content = """
-        Foo, bar
-        baz
-            .version("1.2.3")
-        glubb
-        """
-        pattern = r'\.version\("([0-9]+\.[0-9]+\.[0-9]+)"\)'
-        replacement = "1.2.4"
-
-        with temp_file(content=content) as tmp:
-            replace_string_in_file(tmp, pattern, replacement)
-
-            updated_content = tmp.read_text(encoding="utf-8")
-
-            # Verify the replacement was performed correctly
-            self.assertNotRegex(
-                updated_content, "1.2.3"
-            )  # Pattern should not be present
-            self.assertIn(
-                replacement, updated_content
-            )  # Replacement should be present
-
-    def test_replace_string_in_file_no_match(self):
-        # Define the test parameters
-        content = """
-        Foo, bar
-        baz
-            .versio("1.2.3")
-        glubb
-        """
-        pattern = r'\.version\("([0-9]+\.[0-9]+\.[0-9]+)"\)'
-        replacement = "1.2.4"
-
-        with temp_file(content=content) as tmp:
-            # Call the function under test
-            replace_string_in_file(tmp, pattern, replacement)
-
-            # Read the content of the unmodified file
-            updated_content = tmp.read_text(encoding="utf-8")
-
-            # Verify the content remains unchanged
-            self.assertNotRegex(updated_content, replacement)
-            self.assertEqual(updated_content, content)
+server.port=8080
+"""
 
 
 class GetCurrentJavaVersionCommandTestCase(unittest.TestCase):
-    def test_get_current_version(self):
-        content = """
-        
-        4.0.0net.greenbone.umbrella
-        msspadminservice2023.5.3"""
-        with temp_file(content, name="pom.xml", change_into=True):
-            cmd = JavaVersionCommand(PEP440VersioningScheme)
-            version = cmd.get_current_version()
+    def test_getting_version(self):
+        with temp_directory(change_into=True):
+            version_file_path = Path("upgradeVersion.json")
+            version_file_path.write_text(
+                TEMPLATE_UPGRADE_VERSION_SINGLE_JSON,
+                encoding="utf-8",
+            )
+
+            version = "2023.9.3"
+            readme_file_path = Path("README.md")
+            readme_file_path.write_text(
+                TEMPLATE_UPGRADE_VERSION_MARKDOWN.format(version),
+                encoding="utf-8",
+            )
+
+            result_version = JavaVersionCommand(
+                SemanticVersioningScheme
+            ).get_current_version()
 
             self.assertEqual(
-                version, PEP440VersioningScheme.parse_version("2023.5.3")
+                result_version, SemanticVersioningScheme.parse_version(version)
             )
 
-    def test_no_project_file(self):
+            version_file_path.unlink()
+            readme_file_path.unlink()
+
+    def test_getting_version_no_files_configured(self):
+        exp_err_msg = "no version found"
         with temp_directory(change_into=True), self.assertRaisesRegex(
-            VersionError, ".* file not found."
+            VersionError,
+            exp_err_msg,
         ):
-            cmd = JavaVersionCommand(PEP440VersioningScheme)
-            cmd.get_current_version()
-
-    def test_no_package_version(self):
-        content = """
-        
-            4.0.0net.greenbone.umbrella
-            msspadminservice"""
-        with temp_file(
-            content, name="pom.xml", change_into=True
-        ), self.assertRaisesRegex(VersionError, "Version tag missing in"):
-            cmd = JavaVersionCommand(PEP440VersioningScheme)
-            cmd.get_current_version()
-
-    def test_no_valid_xml_in_pom(self):
-        content = "<"
-        with temp_file(
-            content, name="pom.xml", change_into=True
-        ), self.assertRaisesRegex(
-            VersionError, "StartTag: invalid element name,"
+            version_file_path = Path("upgradeVersion.json")
+            version_file_path.write_text(
+                """{"files": []}""",
+                encoding="utf-8",
+            )
+
+            JavaVersionCommand(SemanticVersioningScheme).get_current_version()
+
+            version_file_path.unlink()
+
+    def test_getting_version_without_version_config(self):
+        exp_err_msg = (
+            r"No /tmp/.*/upgradeVersion\.json config file found\. "
+            r"This file is required for pontos"
+        )
+        with temp_directory(change_into=True), self.assertRaisesRegex(
+            VersionError,
+            exp_err_msg,
         ):
-            cmd = JavaVersionCommand(PEP440VersioningScheme)
-            cmd.get_current_version()
-
-        content = ""
-        with temp_file(
-            content, name="pom.xml", change_into=True
-        ), self.assertRaisesRegex(
-            VersionError, "Premature end of data in tag foo"
+            JavaVersionCommand(SemanticVersioningScheme).get_current_version()
+
+
+class VerifyJavaVersionCommandTestCase(unittest.TestCase):
+    def test_verify_version(self):
+        with temp_directory(change_into=True):
+            version_file_path = Path("upgradeVersion.json")
+            version_file_path.write_text(
+                TEMPLATE_UPGRADE_VERSION_MULTI_JSON, encoding="utf-8"
+            )
+
+            version = "2023.9.3"
+            readme_file_path = Path("README.md")
+            readme_file_path.write_text(
+                TEMPLATE_UPGRADE_VERSION_MARKDOWN.format(version),
+                encoding="utf-8",
+            )
+            properties_file_path = Path("application.properties")
+            properties_file_path.write_text(
+                TEMPLATE_UPGRADE_VERSION_WITH_VERSION_PROPERTIES.format(
+                    version
+                ),
+                encoding="latin-1",
+            )
+
+            JavaVersionCommand(SemanticVersioningScheme).verify_version(
+                SemanticVersioningScheme.parse_version(version)
+            )
+
+            version_file_path.unlink()
+            readme_file_path.unlink()
+            properties_file_path.unlink()
+
+    def test_verify_version_does_not_match(self):
+        exp_err_msg = (
+            r"Provided version 2023\.9\.4 does not match the "
+            + r"current version 2023\.9\.3 "
+            + r"in '/tmp/.*/upgradeVersion\.json'"
+        )
+
+        with temp_directory(change_into=True), self.assertRaisesRegex(
+            VersionError,
+            exp_err_msg,
         ):
-            cmd = JavaVersionCommand(PEP440VersioningScheme)
-            cmd.get_current_version()
+            version_file_path = Path("upgradeVersion.json")
+            version_file_path.write_text(
+                TEMPLATE_UPGRADE_VERSION_SINGLE_JSON, encoding="utf-8"
+            )
+
+            version = "2023.9.3"
+            new_version = "2023.9.4"
+            readme_file_path = Path("README.md")
+            readme_file_path.write_text(
+                TEMPLATE_UPGRADE_VERSION_MARKDOWN.format(version),
+                encoding="utf-8",
+            )
+
+            JavaVersionCommand(SemanticVersioningScheme).verify_version(
+                SemanticVersioningScheme.parse_version(new_version)
+            )
+
+            version_file_path.unlink()
+            readme_file_path.unlink()
 
 
 class UpdateJavaVersionCommandTestCase(unittest.TestCase):
-    swagger_file = "SwaggerConfig.java"
+    def test_update_version(self):
+        with temp_directory(change_into=True):
+            version_file_path = Path("upgradeVersion.json")
+            version_file_path.write_text(
+                TEMPLATE_UPGRADE_VERSION_SINGLE_JSON, encoding="utf-8"
+            )
 
-    def test_update_version_file(self):
-        content = """
-        
-        4.0.0net.greenbone.umbrella
-        msspadminservice2023.5.3"""
+            version = "2023.9.3"
+            readme_file_path = Path("README.md")
+            readme_file_path.write_text(
+                TEMPLATE_UPGRADE_VERSION_MARKDOWN.format(version),
+                encoding="utf-8",
+            )
 
-        with temp_file(content, name="pom.xml", change_into=True) as temp:
-            cmd = JavaVersionCommand(PEP440VersioningScheme)
-            cmd.get_current_version()
-            updated = cmd.update_version(
-                PEP440VersioningScheme.parse_version("2023.6.0")
+            new_version = "2023.9.4"
+            updated_version_obj = JavaVersionCommand(
+                SemanticVersioningScheme
+            ).update_version(
+                SemanticVersioningScheme.parse_version(new_version)
             )
 
             self.assertEqual(
-                updated.previous,
-                PEP440VersioningScheme.parse_version("2023.5.3"),
+                updated_version_obj.previous,
+                SemanticVersioningScheme.parse_version(version),
             )
             self.assertEqual(
-                updated.new, PEP440VersioningScheme.parse_version("2023.6.0")
-            )
-            self.assertEqual(updated.changed_files, [temp.resolve()])
-
-            with temp.open(mode="r", encoding="utf-8") as fp:
-                fake_pom = etree.parse(fp).getroot()
-
-            self.assertEqual(fake_pom.find("{*}version").text, "2023.6.0")
-
-    def test_update_version_develop(self):
-        content = """
-        
-        4.0.0net.greenbone.umbrella
-        msspadminservice2023.5.3"""
-
-        with temp_file(content, name="pom.xml", change_into=True) as temp:
-            swagger_search_path = Path("src").resolve()
-            cmd = JavaVersionCommand(PEP440VersioningScheme)
-            new_version = PEP440VersioningScheme.parse_version("2023.6.0.dev1")
-            with self.assertLogs("root", level="WARNING") as cm:
-                updated = cmd.update_version(new_version)
-                self.assertEqual(
-                    cm.output,
-                    [
-                        (
-                            f"WARNING:root:File {self.swagger_file} not "
-                            f"found in {swagger_search_path.resolve()}."
-                        )
-                    ],
-                )
-
-            self.assertEqual(
-                updated.previous,
-                PEP440VersioningScheme.parse_version("2023.5.3"),
+                updated_version_obj.new,
+                SemanticVersioningScheme.parse_version(new_version),
             )
             self.assertEqual(
-                updated.new,
-                PEP440VersioningScheme.parse_version("2023.6.0.dev1"),
+                updated_version_obj.changed_files, [Path("README.md")]
             )
-            self.assertEqual(updated.changed_files, [temp.resolve()])
 
-            with temp.open(mode="r", encoding="utf-8") as fp:
-                fake_pom = etree.parse(fp).getroot()
+            content = readme_file_path.read_text(encoding="UTF-8")
+            self.assertEqual(
+                content,
+                TEMPLATE_UPGRADE_VERSION_MARKDOWN.format(new_version),
+            )
 
-            self.assertEqual(fake_pom.find("{*}version").text, "2023.6.0.dev1")
+            version_file_path.unlink()
+            readme_file_path.unlink()
 
-    def test_no_update(self):
-        content = """
-        
-        4.0.0net.greenbone.umbrella
-        msspadminservice2023.5.3"""
+    def test_no_update_version(self):
+        with temp_directory(change_into=True):
+            version_file_path = Path("upgradeVersion.json")
+            version_file_path.write_text(
+                TEMPLATE_UPGRADE_VERSION_SINGLE_JSON,
+                encoding="utf-8",
+            )
 
-        with temp_file(content, name="pom.xml", change_into=True) as temp:
-            cmd = JavaVersionCommand(PEP440VersioningScheme)
-            updated = cmd.update_version(
-                PEP440VersioningScheme.parse_version("2023.5.3")
+            version = "2023.9.3"
+            readme_file_path = Path("README.md")
+            readme_file_path.write_text(
+                TEMPLATE_UPGRADE_VERSION_MARKDOWN.format(version),
+                encoding="utf-8",
             )
 
+            updated_version_obj = JavaVersionCommand(
+                SemanticVersioningScheme
+            ).update_version(SemanticVersioningScheme.parse_version(version))
+
             self.assertEqual(
-                updated.previous,
-                PEP440VersioningScheme.parse_version("2023.5.3"),
+                updated_version_obj.previous,
+                SemanticVersioningScheme.parse_version(version),
             )
             self.assertEqual(
-                updated.new, PEP440VersioningScheme.parse_version("2023.5.3")
+                updated_version_obj.new,
+                SemanticVersioningScheme.parse_version(version),
+            )
+            self.assertEqual(
+                updated_version_obj.changed_files,
+                [],
+            )
+
+            content = readme_file_path.read_text(encoding="UTF-8")
+            self.assertEqual(
+                content,
+                TEMPLATE_UPGRADE_VERSION_MARKDOWN.format(version),
             )
-            self.assertEqual(updated.changed_files, [])
 
-            with temp.open(mode="r", encoding="utf-8") as fp:
-                fake_pom = etree.parse(fp).getroot()
+            version_file_path.unlink()
+            readme_file_path.unlink()
 
-            self.assertEqual(fake_pom.find("{*}version").text, "2023.5.3")
+    def test_forced_update_version(self):
+        with temp_directory(change_into=True):
+            version_file_path = Path("upgradeVersion.json")
+            version_file_path.write_text(
+                TEMPLATE_UPGRADE_VERSION_SINGLE_JSON,
+                encoding="utf-8",
+            )
 
-    def test_forced_update(self):
-        content = """
-        
-        4.0.0net.greenbone.umbrella
-        msspadminservice2023.5.3"""
+            version = "2023.9.3"
+            readme_file_path = Path("README.md")
+            readme_file_path.write_text(
+                TEMPLATE_UPGRADE_VERSION_MARKDOWN.format(version),
+                encoding="utf-8",
+            )
 
-        with temp_file(content, name="pom.xml", change_into=True) as temp:
-            cmd = JavaVersionCommand(PEP440VersioningScheme)
-            updated = cmd.update_version(
-                PEP440VersioningScheme.parse_version("2023.5.3"), force=True
+            updated_version_obj = JavaVersionCommand(
+                SemanticVersioningScheme
+            ).update_version(
+                SemanticVersioningScheme.parse_version(version), force=True
             )
 
             self.assertEqual(
-                updated.previous,
-                PEP440VersioningScheme.parse_version("2023.5.3"),
+                updated_version_obj.previous,
+                SemanticVersioningScheme.parse_version(version),
+            )
+            self.assertEqual(
+                updated_version_obj.new,
+                SemanticVersioningScheme.parse_version(version),
             )
             self.assertEqual(
-                updated.new, PEP440VersioningScheme.parse_version("2023.5.3")
+                updated_version_obj.changed_files,
+                [Path("README.md")],
+            )
+
+            content = readme_file_path.read_text(encoding="UTF-8")
+            self.assertEqual(
+                content,
+                TEMPLATE_UPGRADE_VERSION_MARKDOWN.format(version),
+            )
+
+            version_file_path.unlink()
+            readme_file_path.unlink()
+
+    def test_update_version_upgrade_config_with_wrong_line_number(self):
+        exp_err_msg = (
+            "Line has no version, "
+            "file:'README.md' "
+            "lineNo:4 "
+            "content:'\n'"
+        )
+        with temp_directory(change_into=True), self.assertRaisesRegex(
+            VersionError,
+            exp_err_msg,
+        ):
+            version_file_path = Path("upgradeVersion.json")
+            version_file_path.write_text(
+                TEMPLATE_UPGRADE_VERSION_WITH_LINE_JSON.substitute(LINE_NO="4"),
+                encoding="utf-8",
             )
-            self.assertEqual(updated.changed_files, [temp.resolve()])
 
-            with temp.open(mode="r", encoding="utf-8") as fp:
-                fake_pom = etree.parse(fp).getroot()
+            version = "2023.9.3"
+            readme_file_path = Path("README.md")
+            readme_file_path.write_text(
+                TEMPLATE_UPGRADE_VERSION_MARKDOWN.format(version),
+                encoding="utf-8",
+            )
+
+            new_version = "2023.9.4"
+            JavaVersionCommand(SemanticVersioningScheme).update_version(
+                SemanticVersioningScheme.parse_version(new_version)
+            )
+
+            version_file_path.unlink()
+            readme_file_path.unlink()
+
+
+class ProjectFileJavaVersionCommandTestCase(unittest.TestCase):
+    def test_project_file_not_found(self):
+        with temp_directory(change_into=True):
+            cmd = JavaVersionCommand(SemanticVersioningScheme)
+
+            self.assertFalse(cmd.project_found())
+
+    def test_project_file_found(self):
+        with temp_file(name="upgradeVersion.json", change_into=True):
+            cmd = JavaVersionCommand(SemanticVersioningScheme)
 
-            self.assertEqual(fake_pom.find("{*}version").text, "2023.5.3")
+            self.assertTrue(cmd.project_found())