From 64ae0c34447db020c2fb133bd43966e45666878b Mon Sep 17 00:00:00 2001 From: cef Date: Tue, 16 Jul 2024 12:24:04 +0200 Subject: [PATCH] feat: create xblocks feat: add HTML/CSS support fix: minor changes fix: remove the extra space around the code editor * extra space on right was caused by the 100vh for width instead of 100vw * on the left, the default lineNumbersMinChars value of 5 was causing a huge margin, along with the code folding gutter. See: https://github.com/suren-atoyan/monaco-react/discussions/303 fix: add the border and the box showdow to match mockup styling fix: scroll just the tab content instead, not parent container fix: make the tab switches smaller to match mockups fix: submission button styling and border fix: added multiple fixes and tweaks fix: added multiple fixes and tweaks fix: styling adjustments for the prog language badge --- .../workflows/upgrade-python-requirements.yml | 29 - Makefile | 98 +++ README.md | 38 ++ ai_eval/__init__.py | 6 + ai_eval/base.py | 146 +++++ ai_eval/coding_ai_eval.py | 251 ++++++++ ai_eval/llm.py | 65 ++ ai_eval/shortanswer.py | 152 +++++ ai_eval/static/README.txt | 19 + ai_eval/static/css/coding_ai_eval.css | 139 +++++ ai_eval/static/css/shortanswer.css | 127 ++++ ai_eval/static/html/marked-iframe.html | 7 + ai_eval/static/js/src/coding_ai_eval.js | 215 +++++++ ai_eval/static/js/src/shortanswer.js | 105 ++++ ai_eval/static/js/src/utils.js | 41 ++ ai_eval/templates/coding_ai_eval.html | 31 + ai_eval/templates/monaco.html | 22 + ai_eval/templates/shortanswer.html | 26 + ai_eval/tests/__init__.py | 0 ai_eval/tests/test_ai_eval.py | 56 ++ ai_eval/translations/README.txt | 4 + ai_eval/utils.py | 84 +++ docs/coding-xblock-ai-feedback.png | Bin 0 -> 60677 bytes docs/coding-xblock-html.png | Bin 0 -> 92471 bytes docs/coding-xblock.png | Bin 0 -> 48267 bytes docs/shortanswer-xblock.png | Bin 0 -> 57498 bytes pylintrc | 389 ++++++++++++ pylintrc_tweaks | 10 + requirements/base.in | 6 + requirements/base.txt | 221 +++++++ requirements/ci.in | 4 + requirements/ci.txt | 38 ++ requirements/constraints.txt | 17 + requirements/dev.in | 6 + requirements/dev.txt | 579 ++++++++++++++++++ requirements/pip-tools.in | 5 + requirements/pip-tools.txt | 34 + requirements/pip.in | 6 + requirements/pip.txt | 14 + requirements/private.readme | 15 + requirements/quality.in | 7 + requirements/quality.txt | 490 +++++++++++++++ requirements/test.in | 15 + requirements/test.txt | 404 ++++++++++++ requirements/workbench.txt | 0 setup.py | 43 ++ 46 files changed, 3935 insertions(+), 29 deletions(-) delete mode 100644 .github/workflows/upgrade-python-requirements.yml create mode 100644 Makefile create mode 100644 README.md create mode 100644 ai_eval/__init__.py create mode 100644 ai_eval/base.py create mode 100644 ai_eval/coding_ai_eval.py create mode 100644 ai_eval/llm.py create mode 100644 ai_eval/shortanswer.py create mode 100644 ai_eval/static/README.txt create mode 100644 ai_eval/static/css/coding_ai_eval.css create mode 100644 ai_eval/static/css/shortanswer.css create mode 100644 ai_eval/static/html/marked-iframe.html create mode 100644 ai_eval/static/js/src/coding_ai_eval.js create mode 100644 ai_eval/static/js/src/shortanswer.js create mode 100644 ai_eval/static/js/src/utils.js create mode 100644 ai_eval/templates/coding_ai_eval.html create mode 100644 ai_eval/templates/monaco.html create mode 100644 ai_eval/templates/shortanswer.html create mode 100644 ai_eval/tests/__init__.py create mode 100644 ai_eval/tests/test_ai_eval.py create mode 100644 ai_eval/translations/README.txt create mode 100644 ai_eval/utils.py create mode 100644 docs/coding-xblock-ai-feedback.png create mode 100644 docs/coding-xblock-html.png create mode 100644 docs/coding-xblock.png create mode 100644 docs/shortanswer-xblock.png create mode 100644 pylintrc create mode 100644 pylintrc_tweaks create mode 100644 requirements/base.in create mode 100644 requirements/base.txt create mode 100644 requirements/ci.in create mode 100644 requirements/ci.txt create mode 100644 requirements/constraints.txt create mode 100644 requirements/dev.in create mode 100644 requirements/dev.txt create mode 100644 requirements/pip-tools.in create mode 100644 requirements/pip-tools.txt create mode 100644 requirements/pip.in create mode 100644 requirements/pip.txt create mode 100644 requirements/private.readme create mode 100644 requirements/quality.in create mode 100644 requirements/quality.txt create mode 100644 requirements/test.in create mode 100644 requirements/test.txt create mode 100644 requirements/workbench.txt create mode 100644 setup.py diff --git a/.github/workflows/upgrade-python-requirements.yml b/.github/workflows/upgrade-python-requirements.yml deleted file mode 100644 index d2aef30..0000000 --- a/.github/workflows/upgrade-python-requirements.yml +++ /dev/null @@ -1,29 +0,0 @@ -name: Upgrade Python Requirements - -on: - schedule: - - cron: "0 0 * * 1" - workflow_dispatch: - inputs: - branch: - description: Target branch against which to create requirements PR - required: true - default: master - -jobs: - call-upgrade-python-requirements-workflow: - uses: openedx/.github/.github/workflows/upgrade-python-requirements.yml@master - # Do not run on forks - if: github.repository_owner == 'open-craft' - with: - branch: ${{ github.event.inputs.branch || 'master' }} - # optional parameters below; fill in if you'd like github or email notifications - # user_reviewers: "" - # team_reviewers: "" - # email_address: "" - # send_success_notification: false - secrets: - requirements_bot_github_token: ${{ secrets.REQUIREMENTS_BOT_GITHUB_TOKEN }} - requirements_bot_github_email: ${{ secrets.REQUIREMENTS_BOT_GITHUB_EMAIL }} - edx_smtp_username: ${{ secrets.EDX_SMTP_USERNAME }} - edx_smtp_password: ${{ secrets.EDX_SMTP_PASSWORD }} diff --git a/Makefile b/Makefile new file mode 100644 index 0000000..c992e2f --- /dev/null +++ b/Makefile @@ -0,0 +1,98 @@ +.PHONY: clean help compile_translations dummy_translations extract_translations detect_changed_source_translations \ + build_dummy_translations validate_translations check_translations_up_to_date \ + requirements selfcheck test test.python test.unit test.quality upgrade + +.DEFAULT_GOAL := help + +WORKING_DIR := ai_eval +JS_TARGET := $(WORKING_DIR)/public/js/translations +EXTRACT_DIR := $(WORKING_DIR)/conf/locale/en/LC_MESSAGES +EXTRACTED_DJANGO_PARTIAL := $(EXTRACT_DIR)/django-partial.po +EXTRACTED_DJANGOJS_PARTIAL := $(EXTRACT_DIR)/djangojs-partial.po +EXTRACTED_DJANGO := $(EXTRACT_DIR)/django.po + +help: ## display this help message + @echo "Please use \`make ' where is one of" + @perl -nle'print $& if m{^[a-zA-Z_-]+:.*?## .*$$}' $(MAKEFILE_LIST) | sort | awk 'BEGIN {FS = ":.*?## "}; {printf "\033[36m %-25s\033[0m %s\n", $$1, $$2}' + +clean: ## remove generated byte code, coverage reports, and build artifacts + find . -name '__pycache__' -exec rm -rf {} + + find . -name '*.pyc' -exec rm -f {} + + find . -name '*.pyo' -exec rm -f {} + + find . -name '*~' -exec rm -f {} + + rm -fr build/ + rm -fr dist/ + rm -fr *.egg-info + +## Localization targets + +extract_translations: ## extract strings to be translated, outputting .po files + cd $(WORKING_DIR) && i18n_tool extract + mv $(EXTRACTED_DJANGO_PARTIAL) $(EXTRACTED_DJANGO) + # Safely concatenate djangojs if it exists. The file will exist in this repo, but we're trying to follow a pattern + # between all repositories that use i18n_tool + if test -f $(EXTRACTED_DJANGOJS_PARTIAL); then \ + msgcat $(EXTRACTED_DJANGO) $(EXTRACTED_DJANGOJS_PARTIAL) -o $(EXTRACTED_DJANGO) && \ + rm $(EXTRACTED_DJANGOJS_PARTIAL); \ + fi + sed -i'' -e 's/nplurals=INTEGER/nplurals=2/' $(EXTRACTED_DJANGO) + sed -i'' -e 's/plural=EXPRESSION/plural=\(n != 1\)/' $(EXTRACTED_DJANGO) + +compile_translations: ## compile translation files, outputting .mo files for each supported language + cd $(WORKING_DIR) && i18n_tool generate -v + python manage.py compilejsi18n --namespace DragAndDropI18N --output $(JS_TARGET) + +detect_changed_source_translations: + cd $(WORKING_DIR) && i18n_tool changed + +dummy_translations: ## generate dummy translation (.po) files + cd $(WORKING_DIR) && i18n_tool dummy + +build_dummy_translations: dummy_translations compile_translations ## generate and compile dummy translation files + +validate_translations: build_dummy_translations detect_changed_source_translations ## validate translations + +check_translations_up_to_date: extract_translations compile_translations dummy_translations detect_changed_source_translations ## extract, compile, and check if translation files are up-to-date + +piptools: ## install pinned version of pip-compile and pip-sync + pip install -r requirements/pip.txt + pip install -r requirements/pip-tools.txt + +requirements: piptools ## install test requirements locally + pip-sync requirements/ci.txt + +requirements_python: piptools ## install all requirements locally + pip-sync requirements/dev.txt requirements/private.* + +test.quality: selfcheck ## run quality checkers on the codebase + tox -e quality + +test.python: ## run python unit tests in the local virtualenv + pytest --cov ai_eval $(TEST) + +test.unit: ## run all unit tests + tox $(TEST) + +test: test.unit test.quality ## Run all tests + tox -e translations + +# Define PIP_COMPILE_OPTS=-v to get more information during make upgrade. +PIP_COMPILE = pip-compile --upgrade $(PIP_COMPILE_OPTS) + +upgrade: export CUSTOM_COMPILE_COMMAND=make upgrade +upgrade: ## update the requirements/*.txt files with the latest packages satisfying requirements/*.in + pip install -qr requirements/pip-tools.txt + # Make sure to compile files after any other files they include! + $(PIP_COMPILE) --allow-unsafe -o requirements/pip.txt requirements/pip.in + $(PIP_COMPILE) -o requirements/pip-tools.txt requirements/pip-tools.in + pip install -qr requirements/pip.txt + pip install -qr requirements/pip-tools.txt + $(PIP_COMPILE) -o requirements/base.txt requirements/base.in + $(PIP_COMPILE) -o requirements/test.txt requirements/test.in + $(PIP_COMPILE) -o requirements/quality.txt requirements/quality.in + $(PIP_COMPILE) -o requirements/ci.txt requirements/ci.in + $(PIP_COMPILE) -o requirements/dev.txt requirements/dev.in + sed -i '/^[dD]jango==/d' requirements/test.txt + +selfcheck: ## check that the Makefile is well-formed + @echo "The Makefile is well-formed." diff --git a/README.md b/README.md new file mode 100644 index 0000000..3c897f0 --- /dev/null +++ b/README.md @@ -0,0 +1,38 @@ +## Introduction + +This repository hosts two Open edX XBlocks: + +1. **Short Answer with AI Evaluation**: This XBlock allows students to submit short answers, which are then evaluated with the help of a large language model (LLM). +2. **Coding with AI Evaluation**: This XBlock allows students to submit code in a text editor. The code is executed via a third-party API (currently using [Judge0](https://judge0.com/)), and both the code and its output are sent to an LLM for feedback. + +## Screeshots + +| ![Short Answer with AI evaluation Xblock](docs/shortanswer-xblock.png) | ![Coding with AI evaluation Xblock](docs/coding-xblock.png) | +|-----------------------------------------------------------------------|----------------------------------------------------------------| +| ![Coding with AI evaluation Xblock HTML](docs/coding-xblock-ai-feedback.png) | ![Coding with AI evaluation Xblock AI feedback](docs/coding-xblock-html.png) | + + + +## Setup + +### Using Tutor + +1. Add the following line to the `OPENEDX_EXTRA_PIP_REQUIREMENTS` in your Tutor `config.yml` file: + ```yaml + OPENEDX_EXTRA_PIP_REQUIREMENTS: + - git+https://github.com/open-craft/xblock-ai-evaluation + ``` + You can append `@vX.Y.Z` to the URL to specify your desired version. + +2. Launch Tutor. + +3. In the Open edX platform, navigate to `Settings > Advanced Settings` and add `shortanswer_ai_eval` and `coding_ai_eval` to the `Advanced Module List`. + +4. Add either XBlock using the `Advanced` button in the `Add New Component` section of Studio. + +5. Configure the added Xblock and make sure to add correct API keys. You can format your question and prompts using [Markdown](https://marked.js.org/demo/). + +## Dependencies +- [Judge0 API](https://judge0.com/) +- [Monaco editor](https://github.com/microsoft/monaco-editor) +- [LiteLLM](https://github.com/BerriAI/litellm) \ No newline at end of file diff --git a/ai_eval/__init__.py b/ai_eval/__init__.py new file mode 100644 index 0000000..63412c2 --- /dev/null +++ b/ai_eval/__init__.py @@ -0,0 +1,6 @@ +""" +Xblock to have short text and code entries with AI-driven evaluation. +""" + +from .shortanswer import ShortAnswerAIEvalXBlock +from .coding_ai_eval import CodingAIEvalXBlock diff --git a/ai_eval/base.py b/ai_eval/base.py new file mode 100644 index 0000000..3e67e7f --- /dev/null +++ b/ai_eval/base.py @@ -0,0 +1,146 @@ +"""Base Xblock with AI evaluation.""" + +import pkg_resources + +from django.utils.translation import gettext_noop as _ +from xblock.core import XBlock +from xblock.fields import String, Scope, Dict +from xblock.validation import ValidationMessage + + +from .llm import SupportedModels + +try: + from xblock.utils.studio_editable import StudioEditableXBlockMixin +except ModuleNotFoundError: # For compatibility with Palm and earlier + from xblockutils.studio_editable import StudioEditableXBlockMixin + +try: + from xblock.utils.resources import ResourceLoader +except ( + ModuleNotFoundError +): # For backward compatibility with releases older than Quince. + from xblockutils.resources import ResourceLoader + + +class AIEvalXBlock(StudioEditableXBlockMixin, XBlock): + """ + Base class for Xblocks with AI evaluation + """ + + USER_KEY = "USER" + LLM_KEY = "LLM" + + loader = ResourceLoader(__name__) + + icon_class = "problem" + model_api_key = String( + display_name=_("Chosen model API Key"), + help=_("Enter your the API Key of your chosen model."), + default="", + scope=Scope.settings, + ) + model_api_url = String( + display_name=_("Set your API URL"), + help=_( + "Fill this only for LLama. This required with models that don't have an official provider." + " Example URL: https://model-provider-example/llama3_70b" + ), + default=None, + scope=Scope.settings, + ) + model = String( + display_name=_("AI model"), + help=_("Select the AI language model to use."), + values=[ + {"display_name": model, "value": model} for model in SupportedModels.list() + ], + Scope=Scope.settings, + default=SupportedModels.GPT4O.value, + ) + + evaluation_prompt = String( + display_name=_("Evaluation prompt"), + help=_( + "Enter the evaluation prompt given to the model." + " The question will be inserted right after it." + " The student's answer would then follow the question. Markdown format can be used." + ), + default="You are a teacher. Evaluate the student's answer for the following question:", + multiline_editor=True, + scope=Scope.settings, + ) + question = String( + display_name=_("Question"), + help=_( + "Enter the question you would like the students to answer." + " Markdown format can be used." + ), + default="", + multiline_editor=True, + scope=Scope.settings, + ) + + messages = Dict( + help=_("Dictionary with chat messages"), + scope=Scope.user_state, + default={USER_KEY: [], LLM_KEY: []}, + ) + editable_fields = ( + "display_name", + "evaluation_prompt", + "question", + "model", + "model_api_key", + "model_api_url", + ) + + def resource_string(self, path): + """Handy helper for getting resources from our kit.""" + data = pkg_resources.resource_string(__name__, path) + return data.decode("utf8") + + def validate_field_data(self, validation, data): + """ + Validate fields. + """ + + if not data.model or data.model not in SupportedModels.list(): + validation.add( + ValidationMessage( + ValidationMessage.ERROR, + _( # pylint: disable=translation-of-non-string + f"Model field is mandatory and must be one of {', '.join(SupportedModels.list())}" + ), + ) + ) + + if not data.model_api_key: + validation.add( + ValidationMessage( + ValidationMessage.ERROR, _("Model API key is mandatory") + ) + ) + + if data.model == SupportedModels.LLAMA and not data.model_api_url: + validation.add( + ValidationMessage( + ValidationMessage.ERROR, + _("API URL field is mandatory when using ollama/llama2."), + ) + ) + + if data.model != SupportedModels.LLAMA and data.model_api_url: + validation.add( + ValidationMessage( + ValidationMessage.ERROR, + _("API URL field can be set only when using ollama/llama2."), + ) + ) + + if not data.question: + validation.add( + ValidationMessage( + ValidationMessage.ERROR, _("Question field is mandatory") + ) + ) diff --git a/ai_eval/coding_ai_eval.py b/ai_eval/coding_ai_eval.py new file mode 100644 index 0000000..28a78d2 --- /dev/null +++ b/ai_eval/coding_ai_eval.py @@ -0,0 +1,251 @@ +"""Coding Xblock with AI evaluation.""" + +import logging +import traceback +import pkg_resources + + +from django.utils.translation import gettext_noop as _ +from web_fragments.fragment import Fragment +from xblock.core import XBlock +from xblock.exceptions import JsonHandlerError +from xblock.fields import Dict, Scope, String +from xblock.validation import ValidationMessage + +from .llm import get_llm_response +from .base import AIEvalXBlock +from .utils import ( + submit_code, + get_submission_result, + SUPPORTED_LANGUAGE_MAP, + LanguageLabels, +) + +logger = logging.getLogger(__name__) + +USER_RESPONSE = "USER_RESPONSE" +AI_EVALUATION = "AI_EVALUATION" +CODE_EXEC_RESULT = "CODE_EXEC_RESULT" + + +class CodingAIEvalXBlock(AIEvalXBlock): + """ + TO-DO: document what your XBlock does. + """ + + has_author_view = True + + display_name = String( + display_name=_("Display Name"), + help=_("Name of the component in the studio"), + default="Coding with AI Evaluation", + scope=Scope.settings, + ) + + judge0_api_key = String( + display_name=_("Judge0 API Key"), + help=_( + "Enter your the Judge0 API key used to execute code on Judge0." + " Get your key at https://rapidapi.com/judge0-official/api/judge0-ce." + ), + default="", + scope=Scope.settings, + ) + + language = String( + display_name=_("Programming Language"), + help=_("The programming language used for this Xblock."), + values=[ + {"display_name": language, "value": language} + for language in SUPPORTED_LANGUAGE_MAP + ], + default=LanguageLabels.Python, + Scope=Scope.settings, + ) + messages = Dict( + help=_("Dictionary with chat messages"), + scope=Scope.user_state, + default={USER_RESPONSE: "", AI_EVALUATION: "", CODE_EXEC_RESULT: {}}, + ) + + editable_fields = AIEvalXBlock.editable_fields + ("judge0_api_key", "language") + + def resource_string(self, path): + """Handy helper for getting resources from our kit.""" + data = pkg_resources.resource_string(__name__, path) + return data.decode("utf8") + + def student_view(self, context=None): + """ + The primary view of the CodingAIEvalXBlock, shown to students + when viewing courses. + """ + html = self.loader.render_django_template( + "/templates/coding_ai_eval.html", + { + "self": self, + }, + ) + + frag = Fragment(html) + frag.add_css(self.resource_string("static/css/coding_ai_eval.css")) + frag.add_javascript(self.resource_string("static/js/src/utils.js")) + + frag.add_javascript(self.resource_string("static/js/src/coding_ai_eval.js")) + + monaco_html = self.loader.render_django_template( + "/templates/monaco.html", + { + "monaco_language": SUPPORTED_LANGUAGE_MAP[self.language].monaco_id, + }, + ) + marked_html = self.resource_string("static/html/marked-iframe.html") + js_data = { + "monaco_html": monaco_html, + "question": self.question, + "code": self.messages[USER_RESPONSE], + "ai_evaluation": self.messages[AI_EVALUATION], + "code_exec_result": self.messages[CODE_EXEC_RESULT], + "marked_html": marked_html, + "language": self.language, + } + frag.initialize_js("CodingAIEvalXBlock", js_data) + return frag + + def author_view(self, context=None): + """ + Create preview to be show to course authors in Studio. + """ + if not self.validate(): + fragment = Fragment() + fragment.add_content( + _( + "To ensure this component works correctly, please fix the validation issues." + ) + ) + return fragment + + return self.student_view(context=context) + + def validate_field_data(self, validation, data): + """ + Validate fields + """ + + super().validate_field_data(validation, data) + + if data.language != LanguageLabels.HTML_CSS and not data.judge0_api_key: + validation.add( + ValidationMessage( + ValidationMessage.ERROR, _("Judge0 API key is mandatory") + ) + ) + + @XBlock.json_handler + def get_response(self, data, suffix=""): # pylint: disable=unused-argument + """Get LLM feedback.""" + + answer = f""" + student code : + + {data['code']} + """ + + # stdout and stderr only for executable languages (non HTML) + if self.language != LanguageLabels.HTML_CSS: + answer += f""" + stdout: + + {data['stdout']} + + stderr: + + {data['stderr']} + """ + + messages = [ + { + "role": "system", + "content": f""" + {self.evaluation_prompt} + + {self.question}. + + The programmimg language is {self.language} + + Evaluation must be in Makrdown format. + """, + }, + { + "content": f""" Here is the student's answer: + {answer} + """, + "role": "user", + }, + ] + + try: + response = get_llm_response( + self.model, + self.model_api_key, + messages, + self.model_api_url, + ) + + except Exception as e: + traceback.print_exc() + logger.error( + f"Failed while making LLM request using model {self.model}. Eaised error type: {type(e)}, Error: {e}" + ) + raise JsonHandlerError(500, "A probem occured. Please retry.") from e + + if response: + self.messages[USER_RESPONSE] = data["code"] + self.messages[AI_EVALUATION] = response + self.messages[CODE_EXEC_RESULT] = { + "stdout": data["stdout"], + "stderr": data["stderr"], + } + return {"response": response} + + raise JsonHandlerError(500, "No AI Evaluation available. Please retry.") + + @XBlock.json_handler + def submit_code_handler(self, data, suffix=""): # pylint: disable=unused-argument + """ + Submit code to Judge0. + """ + submission_id = submit_code( + self.judge0_api_key, data["user_code"], self.language + ) + return {"submission_id": submission_id} + + @XBlock.json_handler + def get_submission_result_handler( + self, data, suffix="" + ): # pylint: disable=unused-argument + """ + Get code submission result. + """ + submission_id = data["submission_id"] + return get_submission_result(self.judge0_api_key, submission_id) + + @staticmethod + def workbench_scenarios(): + """A canned scenario for display in the workbench.""" + return [ + ( + "CodingAIEvalXBlock", + """ + """, + ), + ( + "Multiple CodingAIEvalXBlock", + """ + + + + + """, + ), + ] diff --git a/ai_eval/llm.py b/ai_eval/llm.py new file mode 100644 index 0000000..0c956e7 --- /dev/null +++ b/ai_eval/llm.py @@ -0,0 +1,65 @@ +""" +Integration with LLMs. +""" + +from enum import Enum +from litellm import completion + + +class SupportedModels(Enum): + """ + LLM Models supported by the CodingAIEvalXBlock and ShortAnswerAIEvalXBlock + """ + + GPT4O = "gpt-4o" + GEMINI_PRO = "gemini/gemini-pro" + CLAUDE_SONNET = "claude-3-5-sonnet-20240620" + LLAMA = "ollama/llama2" + + @staticmethod + def list(): + return [str(m.value) for m in SupportedModels] + + +def get_llm_response( + model: SupportedModels, api_key: str, messages: list, api_base: str +) -> str: + """ + Get LLm response. + + Args: + model (SupportedModels): The model to use for generating the response. This should be an instance of + the SupportedModels enum, specifying which LLM model to call. + api_key (str): The API key required for authenticating with the LLM service. This key should be kept + confidential and used to authorize requests to the service. + messages (list): A list of message objects to be sent to the LLM. Each message should be a dictionary + with the following format: + + { + "content": str, # The content of the message. This is the text that you want to send to the LLM. + "role": str # The role of the message sender. This must be one of the following values: + # "user" - Represents a user message. + # "system" - Represents a system message, typically used for instructions or context. + # "assistant" - Represents a response or message from the LLM itself. + } + + Example: + [ + {"content": "Hello, how are you?", "role": "user"}, + {"content": "I'm here to help you.", "role": "assistant"} + ] + api_base (str): The base URL of the LLM API endpoint. This is the root URL used to construct the full + API request URL. This is required only when using Llama which doesn't have an official provider. + + Returns: + str: The response text from the LLM. This is typically the generated output based on the provided + messages. + """ + kwargs = {} + if api_base: + kwargs["api_base"] = api_base + return ( + completion(model=model, api_key=api_key, messages=messages, **kwargs) + .choices[0] + .message.content + ) diff --git a/ai_eval/shortanswer.py b/ai_eval/shortanswer.py new file mode 100644 index 0000000..e9514da --- /dev/null +++ b/ai_eval/shortanswer.py @@ -0,0 +1,152 @@ +"""Short answers Xblock with AI evaluation.""" + +import logging +import traceback + + +from django.utils.translation import gettext_noop as _ +from web_fragments.fragment import Fragment +from xblock.core import XBlock +from xblock.exceptions import JsonHandlerError +from xblock.fields import Integer, String, Scope +from xblock.validation import ValidationMessage + +from .llm import get_llm_response +from .base import AIEvalXBlock + + +logger = logging.getLogger(__name__) + + +class ShortAnswerAIEvalXBlock(AIEvalXBlock): + """ + Short Answer Xblock. + """ + + display_name = String( + display_name=_("Display Name"), + help=_("Name of the component in the studio"), + default="Short answer with AI Evaluation", + scope=Scope.settings, + ) + + max_responses = Integer( + display_name=_("Max Responses"), + help=_("The maximum number of response messages the student can submit"), + scope=Scope.settings, + default=3, + ) + + editable_fields = AIEvalXBlock.editable_fields + ("max_responses",) + + def validate_field_data(self, validation, data): + """ + Validate fields + """ + + super().validate_field_data(validation, data) + + if not data.max_responses or data.max_responses <= 0 or data.max_responses > 9: + validation.add( + ValidationMessage( + ValidationMessage.ERROR, + _("max responses must be an integer between 1 and 9"), + ) + ) + + def student_view(self, context=None): + """ + The primary view of the ShortAnswerAIEvalXBlock, shown to students + when viewing courses. + """ + + frag = Fragment() + frag.add_content( + self.loader.render_django_template( + "/templates/shortanswer.html", + { + "self": self, + }, + ) + ) + + frag.add_css(self.resource_string("static/css/shortanswer.css")) + frag.add_javascript(self.resource_string("static/js/src/utils.js")) + frag.add_javascript(self.resource_string("static/js/src/shortanswer.js")) + + marked_html = self.resource_string("static/html/marked-iframe.html") + + js_data = { + "question": self.question, + "messages": self.messages, + "max_responses": self.max_responses, + "marked_html": marked_html, + } + frag.initialize_js("ShortAnswerAIEvalXBlock", js_data) + return frag + + @XBlock.json_handler + def get_response(self, data, suffix=""): # pylint: disable=unused-argument + """Get LLM feedback""" + user_submission = str(data["user_input"]) + system_msg = { + "role": "system", + "content": f""" + {self.evaluation_prompt} + + {self.question}. + + Evaluation must be in Makrdown format. + """, + } + messages = [system_msg] + # add previous messages + # the first AI role is 'system' which defines the LLM's personnality and behavior. + # subsequent roles are 'assistant' and 'user' + for i in range(len(self.messages[self.USER_KEY])): + messages.append( + {"content": self.messages[self.USER_KEY][i], "role": "user"} + ) + messages.append( + {"content": self.messages[self.LLM_KEY][i], "role": "assistant"} + ) + + messages.append({"role": "user", "content": user_submission}) + + try: + response = get_llm_response( + self.model, self.model_api_key, messages, self.model_api_url + ) + + except Exception as e: + traceback.print_exc() + logger.error( + f"Failed while making LLM request using model {self.model}. Eaised error type: {type(e)}, Error: {e}" + ) + raise JsonHandlerError(500, "A probem occured. Please retry.") from e + + if response: + self.messages[self.USER_KEY].append(user_submission) + self.messages[self.LLM_KEY].append(response) + return {"response": response} + + raise JsonHandlerError(500, "A probem occured. The LLM sent an empty response.") + + @staticmethod + def workbench_scenarios(): + """A canned scenario for display in the workbench.""" + return [ + ( + "ShortAnswerAIEvalXBlock", + """ + """, + ), + ( + "Multiple ShortAnswerAIEvalXBlock", + """ + + + + """, + ), + ] diff --git a/ai_eval/static/README.txt b/ai_eval/static/README.txt new file mode 100644 index 0000000..0472ef6 --- /dev/null +++ b/ai_eval/static/README.txt @@ -0,0 +1,19 @@ +This static directory is for files that should be included in your kit as plain +static files. + +You can ask the runtime for a URL that will retrieve these files with: + + url = self.runtime.local_resource_url(self, "static/js/lib.js") + +The default implementation is very strict though, and will not serve files from +the static directory. It will serve files from a directory named "public". +Create a directory alongside this one named "public", and put files there. +Then you can get a url with code like this: + + url = self.runtime.local_resource_url(self, "public/js/lib.js") + +The sample code includes a function you can use to read the content of files +in the static directory, like this: + + frag.add_javascript(self.resource_string("static/js/my_block.js")) + diff --git a/ai_eval/static/css/coding_ai_eval.css b/ai_eval/static/css/coding_ai_eval.css new file mode 100644 index 0000000..b037357 --- /dev/null +++ b/ai_eval/static/css/coding_ai_eval.css @@ -0,0 +1,139 @@ +.used-prog-language { + flex: 5; + margin: 0.5rem 1rem; + text-align: end; +} + +.used-prog-language span { + background-color: #00262b; + color: white; + display: inline-block; + padding: .25em .4em; + font-size: 75%; + font-weight: 700; + line-height: 1; + text-align: center; + white-space: nowrap; + vertical-align: baseline; + border-radius: .25rem; +} + +.eval-ai-container { + display: flex; + max-height: 600px; + box-shadow: 0px 0px 10px 0px #0000001A; + border: 1px solid #CED4DA; + border-radius: 4px; +} + +.eval-ai-container .eval-ai-code-editor { + flex: 5; +} + +.eval-ai-container #monaco { + min-height: 500px; + width: 100%; + border-bottom: 1.5px solid #CED4DA; +} + +.eval-ai-container .result { + flex: 3; + background-color: #f5f5f5; + overflow-y: hidden; + border-top-right-radius: 4px; + border-bottom-right-radius: 4px; +} + +.eval-ai-container .html-render { + height: 100vh; +} + +.eval-ai-container .eval-ai-buttons { + display: flex; + justify-content: flex-end; +} + +.eval-ai-container .submit-loader { + margin-left: 5px; +} + +.eval-ai-container .eval-ai-buttons .eval-ai-button { + cursor: pointer; + margin: 10px; + text-align: center; + height: fit-content; + padding: 8px 12px; + border-radius: 4px; + font-size: 0.875em; + line-height: 1.25em; +} + +.eval-ai-container .eval-ai-buttons .disabled-btn { + opacity: 0.8; + cursor: not-allowed !important; +} + +.eval-ai-container .eval-ai-buttons #submit-button { + background-color: #00262b; + color: white; + border: none; +} + +.eval-ai-container .eval-ai-buttons #reset-button:hover { + background-color: #edeae9; +} + + + +.eval-ai-container .stderr { + margin-top: 10px; + color: red; + white-space: pre-wrap; +} + +.eval-ai-container .stdout { + white-space: pre-wrap; +} + +/* tabs */ +.tab { + display: flex; + border-bottom: 1px solid #edeae9; +} + +.tab .result-tab-btn { + float: left; + border: none; + outline: none; + cursor: pointer; + padding: 8px 12px; + transition: 0.3s; + font-size: 0.875em; + line-height: 1.25em; +} + +.tab .result-tab-btn:hover { + background-color: #ddd; +} + +.tab .result-tab-btn.active { + border-bottom: 2px solid #546d70; +} + +.tabcontent { + padding: 6px 12px; + border-top: none; + animation: fadeEffect 1s; + overflow-y: scroll; + height: calc(100% - 48px); +} + +@keyframes fadeEffect { + from { + opacity: 0; + } + + to { + opacity: 1; + } +} diff --git a/ai_eval/static/css/shortanswer.css b/ai_eval/static/css/shortanswer.css new file mode 100644 index 0000000..48ab5b8 --- /dev/null +++ b/ai_eval/static/css/shortanswer.css @@ -0,0 +1,127 @@ +/* CSS for ShortAnswerAIEvalXBlock */ + +.shortanswer_block .count { + font-weight: bold; +} + +.shortanswer_block p { + cursor: pointer; +} + +.chat-history { + min-height: 250px; + max-height: 400px; + overflow-y: auto; + margin-bottom: 10px; + padding: 0px 2em; +} + +.chat-message-container { + display: flex; +} +.chat-message-container .chat-message { + flex: 0 1 auto; + max-width: 80%; + padding: 10px 10px 5px 10px; + margin-bottom: 10px; + border-radius: 5px; +} + +.user-answer { + text-align: right; + margin-left: auto; + background-color: #f0f3f5; + color: #44586c; +} + +.ai-eval, +.message-spinner { + text-align: left; + color: white; + margin-right: auto; + background-color: #476480; +} +.ai-eval * { + color: white !important; +} + +.submit-row { + display: flex; + margin-bottom: 1em; + font-size: 16px; + padding: 10px; +} + +.submit-row .user-input { + flex: 8; + height: auto; + margin-right: 10px; + border: 1px solid gray; + border-radius: 5px; + overflow: auto; + max-height: 200px; + resize: none; +} + +.submit-row #submit-button { + flex: 1; + height: fit-content; + text-align: center; + padding: 10px 0; + margin-left: auto; + background-color: #00262b; + color: white; + border-radius: 5px; + border: none; + cursor: pointer; +} +.submit-row .disabled-btn { + opacity: 0.8; + cursor: not-allowed !important; +} +/* spinner animation */ +.chat-message-container .message-spinner > div { + width: 4px; + height: 4px; + margin-right: 2px; + background-color: white; + + border-radius: 100%; + display: inline-block; + -webkit-animation: chat-block-sk-bouncedelay 1.4s infinite ease-in-out both; + animation: chat-block-sk-bouncedelay 1.4s infinite ease-in-out both; +} + +.chat-message-container.message-spinner .bounce1 { + -webkit-animation-delay: -0.32s; + animation-delay: -0.32s; +} + +.chat-message-container .message-spinner .bounce2 { + -webkit-animation-delay: -0.16s; + animation-delay: -0.16s; +} + +@-webkit-keyframes chat-block-sk-bouncedelay { + 0%, + 80%, + 100% { + -webkit-transform: scale(0); + } + 40% { + -webkit-transform: scale(1); + } +} + +@keyframes chat-block-sk-bouncedelay { + 0%, + 80%, + 100% { + -webkit-transform: scale(0); + transform: scale(0); + } + 40% { + -webkit-transform: scale(1); + transform: scale(1); + } +} diff --git a/ai_eval/static/html/marked-iframe.html b/ai_eval/static/html/marked-iframe.html new file mode 100644 index 0000000..d21a301 --- /dev/null +++ b/ai_eval/static/html/marked-iframe.html @@ -0,0 +1,7 @@ + + + + + + + \ No newline at end of file diff --git a/ai_eval/static/js/src/coding_ai_eval.js b/ai_eval/static/js/src/coding_ai_eval.js new file mode 100644 index 0000000..512fbfe --- /dev/null +++ b/ai_eval/static/js/src/coding_ai_eval.js @@ -0,0 +1,215 @@ +/* Javascript for CodingAIEvalXBlock. */ +function CodingAIEvalXBlock(runtime, element, data) { + const runCodeHandlerURL = runtime.handlerUrl(element, "submit_code_handler"); + const submissionResultURL = runtime.handlerUrl( + element, + "get_submission_result_handler", + ); + loadMarkedInIframe(data.marked_html); + const llmResponseHandlerURL = runtime.handlerUrl(element, "get_response"); + const HTML_CSS = "HTML/CSS"; + const HTML_PLACEHOLER = + "\n\n\n\n\n\n

