locales-Lauf en
[kivitendo-erp.git] / SL / DB / Helper / ValidateAssembly.pm
1 package SL::DB::Helper::ValidateAssembly;
2
3 use strict;
4 use parent qw(Exporter);
5 our @EXPORT = qw(validate_assembly);
6
7 use SL::Locale::String;
8 use SL::DB::Part;
9 use SL::DB::Assembly;
10
11 sub validate_assembly {
12   my ($new_part, $part) = @_;
13
14   return t8("The assembly '#1' cannot be a part from itself.", $part->partnumber) if $new_part->id == $part->id;
15
16   my @seen = ($part->id);
17
18   return assembly_loop_exists(0, $new_part, @seen);
19 }
20
21 sub assembly_loop_exists {
22   my ($depth, $new_part, @seen) = @_;
23
24   return t8("Too much recursions in assembly tree (>100)") if $depth > 100;
25
26   # 1. check part is an assembly
27   return unless $new_part->is_assembly;
28
29   # 2. check assembly is still in list
30   return t8("The assembly '#1' would make a loop in assembly tree.", $new_part->partnumber) if grep { $_ == $new_part->id } @seen;
31
32   # 3. add to new list
33
34   push @seen, $new_part->id;
35
36   # 4. go into depth for each child
37
38   foreach my $assembly ($new_part->assemblies) {
39     my $retval = assembly_loop_exists($depth + 1, $assembly->part, @seen);
40     return $retval if $retval;
41   }
42   return undef;
43 }
44
45 1;
46
47 __END__
48
49 =encoding utf-8
50
51 =head1 NAME
52
53 SL::DB::Helper::ValidateAssembly - Mixin to check loops in assemblies
54
55 =head1 SYNOPSIS
56
57 SL::DB::Helper::ValidateAssembly->validate_assembly($newpart,$assembly_part);
58
59
60 =head1 HELPER FUNCTION
61
62 =over 4
63
64 =item C<validate_assembly new_part_object  part_object>
65
66 A new part is added to an assembly. C<new_part_object> is the part which is want to added.
67
68 First it was checked if the new part is equal the actual part.
69 Then recursively all assemblies in the assemby are checked for a loop.
70
71 The function returns an error string if a loop exists or the maximum of 100 iterations is reached
72 else on success ''.
73
74 =back
75
76 =head1 AUTHOR
77
78 Martin Helmling E<lt>martin.helmling@opendynamic.de>E<gt>
79
80 =cut