This is an automated email from the ASF dual-hosted git repository.
aradzinski pushed a commit to branch NLPCRAFT-206
in repository https://gitbox.apache.org/repos/asf/incubator-nlpcraft.git
The following commit(s) were added to refs/heads/NLPCRAFT-206 by this push:
new f5bef38 WIP.
f5bef38 is described below
commit f5bef38a647d9f8804ae5bacde44040e0b218f9a
Author: Aaron Radzinzski <[email protected]>
AuthorDate: Fri Mar 5 16:14:28 2021 -0800
WIP.
---
.../intent/impl/NCIntentDslBaselCompiler.scala | 1 -
.../model/intent/impl/NCIntentSolverEngine.scala | 51 +++--
.../probe/mgrs/deploy/NCDeployManager.scala | 207 ++++++++++-----------
.../nlpcraft/probe/mgrs/model/NCModelManager.scala | 3 +-
4 files changed, 137 insertions(+), 125 deletions(-)
diff --git
a/nlpcraft/src/main/scala/org/apache/nlpcraft/model/intent/impl/NCIntentDslBaselCompiler.scala
b/nlpcraft/src/main/scala/org/apache/nlpcraft/model/intent/impl/NCIntentDslBaselCompiler.scala
index 16db816..95d35b3 100644
---
a/nlpcraft/src/main/scala/org/apache/nlpcraft/model/intent/impl/NCIntentDslBaselCompiler.scala
+++
b/nlpcraft/src/main/scala/org/apache/nlpcraft/model/intent/impl/NCIntentDslBaselCompiler.scala
@@ -23,7 +23,6 @@ import org.apache.commons.lang3.StringUtils
import org.apache.nlpcraft.common._
import org.apache.nlpcraft.model.NCToken
import org.apache.nlpcraft.model.intent.utils.{NCDslTermContext,
NCDslTermRetVal}
-import org.apache.nlpcraft.model.intent.utils.ver2.NCDslTermRetVal
import java.lang.{Double ⇒ JDouble, Long ⇒ JLong}
import java.time.LocalDate
diff --git
a/nlpcraft/src/main/scala/org/apache/nlpcraft/model/intent/impl/NCIntentSolverEngine.scala
b/nlpcraft/src/main/scala/org/apache/nlpcraft/model/intent/impl/NCIntentSolverEngine.scala
index d2a5bfa..a9b688a 100644
---
a/nlpcraft/src/main/scala/org/apache/nlpcraft/model/intent/impl/NCIntentSolverEngine.scala
+++
b/nlpcraft/src/main/scala/org/apache/nlpcraft/model/intent/impl/NCIntentSolverEngine.scala
@@ -494,11 +494,22 @@ object NCIntentSolverEngine extends LazyLogging with
NCOpenCensusTrace {
var abort = false
val ordered = intent.ordered
var lastTermMatch: TermMatch = null
+
+ val termCtx = NCDslTermContext( // TODO
+ intentMeta = null,
+ reqMeta = null,
+ usrMeta = null,
+ convMeta = null,
+ compMeta = null,
+ fragMeta = null,
+ req = ctx.getRequest
+ )
// Check terms.
for (term ← intent.terms if !abort) {
solveTerm(
term,
+ termCtx,
senToks,
if (term.conv) convToks else Seq.empty
) match {
@@ -592,8 +603,10 @@ object NCIntentSolverEngine extends LazyLogging with
NCOpenCensusTrace {
}
/**
- *
+ * Solves term.
+ *
* @param term
+ * @param ctx
* @param convToks
* @param senToks
* @return
@@ -601,10 +614,11 @@ object NCIntentSolverEngine extends LazyLogging with
NCOpenCensusTrace {
@throws[NCE]
private def solveTerm(
term: NCDslTerm,
+ ctx: NCDslTermContext,
senToks: Seq[UsedToken],
convToks: Seq[UsedToken]
): Option[TermMatch] =
- solvePredicate(term.pred, term.min, term.max, senToks, convToks) match
{
+ solvePredicate(term.pred, ctx, term.min, term.max, senToks, convToks)
match {
case Some((usedToks, predWeight)) ⇒ Some(
TermMatch(
term.id,
@@ -637,8 +651,10 @@ object NCIntentSolverEngine extends LazyLogging with
NCOpenCensusTrace {
}
/**
+ * Solves term's predicate.
*
* @param pred
+ * @param ctx
* @param min
* @param max
* @param senToks
@@ -648,6 +664,7 @@ object NCIntentSolverEngine extends LazyLogging with
NCOpenCensusTrace {
@throws[NCE]
private def solvePredicate(
pred: (NCToken, NCDslTermContext) ⇒ (Boolean/*Predicate.*/,
Boolean/*Whether or not token was used.*/),
+ ctx: NCDslTermContext,
min: Int,
max: Int,
senToks: Seq[UsedToken],
@@ -658,23 +675,35 @@ object NCIntentSolverEngine extends LazyLogging with
NCOpenCensusTrace {
// and conversation will be used only to get to the 'max' number of
the item.
var usedToks = List.empty[UsedToken]
+
+ var matches = 0
// Collect to the 'max' from sentence & conversation, if possible.
- for (col ← Seq(senToks, convToks); tok ← col.filter(!_.used) if
usedToks.lengthCompare(max) < 0)
- if (pred.apply(tok.token))
- usedToks :+= tok
-
- // We couldn't collect even 'min' tokens.
- if (usedToks.lengthCompare(min) < 0)
+ for (col ← Seq(senToks, convToks); tok ← col.filter(!_.used) if
usedToks.lengthCompare(max) < 0) {
+ val (res, used) = pred.apply(tok.token, ctx)
+
+ if (res) {
+ matches += 1
+
+ if (used)
+ usedToks :+= tok
+ }
+ }
+
+ // We couldn't collect even 'min' matches.
+ if (matches < min)
None
- // Item is optional (min == 0) and no tokens collected (valid result).
- else if (usedToks.isEmpty) {
+ // Term is optional (min == 0) and no matches found (valid result).
+ else if (matches == 0) {
require(min == 0)
+ require(usedToks.isEmpty)
Some(usedToks → new Weight(0, 0))
}
- // We've collected some tokens (and min > 0).
+ // We've found some matches (and min > 0).
else {
+ require(matches > 0 && matches > min)
+
val convSrvReqIds =
convToks.map(_.token.getServerRequestId).distinct
// Number of tokens from the current sentence.
diff --git
a/nlpcraft/src/main/scala/org/apache/nlpcraft/probe/mgrs/deploy/NCDeployManager.scala
b/nlpcraft/src/main/scala/org/apache/nlpcraft/probe/mgrs/deploy/NCDeployManager.scala
index ab71498..4f281d4 100644
---
a/nlpcraft/src/main/scala/org/apache/nlpcraft/probe/mgrs/deploy/NCDeployManager.scala
+++
b/nlpcraft/src/main/scala/org/apache/nlpcraft/probe/mgrs/deploy/NCDeployManager.scala
@@ -76,10 +76,11 @@ object NCDeployManager extends NCService with
DecorateAsScala {
CLS_JAVA_LST,
CLS_JAVA_OPT
)
-
- private final val SEPARATORS = Seq('?', ',', '.', '-', '!')
-
+
type Callback = Function[NCIntentMatch, NCResult]
+ type Intent = (NCDslIntent, Callback)
+
+ private final val SEPARATORS = Seq('?', ',', '.', '-', '!')
@volatile private var data: ArrayBuffer[NCProbeModel] = _
@volatile private var mdlFactory: NCModelFactory = _
@@ -1155,7 +1156,7 @@ object NCDeployManager extends NCService with
DecorateAsScala {
// Checks correctness of term IDs.
// Note we don't restrict them to be duplicated.
- val intentTermIds = terms.filter(_.getId != null).map(_.getId)
+ val intentTermIds = terms.filter(_.id != null).map(_.id)
val invalidIds = termIds.filter(id ⇒ !intentTermIds.contains(id))
if (invalidIds.nonEmpty) {
@@ -1175,7 +1176,7 @@ object NCDeployManager extends NCService with
DecorateAsScala {
checkTypes(mdlId, mtd, tokParamTypes, paramGenTypes, ctxFirstParam)
// Checks limits.
- val allLimits = terms.map(t ⇒ t.getId → (t.getMin, t.getMax)).toMap
+ val allLimits = terms.map(t ⇒ t.id → (t.min, t.max)).toMap
checkMinMax(mdlId, mtd, tokParamTypes, termIds.map(allLimits),
ctxFirstParam)
@@ -1452,83 +1453,69 @@ object NCDeployManager extends NCService with
DecorateAsScala {
* @param o Object.
* @return Methods.
*/
- private def getProcessedMethods(o: AnyRef): Set[Method] = {
+ private def getAllMethods(o: AnyRef): Set[Method] = {
val claxx = o.getClass
(claxx.getDeclaredMethods ++ claxx.getMethods).toSet
}
-
+
/**
*
* @param mdl
*/
@throws[NCE]
- private def scanIntents(mdl: NCModel): Map[NCDslIntent, Callback] = {
+ private def scanIntents(mdl: NCModel): Set[Intent] = {
val mdlId = mdl.getId
-
- getProcessedMethods(mdl).flatMap(m ⇒ {
- // Direct in-the-class and referenced intents.
- val clsArr = m.getAnnotationsByType(CLS_INTENT)
- val refArr = m.getAnnotationsByType(CLS_INTENT_REF)
-
- if (clsArr.length > 1 || refArr.length > 1 || (clsArr.nonEmpty &&
refArr.nonEmpty))
- throw new NCE(s"Only one @NCIntent or @NCIntentRef annotation
is allowed for callback [" +
- s"mdlId=$mdlId, " +
- s"callback=${method2Str(m)}" +
- s"]")
-
- val cls = m.getAnnotation(CLS_INTENT)
-
- if (cls != null)
- Some(NCIntentDslCompiler.compile(cls.value(), mdl.getId), m)
- else {
- val ref = m.getAnnotation(CLS_INTENT_REF)
-
- if (ref != null)
- mdl match {
- case adapter: NCModelFileAdapter ⇒
- val refId = ref.value().trim
-
- val compiledIntents = adapter
- .getIntents
- .asScala
- .map(NCIntentDslCompiler.compile(_, mdl.getId))
-
- U.getDups(compiledIntents.toSeq.map(_.id)) match {
- case ids if ids.nonEmpty ⇒
- throw new NCE(s"Duplicate intent IDs found
[" +
+ val intents = mutable.Buffer.empty[Intent]
+
+ for (m ← getAllMethods(mdl)) {
+ // Process inline intent declarations by @NCIntent annotation.
+ for (ann ← m.getAnnotationsByType(CLS_INTENT); intent ←
NCIntentDslCompiler.compile(ann.value(), mdl.getId))
+ intents += (intent → prepareCallback(m, mdl, intent))
+
+ // Process intent references from @NCIntentRef annotation.
+ for (ann ← m.getAnnotationsByType(CLS_INTENT_REF)) {
+ mdl match {
+ case adapter: NCModelFileAdapter ⇒
+ val refId = ann.value().trim
+
+ val compiledIntents = adapter
+ .getIntents
+ .asScala
+ .flatMap(NCIntentDslCompiler.compile(_, mdl.getId))
+
+ U.getDups(compiledIntents.toSeq.map(_.id)) match {
+ case ids if ids.nonEmpty ⇒
+ throw new NCE(s"Duplicate intent IDs found [" +
+ s"mdlId=$mdlId, " +
+ s"origin=${adapter.getOrigin}, " +
+ s"ids=${ids.mkString(",")}" +
+ s"]")
+
+ case _ ⇒ ()
+ }
+
+ compiledIntents.find(_.id == refId) match {
+ case Some(intent) ⇒ Some(intent,
prepareCallback(m, mdl, intent))
+ case None ⇒
+ throw new NCE(
+ s"@IntentRef($refId) references unknown
intent ID [" +
s"mdlId=$mdlId, " +
- s"origin=${adapter.getOrigin}, " +
- s"ids=${ids.mkString(",")}" +
+ s"refId=$refId, " +
+ s"callback=${method2Str(m)}" +
s"]")
-
- case _ ⇒ ()
- }
-
- compiledIntents.find(_.id == refId) match {
- case Some(intent) ⇒ Some(intent, m)
- case None ⇒
- throw new NCE(
- s"@IntentRef($refId) references
unknown intent ID [" +
- s"mdlId=$mdlId, " +
- s"refId=$refId, " +
- s"callback=${method2Str(m)}" +
- s"]")
- }
-
- case _ ⇒
- throw new NCE(s"@IntentRef annotation can only be
used for models extending 'NCModelFileAdapter' class [" +
- s"mdlId=$mdlId, " +
- s"callback=${method2Str(m)}" +
- s"]")
- }
- else
- None
+ }
+
+ case _ ⇒
+ throw new NCE(s"@IntentRef annotation can only be used
for models extending 'NCModelFileAdapter' class [" +
+ s"mdlId=$mdlId, " +
+ s"callback=${method2Str(m)}" +
+ s"]")
+ }
}
- })
- .map {
- case (intent, m) ⇒ intent → prepareCallback(m, mdl, intent)
- }.toMap
+ }
+
+ intents.toSet
}
/**
@@ -1541,62 +1528,58 @@ object NCDeployManager extends NCService with
DecorateAsScala {
var annFound = false
val mdlId = mdl.getId
- val samples =
- getProcessedMethods(mdl).flatMap(mtd ⇒ {
- def mkMethodName: String =
s"$C${mtd.getDeclaringClass.getName}#${mtd.getName}(...)$RST"
+ val samples = getAllMethods(mdl).flatMap(mtd ⇒ {
+ def mkMethodName: String =
s"$C${mtd.getDeclaringClass.getName}#${mtd.getName}(...)$RST"
- val smpAnns = mtd.getAnnotationsByType(CLS_SAMPLE)
+ val smpAnns = mtd.getAnnotationsByType(CLS_SAMPLE)
+ val intAnn = mtd.getAnnotation(CLS_INTENT)
+ val refAnn = mtd.getAnnotation(CLS_INTENT_REF)
- require(smpAnns != null)
+ if (smpAnns.nonEmpty || intAnn != null || refAnn != null) {
+ annFound = true
- val intAnn = mtd.getAnnotation(CLS_INTENT)
- val refAnn = mtd.getAnnotation(CLS_INTENT_REF)
+ def mkIntentId(): String =
+ if (intAnn != null)
+ NCIntentDslCompiler.compile(intAnn.value(), mdlId).id
+ else if (refAnn != null)
+ refAnn.value().trim
+ else
+ throw new AssertionError()
- if (smpAnns.nonEmpty || intAnn != null || refAnn != null) {
- annFound = true
+ if (smpAnns.nonEmpty) {
+ if (intAnn == null && refAnn == null) {
+ logger.warn(s"`@${CLS_SAMPLE.getSimpleName} annotation
without corresponding @NCIntent or @NCIntentRef annotations: $mkMethodName")
- def mkIntentId(): String =
- if (intAnn != null)
- NCIntentDslCompiler.compile(intAnn.value(),
mdlId).id
- else if (refAnn != null)
- refAnn.value().trim
- else
- throw new AssertionError()
+ None
+ }
+ else {
+ val samples = smpAnns.toSeq.map(_.value().toSeq)
- if (smpAnns.nonEmpty) {
- if (intAnn == null && refAnn == null) {
- logger.warn(s"`@${CLS_SAMPLE.getSimpleName}
annotation without corresponding @NCIntent or @NCIntentRef annotations:
$mkMethodName")
+ if (samples.exists(_.isEmpty)) {
+ logger.warn(s"@${CLS_SAMPLE.getSimpleName}
annotation is empty: $mkMethodName")
None
}
- else {
- val samples = smpAnns.toSeq.map(_.value().toSeq)
-
- if (samples.exists(_.isEmpty)) {
- logger.warn(s"@${CLS_SAMPLE.getSimpleName}
annotation is empty: $mkMethodName")
+ else if (U.containsDups(samples.flatten.toList)) {
+ logger.warn(s"@${CLS_SAMPLE.getSimpleName}
annotation has duplicates: $mkMethodName")
- None
- }
- else if (U.containsDups(samples.flatten.toList)) {
- logger.warn(s"@${CLS_SAMPLE.getSimpleName}
annotation has duplicates: $mkMethodName")
-
- // Samples is list of list. Duplicates cannot
be inside one list,
- // but possible between different lists.
- Some(mkIntentId() →
samples.map(_.distinct).distinct)
- }
- else
- Some(mkIntentId() → samples)
+ // Samples is list of list. Duplicates cannot be
inside one list,
+ // but possible between different lists.
+ Some(mkIntentId() →
samples.map(_.distinct).distinct)
}
- }
- else {
- logger.warn(s"@${CLS_SAMPLE.getSimpleName} annotation
is missing for: $mkMethodName")
-
- None
+ else
+ Some(mkIntentId() → samples)
}
}
- else
+ else {
+ logger.warn(s"@${CLS_SAMPLE.getSimpleName} annotation is
missing for: $mkMethodName")
+
None
- }).toMap
+ }
+ }
+ else
+ None
+ }).toMap
val parser = new NCMacroParser
@@ -1625,7 +1608,7 @@ object NCDeployManager extends NCService with
DecorateAsScala {
logger.warn(s"@IntentSample sample doesn't contain
any direct synonyms [" +
s"mdlId=$mdlId, " +
s"sample='$s'" +
- s"]")
+ s"]")
}
}
diff --git
a/nlpcraft/src/main/scala/org/apache/nlpcraft/probe/mgrs/model/NCModelManager.scala
b/nlpcraft/src/main/scala/org/apache/nlpcraft/probe/mgrs/model/NCModelManager.scala
index 1cc0fc9..6e5d23d 100644
---
a/nlpcraft/src/main/scala/org/apache/nlpcraft/probe/mgrs/model/NCModelManager.scala
+++
b/nlpcraft/src/main/scala/org/apache/nlpcraft/probe/mgrs/model/NCModelManager.scala
@@ -72,10 +72,11 @@ object NCModelManager extends NCService with
DecorateAsScala {
s"Intents: $intentCnt" + (if (intentCnt == 0) s"
${r("(!)")}" else "")
),
w.intents
- .map(_.toDslString)
+ .map(_.dsl)
.flatMap(s ⇒
s
.replaceAll("intent=", s"${g("intent")}=")
+ .replaceAll("fragment=", s"${b("fragment")}=")
.replaceAll(" term", s"\n
${c("term")}").split("\n")
)
)