Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion src/main/scala/eu/neverblink/jelly/cli/util/IoUtil.scala
Original file line number Diff line number Diff line change
Expand Up @@ -31,5 +31,5 @@ object IoUtil:
val file = File(fileName)
val suppFile = file.getParentFile
val parentFile = if (suppFile != null) suppFile else File(".")
if !parentFile.canWrite then throw OutputFileCannotBeCreated(fileName)
if !parentFile.canWrite || !file.canWrite then throw OutputFileCannotBeCreated(fileName)
FileOutputStream(file, true)
195 changes: 95 additions & 100 deletions src/test/scala/eu/neverblink/jelly/cli/command/RdfFromJellySpec.scala
Original file line number Diff line number Diff line change
Expand Up @@ -2,68 +2,64 @@ package eu.neverblink.jelly.cli.command

import com.google.protobuf.InvalidProtocolBufferException
import eu.neverblink.jelly.cli.*

import eu.neverblink.jelly.cli.command.helpers.*
import eu.neverblink.jelly.cli.command.rdf.*
import org.apache.jena.riot.RDFLanguages
import org.scalatest.matchers.should.Matchers
import org.scalatest.wordspec.AnyWordSpec

import java.nio.file.attribute.PosixFilePermissions
import java.nio.file.{Files, Paths}
import java.nio.file.attribute.PosixFilePermissions
import scala.io.Source
import scala.util.Using

class RdfFromJellySpec extends AnyWordSpec with Matchers with CleanUpAfterTest:
class RdfFromJellySpec extends AnyWordSpec with Matchers with TestFixtureHelper:

protected val dHelper: DataGenHelper = DataGenHelper("testRdfFromJelly")
protected val testCardinality: Integer = 33

