Skip to content

Commit

Permalink
Preserve typing information during expression compilation
Browse files Browse the repository at this point in the history
  • Loading branch information
Elmacioro committed Sep 23, 2024
1 parent 627c288 commit 03d4a47
Show file tree
Hide file tree
Showing 4 changed files with 37 additions and 20 deletions.
1 change: 1 addition & 0 deletions docs/Changelog.md
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,7 @@
* Jackson 2.15.4 -> 2.17.2
* cats 2.10 -> 2.12
* [#6805](https://github.com/TouK/nussknacker/pull/6805) Support for Flink 1.19.1
* [#6925](https://github.com/TouK/nussknacker/pull/6925) Fix situation when preset labels were presented as `null` when node didn't pass the validation.

## 1.17

Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
package pl.touk.nussknacker.engine.compile

import cats.data.ValidatedNel
import cats.data.IorNel
import com.typesafe.scalalogging.LazyLogging
import pl.touk.nussknacker.engine.api.context.ProcessCompilationError
import pl.touk.nussknacker.engine.api.definition.Parameter
Expand All @@ -24,7 +24,7 @@ class ComponentExecutorFactory(parameterEvaluator: ParameterEvaluator) extends L
)(
implicit nodeId: NodeId,
metaData: MetaData
): ValidatedNel[ProcessCompilationError, ComponentExecutor] = {
): IorNel[ProcessCompilationError, ComponentExecutor] = {
NodeValidationExceptionHandler.handleExceptions {
doCreateComponentExecutor[ComponentExecutor](
component,
Expand All @@ -34,7 +34,7 @@ class ComponentExecutorFactory(parameterEvaluator: ParameterEvaluator) extends L
componentUseCase,
nonServicesLazyParamStrategy
)
}
}.toIor
}

private def doCreateComponentExecutor[ComponentExecutor](
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
package pl.touk.nussknacker.engine.compile

import cats.data.Validated.{Valid, invalid, invalidNel, valid}
import cats.data.{NonEmptyList, Validated, ValidatedNel}
import cats.data.Validated.{Invalid, Valid, invalid, invalidNel, valid}
import cats.data.{Ior, IorNel, NonEmptyList, Validated, ValidatedNel}
import cats.instances.list._
import pl.touk.nussknacker.engine.ModelData
import pl.touk.nussknacker.engine.api.{MetaData, NodeId}
Expand Down Expand Up @@ -125,7 +125,7 @@ class ExpressionCompiler(
)(
implicit nodeId: NodeId,
metaData: MetaData
): ValidatedNel[PartSubGraphCompilationError, List[CompiledParameter]] = {
): IorNel[PartSubGraphCompilationError, List[CompiledParameter]] = {
compileNodeParameters(
parameterDefinitions,
nodeParameters,
Expand All @@ -152,7 +152,7 @@ class ExpressionCompiler(
)(
implicit nodeId: NodeId,
metaData: MetaData
): ValidatedNel[PartSubGraphCompilationError, List[(TypedParameter, Parameter)]] = {
): IorNel[PartSubGraphCompilationError, List[(TypedParameter, Parameter)]] = {

val redundantMissingValidation = Validations.validateRedundantAndMissingParameters(
parameterDefinitions,
Expand All @@ -178,9 +178,15 @@ class ExpressionCompiler(
}
val allCompiledParams = (compiledParams ++ compiledBranchParams).sequence

allCompiledParams
.andThen(allParams => Validations.validateWithCustomValidators(allParams, paramValidatorsMap))
.combine(redundantMissingValidation.map(_ => List()))
for {
compiledParams <- allCompiledParams.toIor
paramsAfterValidation = Validations.validateWithCustomValidators(compiledParams, paramValidatorsMap) match {
case Valid(a) => Ior.right(a)
// We want to preserve typing information from allCompiledParams even if custom validators give us some errors
case Invalid(e) => Ior.both(e, compiledParams)
}
combinedParams <- redundantMissingValidation.map(_ => List()).toIor.combine(paramsAfterValidation)
} yield combinedParams
}

private def parameterValidatorsMap(parameterDefinitions: List[Parameter], globalVariables: Map[String, TypingResult])(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -281,16 +281,18 @@ class NodeCompiler(
}
val validParams =
expressionCompiler.compileExecutorComponentNodeParameters(validParamDefs.value, ref.parameters, ctx)
val validParamsCombinedErrors = validParams.combine(
NonEmptyList
.fromList(validParamDefs.written)
.map(invalid)
.getOrElse(valid(List.empty[CompiledParameter]))
)
val validParamsCombinedErrors = validParams
.fold(Invalid(_), Valid(_), (a, _) => Invalid(a))
.combine(
NonEmptyList
.fromList(validParamDefs.written)
.map(invalid)
.getOrElse(valid(List.empty[CompiledParameter]))
)
val expressionTypingInfo =
validParams
.map(_.map(p => p.name.value -> p.typingInfo).toMap)
.valueOr(_ => Map.empty[String, ExpressionTypingInfo])
.getOrElse(Map.empty[String, ExpressionTypingInfo])
NodeCompilationResult(expressionTypingInfo, None, newCtx, validParamsCombinedErrors)
}

Expand Down Expand Up @@ -558,7 +560,7 @@ class NodeCompiler(
ctx,
branchContexts
)
.andThen { compiledParameters =>
.flatMap { compiledParameters =>
factory
.createComponentExecutor[ComponentExecutor](
componentDefinition,
Expand All @@ -581,7 +583,10 @@ class NodeCompiler(
(typingInfo, componentExecutor)
}
}
(compiledObjectWithTypingInfo.map(_._1).valueOr(_ => Map.empty), compiledObjectWithTypingInfo.map(_._2))
(
compiledObjectWithTypingInfo.map(_._1).getOrElse(Map.empty),
compiledObjectWithTypingInfo.map(_._2).fold(Invalid(_), Valid(_), (a, _) => Invalid(a))
)
}

private def contextAfterMethodBasedCreatedComponentExecutor[ComponentExecutor](
Expand Down Expand Up @@ -683,7 +688,12 @@ class NodeCompiler(
)
}
val nodeTypingInfo = computedParameters.map(_.map(p => p.name.value -> p.typingInfo).toMap).getOrElse(Map.empty)
NodeCompilationResult(nodeTypingInfo, None, outputCtx, serviceRef)
NodeCompilationResult(
nodeTypingInfo,
None,
outputCtx,
serviceRef.fold(Invalid(_), Valid(_), (a, _) => Invalid(a))
)
}

}
Expand Down

0 comments on commit 03d4a47

Please sign in to comment.