add cuts to avoid multiple action paths
[scpubgit/DKit.git] / lib / DX / ResultStream.pm
CommitLineData
94565614 1package DX::ResultStream;
2
deec7cc4 3use DX::Result;
94565614 4use Moo;
5
6has for_state => (is => 'ro', required => 1);
7
8has _current_state => (is => 'rw');
9
10has is_exhausted => (is => 'rwp');
11
5ef4d923 12has observation_policy => (is => 'ro', default => sub { sub { 0 } });
13
94565614 14sub next {
15 my ($self) = @_;
16 return if $self->is_exhausted;
5ef4d923 17 my $state = do {
94565614 18 if (my $cur = $self->_current_state) {
5622b4df 19 $cur->push_backtrack;
94565614 20 } else {
21 $self->for_state
22 }
23 };
5ef4d923 24 STATE: while ($state = $self->_current_state($state->run)) {
25 last if $state->isa('DX::State');
26 if ($state->isa('DX::ObservationRequired')) {
27 if ($self->observation_policy->($state->observer)) {
28 my ($type, $value) = $state->observer->run;
29 $state = $state->resume;
30 $state->facts->{$type}->set_value($value);
31 } else {
32 die "Observation refused";
33 }
34 } else {
35 die "WTF: ".$state;
36 }
37 }
5622b4df 38 unless ($state) {
39 $self->_set_is_exhausted(1);
40 return;
41 }
deec7cc4 42 return DX::Result->new(state => $state->copy_vars);
94565614 43}
44
26300a7d 45sub results {
46 my ($self) = @_;
47 my @all;
48 while (my $next = $self->next) {
49 push @all, $next;
50 }
51 return @all;
52}
53
94565614 541;