"rdf from-jelly command" should {
"handle conversion of Jelly to NTriples" when {
"a file to output stream" in {
val jellyFile = dHelper.generateJellyFile(3)
val nQuadString = dHelper.generateNQuadString(3)
"a file to output stream" in withFullJellyFile { j =>
val nQuadString = DataGenHelper.generateNQuadString(testCardinality)
val (out, err) =
RdfFromJelly.runTestCommand(List("rdf", "from-jelly", jellyFile))
RdfFromJelly.runTestCommand(List("rdf", "from-jelly", j))
val sortedOut = out.split("\n").map(_.trim).sorted
val sortedQuads = nQuadString.split("\n").map(_.trim).sorted
sortedOut should contain theSameElementsAs sortedQuads
}

"input stream to output stream" in {
val input = dHelper.generateJellyInputStream(3)
val input = DataGenHelper.generateJellyInputStream(testCardinality)
RdfFromJelly.setStdIn(input)
val nQuadString = dHelper.generateNQuadString(3)
val nQuadString = DataGenHelper.generateNQuadString(testCardinality)
val (out, err) = RdfFromJelly.runTestCommand(
List("rdf", "from-jelly", "--out-format", RdfFormatOption.NQuads.cliOptions.head),
)
val sortedOut = out.split("\n").map(_.trim).sorted
val sortedQuads = nQuadString.split("\n").map(_.trim).sorted
sortedOut should contain theSameElementsAs sortedQuads
}
"a file to file" in {
val jellyFile = dHelper.generateJellyFile(3)
val nQuadString = dHelper.generateNQuadString(3)
val outputFile = dHelper.generateFile(RDFLanguages.NQUADS)
val (out, err) =
RdfFromJelly.runTestCommand(
List("rdf", "from-jelly", jellyFile, "--to", outputFile),
)
val sortedOut = Using.resource(Source.fromFile(outputFile)) { content =>
content.getLines().toList.map(_.trim).sorted
"a file to file" in withFullJellyFile { j =>
withEmptyQuadFile { q =>
val nQuadString = DataGenHelper.generateNQuadString(testCardinality)
val (out, err) =
RdfFromJelly.runTestCommand(
List("rdf", "from-jelly", j, "--to", q),
)
val sortedOut = Using.resource(Source.fromFile(q)) { content =>
content.getLines().toList.map(_.trim).sorted
}
val sortedQuads = nQuadString.split("\n").map(_.trim).sorted
sortedOut should contain theSameElementsAs sortedQuads
out.length should be(0)
}
val sortedQuads = nQuadString.split("\n").map(_.trim).sorted
sortedOut should contain theSameElementsAs sortedQuads
out.length should be(0)
}
"an input stream to file" in {
val input = dHelper.generateJellyInputStream(3)
"an input stream to file" in withEmptyQuadFile { q =>
val input = DataGenHelper.generateJellyInputStream(testCardinality)
RdfFromJelly.setStdIn(input)
val outputFile = dHelper.generateFile(RDFLanguages.NQUADS)
val nQuadString = dHelper.generateNQuadString(3)
val nQuadString = DataGenHelper.generateNQuadString(testCardinality)
val (out, err) =
RdfFromJelly.runTestCommand(List("rdf", "from-jelly", "--to", outputFile))
val sortedOut = Using.resource(Source.fromFile(outputFile)) { content =>
RdfFromJelly.runTestCommand(List("rdf", "from-jelly", "--to", q))
val sortedOut = Using.resource(Source.fromFile(q)) { content =>
content.getLines().toList.map(_.trim).sorted
}
val sortedQuads = nQuadString.split("\n").map(_.trim).sorted
Expand All @@ -72,14 +68,13 @@ class RdfFromJellySpec extends AnyWordSpec with Matchers with CleanUpAfterTest:
}
}
"handle conversion of Jelly binary to text" when {
"a file to output stream" in {
val jellyFile = dHelper.generateJellyFile(3)
"a file to output stream" in withFullJellyFile { j =>
val (out, err) =
RdfFromJelly.runTestCommand(
List(
"rdf",
"from-jelly",
jellyFile,
j,
"--out-format",
RdfFormatOption.JellyText.cliOptions.head,
),
Expand All @@ -99,7 +94,7 @@ class RdfFromJellySpec extends AnyWordSpec with Matchers with CleanUpAfterTest:
| }
|}""".stripMargin
out should include(outString)
"rows".r.findAllIn(out).length should be(10)
"rows".r.findAllIn(out).length should be(70)
"http://example.org/predicate/".r.findAllIn(out).length should be(1)
}
}
Expand All @@ -114,87 +109,87 @@ class RdfFromJellySpec extends AnyWordSpec with Matchers with CleanUpAfterTest:
RdfFromJelly.getErrString should include(msg)
exception.code should be(1)
}
"input file is not accessible" in {
val jellyFile = dHelper.generateJellyFile(3)
"input file is not accessible" in withFullJellyFile { j =>
val permissions = PosixFilePermissions.fromString("---------")
Files.setPosixFilePermissions(
Paths.get(jellyFile),
Paths.get(j),
permissions,
)
val exception =
intercept[ExitException] {

RdfFromJelly.runTestCommand(List("rdf", "from-jelly", jellyFile))
RdfFromJelly.runTestCommand(List("rdf", "from-jelly", j))
}
val msg = InputFileInaccessible(jellyFile).getMessage
val msg = InputFileInaccessible(j).getMessage
RdfFromJelly.getErrString should include(msg)
exception.code should be(1)
}
"output file cannot be created" in {
val jellyFile = dHelper.generateJellyFile(3)
val unreachableDir = dHelper.makeTestDir()
Paths.get(unreachableDir).toFile.setWritable(false)
val quadFile = dHelper.generateFile()
val exception =
intercept[ExitException] {
"output file cannot be created" in withFullJellyFile { j =>
withEmptyQuadFile { q =>
Paths.get(q).toFile.setWritable(false)
val exception =
intercept[ExitException] {

RdfFromJelly.runTestCommand(
List("rdf", "from-jelly", j, "--to", q),
)
}
val msg = OutputFileCannotBeCreated(q).getMessage
Paths.get(q).toFile.setWritable(true)
RdfFromJelly.getErrString should include(msg)
exception.code should be(1)

}

RdfFromJelly.runTestCommand(
List("rdf", "from-jelly", jellyFile, "--to", quadFile),
)
}
val msg = OutputFileCannotBeCreated(quadFile).getMessage
Paths.get(unreachableDir).toFile.setWritable(true)
RdfFromJelly.getErrString should include(msg)
exception.code should be(1)
}
"deserializing error occurs" in {
val jellyFile = dHelper.generateJellyFile(3)
val quadFile = dHelper.generateFile()
RdfFromJelly.runTestCommand(
List("rdf", "from-jelly", jellyFile, "--to", quadFile),
)
val exception =
intercept[ExitException] {
RdfFromJelly.runTestCommand(
List("rdf", "from-jelly", quadFile),
)
}
val msg = InvalidJellyFile(new InvalidProtocolBufferException("")).getMessage
val errContent = RdfFromJelly.getErrString
errContent should include(msg)
errContent should include("Run with --debug to see the complete stack trace.")
exception.code should be(1)
"deserializing error occurs" in withFullJellyFile { j =>
withEmptyQuadFile { q =>
RdfFromJelly.runTestCommand(
List("rdf", "from-jelly", j, "--to", q),
)
val exception =
intercept[ExitException] {
RdfFromJelly.runTestCommand(
List("rdf", "from-jelly", q),
)
}
val msg = InvalidJellyFile(new InvalidProtocolBufferException("")).getMessage
val errContent = RdfFromJelly.getErrString
errContent should include(msg)
errContent should include("Run with --debug to see the complete stack trace.")
exception.code should be(1)
}
}
"parsing error occurs with debug set" in {
val jellyFile = dHelper.generateJellyFile(3)
val quadFile = dHelper.generateFile()
RdfFromJelly.runTestCommand(
List("rdf", "from-jelly", jellyFile, "--to", quadFile),
)
val exception =
intercept[ExitException] {
RdfFromJelly.runTestCommand(
List("rdf", "from-jelly", quadFile, "--debug"),
)
}
val msg = InvalidJellyFile(new InvalidProtocolBufferException("")).getMessage
val errContent = RdfFromJelly.getErrString
errContent should include(msg)
errContent should include("eu.neverblink.jelly.cli.InvalidJellyFile")
exception.code should be(1)
"parsing error occurs with debug set" in withFullJellyFile { j =>
withEmptyQuadFile { q =>
RdfFromJelly.runTestCommand(
List("rdf", "from-jelly", j, "--to", q),
)
val exception =
intercept[ExitException] {
RdfFromJelly.runTestCommand(
List("rdf", "from-jelly", q, "--debug"),
)
}
val msg = InvalidJellyFile(new InvalidProtocolBufferException("")).getMessage
val errContent = RdfFromJelly.getErrString
errContent should include(msg)
errContent should include("eu.neverblink.jelly.cli.InvalidJellyFile")
exception.code should be(1)
}
}
"invalid output format supplied" in {
val jellyFile = dHelper.generateJellyFile(3)
val quadFile = dHelper.generateFile()
val exception =
intercept[ExitException] {
RdfFromJelly.runTestCommand(
List("rdf", "from-jelly", jellyFile, "--to", quadFile, "--out-format", "invalid"),
)
}
val msg = InvalidFormatSpecified("invalid", RdfFromJellyPrint.validFormatsString)
RdfFromJelly.getErrString should include(msg.getMessage)
exception.code should be(1)
"invalid output format supplied" in withFullJellyFile { j =>
withEmptyQuadFile { q =>
val exception =
intercept[ExitException] {
RdfFromJelly.runTestCommand(
List("rdf", "from-jelly", j, "--to", q, "--out-format", "invalid"),
)
}
val msg = InvalidFormatSpecified("invalid", RdfFromJellyPrint.validFormatsString)
RdfFromJelly.getErrString should include(msg.getMessage)
exception.code should be(1)
}
}
}
}
70 changes: 31 additions & 39 deletions src/test/scala/eu/neverblink/jelly/cli/command/RdfToJellySpec.scala
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
package eu.neverblink.jelly.cli.command

import eu.neverblink.jelly.cli.{ExitException, InvalidFormatSpecified}
import eu.neverblink.jelly.cli.command.helpers.{CleanUpAfterTest, DataGenHelper}
import eu.neverblink.jelly.cli.command.helpers.{DataGenHelper, TestFixtureHelper}
import eu.neverblink.jelly.cli.command.rdf.{RdfFormatOption, RdfToJelly, RdfToJellyPrint}
import eu.ostrzyciel.jelly.convert.jena.riot.JellyLanguage
import org.apache.jena.rdf.model.{Model, ModelFactory}
Expand All @@ -12,9 +12,9 @@ import org.apache.jena.riot.RDFParser
import java.io.{ByteArrayInputStream, FileInputStream, InputStream}
import scala.util.Using

class RdfToJellySpec extends AnyWordSpec with Matchers with CleanUpAfterTest:
class RdfToJellySpec extends AnyWordSpec with TestFixtureHelper with Matchers:

protected val dHelper: DataGenHelper = DataGenHelper("testRdfToJelly")
protected val testCardinality: Integer = 33

def translateJellyBack(inputStream: InputStream): Model =
Using(inputStream) { content =>
Expand All @@ -28,60 +28,52 @@ class RdfToJellySpec extends AnyWordSpec with Matchers with CleanUpAfterTest:

"rdf to-jelly command" should {
"handle conversion of NTriples to Jelly" when {
"a file to output stream" in {
val nQuadFile = dHelper.generateNQuadFile(3)
val tripleModel = dHelper.generateTripleModel(3)
"a file to output stream" in withFullQuadFile { f =>
val (out, err) =
RdfToJelly.runTestCommand(List("rdf", "to-jelly", nQuadFile))
RdfToJelly.runTestCommand(List("rdf", "to-jelly", f))
val newIn = new ByteArrayInputStream(RdfToJelly.getOutBytes)
val content = translateJellyBack(newIn)
content.containsAll(tripleModel.listStatements())
content.containsAll(DataGenHelper.generateTripleModel(testCardinality).listStatements())
}

"a file to file" in {
val nQuadFile = dHelper.generateNQuadFile(3)
val newFile = dHelper.generateFile(JellyLanguage.JELLY)
val tripleModel = dHelper.generateTripleModel(3)
val (out, err) =
RdfToJelly.runTestCommand(List("rdf", "to-jelly", nQuadFile, "--to", newFile))
val content = translateJellyBack(new FileInputStream(newFile))
content.containsAll(tripleModel.listStatements())
"a file to file" in withFullQuadFile { f =>
withEmptyJellyFile { j =>
val (out, err) =
RdfToJelly.runTestCommand(List("rdf", "to-jelly", f, "--to", j))
val content = translateJellyBack(new FileInputStream(j))
content.containsAll(DataGenHelper.generateTripleModel(testCardinality).listStatements())
}
}

"input stream to output stream" in {
val testNumber = 10
val input = dHelper.generateNQuadInputStream(testNumber)
val input = DataGenHelper.generateNQuadInputStream(testCardinality)
RdfToJelly.setStdIn(input)
val tripleModel = dHelper.generateTripleModel(testNumber)
val tripleModel = DataGenHelper.generateTripleModel(testCardinality)
val (out, err) = RdfToJelly.runTestCommand(
List("rdf", "to-jelly", "--in-format", RdfFormatOption.NQuads.cliOptions.head),
)
val newIn = new ByteArrayInputStream(RdfToJelly.getOutBytes)
val content = translateJellyBack(newIn)
content.containsAll(tripleModel.listStatements())
}

"an input stream to file" in {
val testNumber = 23
val input = dHelper.generateNQuadInputStream(testNumber)
"an input stream to file" in withEmptyJellyFile { j =>
val input = DataGenHelper.generateNQuadInputStream(testCardinality)
RdfToJelly.setStdIn(input)
val newFile = dHelper.generateFile(JellyLanguage.JELLY)
val tripleModel = dHelper.generateTripleModel(testNumber)
val (out, err) = RdfToJelly.runTestCommand(List("rdf", "to-jelly", "--to", newFile))
val content = translateJellyBack(new FileInputStream(newFile))
val tripleModel = DataGenHelper.generateTripleModel(testCardinality)
val (out, err) = RdfToJelly.runTestCommand(List("rdf", "to-jelly", "--to", j))
val content = translateJellyBack(new FileInputStream(j))
content.containsAll(tripleModel.listStatements())
}
}
"throw proper exception" when {
"invalid format is specified" in {
val jellyFile = dHelper.generateNQuadFile(3)
val exception =
intercept[ExitException] {
RdfToJelly.runTestCommand(List("rdf", "to-jelly", jellyFile, "--in-format", "invalid"))
}
val msg = InvalidFormatSpecified("invalid", RdfToJellyPrint.validFormatsString)
RdfToJelly.getErrString should include(msg.getMessage)
exception.code should be(1)
}
}
"throw proper exception" when {
"invalid format is specified" in withFullQuadFile { f =>
val exception =
intercept[ExitException] {
RdfToJelly.runTestCommand(List("rdf", "to-jelly", f, "--in-format", "invalid"))
}
val msg = InvalidFormatSpecified("invalid", RdfToJellyPrint.validFormatsString)
RdfToJelly.getErrString should include(msg.getMessage)
exception.code should be(1)
}

}
Loading