Commit 5612cb33 by Amelin Konstantin

Add zip handling

parent eba24207
Here is an information about using components. Here is an information about using components.
Scala. Scala.
Scala is licensed under the BSD 3-Clause License. https://www.scala-lang.org/license/ Scala is licensed under the Apache License, Version 2.0 (the “License”). https://www.scala-lang.org/license/
Scala-xml. Scala-xml.
Scala/scala-xml is licensed under the Apache License 2.0. https://github.com/scala/scala-xml/blob/master/LICENSE Scala/scala-xml is licensed under the Apache License 2.0. https://github.com/scala/scala-xml/blob/master/LICENSE
...@@ -17,3 +17,8 @@ Sbt/sbt is licensed under the Apache License 2.0. https://github.com/sbt/sbt/blo ...@@ -17,3 +17,8 @@ Sbt/sbt is licensed under the Apache License 2.0. https://github.com/sbt/sbt/blo
Sbt-assembly. Sbt-assembly.
Sbt/sbt-assembly is licensed under the MIT License. https://github.com/sbt/sbt-assembly/blob/master/LICENSE Sbt/sbt-assembly is licensed under the MIT License. https://github.com/sbt/sbt-assembly/blob/master/LICENSE
Java SE Development Kit 8u191.
https://www.oracle.com/technetwork/java/javase/downloads/jdk8-downloads-2133151.html
Java SE Development Kit 8u191 is licensed under the "Oracle Binary Code License Agreement for the Java SE Platform Products and JavaFX"
https://www.oracle.com/technetwork/java/javase/terms/license/index.html
\ No newline at end of file
File added
File added
Конвертер НРД <-> РТС. Конвертер НРД <-> СПБ.
Технические требования, функционал. Технические требования, функционал.
Конвертер работает в операционных системах с поддержкой Java. Необходима установленная JRE версии 8 и выше. Конвертер работает в операционных системах с поддержкой Java 8. Необходима установленная JRE версии 8.
Запуск осуществляется из командной строки с двумя параметрами: путь к директории входящих сообщений, путь к директории сконвертированных сообщений. Запуск осуществляется из командной строки с двумя параметрами: путь к директории входящих сообщений, путь к директории сконвертированных сообщений.
Конвертер работает по принципу пакетного обработчика. Действие выполняется над всеми файлами, находящимися в директории входящих сообщений. Конвертер работает по принципу пакетного обработчика. Действие выполняется над всеми файлами, находящимися в директории входящих сообщений.
Поддерживается формат xml и zip (архив, cодержащий xml файлы).
Лог файл с отчетом о конвертации сохраняется в директории сконвертированных сообщений. Лог файл с отчетом о конвертации сохраняется в директории сконвертированных сообщений.
Запуск. Запуск.
......
...@@ -2,6 +2,8 @@ import com.typesafe.config.{Config, ConfigFactory} ...@@ -2,6 +2,8 @@ import com.typesafe.config.{Config, ConfigFactory}
import scala.xml._ import scala.xml._
import java.nio.file.{Files, Path, Paths, StandardOpenOption} import java.nio.file.{Files, Path, Paths, StandardOpenOption}
import java.io.{FileInputStream, InputStream}
import java.util.zip.ZipFile
import java.time.LocalDateTime import java.time.LocalDateTime
import scala.util.{Failure, Success, Try} import scala.util.{Failure, Success, Try}
...@@ -13,6 +15,85 @@ object Main { ...@@ -13,6 +15,85 @@ object Main {
val debugMode: Boolean = conf.getBoolean("debug") val debugMode: Boolean = conf.getBoolean("debug")
val logFileName: String = conf.getString("log") val logFileName: String = conf.getString("log")
def main(args: Array[String]): Unit = {
println("Converting NSD -> SPB has been started...")
if (args.length != 2)
println("Error. Converting hasn`t been finished: Undefined INPUT/OUTPUT directory.\nUsage: run INPUT OUTPUT")
else if (!Files.exists(Paths.get(args(0))))
println("Error. Converting hasn`t been finished: INPUT directory doesn`t exist")
else if (!Files.exists(Paths.get(args(1))))
println("Error. Converting hasn`t been finished: OUTPUT directory doesn`t exist")
else {
val p = new PrettyPrinter(160, 2)
val nsdXmlValid = XMLValid(getClass.getResource("/nsd/nsd-ext-merged-schema.xsd"))
val rtsXmlValid = XMLValid(getClass.getResource("/rts/fpml-recordkeeping-merged-schema.xsd"))
var logString = ""
for (v <- Files.walk(Paths.get(args(0))).toArray; f = v.asInstanceOf[Path]; if !Files.isDirectory(f)) {
val fSourceName= f.getFileName.toString
val fSourceNameArray = fSourceName.split('.')
val fSourceNameBase = fSourceNameArray.head
val fSourceNameExtension = fSourceNameArray.last.toLowerCase
val now = LocalDateTime.now().toString
if (fSourceNameExtension == "zip") Try {
val fZip = new ZipFile(f.toFile)
val fZipEntries = fZip.entries
while (fZipEntries.hasMoreElements) {
val e = fZipEntries.nextElement
val fZipEntryName = e.getName
val nowForZip = LocalDateTime.now().toString
Try {
convert(
fZip.getInputStream(e),
s"${fSourceNameBase}_$fZipEntryName",
s"Converted_${fSourceNameBase}_$fZipEntryName",
nsdXmlValid,
rtsXmlValid,
p)
} match {
case Success((oXml, ti)) =>
XML.save(Paths.get(args(1), s"Converted_${fSourceNameBase}_$fZipEntryName").toString, oXml, xmlDecl = true)
logString += s"$nowForZip\n$ti"
case Failure(ex) => logString += s"'$nowForZip\nImpossible to convert'${fSourceNameBase}_$fZipEntryName': ${ex.getMessage}\n\n"
}
}
} match {
case Success(_) =>
case Failure(ex) => logString += s"'$now\nImpossible to convert'$fSourceName': ${ex.getMessage}\n\n"
}
else Try {
convert(
new FileInputStream(f.toFile),
s"$fSourceNameBase",
s"Converted_$fSourceName",
nsdXmlValid,
rtsXmlValid,
p)
} match {
case Success((oXml,ti)) =>
XML.save(Paths.get(args(1), s"Converted_$fSourceName").toString, oXml, xmlDecl = true)
logString += s"$now\n$ti"
case Failure(ex) => logString += s"'$now\nImpossible to convert'$fSourceName': ${ex.getMessage}\n\n"
}
}
Try {
Files.write(
Paths.get(args(1), logFileName),
logString.getBytes("utf-8"),
StandardOpenOption.CREATE,
StandardOpenOption.TRUNCATE_EXISTING)
} match {
case Success(_) => println(s"Converting has been finished. $logFileName located in ${args(1)}")
case Failure(ex) => println(s"Error. Converting hasn`t been finished: ${ex.getMessage}")
}
}
}
implicit def templateFactory(source: Node): Template = { implicit def templateFactory(source: Node): Template = {
Try { (source \\ "trade").head.child Try { (source \\ "trade").head.child
.filter { .filter {
...@@ -59,72 +140,39 @@ object Main { ...@@ -59,72 +140,39 @@ object Main {
} }
} }
def main(args: Array[String]): Unit = { def convert(
println("Converting NSD <-> RTS has been started...") inputStream: InputStream,
sName: String,
if (args.length != 2) oName: String,
println("Error. Converting hasn`t been finished: Undefined INPUT/OUTPUT directory.\nUsage: run INPUT OUTPUT") nsdScheme: XMLValid,
else if (!Files.exists(Paths.get(args(0)))) rtsScheme: XMLValid,
println("Error. Converting hasn`t been finished: INPUT directory doesn`t exist") pp: PrettyPrinter): (Node, String) = {
else if (!Files.exists(Paths.get(args(1)))) val sourceXml = XML.load(inputStream)
println("Error. Converting hasn`t been finished: OUTPUT directory doesn`t exist")
else {
val p = new PrettyPrinter(160, 2)
val nsdXmlValid = XMLValid(getClass.getResource("/nsd/nsd-ext-merged-schema.xsd"))
val rtsXmlValid = XMLValid(getClass.getResource("/rts/fpml-recordkeeping-merged-schema.xsd"))
var logString = ""
for (v <- Files.walk(Paths.get(args(0))).toArray; f = v.asInstanceOf[Path]; if !Files.isDirectory(f)) {
val fSourceName= f.getFileName.toString
val fOutputName = s"Converted_$fSourceName"
val now = LocalDateTime.now().toString
Try {
val sourceXml = XML.loadFile(f.toString)
val template = Template(sourceXml) val template = Template(sourceXml)
/* temporary */ /* temporary */
val outputXml = XML.loadString(p.format(template.render) val outputXml = XML.loadString(pp.format(template.render)
.replace("RP0058900001", "MFBIM") .replace("RP0058900001", "MFBIM")
.replace("NDC000000000", "SPB01") .replace("NDC000000000", "SPB01")
.replace("НКО АО НРД", "ПАО «Санкт-Петербургская биржа»")) .replace("НКО АО НРД", "ПАО «Санкт-Петербургская биржа»"))
val sourceXmlValid = if (template.isStraight) nsdXmlValid else rtsXmlValid val sourceXmlValid = if (template.isStraight) nsdScheme else rtsScheme
val outputXmlValid = if (template.isStraight) rtsXmlValid else nsdXmlValid val outputXmlValid = if (template.isStraight) rtsScheme else nsdScheme
val msgCheckSource = Try { val msgCheckSource = Try {
sourceXmlValid.loadString(sourceXml.mkString) sourceXmlValid.loadString(sourceXml.mkString)
} match { } match {
case Success(_) => s"'$fSourceName' successfully checked against schema" case Success(_) => s"'$sName' successfully checked against schema"
case Failure(ex) => s"'$fSourceName' isn`t wellformed or invalid: ${ex.getMessage}" case Failure(ex) => s"'$sName' isn`t wellformed or invalid: ${ex.getMessage}"
} }
val msgCheckOutput = Try { val msgCheckOutput = Try {
outputXmlValid.loadString(outputXml.mkString) outputXmlValid.loadString(outputXml.mkString)
} match { } match {
case Success(_) => s"'$fOutputName' successfully checked against schema" case Success(_) => s"'$oName' successfully checked against schema"
case Failure(ex) => s"'$fOutputName' isn`t wellformed or invalid: ${ex.getMessage}" case Failure(ex) => s"'$oName' isn`t wellformed or invalid: ${ex.getMessage}"
}
XML.save(Paths.get(args(1), fOutputName).toString, outputXml, xmlDecl = true)
template.info(s"$now\n$msgCheckSource\n$msgCheckOutput") + "\n\n"
} match {
case Success(ti) => logString += ti
case Failure(ex) => logString += s"'$now\nImpossible to convert'$fSourceName': ${ex.getMessage}\n\n"
}
} }
Try { (outputXml, template.info(s"$msgCheckSource\n$msgCheckOutput") + "\n\n")
Files.write(
Paths.get(args(1), logFileName),
logString.getBytes("utf-8"),
StandardOpenOption.CREATE,
StandardOpenOption.TRUNCATE_EXISTING)
} match {
case Success(_) => println(s"Converting has been finished. $logFileName located in ${args(1)}")
case Failure(ex) => println(s"Error. Converting hasn`t been finished: ${ex.getMessage}")
}
}
} }
} }
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment