Completed
Push — master ( a29d2d...4681dd )
by Hannes
10:53 queued 08:08
created

Grammar::parseR_REQ_CREATE_MANDATE()   F

Complexity

Conditions 21
Paths > 20000

Size

Total Lines 132
Code Lines 72

Duplication

Lines 23
Ratio 17.42 %

Importance

Changes 0
Metric Value
dl 23
loc 132
rs 2
c 0
b 0
f 0
cc 21
eloc 72
nc 44065
nop 0

How to fix   Long Method    Complexity   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
3
namespace byrokrat\autogiro;
4
5
use byrokrat\autogiro\Tree\FileNode;
6
use byrokrat\autogiro\Tree\LayoutNode;
7
use byrokrat\autogiro\Tree\OpeningNode;
8
use byrokrat\autogiro\Tree\ClosingNode;
9
use byrokrat\autogiro\Tree\RequestMandateCreationNode;
10
use byrokrat\autogiro\Tree\RequestMandateAcceptanceNode;
11
use byrokrat\autogiro\Tree\RequestMandateRejectionNode;
12
use byrokrat\autogiro\Tree\RequestMandateUpdateNode;
13
use byrokrat\autogiro\Tree\RequestMandateDeletionNode;
14
use byrokrat\autogiro\Tree\RequestIncomingTransactionNode;
15
use byrokrat\autogiro\Tree\RequestOutgoingTransactionNode;
16
use byrokrat\autogiro\Tree\RequestTransactionDeletionNode;
17
use byrokrat\autogiro\Tree\RequestTransactionUpdateNode;
18
use byrokrat\autogiro\Tree\MandateResponseNode;
19
use byrokrat\autogiro\Tree\PersonalIdNode;
20
use byrokrat\autogiro\Tree\OrganizationIdNode;
21
use byrokrat\autogiro\Tree\AmountNode;
22
use byrokrat\autogiro\Tree\AccountNode;
23
use byrokrat\autogiro\Tree\BankgiroNode;
24
use byrokrat\autogiro\Tree\BgcCustomerNumberNode;
25
use byrokrat\autogiro\Tree\MessageNode;
26
use byrokrat\autogiro\Tree\PayerNumberNode;
27
28
class Grammar
29
{
30
    protected $string;
31
    protected $position;
32
    protected $value;
33
    protected $cache;
34
    protected $cut;
35
    protected $errors;
36
    protected $warnings;
37
38
    protected function parseFILE()
39
    {
40
        $_position = $this->position;
41
42
        if (isset($this->cache['FILE'][$_position])) {
43
            $_success = $this->cache['FILE'][$_position]['success'];
44
            $this->position = $this->cache['FILE'][$_position]['position'];
45
            $this->value = $this->cache['FILE'][$_position]['value'];
46
47
            return $_success;
48
        }
49
50
        $_value3 = array();
51
52
        $_success = $this->parseRESET_LINE_COUNT();
53
54
        if ($_success) {
55
            $_value3[] = $this->value;
56
57
            $_position1 = $this->position;
58
            $_cut2 = $this->cut;
59
60
            $this->cut = false;
61
            $_success = $this->parseL_REQ_CONTAINER();
62
63
            if (!$_success && !$this->cut) {
64
                $this->position = $_position1;
65
66
                $_success = $this->parseL_RESP_MANDATE();
67
            }
68
69
            $this->cut = $_cut2;
70
71
            if ($_success) {
72
                $layout = $this->value;
73
            }
74
        }
75
76
        if ($_success) {
77
            $_value3[] = $this->value;
78
79
            $this->value = $_value3;
80
        }
81
82
        if ($_success) {
83
            $this->value = call_user_func(function () use (&$layout) {
84
                return $layout;
85
            });
86
        }
87
88
        $this->cache['FILE'][$_position] = array(
89
            'success' => $_success,
90
            'position' => $this->position,
91
            'value' => $this->value
92
        );
93
94
        if (!$_success) {
95
            $this->report($_position, 'FILE');
96
        }
97
98
        return $_success;
99
    }
100
101
    protected function parseRESET_LINE_COUNT()
102
    {
103
        $_position = $this->position;
104
105
        if (isset($this->cache['RESET_LINE_COUNT'][$_position])) {
106
            $_success = $this->cache['RESET_LINE_COUNT'][$_position]['success'];
107
            $this->position = $this->cache['RESET_LINE_COUNT'][$_position]['position'];
108
            $this->value = $this->cache['RESET_LINE_COUNT'][$_position]['value'];
109
110
            return $_success;
111
        }
112
113
        if (substr($this->string, $this->position, strlen('')) === '') {
114
            $_success = true;
115
            $this->value = substr($this->string, $this->position, strlen(''));
116
            $this->position += strlen('');
117
        } else {
118
            $_success = false;
119
120
            $this->report($this->position, '\'\'');
121
        }
122
123
        if ($_success) {
124
            $this->value = call_user_func(function () {
125
                $this->currentLineNr = 0;
126
            });
127
        }
128
129
        $this->cache['RESET_LINE_COUNT'][$_position] = array(
130
            'success' => $_success,
131
            'position' => $this->position,
132
            'value' => $this->value
133
        );
134
135
        if (!$_success) {
136
            $this->report($_position, 'RESET_LINE_COUNT');
137
        }
138
139
        return $_success;
140
    }
141
142
    protected function parseR_GENERIC_OPENING()
143
    {
144
        $_position = $this->position;
145
146
        if (isset($this->cache['R_GENERIC_OPENING'][$_position])) {
147
            $_success = $this->cache['R_GENERIC_OPENING'][$_position]['success'];
148
            $this->position = $this->cache['R_GENERIC_OPENING'][$_position]['position'];
149
            $this->value = $this->cache['R_GENERIC_OPENING'][$_position]['value'];
150
151
            return $_success;
152
        }
153
154
        $_value4 = array();
155
156
        if (substr($this->string, $this->position, strlen('01')) === '01') {
157
            $_success = true;
158
            $this->value = substr($this->string, $this->position, strlen('01'));
159
            $this->position += strlen('01');
160
        } else {
161
            $_success = false;
162
163
            $this->report($this->position, '\'01\'');
164
        }
165
166
        if ($_success) {
167
            $_value4[] = $this->value;
168
169
            if (substr($this->string, $this->position, strlen('AUTOGIRO')) === 'AUTOGIRO') {
170
                $_success = true;
171
                $this->value = substr($this->string, $this->position, strlen('AUTOGIRO'));
172
                $this->position += strlen('AUTOGIRO');
173
            } else {
174
                $_success = false;
175
176
                $this->report($this->position, '\'AUTOGIRO\'');
177
            }
178
        }
179
180
        if ($_success) {
181
            $_value4[] = $this->value;
182
183
            $_success = $this->parseS10();
184
        }
185
186
        if ($_success) {
187
            $_value4[] = $this->value;
188
189
            $_success = $this->parseS();
190
        }
191
192
        if ($_success) {
193
            $_value4[] = $this->value;
194
195
            $_success = $this->parseS();
196
        }
197
198
        if ($_success) {
199
            $_value4[] = $this->value;
200
201
            $_success = $this->parseS();
202
        }
203
204
        if ($_success) {
205
            $_value4[] = $this->value;
206
207
            $_success = $this->parseS();
208
        }
209
210
        if ($_success) {
211
            $_value4[] = $this->value;
212
213
            $_success = $this->parseDATE();
214
215
            if ($_success) {
216
                $date = $this->value;
217
            }
218
        }
219
220
        if ($_success) {
221
            $_value4[] = $this->value;
222
223
            $_success = $this->parseS10();
224
        }
225
226
        if ($_success) {
227
            $_value4[] = $this->value;
228
229
            $_success = $this->parseS();
230
        }
231
232
        if ($_success) {
233
            $_value4[] = $this->value;
234
235
            $_success = $this->parseS();
236
        }
237
238
        if ($_success) {
239
            $_value4[] = $this->value;
240
241
            $_success = $this->parseA20();
242
243
            if ($_success) {
244
                $layout = $this->value;
245
            }
246
        }
247
248
        if ($_success) {
249
            $_value4[] = $this->value;
250
251
            $_success = $this->parseCUST_NR();
252
253
            if ($_success) {
254
                $custNr = $this->value;
255
            }
256
        }
257
258
        if ($_success) {
259
            $_value4[] = $this->value;
260
261
            $_success = $this->parseBANKGIRO();
262
263
            if ($_success) {
264
                $bg = $this->value;
265
            }
266
        }
267
268
        if ($_success) {
269
            $_value4[] = $this->value;
270
271
            $_success = $this->parseEOR();
272
        }
273
274
        if ($_success) {
275
            $_value4[] = $this->value;
276
277
            $this->value = $_value4;
278
        }
279
280
        if ($_success) {
281
            $this->value = call_user_func(function () use (&$date, &$layout, &$custNr, &$bg) {
282
                return new OpeningNode(rtrim($layout), $date, $custNr, $bg, $this->currentLineNr);
283
            });
284
        }
285
286
        $this->cache['R_GENERIC_OPENING'][$_position] = array(
287
            'success' => $_success,
288
            'position' => $this->position,
289
            'value' => $this->value
290
        );
291
292
        if (!$_success) {
293
            $this->report($_position, 'R_GENERIC_OPENING');
294
        }
295
296
        return $_success;
297
    }
298
299
    protected function parseL_REQ_CONTAINER()
300
    {
301
        $_position = $this->position;
302
303
        if (isset($this->cache['L_REQ_CONTAINER'][$_position])) {
304
            $_success = $this->cache['L_REQ_CONTAINER'][$_position]['success'];
305
            $this->position = $this->cache['L_REQ_CONTAINER'][$_position]['position'];
306
            $this->value = $this->cache['L_REQ_CONTAINER'][$_position]['value'];
307
308
            return $_success;
309
        }
310
311
        $_position5 = $this->position;
312
        $_cut6 = $this->cut;
313
314
        $this->cut = false;
315
        $_success = $this->parseL_REQ_MANDATE();
316
317
        if (!$_success && !$this->cut) {
318
            $this->position = $_position5;
319
320
            $_success = $this->parseL_REQ_PAYMENT();
321
        }
322
323
        if (!$_success && !$this->cut) {
324
            $this->position = $_position5;
325
326
            $_success = $this->parseL_REQ_AMENDMENT();
327
        }
328
329
        $this->cut = $_cut6;
330
331
        if ($_success) {
332
            $_value8 = array($this->value);
333
            $_cut9 = $this->cut;
334
335
            while (true) {
336
                $_position7 = $this->position;
337
338
                $this->cut = false;
339
                $_position5 = $this->position;
340
                $_cut6 = $this->cut;
341
342
                $this->cut = false;
343
                $_success = $this->parseL_REQ_MANDATE();
344
345
                if (!$_success && !$this->cut) {
346
                    $this->position = $_position5;
347
348
                    $_success = $this->parseL_REQ_PAYMENT();
349
                }
350
351
                if (!$_success && !$this->cut) {
352
                    $this->position = $_position5;
353
354
                    $_success = $this->parseL_REQ_AMENDMENT();
355
                }
356
357
                $this->cut = $_cut6;
358
359
                if (!$_success) {
360
                    break;
361
                }
362
363
                $_value8[] = $this->value;
364
            }
365
366
            if (!$this->cut) {
367
                $_success = true;
368
                $this->position = $_position7;
369
                $this->value = $_value8;
370
            }
371
372
            $this->cut = $_cut9;
373
        }
374
375
        if ($_success) {
376
            $layouts = $this->value;
377
        }
378
379
        if ($_success) {
380
            $this->value = call_user_func(function () use (&$layouts) {
381
                return new FileNode(...$layouts);
382
            });
383
        }
384
385
        $this->cache['L_REQ_CONTAINER'][$_position] = array(
386
            'success' => $_success,
387
            'position' => $this->position,
388
            'value' => $this->value
389
        );
390
391
        if (!$_success) {
392
            $this->report($_position, 'L_REQ_CONTAINER');
393
        }
394
395
        return $_success;
396
    }
397
398
    protected function parseR_REQ_OPENING()
399
    {
400
        $_position = $this->position;
401
402
        if (isset($this->cache['R_REQ_OPENING'][$_position])) {
403
            $_success = $this->cache['R_REQ_OPENING'][$_position]['success'];
404
            $this->position = $this->cache['R_REQ_OPENING'][$_position]['position'];
405
            $this->value = $this->cache['R_REQ_OPENING'][$_position]['value'];
406
407
            return $_success;
408
        }
409
410
        $_value10 = array();
411
412
        if (substr($this->string, $this->position, strlen('01')) === '01') {
413
            $_success = true;
414
            $this->value = substr($this->string, $this->position, strlen('01'));
415
            $this->position += strlen('01');
416
        } else {
417
            $_success = false;
418
419
            $this->report($this->position, '\'01\'');
420
        }
421
422
        if ($_success) {
423
            $_value10[] = $this->value;
424
425
            $_success = $this->parseDATE();
426
427
            if ($_success) {
428
                $date = $this->value;
429
            }
430
        }
431
432
        if ($_success) {
433
            $_value10[] = $this->value;
434
435
            if (substr($this->string, $this->position, strlen('AUTOGIRO')) === 'AUTOGIRO') {
436
                $_success = true;
437
                $this->value = substr($this->string, $this->position, strlen('AUTOGIRO'));
438
                $this->position += strlen('AUTOGIRO');
439
            } else {
440
                $_success = false;
441
442
                $this->report($this->position, '\'AUTOGIRO\'');
443
            }
444
        }
445
446
        if ($_success) {
447
            $_value10[] = $this->value;
448
449
            $_success = $this->parseS20();
450
        }
451
452
        if ($_success) {
453
            $_value10[] = $this->value;
454
455
            $_success = $this->parseS20();
456
        }
457
458
        if ($_success) {
459
            $_value10[] = $this->value;
460
461
            $_success = $this->parseS();
462
        }
463
464
        if ($_success) {
465
            $_value10[] = $this->value;
466
467
            $_success = $this->parseS();
468
        }
469
470
        if ($_success) {
471
            $_value10[] = $this->value;
472
473
            $_success = $this->parseS();
474
        }
475
476
        if ($_success) {
477
            $_value10[] = $this->value;
478
479
            $_success = $this->parseS();
480
        }
481
482
        if ($_success) {
483
            $_value10[] = $this->value;
484
485
            $_success = $this->parseCUST_NR();
486
487
            if ($_success) {
488
                $custNr = $this->value;
489
            }
490
        }
491
492
        if ($_success) {
493
            $_value10[] = $this->value;
494
495
            $_success = $this->parseBANKGIRO();
496
497
            if ($_success) {
498
                $bg = $this->value;
499
            }
500
        }
501
502
        if ($_success) {
503
            $_value10[] = $this->value;
504
505
            $_success = $this->parseEOR();
506
        }
507
508
        if ($_success) {
509
            $_value10[] = $this->value;
510
511
            $this->value = $_value10;
512
        }
513
514
        if ($_success) {
515
            $this->value = call_user_func(function () use (&$date, &$custNr, &$bg) {
516
                // TODO layout_request kan vara ''
517
                    // kanske lägga in ett test i visitor som kontrollerar att layoutId är ett känt värde... ??
518
                return new OpeningNode('', $date, $custNr, $bg, $this->currentLineNr);
519
            });
520
        }
521
522
        $this->cache['R_REQ_OPENING'][$_position] = array(
523
            'success' => $_success,
524
            'position' => $this->position,
525
            'value' => $this->value
526
        );
527
528
        if (!$_success) {
529
            $this->report($_position, 'R_REQ_OPENING');
530
        }
531
532
        return $_success;
533
    }
534
535
    protected function parseL_REQ_MANDATE()
536
    {
537
        $_position = $this->position;
538
539
        if (isset($this->cache['L_REQ_MANDATE'][$_position])) {
540
            $_success = $this->cache['L_REQ_MANDATE'][$_position]['success'];
541
            $this->position = $this->cache['L_REQ_MANDATE'][$_position]['position'];
542
            $this->value = $this->cache['L_REQ_MANDATE'][$_position]['value'];
543
544
            return $_success;
545
        }
546
547
        $_value16 = array();
548
549
        $_success = $this->parseR_REQ_OPENING();
550
551
        if ($_success) {
552
            $opening = $this->value;
553
        }
554
555
        if ($_success) {
556
            $_value16[] = $this->value;
557
558
            $_position11 = $this->position;
559
            $_cut12 = $this->cut;
560
561
            $this->cut = false;
562
            $_success = $this->parseR_REQ_CREATE_MANDATE();
563
564
            if (!$_success && !$this->cut) {
565
                $this->position = $_position11;
566
567
                $_success = $this->parseR_REQ_CONFIRM_MANDATE();
568
            }
569
570
            if (!$_success && !$this->cut) {
571
                $this->position = $_position11;
572
573
                $_success = $this->parseR_REQ_UPDATE_MANDATE();
574
            }
575
576
            if (!$_success && !$this->cut) {
577
                $this->position = $_position11;
578
579
                $_success = $this->parseR_REQ_DEL_MANDATE();
580
            }
581
582
            $this->cut = $_cut12;
583
584
            if ($_success) {
585
                $_value14 = array($this->value);
586
                $_cut15 = $this->cut;
587
588
                while (true) {
589
                    $_position13 = $this->position;
590
591
                    $this->cut = false;
592
                    $_position11 = $this->position;
593
                    $_cut12 = $this->cut;
594
595
                    $this->cut = false;
596
                    $_success = $this->parseR_REQ_CREATE_MANDATE();
597
598
                    if (!$_success && !$this->cut) {
599
                        $this->position = $_position11;
600
601
                        $_success = $this->parseR_REQ_CONFIRM_MANDATE();
602
                    }
603
604
                    if (!$_success && !$this->cut) {
605
                        $this->position = $_position11;
606
607
                        $_success = $this->parseR_REQ_UPDATE_MANDATE();
608
                    }
609
610
                    if (!$_success && !$this->cut) {
611
                        $this->position = $_position11;
612
613
                        $_success = $this->parseR_REQ_DEL_MANDATE();
614
                    }
615
616
                    $this->cut = $_cut12;
617
618
                    if (!$_success) {
619
                        break;
620
                    }
621
622
                    $_value14[] = $this->value;
623
                }
624
625
                if (!$this->cut) {
626
                    $_success = true;
627
                    $this->position = $_position13;
628
                    $this->value = $_value14;
629
                }
630
631
                $this->cut = $_cut15;
632
            }
633
634
            if ($_success) {
635
                $records = $this->value;
636
            }
637
        }
638
639
        if ($_success) {
640
            $_value16[] = $this->value;
641
642
            $this->value = $_value16;
643
        }
644
645
        if ($_success) {
646
            $this->value = call_user_func(function () use (&$opening, &$records) {
647
                $opening->setAttribute('layout_name', Layouts::LAYOUT_MANDATE_REQUEST);
648
649
                return new LayoutNode(
650
                    $opening,
651
                    new ClosingNode($opening->getAttribute('date'), count($records), $this->currentLineNr),
652
                    ...$records
653
                );
654
            });
655
        }
656
657
        $this->cache['L_REQ_MANDATE'][$_position] = array(
658
            'success' => $_success,
659
            'position' => $this->position,
660
            'value' => $this->value
661
        );
662
663
        if (!$_success) {
664
            $this->report($_position, 'L_REQ_MANDATE');
665
        }
666
667
        return $_success;
668
    }
669
670
    protected function parseR_REQ_CREATE_MANDATE()
671
    {
672
        $_position = $this->position;
673
674
        if (isset($this->cache['R_REQ_CREATE_MANDATE'][$_position])) {
675
            $_success = $this->cache['R_REQ_CREATE_MANDATE'][$_position]['success'];
676
            $this->position = $this->cache['R_REQ_CREATE_MANDATE'][$_position]['position'];
677
            $this->value = $this->cache['R_REQ_CREATE_MANDATE'][$_position]['value'];
678
679
            return $_success;
680
        }
681
682
        $_value20 = array();
683
684
        if (substr($this->string, $this->position, strlen('04')) === '04') {
685
            $_success = true;
686
            $this->value = substr($this->string, $this->position, strlen('04'));
687
            $this->position += strlen('04');
688
        } else {
689
            $_success = false;
690
691
            $this->report($this->position, '\'04\'');
692
        }
693
694
        if ($_success) {
695
            $_value20[] = $this->value;
696
697
            $_success = $this->parseBANKGIRO();
698
699
            if ($_success) {
700
                $bg = $this->value;
701
            }
702
        }
703
704
        if ($_success) {
705
            $_value20[] = $this->value;
706
707
            $_success = $this->parsePAYER_NR();
708
709
            if ($_success) {
710
                $payerNr = $this->value;
711
            }
712
        }
713
714
        if ($_success) {
715
            $_value20[] = $this->value;
716
717
            $_success = $this->parseACCOUNT();
718
719
            if ($_success) {
720
                $account = $this->value;
721
            }
722
        }
723
724
        if ($_success) {
725
            $_value20[] = $this->value;
726
727
            $_success = $this->parseID();
728
729
            if ($_success) {
730
                $id = $this->value;
731
            }
732
        }
733
734
        if ($_success) {
735
            $_value20[] = $this->value;
736
737
            $_position18 = $this->position;
738
            $_cut19 = $this->cut;
739
740
            $this->cut = false;
741
            $_value17 = array();
742
743
            $_success = $this->parseS20();
744
745
            if ($_success) {
746
                $_value17[] = $this->value;
747
748
                $_success = $this->parseS();
749
            }
750
751
            if ($_success) {
752
                $_value17[] = $this->value;
753
754
                $_success = $this->parseS();
755
            }
756
757
            if ($_success) {
758
                $_value17[] = $this->value;
759
760
                $this->value = $_value17;
761
            }
762
763
            if (!$_success && !$this->cut) {
764
                $_success = true;
765
                $this->position = $_position18;
766
                $this->value = null;
767
            }
768
769
            $this->cut = $_cut19;
770
        }
771
772
        if ($_success) {
773
            $_value20[] = $this->value;
774
775
            $_success = $this->parseEOR();
776
        }
777
778
        if ($_success) {
779
            $_value20[] = $this->value;
780
781
            $this->value = $_value20;
782
        }
783
784
        if ($_success) {
785
            $this->value = call_user_func(function () use (&$bg, &$payerNr, &$account, &$id) {
786
                return new RequestMandateCreationNode($bg, $payerNr, $account, $id, $this->currentLineNr);
787
            });
788
        }
789
790
        $this->cache['R_REQ_CREATE_MANDATE'][$_position] = array(
791
            'success' => $_success,
792
            'position' => $this->position,
793
            'value' => $this->value
794
        );
795
796
        if (!$_success) {
797
            $this->report($_position, 'R_REQ_CREATE_MANDATE');
798
        }
799
800
        return $_success;
801
    }
802
803
    protected function parseR_REQ_CONFIRM_MANDATE()
804
    {
805
        $_position = $this->position;
806
807
        if (isset($this->cache['R_REQ_CONFIRM_MANDATE'][$_position])) {
808
            $_success = $this->cache['R_REQ_CONFIRM_MANDATE'][$_position]['success'];
809
            $this->position = $this->cache['R_REQ_CONFIRM_MANDATE'][$_position]['position'];
810
            $this->value = $this->cache['R_REQ_CONFIRM_MANDATE'][$_position]['value'];
811
812
            return $_success;
813
        }
814
815
        $_value24 = array();
816
817
        if (substr($this->string, $this->position, strlen('04')) === '04') {
818
            $_success = true;
819
            $this->value = substr($this->string, $this->position, strlen('04'));
820
            $this->position += strlen('04');
821
        } else {
822
            $_success = false;
823
824
            $this->report($this->position, '\'04\'');
825
        }
826
827
        if ($_success) {
828
            $_value24[] = $this->value;
829
830
            $_success = $this->parseBANKGIRO();
831
832
            if ($_success) {
833
                $bg = $this->value;
834
            }
835
        }
836
837
        if ($_success) {
838
            $_value24[] = $this->value;
839
840
            $_success = $this->parsePAYER_NR();
841
842
            if ($_success) {
843
                $payerNr = $this->value;
844
            }
845
        }
846
847
        if ($_success) {
848
            $_value24[] = $this->value;
849
850
            $_position22 = $this->position;
851
            $_cut23 = $this->cut;
852
853
            $this->cut = false;
854
            $_value21 = array();
855
856
            $_success = $this->parseA40();
857
858
            if ($_success) {
859
                $_value21[] = $this->value;
860
861
                $_success = $this->parseA5();
862
            }
863
864
            if ($_success) {
865
                $_value21[] = $this->value;
866
867
                $_success = $this->parseA();
868
            }
869
870
            if ($_success) {
871
                $_value21[] = $this->value;
872
873
                $_success = $this->parseA();
874
            }
875
876
            if ($_success) {
877
                $_value21[] = $this->value;
878
879
                $_success = $this->parseA();
880
            }
881
882
            if ($_success) {
883
                $_value21[] = $this->value;
884
885
                if (substr($this->string, $this->position, strlen('AV')) === 'AV') {
886
                    $_success = true;
887
                    $this->value = substr($this->string, $this->position, strlen('AV'));
888
                    $this->position += strlen('AV');
889
                } else {
890
                    $_success = false;
891
892
                    $this->report($this->position, '\'AV\'');
893
                }
894
895
                if ($_success) {
896
                    $reject = $this->value;
897
                }
898
            }
899
900
            if ($_success) {
901
                $_value21[] = $this->value;
902
903
                $this->value = $_value21;
904
            }
905
906
            if (!$_success && !$this->cut) {
907
                $_success = true;
908
                $this->position = $_position22;
909
                $this->value = null;
910
            }
911
912
            $this->cut = $_cut23;
913
        }
914
915
        if ($_success) {
916
            $_value24[] = $this->value;
917
918
            $_success = $this->parseEOR();
919
        }
920
921
        if ($_success) {
922
            $_value24[] = $this->value;
923
924
            $this->value = $_value24;
925
        }
926
927
        if ($_success) {
928
            $this->value = call_user_func(function () use (&$bg, &$payerNr, &$reject) {
929
                return $reject == 'AV'
930
                    ? new RequestMandateRejectionNode($bg, $payerNr, $this->currentLineNr)
931
                    : new RequestMandateAcceptanceNode($bg, $payerNr, $this->currentLineNr);
932
            });
933
        }
934
935
        $this->cache['R_REQ_CONFIRM_MANDATE'][$_position] = array(
936
            'success' => $_success,
937
            'position' => $this->position,
938
            'value' => $this->value
939
        );
940
941
        if (!$_success) {
942
            $this->report($_position, 'R_REQ_CONFIRM_MANDATE');
943
        }
944
945
        return $_success;
946
    }
947
948
    protected function parseR_REQ_UPDATE_MANDATE()
949
    {
950
        $_position = $this->position;
951
952
        if (isset($this->cache['R_REQ_UPDATE_MANDATE'][$_position])) {
953
            $_success = $this->cache['R_REQ_UPDATE_MANDATE'][$_position]['success'];
954
            $this->position = $this->cache['R_REQ_UPDATE_MANDATE'][$_position]['position'];
955
            $this->value = $this->cache['R_REQ_UPDATE_MANDATE'][$_position]['value'];
956
957
            return $_success;
958
        }
959
960
        $_value25 = array();
961
962
        if (substr($this->string, $this->position, strlen('05')) === '05') {
963
            $_success = true;
964
            $this->value = substr($this->string, $this->position, strlen('05'));
965
            $this->position += strlen('05');
966
        } else {
967
            $_success = false;
968
969
            $this->report($this->position, '\'05\'');
970
        }
971
972
        if ($_success) {
973
            $_value25[] = $this->value;
974
975
            $_success = $this->parseBANKGIRO();
976
977
            if ($_success) {
978
                $oldBg = $this->value;
979
            }
980
        }
981
982
        if ($_success) {
983
            $_value25[] = $this->value;
984
985
            $_success = $this->parsePAYER_NR();
986
987
            if ($_success) {
988
                $oldPayerNr = $this->value;
989
            }
990
        }
991
992
        if ($_success) {
993
            $_value25[] = $this->value;
994
995
            $_success = $this->parseBANKGIRO();
996
997
            if ($_success) {
998
                $newBg = $this->value;
999
            }
1000
        }
1001
1002
        if ($_success) {
1003
            $_value25[] = $this->value;
1004
1005
            $_success = $this->parsePAYER_NR();
1006
1007
            if ($_success) {
1008
                $newPayerNr = $this->value;
1009
            }
1010
        }
1011
1012
        if ($_success) {
1013
            $_value25[] = $this->value;
1014
1015
            $_success = $this->parseEOR();
1016
        }
1017
1018
        if ($_success) {
1019
            $_value25[] = $this->value;
1020
1021
            $this->value = $_value25;
1022
        }
1023
1024
        if ($_success) {
1025
            $this->value = call_user_func(function () use (&$oldBg, &$oldPayerNr, &$newBg, &$newPayerNr) {
1026
                return new RequestMandateUpdateNode($oldBg, $oldPayerNr, $newBg, $newPayerNr, $this->currentLineNr);
1027
            });
1028
        }
1029
1030
        $this->cache['R_REQ_UPDATE_MANDATE'][$_position] = array(
1031
            'success' => $_success,
1032
            'position' => $this->position,
1033
            'value' => $this->value
1034
        );
1035
1036
        if (!$_success) {
1037
            $this->report($_position, 'R_REQ_UPDATE_MANDATE');
1038
        }
1039
1040
        return $_success;
1041
    }
1042
1043
    protected function parseR_REQ_DEL_MANDATE()
1044
    {
1045
        $_position = $this->position;
1046
1047
        if (isset($this->cache['R_REQ_DEL_MANDATE'][$_position])) {
1048
            $_success = $this->cache['R_REQ_DEL_MANDATE'][$_position]['success'];
1049
            $this->position = $this->cache['R_REQ_DEL_MANDATE'][$_position]['position'];
1050
            $this->value = $this->cache['R_REQ_DEL_MANDATE'][$_position]['value'];
1051
1052
            return $_success;
1053
        }
1054
1055
        $_value26 = array();
1056
1057
        if (substr($this->string, $this->position, strlen('03')) === '03') {
1058
            $_success = true;
1059
            $this->value = substr($this->string, $this->position, strlen('03'));
1060
            $this->position += strlen('03');
1061
        } else {
1062
            $_success = false;
1063
1064
            $this->report($this->position, '\'03\'');
1065
        }
1066
1067
        if ($_success) {
1068
            $_value26[] = $this->value;
1069
1070
            $_success = $this->parseBANKGIRO();
1071
1072
            if ($_success) {
1073
                $bg = $this->value;
1074
            }
1075
        }
1076
1077
        if ($_success) {
1078
            $_value26[] = $this->value;
1079
1080
            $_success = $this->parsePAYER_NR();
1081
1082
            if ($_success) {
1083
                $payerNr = $this->value;
1084
            }
1085
        }
1086
1087
        if ($_success) {
1088
            $_value26[] = $this->value;
1089
1090
            $_success = $this->parseEOR();
1091
        }
1092
1093
        if ($_success) {
1094
            $_value26[] = $this->value;
1095
1096
            $this->value = $_value26;
1097
        }
1098
1099
        if ($_success) {
1100
            $this->value = call_user_func(function () use (&$bg, &$payerNr) {
1101
                return new RequestMandateDeletionNode($bg, $payerNr, $this->currentLineNr);
1102
            });
1103
        }
1104
1105
        $this->cache['R_REQ_DEL_MANDATE'][$_position] = array(
1106
            'success' => $_success,
1107
            'position' => $this->position,
1108
            'value' => $this->value
1109
        );
1110
1111
        if (!$_success) {
1112
            $this->report($_position, 'R_REQ_DEL_MANDATE');
1113
        }
1114
1115
        return $_success;
1116
    }
1117
1118
    protected function parseL_REQ_PAYMENT()
1119
    {
1120
        $_position = $this->position;
1121
1122
        if (isset($this->cache['L_REQ_PAYMENT'][$_position])) {
1123
            $_success = $this->cache['L_REQ_PAYMENT'][$_position]['success'];
1124
            $this->position = $this->cache['L_REQ_PAYMENT'][$_position]['position'];
1125
            $this->value = $this->cache['L_REQ_PAYMENT'][$_position]['value'];
1126
1127
            return $_success;
1128
        }
1129
1130
        $_value30 = array();
1131
1132
        $_success = $this->parseR_REQ_OPENING();
1133
1134
        if ($_success) {
1135
            $opening = $this->value;
1136
        }
1137
1138
        if ($_success) {
1139
            $_value30[] = $this->value;
1140
1141
            if (substr($this->string, $this->position, strlen('')) === '') {
1142
                $_success = true;
1143
                $this->value = substr($this->string, $this->position, strlen(''));
1144
                $this->position += strlen('');
1145
            } else {
1146
                $_success = false;
1147
1148
                $this->report($this->position, '\'\'');
1149
            }
1150
1151
            if ($_success) {
1152
                $_value28 = array($this->value);
1153
                $_cut29 = $this->cut;
1154
1155
                while (true) {
1156
                    $_position27 = $this->position;
1157
1158
                    $this->cut = false;
1159
                    if (substr($this->string, $this->position, strlen('')) === '') {
1160
                        $_success = true;
1161
                        $this->value = substr($this->string, $this->position, strlen(''));
1162
                        $this->position += strlen('');
1163
                    } else {
1164
                        $_success = false;
1165
1166
                        $this->report($this->position, '\'\'');
1167
                    }
1168
1169
                    if (!$_success) {
1170
                        break;
1171
                    }
1172
1173
                    $_value28[] = $this->value;
1174
                }
1175
1176
                if (!$this->cut) {
1177
                    $_success = true;
1178
                    $this->position = $_position27;
1179
                    $this->value = $_value28;
1180
                }
1181
1182
                $this->cut = $_cut29;
1183
            }
1184
1185
            if ($_success) {
1186
                $records = $this->value;
1187
            }
1188
        }
1189
1190
        if ($_success) {
1191
            $_value30[] = $this->value;
1192
1193
            $this->value = $_value30;
1194
        }
1195
1196
        if ($_success) {
1197
            $this->value = call_user_func(function () use (&$opening, &$records) {
1198
                $opening->setAttribute('layout_name', Layouts::LAYOUT_PAYMENT_REQUEST);
1199
1200
                return new LayoutNode(
1201
                    $opening,
1202
                    new ClosingNode($opening->getAttribute('date'), count($records), $this->currentLineNr),
1203
                    ...$records
1204
                );
1205
            });
1206
        }
1207
1208
        $this->cache['L_REQ_PAYMENT'][$_position] = array(
1209
            'success' => $_success,
1210
            'position' => $this->position,
1211
            'value' => $this->value
1212
        );
1213
1214
        if (!$_success) {
1215
            $this->report($_position, 'L_REQ_PAYMENT');
1216
        }
1217
1218
        return $_success;
1219
    }
1220
1221
    protected function parseL_REQ_AMENDMENT()
1222
    {
1223
        $_position = $this->position;
1224
1225
        if (isset($this->cache['L_REQ_AMENDMENT'][$_position])) {
1226
            $_success = $this->cache['L_REQ_AMENDMENT'][$_position]['success'];
1227
            $this->position = $this->cache['L_REQ_AMENDMENT'][$_position]['position'];
1228
            $this->value = $this->cache['L_REQ_AMENDMENT'][$_position]['value'];
1229
1230
            return $_success;
1231
        }
1232
1233
        $_value34 = array();
1234
1235
        $_success = $this->parseR_REQ_OPENING();
1236
1237
        if ($_success) {
1238
            $opening = $this->value;
1239
        }
1240
1241
        if ($_success) {
1242
            $_value34[] = $this->value;
1243
1244
            if (substr($this->string, $this->position, strlen('')) === '') {
1245
                $_success = true;
1246
                $this->value = substr($this->string, $this->position, strlen(''));
1247
                $this->position += strlen('');
1248
            } else {
1249
                $_success = false;
1250
1251
                $this->report($this->position, '\'\'');
1252
            }
1253
1254
            if ($_success) {
1255
                $_value32 = array($this->value);
1256
                $_cut33 = $this->cut;
1257
1258
                while (true) {
1259
                    $_position31 = $this->position;
1260
1261
                    $this->cut = false;
1262
                    if (substr($this->string, $this->position, strlen('')) === '') {
1263
                        $_success = true;
1264
                        $this->value = substr($this->string, $this->position, strlen(''));
1265
                        $this->position += strlen('');
1266
                    } else {
1267
                        $_success = false;
1268
1269
                        $this->report($this->position, '\'\'');
1270
                    }
1271
1272
                    if (!$_success) {
1273
                        break;
1274
                    }
1275
1276
                    $_value32[] = $this->value;
1277
                }
1278
1279
                if (!$this->cut) {
1280
                    $_success = true;
1281
                    $this->position = $_position31;
1282
                    $this->value = $_value32;
1283
                }
1284
1285
                $this->cut = $_cut33;
1286
            }
1287
1288
            if ($_success) {
1289
                $records = $this->value;
1290
            }
1291
        }
1292
1293
        if ($_success) {
1294
            $_value34[] = $this->value;
1295
1296
            $this->value = $_value34;
1297
        }
1298
1299
        if ($_success) {
1300
            $this->value = call_user_func(function () use (&$opening, &$records) {
1301
                $opening->setAttribute('layout_name', Layouts::LAYOUT_AMENDMENT_REQUEST);
1302
1303
                return new LayoutNode(
1304
                    $opening,
1305
                    new ClosingNode($opening->getAttribute('date'), count($records), $this->currentLineNr),
1306
                    ...$records
1307
                );
1308
            });
1309
        }
1310
1311
        $this->cache['L_REQ_AMENDMENT'][$_position] = array(
1312
            'success' => $_success,
1313
            'position' => $this->position,
1314
            'value' => $this->value
1315
        );
1316
1317
        if (!$_success) {
1318
            $this->report($_position, 'L_REQ_AMENDMENT');
1319
        }
1320
1321
        return $_success;
1322
    }
1323
1324
    protected function parseL_RESP_MANDATE()
1325
    {
1326
        $_position = $this->position;
1327
1328
        if (isset($this->cache['L_RESP_MANDATE'][$_position])) {
1329
            $_success = $this->cache['L_RESP_MANDATE'][$_position]['success'];
1330
            $this->position = $this->cache['L_RESP_MANDATE'][$_position]['position'];
1331
            $this->value = $this->cache['L_RESP_MANDATE'][$_position]['value'];
1332
1333
            return $_success;
1334
        }
1335
1336
        $_value40 = array();
1337
1338
        $_position35 = $this->position;
1339
        $_cut36 = $this->cut;
1340
1341
        $this->cut = false;
1342
        $_success = $this->parseR_GENERIC_OPENING();
1343
1344
        if (!$_success && !$this->cut) {
1345
            $this->position = $_position35;
1346
1347
            $_success = $this->parseR_RESP_MANDATE_OPENING_OLD();
1348
        }
1349
1350
        $this->cut = $_cut36;
1351
1352
        if ($_success) {
1353
            $opening = $this->value;
1354
        }
1355
1356
        if ($_success) {
1357
            $_value40[] = $this->value;
1358
1359
            $_value38 = array();
1360
            $_cut39 = $this->cut;
1361
1362
            while (true) {
1363
                $_position37 = $this->position;
1364
1365
                $this->cut = false;
1366
                $_success = $this->parseR_RESP_MANDATE();
1367
1368
                if (!$_success) {
1369
                    break;
1370
                }
1371
1372
                $_value38[] = $this->value;
1373
            }
1374
1375
            if (!$this->cut) {
1376
                $_success = true;
1377
                $this->position = $_position37;
1378
                $this->value = $_value38;
1379
            }
1380
1381
            $this->cut = $_cut39;
1382
1383
            if ($_success) {
1384
                $mandates = $this->value;
1385
            }
1386
        }
1387
1388
        if ($_success) {
1389
            $_value40[] = $this->value;
1390
1391
            $_success = $this->parseR_RESP_MANDATE_CLOSING();
1392
1393
            if ($_success) {
1394
                $closing = $this->value;
1395
            }
1396
        }
1397
1398
        if ($_success) {
1399
            $_value40[] = $this->value;
1400
1401
            $this->value = $_value40;
1402
        }
1403
1404
        if ($_success) {
1405
            $this->value = call_user_func(function () use (&$opening, &$mandates, &$closing) {
1406
                return new FileNode(new LayoutNode($opening, $closing, ...$mandates));
1407
            });
1408
        }
1409
1410
        $this->cache['L_RESP_MANDATE'][$_position] = array(
1411
            'success' => $_success,
1412
            'position' => $this->position,
1413
            'value' => $this->value
1414
        );
1415
1416
        if (!$_success) {
1417
            $this->report($_position, 'L_RESP_MANDATE');
1418
        }
1419
1420
        return $_success;
1421
    }
1422
1423
    protected function parseR_RESP_MANDATE_OPENING_OLD()
1424
    {
1425
        $_position = $this->position;
1426
1427
        if (isset($this->cache['R_RESP_MANDATE_OPENING_OLD'][$_position])) {
1428
            $_success = $this->cache['R_RESP_MANDATE_OPENING_OLD'][$_position]['success'];
1429
            $this->position = $this->cache['R_RESP_MANDATE_OPENING_OLD'][$_position]['position'];
1430
            $this->value = $this->cache['R_RESP_MANDATE_OPENING_OLD'][$_position]['value'];
1431
1432
            return $_success;
1433
        }
1434
1435
        $_value41 = array();
1436
1437
        if (substr($this->string, $this->position, strlen('01')) === '01') {
1438
            $_success = true;
1439
            $this->value = substr($this->string, $this->position, strlen('01'));
1440
            $this->position += strlen('01');
1441
        } else {
1442
            $_success = false;
1443
1444
            $this->report($this->position, '\'01\'');
1445
        }
1446
1447
        if ($_success) {
1448
            $_value41[] = $this->value;
1449
1450
            $_success = $this->parseDATE();
1451
1452
            if ($_success) {
1453
                $date = $this->value;
1454
            }
1455
        }
1456
1457
        if ($_success) {
1458
            $_value41[] = $this->value;
1459
1460
            $_success = $this->parseBGC_CLEARING();
1461
        }
1462
1463
        if ($_success) {
1464
            $_value41[] = $this->value;
1465
1466
            $_success = $this->parseBANKGIRO();
1467
1468
            if ($_success) {
1469
                $bg = $this->value;
1470
            }
1471
        }
1472
1473
        if ($_success) {
1474
            $_value41[] = $this->value;
1475
1476
            if (substr($this->string, $this->position, strlen('AG-MEDAVI')) === 'AG-MEDAVI') {
1477
                $_success = true;
1478
                $this->value = substr($this->string, $this->position, strlen('AG-MEDAVI'));
1479
                $this->position += strlen('AG-MEDAVI');
1480
            } else {
1481
                $_success = false;
1482
1483
                $this->report($this->position, '\'AG-MEDAVI\'');
1484
            }
1485
        }
1486
1487
        if ($_success) {
1488
            $_value41[] = $this->value;
1489
1490
            $_success = $this->parseEOR();
1491
        }
1492
1493
        if ($_success) {
1494
            $_value41[] = $this->value;
1495
1496
            $this->value = $_value41;
1497
        }
1498
1499
        if ($_success) {
1500
            $this->value = call_user_func(function () use (&$date, &$bg) {
1501
                return new OpeningNode(
1502
                    'AG-MEDAVI',
1503
                    $date,
1504
                    new BgcCustomerNumberNode($this->currentLineNr, ''),
1505
                    $bg,
1506
                    $this->currentLineNr
1507
                );
1508
            });
1509
        }
1510
1511
        $this->cache['R_RESP_MANDATE_OPENING_OLD'][$_position] = array(
1512
            'success' => $_success,
1513
            'position' => $this->position,
1514
            'value' => $this->value
1515
        );
1516
1517
        if (!$_success) {
1518
            $this->report($_position, 'R_RESP_MANDATE_OPENING_OLD');
1519
        }
1520
1521
        return $_success;
1522
    }
1523
1524
    protected function parseR_RESP_MANDATE()
1525
    {
1526
        $_position = $this->position;
1527
1528
        if (isset($this->cache['R_RESP_MANDATE'][$_position])) {
1529
            $_success = $this->cache['R_RESP_MANDATE'][$_position]['success'];
1530
            $this->position = $this->cache['R_RESP_MANDATE'][$_position]['position'];
1531
            $this->value = $this->cache['R_RESP_MANDATE'][$_position]['value'];
1532
1533
            return $_success;
1534
        }
1535
1536
        $_value50 = array();
1537
1538
        if (substr($this->string, $this->position, strlen('73')) === '73') {
1539
            $_success = true;
1540
            $this->value = substr($this->string, $this->position, strlen('73'));
1541
            $this->position += strlen('73');
1542
        } else {
1543
            $_success = false;
1544
1545
            $this->report($this->position, '\'73\'');
1546
        }
1547
1548
        if ($_success) {
1549
            $_value50[] = $this->value;
1550
1551
            $_success = $this->parseBANKGIRO();
1552
1553
            if ($_success) {
1554
                $bg = $this->value;
1555
            }
1556
        }
1557
1558
        if ($_success) {
1559
            $_value50[] = $this->value;
1560
1561
            $_success = $this->parsePAYER_NR();
1562
1563
            if ($_success) {
1564
                $payerNr = $this->value;
1565
            }
1566
        }
1567
1568
        if ($_success) {
1569
            $_value50[] = $this->value;
1570
1571
            $_position43 = $this->position;
1572
1573
            $_value42 = array();
1574
1575
            $_success = $this->parseA10();
1576
1577
            if ($_success) {
1578
                $_value42[] = $this->value;
1579
1580
                $_success = $this->parseA5();
1581
            }
1582
1583
            if ($_success) {
1584
                $_value42[] = $this->value;
1585
1586
                $_success = $this->parseA();
1587
            }
1588
1589
            if ($_success) {
1590
                $_value42[] = $this->value;
1591
1592
                $this->value = $_value42;
1593
            }
1594
1595
            if ($_success) {
1596
                $this->value = strval(substr($this->string, $_position43, $this->position - $_position43));
1597
            }
1598
1599
            if ($_success) {
1600
                $accountNr = $this->value;
1601
            }
1602
        }
1603
1604
        if ($_success) {
1605
            $_value50[] = $this->value;
1606
1607
            $_success = $this->parseID();
1608
1609
            if ($_success) {
1610
                $id = $this->value;
1611
            }
1612
        }
1613
1614
        if ($_success) {
1615
            $_value50[] = $this->value;
1616
1617
            $_success = $this->parseA5();
1618
        }
1619
1620
        if ($_success) {
1621
            $_value50[] = $this->value;
1622
1623
            $_position45 = $this->position;
1624
1625
            $_value44 = array();
1626
1627
            $_success = $this->parseN();
1628
1629
            if ($_success) {
1630
                $_value44[] = $this->value;
1631
1632
                $_success = $this->parseN();
1633
            }
1634
1635
            if ($_success) {
1636
                $_value44[] = $this->value;
1637
1638
                $this->value = $_value44;
1639
            }
1640
1641
            if ($_success) {
1642
                $this->value = strval(substr($this->string, $_position45, $this->position - $_position45));
1643
            }
1644
1645
            if ($_success) {
1646
                $info = $this->value;
1647
            }
1648
        }
1649
1650
        if ($_success) {
1651
            $_value50[] = $this->value;
1652
1653
            $_position47 = $this->position;
1654
1655
            $_value46 = array();
1656
1657
            $_success = $this->parseN();
1658
1659
            if ($_success) {
1660
                $_value46[] = $this->value;
1661
1662
                $_success = $this->parseN();
1663
            }
1664
1665
            if ($_success) {
1666
                $_value46[] = $this->value;
1667
1668
                $this->value = $_value46;
1669
            }
1670
1671
            if ($_success) {
1672
                $this->value = strval(substr($this->string, $_position47, $this->position - $_position47));
1673
            }
1674
1675
            if ($_success) {
1676
                $comment = $this->value;
1677
            }
1678
        }
1679
1680
        if ($_success) {
1681
            $_value50[] = $this->value;
1682
1683
            $_position48 = $this->position;
1684
            $_cut49 = $this->cut;
1685
1686
            $this->cut = false;
1687
            $_success = $this->parseDATE();
1688
1689
            if (!$_success && !$this->cut) {
1690
                $_success = true;
1691
                $this->position = $_position48;
1692
                $this->value = null;
1693
            }
1694
1695
            $this->cut = $_cut49;
1696
1697
            if ($_success) {
1698
                $date = $this->value;
1699
            }
1700
        }
1701
1702
        if ($_success) {
1703
            $_value50[] = $this->value;
1704
1705
            $_success = $this->parseEOR();
1706
        }
1707
1708
        if ($_success) {
1709
            $_value50[] = $this->value;
1710
1711
            $this->value = $_value50;
1712
        }
1713
1714
        if ($_success) {
1715
            $this->value = call_user_func(function () use (&$bg, &$payerNr, &$accountNr, &$id, &$info, &$comment, &$date) {
1716
                // TODO fundera om jag kan dela upp denna i flera R_ så att jag kan använda ACCOUNT ...
1717
                $accountNr = trim(ltrim($accountNr, '0'));
1718
1719
                return new MandateResponseNode(
1720
                    $bg,
1721
                    $payerNr,
1722
                    new AccountNode($this->currentLineNr, $accountNr ?: $payerNr->getValue()),
1723
                    $id,
1724
                    new MessageNode($this->currentLineNr, "73.$info"),
1725
                    new MessageNode($this->currentLineNr, "73.comment.$comment"),
1726
                    $date ?: new \DateTimeImmutable('@0'),
1727
                    $this->currentLineNr
1728
                );
1729
            });
1730
        }
1731
1732
        $this->cache['R_RESP_MANDATE'][$_position] = array(
1733
            'success' => $_success,
1734
            'position' => $this->position,
1735
            'value' => $this->value
1736
        );
1737
1738
        if (!$_success) {
1739
            $this->report($_position, 'R_RESP_MANDATE');
1740
        }
1741
1742
        return $_success;
1743
    }
1744
1745
    protected function parseR_RESP_MANDATE_CLOSING()
1746
    {
1747
        $_position = $this->position;
1748
1749
        if (isset($this->cache['R_RESP_MANDATE_CLOSING'][$_position])) {
1750
            $_success = $this->cache['R_RESP_MANDATE_CLOSING'][$_position]['success'];
1751
            $this->position = $this->cache['R_RESP_MANDATE_CLOSING'][$_position]['position'];
1752
            $this->value = $this->cache['R_RESP_MANDATE_CLOSING'][$_position]['value'];
1753
1754
            return $_success;
1755
        }
1756
1757
        $_value53 = array();
1758
1759
        if (substr($this->string, $this->position, strlen('09')) === '09') {
1760
            $_success = true;
1761
            $this->value = substr($this->string, $this->position, strlen('09'));
1762
            $this->position += strlen('09');
1763
        } else {
1764
            $_success = false;
1765
1766
            $this->report($this->position, '\'09\'');
1767
        }
1768
1769
        if ($_success) {
1770
            $_value53[] = $this->value;
1771
1772
            $_success = $this->parseDATE();
1773
1774
            if ($_success) {
1775
                $date = $this->value;
1776
            }
1777
        }
1778
1779
        if ($_success) {
1780
            $_value53[] = $this->value;
1781
1782
            $_success = $this->parseBGC_CLEARING();
1783
        }
1784
1785
        if ($_success) {
1786
            $_value53[] = $this->value;
1787
1788
            $_position52 = $this->position;
1789
1790
            $_value51 = array();
1791
1792
            $_success = $this->parseN5();
1793
1794
            if ($_success) {
1795
                $_value51[] = $this->value;
1796
1797
                $_success = $this->parseN();
1798
            }
1799
1800
            if ($_success) {
1801
                $_value51[] = $this->value;
1802
1803
                $_success = $this->parseN();
1804
            }
1805
1806
            if ($_success) {
1807
                $_value51[] = $this->value;
1808
1809
                $this->value = $_value51;
1810
            }
1811
1812
            if ($_success) {
1813
                $this->value = strval(substr($this->string, $_position52, $this->position - $_position52));
1814
            }
1815
1816
            if ($_success) {
1817
                $nrOfPosts = $this->value;
1818
            }
1819
        }
1820
1821
        if ($_success) {
1822
            $_value53[] = $this->value;
1823
1824
            $_success = $this->parseEOR();
1825
        }
1826
1827
        if ($_success) {
1828
            $_value53[] = $this->value;
1829
1830
            $this->value = $_value53;
1831
        }
1832
1833
        if ($_success) {
1834
            $this->value = call_user_func(function () use (&$date, &$nrOfPosts) {
1835
                return new ClosingNode($date, intval($nrOfPosts), $this->currentLineNr);
1836
            });
1837
        }
1838
1839
        $this->cache['R_RESP_MANDATE_CLOSING'][$_position] = array(
1840
            'success' => $_success,
1841
            'position' => $this->position,
1842
            'value' => $this->value
1843
        );
1844
1845
        if (!$_success) {
1846
            $this->report($_position, 'R_RESP_MANDATE_CLOSING');
1847
        }
1848
1849
        return $_success;
1850
    }
1851
1852
    protected function parseACCOUNT()
1853
    {
1854
        $_position = $this->position;
1855
1856
        if (isset($this->cache['ACCOUNT'][$_position])) {
1857
            $_success = $this->cache['ACCOUNT'][$_position]['success'];
1858
            $this->position = $this->cache['ACCOUNT'][$_position]['position'];
1859
            $this->value = $this->cache['ACCOUNT'][$_position]['value'];
1860
1861
            return $_success;
1862
        }
1863
1864
        $_position55 = $this->position;
1865
1866
        $_value54 = array();
1867
1868
        $_success = $this->parseN10();
1869
1870
        if ($_success) {
1871
            $_value54[] = $this->value;
1872
1873
            $_success = $this->parseN5();
1874
        }
1875
1876
        if ($_success) {
1877
            $_value54[] = $this->value;
1878
1879
            $_success = $this->parseN();
1880
        }
1881
1882
        if ($_success) {
1883
            $_value54[] = $this->value;
1884
1885
            $this->value = $_value54;
1886
        }
1887
1888
        if ($_success) {
1889
            $this->value = strval(substr($this->string, $_position55, $this->position - $_position55));
1890
        }
1891
1892
        if ($_success) {
1893
            $number = $this->value;
1894
        }
1895
1896
        if ($_success) {
1897
            $this->value = call_user_func(function () use (&$number) {
1898
                return new AccountNode($this->currentLineNr, ltrim($number, '0'));
1899
            });
1900
        }
1901
1902
        $this->cache['ACCOUNT'][$_position] = array(
1903
            'success' => $_success,
1904
            'position' => $this->position,
1905
            'value' => $this->value
1906
        );
1907
1908
        if (!$_success) {
1909
            $this->report($_position, 'ACCOUNT');
1910
        }
1911
1912
        return $_success;
1913
    }
1914
1915
    protected function parseBANKGIRO()
1916
    {
1917
        $_position = $this->position;
1918
1919
        if (isset($this->cache['BANKGIRO'][$_position])) {
1920
            $_success = $this->cache['BANKGIRO'][$_position]['success'];
1921
            $this->position = $this->cache['BANKGIRO'][$_position]['position'];
1922
            $this->value = $this->cache['BANKGIRO'][$_position]['value'];
1923
1924
            return $_success;
1925
        }
1926
1927
        $_success = $this->parseN10();
1928
1929
        if ($_success) {
1930
            $number = $this->value;
1931
        }
1932
1933
        if ($_success) {
1934
            $this->value = call_user_func(function () use (&$number) {
1935
                return new BankgiroNode($this->currentLineNr, ltrim($number, '0'));
1936
            });
1937
        }
1938
1939
        $this->cache['BANKGIRO'][$_position] = array(
1940
            'success' => $_success,
1941
            'position' => $this->position,
1942
            'value' => $this->value
1943
        );
1944
1945
        if (!$_success) {
1946
            $this->report($_position, 'BANKGIRO');
1947
        }
1948
1949
        return $_success;
1950
    }
1951
1952
    protected function parseBGC_CLEARING()
1953
    {
1954
        $_position = $this->position;
1955
1956
        if (isset($this->cache['BGC_CLEARING'][$_position])) {
1957
            $_success = $this->cache['BGC_CLEARING'][$_position]['success'];
1958
            $this->position = $this->cache['BGC_CLEARING'][$_position]['position'];
1959
            $this->value = $this->cache['BGC_CLEARING'][$_position]['value'];
1960
1961
            return $_success;
1962
        }
1963
1964
        if (substr($this->string, $this->position, strlen('9900')) === '9900') {
1965
            $_success = true;
1966
            $this->value = substr($this->string, $this->position, strlen('9900'));
1967
            $this->position += strlen('9900');
1968
        } else {
1969
            $_success = false;
1970
1971
            $this->report($this->position, '\'9900\'');
1972
        }
1973
1974
        $this->cache['BGC_CLEARING'][$_position] = array(
1975
            'success' => $_success,
1976
            'position' => $this->position,
1977
            'value' => $this->value
1978
        );
1979
1980
        if (!$_success) {
1981
            $this->report($_position, 'BGC_CLEARING');
1982
        }
1983
1984
        return $_success;
1985
    }
1986
1987
    protected function parseCUST_NR()
1988
    {
1989
        $_position = $this->position;
1990
1991
        if (isset($this->cache['CUST_NR'][$_position])) {
1992
            $_success = $this->cache['CUST_NR'][$_position]['success'];
1993
            $this->position = $this->cache['CUST_NR'][$_position]['position'];
1994
            $this->value = $this->cache['CUST_NR'][$_position]['value'];
1995
1996
            return $_success;
1997
        }
1998
1999
        $_position57 = $this->position;
2000
2001
        $_value56 = array();
2002
2003
        $_success = $this->parseN5();
2004
2005
        if ($_success) {
2006
            $_value56[] = $this->value;
2007
2008
            $_success = $this->parseN();
2009
        }
2010
2011
        if ($_success) {
2012
            $_value56[] = $this->value;
2013
2014
            $this->value = $_value56;
2015
        }
2016
2017
        if ($_success) {
2018
            $this->value = strval(substr($this->string, $_position57, $this->position - $_position57));
2019
        }
2020
2021
        if ($_success) {
2022
            $nr = $this->value;
2023
        }
2024
2025
        if ($_success) {
2026
            $this->value = call_user_func(function () use (&$nr) {
2027
                return new BgcCustomerNumberNode($this->currentLineNr, ltrim($nr, '0'));
2028
            });
2029
        }
2030
2031
        $this->cache['CUST_NR'][$_position] = array(
2032
            'success' => $_success,
2033
            'position' => $this->position,
2034
            'value' => $this->value
2035
        );
2036
2037
        if (!$_success) {
2038
            $this->report($_position, 'CUST_NR');
2039
        }
2040
2041
        return $_success;
2042
    }
2043
2044
    protected function parseDATE()
2045
    {
2046
        $_position = $this->position;
2047
2048
        if (isset($this->cache['DATE'][$_position])) {
2049
            $_success = $this->cache['DATE'][$_position]['success'];
2050
            $this->position = $this->cache['DATE'][$_position]['position'];
2051
            $this->value = $this->cache['DATE'][$_position]['value'];
2052
2053
            return $_success;
2054
        }
2055
2056
        $_position59 = $this->position;
2057
2058
        $_value58 = array();
2059
2060
        $_success = $this->parseN5();
2061
2062
        if ($_success) {
2063
            $_value58[] = $this->value;
2064
2065
            $_success = $this->parseN();
2066
        }
2067
2068
        if ($_success) {
2069
            $_value58[] = $this->value;
2070
2071
            $_success = $this->parseN();
2072
        }
2073
2074
        if ($_success) {
2075
            $_value58[] = $this->value;
2076
2077
            $_success = $this->parseN();
2078
        }
2079
2080
        if ($_success) {
2081
            $_value58[] = $this->value;
2082
2083
            $this->value = $_value58;
2084
        }
2085
2086
        if ($_success) {
2087
            $this->value = strval(substr($this->string, $_position59, $this->position - $_position59));
2088
        }
2089
2090
        if ($_success) {
2091
            $date = $this->value;
2092
        }
2093
2094
        if ($_success) {
2095
            $this->value = call_user_func(function () use (&$date) {
2096
                return new \DateTimeImmutable($date . '000000');
2097
            });
2098
        }
2099
2100
        $this->cache['DATE'][$_position] = array(
2101
            'success' => $_success,
2102
            'position' => $this->position,
2103
            'value' => $this->value
2104
        );
2105
2106
        if (!$_success) {
2107
            $this->report($_position, 'DATE');
2108
        }
2109
2110
        return $_success;
2111
    }
2112
2113
    protected function parseID()
2114
    {
2115
        $_position = $this->position;
2116
2117
        if (isset($this->cache['ID'][$_position])) {
2118
            $_success = $this->cache['ID'][$_position]['success'];
2119
            $this->position = $this->cache['ID'][$_position]['position'];
2120
            $this->value = $this->cache['ID'][$_position]['value'];
2121
2122
            return $_success;
2123
        }
2124
2125
        $_value62 = array();
2126
2127
        $_position61 = $this->position;
2128
2129
        $_value60 = array();
2130
2131
        $_success = $this->parseA();
2132
2133
        if ($_success) {
2134
            $_value60[] = $this->value;
2135
2136
            $_success = $this->parseA();
2137
        }
2138
2139
        if ($_success) {
2140
            $_value60[] = $this->value;
2141
2142
            $this->value = $_value60;
2143
        }
2144
2145
        if ($_success) {
2146
            $this->value = strval(substr($this->string, $_position61, $this->position - $_position61));
2147
        }
2148
2149
        if ($_success) {
2150
            $century = $this->value;
2151
        }
2152
2153
        if ($_success) {
2154
            $_value62[] = $this->value;
2155
2156
            $_success = $this->parseA10();
2157
2158
            if ($_success) {
2159
                $number = $this->value;
2160
            }
2161
        }
2162
2163
        if ($_success) {
2164
            $_value62[] = $this->value;
2165
2166
            $this->value = $_value62;
2167
        }
2168
2169
        if ($_success) {
2170
            $this->value = call_user_func(function () use (&$century, &$number) {
2171
                return in_array($century, ['00', '99'])
2172
                    ? new OrganizationIdNode($this->currentLineNr, $number)
2173
                    : new PersonalIdNode($this->currentLineNr, $century.$number);
2174
            });
2175
        }
2176
2177
        $this->cache['ID'][$_position] = array(
2178
            'success' => $_success,
2179
            'position' => $this->position,
2180
            'value' => $this->value
2181
        );
2182
2183
        if (!$_success) {
2184
            $this->report($_position, 'ID');
2185
        }
2186
2187
        return $_success;
2188
    }
2189
2190
    protected function parsePAYER_NR()
2191
    {
2192
        $_position = $this->position;
2193
2194
        if (isset($this->cache['PAYER_NR'][$_position])) {
2195
            $_success = $this->cache['PAYER_NR'][$_position]['success'];
2196
            $this->position = $this->cache['PAYER_NR'][$_position]['position'];
2197
            $this->value = $this->cache['PAYER_NR'][$_position]['value'];
2198
2199
            return $_success;
2200
        }
2201
2202
        $_position64 = $this->position;
2203
2204
        $_value63 = array();
2205
2206
        $_success = $this->parseN10();
2207
2208
        if ($_success) {
2209
            $_value63[] = $this->value;
2210
2211
            $_success = $this->parseN5();
2212
        }
2213
2214
        if ($_success) {
2215
            $_value63[] = $this->value;
2216
2217
            $_success = $this->parseN();
2218
        }
2219
2220
        if ($_success) {
2221
            $_value63[] = $this->value;
2222
2223
            $this->value = $_value63;
2224
        }
2225
2226
        if ($_success) {
2227
            $this->value = strval(substr($this->string, $_position64, $this->position - $_position64));
2228
        }
2229
2230
        if ($_success) {
2231
            $nr = $this->value;
2232
        }
2233
2234
        if ($_success) {
2235
            $this->value = call_user_func(function () use (&$nr) {
2236
                return new PayerNumberNode($this->currentLineNr, ltrim($nr, '0'));
2237
            });
2238
        }
2239
2240
        $this->cache['PAYER_NR'][$_position] = array(
2241
            'success' => $_success,
2242
            'position' => $this->position,
2243
            'value' => $this->value
2244
        );
2245
2246
        if (!$_success) {
2247
            $this->report($_position, 'PAYER_NR');
2248
        }
2249
2250
        return $_success;
2251
    }
2252
2253
    protected function parseA()
2254
    {
2255
        $_position = $this->position;
2256
2257
        if (isset($this->cache['A'][$_position])) {
2258
            $_success = $this->cache['A'][$_position]['success'];
2259
            $this->position = $this->cache['A'][$_position]['position'];
2260
            $this->value = $this->cache['A'][$_position]['value'];
2261
2262
            return $_success;
2263
        }
2264
2265
        if (preg_match('/^[a-zA-Z0-9 -\\/&]$/', substr($this->string, $this->position, 1))) {
2266
            $_success = true;
2267
            $this->value = substr($this->string, $this->position, 1);
2268
            $this->position += 1;
2269
        } else {
2270
            $_success = false;
2271
        }
2272
2273
        $this->cache['A'][$_position] = array(
2274
            'success' => $_success,
2275
            'position' => $this->position,
2276
            'value' => $this->value
2277
        );
2278
2279
        if (!$_success) {
2280
            $this->report($_position, "ALPHA-NUMERIC");
2281
        }
2282
2283
        return $_success;
2284
    }
2285
2286
    protected function parseA5()
2287
    {
2288
        $_position = $this->position;
2289
2290
        if (isset($this->cache['A5'][$_position])) {
2291
            $_success = $this->cache['A5'][$_position]['success'];
2292
            $this->position = $this->cache['A5'][$_position]['position'];
2293
            $this->value = $this->cache['A5'][$_position]['value'];
2294
2295
            return $_success;
2296
        }
2297
2298
        $_position66 = $this->position;
2299
2300
        $_value65 = array();
2301
2302
        $_success = $this->parseA();
2303
2304
        if ($_success) {
2305
            $_value65[] = $this->value;
2306
2307
            $_success = $this->parseA();
2308
        }
2309
2310
        if ($_success) {
2311
            $_value65[] = $this->value;
2312
2313
            $_success = $this->parseA();
2314
        }
2315
2316
        if ($_success) {
2317
            $_value65[] = $this->value;
2318
2319
            $_success = $this->parseA();
2320
        }
2321
2322
        if ($_success) {
2323
            $_value65[] = $this->value;
2324
2325
            $_success = $this->parseA();
2326
        }
2327
2328
        if ($_success) {
2329
            $_value65[] = $this->value;
2330
2331
            $this->value = $_value65;
2332
        }
2333
2334
        if ($_success) {
2335
            $this->value = strval(substr($this->string, $_position66, $this->position - $_position66));
2336
        }
2337
2338
        $this->cache['A5'][$_position] = array(
2339
            'success' => $_success,
2340
            'position' => $this->position,
2341
            'value' => $this->value
2342
        );
2343
2344
        if (!$_success) {
2345
            $this->report($_position, 'A5');
2346
        }
2347
2348
        return $_success;
2349
    }
2350
2351
    protected function parseA10()
2352
    {
2353
        $_position = $this->position;
2354
2355
        if (isset($this->cache['A10'][$_position])) {
2356
            $_success = $this->cache['A10'][$_position]['success'];
2357
            $this->position = $this->cache['A10'][$_position]['position'];
2358
            $this->value = $this->cache['A10'][$_position]['value'];
2359
2360
            return $_success;
2361
        }
2362
2363
        $_position68 = $this->position;
2364
2365
        $_value67 = array();
2366
2367
        $_success = $this->parseA5();
2368
2369
        if ($_success) {
2370
            $_value67[] = $this->value;
2371
2372
            $_success = $this->parseA5();
2373
        }
2374
2375
        if ($_success) {
2376
            $_value67[] = $this->value;
2377
2378
            $this->value = $_value67;
2379
        }
2380
2381
        if ($_success) {
2382
            $this->value = strval(substr($this->string, $_position68, $this->position - $_position68));
2383
        }
2384
2385
        $this->cache['A10'][$_position] = array(
2386
            'success' => $_success,
2387
            'position' => $this->position,
2388
            'value' => $this->value
2389
        );
2390
2391
        if (!$_success) {
2392
            $this->report($_position, 'A10');
2393
        }
2394
2395
        return $_success;
2396
    }
2397
2398
    protected function parseA20()
2399
    {
2400
        $_position = $this->position;
2401
2402
        if (isset($this->cache['A20'][$_position])) {
2403
            $_success = $this->cache['A20'][$_position]['success'];
2404
            $this->position = $this->cache['A20'][$_position]['position'];
2405
            $this->value = $this->cache['A20'][$_position]['value'];
2406
2407
            return $_success;
2408
        }
2409
2410
        $_position70 = $this->position;
2411
2412
        $_value69 = array();
2413
2414
        $_success = $this->parseA10();
2415
2416
        if ($_success) {
2417
            $_value69[] = $this->value;
2418
2419
            $_success = $this->parseA10();
2420
        }
2421
2422
        if ($_success) {
2423
            $_value69[] = $this->value;
2424
2425
            $this->value = $_value69;
2426
        }
2427
2428
        if ($_success) {
2429
            $this->value = strval(substr($this->string, $_position70, $this->position - $_position70));
2430
        }
2431
2432
        $this->cache['A20'][$_position] = array(
2433
            'success' => $_success,
2434
            'position' => $this->position,
2435
            'value' => $this->value
2436
        );
2437
2438
        if (!$_success) {
2439
            $this->report($_position, 'A20');
2440
        }
2441
2442
        return $_success;
2443
    }
2444
2445
    protected function parseA40()
2446
    {
2447
        $_position = $this->position;
2448
2449
        if (isset($this->cache['A40'][$_position])) {
2450
            $_success = $this->cache['A40'][$_position]['success'];
2451
            $this->position = $this->cache['A40'][$_position]['position'];
2452
            $this->value = $this->cache['A40'][$_position]['value'];
2453
2454
            return $_success;
2455
        }
2456
2457
        $_position72 = $this->position;
2458
2459
        $_value71 = array();
2460
2461
        $_success = $this->parseA20();
2462
2463
        if ($_success) {
2464
            $_value71[] = $this->value;
2465
2466
            $_success = $this->parseA20();
2467
        }
2468
2469
        if ($_success) {
2470
            $_value71[] = $this->value;
2471
2472
            $this->value = $_value71;
2473
        }
2474
2475
        if ($_success) {
2476
            $this->value = strval(substr($this->string, $_position72, $this->position - $_position72));
2477
        }
2478
2479
        $this->cache['A40'][$_position] = array(
2480
            'success' => $_success,
2481
            'position' => $this->position,
2482
            'value' => $this->value
2483
        );
2484
2485
        if (!$_success) {
2486
            $this->report($_position, 'A40');
2487
        }
2488
2489
        return $_success;
2490
    }
2491
2492
    protected function parseN()
2493
    {
2494
        $_position = $this->position;
2495
2496
        if (isset($this->cache['N'][$_position])) {
2497
            $_success = $this->cache['N'][$_position]['success'];
2498
            $this->position = $this->cache['N'][$_position]['position'];
2499
            $this->value = $this->cache['N'][$_position]['value'];
2500
2501
            return $_success;
2502
        }
2503
2504
        if (preg_match('/^[0-9]$/', substr($this->string, $this->position, 1))) {
2505
            $_success = true;
2506
            $this->value = substr($this->string, $this->position, 1);
2507
            $this->position += 1;
2508
        } else {
2509
            $_success = false;
2510
        }
2511
2512
        $this->cache['N'][$_position] = array(
2513
            'success' => $_success,
2514
            'position' => $this->position,
2515
            'value' => $this->value
2516
        );
2517
2518
        if (!$_success) {
2519
            $this->report($_position, "NUMBER");
2520
        }
2521
2522
        return $_success;
2523
    }
2524
2525
    protected function parseN5()
2526
    {
2527
        $_position = $this->position;
2528
2529
        if (isset($this->cache['N5'][$_position])) {
2530
            $_success = $this->cache['N5'][$_position]['success'];
2531
            $this->position = $this->cache['N5'][$_position]['position'];
2532
            $this->value = $this->cache['N5'][$_position]['value'];
2533
2534
            return $_success;
2535
        }
2536
2537
        $_position74 = $this->position;
2538
2539
        $_value73 = array();
2540
2541
        $_success = $this->parseN();
2542
2543
        if ($_success) {
2544
            $_value73[] = $this->value;
2545
2546
            $_success = $this->parseN();
2547
        }
2548
2549
        if ($_success) {
2550
            $_value73[] = $this->value;
2551
2552
            $_success = $this->parseN();
2553
        }
2554
2555
        if ($_success) {
2556
            $_value73[] = $this->value;
2557
2558
            $_success = $this->parseN();
2559
        }
2560
2561
        if ($_success) {
2562
            $_value73[] = $this->value;
2563
2564
            $_success = $this->parseN();
2565
        }
2566
2567
        if ($_success) {
2568
            $_value73[] = $this->value;
2569
2570
            $this->value = $_value73;
2571
        }
2572
2573
        if ($_success) {
2574
            $this->value = strval(substr($this->string, $_position74, $this->position - $_position74));
2575
        }
2576
2577
        $this->cache['N5'][$_position] = array(
2578
            'success' => $_success,
2579
            'position' => $this->position,
2580
            'value' => $this->value
2581
        );
2582
2583
        if (!$_success) {
2584
            $this->report($_position, 'N5');
2585
        }
2586
2587
        return $_success;
2588
    }
2589
2590
    protected function parseN10()
2591
    {
2592
        $_position = $this->position;
2593
2594
        if (isset($this->cache['N10'][$_position])) {
2595
            $_success = $this->cache['N10'][$_position]['success'];
2596
            $this->position = $this->cache['N10'][$_position]['position'];
2597
            $this->value = $this->cache['N10'][$_position]['value'];
2598
2599
            return $_success;
2600
        }
2601
2602
        $_position76 = $this->position;
2603
2604
        $_value75 = array();
2605
2606
        $_success = $this->parseN5();
2607
2608
        if ($_success) {
2609
            $_value75[] = $this->value;
2610
2611
            $_success = $this->parseN5();
2612
        }
2613
2614
        if ($_success) {
2615
            $_value75[] = $this->value;
2616
2617
            $this->value = $_value75;
2618
        }
2619
2620
        if ($_success) {
2621
            $this->value = strval(substr($this->string, $_position76, $this->position - $_position76));
2622
        }
2623
2624
        $this->cache['N10'][$_position] = array(
2625
            'success' => $_success,
2626
            'position' => $this->position,
2627
            'value' => $this->value
2628
        );
2629
2630
        if (!$_success) {
2631
            $this->report($_position, 'N10');
2632
        }
2633
2634
        return $_success;
2635
    }
2636
2637
    protected function parseN20()
2638
    {
2639
        $_position = $this->position;
2640
2641
        if (isset($this->cache['N20'][$_position])) {
2642
            $_success = $this->cache['N20'][$_position]['success'];
2643
            $this->position = $this->cache['N20'][$_position]['position'];
2644
            $this->value = $this->cache['N20'][$_position]['value'];
2645
2646
            return $_success;
2647
        }
2648
2649
        $_position78 = $this->position;
2650
2651
        $_value77 = array();
2652
2653
        $_success = $this->parseN10();
2654
2655
        if ($_success) {
2656
            $_value77[] = $this->value;
2657
2658
            $_success = $this->parseN10();
2659
        }
2660
2661
        if ($_success) {
2662
            $_value77[] = $this->value;
2663
2664
            $this->value = $_value77;
2665
        }
2666
2667
        if ($_success) {
2668
            $this->value = strval(substr($this->string, $_position78, $this->position - $_position78));
2669
        }
2670
2671
        $this->cache['N20'][$_position] = array(
2672
            'success' => $_success,
2673
            'position' => $this->position,
2674
            'value' => $this->value
2675
        );
2676
2677
        if (!$_success) {
2678
            $this->report($_position, 'N20');
2679
        }
2680
2681
        return $_success;
2682
    }
2683
2684
    protected function parseS()
2685
    {
2686
        $_position = $this->position;
2687
2688
        if (isset($this->cache['S'][$_position])) {
2689
            $_success = $this->cache['S'][$_position]['success'];
2690
            $this->position = $this->cache['S'][$_position]['position'];
2691
            $this->value = $this->cache['S'][$_position]['value'];
2692
2693
            return $_success;
2694
        }
2695
2696
        if (substr($this->string, $this->position, strlen(' ')) === ' ') {
2697
            $_success = true;
2698
            $this->value = substr($this->string, $this->position, strlen(' '));
2699
            $this->position += strlen(' ');
2700
        } else {
2701
            $_success = false;
2702
2703
            $this->report($this->position, '\' \'');
2704
        }
2705
2706
        $this->cache['S'][$_position] = array(
2707
            'success' => $_success,
2708
            'position' => $this->position,
2709
            'value' => $this->value
2710
        );
2711
2712
        if (!$_success) {
2713
            $this->report($_position, "SPACE");
2714
        }
2715
2716
        return $_success;
2717
    }
2718
2719
    protected function parseS5()
2720
    {
2721
        $_position = $this->position;
2722
2723
        if (isset($this->cache['S5'][$_position])) {
2724
            $_success = $this->cache['S5'][$_position]['success'];
2725
            $this->position = $this->cache['S5'][$_position]['position'];
2726
            $this->value = $this->cache['S5'][$_position]['value'];
2727
2728
            return $_success;
2729
        }
2730
2731
        $_position80 = $this->position;
2732
2733
        $_value79 = array();
2734
2735
        $_success = $this->parseS();
2736
2737
        if ($_success) {
2738
            $_value79[] = $this->value;
2739
2740
            $_success = $this->parseS();
2741
        }
2742
2743
        if ($_success) {
2744
            $_value79[] = $this->value;
2745
2746
            $_success = $this->parseS();
2747
        }
2748
2749
        if ($_success) {
2750
            $_value79[] = $this->value;
2751
2752
            $_success = $this->parseS();
2753
        }
2754
2755
        if ($_success) {
2756
            $_value79[] = $this->value;
2757
2758
            $_success = $this->parseS();
2759
        }
2760
2761
        if ($_success) {
2762
            $_value79[] = $this->value;
2763
2764
            $this->value = $_value79;
2765
        }
2766
2767
        if ($_success) {
2768
            $this->value = strval(substr($this->string, $_position80, $this->position - $_position80));
2769
        }
2770
2771
        $this->cache['S5'][$_position] = array(
2772
            'success' => $_success,
2773
            'position' => $this->position,
2774
            'value' => $this->value
2775
        );
2776
2777
        if (!$_success) {
2778
            $this->report($_position, 'S5');
2779
        }
2780
2781
        return $_success;
2782
    }
2783
2784
    protected function parseS10()
2785
    {
2786
        $_position = $this->position;
2787
2788
        if (isset($this->cache['S10'][$_position])) {
2789
            $_success = $this->cache['S10'][$_position]['success'];
2790
            $this->position = $this->cache['S10'][$_position]['position'];
2791
            $this->value = $this->cache['S10'][$_position]['value'];
2792
2793
            return $_success;
2794
        }
2795
2796
        $_position82 = $this->position;
2797
2798
        $_value81 = array();
2799
2800
        $_success = $this->parseS5();
2801
2802
        if ($_success) {
2803
            $_value81[] = $this->value;
2804
2805
            $_success = $this->parseS5();
2806
        }
2807
2808
        if ($_success) {
2809
            $_value81[] = $this->value;
2810
2811
            $this->value = $_value81;
2812
        }
2813
2814
        if ($_success) {
2815
            $this->value = strval(substr($this->string, $_position82, $this->position - $_position82));
2816
        }
2817
2818
        $this->cache['S10'][$_position] = array(
2819
            'success' => $_success,
2820
            'position' => $this->position,
2821
            'value' => $this->value
2822
        );
2823
2824
        if (!$_success) {
2825
            $this->report($_position, 'S10');
2826
        }
2827
2828
        return $_success;
2829
    }
2830
2831
    protected function parseS20()
2832
    {
2833
        $_position = $this->position;
2834
2835
        if (isset($this->cache['S20'][$_position])) {
2836
            $_success = $this->cache['S20'][$_position]['success'];
2837
            $this->position = $this->cache['S20'][$_position]['position'];
2838
            $this->value = $this->cache['S20'][$_position]['value'];
2839
2840
            return $_success;
2841
        }
2842
2843
        $_position84 = $this->position;
2844
2845
        $_value83 = array();
2846
2847
        $_success = $this->parseS10();
2848
2849
        if ($_success) {
2850
            $_value83[] = $this->value;
2851
2852
            $_success = $this->parseS10();
2853
        }
2854
2855
        if ($_success) {
2856
            $_value83[] = $this->value;
2857
2858
            $this->value = $_value83;
2859
        }
2860
2861
        if ($_success) {
2862
            $this->value = strval(substr($this->string, $_position84, $this->position - $_position84));
2863
        }
2864
2865
        $this->cache['S20'][$_position] = array(
2866
            'success' => $_success,
2867
            'position' => $this->position,
2868
            'value' => $this->value
2869
        );
2870
2871
        if (!$_success) {
2872
            $this->report($_position, 'S20');
2873
        }
2874
2875
        return $_success;
2876
    }
2877
2878
    protected function parseEOL()
2879
    {
2880
        $_position = $this->position;
2881
2882
        if (isset($this->cache['EOL'][$_position])) {
2883
            $_success = $this->cache['EOL'][$_position]['success'];
2884
            $this->position = $this->cache['EOL'][$_position]['position'];
2885
            $this->value = $this->cache['EOL'][$_position]['value'];
2886
2887
            return $_success;
2888
        }
2889
2890
        $_value87 = array();
2891
2892
        $_position85 = $this->position;
2893
        $_cut86 = $this->cut;
2894
2895
        $this->cut = false;
2896
        if (substr($this->string, $this->position, strlen("\r")) === "\r") {
2897
            $_success = true;
2898
            $this->value = substr($this->string, $this->position, strlen("\r"));
2899
            $this->position += strlen("\r");
2900
        } else {
2901
            $_success = false;
2902
2903
            $this->report($this->position, '"\\r"');
2904
        }
2905
2906
        if (!$_success && !$this->cut) {
2907
            $_success = true;
2908
            $this->position = $_position85;
2909
            $this->value = null;
2910
        }
2911
2912
        $this->cut = $_cut86;
2913
2914
        if ($_success) {
2915
            $_value87[] = $this->value;
2916
2917
            if (substr($this->string, $this->position, strlen("\n")) === "\n") {
2918
                $_success = true;
2919
                $this->value = substr($this->string, $this->position, strlen("\n"));
2920
                $this->position += strlen("\n");
2921
            } else {
2922
                $_success = false;
2923
2924
                $this->report($this->position, '"\\n"');
2925
            }
2926
        }
2927
2928
        if ($_success) {
2929
            $_value87[] = $this->value;
2930
2931
            $this->value = $_value87;
2932
        }
2933
2934
        if ($_success) {
2935
            $this->value = call_user_func(function () {
2936
                $this->currentLineNr++;
2937
            });
2938
        }
2939
2940
        $this->cache['EOL'][$_position] = array(
2941
            'success' => $_success,
2942
            'position' => $this->position,
2943
            'value' => $this->value
2944
        );
2945
2946
        if (!$_success) {
2947
            $this->report($_position, "END_OF_LINE");
2948
        }
2949
2950
        return $_success;
2951
    }
2952
2953
    protected function parseEOR()
2954
    {
2955
        $_position = $this->position;
2956
2957
        if (isset($this->cache['EOR'][$_position])) {
2958
            $_success = $this->cache['EOR'][$_position]['success'];
2959
            $this->position = $this->cache['EOR'][$_position]['position'];
2960
            $this->value = $this->cache['EOR'][$_position]['value'];
2961
2962
            return $_success;
2963
        }
2964
2965
        $_value91 = array();
2966
2967
        $_value89 = array();
2968
        $_cut90 = $this->cut;
2969
2970
        while (true) {
2971
            $_position88 = $this->position;
2972
2973
            $this->cut = false;
2974
            $_success = $this->parseA();
2975
2976
            if (!$_success) {
2977
                break;
2978
            }
2979
2980
            $_value89[] = $this->value;
2981
        }
2982
2983
        if (!$this->cut) {
2984
            $_success = true;
2985
            $this->position = $_position88;
2986
            $this->value = $_value89;
2987
        }
2988
2989
        $this->cut = $_cut90;
2990
2991
        if ($_success) {
2992
            $_value91[] = $this->value;
2993
2994
            $_success = $this->parseEOL();
2995
        }
2996
2997
        if ($_success) {
2998
            $_value91[] = $this->value;
2999
3000
            $this->value = $_value91;
3001
        }
3002
3003
        $this->cache['EOR'][$_position] = array(
3004
            'success' => $_success,
3005
            'position' => $this->position,
3006
            'value' => $this->value
3007
        );
3008
3009
        if (!$_success) {
3010
            $this->report($_position, "END_OF_RECORD");
3011
        }
3012
3013
        return $_success;
3014
    }
3015
3016
    private function line()
3017
    {
3018
        if (!empty($this->errors)) {
3019
            $positions = array_keys($this->errors);
3020
        } else {
3021
            $positions = array_keys($this->warnings);
3022
        }
3023
3024
        return count(explode("\n", substr($this->string, 0, max($positions))));
3025
    }
3026
3027
    private function rest()
3028
    {
3029
        return '"' . substr($this->string, $this->position) . '"';
3030
    }
3031
3032
    protected function report($position, $expecting)
3033
    {
3034
        if ($this->cut) {
3035
            $this->errors[$position][] = $expecting;
3036
        } else {
3037
            $this->warnings[$position][] = $expecting;
3038
        }
3039
    }
3040
3041
    private function expecting()
3042
    {
3043
        if (!empty($this->errors)) {
3044
            ksort($this->errors);
3045
3046
            return end($this->errors)[0];
3047
        }
3048
3049
        ksort($this->warnings);
3050
3051
        return implode(', ', end($this->warnings));
3052
    }
3053
3054
    public function parse($_string)
3055
    {
3056
        $this->string = $_string;
3057
        $this->position = 0;
3058
        $this->value = null;
3059
        $this->cache = array();
3060
        $this->cut = false;
3061
        $this->errors = array();
3062
        $this->warnings = array();
3063
3064
        $_success = $this->parseFILE();
3065
3066
        if ($_success && $this->position < strlen($this->string)) {
3067
            $_success = false;
3068
3069
            $this->report($this->position, "end of file");
3070
        }
3071
3072
        if (!$_success) {
3073
            throw new \InvalidArgumentException("Syntax error, expecting {$this->expecting()} on line {$this->line()}");
3074
        }
3075
3076
        return $this->value;
3077
    }
3078
}