Bug 41107: Add /status/version API endpoint

Adds a new REST API endpoint to retrieve Koha version information.

This implementation includes:
- Koha::Status class for instance status information
- /status/version endpoint returning structured version data
- OpenAPI specification with koha_version definition
- REST controller for handling the endpoint

The returned version object includes:
- version: full version string (e.g., '25.06.00.029')
- major: major version number
- minor: minor version number
- release: major.minor version
- maintenance: major.minor.maintenance version
- development: development version (if applicable)

This prepares the foundation for a future /status endpoint that will
include all information displayed in the about page.

To test:
1. Apply the patch
2. Run:
   $ ktd --shell
  k$ yarn api:bundle
3. Run the tests:
  k$ prove t/Koha/Status.t \
           t/db_dependent/api/v1/status.t
=> SUCCESS: Tests pass!
4. Sign off :-D

Signed-off-by: David Nind <david@davidnind.com>
Signed-off-by: Kyle M Hall <kyle@bywatersolutions.com>
Signed-off-by: Martin Renvoize <martin.renvoize@openfifth.co.uk>
This commit is contained in:
Tomás Cohen Arazi 2025-11-05 10:20:48 -03:00 committed by Martin Renvoize
parent 7929a1198e
commit 68c8b8f13f
No known key found for this signature in database
GPG Key ID: 2D86E0EAEC83711B
7 changed files with 329 additions and 0 deletions

56
Koha/REST/V1/Status.pm Normal file
View File

@ -0,0 +1,56 @@
package Koha::REST::V1::Status;
# This file is part of Koha.
#
# Koha is free software; you can redistribute it and/or modify it
# under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 3 of the License, or
# (at your option) any later version.
#
# 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.
#
# You should have received a copy of the GNU General Public License
# along with Koha; if not, see <https://www.gnu.org/licenses>.
use Modern::Perl;
use Mojo::Base 'Mojolicious::Controller';
use Try::Tiny qw( catch try );
use Koha::Status;
=head1 NAME
Koha::REST::V1::Status - Controller library for status related API endpoints
=head1 API
=head2 Methods
=head3 version
Controller method that returns Koha version information
=cut
sub version {
my $c = shift->openapi->valid_input or return;
return try {
my $status = Koha::Status->new();
my $version_info = $status->version();
return $c->render(
status => 200,
openapi => $version_info
);
} catch {
$c->unhandled_exception($_);
};
}
1;

85
Koha/Status.pm Normal file
View File

@ -0,0 +1,85 @@
package Koha::Status;
# This file is part of Koha.
#
# Koha is free software; you can redistribute it and/or modify it
# under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 3 of the License, or
# (at your option) any later version.
#
# 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.
#
# You should have received a copy of the GNU General Public License
# along with Koha; if not, see <https://www.gnu.org/licenses>.
use Modern::Perl;
use Koha;
=head1 NAME
Koha::Status - Koha instance status information
=head1 SYNOPSIS
use Koha::Status;
my $status = Koha::Status->new();
my $version_info = $status->version();
=head1 DESCRIPTION
This class provides methods to retrieve status information about the Koha instance.
=head1 METHODS
=head2 new
my $status = Koha::Status->new();
Constructor.
=cut
sub new {
my ($class) = @_;
return bless {}, $class;
}
=head2 version
my $version_info = $status->version();
Returns version information in a structured format similar to
Koha::Template::Plugin::Koha->Version but with additional metadata.
Returns a hashref with the following structure:
- version: full version string
- major: major version number
- minor: minor version number
- release: major.minor version
- maintenance: major.minor.maintenance version
- development: development version (if applicable)
=cut
sub version {
my ($self) = @_;
my $version_string = Koha::version();
my ( $major, $minor, $maintenance, $development ) = split( '\.', $version_string );
return {
version => $version_string,
major => $major,
minor => $minor,
release => $major . "." . $minor,
maintenance => $major . "." . $minor . "." . $maintenance,
development => ( $development && $development ne '000' ) ? $development : undef,
};
}
1;

View File

@ -0,0 +1,30 @@
---
type: object
properties:
version:
type: string
description: Full version string
example: "25.06.00.029"
major:
type: string
description: Major version number
example: "25"
minor:
type: string
description: Minor version number
example: "06"
release:
type: string
description: Release version (major.minor)
example: "25.06"
maintenance:
type: string
description: Maintenance version (major.minor.maintenance)
example: "25.06.00"
development:
type:
- string
- "null"
description: Development version number (null if not a development version)
example: "029"
additionalProperties: false

View File

@ -0,0 +1,44 @@
---
"/status/version":
get:
x-mojo-to: Status#version
operationId: getStatusVersion
tags:
- status
summary: Get Koha version information
description: |
Returns version information for this Koha instance including major, minor,
maintenance and development version numbers.
produces:
- application/json
responses:
"200":
description: A suggestion
schema:
$ref: "../swagger.yaml#/definitions/koha_version"
"400":
description: Bad request
schema:
$ref: "../swagger.yaml#/definitions/error"
"403":
description: Access forbidden
schema:
$ref: "../swagger.yaml#/definitions/error"
"404":
description: Suggestion not found
schema:
$ref: "../swagger.yaml#/definitions/error"
"500":
description: |
Internal server error. Possible `error_code` attribute values:
* `internal_server_error`
schema:
$ref: "../swagger.yaml#/definitions/error"
"503":
description: Under maintenance
schema:
$ref: "../swagger.yaml#/definitions/error"
x-koha-authorization:
permissions:
catalogue: 1

View File

@ -124,6 +124,8 @@ definitions:
$ref: ./definitions/import_batch_profiles.yaml
import_record_match:
$ref: ./definitions/import_record_match.yaml
koha_version:
$ref: definitions/koha_version.yaml
record_source:
$ref: ./definitions/record_source.yaml
invoice:
@ -637,6 +639,8 @@ paths:
$ref: ./paths/transfer_limits.yaml#/~1transfer_limits~1batch
"/transfer_limits/{limit_id}":
$ref: "./paths/transfer_limits.yaml#/~1transfer_limits~1{limit_id}"
/status/version:
$ref: ./paths/status.yaml#/~1status~1version
parameters:
advancededitormacro_id_pp:
description: Advanced editor macro internal identifier
@ -1409,6 +1413,9 @@ tags:
- description: "Manage file transport configurations\n"
name: file_transports
x-displayName: File transports
- description: "System status\n"
name: status
x-displayName: Status
- description: "Manage tickets\n"
name: tickets
x-displayName: Tickets

49
t/Koha/Status.t Executable file
View File

@ -0,0 +1,49 @@
#!/usr/bin/perl
# This file is part of Koha.
#
# Koha is free software; you can redistribute it and/or modify it
# under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 3 of the License, or
# (at your option) any later version.
#
# 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.
#
# You should have received a copy of the GNU General Public License
# along with Koha; if not, see <https://www.gnu.org/licenses>.
use Modern::Perl;
use Test::More tests => 3;
use Test::NoWarnings;
use Koha::Status;
subtest 'new' => sub {
plan tests => 1;
my $status = Koha::Status->new();
isa_ok( $status, 'Koha::Status', 'Constructor returns correct object type' );
};
subtest 'version' => sub {
plan tests => 7;
my $status = Koha::Status->new();
my $version_info = $status->version();
is( ref($version_info), 'HASH', 'version() returns a hashref' );
# Check required fields exist
ok( exists $version_info->{version}, 'version field exists' );
ok( exists $version_info->{major}, 'major field exists' );
ok( exists $version_info->{minor}, 'minor field exists' );
ok( exists $version_info->{release}, 'release field exists' );
ok( exists $version_info->{maintenance}, 'maintenance field exists' );
# Check version format and consistency
like( $version_info->{version}, qr/^\d+\.\d+\.\d+\.\d+$/, 'version has correct format' );
};

58
t/db_dependent/api/v1/status.t Executable file
View File

@ -0,0 +1,58 @@
#!/usr/bin/env perl
# This file is part of Koha.
#
# Koha is free software; you can redistribute it and/or modify it
# under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 3 of the License, or
# (at your option) any later version.
#
# 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.
#
# You should have received a copy of the GNU General Public License
# along with Koha; if not, see <https://www.gnu.org/licenses>.
use Modern::Perl;
use Test::NoWarnings;
use Test::More tests => 2;
use Test::Mojo;
use t::lib::TestBuilder;
use t::lib::Mocks;
use Koha;
use Koha::Database;
my $schema = Koha::Database->new->schema;
my $builder = t::lib::TestBuilder->new;
my $t = Test::Mojo->new('Koha::REST::V1');
t::lib::Mocks::mock_preference( 'RESTBasicAuth', 1 );
subtest 'version() tests' => sub {
plan tests => 8;
$schema->storage->txn_begin;
my $librarian = $builder->build_object(
{
class => 'Koha::Patrons',
value => { flags => 2**2 }, # catalogue flag = 2
}
);
my $password = 'thePassword123';
$librarian->set_password( { password => $password, skip_validation => 1 } );
my $userid = $librarian->userid;
$t->get_ok("//$userid:$password@/api/v1/status/version")->status_is(200)->json_is( '/version' => Koha::version() )
->json_has('/major')->json_has('/minor')->json_has('/release')->json_has('/maintenance')
->json_like( '/version' => qr/^\d+\.\d+\.\d+\.\d+$/ );
$schema->storage->txn_rollback;
};