Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions workflow-runtime/api/workflow-runtime.api
Original file line number Diff line number Diff line change
Expand Up @@ -101,6 +101,7 @@ public abstract interface class com/squareup/workflow1/WorkflowInterceptor$Workf
public abstract fun getIdentifier ()Lcom/squareup/workflow1/WorkflowIdentifier;
public abstract fun getParent ()Lcom/squareup/workflow1/WorkflowInterceptor$WorkflowSession;
public abstract fun getRenderKey ()Ljava/lang/String;
public abstract fun getRuntimeConfig ()Ljava/util/Set;
public abstract fun getSessionId ()J
}

Original file line number Diff line number Diff line change
Expand Up @@ -150,6 +150,9 @@ public interface WorkflowInterceptor {

/** The parent [WorkflowSession] of this workflow, or null if this is the root workflow. */
public val parent: WorkflowSession?

/** The [RuntimeConfig] of the runtime this session is executing in. */
public val runtimeConfig: RuntimeConfig
}

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ package com.squareup.workflow1.internal
import com.squareup.workflow1.ActionApplied
import com.squareup.workflow1.ActionProcessingResult
import com.squareup.workflow1.NoopWorkflowInterceptor
import com.squareup.workflow1.RuntimeConfig
import com.squareup.workflow1.TreeSnapshot
import com.squareup.workflow1.Workflow
import com.squareup.workflow1.WorkflowAction
Expand Down Expand Up @@ -89,6 +90,7 @@ internal class SubtreeManager<PropsT, StateT, OutputT>(
action: WorkflowAction<PropsT, StateT, OutputT>,
childResult: ActionApplied<*>
) -> ActionProcessingResult,
private val runtimeConfig: RuntimeConfig,
private val workflowSession: WorkflowSession? = null,
private val interceptor: WorkflowInterceptor = NoopWorkflowInterceptor,
private val idCounter: IdCounter? = null
Expand Down Expand Up @@ -180,14 +182,15 @@ internal class SubtreeManager<PropsT, StateT, OutputT>(
val childTreeSnapshots = snapshotCache?.get(id)

val workflowNode = WorkflowNode(
id,
child.asStatefulWorkflow(),
initialProps,
childTreeSnapshots,
contextForChildren,
::acceptChildActionResult,
workflowSession,
interceptor,
id = id,
workflow = child.asStatefulWorkflow(),
initialProps = initialProps,
snapshot = childTreeSnapshots,
baseContext = contextForChildren,
runtimeConfig = runtimeConfig,
emitAppliedActionToParent = ::acceptChildActionResult,
parent = workflowSession,
interceptor = interceptor,
idCounter = idCounter
)
return WorkflowChildNode(child, handler, workflowNode)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@ import com.squareup.workflow1.ActionApplied
import com.squareup.workflow1.ActionProcessingResult
import com.squareup.workflow1.NoopWorkflowInterceptor
import com.squareup.workflow1.RenderContext
import com.squareup.workflow1.RuntimeConfig
import com.squareup.workflow1.RuntimeConfigOptions
import com.squareup.workflow1.StatefulWorkflow
import com.squareup.workflow1.TreeSnapshot
import com.squareup.workflow1.Workflow
Expand Down Expand Up @@ -44,6 +46,8 @@ internal class WorkflowNode<PropsT, StateT, OutputT, RenderingT>(
initialProps: PropsT,
snapshot: TreeSnapshot?,
baseContext: CoroutineContext,
// Providing default value so we don't need to specify in test.
override val runtimeConfig: RuntimeConfig = RuntimeConfigOptions.DEFAULT_CONFIG,
private val emitAppliedActionToParent: (ActionApplied<OutputT>) -> ActionProcessingResult =
{ it },
override val parent: WorkflowSession? = null,
Expand All @@ -66,6 +70,7 @@ internal class WorkflowNode<PropsT, StateT, OutputT, RenderingT>(
snapshotCache = snapshot?.childTreeSnapshots,
contextForChildren = coroutineContext,
emitActionToParent = ::applyAction,
runtimeConfig = runtimeConfig,
workflowSession = this,
interceptor = interceptor,
idCounter = idCounter
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,7 @@ internal class WorkflowRunner<PropsT, OutputT, RenderingT>(
initialProps = currentProps,
snapshot = snapshot,
baseContext = scope.coroutineContext,
runtimeConfig = runtimeConfig,
interceptor = interceptor,
idCounter = idCounter
)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -82,6 +82,7 @@ internal class SimpleLoggingWorkflowInterceptorTest {
override val renderKey: String get() = "key"
override val sessionId: Long get() = 42
override val parent: WorkflowSession? get() = null
override val runtimeConfig: RuntimeConfig = RuntimeConfigOptions.DEFAULT_CONFIG
}

private object FakeRenderContext : BaseRenderContext<Unit, Unit, Unit> {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -216,6 +216,7 @@ internal class WorkflowInterceptorTest {
override val renderKey: String = ""
override val sessionId: Long = 0
override val parent: WorkflowSession? = null
override val runtimeConfig: RuntimeConfig = RuntimeConfigOptions.DEFAULT_CONFIG
}

private object TestWorkflow : StatefulWorkflow<String, String, String, String>() {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@ package com.squareup.workflow1.internal

import com.squareup.workflow1.BaseRenderContext
import com.squareup.workflow1.NoopWorkflowInterceptor
import com.squareup.workflow1.RuntimeConfig
import com.squareup.workflow1.RuntimeConfigOptions
import com.squareup.workflow1.Sink
import com.squareup.workflow1.Snapshot
import com.squareup.workflow1.Workflow
Expand Down Expand Up @@ -331,5 +333,6 @@ internal class ChainedWorkflowInterceptorTest {
override val renderKey: String = ""
override val sessionId: Long = 0
override val parent: WorkflowSession? = null
override val runtimeConfig: RuntimeConfig = RuntimeConfigOptions.DEFAULT_CONFIG
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ package com.squareup.workflow1.internal

import com.squareup.workflow1.ActionApplied
import com.squareup.workflow1.ActionProcessingResult
import com.squareup.workflow1.RuntimeConfigOptions
import com.squareup.workflow1.Snapshot
import com.squareup.workflow1.StatefulWorkflow
import com.squareup.workflow1.TreeSnapshot
Expand Down Expand Up @@ -307,7 +308,12 @@ internal class SubtreeManagerTest {

private fun <P, S, O : Any> subtreeManagerForTest(
snapshotCache: Map<WorkflowNodeId, TreeSnapshot>? = null
) = SubtreeManager<P, S, O>(snapshotCache, context, emitActionToParent = { action, childResult ->
ActionApplied(WorkflowOutput(action), childResult.stateChanged)
})
) = SubtreeManager<P, S, O>(
snapshotCache = snapshotCache,
contextForChildren = context,
runtimeConfig = RuntimeConfigOptions.DEFAULT_CONFIG,
emitActionToParent = { action, childResult ->
ActionApplied(WorkflowOutput(action), childResult.stateChanged)
}
)
}
Original file line number Diff line number Diff line change
Expand Up @@ -5,12 +5,16 @@ package com.squareup.workflow1.internal

import com.squareup.workflow1.ActionApplied
import com.squareup.workflow1.BaseRenderContext
import com.squareup.workflow1.RuntimeConfig
import com.squareup.workflow1.RuntimeConfigOptions
import com.squareup.workflow1.RuntimeConfigOptions.RENDER_ONLY_WHEN_STATE_CHANGES
import com.squareup.workflow1.Sink
import com.squareup.workflow1.Snapshot
import com.squareup.workflow1.StatefulWorkflow
import com.squareup.workflow1.TreeSnapshot
import com.squareup.workflow1.Workflow
import com.squareup.workflow1.WorkflowAction
import com.squareup.workflow1.WorkflowExperimentalRuntime
import com.squareup.workflow1.WorkflowIdentifier
import com.squareup.workflow1.WorkflowInterceptor
import com.squareup.workflow1.WorkflowInterceptor.RenderContextInterceptor
Expand Down Expand Up @@ -818,6 +822,49 @@ internal class WorkflowNodeTest {
assertEquals(0, interceptedSession.sessionId)
assertEquals("foo", interceptedSession.renderKey)
assertEquals(42, interceptedSession.parent!!.sessionId)
assertEquals(RuntimeConfigOptions.DEFAULT_CONFIG, interceptedSession.runtimeConfig)

val cause = CancellationException("stop")
node.cancel(cause)
assertSame(cause, cancellationException)
}

@OptIn(WorkflowExperimentalRuntime::class)
@Test
fun interceptor_handles_scope_start_and_cancellation_with_config() {
lateinit var interceptedScope: CoroutineScope
lateinit var interceptedSession: WorkflowSession
lateinit var cancellationException: Throwable
val interceptor = object : WorkflowInterceptor {
override fun onSessionStarted(
workflowScope: CoroutineScope,
session: WorkflowSession
) {
interceptedScope = workflowScope
interceptedSession = session
workflowScope.coroutineContext[Job]!!.invokeOnCompletion {
cancellationException = it!!
}
}
}
val workflow = Workflow.rendering(Unit)
val node = WorkflowNode(
id = workflow.id(key = "foo"),
workflow = workflow.asStatefulWorkflow(),
initialProps = Unit,
snapshot = null,
interceptor = interceptor,
baseContext = Unconfined,
runtimeConfig = setOf(RENDER_ONLY_WHEN_STATE_CHANGES),
parent = TestSession(42)
)

assertSame(node.coroutineContext, interceptedScope.coroutineContext)
assertEquals(workflow.identifier, interceptedSession.identifier)
assertEquals(0, interceptedSession.sessionId)
assertEquals("foo", interceptedSession.renderKey)
assertEquals(42, interceptedSession.parent!!.sessionId)
assertEquals(setOf(RENDER_ONLY_WHEN_STATE_CHANGES), interceptedSession.runtimeConfig)

val cause = CancellationException("stop")
node.cancel(cause)
Expand Down Expand Up @@ -1292,5 +1339,6 @@ internal class WorkflowNodeTest {
override val identifier: WorkflowIdentifier = Workflow.rendering(Unit).identifier
override val renderKey: String = ""
override val parent: WorkflowSession? = null
override val runtimeConfig: RuntimeConfig = RuntimeConfigOptions.DEFAULT_CONFIG
}
}