From 258e663180b63c55b6e3bb815136f7656fac226d Mon Sep 17 00:00:00 2001 From: Samson Akol Date: Thu, 1 Feb 2024 14:13:40 +0300 Subject: [PATCH 1/4] Adds level property to the ancestors schema definition --- js/EmbedTopicsRequest.js | 9 ++++++++- le_utils/constants/embed_topics_request.py | 11 ++++++++++- spec/schema-embed_topics_request.json | 9 ++++++++- 3 files changed, 26 insertions(+), 3 deletions(-) diff --git a/js/EmbedTopicsRequest.js b/js/EmbedTopicsRequest.js index f5de42e..f9400c1 100644 --- a/js/EmbedTopicsRequest.js +++ b/js/EmbedTopicsRequest.js @@ -14,7 +14,14 @@ export const SCHEMA = { "type": "array", "description": "The ancestors of the topic, in order, from the parent to the root", "items": { - "$ref": "#/definitions/topic" + "$ref": "#/definitions/topic", + "properties": { + "level": { + "type": "integer", + "description": "The level of the ancestor, where the parent is 1 and the root is the highest level" + } + }, + "required": ["level"] } }, "language": { diff --git a/le_utils/constants/embed_topics_request.py b/le_utils/constants/embed_topics_request.py index 8b54b63..b902066 100644 --- a/le_utils/constants/embed_topics_request.py +++ b/le_utils/constants/embed_topics_request.py @@ -19,7 +19,16 @@ "ancestors": { "type": "array", "description": "The ancestors of the topic, in order, from the parent to the root", - "items": {"$ref": "#/definitions/topic"}, + "items": { + "$ref": "#/definitions/topic", + "properties": { + "level": { + "type": "integer", + "description": "The level of the ancestor, where the parent is 1 and the root is the highest level", + } + }, + "required": ["level"], + }, }, "language": { "type": "string", diff --git a/spec/schema-embed_topics_request.json b/spec/schema-embed_topics_request.json index e721f6e..693a3d7 100644 --- a/spec/schema-embed_topics_request.json +++ b/spec/schema-embed_topics_request.json @@ -9,7 +9,14 @@ "type": "array", "description": "The ancestors of the topic, in order, from the parent to the root", "items": { - "$ref": "#/definitions/topic" + "$ref": "#/definitions/topic", + "properties": { + "level": { + "type": "integer", + "description": "The level of the ancestor, where the parent is 1 and the root is the highest level" + } + }, + "required": ["level"] } }, "language": { From b890010943d3c5c3dbdc7ae36336f0fdb58e7bb7 Mon Sep 17 00:00:00 2001 From: Samson Akol Date: Thu, 1 Feb 2024 14:16:01 +0300 Subject: [PATCH 2/4] bumbs version --- js/package.json | 2 +- setup.py | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/js/package.json b/js/package.json index a07f5cf..08b8d4d 100644 --- a/js/package.json +++ b/js/package.json @@ -27,5 +27,5 @@ "scripts": { "test": "echo \"Error: no test specified\" && exit 1" }, - "version": "0.2.4" + "version": "0.2.5" } \ No newline at end of file diff --git a/setup.py b/setup.py index 7ec2e87..e6e4f7e 100644 --- a/setup.py +++ b/setup.py @@ -12,7 +12,7 @@ setup( name="le-utils", packages=find_packages(), - version="0.2.4", + version="0.2.5", description="LE-Utils contains shared constants used in Kolibri, Ricecooker, and Kolibri Studio.", long_description=long_description, long_description_content_type="text/markdown", From b6c558b26abca642bc3caa9dea99afaee683880d Mon Sep 17 00:00:00 2001 From: Samson Akol Date: Thu, 1 Feb 2024 19:36:45 +0300 Subject: [PATCH 3/4] Adds level property to the ancestors schema definition --- js/EmbedTopicsRequest.js | 72 ++++++++++++++++------ le_utils/constants/embed_topics_request.py | 55 ++++++++++------- spec/schema-embed_topics_request.json | 72 ++++++++++++++++------ tests/test_schemas.py | 33 +++++++++- 4 files changed, 171 insertions(+), 61 deletions(-) diff --git a/js/EmbedTopicsRequest.js b/js/EmbedTopicsRequest.js index f9400c1..5556619 100644 --- a/js/EmbedTopicsRequest.js +++ b/js/EmbedTopicsRequest.js @@ -10,41 +10,75 @@ export const SCHEMA = { "description": "Schema for embed topics requests received by RayServe", "additionalProperties": false, "definitions": { - "ancestors": { - "type": "array", - "description": "The ancestors of the topic, in order, from the parent to the root", - "items": { - "$ref": "#/definitions/topic", - "properties": { - "level": { - "type": "integer", - "description": "The level of the ancestor, where the parent is 1 and the root is the highest level" - } - }, - "required": ["level"] - } + "id": { + "type": "string", + "description": "The ID of the topic content node on Studio" + }, + "title": { + "type": "string", + "description": "The title of the topic" + }, + "description": { + "type": "string", + "description": "The description of the topic" }, "language": { "type": "string", "description": "Language code from https://github.com/learningequality/le-utils/blob/main/le_utils/resources/languagelookup.json", "pattern": "^[a-z]{2,3}(?:-[a-zA-Z]+)?$" }, + "level": { + "type": "integer", + "description": "The level of the ancestor, where the parent is 1 and the root is the highest level" + }, + "ancestor": { + "type": "object", + "description": "An ancestor in the tree structure", + "additionalProperties": false, + "properties": { + "id": { + "$ref": "#/definitions/id" + }, + "title": { + "$ref": "#/definitions/title" + }, + "description": { + "$ref": "#/definitions/description" + }, + "language": { + "$ref": "#/definitions/language" + }, + "level": { + "$ref": "#/definitions/level" + } + }, + "required": [ + "id", + "title", + "description", + "level" + ] + }, + "ancestors": { + "type": "array", + "description": "The ancestors of the topic, in order, from the parent to the root", + "items": { + "$ref": "#/definitions/ancestor" + } + }, "topic": { "type": "object", "description": "A topic in the tree structure", "additionalProperties": false, "properties": { "id": { - "type": "string", - "description": "The ID of the topic content node on Studio" + "$ref": "#/definitions/id" }, "title": { - "type": "string", - "description": "The title of the topic" + "$ref": "#/definitions/title" }, "description": { - "type": "string", - "description": "The description of the topic" + "$ref": "#/definitions/description" }, "language": { "$ref": "#/definitions/language" diff --git a/le_utils/constants/embed_topics_request.py b/le_utils/constants/embed_topics_request.py index b902066..fb92359 100644 --- a/le_utils/constants/embed_topics_request.py +++ b/le_utils/constants/embed_topics_request.py @@ -16,39 +16,50 @@ "description": "Schema for embed topics requests received by RayServe", "additionalProperties": False, "definitions": { - "ancestors": { - "type": "array", - "description": "The ancestors of the topic, in order, from the parent to the root", - "items": { - "$ref": "#/definitions/topic", - "properties": { - "level": { - "type": "integer", - "description": "The level of the ancestor, where the parent is 1 and the root is the highest level", - } - }, - "required": ["level"], - }, + "id": { + "type": "string", + "description": "The ID of the topic content node on Studio", + }, + "title": {"type": "string", "description": "The title of the topic"}, + "description": { + "type": "string", + "description": "The description of the topic", }, "language": { "type": "string", "description": "Language code from https://github.com/learningequality/le-utils/blob/main/le_utils/resources/languagelookup.json", "pattern": "^[a-z]{2,3}(?:-[a-zA-Z]+)?$", }, + "level": { + "type": "integer", + "description": "The level of the ancestor, where the parent is 1 and the root is the highest level", + }, + "ancestor": { + "type": "object", + "description": "An ancestor in the tree structure", + "additionalProperties": False, + "properties": { + "id": {"$ref": "#/definitions/id"}, + "title": {"$ref": "#/definitions/title"}, + "description": {"$ref": "#/definitions/description"}, + "language": {"$ref": "#/definitions/language"}, + "level": {"$ref": "#/definitions/level"}, + }, + "required": ["id", "title", "description", "level"], + }, + "ancestors": { + "type": "array", + "description": "The ancestors of the topic, in order, from the parent to the root", + "items": {"$ref": "#/definitions/ancestor"}, + }, "topic": { "type": "object", "description": "A topic in the tree structure", "additionalProperties": False, "properties": { - "id": { - "type": "string", - "description": "The ID of the topic content node on Studio", - }, - "title": {"type": "string", "description": "The title of the topic"}, - "description": { - "type": "string", - "description": "The description of the topic", - }, + "id": {"$ref": "#/definitions/id"}, + "title": {"$ref": "#/definitions/title"}, + "description": {"$ref": "#/definitions/description"}, "language": {"$ref": "#/definitions/language"}, "ancestors": {"$ref": "#/definitions/ancestors"}, }, diff --git a/spec/schema-embed_topics_request.json b/spec/schema-embed_topics_request.json index 693a3d7..ed9f91a 100644 --- a/spec/schema-embed_topics_request.json +++ b/spec/schema-embed_topics_request.json @@ -5,41 +5,75 @@ "description": "Schema for embed topics requests received by RayServe", "additionalProperties": false, "definitions": { - "ancestors": { - "type": "array", - "description": "The ancestors of the topic, in order, from the parent to the root", - "items": { - "$ref": "#/definitions/topic", - "properties": { - "level": { - "type": "integer", - "description": "The level of the ancestor, where the parent is 1 and the root is the highest level" - } - }, - "required": ["level"] - } + "id": { + "type": "string", + "description": "The ID of the topic content node on Studio" + }, + "title": { + "type": "string", + "description": "The title of the topic" + }, + "description": { + "type": "string", + "description": "The description of the topic" }, "language": { "type": "string", "description": "Language code from https://github.com/learningequality/le-utils/blob/main/le_utils/resources/languagelookup.json", "pattern": "^[a-z]{2,3}(?:-[a-zA-Z]+)?$" }, + "level": { + "type": "integer", + "description": "The level of the ancestor, where the parent is 1 and the root is the highest level" + }, + "ancestor": { + "type": "object", + "description": "An ancestor in the tree structure", + "additionalProperties": false, + "properties": { + "id": { + "$ref": "#/definitions/id" + }, + "title": { + "$ref": "#/definitions/title" + }, + "description": { + "$ref": "#/definitions/description" + }, + "language": { + "$ref": "#/definitions/language" + }, + "level": { + "$ref": "#/definitions/level" + } + }, + "required": [ + "id", + "title", + "description", + "level" + ] + }, + "ancestors": { + "type": "array", + "description": "The ancestors of the topic, in order, from the parent to the root", + "items": { + "$ref": "#/definitions/ancestor" + } + }, "topic": { "type": "object", "description": "A topic in the tree structure", "additionalProperties": false, "properties": { "id": { - "type": "string", - "description": "The ID of the topic content node on Studio" + "$ref": "#/definitions/id" }, "title": { - "type": "string", - "description": "The title of the topic" + "$ref": "#/definitions/title" }, "description": { - "type": "string", - "description": "The description of the topic" + "$ref": "#/definitions/description" }, "language": { "$ref": "#/definitions/language" diff --git a/tests/test_schemas.py b/tests/test_schemas.py index d8f3f34..82c6301 100644 --- a/tests/test_schemas.py +++ b/tests/test_schemas.py @@ -272,7 +272,7 @@ def test_completion_criteria__reference__invalid(): @pytest.mark.skipif(jsonschema is None, reason="jsonschema package is unavailable") -def test_embed__topics__valid(): +def test_embed__topics__without__ancestors__valid(): with _assert_not_raises(jsonschema.ValidationError): validate_embed_topics_request( { @@ -293,6 +293,37 @@ def test_embed__topics__valid(): ) +@pytest.mark.skipif(jsonschema is None, reason="jsonschema package is unavailable") +def test_embed__topics__with__ancestors__valid(): + with _assert_not_raises(jsonschema.ValidationError): + validate_embed_topics_request( + { + "topics": [ + { + "id": "456", + "title": "Target topic", + "description": "Target description", + "language": "en", + "ancestors": [ + { + "id": "456", + "title": "Parent topic", + "description": "Parent description", + "language": "en", + "level": 1, + } + ], + } + ], + "metadata": { + "channel_id": "000", + "channel_title": "Channel title", + "some_additional_field": "some_random_value", + }, + } + ) + + @pytest.mark.skipif(jsonschema is None, reason="jsonschema package is unavailable") def test_embed__content__valid(): with _assert_not_raises(jsonschema.ValidationError): From 55fe5d4165cc09962282ed928e388be4f40d02e0 Mon Sep 17 00:00:00 2001 From: Samson Akol Date: Fri, 2 Feb 2024 02:08:59 +0300 Subject: [PATCH 4/4] clarifies the level property --- js/EmbedTopicsRequest.js | 4 ++-- le_utils/constants/embed_topics_request.py | 4 ++-- spec/schema-embed_topics_request.json | 4 ++-- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/js/EmbedTopicsRequest.js b/js/EmbedTopicsRequest.js index 5556619..0ba9c52 100644 --- a/js/EmbedTopicsRequest.js +++ b/js/EmbedTopicsRequest.js @@ -29,7 +29,7 @@ export const SCHEMA = { }, "level": { "type": "integer", - "description": "The level of the ancestor, where the parent is 1 and the root is the highest level" + "description": "The level of the ancestor, where the root is 0 and the parent is the highest level" }, "ancestor": { "type": "object", @@ -61,7 +61,7 @@ export const SCHEMA = { }, "ancestors": { "type": "array", - "description": "The ancestors of the topic, in order, from the parent to the root", + "description": "The ancestors of the topic. Please see 'level' in the ancestor schema for more information", "items": { "$ref": "#/definitions/ancestor" } diff --git a/le_utils/constants/embed_topics_request.py b/le_utils/constants/embed_topics_request.py index fb92359..7158785 100644 --- a/le_utils/constants/embed_topics_request.py +++ b/le_utils/constants/embed_topics_request.py @@ -32,7 +32,7 @@ }, "level": { "type": "integer", - "description": "The level of the ancestor, where the parent is 1 and the root is the highest level", + "description": "The level of the ancestor, where the root is 0 and the parent is the highest level", }, "ancestor": { "type": "object", @@ -49,7 +49,7 @@ }, "ancestors": { "type": "array", - "description": "The ancestors of the topic, in order, from the parent to the root", + "description": "The ancestors of the topic. Please see 'level' in the ancestor schema for more information", "items": {"$ref": "#/definitions/ancestor"}, }, "topic": { diff --git a/spec/schema-embed_topics_request.json b/spec/schema-embed_topics_request.json index ed9f91a..8b259db 100644 --- a/spec/schema-embed_topics_request.json +++ b/spec/schema-embed_topics_request.json @@ -24,7 +24,7 @@ }, "level": { "type": "integer", - "description": "The level of the ancestor, where the parent is 1 and the root is the highest level" + "description": "The level of the ancestor, where the root is 0 and the parent is the highest level" }, "ancestor": { "type": "object", @@ -56,7 +56,7 @@ }, "ancestors": { "type": "array", - "description": "The ancestors of the topic, in order, from the parent to the root", + "description": "The ancestors of the topic. Please see 'level' in the ancestor schema for more information", "items": { "$ref": "#/definitions/ancestor" }