यहाँ एक config पढ़ने के लिए एक्सएमएल और एक मामले वर्ग का उपयोग करने का एक उदाहरण है:
यहाँ लोड हो रहा है रंगमंच की सामग्री के लिए कुछ उदाहरण कोड के रूप में स्काला नक्शा जोड़ तोड़, उसके बाद फिर से .properties के रूप में बचत है,। एक वास्तविक वर्ग एक मानचित्र से बेहतर हो सकता है। (आप यह भी कर सकते हैं कि एसबीटी और कम से कम एक प्रोजेक्ट क्या करता है, कॉन्फ़िगर को स्केल स्रोत के रूप में ले जाएं और इसे संकलित करें; इसे सहेजना कम स्वचालित है या एक प्रतिलिपि स्क्रिप्ट के रूप में। मैंने गुग नहीं किया है, लेकिन किसी ने ऐसा किया होगा।
case class PluginDescription(name: String, classname: String) {
def toXML: Node = {
<plugin>
<name>{name}</name>
<classname>{classname}</classname>
</plugin>
}
}
object PluginDescription {
def fromXML(xml: Node): PluginDescription = {
// extract one field
def getField(field: String): Option[String] = {
val text = (xml \\ field).text.trim
if (text == "") None else Some(text)
}
def extracted = {
val name = "name"
val claas = "classname"
val vs = Map(name -> getField(name), claas -> getField(claas))
if (vs.values exists (_.isEmpty)) fail()
else PluginDescription(name = vs(name).get, classname = vs(claas).get)
}
def fail() = throw new RuntimeException("Bad plugin descriptor.")
// check the top-level tag
xml match {
case <plugin>{_*}</plugin> => extracted
case _ => fail()
}
}
}
इस कोड को संजीदगी से एक मामले वर्ग के लागू कॉल:)
Here's the simpler code.
इस संस्करण में एक मामला वर्ग का उपयोग करता है। उपयोग का मामला यह है कि कॉन्फ़िगरेशन से अनुपलब्ध फ़ील्ड डिफ़ॉल्ट तर्कों द्वारा आपूर्ति की जा सकती हैं। यहां कोई प्रकार का रूपांतरण नहीं है। उदा।, case class Config(foo: String = "bar")
।
// isn't it easier to write a quick loop to reflect the field names?
import scala.reflect.runtime.{currentMirror => cm, universe => ru}
import ru._
def fromXML(xml: Node): Option[PluginDescription] = {
def extract[A]()(implicit tt: TypeTag[A]): Option[A] = {
// extract one field
def getField(field: String): Option[String] = {
val text = (xml \\ field).text.trim
if (text == "") None else Some(text)
}
val apply = ru.newTermName("apply")
val module = ru.typeOf[A].typeSymbol.companionSymbol.asModule
val ts = module.moduleClass.typeSignature
val m = (ts member apply).asMethod
val im = cm reflect (cm reflectModule module).instance
val mm = im reflectMethod m
def getDefault(i: Int): Option[Any] = {
val n = ru.newTermName("apply$default$" + (i+1))
val m = ts member n
if (m == NoSymbol) None
else Some((im reflectMethod m.asMethod)())
}
def extractArgs(pss: List[List[Symbol]]): List[Option[Any]] =
pss.flatten.zipWithIndex map (p => getField(p._1.name.encoded) orElse getDefault(p._2))
val args = extractArgs(m.paramss)
if (args exists (!_.isDefined)) None
else Some(mm(args.flatten: _*).asInstanceOf[A])
}
// check the top-level tag
xml match {
case <plugin>{_*}</plugin> => extract[PluginDescription]()
case _ => None
}
}
एक्सएमएल loadFile
और save
है, यह बहुत बुरा वहाँ Properties
के लिए कोई एक लाइनर हो रहा है है।
$ scala
Welcome to Scala version 2.10.0-RC5 (Java HotSpot(TM) 64-Bit Server VM, Java 1.7.0_06).
Type in expressions to have them evaluated.
Type :help for more information.
scala> import reflect.io._
import reflect.io._
scala> import java.util._
import java.util._
scala> import java.io.{StringReader, File=>JFile}
import java.io.{StringReader, File=>JFile}
scala> import scala.collection.JavaConverters._
import scala.collection.JavaConverters._
scala> val p = new Properties
p: java.util.Properties = {}
scala> p load new StringReader(
| (new File(new JFile("t.properties"))).slurp)
scala> p.asScala
res2: scala.collection.mutable.Map[String,String] = Map(foo -> bar)
स्रोत
2012-12-18 06:43:12
मैं JSON4s का उपयोग कर जेएसओएन को क्रमबद्ध करने के लिए समाप्त हुआ https://github.com/json4s/json4s सभी सुझावों के लिए धन्यवाद। – Dave