diff --git a/Koha/REST/V1/RecordSources.pm b/Koha/REST/V1/RecordSources.pm index 46ba7dbc6e..b3d2320b97 100644 --- a/Koha/REST/V1/RecordSources.pm +++ b/Koha/REST/V1/RecordSources.pm @@ -81,6 +81,17 @@ sub add { openapi => $c->objects->to_api($source) ); } catch { + if ( blessed $_ and $_->isa('Koha::Exceptions::Object::DuplicateID') ) { + return $c->render( + status => 409, + openapi => { error => 'Duplicate name.' } + ); + } elsif ( blessed $_ and $_->isa('Koha::Exceptions::BadParameter') ) { + return $c->render( + status => 409, + openapi => { error => 'Name not allowed.' } + ); + } $c->unhandled_exception($_); }; } @@ -97,11 +108,29 @@ sub update { return $c->render_resource_not_found("Record source") unless $source; + if ( $source->is_system ) { + return $c->render( + status => 409, + openapi => { error => 'Cannot edit system defined value.' } + ); + } + return try { $source->set_from_api( $c->req->json )->store; $source->discard_changes; return $c->render( status => 200, openapi => $c->objects->to_api($source) ); } catch { + if ( blessed $_ and $_->isa('Koha::Exceptions::Object::DuplicateID') ) { + return $c->render( + status => 409, + openapi => { error => 'Duplicate name.' } + ); + } elsif ( blessed $_ and $_->isa('Koha::Exceptions::BadParameter') ) { + return $c->render( + status => 409, + openapi => { error => 'Name not allowed.' } + ); + } $c->unhandled_exception($_); }; } @@ -130,6 +159,14 @@ sub delete { error_code => 'cannot_delete_used', } ); + } elsif ( blessed $_ and $_->isa('Koha::Exceptions::CannotDeleteDefault') ) { + return $c->render( + status => 409, + openapi => { + error => 'Cannot delete system defined record source', + error_code => 'cannot_delete_is_system', + } + ); } $c->unhandled_exception($_); }; diff --git a/Koha/RecordSource.pm b/Koha/RecordSource.pm index 9c11f695e6..a2214c9ff8 100644 --- a/Koha/RecordSource.pm +++ b/Koha/RecordSource.pm @@ -46,6 +46,31 @@ sub usage_count { return $self->_result->biblio_metadatas->count(); } +=head3 store + +=cut + +sub store { + my ($self) = @_; + Koha::Exceptions::BadParameter->throw('* not allowed') if $self->name eq '*'; + + return $self->SUPER::store; +} + +=head3 delete + +Overridden delete method to prevent system default deletions + +=cut + +sub delete { + my ($self) = @_; + + Koha::Exceptions::CannotDeleteDefault->throw if $self->is_system; + + return $self->SUPER::delete; +} + =head2 Internal methods =head3 _type diff --git a/api/v1/swagger/definitions/record_source.yaml b/api/v1/swagger/definitions/record_source.yaml index 4bd3f05265..de52257e9b 100644 --- a/api/v1/swagger/definitions/record_source.yaml +++ b/api/v1/swagger/definitions/record_source.yaml @@ -14,6 +14,9 @@ properties: usage_count: description: Record source usage count (x-koha-embed) type: integer + is_system: + description: Is this record source system or not + type: boolean additionalProperties: false required: - name diff --git a/api/v1/swagger/paths/record_sources.yaml b/api/v1/swagger/paths/record_sources.yaml index 732368e2ae..dc197ac9f3 100644 --- a/api/v1/swagger/paths/record_sources.yaml +++ b/api/v1/swagger/paths/record_sources.yaml @@ -97,6 +97,13 @@ description: Not allowed schema: $ref: "../swagger.yaml#/definitions/error" + "409": + description: | + Conflict creating the resource. Possible `error_code` attribute values: + + * `duplicate` + schema: + $ref: "../swagger.yaml#/definitions/error" "500": description: | Internal server error. Possible `error_code` attribute values: @@ -198,6 +205,13 @@ description: Not found schema: $ref: "../swagger.yaml#/definitions/error" + "409": + description: | + Conflict creating the resource. Possible `error_code` attribute values: + + * `duplicate` + schema: + $ref: "../swagger.yaml#/definitions/error" "500": description: | Internal server error. Possible `error_code` attribute values: @@ -248,6 +262,7 @@ Conflict in deleting resource. Possible `error_code` attribute values: * `cannot_delete_used`: record source linked to a record cannot be deleted. + * `cannot_delete_is_system`: record source is system defined and cannot be deleted. schema: $ref: "../swagger.yaml#/definitions/error" "500": diff --git a/installer/data/mysql/atomicupdate/bug_35380.pl b/installer/data/mysql/atomicupdate/bug_35380.pl new file mode 100644 index 0000000000..3d112ed43d --- /dev/null +++ b/installer/data/mysql/atomicupdate/bug_35380.pl @@ -0,0 +1,43 @@ +use Modern::Perl; + +return { + bug_number => "35380", + description => + "Add new unique name to record sources, add default record sources, add is_system column to default record sources.", + up => sub { + my ($args) = @_; + my ( $dbh, $out ) = @$args{qw(dbh out)}; + + # change name to be unique + if ( !unique_key_exists( 'record_sources', 'name' ) ) { + $dbh->do( + q{ + ALTER TABLE record_sources + ADD UNIQUE KEY name (`name`) + } + ); + say $out "Added unique key 'name' "; + } + + # add column is system + unless ( column_exists( 'record_sources', 'is_system' ) ) { + $dbh->do( + q{ ALTER TABLE record_sources ADD COLUMN `is_system` TINYINT(1) NOT NULL DEFAULT 0 AFTER can_be_edited } + ); + say $out "Added column 'record_sources.is_system'"; + } + + $dbh->do( + q{ + INSERT IGNORE INTO record_sources ( name, can_be_edited, is_system ) + VALUES + ('batchmod', 1, 1 ), + ('intranet', 1, 1 ), + ('batchimport', 1, 1 ), + ('z3950', 1, 1 ), + ('bulkmarcimport', 1, 1 ), + ('import_lexile', 1, 1 ) + } + ); + }, +}; diff --git a/installer/data/mysql/kohastructure.sql b/installer/data/mysql/kohastructure.sql index 00e86d535e..ada8472dcc 100644 --- a/installer/data/mysql/kohastructure.sql +++ b/installer/data/mysql/kohastructure.sql @@ -5679,7 +5679,9 @@ CREATE TABLE `record_sources` ( `record_source_id` int(11) NOT NULL AUTO_INCREMENT COMMENT 'Primary key for the `record_sources` table', `name` text NOT NULL COMMENT 'User defined name for the record source', `can_be_edited` tinyint(1) NOT NULL DEFAULT 0 COMMENT 'If records from this source can be edited', - PRIMARY KEY (`record_source_id`) + `is_system` tinyint(1) NOT NULL DEFAULT 0, + PRIMARY KEY (`record_source_id`), + UNIQUE KEY `name` (`name`(191)) ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci; /*!40101 SET character_set_client = @saved_cs_client */;