From ba447d21babd049228b74df5d8e7244ec98bd596 Mon Sep 17 00:00:00 2001 From: Eugene Yokota Date: Fri, 26 Jun 2020 12:20:23 -0400 Subject: [PATCH 1/2] Add integration test Ref https://github.com/foundweekends/giter8/issues/469 --- .travis.yml | 2 +- build.sbt | 13 +++++++++--- launcher/src/main/scala/LauncherMain.scala | 10 ++++----- launcher/src/test/scala/LauncherTest.scala | 24 ++++++++++++++++++++++ project/Dependencies.scala | 1 + project/build.properties | 2 +- 6 files changed, 42 insertions(+), 10 deletions(-) create mode 100644 launcher/src/test/scala/LauncherTest.scala diff --git a/.travis.yml b/.travis.yml index b51a7a06..9cf5d842 100644 --- a/.travis.yml +++ b/.travis.yml @@ -14,7 +14,7 @@ jobs: - stage: test env: SBT_VERSION=1.2.8 jdk: openjdk8 - script: sbt "-no-colors" "^^ $SBT_VERSION" ";publishLocal;scalafmtCheckAll;plugin/scripted;scaffold/scripted;lib/test;app/compile" + script: sbt "-no-colors" "^^ $SBT_VERSION" ";publishLocal;scalafmtCheckAll;launcher/test;plugin/scripted;scaffold/scripted;lib/test;app/compile" - name: "Scala 2.13" script: - sbt "++ 2.13.2" app/test lib/test diff --git a/build.sbt b/build.sbt index 96ac46ad..b5bf71fc 100644 --- a/build.sbt +++ b/build.sbt @@ -1,7 +1,7 @@ import Dependencies._ import CrossVersion.partialVersion -val g8version = "0.13.0-SNAPSHOT" +val g8version = "0.13.1-SNAPSHOT" val javaVmArgs: List[String] = { import scala.collection.JavaConverters._ @@ -187,8 +187,15 @@ lazy val launcher = (project in file("launcher")) description := "Command line tool to apply templates defined on GitHub", name := "giter8-launcher", crossScalaVersions := List(scala212, scala213), - libraryDependencies += coursier, - run / fork := true + libraryDependencies ++= Seq( + coursier, + verify % Test, + sbtIo % Test + ), + testFrameworks += new TestFramework("verify.runner.Framework"), + run / fork := true, + Test / fork := true, + Test / javaOptions ++= Seq(s"""-DG8_HOME=${target.value / "home"}""") // assemblyMergeStrategy in assembly := { // case "plugin.properties" => MergeStrategy.concat // case "module-info.class" => MergeStrategy.discard diff --git a/launcher/src/main/scala/LauncherMain.scala b/launcher/src/main/scala/LauncherMain.scala index 26288ce2..6e90a978 100644 --- a/launcher/src/main/scala/LauncherMain.scala +++ b/launcher/src/main/scala/LauncherMain.scala @@ -4,7 +4,7 @@ import java.net.URLClassLoader import java.io.{BufferedInputStream, File, FileInputStream} import java.util.Properties import java.lang.reflect.InvocationTargetException -import java.nio.file.Files +import java.nio.file.{Files, StandardCopyOption} object LauncherMain extends Runner with App { java.util.logging.Logger.getLogger("").setLevel(java.util.logging.Level.SEVERE) @@ -35,7 +35,7 @@ class LauncherProcessor extends Processor { (if (forceOverwrite) Vector("-f") else Vector()) ++ (outputDirectory match { case Some(out) => Vector("-o", out.toString); case _ => Vector() }) val giter8Files = giter8Artifacts(g8v) - virtuallyRun(giter8Files, virtualArgument) + virtuallyRun(giter8Files, virtualArgument, workingDirectory) Right("") } @@ -67,7 +67,7 @@ class LauncherProcessor extends Processor { } downloadedJars map { downloaded => val t = bootDir / downloaded.getName - Files.copy(downloaded.toPath, t.toPath).toFile + Files.copy(downloaded.toPath, t.toPath, StandardCopyOption.REPLACE_EXISTING).toFile } } // push launcher JAR to the end of classpath to avoid Scala version clash @@ -83,9 +83,9 @@ class LauncherProcessor extends Processor { } // uses classloader trick to run - def virtuallyRun(files: Seq[File], args: Seq[String]): Unit = { + def virtuallyRun(files: Seq[File], args: Seq[String], workingDirectory: File): Unit = { val cl = new URLClassLoader(files.map(_.toURL).toArray, null) - call("giter8.Giter8", "run", cl)(classOf[Array[String]])(args.toArray) + call("giter8.Giter8", "run", cl)(classOf[Array[String]], classOf[File])(args.toArray, workingDirectory) } def giter8Version(templateDir: File): Option[String] = { diff --git a/launcher/src/test/scala/LauncherTest.scala b/launcher/src/test/scala/LauncherTest.scala new file mode 100644 index 00000000..79adee63 --- /dev/null +++ b/launcher/src/test/scala/LauncherTest.scala @@ -0,0 +1,24 @@ +package testpkg + +import giter8._ +import verify._ +import java.io.File +import sbt.io.IO + +object LauncherTest extends BasicTestSuite { + lazy val launcher = new Runner { + def run(args: Array[String], workingDirectory: File): Int = { + run(args, workingDirectory, new LauncherProcessor) + } + } + implicit private class RichFile(file: File) { + def /(child: String): File = new File(file, child) + } + + test("runs scala/scala-seed.g8") { + IO.withTemporaryDirectory { dir => + launcher.run(Array("scala/scala-seed.g8", "--name=hello"), dir) + assert((dir / "hello" / "build.sbt").exists) + } + } +} diff --git a/project/Dependencies.scala b/project/Dependencies.scala index 4dcd942b..21c195f7 100644 --- a/project/Dependencies.scala +++ b/project/Dependencies.scala @@ -21,6 +21,7 @@ object Dependencies { val scalacheck = "org.scalacheck" %% "scalacheck" % "1.14.3" val scalatest = "org.scalatest" %% "scalatest" % "3.2.0" val scalamock = "org.scalamock" %% "scalamock" % "4.4.0" + val verify = "com.eed3si9n.verify" %% "verify" % "0.2.0" val sbtIo = "org.scala-sbt" %% "io" % "1.3.4" val scala212 = "2.12.11" val scala213 = "2.13.2" diff --git a/project/build.properties b/project/build.properties index 797e7ccf..c0bab049 100644 --- a/project/build.properties +++ b/project/build.properties @@ -1 +1 @@ -sbt.version=1.3.10 +sbt.version=1.2.8 From 6ea65549aaea0601c3ecaceb63445488a9fd5a82 Mon Sep 17 00:00:00 2001 From: Eugene Yokota Date: Fri, 26 Jun 2020 14:16:37 -0400 Subject: [PATCH 2/2] Fix SshAgentSessionFactory setting --- build.sbt | 1 + .../scala/ConsoleCredentialsProvider.scala | 41 ++++++++++--------- cli-git/src/main/scala/GitInteractor.scala | 7 +++- launcher/src/test/scala/LauncherTest.scala | 9 ++++ project/Dependencies.scala | 1 + 5 files changed, 38 insertions(+), 21 deletions(-) diff --git a/build.sbt b/build.sbt index b5bf71fc..5e7c36d5 100644 --- a/build.sbt +++ b/build.sbt @@ -142,6 +142,7 @@ lazy val gitsupport = (project in file("cli-git")) jsch, jschSshAgent, jschConnectorFactory, + jgitJsch, commonsIo, scalatest % Test, scalamock % Test diff --git a/cli-git/src/main/scala/ConsoleCredentialsProvider.scala b/cli-git/src/main/scala/ConsoleCredentialsProvider.scala index 20c7acdf..049c650b 100644 --- a/cli-git/src/main/scala/ConsoleCredentialsProvider.scala +++ b/cli-git/src/main/scala/ConsoleCredentialsProvider.scala @@ -26,26 +26,29 @@ object ConsoleCredentialsProvider extends CredentialsProvider { def supports(items: CredentialItem*) = true def get(uri: URIish, items: CredentialItem*): Boolean = { - items foreach { - case i: CredentialItem.Username => - val username = System.console.readLine("%s: ", i.getPromptText) - i.setValue(username) - - case i: CredentialItem.Password => - val password = System.console.readPassword("%s: ", i.getPromptText) - i.setValueNoCopy(password) - - case i: CredentialItem.InformationalMessage => - System.console.printf("%s\n", i.getPromptText) - - case i: CredentialItem.YesNoType => - i.setValue(askYesNo(i.getPromptText)) - - case i: CredentialItem.StringType if uri.getScheme == "ssh" => - val password = String.valueOf(System.console.readPassword("%s: ", i.getPromptText)) - i.setValue(password) + if (System.console == null) false + else { + items foreach { + case i: CredentialItem.Username => + val username = System.console.readLine("%s: ", i.getPromptText) + i.setValue(username) + + case i: CredentialItem.Password => + val password = System.console.readPassword("%s: ", i.getPromptText) + i.setValueNoCopy(password) + + case i: CredentialItem.InformationalMessage => + System.console.printf("%s\n", i.getPromptText) + + case i: CredentialItem.YesNoType => + i.setValue(askYesNo(i.getPromptText)) + + case i: CredentialItem.StringType if uri.getScheme == "ssh" => + val password = String.valueOf(System.console.readPassword("%s: ", i.getPromptText)) + i.setValue(password) + } + true } - true } @scala.annotation.tailrec diff --git a/cli-git/src/main/scala/GitInteractor.scala b/cli-git/src/main/scala/GitInteractor.scala index 961b6704..b044b4e1 100644 --- a/cli-git/src/main/scala/GitInteractor.scala +++ b/cli-git/src/main/scala/GitInteractor.scala @@ -21,7 +21,7 @@ import java.io.File import giter8.GitInteractor.TransportError import org.eclipse.jgit.api.errors.TransportException -import org.eclipse.jgit.transport.{CredentialsProvider, SshSessionFactory} +import org.eclipse.jgit.transport.{CredentialsProvider, SshSessionFactory, SshTransport} import org.eclipse.jgit.api.{Git => JGit} import scala.util.{Failure, Success, Try} @@ -42,7 +42,6 @@ object GitInteractor { class JGitInteractor(knownHosts: Option[String]) extends GitInteractor { CredentialsProvider.setDefault(ConsoleCredentialsProvider) - SshSessionFactory.setInstance(new SshAgentSessionFactory(knownHosts)) override def cloneRepository(url: String, dest: File): Try[Unit] = Try { JGit @@ -50,6 +49,10 @@ class JGitInteractor(knownHosts: Option[String]) extends GitInteractor { .setURI(url) .setDirectory(dest) .setCredentialsProvider(ConsoleCredentialsProvider) + .setTransportConfigCallback({ + case sshTransport: SshTransport => sshTransport.setSshSessionFactory(new SshAgentSessionFactory(knownHosts)) + case x => x + }) .call() .close() } diff --git a/launcher/src/test/scala/LauncherTest.scala b/launcher/src/test/scala/LauncherTest.scala index 79adee63..33a60dd3 100644 --- a/launcher/src/test/scala/LauncherTest.scala +++ b/launcher/src/test/scala/LauncherTest.scala @@ -21,4 +21,13 @@ object LauncherTest extends BasicTestSuite { assert((dir / "hello" / "build.sbt").exists) } } + + /* + test("runs git@github.com:scala/scala-seed.g8.git") { + IO.withTemporaryDirectory { dir => + launcher.run(Array("git@github.com:scala/scala-seed.g8.git", "--name=hello"), dir) + assert((dir / "hello" / "build.sbt").exists) + } + } + */ } diff --git a/project/Dependencies.scala b/project/Dependencies.scala index 21c195f7..e677fc30 100644 --- a/project/Dependencies.scala +++ b/project/Dependencies.scala @@ -14,6 +14,7 @@ object Dependencies { ExclusionRule("com.sun.jdmk", "jmxtools"), ExclusionRule("com.sun.jmx", "jmxri") ) + val jgitJsch = "org.eclipse.jgit" % "org.eclipse.jgit.ssh.jsch" % "5.8.0.202006091008-r" val jsch = "com.jcraft" % "jsch.agentproxy.jsch" % "0.0.9" val jschSshAgent = "com.jcraft" % "jsch.agentproxy.sshagent" % "0.0.9" val jschConnectorFactory = "com.jcraft" % "jsch.agentproxy.connector-factory" % "0.0.9"