-
Notifications
You must be signed in to change notification settings - Fork 15
[test_runner] Simplify use of channels in step interface #121
Conversation
The logic of the test runner is not modular enough to accomodate the need for implementing a cleanup pipeline. This revision refactors the test runner so that the concept of pipeline can be re-used. The eventual goal is to deploy two pipelines, one for testing and one for cleanup.
This revision further simplifies the routing logic and removes the dependency of the pipeline over the list of targets. The latter is important to implement pipelines that might have a variable number of targets coming in that cannot be predicted beforehand.
After extracting the pipeline logic, the routing logic was still part of the pipeline and very monolithic. This patch extracts the routing logic into a dedicated structure and splits it into routeIn logic and routeOut logic, which makes it unit-testable.
Pipeline and routing logic are now split into different files. Unit tests for the routing logic have been added.
This patch adds support for implementing a cleanup pipeline, which runs cleanup steps, after the main test pipeline. One of the requirements of ConTest has always been that it should support a "cleanup" phase, and this adds support for it. The cleanup pipeline is described in the same was test steps have been described so far: and additional "cleanup" section in the test descriptor is deserialized to implement a pipeline which runs the required cleanup steps.
Codecov Report
@@ Coverage Diff @@
## master #121 +/- ##
==========================================
+ Coverage 63.14% 64.58% +1.44%
==========================================
Files 51 58 +7
Lines 2846 3103 +257
==========================================
+ Hits 1797 2004 +207
- Misses 813 855 +42
- Partials 236 244 +8
Continue to review full report at Codecov.
|
The relevant change to understand this PR is to be looked into the
to
where
|
The interface of TestSteps so far has dictated that targets should be forwarded to two different channels for success and failure. This makes several parts of ConTest logic relatively complicated. In order to simplify the framework, this braking change reduces the number out output channels that a test step needs to handle to only one. The object returned by the step might include error information for targets which failed in the test step.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
47f9a1d -- LGTM
targetResultCh <- &target.Result{Target: t} | ||
} | ||
}() | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
just a thought:
It seems to me it is wrong when a pipeline instance knows it's position (mixed-up entities). Otherwise you require to understand more context while looking into this function. Though it does not worth time of inventing something else: never mind, anyway :)
log.Panicf("timeout while writing result for target %+v after %v", pendingTarget, r.timeouts.MessageTimeout) | ||
} | ||
}() | ||
|
||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It would be nice to cover this function with unit-tests. I would like to try to propose a much simpler implementation of this function :)
select { | ||
case <-terminate: | ||
err = fmt.Errorf("termination requested for routing into %s", r.bundle.StepLabel) | ||
case r.routingChannels.targetResult <- targetResult: | ||
case <-time.After(r.timeouts.MessageTimeout): | ||
log.Panicf("could not forward failed target (%+v) to the test runner: %v", t, targetResult.Err) | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
just a thought:
I see similar logic is duplicated a lot of times. And I see you tried to deduplicate it through writeTargets
. And if I understand correctly you haven't reused the same method, because it attached to *TestRunner
. However it consumes only timeouts
, so: may be you might just move the function from *TestRunner
to somewhere reachable from both entities?
stepInResult <- fmt.Errorf("not all targets received by teste step") | ||
} else { | ||
stepInResult <- nil | ||
err = fmt.Errorf("not all targets received by teste step") |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think it's not the first time I see this typo: teste
→ test
. Does "teste" mean something on Italian? :)
if err := ev.Emit(testevent.Data{EventName: FailedEvent, Target: target, Payload: nil}); err != nil { | ||
return fmt.Errorf("failed to emit failed event: %v", err) | ||
} else { | ||
log.Infof("target %v succeded", result.Target) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nitpicking:
A typo: succeded
→ succeeded
case ch.Out <- result: | ||
if result.Err != nil { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
just a thought:
Since result is transmitter as a pointer, there a potential race condition here. We create a constraint to guarantee we will not change the result in the core. It seems to be not the best example.
Why not to emit the event before sending the result?
} | ||
|
||
select { | ||
case <-cancel: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
warning:
Missing passthrough
or return nil
.
_ = ev.Emit(evData) | ||
log.Infof("Run: target %s succeeded: %s", target, params.GetOne("text")) | ||
ch.Out <- target | ||
eventName = event.Name("TargetSucceeded") |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nitpicking:
Extra event.Name(
.
Being superseded by #208 |
NOTE: this is an API breaking change.
The interface of TestSteps so far has dictated that targets should be
forwarded to two different channels for success and failure. This makes
several parts of ConTest logic relatively complicated. In order to
simplify the framework, this braking change reduces the number out
output channels that a test step needs to handle to only one. The object
returned by the step might include error information for targets which
failed in the test step.