From 6963eabf9e4828f377c9554acf489fed15adc6e3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=9D=D0=B8=D0=BA=D0=B8=D1=82=D0=B0=20=D0=92=D0=B5=D0=BB?= =?UTF-8?q?=D0=B8=D0=BA=D0=B8=D0=B9?= Date: Mon, 27 Nov 2023 00:23:55 +0500 Subject: [PATCH 01/13] Delete unused files --- src/test/testData/description.txt | 1 + src/test/testData/rename/foo.xml | 3 --- src/test/testData/rename/foo_after.xml | 3 --- 3 files changed, 1 insertion(+), 6 deletions(-) create mode 100644 src/test/testData/description.txt delete mode 100644 src/test/testData/rename/foo.xml delete mode 100644 src/test/testData/rename/foo_after.xml diff --git a/src/test/testData/description.txt b/src/test/testData/description.txt new file mode 100644 index 0000000..7aadeb6 --- /dev/null +++ b/src/test/testData/description.txt @@ -0,0 +1 @@ +The current folder is used to generate test data \ No newline at end of file diff --git a/src/test/testData/rename/foo.xml b/src/test/testData/rename/foo.xml deleted file mode 100644 index b21e9f2..0000000 --- a/src/test/testData/rename/foo.xml +++ /dev/null @@ -1,3 +0,0 @@ - - 1>Foo - diff --git a/src/test/testData/rename/foo_after.xml b/src/test/testData/rename/foo_after.xml deleted file mode 100644 index 980ca96..0000000 --- a/src/test/testData/rename/foo_after.xml +++ /dev/null @@ -1,3 +0,0 @@ - - Foo - From 0a4e5890da12fc385718a5fa1d0de10f60e40c12 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=9D=D0=B8=D0=BA=D0=B8=D1=82=D0=B0=20=D0=92=D0=B5=D0=BB?= =?UTF-8?q?=D0=B8=D0=BA=D0=B8=D0=B9?= Date: Mon, 27 Nov 2023 01:12:29 +0500 Subject: [PATCH 02/13] (#8) Fix relative paths handling --- .../gitglobalhookslocator/git/HooksFolder.kt | 2 +- .../git/extensions/GitExtensions.kt | 28 +++++- .../git/utils/SystemPathUtils.kt | 32 ++++++ .../gitTests/GetGlobalHooksPathTests.kt | 98 ++++++++++++++++++- .../gitTests/testEngine/HookTestBase.kt | 2 +- 5 files changed, 155 insertions(+), 7 deletions(-) create mode 100644 src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/utils/SystemPathUtils.kt diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/HooksFolder.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/HooksFolder.kt index ac2a431..9a5c6f9 100644 --- a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/HooksFolder.kt +++ b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/HooksFolder.kt @@ -34,7 +34,7 @@ class HooksFolder(git: Git) { = hooks.isEmpty() init { - path = Path.of(git.getGlobalHooksPath()) + path = git.getGlobalHooksPath() val files = try { Files.list(path) diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/extensions/GitExtensions.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/extensions/GitExtensions.kt index aaafdf8..8582149 100644 --- a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/extensions/GitExtensions.kt +++ b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/extensions/GitExtensions.kt @@ -1,14 +1,36 @@ package com.github.y0ung3r.gitglobalhookslocator.git.extensions import com.github.y0ung3r.gitglobalhookslocator.git.Git +import com.github.y0ung3r.gitglobalhookslocator.git.utils.SystemPathUtils +import java.nio.file.Path -fun Git.getGlobalHooksPath(): String { - val path = executeCommand( +private const val SLASHES_PATTERN = "[/\\\\]" +private const val HOME_PATTERN = "^~$SLASHES_PATTERN" +private const val CURRENT_DIR_PATTERN = "^.$SLASHES_PATTERN" +private const val ROOT_PATTERN = "^$SLASHES_PATTERN" + +fun Git.getGlobalHooksPath(): Path { + val rawPath = executeCommand( Git.GIT_CONFIG_COMMAND, Git.GIT_GLOBAL_COMMAND, Git.GIT_CONFIG_GET_COMMAND, Git.GIT_HOOKS_PATH_SECTION ) - return path.value + val targetPath = rawPath.value + .replaceFirst( + Regex(HOME_PATTERN), + SystemPathUtils.getUserHomePath() + ) + .replaceFirst( + Regex(CURRENT_DIR_PATTERN), + SystemPathUtils.getCurrentDirectoryPath() + ) + .replaceFirst( + Regex(ROOT_PATTERN), + SystemPathUtils.getRootPath() + ) + + return Path.of(targetPath) + .toAbsolutePath() } \ No newline at end of file diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/utils/SystemPathUtils.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/utils/SystemPathUtils.kt new file mode 100644 index 0000000..2018cd3 --- /dev/null +++ b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/utils/SystemPathUtils.kt @@ -0,0 +1,32 @@ +package com.github.y0ung3r.gitglobalhookslocator.git.utils + +object SystemPathUtils { + private const val ROOT_KEY = "SystemDrive" + private const val USER_HOME_KEY = "user.home" + private const val USER_DIR_KEY = "user.dir" + + @JvmStatic + private fun wrapWithSlash(path: String): String + = "$path/" + + @JvmStatic + private fun getSystemPath(key: String): String { + val systemPath = System + .getProperty(key) + .replace("\\", "/") // The replacement eliminates the need to escape the string + + return wrapWithSlash(systemPath) + } + + @JvmStatic + fun getUserHomePath(): String + = getSystemPath(USER_HOME_KEY) + + @JvmStatic + fun getCurrentDirectoryPath(): String + = getSystemPath(USER_DIR_KEY) + + @JvmStatic + fun getRootPath(): String + = wrapWithSlash(System.getenv(ROOT_KEY)) +} diff --git a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt index b3419b8..8d87edf 100644 --- a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt +++ b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt @@ -4,14 +4,16 @@ import com.github.y0ung3r.gitglobalhookslocator.gitTests.testEngine.RespondInter import com.github.y0ung3r.gitglobalhookslocator.git.Git import com.github.y0ung3r.gitglobalhookslocator.git.cli.CliResponse import com.github.y0ung3r.gitglobalhookslocator.git.extensions.getGlobalHooksPath +import com.github.y0ung3r.gitglobalhookslocator.git.utils.SystemPathUtils import org.junit.Assert.assertEquals import org.junit.Test +import java.nio.file.Path class GetGlobalHooksPathTests { @Test - fun `Should returns global hooks path`() { + fun `Should returns absolute global hooks path using absolute path`() { // Arrange - val expectedPath = "~/.git/hooks" + val expectedPath = "C:/Users/user/.git/hooks" val sut = Git( RespondInterchangeably( CliResponse(Git.minRequiredVersion.toString()), @@ -22,6 +24,98 @@ class GetGlobalHooksPathTests { // Act val actualPath = sut.getGlobalHooksPath() + // Assert + assertEquals(Path.of(expectedPath), actualPath) + } + + @Test + fun `Should returns absolute global hooks path using relative path`() { + // Arrange + val expectedPath = Path.of( + SystemPathUtils.getCurrentDirectoryPath(), + ".git", + "hooks" + ) + + val sut = Git( + RespondInterchangeably( + CliResponse(Git.minRequiredVersion.toString()), + CliResponse(".git/hooks") + ) + ) + + // Act + val actualPath = sut.getGlobalHooksPath() + + // Assert + assertEquals(expectedPath, actualPath) + } + + @Test + fun `Should resolve path using $HOME variable`() { + // Arrange + val expectedPath = Path.of( + SystemPathUtils.getUserHomePath(), + ".git", + "hooks" + ) + + val sut = Git( + RespondInterchangeably( + CliResponse(Git.minRequiredVersion.toString()), + CliResponse("~/.git/hooks") + ) + ) + + // Act + val actualPath = sut.getGlobalHooksPath() + + // Assert + assertEquals(expectedPath, actualPath) + } + + @Test + fun `Should resolve path using $CURRENTDIR variable`() { + // Arrange + val expectedPath = Path.of( + SystemPathUtils.getCurrentDirectoryPath(), + ".git", + "hooks" + ) + + val sut = Git( + RespondInterchangeably( + CliResponse(Git.minRequiredVersion.toString()), + CliResponse("./.git/hooks") + ) + ) + + // Act + val actualPath = sut.getGlobalHooksPath() + + // Assert + assertEquals(expectedPath, actualPath) + } + + @Test + fun `Should resolve path using root pointer`() { + // Arrange + val expectedPath = Path.of( + SystemPathUtils.getRootPath(), + ".git", + "hooks" + ) + + val sut = Git( + RespondInterchangeably( + CliResponse(Git.minRequiredVersion.toString()), + CliResponse("/.git/hooks") + ) + ) + + // Act + val actualPath = sut.getGlobalHooksPath() + // Assert assertEquals(expectedPath, actualPath) } diff --git a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/testEngine/HookTestBase.kt b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/testEngine/HookTestBase.kt index 50c0838..790b1bb 100644 --- a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/testEngine/HookTestBase.kt +++ b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/testEngine/HookTestBase.kt @@ -7,7 +7,7 @@ import java.nio.file.Path abstract class HookTestBase { companion object { - const val BASE_PATH = "src/test/testData/hooks" + private const val BASE_PATH = "src/test/testData/hooks" private const val DISABLED_HOOK = "disabled" private const val ENABLED_HOOK = "enabled" From 7b717c663b1c25b16965ac894f872cf5f2b09bff Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=9D=D0=B8=D0=BA=D0=B8=D1=82=D0=B0=20=D0=92=D0=B5=D0=BB?= =?UTF-8?q?=D0=B8=D0=BA=D0=B8=D0=B9?= Date: Mon, 27 Nov 2023 01:28:01 +0500 Subject: [PATCH 03/13] Fix tests --- .../git/extensions/GitExtensions.kt | 5 ---- .../git/utils/SystemPathUtils.kt | 11 +-------- .../gitTests/GetGlobalHooksPathTests.kt | 23 ------------------- 3 files changed, 1 insertion(+), 38 deletions(-) diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/extensions/GitExtensions.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/extensions/GitExtensions.kt index 8582149..262da5f 100644 --- a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/extensions/GitExtensions.kt +++ b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/extensions/GitExtensions.kt @@ -7,7 +7,6 @@ import java.nio.file.Path private const val SLASHES_PATTERN = "[/\\\\]" private const val HOME_PATTERN = "^~$SLASHES_PATTERN" private const val CURRENT_DIR_PATTERN = "^.$SLASHES_PATTERN" -private const val ROOT_PATTERN = "^$SLASHES_PATTERN" fun Git.getGlobalHooksPath(): Path { val rawPath = executeCommand( @@ -26,10 +25,6 @@ fun Git.getGlobalHooksPath(): Path { Regex(CURRENT_DIR_PATTERN), SystemPathUtils.getCurrentDirectoryPath() ) - .replaceFirst( - Regex(ROOT_PATTERN), - SystemPathUtils.getRootPath() - ) return Path.of(targetPath) .toAbsolutePath() diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/utils/SystemPathUtils.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/utils/SystemPathUtils.kt index 2018cd3..fee9695 100644 --- a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/utils/SystemPathUtils.kt +++ b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/utils/SystemPathUtils.kt @@ -1,21 +1,16 @@ package com.github.y0ung3r.gitglobalhookslocator.git.utils object SystemPathUtils { - private const val ROOT_KEY = "SystemDrive" private const val USER_HOME_KEY = "user.home" private const val USER_DIR_KEY = "user.dir" - @JvmStatic - private fun wrapWithSlash(path: String): String - = "$path/" - @JvmStatic private fun getSystemPath(key: String): String { val systemPath = System .getProperty(key) .replace("\\", "/") // The replacement eliminates the need to escape the string - return wrapWithSlash(systemPath) + return "$systemPath/" } @JvmStatic @@ -25,8 +20,4 @@ object SystemPathUtils { @JvmStatic fun getCurrentDirectoryPath(): String = getSystemPath(USER_DIR_KEY) - - @JvmStatic - fun getRootPath(): String - = wrapWithSlash(System.getenv(ROOT_KEY)) } diff --git a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt index 8d87edf..d19da67 100644 --- a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt +++ b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt @@ -96,27 +96,4 @@ class GetGlobalHooksPathTests { // Assert assertEquals(expectedPath, actualPath) } - - @Test - fun `Should resolve path using root pointer`() { - // Arrange - val expectedPath = Path.of( - SystemPathUtils.getRootPath(), - ".git", - "hooks" - ) - - val sut = Git( - RespondInterchangeably( - CliResponse(Git.minRequiredVersion.toString()), - CliResponse("/.git/hooks") - ) - ) - - // Act - val actualPath = sut.getGlobalHooksPath() - - // Assert - assertEquals(expectedPath, actualPath) - } } \ No newline at end of file From 89d0a318c08ea646f593e4fa8a417cc2f020666f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=9D=D0=B8=D0=BA=D0=B8=D1=82=D0=B0=20=D0=92=D0=B5=D0=BB?= =?UTF-8?q?=D0=B8=D0=BA=D0=B8=D0=B9?= Date: Mon, 27 Nov 2023 01:37:34 +0500 Subject: [PATCH 04/13] Fix compiler warnings --- .../toolWindow/GitGlobalHooksLocatorWindow.kt | 3 -- .../gitTests/GetGlobalHooksPathTests.kt | 29 ++++--------------- .../gitTests/SemanticVersionTests.kt | 4 --- 3 files changed, 5 insertions(+), 31 deletions(-) diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/ui/toolWindow/GitGlobalHooksLocatorWindow.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/ui/toolWindow/GitGlobalHooksLocatorWindow.kt index 731fbff..f34b0aa 100644 --- a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/ui/toolWindow/GitGlobalHooksLocatorWindow.kt +++ b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/ui/toolWindow/GitGlobalHooksLocatorWindow.kt @@ -8,10 +8,7 @@ import com.intellij.ide.wizard.withVisualPadding import com.intellij.openapi.wm.ToolWindow import com.intellij.ui.components.JBCheckBox import com.intellij.ui.dsl.builder.Align -import com.intellij.ui.dsl.builder.LabelPosition import com.intellij.ui.dsl.builder.panel -import com.intellij.ui.dsl.gridLayout.HorizontalAlign -import com.intellij.ui.dsl.gridLayout.VerticalAlign import javax.swing.JComponent class GitGlobalHooksLocatorWindow(toolWindow: ToolWindow) { diff --git a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt index d19da67..77d8a0d 100644 --- a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt +++ b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt @@ -10,37 +10,18 @@ import org.junit.Test import java.nio.file.Path class GetGlobalHooksPathTests { - @Test - fun `Should returns absolute global hooks path using absolute path`() { - // Arrange - val expectedPath = "C:/Users/user/.git/hooks" - val sut = Git( - RespondInterchangeably( - CliResponse(Git.minRequiredVersion.toString()), - CliResponse(expectedPath) - ) - ) - - // Act - val actualPath = sut.getGlobalHooksPath() - - // Assert - assertEquals(Path.of(expectedPath), actualPath) - } - @Test fun `Should returns absolute global hooks path using relative path`() { // Arrange - val expectedPath = Path.of( - SystemPathUtils.getCurrentDirectoryPath(), - ".git", - "hooks" - ) + val relativePath = "/.git/hooks" + val expectedPath = Path + .of(relativePath) + .toAbsolutePath() val sut = Git( RespondInterchangeably( CliResponse(Git.minRequiredVersion.toString()), - CliResponse(".git/hooks") + CliResponse(relativePath) ) ) diff --git a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/SemanticVersionTests.kt b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/SemanticVersionTests.kt index e054a1e..7242d57 100644 --- a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/SemanticVersionTests.kt +++ b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/SemanticVersionTests.kt @@ -1,11 +1,7 @@ package com.github.y0ung3r.gitglobalhookslocator.gitTests import com.github.y0ung3r.gitglobalhookslocator.git.SemanticVersion -import com.github.y0ung3r.gitglobalhookslocator.git.exceptions.ProvidedSemanticVersionIsInvalidException import org.junit.Assert.assertEquals -import org.junit.Test -import org.junit.runner.RunWith -import org.junit.runners.Parameterized import org.junit.runners.Parameterized.Parameters //@RunWith(Parameterized::class) From 0d672fcfa0e2ac4cf2fcdb901f462bca38fa6fbd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=9D=D0=B8=D0=BA=D0=B8=D1=82=D0=B0=20=D0=92=D0=B5=D0=BB?= =?UTF-8?q?=D0=B8=D0=BA=D0=B8=D0=B9?= Date: Mon, 27 Nov 2023 01:54:58 +0500 Subject: [PATCH 05/13] Refactor tests related to hooks --- .../gitglobalhookslocator/git/HookEntry.kt | 4 ++-- .../gitglobalhookslocator/git/HooksFolder.kt | 6 +++--- .../gitTests/HookEntryTests.kt | 4 ++-- .../gitTests/HooksFolderTests.kt | 17 +++++++++++++++-- .../gitTests/testEngine/HookTestBase.kt | 2 +- 5 files changed, 23 insertions(+), 10 deletions(-) diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/HookEntry.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/HookEntry.kt index 9c93052..023c7ef 100644 --- a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/HookEntry.kt +++ b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/HookEntry.kt @@ -20,12 +20,12 @@ class HookEntry(private var file: File) { val name: String = HooksFolder - .availableHooks + .supportedHooks .first { file.nameWithoutExtension.contains(it) } fun isDisabled() = HooksFolder - .availableHooks + .supportedHooks .all { it != file.nameWithoutExtension } fun enable() { diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/HooksFolder.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/HooksFolder.kt index 9a5c6f9..ba3fde4 100644 --- a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/HooksFolder.kt +++ b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/HooksFolder.kt @@ -10,7 +10,7 @@ import java.nio.file.NoSuchFileException class HooksFolder(git: Git) { companion object { @JvmStatic - val availableHooks = arrayOf( + val supportedHooks = arrayOf( "pre-commit", "prepare-commit-msg", "commit-msg", @@ -41,7 +41,7 @@ class HooksFolder(git: Git) { } catch (exception: NoSuchFileException) { thisLogger() - .info("Provided hooks path doesn't exists", exception) + .info("Provided hooks path is not valid", exception) emptyList() .stream() @@ -49,7 +49,7 @@ class HooksFolder(git: Git) { hooks = files .filter { - availableHooks + supportedHooks .any { hookName -> it.fileName.nameWithoutExtension.contains(hookName) } } diff --git a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/HookEntryTests.kt b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/HookEntryTests.kt index 067efc6..10e517f 100644 --- a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/HookEntryTests.kt +++ b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/HookEntryTests.kt @@ -22,7 +22,7 @@ class HookEntryTests(private val hookName: String) : HookTestBase() { } @Test - fun `Should be disabled if hook name not contains in available Git hooks`() { // TODO: Rename test + fun `Hook should be disabled`() { // Arrange val sut = HookEntry.load(getDisabledHookPath(hookName)) @@ -31,7 +31,7 @@ class HookEntryTests(private val hookName: String) : HookTestBase() { } @Test - fun `Should be enabled if hook name contains in available Git hooks`() { // TODO: Rename test + fun `Hook should be enabled`() { // Arrange val sut = HookEntry.load(getEnabledHookPath(hookName)) diff --git a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/HooksFolderTests.kt b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/HooksFolderTests.kt index 0410649..1fe53f5 100644 --- a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/HooksFolderTests.kt +++ b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/HooksFolderTests.kt @@ -7,6 +7,7 @@ import com.github.y0ung3r.gitglobalhookslocator.git.HooksFolder import com.github.y0ung3r.gitglobalhookslocator.git.cli.CliResponse import org.junit.Assert import org.junit.Assert.assertEquals +import org.junit.Assert.assertTrue import org.junit.Test import java.nio.file.Path @@ -21,6 +22,18 @@ class HooksFolderTests : HookTestBase() { ) } + @Test + fun `Should be empty if provided empty path`() { + // Arrange + val git = getGit(Path.of("")) + + // Act + val sut = HooksFolder(git) + + // Assert + assertTrue(sut.isEmpty()) + } + @Test fun `Should load all hooks from disabled hooks path`() { // Arrange @@ -30,7 +43,7 @@ class HooksFolderTests : HookTestBase() { val sut = HooksFolder(git) // Assert - assertEquals(HooksFolder.availableHooks.size, sut.hooks.size) + assertEquals(HooksFolder.supportedHooks.size, sut.hooks.size) } @Test @@ -42,7 +55,7 @@ class HooksFolderTests : HookTestBase() { val sut = HooksFolder(git) // Assert - assertEquals(HooksFolder.availableHooks.size, sut.hooks.size) + assertEquals(HooksFolder.supportedHooks.size, sut.hooks.size) } @Test diff --git a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/testEngine/HookTestBase.kt b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/testEngine/HookTestBase.kt index 790b1bb..868377a 100644 --- a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/testEngine/HookTestBase.kt +++ b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/testEngine/HookTestBase.kt @@ -65,7 +65,7 @@ abstract class HookTestBase { @JvmStatic @Parameterized.Parameters fun hookNames() - = HooksFolder.availableHooks + = HooksFolder.supportedHooks } init { From 03d4bcfc731874f4ce9c89f9f15da8780bc5b77c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=9D=D0=B8=D0=BA=D0=B8=D1=82=D0=B0=20=D0=92=D0=B5=D0=BB?= =?UTF-8?q?=D0=B8=D0=BA=D0=B8=D0=B9?= Date: Mon, 27 Nov 2023 02:46:45 +0500 Subject: [PATCH 06/13] (#6) Fix empty core.hooksPath value handling --- .../y0ung3r/gitglobalhookslocator/git/Git.kt | 12 +++-- .../git/cli/DefaultCliCommandExecutor.kt | 29 ++++++++--- .../git/cli/NotFoundCliResponse.kt | 4 +- .../exceptions/GitCommandNotFoundException.kt | 13 ++++- .../git/extensions/GitExtensions.kt | 27 ++++++++--- .../gitTests/GetGlobalHooksPathTests.kt | 48 +++++++++++++++++++ .../gitTests/GetInstalledVersionTests.kt | 11 +++++ 7 files changed, 124 insertions(+), 20 deletions(-) diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/Git.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/Git.kt index 24f80c9..a55893f 100644 --- a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/Git.kt +++ b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/Git.kt @@ -1,12 +1,13 @@ package com.github.y0ung3r.gitglobalhookslocator.git import com.github.y0ung3r.gitglobalhookslocator.git.cli.DefaultCliCommandExecutor +import com.github.y0ung3r.gitglobalhookslocator.git.cli.EmptyCliResponse import com.github.y0ung3r.gitglobalhookslocator.git.cli.NotFoundCliResponse +import com.github.y0ung3r.gitglobalhookslocator.git.cli.interfaces.CliCommandExecutor import com.github.y0ung3r.gitglobalhookslocator.git.exceptions.GitCommandNotFoundException import com.github.y0ung3r.gitglobalhookslocator.git.exceptions.GitIsNotInstalledException import com.github.y0ung3r.gitglobalhookslocator.git.exceptions.GitVersionIsNotSupportedException import com.github.y0ung3r.gitglobalhookslocator.git.extensions.toGitResponse -import com.github.y0ung3r.gitglobalhookslocator.git.cli.interfaces.CliCommandExecutor class Git(private val commandExecutor: CliCommandExecutor) { companion object { @@ -16,6 +17,7 @@ class Git(private val commandExecutor: CliCommandExecutor) { const val GIT_GLOBAL_COMMAND = "--global" const val GIT_CONFIG_GET_COMMAND = "--get" const val GIT_HOOKS_PATH_SECTION = "core.hooksPath" + const val DEFAULT_HOOKS_PATH = "./.git/hooks" @JvmStatic val minRequiredVersion = SemanticVersion(2, 9, 0) @@ -41,13 +43,17 @@ class Git(private val commandExecutor: CliCommandExecutor) { processBuilder.redirectErrorStream(true) return when (val response = commandExecutor.execute(processBuilder)) { - is NotFoundCliResponse -> throw GitCommandNotFoundException(*params) + is NotFoundCliResponse -> throw GitCommandNotFoundException(response.value, *params) else -> response.toGitResponse() } } fun getInstalledVersion() : SemanticVersion { - val installedVersion = executeCommand(GIT_VERSION_COMMAND) + val installedVersion = try { + executeCommand(GIT_VERSION_COMMAND) + } catch (exception: GitCommandNotFoundException) { + GitResponse(EmptyCliResponse()) + } return when { !installedVersion.isEmpty() -> SemanticVersion.parse(installedVersion.value) diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/cli/DefaultCliCommandExecutor.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/cli/DefaultCliCommandExecutor.kt index 82aa735..f6352bb 100644 --- a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/cli/DefaultCliCommandExecutor.kt +++ b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/cli/DefaultCliCommandExecutor.kt @@ -2,31 +2,48 @@ package com.github.y0ung3r.gitglobalhookslocator.git.cli import com.github.y0ung3r.gitglobalhookslocator.git.cli.interfaces.CliCommandExecutor import java.io.BufferedReader +import java.io.IOException import java.io.InputStreamReader import java.nio.charset.StandardCharsets class DefaultCliCommandExecutor : CliCommandExecutor { private companion object { const val TERMINATION_EXIT_CODE = 0 + const val NOT_FOUND_EXIT_CODE = 1 } - override fun execute(processBuilder: ProcessBuilder) : CliResponse { + override fun execute(processBuilder: ProcessBuilder): CliResponse + = try { + handle(processBuilder) + } catch (exception: Exception) { + when (exception) { + is IOException, is InterruptedException, is RuntimeException + -> NotFoundCliResponse(exception.message) + + else -> throw exception + } + } + + private fun handle(processBuilder: ProcessBuilder) : CliResponse { val process = processBuilder.start() val streamReader = InputStreamReader(process.inputStream, StandardCharsets.UTF_8) val bufferedReader = BufferedReader(streamReader) - val response = StringBuilder() + val responseBuilder = StringBuilder() var line: String? = bufferedReader.readLine() while (line != null) { - response.append(line) - response.append(System.lineSeparator()) + responseBuilder.append(line) + responseBuilder.append(System.lineSeparator()) line = bufferedReader.readLine() } + val response = responseBuilder.toString() + return when (process.waitFor()) { - TERMINATION_EXIT_CODE -> CliResponse(response.toString()) - else -> NotFoundCliResponse(response.toString()) + TERMINATION_EXIT_CODE -> CliResponse(response) + NOT_FOUND_EXIT_CODE -> NotFoundCliResponse(response) + else -> EmptyCliResponse() } } } \ No newline at end of file diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/cli/NotFoundCliResponse.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/cli/NotFoundCliResponse.kt index 536fed5..8c51466 100644 --- a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/cli/NotFoundCliResponse.kt +++ b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/cli/NotFoundCliResponse.kt @@ -1,4 +1,4 @@ package com.github.y0ung3r.gitglobalhookslocator.git.cli -class NotFoundCliResponse(details: String) - : CliResponse(details) \ No newline at end of file +class NotFoundCliResponse(details: String? = null) + : CliResponse(details ?: "") \ No newline at end of file diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/exceptions/GitCommandNotFoundException.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/exceptions/GitCommandNotFoundException.kt index 184eb93..7cada95 100644 --- a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/exceptions/GitCommandNotFoundException.kt +++ b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/exceptions/GitCommandNotFoundException.kt @@ -1,4 +1,13 @@ package com.github.y0ung3r.gitglobalhookslocator.git.exceptions -class GitCommandNotFoundException(vararg params: String) - : Exception("Native Git command \"git ${params.joinToString(" ")}\" not found") \ No newline at end of file +class GitCommandNotFoundException(details: String, vararg params: String) + : Exception("Native Git command \"git ${params.joinToString(" ")}\" not found ${mapDetails(details)}") +{ + private companion object { + fun mapDetails(details: String): String + = when (details) { + "" -> details + else -> "($details)" + } + } +} \ No newline at end of file diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/extensions/GitExtensions.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/extensions/GitExtensions.kt index 262da5f..612b50c 100644 --- a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/extensions/GitExtensions.kt +++ b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/extensions/GitExtensions.kt @@ -1,22 +1,34 @@ package com.github.y0ung3r.gitglobalhookslocator.git.extensions import com.github.y0ung3r.gitglobalhookslocator.git.Git +import com.github.y0ung3r.gitglobalhookslocator.git.GitResponse +import com.github.y0ung3r.gitglobalhookslocator.git.cli.CliResponse +import com.github.y0ung3r.gitglobalhookslocator.git.exceptions.GitCommandNotFoundException import com.github.y0ung3r.gitglobalhookslocator.git.utils.SystemPathUtils import java.nio.file.Path private const val SLASHES_PATTERN = "[/\\\\]" +private const val EMPTY_PATTERN = "^$" private const val HOME_PATTERN = "^~$SLASHES_PATTERN" private const val CURRENT_DIR_PATTERN = "^.$SLASHES_PATTERN" fun Git.getGlobalHooksPath(): Path { - val rawPath = executeCommand( - Git.GIT_CONFIG_COMMAND, - Git.GIT_GLOBAL_COMMAND, - Git.GIT_CONFIG_GET_COMMAND, - Git.GIT_HOOKS_PATH_SECTION - ) + val rawPath = try { + executeCommand( + Git.GIT_CONFIG_COMMAND, + Git.GIT_GLOBAL_COMMAND, + Git.GIT_CONFIG_GET_COMMAND, + Git.GIT_HOOKS_PATH_SECTION + ) + } catch (exception: GitCommandNotFoundException) { + GitResponse(CliResponse(Git.DEFAULT_HOOKS_PATH)) + } val targetPath = rawPath.value + .replaceFirst( + Regex(EMPTY_PATTERN), + Git.DEFAULT_HOOKS_PATH + ) .replaceFirst( Regex(HOME_PATTERN), SystemPathUtils.getUserHomePath() @@ -26,6 +38,7 @@ fun Git.getGlobalHooksPath(): Path { SystemPathUtils.getCurrentDirectoryPath() ) - return Path.of(targetPath) + return Path + .of(targetPath) .toAbsolutePath() } \ No newline at end of file diff --git a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt index 77d8a0d..9a44011 100644 --- a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt +++ b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt @@ -3,6 +3,8 @@ package com.github.y0ung3r.gitglobalhookslocator.gitTests import com.github.y0ung3r.gitglobalhookslocator.gitTests.testEngine.RespondInterchangeably import com.github.y0ung3r.gitglobalhookslocator.git.Git import com.github.y0ung3r.gitglobalhookslocator.git.cli.CliResponse +import com.github.y0ung3r.gitglobalhookslocator.git.cli.EmptyCliResponse +import com.github.y0ung3r.gitglobalhookslocator.git.cli.NotFoundCliResponse import com.github.y0ung3r.gitglobalhookslocator.git.extensions.getGlobalHooksPath import com.github.y0ung3r.gitglobalhookslocator.git.utils.SystemPathUtils import org.junit.Assert.assertEquals @@ -10,6 +12,52 @@ import org.junit.Test import java.nio.file.Path class GetGlobalHooksPathTests { + @Test + fun `Should returns default hooks path if path is not overridden`() { + // Arrange + val expectedPath = Path.of( + SystemPathUtils.getCurrentDirectoryPath(), + ".git", + "hooks" + ) + + val sut = Git( + RespondInterchangeably( + CliResponse(Git.minRequiredVersion.toString()), + NotFoundCliResponse() + ) + ) + + // Act + val actualPath = sut.getGlobalHooksPath() + + // Assert + assertEquals(expectedPath, actualPath) + } + + @Test + fun `Should returns default hooks path if path is empty`() { + // Arrange + val expectedPath = Path.of( + SystemPathUtils.getCurrentDirectoryPath(), + ".git", + "hooks" + ) + + val sut = Git( + RespondInterchangeably( + CliResponse(Git.minRequiredVersion.toString()), + EmptyCliResponse() + ) + ) + + // Act + val actualPath = sut.getGlobalHooksPath() + + // Assert + assertEquals(expectedPath, actualPath) + } + @Test fun `Should returns absolute global hooks path using relative path`() { // Arrange diff --git a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetInstalledVersionTests.kt b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetInstalledVersionTests.kt index 70c1433..dae2315 100644 --- a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetInstalledVersionTests.kt +++ b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetInstalledVersionTests.kt @@ -5,6 +5,7 @@ import com.github.y0ung3r.gitglobalhookslocator.git.cli.EmptyCliResponse import com.github.y0ung3r.gitglobalhookslocator.git.Git import com.github.y0ung3r.gitglobalhookslocator.git.cli.CliResponse import com.github.y0ung3r.gitglobalhookslocator.git.SemanticVersion +import com.github.y0ung3r.gitglobalhookslocator.git.cli.NotFoundCliResponse import com.github.y0ung3r.gitglobalhookslocator.git.exceptions.GitIsNotInstalledException import org.junit.Assert.assertEquals import org.junit.Test @@ -12,6 +13,16 @@ import org.junit.Test class GetInstalledVersionTests { @Test(expected = GitIsNotInstalledException::class) fun `Should throws exception if Git is not installed`() { + // Arrange & Act & Assert + Git( + RespondOnce( + NotFoundCliResponse() + ) + ) + } + + @Test(expected = GitIsNotInstalledException::class) + fun `Should throws exception if Git returns empty value`() { // Arrange & Act & Assert Git( RespondOnce( From e44570df6e2fe1475a0603b099333ea8dcfc6a15 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=9D=D0=B8=D0=BA=D0=B8=D1=82=D0=B0=20=D0=92=D0=B5=D0=BB?= =?UTF-8?q?=D0=B8=D0=BA=D0=B8=D0=B9?= Date: Mon, 27 Nov 2023 02:55:08 +0500 Subject: [PATCH 07/13] Change default path to global hooks --- .../y0ung3r/gitglobalhookslocator/git/Git.kt | 2 +- .../gitTests/GetGlobalHooksPathTests.kt | 4 +-- .../gitTests/HooksFolderTests.kt | 28 +++++-------------- 3 files changed, 10 insertions(+), 24 deletions(-) diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/Git.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/Git.kt index a55893f..5d0f372 100644 --- a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/Git.kt +++ b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/Git.kt @@ -17,7 +17,7 @@ class Git(private val commandExecutor: CliCommandExecutor) { const val GIT_GLOBAL_COMMAND = "--global" const val GIT_CONFIG_GET_COMMAND = "--get" const val GIT_HOOKS_PATH_SECTION = "core.hooksPath" - const val DEFAULT_HOOKS_PATH = "./.git/hooks" + const val DEFAULT_HOOKS_PATH = "~/.git/hooks" @JvmStatic val minRequiredVersion = SemanticVersion(2, 9, 0) diff --git a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt index 9a44011..13c736c 100644 --- a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt +++ b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetGlobalHooksPathTests.kt @@ -16,7 +16,7 @@ class GetGlobalHooksPathTests { fun `Should returns default hooks path if path is not overridden`() { // Arrange val expectedPath = Path.of( - SystemPathUtils.getCurrentDirectoryPath(), + SystemPathUtils.getUserHomePath(), ".git", "hooks" ) @@ -39,7 +39,7 @@ class GetGlobalHooksPathTests { fun `Should returns default hooks path if path is empty`() { // Arrange val expectedPath = Path.of( - SystemPathUtils.getCurrentDirectoryPath(), + SystemPathUtils.getUserHomePath(), ".git", "hooks" ) diff --git a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/HooksFolderTests.kt b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/HooksFolderTests.kt index 1fe53f5..9c2369c 100644 --- a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/HooksFolderTests.kt +++ b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/HooksFolderTests.kt @@ -1,13 +1,11 @@ package com.github.y0ung3r.gitglobalhookslocator.gitTests -import com.github.y0ung3r.gitglobalhookslocator.gitTests.testEngine.HookTestBase -import com.github.y0ung3r.gitglobalhookslocator.gitTests.testEngine.RespondInterchangeably import com.github.y0ung3r.gitglobalhookslocator.git.Git import com.github.y0ung3r.gitglobalhookslocator.git.HooksFolder import com.github.y0ung3r.gitglobalhookslocator.git.cli.CliResponse -import org.junit.Assert -import org.junit.Assert.assertEquals -import org.junit.Assert.assertTrue +import com.github.y0ung3r.gitglobalhookslocator.gitTests.testEngine.HookTestBase +import com.github.y0ung3r.gitglobalhookslocator.gitTests.testEngine.RespondInterchangeably +import org.junit.Assert.* import org.junit.Test import java.nio.file.Path @@ -22,18 +20,6 @@ class HooksFolderTests : HookTestBase() { ) } - @Test - fun `Should be empty if provided empty path`() { - // Arrange - val git = getGit(Path.of("")) - - // Act - val sut = HooksFolder(git) - - // Assert - assertTrue(sut.isEmpty()) - } - @Test fun `Should load all hooks from disabled hooks path`() { // Arrange @@ -65,7 +51,7 @@ class HooksFolderTests : HookTestBase() { val sut = HooksFolder(git) // Act & Assert - Assert.assertTrue(sut.isAllDisabled()) + assertTrue(sut.isAllDisabled()) } @Test @@ -75,7 +61,7 @@ class HooksFolderTests : HookTestBase() { val sut = HooksFolder(git) // Act & Assert - Assert.assertFalse(sut.isAllDisabled()) + assertFalse(sut.isAllDisabled()) } @Test @@ -88,7 +74,7 @@ class HooksFolderTests : HookTestBase() { sut.disableAll() // Assert - Assert.assertTrue(sut.isAllDisabled()) + assertTrue(sut.isAllDisabled()) } @Test @@ -101,6 +87,6 @@ class HooksFolderTests : HookTestBase() { sut.enableAll() // Assert - Assert.assertFalse(sut.isAllDisabled()) + assertFalse(sut.isAllDisabled()) } } \ No newline at end of file From 586c19903e9d82b3973b1049e01758220ddb8004 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=9D=D0=B8=D0=BA=D0=B8=D1=82=D0=B0=20=D0=92=D0=B5=D0=BB?= =?UTF-8?q?=D0=B8=D0=BA=D0=B8=D0=B9?= Date: Mon, 27 Nov 2023 03:09:22 +0500 Subject: [PATCH 08/13] Bump plugin version to 0.0.2 --- CHANGELOG.md | 9 +++++---- gradle.properties | 2 +- src/main/resources/META-INF/plugin.xml | 5 ----- 3 files changed, 6 insertions(+), 10 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index cd3d9c2..a1c358f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,9 +1,10 @@ -# GitGlobalHooksLocator Changelog +# Changelog ## [Unreleased] -## [0.0.1] - -- Initial release +## [0.0.2] +### Fixed +- Fix empty core.hooksPath value handling +- Fix relative paths handling \ No newline at end of file diff --git a/gradle.properties b/gradle.properties index 9782186..b816166 100644 --- a/gradle.properties +++ b/gradle.properties @@ -4,7 +4,7 @@ pluginGroup = com.github.y0ung3r.gitglobalhookslocator pluginName = GitGlobalHooksLocator pluginRepositoryUrl = https://github.com/y0ung3r/GitGlobalHooksLocator # SemVer format -> https://semver.org -pluginVersion = 0.0.1 +pluginVersion = 0.0.2 # Supported build number ranges and IntelliJ Platform versions -> https://plugins.jetbrains.com/docs/intellij/build-number-ranges.html pluginSinceBuild = 223 diff --git a/src/main/resources/META-INF/plugin.xml b/src/main/resources/META-INF/plugin.xml index 46c7e66..848b3e5 100644 --- a/src/main/resources/META-INF/plugin.xml +++ b/src/main/resources/META-INF/plugin.xml @@ -4,11 +4,6 @@ Git Global Hooks Locator y0ung3r - - - com.intellij.modules.platform messages.LocatorBundle From 022c7fe66b5e6d0c74590f70595fde5b47ed3441 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=9D=D0=B8=D0=BA=D0=B8=D1=82=D0=B0=20=D0=92=D0=B5=D0=BB?= =?UTF-8?q?=D0=B8=D0=BA=D0=B8=D0=B9?= Date: Tue, 28 Nov 2023 00:31:37 +0500 Subject: [PATCH 09/13] (#7) Replace SemanticVersion with the more specialized GitVersion --- .../y0ung3r/gitglobalhookslocator/git/Git.kt | 6 +- .../gitglobalhookslocator/git/GitVersion.kt | 56 +++++++++++++++++++ .../git/SemanticVersion.kt | 47 ---------------- .../ProvidedGitVersionIsInvalidException.kt | 4 ++ ...ovidedSemanticVersionIsInvalidException.kt | 4 -- .../gitTests/GetInstalledVersionTests.kt | 4 +- .../gitTests/MinGitVersionTests.kt | 8 +-- 7 files changed, 69 insertions(+), 60 deletions(-) create mode 100644 src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/GitVersion.kt delete mode 100644 src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/SemanticVersion.kt create mode 100644 src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/exceptions/ProvidedGitVersionIsInvalidException.kt delete mode 100644 src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/exceptions/ProvidedSemanticVersionIsInvalidException.kt diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/Git.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/Git.kt index 5d0f372..b7b3908 100644 --- a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/Git.kt +++ b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/Git.kt @@ -20,7 +20,7 @@ class Git(private val commandExecutor: CliCommandExecutor) { const val DEFAULT_HOOKS_PATH = "~/.git/hooks" @JvmStatic - val minRequiredVersion = SemanticVersion(2, 9, 0) + val minRequiredVersion = GitVersion(2, 9, 0) @JvmStatic val instance = Git(DefaultCliCommandExecutor()) @@ -48,7 +48,7 @@ class Git(private val commandExecutor: CliCommandExecutor) { } } - fun getInstalledVersion() : SemanticVersion { + fun getInstalledVersion() : GitVersion { val installedVersion = try { executeCommand(GIT_VERSION_COMMAND) } catch (exception: GitCommandNotFoundException) { @@ -56,7 +56,7 @@ class Git(private val commandExecutor: CliCommandExecutor) { } return when { - !installedVersion.isEmpty() -> SemanticVersion.parse(installedVersion.value) + !installedVersion.isEmpty() -> GitVersion.parse(installedVersion.value) else -> throw GitIsNotInstalledException() } } diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/GitVersion.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/GitVersion.kt new file mode 100644 index 0000000..1bbe645 --- /dev/null +++ b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/GitVersion.kt @@ -0,0 +1,56 @@ +package com.github.y0ung3r.gitglobalhookslocator.git + +import com.github.y0ung3r.gitglobalhookslocator.git.exceptions.ProvidedGitVersionIsInvalidException + +class GitVersion(val major: Int, val minor: Int, val patch: Int) : Comparable { + companion object { + /* + * From git sources: + * The format of this string should be kept stable for compatibility + * with external projects that rely on the output of "git version" + * https://github.com/git/git/blob/564d0252ca632e0264ed670534a51d18a689ef5d/help.c#L741 + */ + private const val PREFIX = "git version" + private const val VERSION_PATTERN = "^$PREFIX (0|[1-9]\\d*)\\.(0|[1-9]\\d*)\\.(0|[1-9]\\d*)?" + + fun parse(version: String) : GitVersion { + val match = Regex(VERSION_PATTERN).findAll(version).firstOrNull() + ?: throw ProvidedGitVersionIsInvalidException(version) + + return try { + match.groupValues.let { + GitVersion(it[1].toInt(), it[2].toInt(), it[3].toInt()) + } + } catch (exception: NumberFormatException) { + throw ProvidedGitVersionIsInvalidException(version) + } + } + } + + override fun compareTo(other: GitVersion): Int = + when { + major > other.major -> 1 + major < other.major -> -1 + minor > other.minor -> 1 + minor < other.minor -> -1 + patch > other.patch -> 1 + patch < other.patch -> -1 + else -> 0 + } + + override fun equals(other: Any?): Boolean { + val version = other as? GitVersion + + return when { + version == null -> false + compareTo(version) == 0 -> true + else -> false + } + } + + override fun hashCode(): Int + = major.hashCode() * 31 + minor.hashCode() * 31 + patch.hashCode() + + override fun toString(): String + = "$PREFIX $major.$minor.$patch" +} \ No newline at end of file diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/SemanticVersion.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/SemanticVersion.kt deleted file mode 100644 index f954283..0000000 --- a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/SemanticVersion.kt +++ /dev/null @@ -1,47 +0,0 @@ -package com.github.y0ung3r.gitglobalhookslocator.git - -import com.github.y0ung3r.gitglobalhookslocator.git.exceptions.ProvidedSemanticVersionIsInvalidException - -class SemanticVersion(val major: Int, val minor: Int, val patch: Int) : Comparable { - companion object { - private const val COMPONENTS_DELIMITER = '.' - private const val VERSION_PATTERN = "(0|[1-9]\\d*)\\.(0|[1-9]\\d*)\\.(0|[1-9]\\d*)?" - - @JvmStatic - fun parse(version: String): SemanticVersion { - val match = Regex(VERSION_PATTERN).findAll(version).firstOrNull() - ?: throw ProvidedSemanticVersionIsInvalidException(version) - - return match.value.split(COMPONENTS_DELIMITER).let { - SemanticVersion(it[0].toInt(), it[1].toInt(), it[2].toInt()) - } - } - } - - override fun compareTo(other: SemanticVersion): Int = - when { - major > other.major -> 1 - major < other.major -> -1 - minor > other.minor -> 1 - minor < other.minor -> -1 - patch > other.patch -> 1 - patch < other.patch -> -1 - else -> 0 - } - - override fun equals(other: Any?): Boolean { - val version = other as? SemanticVersion - - return when { - version == null -> false - compareTo(version) == 0 -> true - else -> false - } - } - - override fun hashCode(): Int - = major.hashCode() * 31 + minor.hashCode() * 31 + patch.hashCode() - - override fun toString(): String - = "$major.$minor.$patch" -} \ No newline at end of file diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/exceptions/ProvidedGitVersionIsInvalidException.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/exceptions/ProvidedGitVersionIsInvalidException.kt new file mode 100644 index 0000000..6956a36 --- /dev/null +++ b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/exceptions/ProvidedGitVersionIsInvalidException.kt @@ -0,0 +1,4 @@ +package com.github.y0ung3r.gitglobalhookslocator.git.exceptions + +class ProvidedGitVersionIsInvalidException(version: String) + : Exception("The provided version does not conform to git versioning: $version") \ No newline at end of file diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/exceptions/ProvidedSemanticVersionIsInvalidException.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/exceptions/ProvidedSemanticVersionIsInvalidException.kt deleted file mode 100644 index 19bc7d7..0000000 --- a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/git/exceptions/ProvidedSemanticVersionIsInvalidException.kt +++ /dev/null @@ -1,4 +0,0 @@ -package com.github.y0ung3r.gitglobalhookslocator.git.exceptions - -class ProvidedSemanticVersionIsInvalidException(version: String) - : Exception("The provided version does not conform to semantic versioning: $version") \ No newline at end of file diff --git a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetInstalledVersionTests.kt b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetInstalledVersionTests.kt index dae2315..86ac371 100644 --- a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetInstalledVersionTests.kt +++ b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GetInstalledVersionTests.kt @@ -4,7 +4,7 @@ import com.github.y0ung3r.gitglobalhookslocator.gitTests.testEngine.RespondOnce import com.github.y0ung3r.gitglobalhookslocator.git.cli.EmptyCliResponse import com.github.y0ung3r.gitglobalhookslocator.git.Git import com.github.y0ung3r.gitglobalhookslocator.git.cli.CliResponse -import com.github.y0ung3r.gitglobalhookslocator.git.SemanticVersion +import com.github.y0ung3r.gitglobalhookslocator.git.GitVersion import com.github.y0ung3r.gitglobalhookslocator.git.cli.NotFoundCliResponse import com.github.y0ung3r.gitglobalhookslocator.git.exceptions.GitIsNotInstalledException import org.junit.Assert.assertEquals @@ -34,7 +34,7 @@ class GetInstalledVersionTests { @Test fun `Should returns Git version info`() { // Arrange - val expectedVersion = SemanticVersion(2, 9, 2) + val expectedVersion = GitVersion(2, 9, 2) val sut = Git( RespondOnce( CliResponse(expectedVersion.toString()) diff --git a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/MinGitVersionTests.kt b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/MinGitVersionTests.kt index ae76e94..3006fda 100644 --- a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/MinGitVersionTests.kt +++ b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/MinGitVersionTests.kt @@ -15,10 +15,10 @@ class MinGitVersionTests(private val unsupportedVersion: String, private val sup @JvmStatic @Parameters fun version() = arrayOf( - arrayOf("1.0.0", "2.9.0"), - arrayOf("1.0.1", "2.9.1"), - arrayOf("2.0.0", "2.43.0"), - arrayOf("2.0.1", "2.43.1"), + arrayOf("git version 1.0.0", "git version 2.9.0"), + arrayOf("git version 1.0.1", "git version 2.9.1"), + arrayOf("git version 2.0.0", "git version 2.43.0"), + arrayOf("git version 2.0.1", "git version 2.43.1"), ) } From 8b34e08ffcc42d0dbe957ec9e442a7ab3e2a500c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=9D=D0=B8=D0=BA=D0=B8=D1=82=D0=B0=20=D0=92=D0=B5=D0=BB?= =?UTF-8?q?=D0=B8=D0=BA=D0=B8=D0=B9?= Date: Tue, 28 Nov 2023 00:32:16 +0500 Subject: [PATCH 10/13] (#7) Fix related tests --- .../gitTests/GitVersionTests.kt | 80 +++++++++++++++++++ .../gitTests/SemanticVersionTests.kt | 50 ------------ 2 files changed, 80 insertions(+), 50 deletions(-) create mode 100644 src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GitVersionTests.kt delete mode 100644 src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/SemanticVersionTests.kt diff --git a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GitVersionTests.kt b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GitVersionTests.kt new file mode 100644 index 0000000..7d14a39 --- /dev/null +++ b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GitVersionTests.kt @@ -0,0 +1,80 @@ +package com.github.y0ung3r.gitglobalhookslocator.gitTests + +import com.github.y0ung3r.gitglobalhookslocator.git.GitVersion +import com.github.y0ung3r.gitglobalhookslocator.git.exceptions.ProvidedGitVersionIsInvalidException +import org.junit.Assert.assertEquals +import org.junit.Test +import org.junit.runner.RunWith +import org.junit.runners.Parameterized +import org.junit.runners.Parameterized.Parameters + +@RunWith(Parameterized::class) +class GitVersionTests( + private val invalidVersion: String, + private val validVersion: String, + private val validMajor: Int, + private val validMinor: Int, + private val validPatch: Int) { + companion object { + @JvmStatic + @Parameters + fun versions() = arrayOf( + arrayOf("git version 1.-1.0", "git version 2.42.0.windows.2", 2, 42, 0), + arrayOf("git version 0.0.-1", "git version 0.99.9n", 0, 99, 9), + arrayOf("git version 1", "git version 2.33.0.windows.2", 2, 33, 0), + arrayOf("git version ", "git version 1.5.6.6", 1, 5, 6), + arrayOf("1.-1.0", "git version 2.19.6", 2, 19, 6), + arrayOf("0.0.-1", "git version 2.27.1", 2, 27, 1), + arrayOf("1", "git version 2.31.8", 2, 31, 8), + arrayOf(" ", "git version 2.42.0", 2, 42, 0), + arrayOf("", "git version 2.40.1", 2, 40, 1), + arrayOf("git version 1.0", "git version 1.7.12.4", 1, 7, 12), + arrayOf("git version 1.0-alpha", "git version 2.14.6-alpha.01", 2, 14, 6), + arrayOf("git version 1.0-alpha.01", "git version 2.38.3", 2, 38, 3), + arrayOf("1.0", "git version 1.0.13", 1, 0, 13), + arrayOf("1.0-alpha", "git version 1.9.5", 1, 9, 5), + arrayOf("1.0-alpha.01", "git version 2.32.7", 2, 32, 7), + arrayOf("git version a1.0.0", "git version 2.6.0-rc0", 2, 6, 0), + arrayOf("git version 1.a0.0", "git version 1.2.3-alpha.b.3", 1, 2, 3), + arrayOf("git version 1.0.a0", "git version 2.3.1-alpha", 2, 3, 1) + ) + } + + @Test(expected = ProvidedGitVersionIsInvalidException::class) + fun `Should throws exception if provided version is not valid`() { + // Arrange & Act & Assert + GitVersion.parse(invalidVersion) + } + + @Test + fun `Should parse version properly`() { + // Arrange & Act & Assert + GitVersion.parse(validVersion) + } + + @Test + fun `Should returns version properly`() { + // Arrange & Act + val sut = GitVersion.parse(validVersion) + + // Assert + sut.also { + assertEquals(it.major, validMajor) + assertEquals(it.minor, validMinor) + assertEquals(it.patch, validPatch) + } + } + + @Test + fun `Should returns string representation`() { + // Arrange + val expectedRepresentation = GitVersion(validMajor, validMinor, validPatch).toString() + val sut = GitVersion.parse(validVersion) + + // Act + val actualRepresentation = sut.toString() + + // Assert + assertEquals(expectedRepresentation, actualRepresentation) + } +} \ No newline at end of file diff --git a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/SemanticVersionTests.kt b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/SemanticVersionTests.kt deleted file mode 100644 index 7242d57..0000000 --- a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/SemanticVersionTests.kt +++ /dev/null @@ -1,50 +0,0 @@ -package com.github.y0ung3r.gitglobalhookslocator.gitTests - -import com.github.y0ung3r.gitglobalhookslocator.git.SemanticVersion -import org.junit.Assert.assertEquals -import org.junit.runners.Parameterized.Parameters - -//@RunWith(Parameterized::class) -class SemanticVersionTests(private val invalidVersion: String, private val validVersion: String) { - companion object { - @JvmStatic - @Parameters - fun versions() = arrayOf( - arrayOf("-1.0.0", "0.0.0"), - arrayOf("1.-1.0", "1.2.3-alpha.1+build"), - arrayOf("0.0.-1", "1.0"), - arrayOf("1", "git version 2.33.0.windows.2"), - arrayOf("", "0.99.9n"), - arrayOf("1.0", "1.7.12.4"), - arrayOf("1.0-alpha", "v2.43.0-rc1"), - arrayOf("1.0-alpha.01", "2.38.3"), - arrayOf("a1.0.0", "v2.6.0-rc0"), - arrayOf("1.a0.0", "1.2.3-alpha.b.3"), - arrayOf("1.0.a0", "2.3.1-alpha") - ) - } - - //@Test(expected = ProvidedSemanticVersionIsInvalidException::class) - fun `Should throws exception if provided version is not valid`() { - // Arrange & Act & Assert - SemanticVersion.parse(invalidVersion) - } - - //@Test - fun `Should parse version properly`() { - // Arrange & Act & Assert - SemanticVersion.parse(validVersion) - } - - //@Test - fun `Should returns string representation of version`() { - // Arrange - val sut = SemanticVersion.parse(validVersion) - - // Act - val actualRepresentation = sut.toString() - - // Assert - assertEquals(validVersion, actualRepresentation) - } -} \ No newline at end of file From 461d07cba597394f3fab6f43ac1879269ba6faf6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=9D=D0=B8=D0=BA=D0=B8=D1=82=D0=B0=20=D0=92=D0=B5=D0=BB?= =?UTF-8?q?=D0=B8=D0=BA=D0=B8=D0=B9?= Date: Tue, 28 Nov 2023 00:35:03 +0500 Subject: [PATCH 11/13] Suppress "unused" warning in LocatorBundle --- .../com/github/y0ung3r/gitglobalhookslocator/LocatorBundle.kt | 1 + 1 file changed, 1 insertion(+) diff --git a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/LocatorBundle.kt b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/LocatorBundle.kt index e1acca7..5c8f780 100644 --- a/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/LocatorBundle.kt +++ b/src/main/kotlin/com/github/y0ung3r/gitglobalhookslocator/LocatorBundle.kt @@ -9,6 +9,7 @@ private const val BUNDLE = "messages.LocatorBundle" object LocatorBundle : DynamicBundle(BUNDLE) { + @Suppress("unused") @JvmStatic fun message(@PropertyKey(resourceBundle = BUNDLE) key: String, vararg params: Any) = getMessage(key, *params) From 5e8e0cfe10208dcfb91d140b9bbef778c7d4d9b2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=9D=D0=B8=D0=BA=D0=B8=D1=82=D0=B0=20=D0=92=D0=B5=D0=BB?= =?UTF-8?q?=D0=B8=D0=BA=D0=B8=D0=B9?= Date: Tue, 28 Nov 2023 00:45:49 +0500 Subject: [PATCH 12/13] Add additional test case to GitVersionTests --- .../y0ung3r/gitglobalhookslocator/gitTests/GitVersionTests.kt | 1 + 1 file changed, 1 insertion(+) diff --git a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GitVersionTests.kt b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GitVersionTests.kt index 7d14a39..acfff80 100644 --- a/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GitVersionTests.kt +++ b/src/test/kotlin/com/github/y0ung3r/gitglobalhookslocator/gitTests/GitVersionTests.kt @@ -19,6 +19,7 @@ class GitVersionTests( @JvmStatic @Parameters fun versions() = arrayOf( + arrayOf("git version -1.0.0", "git version 1.1.1", 1, 1, 1), arrayOf("git version 1.-1.0", "git version 2.42.0.windows.2", 2, 42, 0), arrayOf("git version 0.0.-1", "git version 0.99.9n", 0, 99, 9), arrayOf("git version 1", "git version 2.33.0.windows.2", 2, 33, 0), From bbf1f934e66f1ee04589ae138e48034e3ea054da Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=9D=D0=B8=D0=BA=D0=B8=D1=82=D0=B0=20=D0=92=D0=B5=D0=BB?= =?UTF-8?q?=D0=B8=D0=BA=D0=B8=D0=B9?= Date: Tue, 28 Nov 2023 00:48:07 +0500 Subject: [PATCH 13/13] Update CHANGELOG.md --- CHANGELOG.md | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index a1c358f..b022180 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,4 +7,7 @@ ## [0.0.2] ### Fixed - Fix empty core.hooksPath value handling -- Fix relative paths handling \ No newline at end of file +- Fix relative paths handling + +### Changed +- Git version handling \ No newline at end of file