This is a heading

\n

This is a paragraph.

\n\n"; + + const iframe = $("#monaco", element)[0]; + const submitButton = $("#submit-button", element); + const resetButton = $("#reset-button", element); + const AIFeeback = $("#ai-feedback", element); + const stdout = $(".stdout", element); + const stderr = $(".stderr", element); + const htmlRenderIframe = $(".html-render", element); + + const MAX_JUDGE0_RETRY_ITER = 5; + const WAIT_TIME_MS = 1000; + + $(function () { + // The newer runtime uses the 'data-usage' attribute, while the LMS uses 'data-usage-id' + // A Jquery object can sometimes be returned e.g. after a studio field edit, we handle it with ?.[0] + const xblockUsageId = + element.getAttribute?.("data-usage") || + element.getAttribute?.("data-usage-id") || + element?.[0].getAttribute("data-usage-id"); + + if (!xblockUsageId) { + throw new Error( + "XBlock is missing a usage ID attribute on its root HTML node.", + ); + } + + // __USAGE_ID_PLACEHOLDER__ is the event data sent from the monaco iframe after loading + // we rely on the usage_id to limit the event to the Xblock scope + iframe.srcdoc = data.monaco_html.replace( + "__USAGE_ID_PLACEHOLDER__", + xblockUsageId, + ); + runFuncAfterLoading(init); + function submitCode() { + const code = iframe.contentWindow.editor.getValue(); + return $.ajax({ + url: runCodeHandlerURL, + method: "POST", + data: JSON.stringify({ user_code: code }), + }); + } + function delay(ms, data) { + const deferred = $.Deferred(); + setTimeout(function () { + deferred.resolve(data); + }, ms); + return deferred.promise(); + } + function getSubmissionResult(data) { + let retries = 0; + const deferred = $.Deferred(); + + function attempt() { + return $.ajax({ + url: submissionResultURL, + method: "POST", + data: JSON.stringify({ submission_id: data.submission_id }), + }) + .then(function (result) { + console.log("result", result, retries) + if (result.status.id === 1 || result.status.id === 2) { + // https://ce.judge0.com/#statuses-and-languages-status-get + // Retry if status is 1 (In Queue) or 2 (Processing) + if (retries < MAX_JUDGE0_RETRY_ITER) { + retries++; + console.log("Judge0 fetch result retry attempt:", retries); + setTimeout(function () { + attempt(); + }, WAIT_TIME_MS); + } else { + deferred.reject(new Error("Judge0 submission result fetch failed after " + MAX_JUDGE0_RETRY_ITER + " attempts.")); + } + } else { + const output = [result.compile_output, result.stdout].join("\n").trim(); + stdout.text(output); + stderr.text(result.stderr); + deferred.resolve(result); + } + + + }) + .fail(function (error) { + console.log("Error: ", error); + deferred.reject(new Error("An error occured while trying to fetch Judge0 submission result.")); + }); + } + attempt(); + return deferred.promise(); + } + + function getLLMFeedback(data) { + return $.ajax({ + url: llmResponseHandlerURL, + method: "POST", + data: JSON.stringify({ + code: iframe.contentWindow.editor.getValue(), + stdout: data.stdout, + stderr: data.stderr, + }), + success: function (data) { + console.log(data); + AIFeeback.html(MarkdownToHTML(data.response)); + $("#ai-feedback-tab", element).click(); + }, + }); + } + + resetButton.click(() => { + iframe.contentWindow.editor.setValue(""); + }); + + submitButton.click(() => { + const code = iframe.contentWindow.editor.getValue(); + if (!code?.length) { + return; + } + disableSubmitButton(); + var deferred = null; + if (data.language === HTML_CSS) { + // no need to submit HTML code, we directly get LLM feedback + deferred = getLLMFeedback({ stdout: "", stderr: "" }); + } else { + deferred = submitCode() + .then(function (data) { + return delay(WAIT_TIME_MS * 2, data); + }) + .then(getSubmissionResult) + .then(getLLMFeedback); + } + + deferred + .done(function (data) { + enableSubmitButton(); + }) + .fail(function (error) { + console.log("Error: ", error); + enableSubmitButton(); + alert("A problem occured while submitting the code."); + }); + }); + + function init() { + $("#question-text", element).html(MarkdownToHTML(data.question)); + // Triggered when the Monaco editor loads. + // Since a Unit can have multiple instances of this Xblock, + // we use the XblockUsageId to differentiate between them. + window.addEventListener("message", function (event) { + if (event.data === xblockUsageId) { + if (data.code?.length) { + iframe.contentWindow.editor.setValue(data.code); + } + + AIFeeback.html(MarkdownToHTML(data.ai_evaluation || "")); + if (data.language === HTML_CSS) { + // render HTML/CSS into iframe + if (data.code?.length) { + renderUserHTML(data.code); + } else { + iframe.contentWindow.editor.setValue(HTML_PLACEHOLER); + renderUserHTML(HTML_PLACEHOLER); + } + addMonacoHTMLRenderEventListener(); + } else { + // load existing results for executable languages + stdout.text(data.code_exec_result?.stdout || ""); + stderr.text(data.code_exec_result?.stderr || ""); + } + } + }); + } + function addMonacoHTMLRenderEventListener() { + iframe.contentWindow.editor.onDidChangeModelContent((event) => { + renderUserHTML(iframe.contentWindow.editor.getValue()); + }); + } + function renderUserHTML(userHTML) { + htmlRenderIframe.attr("srcdoc", stripScriptTags(userHTML)); + } + }); + + function disableSubmitButton() { + submitButton.append(''); + submitButton.prop("disabled", true); + submitButton.addClass("disabled-btn"); + } + + function enableSubmitButton() { + $(".submit-loader", element).remove(); + submitButton.prop("disabled", false); + submitButton.removeClass("disabled-btn"); + } + + // basic tabs + $(".tablinks", element).click((event) => { + $(".tabcontent", element).hide(); + $(".tablinks", element).removeClass("active"); + $(event.target).addClass("active"); + const contentID = "#" + $(event.target).data("id"); + $(contentID, element).show(); + }); + // default tab + $("#defaultOpen", element).click(); +} diff --git a/ai_eval/static/js/src/shortanswer.js b/ai_eval/static/js/src/shortanswer.js new file mode 100644 index 0000000..4bbd0ab --- /dev/null +++ b/ai_eval/static/js/src/shortanswer.js @@ -0,0 +1,105 @@ +/* Javascript for ShortAnswerAIEvalXBlock. */ +function ShortAnswerAIEvalXBlock(runtime, element, data) { + const handlerUrl = runtime.handlerUrl(element, "get_response"); + + loadMarkedInIframe(data.marked_html); + + $(function () { + const spinner = $(".message-spinner", element); + const spinnnerContainer = $("#chat-spinner-container", element); + const submitButton = $("#submit-button", element); + const userInput = $(".user-input", element); + const userInputElem = userInput[0]; + let initDone = false; + + runFuncAfterLoading(init); + + function getResponse() { + if (!userInput.val().length) return; + + disableInput(); + spinner.show(); + insertUserMessage(userInput.val()); + $.ajax({ + url: handlerUrl, + method: "POST", + data: JSON.stringify({ user_input: userInput.val() }), + success: function (response) { + spinner.hide(); + insertAIMessage(response.response); + userInput.val(""); + if ($(".user-answer", element).length >= data.max_responses) { + disableInput(); + } else { + enableInput(); + } + }, + error: function (jqXHR, textStatus, errorThrown) { + spinner.hide(); + alert(errorThrown); + + deleteLastMessage(); + enableInput(); + }, + }); + } + + submitButton.click(getResponse); + + function disableInput() { + userInput.prop("disabled", true); + userInput.removeAttr("placeholder"); + submitButton.prop("disabled", true); + submitButton.addClass("disabled-btn"); + } + + function enableInput() { + userInput.prop("disabled", false); + submitButton.prop("disabled", false); + submitButton.removeClass("disabled-btn"); + } + + function adjustTextareaHeight(element) { + element.style.height = ""; + element.style.height = element.scrollHeight + "px"; + } + userInputElem.addEventListener("input", (event) => { + adjustTextareaHeight(userInputElem); + }); + + function init() { + if (initDone) return; + initDone = true; + $("#question-text", element).html(MarkdownToHTML(data.question)); + for (let i = 0; i < data.messages.USER.length; i++) { + insertUserMessage(data.messages.USER[i]); + insertAIMessage(data.messages.LLM[i]); + } + if ( + data.messages.USER.length && + data.messages.USER.length >= data.max_responses + ) { + disableInput(); + } + } + + function insertUserMessage(msg) { + if (msg?.length) { + $(`
+
${MarkdownToHTML(msg)}
+
`).insertBefore(spinnnerContainer); + } + } + + function insertAIMessage(msg) { + if (msg?.length) { + $(`
+
${MarkdownToHTML(msg)}
+
`).insertBefore(spinnnerContainer); + } + } + function deleteLastMessage() { + spinnnerContainer.prev().remove(); + } + }); +} diff --git a/ai_eval/static/js/src/utils.js b/ai_eval/static/js/src/utils.js new file mode 100644 index 0000000..063ef98 --- /dev/null +++ b/ai_eval/static/js/src/utils.js @@ -0,0 +1,41 @@ +// we load Marked in a Iframe to avoid RequireJS conflicts with the Xblock runtime +function loadMarkedInIframe(html) { + if (!window.marked && !document.getElementById("marked-iframe")) { + const iframe = document.createElement("iframe"); + iframe.style.display = "none"; + iframe.setAttribute("id", "marked-iframe"); + iframe.srcdoc = html; + document.body.appendChild(iframe); + } +} +function MarkdownToHTML(text) { + window.marked = + window.marked ?? + document.getElementById("marked-iframe").contentWindow.marked; + if (typeof marked !== "undefined") text = marked.parse(text); + return text; +} + +function runFuncAfterLoading(func) { + const markedIframe = document.getElementById("marked-iframe"); + // loading is finished when Marked is available + if (markedIframe.contentWindow.marked) { + func(); + } else { + markedIframe.addEventListener("load", (event) => { + func(); + }); + } +} + +function stripScriptTags(html) { + const div = document.createElement("div"); + div.innerHTML = html; + + const scripts = div.getElementsByTagName("script"); + while (scripts.length > 0) { + scripts[0].parentNode.removeChild(scripts[0]); + } + + return div.innerHTML; +} diff --git a/ai_eval/templates/coding_ai_eval.html b/ai_eval/templates/coding_ai_eval.html new file mode 100644 index 0000000..bf1c687 --- /dev/null +++ b/ai_eval/templates/coding_ai_eval.html @@ -0,0 +1,31 @@ +
+
+
+
+ {{ self.language }} +
+ +
+ Reset + Submit Code +
+
+ +
+
+ Output + AI feedback +
+ +
+ {% if self.language == "HTML/CSS" %} + + {% else %} +
+
+ {% endif %} +
+ +
+
+
diff --git a/ai_eval/templates/monaco.html b/ai_eval/templates/monaco.html new file mode 100644 index 0000000..56de7e5 --- /dev/null +++ b/ai_eval/templates/monaco.html @@ -0,0 +1,22 @@ + + + + + Monaco Editor + + +
+ + + diff --git a/ai_eval/templates/shortanswer.html b/ai_eval/templates/shortanswer.html new file mode 100644 index 0000000..cc73600 --- /dev/null +++ b/ai_eval/templates/shortanswer.html @@ -0,0 +1,26 @@ +
+
+
+ Loading .. +
+
+ +
+
+
+ +
+
+
+ + Submit +
+
+
\ No newline at end of file diff --git a/ai_eval/tests/__init__.py b/ai_eval/tests/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/ai_eval/tests/test_ai_eval.py b/ai_eval/tests/test_ai_eval.py new file mode 100644 index 0000000..3f135ed --- /dev/null +++ b/ai_eval/tests/test_ai_eval.py @@ -0,0 +1,56 @@ +""" +Testing module. +""" + +import unittest +from xblock.field_data import DictFieldData +from xblock.test.toy_runtime import ToyRuntime +from ai_eval import CodingAIEvalXBlock, ShortAnswerAIEvalXBlock + + +class TestCodingAIEvalXBlock(unittest.TestCase): + """Tests for CodingAIEvalXBlock""" + + def test_basics_student_view(self): + """Test the basic view loads.""" + data = { + "language": "Python", + "question": "ca va?", + "code": "", + "ai_evaluation": "", + "code_exec_result": {}, + "marked_html": '\n\n\n\n \n\n', + "monaco_html": '\n\n\n ' + '\n Monaco Editor\n\n\n \n \n\n\n", + } + block = CodingAIEvalXBlock(ToyRuntime(), DictFieldData(data), None) + frag = block.student_view() + self.assertEqual(data, frag.json_init_args) + self.assertIn('
', frag.content) + + +class TestShortAnswerAIEvalXBlock(unittest.TestCase): + """Tests for ShortAnswerAIEvalXBlock""" + + def test_basics_student_view(self): + """Test the basic view loads.""" + data = { + "question": "ca va?", + "messages": {"USER": [], "LLM": []}, + "max_responses": 3, + "marked_html": '\n\n\n\n \n\n', + } + block = ShortAnswerAIEvalXBlock(ToyRuntime(), DictFieldData(data), None) + frag = block.student_view() + self.assertEqual(data, frag.json_init_args) + self.assertIn('
', frag.content) diff --git a/ai_eval/translations/README.txt b/ai_eval/translations/README.txt new file mode 100644 index 0000000..0493bcc --- /dev/null +++ b/ai_eval/translations/README.txt @@ -0,0 +1,4 @@ +Use this translations directory to provide internationalized strings for your XBlock project. + +For more information on how to enable translations, visit the Open edX XBlock tutorial on Internationalization: +http://edx.readthedocs.org/projects/xblock-tutorial/en/latest/edx_platform/edx_lms.html diff --git a/ai_eval/utils.py b/ai_eval/utils.py new file mode 100644 index 0000000..cf866bf --- /dev/null +++ b/ai_eval/utils.py @@ -0,0 +1,84 @@ +""" +Utilities +""" + +from dataclasses import dataclass +import requests + + +@dataclass +class ProgrammimgLanguage: + """A programming language.""" + + monaco_id: str + judge0_id: int + + +class LanguageLabels: + """Language labels as seen by users.""" + + Python = "Python" + JavaScript = "JavaScript" + Java = "Java" + CPP = "C++" + HTML_CSS = "HTML/CSS" + + +# supported programming languages and their IDs in judge0 and monaco +# https://ce.judge0.com/#statuses-and-languages-active-and-archived-languages +SUPPORTED_LANGUAGE_MAP = { + LanguageLabels.Python: ProgrammimgLanguage( + monaco_id="python", judge0_id=92 + ), # Python (3.11.2) + LanguageLabels.JavaScript: ProgrammimgLanguage( + monaco_id="javascript", judge0_id=93 + ), # JavaScript (Node.js 18.15.0) + LanguageLabels.Java: ProgrammimgLanguage( + monaco_id="java", judge0_id=91 + ), # Java (JDK 17.0.6) + LanguageLabels.CPP: ProgrammimgLanguage( + monaco_id="cpp", judge0_id=54 + ), # C++ (GCC 9.2.0) + # Monaco's HTML support includes CSS support within the 'style' tag. + LanguageLabels.HTML_CSS: ProgrammimgLanguage( + monaco_id="html", judge0_id=-1 + ), # no exec +} + + +JUDGE0_BASE_CE_URL = "https://judge0-ce.p.rapidapi.com" + + +def submit_code(api_key: str, code: str, language: str) -> str: + """ + Submit code to the judge0 API. + """ + url = f"{JUDGE0_BASE_CE_URL}/submissions?base64_encoded=false&wait=false" + headers = {"content-type": "application/json", "x-rapidapi-key": api_key} + + data = { + "source_code": code, + "language_id": SUPPORTED_LANGUAGE_MAP[language].judge0_id, + } + + response = requests.post(url, headers=headers, json=data, timeout=10) + response.raise_for_status() + result = response.json() + sub_id = result["token"] + + return sub_id + + +def get_submission_result(api_key: str, submission_id: str): + """ + Get result from Judge0 submission. + """ + + url = f"{JUDGE0_BASE_CE_URL}/submissions/{submission_id}?base64_encoded=false&fields=*" + headers = {"content-type": "application/json", "x-rapidapi-key": api_key} + + response = requests.get(url, headers=headers, timeout=10) + response.raise_for_status() + result = response.json() + + return result diff --git a/docs/coding-xblock-ai-feedback.png b/docs/coding-xblock-ai-feedback.png new file mode 100644 index 0000000000000000000000000000000000000000..d676db263bb6a679eb7f3028d56f6f832bc66b4f GIT binary patch literal 60677 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 r+R?6qIW(Y7)-KDM86ut*cK6s$YiaxB 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 literal 0 HcmV?d00001 diff --git a/docs/coding-xblock-html.png b/docs/coding-xblock-html.png new file mode 100644 index 0000000000000000000000000000000000000000..df43202a228e0c50be2b792831dda475349001f0 GIT binary patch literal 92471 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 literal 0 HcmV?d00001 diff --git a/docs/coding-xblock.png b/docs/coding-xblock.png new file mode 100644 index 0000000000000000000000000000000000000000..cf8a0a33941aa2d4238722438a5968f36a2cd5e5 GIT binary patch literal 48267 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ìJg<> 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 E02^mORR910 literal 0 HcmV?d00001 diff --git a/docs/shortanswer-xblock.png b/docs/shortanswer-xblock.png new file mode 100644 index 0000000000000000000000000000000000000000..b55f91f091c20b3ccb5fd96d46e3aa82a7467d32 GIT binary patch literal 57498 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\.\. \w+: .*))$ +single-line-if-stmt = no +max-module-lines = 1000 +indent-string = ' ' + +[MISCELLANEOUS] +notes = FIXME,XXX,TODO + +[SIMILARITIES] +min-similarity-lines = 4 +ignore-comments = yes +ignore-docstrings = yes +ignore-imports = no + +[TYPECHECK] +ignore-mixin-members = yes +ignored-classes = SQLObject +unsafe-load-any-extension = yes +generated-members = + REQUEST, + acl_users, + aq_parent, + objects, + DoesNotExist, + can_read, + can_write, + get_url, + size, + content, + status_code, + create, + build, + fields, + tag, + org, + course, + category, + name, + revision, + _meta, + +[VARIABLES] +init-import = no +dummy-variables-rgx = _|dummy|unused|.*_unused +additional-builtins = + +[CLASSES] +defining-attr-methods = __init__,__new__,setUp +valid-classmethod-first-arg = cls +valid-metaclass-classmethod-first-arg = mcs + +[DESIGN] +max-args = 5 +ignored-argument-names = _.* +max-locals = 15 +max-returns = 6 +max-branches = 12 +max-statements = 50 +max-parents = 7 +max-attributes = 7 +min-public-methods = 2 +max-public-methods = 20 + +[IMPORTS] +deprecated-modules = regsub,TERMIOS,Bastion,rexec +import-graph = +ext-import-graph = +int-import-graph = + +[EXCEPTIONS] +overgeneral-exceptions = builtins.Exception + +# 6114ba904f03712e1def5d0f459a5ce5a0927223 diff --git a/pylintrc_tweaks b/pylintrc_tweaks new file mode 100644 index 0000000..f24c494 --- /dev/null +++ b/pylintrc_tweaks @@ -0,0 +1,10 @@ +# pylintrc tweaks for use with edx_lint. +[MASTER] +ignore = migrations +load-plugins = edx_lint.pylint,pylint_django,pylint_celery + +[MESSAGES CONTROL] +disable+= + django-not-configured, + unused-argument, + unsubscriptable-object diff --git a/requirements/base.in b/requirements/base.in new file mode 100644 index 0000000..c02823b --- /dev/null +++ b/requirements/base.in @@ -0,0 +1,6 @@ +# Core requirements for using this application +-c constraints.txt + +django-statici18n +XBlock[django] +litellm \ No newline at end of file diff --git a/requirements/base.txt b/requirements/base.txt new file mode 100644 index 0000000..6e546df --- /dev/null +++ b/requirements/base.txt @@ -0,0 +1,221 @@ +# +# This file is autogenerated by pip-compile with Python 3.8 +# by the following command: +# +# make upgrade +# +aiohappyeyeballs==2.3.4 + # via aiohttp +aiohttp==3.10.0 + # via litellm +aiosignal==1.3.1 + # via aiohttp +annotated-types==0.7.0 + # via pydantic +anyio==4.4.0 + # via + # httpx + # openai +appdirs==1.4.4 + # via fs +asgiref==3.8.1 + # via django +async-timeout==4.0.3 + # via aiohttp +attrs==23.2.0 + # via + # aiohttp + # jsonschema + # referencing +backports-zoneinfo==0.2.1 ; python_version < "3.9" + # via + # -c requirements/constraints.txt + # django +boto3==1.34.151 + # via fs-s3fs +botocore==1.34.151 + # via + # boto3 + # s3transfer +certifi==2024.7.4 + # via + # httpcore + # httpx + # requests +charset-normalizer==3.3.2 + # via requests +click==8.1.7 + # via litellm +distro==1.9.0 + # via openai +django==4.2.14 + # via + # -c https://raw.githubusercontent.com/edx/edx-lint/master/edx_lint/files/common_constraints.txt + # django-appconf + # django-statici18n + # openedx-django-pyfs +django-appconf==1.0.6 + # via django-statici18n +django-statici18n==2.5.0 + # via -r requirements/base.in +exceptiongroup==1.2.2 + # via anyio +filelock==3.15.4 + # via huggingface-hub +frozenlist==1.4.1 + # via + # aiohttp + # aiosignal +fs==2.4.16 + # via + # fs-s3fs + # openedx-django-pyfs + # xblock +fs-s3fs==1.1.1 + # via openedx-django-pyfs +fsspec==2024.6.1 + # via huggingface-hub +h11==0.14.0 + # via httpcore +httpcore==1.0.5 + # via httpx +httpx==0.27.0 + # via openai +huggingface-hub==0.24.5 + # via tokenizers +idna==3.7 + # via + # anyio + # httpx + # requests + # yarl +importlib-metadata==6.11.0 + # via + # -c https://raw.githubusercontent.com/edx/edx-lint/master/edx_lint/files/common_constraints.txt + # litellm +importlib-resources==6.4.0 + # via + # jsonschema + # jsonschema-specifications +jinja2==3.1.4 + # via litellm +jmespath==1.0.1 + # via + # boto3 + # botocore +jsonschema==4.23.0 + # via litellm +jsonschema-specifications==2023.12.1 + # via jsonschema +lazy==1.6 + # via xblock +litellm==1.42.6 + # via -r requirements/base.in +lxml==5.2.2 + # via xblock +mako==1.3.5 + # via xblock +markupsafe==2.1.5 + # via + # jinja2 + # mako + # xblock +multidict==6.0.5 + # via + # aiohttp + # yarl +openai==1.37.1 + # via litellm +openedx-django-pyfs==3.6.0 + # via xblock +packaging==24.1 + # via huggingface-hub +pkgutil-resolve-name==1.3.10 + # via jsonschema +pydantic==2.8.2 + # via + # litellm + # openai +pydantic-core==2.20.1 + # via pydantic +python-dateutil==2.9.0.post0 + # via + # botocore + # xblock +python-dotenv==1.0.1 + # via litellm +pytz==2024.1 + # via xblock +pyyaml==6.0.1 + # via + # huggingface-hub + # xblock +referencing==0.35.1 + # via + # jsonschema + # jsonschema-specifications +regex==2024.7.24 + # via tiktoken +requests==2.32.3 + # via + # huggingface-hub + # litellm + # tiktoken +rpds-py==0.19.1 + # via + # jsonschema + # referencing +s3transfer==0.10.2 + # via boto3 +simplejson==3.19.2 + # via xblock +six==1.16.0 + # via + # fs + # fs-s3fs + # python-dateutil +sniffio==1.3.1 + # via + # anyio + # httpx + # openai +sqlparse==0.5.1 + # via django +tiktoken==0.7.0 + # via litellm +tokenizers==0.19.1 + # via litellm +tqdm==4.66.4 + # via + # huggingface-hub + # openai +typing-extensions==4.12.2 + # via + # annotated-types + # anyio + # asgiref + # huggingface-hub + # openai + # pydantic + # pydantic-core +urllib3==1.26.19 + # via + # botocore + # requests +web-fragments==2.2.0 + # via xblock +webob==1.8.7 + # via xblock +xblock[django]==4.0.1 + # via + # -c requirements/constraints.txt + # -r requirements/base.in +yarl==1.9.4 + # via aiohttp +zipp==3.19.2 + # via + # importlib-metadata + # importlib-resources + +# The following packages are considered to be unsafe in a requirements file: +# setuptools diff --git a/requirements/ci.in b/requirements/ci.in new file mode 100644 index 0000000..3c1c718 --- /dev/null +++ b/requirements/ci.in @@ -0,0 +1,4 @@ +# Requirements for running tests in CI +-c constraints.txt + +tox # Virtualenv management for tests diff --git a/requirements/ci.txt b/requirements/ci.txt new file mode 100644 index 0000000..f0993ea --- /dev/null +++ b/requirements/ci.txt @@ -0,0 +1,38 @@ +# +# This file is autogenerated by pip-compile with Python 3.8 +# by the following command: +# +# make upgrade +# +cachetools==5.4.0 + # via tox +chardet==5.2.0 + # via tox +colorama==0.4.6 + # via tox +distlib==0.3.8 + # via virtualenv +filelock==3.15.4 + # via + # tox + # virtualenv +packaging==24.1 + # via + # pyproject-api + # tox +platformdirs==4.2.2 + # via + # tox + # virtualenv +pluggy==1.5.0 + # via tox +pyproject-api==1.7.1 + # via tox +tomli==2.0.1 + # via + # pyproject-api + # tox +tox==4.16.0 + # via -r requirements/ci.in +virtualenv==20.26.3 + # via tox diff --git a/requirements/constraints.txt b/requirements/constraints.txt new file mode 100644 index 0000000..4146286 --- /dev/null +++ b/requirements/constraints.txt @@ -0,0 +1,17 @@ +# Version constraints for pip-installation. +# +# This file doesn't install any packages. It specifies version constraints +# that will be applied if a package is needed. +# +# When pinning something here, please provide an explanation of why. Ideally, +# link to other information that will help people in the future to remove the +# pin when possible. Writing an issue against the offending project and +# linking to it here is good. + +# Common constraints for edx repos +-c https://raw.githubusercontent.com/edx/edx-lint/master/edx_lint/files/common_constraints.txt + +# For python greater than or equal to 3.9 backports.zoneinfo causing failures +backports.zoneinfo; python_version<"3.9" + +xblock[django]==4.0.1 \ No newline at end of file diff --git a/requirements/dev.in b/requirements/dev.in new file mode 100644 index 0000000..7456111 --- /dev/null +++ b/requirements/dev.in @@ -0,0 +1,6 @@ +# Additional requirements for development of this application +-c constraints.txt + +-r pip-tools.txt # pip-tools and its dependencies, for managing requirements files +-r quality.txt # Core and quality check dependencies +-r ci.txt # dependencies for setting up testing in CI diff --git a/requirements/dev.txt b/requirements/dev.txt new file mode 100644 index 0000000..85f0896 --- /dev/null +++ b/requirements/dev.txt @@ -0,0 +1,579 @@ +# +# This file is autogenerated by pip-compile with Python 3.8 +# by the following command: +# +# make upgrade +# +aiohappyeyeballs==2.3.4 + # via + # -r requirements/quality.txt + # aiohttp +aiohttp==3.10.0 + # via + # -r requirements/quality.txt + # litellm +aiosignal==1.3.1 + # via + # -r requirements/quality.txt + # aiohttp +annotated-types==0.7.0 + # via + # -r requirements/quality.txt + # pydantic +anyio==4.4.0 + # via + # -r requirements/quality.txt + # httpx + # openai +appdirs==1.4.4 + # via + # -r requirements/quality.txt + # fs +arrow==1.3.0 + # via + # -r requirements/quality.txt + # cookiecutter +asgiref==3.8.1 + # via + # -r requirements/quality.txt + # django +astroid==3.2.4 + # via + # -r requirements/quality.txt + # pylint + # pylint-celery +async-timeout==4.0.3 + # via + # -r requirements/quality.txt + # aiohttp +attrs==23.2.0 + # via + # -r requirements/quality.txt + # aiohttp + # jsonschema + # referencing +backports-zoneinfo==0.2.1 ; python_version < "3.9" + # via + # -c requirements/constraints.txt + # -r requirements/quality.txt + # django +binaryornot==0.4.4 + # via + # -r requirements/quality.txt + # cookiecutter +boto3==1.34.151 + # via + # -r requirements/quality.txt + # fs-s3fs +botocore==1.34.151 + # via + # -r requirements/quality.txt + # boto3 + # s3transfer +build==1.2.1 + # via + # -r requirements/pip-tools.txt + # pip-tools +cachetools==5.4.0 + # via + # -r requirements/ci.txt + # tox +certifi==2024.7.4 + # via + # -r requirements/quality.txt + # httpcore + # httpx + # requests +chardet==5.2.0 + # via + # -r requirements/ci.txt + # -r requirements/quality.txt + # binaryornot + # tox +charset-normalizer==3.3.2 + # via + # -r requirements/quality.txt + # requests +click==8.1.7 + # via + # -r requirements/pip-tools.txt + # -r requirements/quality.txt + # click-log + # code-annotations + # cookiecutter + # edx-lint + # litellm + # pip-tools +click-log==0.4.0 + # via + # -r requirements/quality.txt + # edx-lint +code-annotations==1.8.0 + # via + # -r requirements/quality.txt + # edx-lint +colorama==0.4.6 + # via + # -r requirements/ci.txt + # tox +cookiecutter==2.6.0 + # via + # -r requirements/quality.txt + # xblock-sdk +coverage[toml]==7.6.0 + # via + # -r requirements/quality.txt + # pytest-cov +ddt==1.7.2 + # via -r requirements/quality.txt +dill==0.3.8 + # via + # -r requirements/quality.txt + # pylint +distlib==0.3.8 + # via + # -r requirements/ci.txt + # virtualenv +distro==1.9.0 + # via + # -r requirements/quality.txt + # openai +django==4.2.14 + # via + # -c https://raw.githubusercontent.com/edx/edx-lint/master/edx_lint/files/common_constraints.txt + # -r requirements/quality.txt + # django-appconf + # django-statici18n + # edx-i18n-tools + # openedx-django-pyfs + # xblock-sdk +django-appconf==1.0.6 + # via + # -r requirements/quality.txt + # django-statici18n +django-statici18n==2.5.0 + # via -r requirements/quality.txt +edx-i18n-tools==1.6.2 + # via -r requirements/quality.txt +edx-lint==5.3.7 + # via -r requirements/quality.txt +exceptiongroup==1.2.2 + # via + # -r requirements/quality.txt + # anyio + # pytest +filelock==3.15.4 + # via + # -r requirements/ci.txt + # -r requirements/quality.txt + # huggingface-hub + # tox + # virtualenv +frozenlist==1.4.1 + # via + # -r requirements/quality.txt + # aiohttp + # aiosignal +fs==2.4.16 + # via + # -r requirements/quality.txt + # fs-s3fs + # openedx-django-pyfs + # xblock +fs-s3fs==1.1.1 + # via + # -r requirements/quality.txt + # openedx-django-pyfs + # xblock-sdk +fsspec==2024.6.1 + # via + # -r requirements/quality.txt + # huggingface-hub +h11==0.14.0 + # via + # -r requirements/quality.txt + # httpcore +httpcore==1.0.5 + # via + # -r requirements/quality.txt + # httpx +httpx==0.27.0 + # via + # -r requirements/quality.txt + # openai +huggingface-hub==0.24.5 + # via + # -r requirements/quality.txt + # tokenizers +idna==3.7 + # via + # -r requirements/quality.txt + # anyio + # httpx + # requests + # yarl +importlib-metadata==6.11.0 + # via + # -c https://raw.githubusercontent.com/edx/edx-lint/master/edx_lint/files/common_constraints.txt + # -r requirements/pip-tools.txt + # -r requirements/quality.txt + # build + # litellm +importlib-resources==6.4.0 + # via + # -r requirements/quality.txt + # jsonschema + # jsonschema-specifications +iniconfig==2.0.0 + # via + # -r requirements/quality.txt + # pytest +isort==5.13.2 + # via + # -r requirements/quality.txt + # pylint +jinja2==3.1.4 + # via + # -r requirements/quality.txt + # code-annotations + # cookiecutter + # litellm +jmespath==1.0.1 + # via + # -r requirements/quality.txt + # boto3 + # botocore +jsonschema==4.23.0 + # via + # -r requirements/quality.txt + # litellm +jsonschema-specifications==2023.12.1 + # via + # -r requirements/quality.txt + # jsonschema +lazy==1.6 + # via + # -r requirements/quality.txt + # xblock +litellm==1.42.6 + # via -r requirements/quality.txt +lxml==5.2.2 + # via + # -r requirements/quality.txt + # edx-i18n-tools + # xblock + # xblock-sdk +mako==1.3.5 + # via + # -r requirements/quality.txt + # xblock +markdown-it-py==3.0.0 + # via + # -r requirements/quality.txt + # rich +markupsafe==2.1.5 + # via + # -r requirements/quality.txt + # jinja2 + # mako + # xblock +mccabe==0.7.0 + # via + # -r requirements/quality.txt + # pylint +mdurl==0.1.2 + # via + # -r requirements/quality.txt + # markdown-it-py +mock==5.1.0 + # via -r requirements/quality.txt +multidict==6.0.5 + # via + # -r requirements/quality.txt + # aiohttp + # yarl +openai==1.37.1 + # via + # -r requirements/quality.txt + # litellm +openedx-django-pyfs==3.6.0 + # via + # -r requirements/quality.txt + # xblock +packaging==24.1 + # via + # -r requirements/ci.txt + # -r requirements/pip-tools.txt + # -r requirements/quality.txt + # build + # huggingface-hub + # pyproject-api + # pytest + # tox +path==16.16.0 + # via + # -r requirements/quality.txt + # edx-i18n-tools +pbr==6.0.0 + # via + # -r requirements/quality.txt + # stevedore +pip-tools==7.4.1 + # via -r requirements/pip-tools.txt +pkgutil-resolve-name==1.3.10 + # via + # -r requirements/quality.txt + # jsonschema +platformdirs==4.2.2 + # via + # -r requirements/ci.txt + # -r requirements/quality.txt + # pylint + # tox + # virtualenv +pluggy==1.5.0 + # via + # -r requirements/ci.txt + # -r requirements/quality.txt + # pytest + # tox +polib==1.2.0 + # via + # -r requirements/quality.txt + # edx-i18n-tools +pycodestyle==2.12.0 + # via -r requirements/quality.txt +pydantic==2.8.2 + # via + # -r requirements/quality.txt + # litellm + # openai +pydantic-core==2.20.1 + # via + # -r requirements/quality.txt + # pydantic +pygments==2.18.0 + # via + # -r requirements/quality.txt + # rich +pylint==3.2.6 + # via + # -r requirements/quality.txt + # edx-lint + # pylint-celery + # pylint-django + # pylint-plugin-utils +pylint-celery==0.3 + # via + # -r requirements/quality.txt + # edx-lint +pylint-django==2.5.5 + # via + # -r requirements/quality.txt + # edx-lint +pylint-plugin-utils==0.8.2 + # via + # -r requirements/quality.txt + # pylint-celery + # pylint-django +pypng==0.20220715.0 + # via + # -r requirements/quality.txt + # xblock-sdk +pyproject-api==1.7.1 + # via + # -r requirements/ci.txt + # tox +pyproject-hooks==1.1.0 + # via + # -r requirements/pip-tools.txt + # build + # pip-tools +pytest==8.3.2 + # via + # -r requirements/quality.txt + # pytest-cov + # pytest-django +pytest-cov==5.0.0 + # via -r requirements/quality.txt +pytest-django==4.8.0 + # via -r requirements/quality.txt +python-dateutil==2.9.0.post0 + # via + # -r requirements/quality.txt + # arrow + # botocore + # xblock +python-dotenv==1.0.1 + # via + # -r requirements/quality.txt + # litellm +python-slugify==8.0.4 + # via + # -r requirements/quality.txt + # code-annotations + # cookiecutter +pytz==2024.1 + # via + # -r requirements/quality.txt + # xblock +pyyaml==6.0.1 + # via + # -r requirements/quality.txt + # code-annotations + # cookiecutter + # edx-i18n-tools + # huggingface-hub + # xblock +referencing==0.35.1 + # via + # -r requirements/quality.txt + # jsonschema + # jsonschema-specifications +regex==2024.7.24 + # via + # -r requirements/quality.txt + # tiktoken +requests==2.32.3 + # via + # -r requirements/quality.txt + # cookiecutter + # huggingface-hub + # litellm + # tiktoken + # xblock-sdk +rich==13.7.1 + # via + # -r requirements/quality.txt + # cookiecutter +rpds-py==0.19.1 + # via + # -r requirements/quality.txt + # jsonschema + # referencing +s3transfer==0.10.2 + # via + # -r requirements/quality.txt + # boto3 +simplejson==3.19.2 + # via + # -r requirements/quality.txt + # xblock + # xblock-sdk +six==1.16.0 + # via + # -r requirements/quality.txt + # edx-lint + # fs + # fs-s3fs + # python-dateutil +sniffio==1.3.1 + # via + # -r requirements/quality.txt + # anyio + # httpx + # openai +sqlparse==0.5.1 + # via + # -r requirements/quality.txt + # django +stevedore==5.2.0 + # via + # -r requirements/quality.txt + # code-annotations +text-unidecode==1.3 + # via + # -r requirements/quality.txt + # python-slugify +tiktoken==0.7.0 + # via + # -r requirements/quality.txt + # litellm +tokenizers==0.19.1 + # via + # -r requirements/quality.txt + # litellm +tomli==2.0.1 + # via + # -r requirements/ci.txt + # -r requirements/pip-tools.txt + # -r requirements/quality.txt + # build + # coverage + # pip-tools + # pylint + # pyproject-api + # pytest + # tox +tomlkit==0.13.0 + # via + # -r requirements/quality.txt + # pylint +tox==4.16.0 + # via -r requirements/ci.txt +tqdm==4.66.4 + # via + # -r requirements/quality.txt + # huggingface-hub + # openai +types-python-dateutil==2.9.0.20240316 + # via + # -r requirements/quality.txt + # arrow +typing-extensions==4.12.2 + # via + # -r requirements/quality.txt + # annotated-types + # anyio + # asgiref + # astroid + # huggingface-hub + # openai + # pydantic + # pydantic-core + # pylint + # rich +urllib3==1.26.19 + # via + # -r requirements/quality.txt + # botocore + # requests +virtualenv==20.26.3 + # via + # -r requirements/ci.txt + # tox +web-fragments==2.2.0 + # via + # -r requirements/quality.txt + # xblock + # xblock-sdk +webob==1.8.7 + # via + # -r requirements/quality.txt + # xblock + # xblock-sdk +wheel==0.43.0 + # via + # -r requirements/pip-tools.txt + # pip-tools +xblock[django]==4.0.1 + # via + # -c requirements/constraints.txt + # -r requirements/quality.txt + # xblock-sdk +xblock-sdk==0.11.0 + # via -r requirements/quality.txt +yarl==1.9.4 + # via + # -r requirements/quality.txt + # aiohttp +zipp==3.19.2 + # via + # -r requirements/pip-tools.txt + # -r requirements/quality.txt + # importlib-metadata + # importlib-resources + +# The following packages are considered to be unsafe in a requirements file: +# pip +# setuptools diff --git a/requirements/pip-tools.in b/requirements/pip-tools.in new file mode 100644 index 0000000..0295d2c --- /dev/null +++ b/requirements/pip-tools.in @@ -0,0 +1,5 @@ +# Just the dependencies to run pip-tools, mainly for the "upgrade" make target + +-c constraints.txt + +pip-tools # Contains pip-compile, used to generate pip requirements files diff --git a/requirements/pip-tools.txt b/requirements/pip-tools.txt new file mode 100644 index 0000000..3058830 --- /dev/null +++ b/requirements/pip-tools.txt @@ -0,0 +1,34 @@ +# +# This file is autogenerated by pip-compile with Python 3.8 +# by the following command: +# +# make upgrade +# +build==1.2.1 + # via pip-tools +click==8.1.7 + # via pip-tools +importlib-metadata==6.11.0 + # via + # -c https://raw.githubusercontent.com/edx/edx-lint/master/edx_lint/files/common_constraints.txt + # build +packaging==24.1 + # via build +pip-tools==7.4.1 + # via -r requirements/pip-tools.in +pyproject-hooks==1.1.0 + # via + # build + # pip-tools +tomli==2.0.1 + # via + # build + # pip-tools +wheel==0.43.0 + # via pip-tools +zipp==3.19.2 + # via importlib-metadata + +# The following packages are considered to be unsafe in a requirements file: +# pip +# setuptools diff --git a/requirements/pip.in b/requirements/pip.in new file mode 100644 index 0000000..716c6f2 --- /dev/null +++ b/requirements/pip.in @@ -0,0 +1,6 @@ +# Core dependencies for installing other packages +-c constraints.txt + +pip +setuptools +wheel diff --git a/requirements/pip.txt b/requirements/pip.txt new file mode 100644 index 0000000..7b187b8 --- /dev/null +++ b/requirements/pip.txt @@ -0,0 +1,14 @@ +# +# This file is autogenerated by pip-compile with Python 3.8 +# by the following command: +# +# make upgrade +# +wheel==0.43.0 + # via -r requirements/pip.in + +# The following packages are considered to be unsafe in a requirements file: +pip==24.2 + # via -r requirements/pip.in +setuptools==72.1.0 + # via -r requirements/pip.in diff --git a/requirements/private.readme b/requirements/private.readme new file mode 100644 index 0000000..5600a10 --- /dev/null +++ b/requirements/private.readme @@ -0,0 +1,15 @@ +# If there are any Python packages you want to keep in your virtualenv beyond +# those listed in the official requirements files, create a "private.in" file +# and list them there. Generate the corresponding "private.txt" file pinning +# all of their indirect dependencies to specific versions as follows: + +# pip-compile private.in + +# This allows you to use "pip-sync" without removing these packages: + +# pip-sync requirements/*.txt + +# "private.in" and "private.txt" aren't checked into git to avoid merge +# conflicts, and the presence of this file allows "private.*" to be +# included in scripted pip-sync usage without requiring that those files be +# created first. diff --git a/requirements/quality.in b/requirements/quality.in new file mode 100644 index 0000000..76e2b39 --- /dev/null +++ b/requirements/quality.in @@ -0,0 +1,7 @@ +# Requirements for code quality checks +-c constraints.txt + +-r test.txt # Core and testing dependencies for this package + +edx-lint # edX pylint rules and plugins +pycodestyle # PEP 8 compliance validation diff --git a/requirements/quality.txt b/requirements/quality.txt new file mode 100644 index 0000000..a8f70cb --- /dev/null +++ b/requirements/quality.txt @@ -0,0 +1,490 @@ +# +# This file is autogenerated by pip-compile with Python 3.8 +# by the following command: +# +# make upgrade +# +aiohappyeyeballs==2.3.4 + # via + # -r requirements/test.txt + # aiohttp +aiohttp==3.10.0 + # via + # -r requirements/test.txt + # litellm +aiosignal==1.3.1 + # via + # -r requirements/test.txt + # aiohttp +annotated-types==0.7.0 + # via + # -r requirements/test.txt + # pydantic +anyio==4.4.0 + # via + # -r requirements/test.txt + # httpx + # openai +appdirs==1.4.4 + # via + # -r requirements/test.txt + # fs +arrow==1.3.0 + # via + # -r requirements/test.txt + # cookiecutter +asgiref==3.8.1 + # via + # -r requirements/test.txt + # django +astroid==3.2.4 + # via + # pylint + # pylint-celery +async-timeout==4.0.3 + # via + # -r requirements/test.txt + # aiohttp +attrs==23.2.0 + # via + # -r requirements/test.txt + # aiohttp + # jsonschema + # referencing +backports-zoneinfo==0.2.1 ; python_version < "3.9" + # via + # -c requirements/constraints.txt + # -r requirements/test.txt + # django +binaryornot==0.4.4 + # via + # -r requirements/test.txt + # cookiecutter +boto3==1.34.151 + # via + # -r requirements/test.txt + # fs-s3fs +botocore==1.34.151 + # via + # -r requirements/test.txt + # boto3 + # s3transfer +certifi==2024.7.4 + # via + # -r requirements/test.txt + # httpcore + # httpx + # requests +chardet==5.2.0 + # via + # -r requirements/test.txt + # binaryornot +charset-normalizer==3.3.2 + # via + # -r requirements/test.txt + # requests +click==8.1.7 + # via + # -r requirements/test.txt + # click-log + # code-annotations + # cookiecutter + # edx-lint + # litellm +click-log==0.4.0 + # via edx-lint +code-annotations==1.8.0 + # via edx-lint +cookiecutter==2.6.0 + # via + # -r requirements/test.txt + # xblock-sdk +coverage[toml]==7.6.0 + # via + # -r requirements/test.txt + # pytest-cov +ddt==1.7.2 + # via -r requirements/test.txt +dill==0.3.8 + # via pylint +distro==1.9.0 + # via + # -r requirements/test.txt + # openai +django==4.2.14 + # via + # -c https://raw.githubusercontent.com/edx/edx-lint/master/edx_lint/files/common_constraints.txt + # -r requirements/test.txt + # django-appconf + # django-statici18n + # edx-i18n-tools + # openedx-django-pyfs + # xblock-sdk +django-appconf==1.0.6 + # via + # -r requirements/test.txt + # django-statici18n +django-statici18n==2.5.0 + # via -r requirements/test.txt +edx-i18n-tools==1.6.2 + # via -r requirements/test.txt +edx-lint==5.3.7 + # via -r requirements/quality.in +exceptiongroup==1.2.2 + # via + # -r requirements/test.txt + # anyio + # pytest +filelock==3.15.4 + # via + # -r requirements/test.txt + # huggingface-hub +frozenlist==1.4.1 + # via + # -r requirements/test.txt + # aiohttp + # aiosignal +fs==2.4.16 + # via + # -r requirements/test.txt + # fs-s3fs + # openedx-django-pyfs + # xblock +fs-s3fs==1.1.1 + # via + # -r requirements/test.txt + # openedx-django-pyfs + # xblock-sdk +fsspec==2024.6.1 + # via + # -r requirements/test.txt + # huggingface-hub +h11==0.14.0 + # via + # -r requirements/test.txt + # httpcore +httpcore==1.0.5 + # via + # -r requirements/test.txt + # httpx +httpx==0.27.0 + # via + # -r requirements/test.txt + # openai +huggingface-hub==0.24.5 + # via + # -r requirements/test.txt + # tokenizers +idna==3.7 + # via + # -r requirements/test.txt + # anyio + # httpx + # requests + # yarl +importlib-metadata==6.11.0 + # via + # -c https://raw.githubusercontent.com/edx/edx-lint/master/edx_lint/files/common_constraints.txt + # -r requirements/test.txt + # litellm +importlib-resources==6.4.0 + # via + # -r requirements/test.txt + # jsonschema + # jsonschema-specifications +iniconfig==2.0.0 + # via + # -r requirements/test.txt + # pytest +isort==5.13.2 + # via pylint +jinja2==3.1.4 + # via + # -r requirements/test.txt + # code-annotations + # cookiecutter + # litellm +jmespath==1.0.1 + # via + # -r requirements/test.txt + # boto3 + # botocore +jsonschema==4.23.0 + # via + # -r requirements/test.txt + # litellm +jsonschema-specifications==2023.12.1 + # via + # -r requirements/test.txt + # jsonschema +lazy==1.6 + # via + # -r requirements/test.txt + # xblock +litellm==1.42.6 + # via -r requirements/test.txt +lxml==5.2.2 + # via + # -r requirements/test.txt + # edx-i18n-tools + # xblock + # xblock-sdk +mako==1.3.5 + # via + # -r requirements/test.txt + # xblock +markdown-it-py==3.0.0 + # via + # -r requirements/test.txt + # rich +markupsafe==2.1.5 + # via + # -r requirements/test.txt + # jinja2 + # mako + # xblock +mccabe==0.7.0 + # via pylint +mdurl==0.1.2 + # via + # -r requirements/test.txt + # markdown-it-py +mock==5.1.0 + # via -r requirements/test.txt +multidict==6.0.5 + # via + # -r requirements/test.txt + # aiohttp + # yarl +openai==1.37.1 + # via + # -r requirements/test.txt + # litellm +openedx-django-pyfs==3.6.0 + # via + # -r requirements/test.txt + # xblock +packaging==24.1 + # via + # -r requirements/test.txt + # huggingface-hub + # pytest +path==16.16.0 + # via + # -r requirements/test.txt + # edx-i18n-tools +pbr==6.0.0 + # via stevedore +pkgutil-resolve-name==1.3.10 + # via + # -r requirements/test.txt + # jsonschema +platformdirs==4.2.2 + # via pylint +pluggy==1.5.0 + # via + # -r requirements/test.txt + # pytest +polib==1.2.0 + # via + # -r requirements/test.txt + # edx-i18n-tools +pycodestyle==2.12.0 + # via -r requirements/quality.in +pydantic==2.8.2 + # via + # -r requirements/test.txt + # litellm + # openai +pydantic-core==2.20.1 + # via + # -r requirements/test.txt + # pydantic +pygments==2.18.0 + # via + # -r requirements/test.txt + # rich +pylint==3.2.6 + # via + # edx-lint + # pylint-celery + # pylint-django + # pylint-plugin-utils +pylint-celery==0.3 + # via edx-lint +pylint-django==2.5.5 + # via edx-lint +pylint-plugin-utils==0.8.2 + # via + # pylint-celery + # pylint-django +pypng==0.20220715.0 + # via + # -r requirements/test.txt + # xblock-sdk +pytest==8.3.2 + # via + # -r requirements/test.txt + # pytest-cov + # pytest-django +pytest-cov==5.0.0 + # via -r requirements/test.txt +pytest-django==4.8.0 + # via -r requirements/test.txt +python-dateutil==2.9.0.post0 + # via + # -r requirements/test.txt + # arrow + # botocore + # xblock +python-dotenv==1.0.1 + # via + # -r requirements/test.txt + # litellm +python-slugify==8.0.4 + # via + # -r requirements/test.txt + # code-annotations + # cookiecutter +pytz==2024.1 + # via + # -r requirements/test.txt + # xblock +pyyaml==6.0.1 + # via + # -r requirements/test.txt + # code-annotations + # cookiecutter + # edx-i18n-tools + # huggingface-hub + # xblock +referencing==0.35.1 + # via + # -r requirements/test.txt + # jsonschema + # jsonschema-specifications +regex==2024.7.24 + # via + # -r requirements/test.txt + # tiktoken +requests==2.32.3 + # via + # -r requirements/test.txt + # cookiecutter + # huggingface-hub + # litellm + # tiktoken + # xblock-sdk +rich==13.7.1 + # via + # -r requirements/test.txt + # cookiecutter +rpds-py==0.19.1 + # via + # -r requirements/test.txt + # jsonschema + # referencing +s3transfer==0.10.2 + # via + # -r requirements/test.txt + # boto3 +simplejson==3.19.2 + # via + # -r requirements/test.txt + # xblock + # xblock-sdk +six==1.16.0 + # via + # -r requirements/test.txt + # edx-lint + # fs + # fs-s3fs + # python-dateutil +sniffio==1.3.1 + # via + # -r requirements/test.txt + # anyio + # httpx + # openai +sqlparse==0.5.1 + # via + # -r requirements/test.txt + # django +stevedore==5.2.0 + # via code-annotations +text-unidecode==1.3 + # via + # -r requirements/test.txt + # python-slugify +tiktoken==0.7.0 + # via + # -r requirements/test.txt + # litellm +tokenizers==0.19.1 + # via + # -r requirements/test.txt + # litellm +tomli==2.0.1 + # via + # -r requirements/test.txt + # coverage + # pylint + # pytest +tomlkit==0.13.0 + # via pylint +tqdm==4.66.4 + # via + # -r requirements/test.txt + # huggingface-hub + # openai +types-python-dateutil==2.9.0.20240316 + # via + # -r requirements/test.txt + # arrow +typing-extensions==4.12.2 + # via + # -r requirements/test.txt + # annotated-types + # anyio + # asgiref + # astroid + # huggingface-hub + # openai + # pydantic + # pydantic-core + # pylint + # rich +urllib3==1.26.19 + # via + # -r requirements/test.txt + # botocore + # requests +web-fragments==2.2.0 + # via + # -r requirements/test.txt + # xblock + # xblock-sdk +webob==1.8.7 + # via + # -r requirements/test.txt + # xblock + # xblock-sdk +xblock[django]==4.0.1 + # via + # -c requirements/constraints.txt + # -r requirements/test.txt + # xblock-sdk +xblock-sdk==0.11.0 + # via -r requirements/test.txt +yarl==1.9.4 + # via + # -r requirements/test.txt + # aiohttp +zipp==3.19.2 + # via + # -r requirements/test.txt + # importlib-metadata + # importlib-resources + +# The following packages are considered to be unsafe in a requirements file: +# setuptools diff --git a/requirements/test.in b/requirements/test.in new file mode 100644 index 0000000..d5bb585 --- /dev/null +++ b/requirements/test.in @@ -0,0 +1,15 @@ +# Requirements for test runs. +-c constraints.txt + +-r base.txt # Core dependencies for this package + +pytest-cov # pytest extension for code coverage statistics +pytest-django # pytest extension for better Django support +ddt # data-driven tests + +mock # required by the workbench +openedx-django-pyfs # required by the workbench + +edx-i18n-tools # For i18n_tool dummy + +xblock-sdk>0.7 # workbench diff --git a/requirements/test.txt b/requirements/test.txt new file mode 100644 index 0000000..39a089c --- /dev/null +++ b/requirements/test.txt @@ -0,0 +1,404 @@ +# +# This file is autogenerated by pip-compile with Python 3.8 +# by the following command: +# +# make upgrade +# +aiohappyeyeballs==2.3.4 + # via + # -r requirements/base.txt + # aiohttp +aiohttp==3.10.0 + # via + # -r requirements/base.txt + # litellm +aiosignal==1.3.1 + # via + # -r requirements/base.txt + # aiohttp +annotated-types==0.7.0 + # via + # -r requirements/base.txt + # pydantic +anyio==4.4.0 + # via + # -r requirements/base.txt + # httpx + # openai +appdirs==1.4.4 + # via + # -r requirements/base.txt + # fs +arrow==1.3.0 + # via cookiecutter +asgiref==3.8.1 + # via + # -r requirements/base.txt + # django +async-timeout==4.0.3 + # via + # -r requirements/base.txt + # aiohttp +attrs==23.2.0 + # via + # -r requirements/base.txt + # aiohttp + # jsonschema + # referencing +backports-zoneinfo==0.2.1 ; python_version < "3.9" + # via + # -c requirements/constraints.txt + # -r requirements/base.txt + # django +binaryornot==0.4.4 + # via cookiecutter +boto3==1.34.151 + # via + # -r requirements/base.txt + # fs-s3fs +botocore==1.34.151 + # via + # -r requirements/base.txt + # boto3 + # s3transfer +certifi==2024.7.4 + # via + # -r requirements/base.txt + # httpcore + # httpx + # requests +chardet==5.2.0 + # via binaryornot +charset-normalizer==3.3.2 + # via + # -r requirements/base.txt + # requests +click==8.1.7 + # via + # -r requirements/base.txt + # cookiecutter + # litellm +cookiecutter==2.6.0 + # via xblock-sdk +coverage[toml]==7.6.0 + # via pytest-cov +ddt==1.7.2 + # via -r requirements/test.in +distro==1.9.0 + # via + # -r requirements/base.txt + # openai + # via + # -c https://raw.githubusercontent.com/edx/edx-lint/master/edx_lint/files/common_constraints.txt + # -r requirements/base.txt + # django-appconf + # django-statici18n + # edx-i18n-tools + # openedx-django-pyfs + # xblock-sdk +django-appconf==1.0.6 + # via + # -r requirements/base.txt + # django-statici18n +django-statici18n==2.5.0 + # via -r requirements/base.txt +edx-i18n-tools==1.6.2 + # via -r requirements/test.in +exceptiongroup==1.2.2 + # via + # -r requirements/base.txt + # anyio + # pytest +filelock==3.15.4 + # via + # -r requirements/base.txt + # huggingface-hub +frozenlist==1.4.1 + # via + # -r requirements/base.txt + # aiohttp + # aiosignal +fs==2.4.16 + # via + # -r requirements/base.txt + # fs-s3fs + # openedx-django-pyfs + # xblock +fs-s3fs==1.1.1 + # via + # -r requirements/base.txt + # openedx-django-pyfs + # xblock-sdk +fsspec==2024.6.1 + # via + # -r requirements/base.txt + # huggingface-hub +h11==0.14.0 + # via + # -r requirements/base.txt + # httpcore +httpcore==1.0.5 + # via + # -r requirements/base.txt + # httpx +httpx==0.27.0 + # via + # -r requirements/base.txt + # openai +huggingface-hub==0.24.5 + # via + # -r requirements/base.txt + # tokenizers +idna==3.7 + # via + # -r requirements/base.txt + # anyio + # httpx + # requests + # yarl +importlib-metadata==6.11.0 + # via + # -c https://raw.githubusercontent.com/edx/edx-lint/master/edx_lint/files/common_constraints.txt + # -r requirements/base.txt + # litellm +importlib-resources==6.4.0 + # via + # -r requirements/base.txt + # jsonschema + # jsonschema-specifications +iniconfig==2.0.0 + # via pytest +jinja2==3.1.4 + # via + # -r requirements/base.txt + # cookiecutter + # litellm +jmespath==1.0.1 + # via + # -r requirements/base.txt + # boto3 + # botocore +jsonschema==4.23.0 + # via + # -r requirements/base.txt + # litellm +jsonschema-specifications==2023.12.1 + # via + # -r requirements/base.txt + # jsonschema +lazy==1.6 + # via + # -r requirements/base.txt + # xblock +litellm==1.42.6 + # via -r requirements/base.txt +lxml==5.2.2 + # via + # -r requirements/base.txt + # edx-i18n-tools + # xblock + # xblock-sdk +mako==1.3.5 + # via + # -r requirements/base.txt + # xblock +markdown-it-py==3.0.0 + # via rich +markupsafe==2.1.5 + # via + # -r requirements/base.txt + # jinja2 + # mako + # xblock +mdurl==0.1.2 + # via markdown-it-py +mock==5.1.0 + # via -r requirements/test.in +multidict==6.0.5 + # via + # -r requirements/base.txt + # aiohttp + # yarl +openai==1.37.1 + # via + # -r requirements/base.txt + # litellm +openedx-django-pyfs==3.6.0 + # via + # -r requirements/base.txt + # -r requirements/test.in + # xblock +packaging==24.1 + # via + # -r requirements/base.txt + # huggingface-hub + # pytest +path==16.16.0 + # via edx-i18n-tools +pkgutil-resolve-name==1.3.10 + # via + # -r requirements/base.txt + # jsonschema +pluggy==1.5.0 + # via pytest +polib==1.2.0 + # via edx-i18n-tools +pydantic==2.8.2 + # via + # -r requirements/base.txt + # litellm + # openai +pydantic-core==2.20.1 + # via + # -r requirements/base.txt + # pydantic +pygments==2.18.0 + # via rich +pypng==0.20220715.0 + # via xblock-sdk +pytest==8.3.2 + # via + # pytest-cov + # pytest-django +pytest-cov==5.0.0 + # via -r requirements/test.in +pytest-django==4.8.0 + # via -r requirements/test.in +python-dateutil==2.9.0.post0 + # via + # -r requirements/base.txt + # arrow + # botocore + # xblock +python-dotenv==1.0.1 + # via + # -r requirements/base.txt + # litellm +python-slugify==8.0.4 + # via cookiecutter +pytz==2024.1 + # via + # -r requirements/base.txt + # xblock +pyyaml==6.0.1 + # via + # -r requirements/base.txt + # cookiecutter + # edx-i18n-tools + # huggingface-hub + # xblock +referencing==0.35.1 + # via + # -r requirements/base.txt + # jsonschema + # jsonschema-specifications +regex==2024.7.24 + # via + # -r requirements/base.txt + # tiktoken +requests==2.32.3 + # via + # -r requirements/base.txt + # cookiecutter + # huggingface-hub + # litellm + # tiktoken + # xblock-sdk +rich==13.7.1 + # via cookiecutter +rpds-py==0.19.1 + # via + # -r requirements/base.txt + # jsonschema + # referencing +s3transfer==0.10.2 + # via + # -r requirements/base.txt + # boto3 +simplejson==3.19.2 + # via + # -r requirements/base.txt + # xblock + # xblock-sdk +six==1.16.0 + # via + # -r requirements/base.txt + # fs + # fs-s3fs + # python-dateutil +sniffio==1.3.1 + # via + # -r requirements/base.txt + # anyio + # httpx + # openai +sqlparse==0.5.1 + # via + # -r requirements/base.txt + # django +text-unidecode==1.3 + # via python-slugify +tiktoken==0.7.0 + # via + # -r requirements/base.txt + # litellm +tokenizers==0.19.1 + # via + # -r requirements/base.txt + # litellm +tomli==2.0.1 + # via + # coverage + # pytest +tqdm==4.66.4 + # via + # -r requirements/base.txt + # huggingface-hub + # openai +types-python-dateutil==2.9.0.20240316 + # via arrow +typing-extensions==4.12.2 + # via + # -r requirements/base.txt + # annotated-types + # anyio + # asgiref + # huggingface-hub + # openai + # pydantic + # pydantic-core + # rich +urllib3==1.26.19 + # via + # -r requirements/base.txt + # botocore + # requests +web-fragments==2.2.0 + # via + # -r requirements/base.txt + # xblock + # xblock-sdk +webob==1.8.7 + # via + # -r requirements/base.txt + # xblock + # xblock-sdk +xblock[django]==4.0.1 + # via + # -c requirements/constraints.txt + # -r requirements/base.txt + # xblock-sdk +xblock-sdk==0.11.0 + # via -r requirements/test.in +yarl==1.9.4 + # via + # -r requirements/base.txt + # aiohttp +zipp==3.19.2 + # via + # -r requirements/base.txt + # importlib-metadata + # importlib-resources + +# The following packages are considered to be unsafe in a requirements file: +# setuptools diff --git a/requirements/workbench.txt b/requirements/workbench.txt new file mode 100644 index 0000000..e69de29 diff --git a/setup.py b/setup.py new file mode 100644 index 0000000..5254944 --- /dev/null +++ b/setup.py @@ -0,0 +1,43 @@ +"""Setup for shortanswer XBlock.""" + +import os + +from setuptools import setup + + +def package_data(pkg, roots): + """Generic function to find package_data. + + All of the files under each of the `roots` will be declared as package + data for package `pkg`. + + """ + data = [] + for root in roots: + for dirname, _, files in os.walk(os.path.join(pkg, root)): + for fname in files: + data.append(os.path.relpath(os.path.join(dirname, fname), pkg)) + + return {pkg: data} + + +setup( + name="xblock-ai-eval", + version="0.1", + description="XBlocks to write short text and code entries with AI-driven evaluation", + license="AGPL v3", + packages=[ + "ai_eval", + ], + install_requires=[ + "XBlock", + "litellm>=1.42", + ], + entry_points={ + "xblock.v1": [ + "shortanswer_ai_eval = ai_eval:ShortAnswerAIEvalXBlock", + "coding_ai_eval = ai_eval:CodingAIEvalXBlock", + ] + }, + package_data=package_data("ai_eval", ["static", "public", "templates"]), +)