scala/mail-parser/mail-parser.sc: email parser (based on java mail api); ammonite.io script
/*
* Copyright ...
*/
package example
import java.net.InetAddress
import net.liftweb.common._
import net.liftweb.mapper._
import net.liftweb.util._
import net.liftweb.util.Helpers._
object InetAddressHelpers extends InetAddressHelpers
trait InetAddressHelpers {
def normalize(inet: String): Box[String] = tryo {
InetAddress.getByName(inet).getHostAddress
}
def valid_?(inet: String): Boolean = (inet != null) && (tryo {
InetAddress.getByName(inet)
} isDefined ) && (inet.length > 0)
def toBigInt(inet: InetAddress): BigInt = BigInt(1, inet.getAddress)
def toInet(s: String): Box[InetAddress] = s match {
case null | "" => Empty
case _ => tryo { InetAddress.getByName(s) }
}
}
/**
* Postgres specific <code>InetAddress</code> mapping
* (maps to ''inet'' data type).
* Always use <code>asInet</code> to get <code>InetAddress</code> instance.
*/
abstract class MappedInetAddress[T<:Mapper[T]](owner: T) extends
MappedString[T](owner, 128) with InetAddressHelpers {
override def setFilter = normalizeFilter _ :: super.setFilter
override def validate = (valid_?(i_is_!) match {
case true => Nil
case false => List(FieldError(this, "Invalid IP address"))
}) ::: super.validate
def normalizeFilter(inet: String): String = inet match {
case null | "" => null
case s => normalize(s) openOr null
}
def asInet: Box[InetAddress] = toInet(is)
override def targetSQLType = Types.OTHER
override def fieldCreatorString(d: DriverType, colName: String) = d match {
case _d: BasePostgreSQLDriver => colName + " inet"
case _ => super.fieldCreatorString(d, colName)
}
}
/**
* Caution: getters may return <code>null</code> value.
* Always use <code>asInet</code>.
*/
abstract class MappedNullableInetAddress[T<:Mapper[T]](owner: T) extends
MappedInetAddress[T](owner) {
override def defaultValue = null
override def validate = i_is_! match {
case null | "" => Nil
case _ => super.validate
}
override def dbNotNull_? = false
}
/**
* IP network mapper via its start/end fields.
* Implemented validation of IP overlaps, parent network, start, end.
* Maintains network relationships (sub-net/super-net) and updates
* parent field accordingly.
*/
object ExampleNetwork extends ExampleNetwork with
LongKeyedMetaMapper[ExampleNetwork] with LongCRUDify[ExampleNetwork] {
override def validation: List[ExampleNetwork => List[FieldError]] =
startLtEnd _ :: checkOverlap _ :: super.validation
def startLtEnd(n: ExampleNetwork): List[FieldError] = (for {
s <- n.start.asInet
e <- n.end.asInet
} yield (toBigInt(s) < toBigInt(e))) match {
case Full(true) => Nil
case Full(false) =>
List(FieldError(n.start, "Start must be below end"))
case _ =>
List(FieldError(n.start, S ? "Can't compare start/end IP"))
}
def checkOverlap(net: ExampleNetwork): List[FieldError] = {
def run(f: MappedInetAddress[ExampleNetwork]) = {
findAll(inNet(f):_*) filter {!_.comparePrimaryKeys(net)} filter { n =>
net.isSubnetOf(n) match {
case f: Failure => true
case _ => false
}} map { n =>
FieldError(f, "Overlaps with: " + n.start + " - " + n.end)
}
}
run(net.start) ::: run(net.end)
}
override def beforeSave = List(n => n.parent(findParent(a)))
override def afterSave = List(n => children(n.parent.obj) foreach { child =>
child.parent(findParent(child)).save
})
override def afterDelete = List(n => children(Full(n)) foreach { child =>
child.parent(findParent(child)).save
})
def findParent(net: ExampleNetwork): Box[ExampleNetwork] =
findAll(inNet(net):_*) filter {!_.comparePrimaryKeys(net)} sort {
(n1, n2) => (for {
s1 <- n1.size
s2 <- n2.size
} yield s1 < s2) openOr true } firstOption
import OprEnum._
def inNet(inet: MappedInetAddress[ExampleNetwork]) = List(
Cmp(start, <=, Full(inet.is), Empty, Empty),
Cmp(end, >=, Full(inet.is), Empty, Empty)
)
def inNet(net: ExampleNetwork): List[QueryParam[ExampleNetwork]] =
inNet(net.start) ::: inNet(net.end)
def getByNet(s: String, e: String) = Box(findAll(By(start, s), By(end, e)))
def children(n: Box[ExampleNetwork]) = findAll(By(parent, n))
}
class ExampleNetwork extends LongKeyedMapper[ExampleNetwork] with IdPK
with InetAddressHelpers {
override def getSingleton = ExampleNetwork
object start extends MappedInetAddress(this)
object end extends MappedInetAddress(this)
object parent extends LongMappedMapper(this, ExampleNetwork) {
override def dbIncludeInForm_? = false
}
def size: Box[BigInt] = for {
s <- start.asInet
e <- end.asInet
} yield toBigInt(e) - toBigInt(s) + 1
/**
* Checks if this network is subnet of the <code>other</code>.
* @return true if this is subnet of the other
* false if this is supernet
* empty not related at all
* failure if can't compare or network overlap
*/
def isSubnetOf(other: ExampleNetwork): Box[Boolean] = {
def inside(what: BigInt, from: BigInt, to: BigInt): Boolean =
(from <= what) && (what <= to)
(for {
si <- start.asInet
ei <- end.asInet
osi <- other.start.asInet
oei <- other.end.asInet
} yield {
val s = toBigInt(si)
val e = toBigInt(ei)
val os = toBigInt(osi)
val oe = toBigInt(oei)
val s_inside = inside(s, os, oe)
val e_inside = inside(e, os, oe)
val os_inside = inside(os, s, e)
val oe_inside = inside(oe, s, e)
(s_inside, e_inside, os_inside, oe_inside) match {
case (true, true, _, _) => Full(true)
case (_, _, true, true) => Full(false)
case (false, false, false, false) => Empty
case (_, _, _, _) => Failure("IP address overlap with: " + other)
}
}).openOr(Failure("Failed to obtain inet addresses: this: " + this +
", other: " + other))
}
}
// vim: set ts=2 sw=2 et: