Repository: NatLibFi/Annif (language: python)

Issue:
REST API root resource with version information
The Annif REST API currently doesn't have a root resource. A URL such as http://127.0.0.1:5000/v1/ will give a 404 response.

The API could provide a root resource with some basic information about the API service, including the version of Annif, as a JSON object. Something like this:

```json
{ "title": "Annif REST API", "version": "0.60.0" }
```

One fancier way to do this would be to implement the [JSON Home proposal](https://datatracker.ietf.org/doc/html/draft-nottingham-json-home-06). See [this](https://docs.openstack.org/keystone/rocky/user/json_home.html) for a practical example and [this](https://apievangelist.com/2017/08/03/api-discovery-using-json-home/) for some easy to understand examples. But this may be overkill for the purpose of Annif and the JSON Home spec doesn't seem to be widely used.

Elasticsearch also provides information about the API in a root object as JSON. You can see how it looks (without installing it for yourself) in [this](https://community.progress.com/s/article/what-version-of-elasticsearch-do-i-have-installed) post.

The Annif version information, once exposed via the REST API, could be shown in the Finto AI user interface - see https://github.com/NatLibFi/FintoAI/issues/8


Discussion / hints:

Fix patch:
diff --git a/annif/openapi/annif.yaml b/annif/openapi/annif.yaml
index 4b2824575..7d39e1d1f 100644
--- a/annif/openapi/annif.yaml
+++ b/annif/openapi/annif.yaml
@@ -5,6 +5,19 @@ info:
 servers:
 - url: /v1
 paths:
+  /:
+    get:
+      tags:
+      - API information
+      summary: get basic information about the API service
+      operationId: annif.rest.show_info
+      responses:
+        200:
+          description: successful operation
+          content:
+            application/json:
+              schema:
+                $ref: '#/components/schemas/ApiInfo'
   /projects:
     get:
       tags:
@@ -136,6 +149,19 @@ paths:
       x-codegen-request-body-name: documents
 components:
   schemas:
+    ApiInfo:
+      required:
+      - title
+      - version
+      type: object
+      properties:
+        title:
+          type: string
+          example: Annif REST API
+        version:
+          type: string
+          example: 0.60.0
+      description: REST API information
     ProjectBackend:
       required:
       - backend_id
diff --git a/annif/rest.py b/annif/rest.py
index 5d000b1c9..eb383070c 100644
--- a/annif/rest.py
+++ b/annif/rest.py
@@ -1,6 +1,8 @@
 """Definitions for REST API operations. These are wired via Connexion to
 methods defined in the Swagger specification."""
 
+import importlib
+
 import connexion
 
 import annif.registry
@@ -29,6 +31,12 @@ def server_error(err):
     )
 
 
+def show_info():
+    """return version of annif and a title for the api according to Swagger spec"""
+
+    return {"title": "Annif REST API", "version": importlib.metadata.version("annif")}
+
+
 def list_projects():
     """return a dict with projects formatted according to Swagger spec"""
 


Test patch:
diff --git a/tests/test_rest.py b/tests/test_rest.py
index 462eda568..4c9e1d2e7 100644
--- a/tests/test_rest.py
+++ b/tests/test_rest.py
@@ -1,5 +1,7 @@
 """Unit tests for REST API backend code in Annif"""
 
+import importlib
+
 import annif.rest
 
 
@@ -17,6 +19,13 @@ def test_rest_list_projects(app):
         assert "ensemble" in project_ids
 
 
+def test_rest_show_info(app):
+    with app.app_context():
+        result = annif.rest.show_info()
+        version = importlib.metadata.version("annif")
+        assert result == {"title": "Annif REST API", "version": version}
+
+
 def test_rest_show_project_public(app):
     # public projects should be accessible via REST
     with app.app_context():