web-dev-qa-db-fra.com

Comment lire les fichiers du dossier de ressources dans Scala?

J'ai une structure de dossier comme ci-dessous:

- main
-- Java
-- resources 
-- scalaresources
--- commandFiles 

et dans ces dossiers, j'ai mes fichiers que je dois lire. Voici le code:

def readData(runtype: String, snmphost: String, comstring: String, specificType:  String): Unit = {
  val realOrInvFile = "/commandFiles/snmpcmds." +runtype.trim // these files are under commandFiles folder, which I have to read. 
    try {
      if (specificType.equalsIgnoreCase("Cisco")) {
        val specificDeviceFile: String = "/commandFiles/snmpcmds."+runtype.trim+ ".Cisco"
        val realOrInvCmdsList = scala.io.Source.fromFile(realOrInvFile).getLines().toList.filterNot(line => line.startsWith("#")).map{
          //some code 
        }
        val specificCmdsList = scala.io.Source.fromFile(specificDeviceFile).getLines().toList.filterNot(line => line.startsWith("#")).map{
          //some code
        }
      }
    } catch {
      case e: Exception => e.printStackTrace
    }
  }
}
95
Pradip Karad

Les ressources dans Scala fonctionnent exactement comme en Java. Il est préférable de suivre les meilleures pratiques Java et de mettre toutes les ressources dans src/main/resources et src/test/resources.

Exemple de structure de dossier:

testing_styles/
├── build.sbt
├── src
│   └── main
│       ├── resources
│       │   └── readme.txt

Scala 2.12.x && 2.13.x lire une ressource

Pour lire des ressources, l'objet Source fournit la méthode fromResource.

import scala.io.Source
val readmeText : Iterator[String] = Source.fromResource("readme.txt").getLines

lecture des ressources antérieures à 2.12 (toujours mon préféré en raison de la compatibilité des jar)

Pour lire des ressources, vous pouvez utiliser getClass.getResource et getClass.getResourceAsStream.

val stream: InputStream = getClass.getResourceAsStream("/readme.txt")
val lines: Iterator[String] = scala.io.Source.fromInputStream( stream ).getLines

meilleur retour d'erreur (2.12.x && 2.13.x)

Pour éviter les NPE indéfinis Java, tenez compte des points suivants:

import scala.util.Try
import scala.io.Source
import Java.io.FileNotFoundException

object Example {

  def readResourceWithNiceError(resourcePath: String): Try[Iterator[String]] = 
    Try(Source.fromResource(resourcePath).getLines)
      .recover(throw new FileNotFoundException(resourcePath))
 }

bon à savoir

Gardez à l'esprit que getResourceAsStream fonctionne également bien lorsque les ressources font partie d'un jar, getResource, qui renvoie une URL souvent utilisée pour créer un fichier peut y poser des problèmes.

en production

Dans le code de production, je suggère de vérifier que le code source est à nouveau fermé.

175
Andreas Neumann

Pour Scala> = 2.12, utilisez Source.fromResource:

scala.io.Source.fromResource("located_in_resouces.any")
27
Mohsen Kashi

Solution Onliner pour Scala> = 2.12

val source_html = Source.fromResource("file.html").getLines().mkString("\n")
6
freedev
import scala.io.Source

object Demo {

  def main(args: Array[String]): Unit = {

    val fileStream = getClass.getResourceAsStream("/json-sample.js")
    val lines = Source.fromInputStream(fileStream).getLines
    lines.foreach(line => println(line))

  }

}

enter image description here

EDIT: crédit à l'auteur original. Référez-vous le blog complet ici

3
Sri

Pour Scala 2.11Si getLines ne fait pas exactement ce que vous voulez, vous pouvez également copier le fichier du fichier jar dans le système de fichiers local.

Voici un extrait qui lit une clé d’API au format binaire google .p12 dans/resources, l’écrit dans/tmp, puis utilise la chaîne de chemin du fichier comme entrée de spark-google-spreadsheetsécrire .

Dans le monde de sbt-native-packager et sbt-Assembly , la copie au niveau local est également utile avec les tests de fichiers binaires scalatest. Il suffit de les extraire des ressources au niveau local, d'exécuter les tests, puis de les supprimer.

import Java.io.{File, FileOutputStream}
import Java.nio.file.{Files, Paths}

def resourceToLocal(resourcePath: String) = {
  val outPath = "/tmp/" + resourcePath
  if (!Files.exists(Paths.get(outPath))) {
    val resourceFileStream = getClass.getResourceAsStream(s"/${resourcePath}")
    val fos = new FileOutputStream(outPath)
    fos.write(
      Stream.continually(resourceFileStream.read).takeWhile(-1 !=).map(_.toByte).toArray
    )
    fos.close()
  }
  outPath
}

val filePathFromResourcesDirectory = "google-docs-key.p12"
val serviceAccountId = "[something]@drive-integration-[something].iam.gserviceaccount.com"
val googleSheetId = "1nC8Y3a8cvtXhhrpZCNAsP4MBHRm5Uee4xX-rCW3CW_4"
val tabName = "Favorite Cities"

import spark.implicits
val df = Seq(("Brooklyn", "New York"), 
          ("New York City", "New York"), 
          ("San Francisco", "California")).
          toDF("City", "State")

df.write.
  format("com.github.potix2.spark.google.spreadsheets").
  option("serviceAccountId", serviceAccountId).
  option("credentialPath", resourceToLocal(filePathFromResourcesDirectory)).
  save(s"${googleSheetId}/${tabName}")
2
Tony Fraser

Le fichier requis est accessible comme ci-dessous à partir du dossier de ressources dans scala

val file = scala.io.Source.fromFile (s "src/main/resources/app.config"). getLines (). mkString

0
dominicrd