1 package t::lib::TestBuilder;
10 smallint => \&_gen_int,
11 mediumint => \&_gen_int,
12 integer => \&_gen_int,
16 decimal => \&_gen_real,
17 double_precision => \&_gen_real,
19 timestamp => \&_gen_date,
20 datetime => \&_gen_date,
24 varchar => \&_gen_text,
25 tinytext => \&_gen_text,
27 mediumtext => \&_gen_text,
28 longtext => \&_gen_text,
30 set => \&_gen_set_enum,
31 enum => \&_gen_set_enum,
33 tinyblob => \&_gen_blob,
34 mediumblob => \&_gen_blob,
36 longblob => \&_gen_blob,
39 our $default_value = {
42 surname => 'my surname',
43 address => 'my adress',
47 branchname => 'my branchname',
53 default_privacy => 'default',
66 $default_value->{UserPermission}->{code} = $default_value->{UserPermission}->{module_bit};
72 bless( $self, $class );
74 $self->schema( Koha::Database->new()->schema );
75 $self->schema->txn_begin();
76 $self->schema->storage->sql_maker->quote_char('`');
81 my ($self, $schema) = @_;
83 if( defined( $schema ) ) {
84 $self->{schema} = $schema;
86 return $self->{schema};
90 my ($self, $params) = @_;
91 my $source = $self->schema->resultset( $params->{source} );
92 return $source->delete_all();
96 my ($self, $params) = @_;
97 my $source = $params->{source} || return;
98 my $value = $params->{value};
99 my $only_fk = $params->{only_fk} || 0;
101 my $col_values = $self->_buildColumnValues({
107 my $foreign_keys = $self->_getForeignKeys( { source => $source } );
108 for my $fk ( @$foreign_keys ) {
110 my $col_name = $fk->{keys}->[0]->{col_name};
111 if( ref( $col_values->{$col_name} ) eq 'HASH' ) {
112 $fk_value = $col_values->{$col_name};
114 elsif( defined( $col_values->{$col_name} ) ) {
118 my $fk_row = $self->build({
119 source => $fk->{source},
123 my $keys = $fk->{keys};
124 for my $key( @$keys ) {
125 $col_values->{ $key->{col_name} } = $fk_row->{ $key->{col_fk_name} };
126 $data->{ $key->{col_name} } = $fk_row;
132 $new_row = $col_values;
135 $new_row = $self->_storeColumnValues({
137 values => $col_values,
140 $new_row->{_fk} = $data if( defined( $data ) );
146 my $source = $params->{source};
147 $source =~ s|(\w+)$|$1|;
151 sub _buildColumnValues {
152 my ($self, $params) = @_;
153 my $source = _formatSource( { source => $params->{source} } );
154 my $value = $params->{value};
157 my @columns = $self->schema->source($source)->columns;
158 for my $col_name( @columns ) {
159 my $col_value = $self->_buildColumnValue({
161 column_name => $col_name,
164 $col_values->{$col_name} = $col_value if( defined( $col_value ) );
170 # rel_name => $rel_name,
171 # source => $table_name,
173 # col_name => $col_name,
174 # col_fk_name => $col_fk_name,
177 sub _getForeignKeys {
178 my ($self, $params) = @_;
179 my $source = $self->schema->source( $params->{source} );
181 my @foreign_keys = ();
182 my @relationships = $source->relationships;
183 for my $rel_name( @relationships ) {
184 my $rel_info = $source->relationship_info($rel_name);
185 if( $rel_info->{attrs}->{is_foreign_key_constraint} ) {
187 rel_name => $rel_name,
188 source => $rel_info->{source},
192 while( my ($col_fk_name, $col_name) = each(%{$rel_info->{cond}}) ) {
193 $col_name =~ s|self.(\w+)|$1|;
194 $col_fk_name =~ s|foreign.(\w+)|$1|;
196 col_name => $col_name,
197 col_fk_name => $col_fk_name,
200 $rel->{keys} = \@keys;
202 push @foreign_keys, $rel;
205 return \@foreign_keys;
208 sub _storeColumnValues {
209 my ($self, $params) = @_;
210 my $source = $params->{source};
211 my $col_values = $params->{values};
215 $new_row = $self->schema->resultset($source)->update_or_create($col_values);
217 die "$source - $@\n" if ($@);
220 $new_row = { $new_row->get_columns };
222 warn "$source - $@\n" if ($@);
226 sub _buildColumnValue {
227 my ($self, $params) = @_;
228 my $source = $params->{source};
229 my $value = $params->{value};
230 my $col_name = $params->{column_name};
231 my $col_info = $self->schema->source($source)->column_info($col_name);
234 if( exists( $value->{$col_name} ) ) {
235 $col_value = $value->{$col_name};
237 elsif( exists( $default_value->{$source}->{$col_name} ) ) {
238 $col_value = $default_value->{$source}->{$col_name};
240 elsif( not $col_info->{default_value} and not $col_info->{is_auto_increment} and not $col_info->{is_foreign_key} ) {
242 my $data_type = $col_info->{data_type};
243 $data_type =~ s| |_|;
244 $col_value = $gen_type->{$data_type}->( $self, { info => $col_info } );
246 die "The type $col_info->{data_type} is not defined\n" if ($@);
253 my ($self, $params) = @_;
254 my $data_type = $params->{info}->{data_type};
257 if( $data_type eq 'tinyint' ) {
260 elsif( $data_type eq 'smallint' ) {
263 elsif( $data_type eq 'mediumint' ) {
266 elsif( $data_type eq 'integer' ) {
269 elsif( $data_type eq 'bigint' ) {
270 $max = 9223372036854775807;
272 return int( rand($max+1) );
276 my ($self, $params) = @_;
278 if( defined( $params->{info}->{size} ) ) {
279 $max = 10 ** ($params->{info}->{size}->[0] - $params->{info}->{size}->[1]);
281 return rand($max) + 1;
285 my ($self, $params) = @_;
286 return $self->schema->storage->datetime_parser->format_datetime(DateTime->now());
290 my ($self, $params) = @_;
291 # From perldoc String::Random
292 # max: specify the maximum number of characters to return for * and other
293 # regular expression patters that don't return a fixed number of characters
294 my $regex = '[A-Za-z][A-Za-z0-9_]*';
295 my $size = $params->{info}{size};
296 if ( defined $size and $size > 1 ) {
298 } elsif ( defined $size and $size == 1 ) {
301 my $random = String::Random->new( max => $size );
302 return $random->randregex($regex);
306 my ($self, $params) = @_;
307 return $params->{info}->{extra}->{list}->[0];
311 my ($self, $params) = @_;;
318 $self->schema->txn_rollback();
324 t::lib::TestBuilder.pm - Koha module to simplify the writing of tests
328 use t::lib::TestBuilder;
330 Koha module to insert the foreign keys automatically for the tests
334 This module allows to insert automatically an entry in the database. All the database changes are wrapped in a transaction.
335 The foreign keys are created according to the DBIx::Class schema.
336 The taken values are the values by default if it is possible or randomly generated.
342 $builder = t::lib::TestBuilder->new()
344 Constructor - Begins a transaction and returns the object TestBuilder
348 $schema = $builder->schema
350 Getter - Returns the schema of DBIx::Class
354 $builder->clear({ source => $source_name })
358 =item C<$source_name> is the name of the source in the DBIx::Class schema (required)
362 Clears all the data of this source (database table)
367 source => $source_name,
374 =item C<$source_name> is the name of the source in the DBIx::Class schema (required)
376 =item C<$value> is the values for the entry (optional)
378 =item C<$only_fk> is a boolean to indicate if only the foreign keys are created (optional)
382 Inserts an entry in the database by instanciating all the foreign keys.
383 The values can be specified, the values which are not given are default values if they exists or generated randomly.
384 Returns the values of the entry as a hashref with an extra key : _fk which contains all the values of the generated foreign keys.
388 Yohann Dufour <yohann.dufour@biblibre.com>
392 Copyright 2014 - Biblibre SARL
396 This file is part of Koha.
398 Koha is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by
399 the Free Software Foundation; either version 3 of the License, or (at your option) any later version.
401 Koha is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
403 You should have received a copy of the GNU General Public License along with Koha; if not, see <http://www.gnu.org/licenses>.