From 81479ef55a9be92329be35af999f3197fd6c06e2 Mon Sep 17 00:00:00 2001 From: WMF2906 Date: Mon, 25 Mar 2024 15:55:59 -0400 Subject: [PATCH 01/17] added examples folder, changed examples.py to revertrisk_examples.py, and added type hints to function --- .DS_Store | Bin 0 -> 6148 bytes examples/revertrisk_examples.py | 27 +++++++++++++++++++++++++++ 2 files changed, 27 insertions(+) create mode 100644 .DS_Store create mode 100644 examples/revertrisk_examples.py diff --git a/.DS_Store b/.DS_Store new file mode 100644 index 0000000000000000000000000000000000000000..a3da8129405cd069bf2b64ca624758aa8123b64a GIT binary patch literal 6148 zcmeHKPixyS6n{$6RwfK`SfNKjuUVI@?V$AHX6|8!Uh1*I{*c+RNz5F}#K|%U0iV~~ z?)x750{sewewV@ao}`R~WNfE0Ry}z7Nl))tdOz8c1purwiP``S0N|*E6$gtALj9y` zQZW|lWa=3?q!2^#Je9pQZ)^A$8PJOx!zTz}2utf1rZU6{(~I#H_0bO{Dg};fyy72D zi`@8s3-dH7#;w*3t5j=S+dF)R*ZDhtAgBH~7*C2$FnU9+7gDC-q8@}VlX%)~JbWgz zagb#3NChNOj4p3qC0Qh=9XZLOLdE*JgFD>mHuh$-qr<07aoj$hH^uDaNvkQ)FrPbo zcmMI}W%olm%;aY^b71(MDtTaV0asXA%PZ}-{hl1=3#Uy!L+N=YcOHHD{puhb2tMJE)WlJ9V7YzmsXHwbg;C7*tB99ungR52FzZ_ z>-U-ko4jSfGO&pO+8+cep=+?zsJ0F))D-}+hGr#Lr(Z^j5e8j@rAF*QVLB91hca`; zU^*P_!uYucON}}ln7Mo~Gcq$b6sAVU=L_Wy%++X1%YbEIm4T{mHt766|NZ@cHORIs z1D1jRiUC&he6NEknX`2*IXY_v>U&fY@+&p|3c-pxiqV&j;yqL)XctsLbPbjo(Sl-s O1QZRnungQO13v*sh=}k2 literal 0 HcmV?d00001 diff --git a/examples/revertrisk_examples.py b/examples/revertrisk_examples.py new file mode 100644 index 0000000..f1e96ef --- /dev/null +++ b/examples/revertrisk_examples.py @@ -0,0 +1,27 @@ +import json +import requests + +def revert_risk_api_request(language: str, revision_id: int): + use_auth = False + inference_url = 'https://api.wikimedia.org/service/lw/inference/v1/models/' + language + '-reverted:predict' + + if use_auth: + + headers = { + 'Authorization': 'Bearer YOUR_ACCESS_TOKEN', + 'User-Agent': 'YOUR_APP_NAME (YOUR_EMAIL_OR_CONTACT_PAGE)', + 'Content-type': 'application/json' + } + else: + headers = {} + + data = {"rev_id": revision_id} + response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + return response.json() + + +language = "viwiki" +revision_id = 12345 +response = revert_risk_api_request(language, revision_id) + +print(response) From 788689a415035c36f9f3b14cbb671a36f0d540a8 Mon Sep 17 00:00:00 2001 From: mercelisvaughan <55514935+mercelisvaughan@users.noreply.github.com> Date: Wed, 20 Mar 2024 19:46:43 -0400 Subject: [PATCH 02/17] Update README.md --- README.md | 14 ++++---------- 1 file changed, 4 insertions(+), 10 deletions(-) diff --git a/README.md b/README.md index 2ebc258..dafe282 100644 --- a/README.md +++ b/README.md @@ -1,12 +1,6 @@ # liftwing-python +

LiftWing-python

+ +This is a Python module that *sends a user's request to the LiftWing API and gets back a response*. + -This project involves building a python package that can act as a model registry for the machine learning models deployed on Lift Wing.
A model registry acts as the source of truth for the deployed models and their versions offering two main benefits: -* Versioning and tracking of models: this allows an easier access to model version and tracking -* Collaboration and reproducibility: in order to download a model the user only needs to interact with the registry. -Implementation Proposal
A python package that allows that has different install options according to the model as each model server has different package requirements. The user, after installing the package, will be able to load a Lift Wing model and make predictions.
Taking into consideration the short duration of the internship as well as the fact that we want the person to get to know the Wikimedia community, our way of working as well as get the chance to study and dive into technical topics, the package will first deal with 1-2 models in order to create a complete proof of concept for this work. Also, to avoid blocking this work by other systems/factors or permissions it will be based on our public interfaces:
The python package will have a repository on GitHub with CI/CD setup using Github Actions that will automatically upload the python package to the PyPI repository.
Models for the packages will be fetched by the public analytics repository https://analytics.wikimedia.org/published/wmf-ml-models/ -There will be two modes of operation for each model: -* Offline: the user can download and load the model and start making predictions with it. This is particularly useful for experimentation or in the case when someone wants to make a big number of batch requests that would otherwise fail due to rate limiting. -* Online: The user can make requests to the public APIs (Lift Wing API Gateway) using the package as a client. -Notes/Considerations: -* We would have to figure out a (nice) way to integrate this with the deployment charts repo in order to get the model version we need to deploy. -* Model’s python dependencies: Each model has been developed separately and may require different python libraries and versions. This means that the python package should have different installation options which will reflect the dependencies of a specific model. From c1260f532ee91079bf4f00705af026c89b93c30d Mon Sep 17 00:00:00 2001 From: mercelisvaughan <55514935+mercelisvaughan@users.noreply.github.com> Date: Wed, 20 Mar 2024 19:48:30 -0400 Subject: [PATCH 03/17] Add files via upload --- example.py | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+) create mode 100644 example.py diff --git a/example.py b/example.py new file mode 100644 index 0000000..d498169 --- /dev/null +++ b/example.py @@ -0,0 +1,28 @@ +import json +import requests + +def revert_risk_api_request(language, revision_id): + + use_auth = False + inference_url = 'https://api.wikimedia.org/service/lw/inference/v1/models/' + language + '-reverted:predict' + + if use_auth: + + headers = { + 'Authorization': 'Bearer YOUR_ACCESS_TOKEN', + 'User-Agent': 'YOUR_APP_NAME (YOUR_EMAIL_OR_CONTACT_PAGE)', + 'Content-type': 'application/json' + } + else: + headers = {} + + data = {"rev_id": revision_id} + response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + return response.json() + + +language = "viwiki" +revision_id = 12345 +response = revert_risk_api_request(language, revision_id) + +print(response) From f58bfabf5a6f9ee362fcd19f95fa795ee739bf67 Mon Sep 17 00:00:00 2001 From: mercelisvaughan <55514935+mercelisvaughan@users.noreply.github.com> Date: Wed, 20 Mar 2024 19:59:51 -0400 Subject: [PATCH 04/17] a function that will make a request to revertrisk language agnostic API that accepts a string for language and an integer for revision id, it will make the request and return the json response --- example.py | 3 --- 1 file changed, 3 deletions(-) diff --git a/example.py b/example.py index d498169..6bdd9d1 100644 --- a/example.py +++ b/example.py @@ -2,7 +2,6 @@ import requests def revert_risk_api_request(language, revision_id): - use_auth = False inference_url = 'https://api.wikimedia.org/service/lw/inference/v1/models/' + language + '-reverted:predict' @@ -20,9 +19,7 @@ def revert_risk_api_request(language, revision_id): response = requests.post(inference_url, headers=headers, data=json.dumps(data)) return response.json() - language = "viwiki" revision_id = 12345 response = revert_risk_api_request(language, revision_id) - print(response) From 6740d3f0878015472ba5d97efc6acb04a46f0205 Mon Sep 17 00:00:00 2001 From: mercelisvaughan <55514935+mercelisvaughan@users.noreply.github.com> Date: Mon, 25 Mar 2024 15:23:09 -0400 Subject: [PATCH 05/17] Update README.md with longer explanation --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index dafe282..c8f580d 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@ # liftwing-python

LiftWing-python

-This is a Python module that *sends a user's request to the LiftWing API and gets back a response*. - +This is a Python package that acts as a client and allows users to make requests to the LiftWing API. +Its purpose is to allow users to interact with the API by writing python code instead of manipulating HTTP requests. From cb99e1c6adc9aa81dff44038a4396f7e5026948c Mon Sep 17 00:00:00 2001 From: WMF2906 Date: Tue, 26 Mar 2024 10:54:24 -0400 Subject: [PATCH 06/17] added examples dir, renamed file, added more function arguments and added validation for response and unit test package --- example.py | 25 ------------------------- examples/revertrisk_examples.py | 18 +++++++++++------- tests/revertrisk_examplestest.py | 0 3 files changed, 11 insertions(+), 32 deletions(-) delete mode 100644 example.py create mode 100644 tests/revertrisk_examplestest.py diff --git a/example.py b/example.py deleted file mode 100644 index 6bdd9d1..0000000 --- a/example.py +++ /dev/null @@ -1,25 +0,0 @@ -import json -import requests - -def revert_risk_api_request(language, revision_id): - use_auth = False - inference_url = 'https://api.wikimedia.org/service/lw/inference/v1/models/' + language + '-reverted:predict' - - if use_auth: - - headers = { - 'Authorization': 'Bearer YOUR_ACCESS_TOKEN', - 'User-Agent': 'YOUR_APP_NAME (YOUR_EMAIL_OR_CONTACT_PAGE)', - 'Content-type': 'application/json' - } - else: - headers = {} - - data = {"rev_id": revision_id} - response = requests.post(inference_url, headers=headers, data=json.dumps(data)) - return response.json() - -language = "viwiki" -revision_id = 12345 -response = revert_risk_api_request(language, revision_id) -print(response) diff --git a/examples/revertrisk_examples.py b/examples/revertrisk_examples.py index f1e96ef..79468cd 100644 --- a/examples/revertrisk_examples.py +++ b/examples/revertrisk_examples.py @@ -1,15 +1,14 @@ import json import requests -def revert_risk_api_request(language: str, revision_id: int): +def revert_risk_api_request(language: str, revision_id: int, use_auth: bool, access_token: str, user_agent: str): use_auth = False - inference_url = 'https://api.wikimedia.org/service/lw/inference/v1/models/' + language + '-reverted:predict' - + inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict" if use_auth: headers = { - 'Authorization': 'Bearer YOUR_ACCESS_TOKEN', - 'User-Agent': 'YOUR_APP_NAME (YOUR_EMAIL_OR_CONTACT_PAGE)', + 'Authorization': f'Bearer {access_token}', + 'User-Agent': user_agent, 'Content-type': 'application/json' } else: @@ -17,11 +16,16 @@ def revert_risk_api_request(language: str, revision_id: int): data = {"rev_id": revision_id} response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + if response.status_code == 200: + return response.json() + else: + response.status_code == 400 + #raise ValueError(f"Unexpected error occurred: {response.status_code}") + return response.json() language = "viwiki" revision_id = 12345 -response = revert_risk_api_request(language, revision_id) - +response = revert_risk_api_request(language, revision_id, use_auth=False, access_token="", user_agent="") print(response) diff --git a/tests/revertrisk_examplestest.py b/tests/revertrisk_examplestest.py new file mode 100644 index 0000000..e69de29 From 82d2e0a885acb0c94844ef6e88abd788db8ebf94 Mon Sep 17 00:00:00 2001 From: WMF2906 Date: Fri, 29 Mar 2024 16:34:02 -0400 Subject: [PATCH 07/17] added extra test --- .vscode/settings.json | 5 +++++ examples/__init__.py | 0 examples/revertrisk_examples.py | 12 ++++++++---- tests/revertrisk_examplestest.py | 25 +++++++++++++++++++++++++ 4 files changed, 38 insertions(+), 4 deletions(-) create mode 100644 .vscode/settings.json create mode 100644 examples/__init__.py diff --git a/.vscode/settings.json b/.vscode/settings.json new file mode 100644 index 0000000..71e6517 --- /dev/null +++ b/.vscode/settings.json @@ -0,0 +1,5 @@ +{ + "python.analysis.extraPaths": [ + "./examples" + ] +} \ No newline at end of file diff --git a/examples/__init__.py b/examples/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/examples/revertrisk_examples.py b/examples/revertrisk_examples.py index 79468cd..fd7d87f 100644 --- a/examples/revertrisk_examples.py +++ b/examples/revertrisk_examples.py @@ -1,7 +1,7 @@ import json import requests -def revert_risk_api_request(language: str, revision_id: int, use_auth: bool, access_token: str, user_agent: str): +def revert_risk_api_request(language: str, revision_id: int): use_auth = False inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict" if use_auth: @@ -20,12 +20,16 @@ def revert_risk_api_request(language: str, revision_id: int, use_auth: bool, acc return response.json() else: response.status_code == 400 - #raise ValueError(f"Unexpected error occurred: {response.status_code}") - - return response.json() + raise ValueError(f"Unexpected error occurred: {response.status_code}") language = "viwiki" revision_id = 12345 +<<<<<<< HEAD response = revert_risk_api_request(language, revision_id, use_auth=False, access_token="", user_agent="") +======= +response = revert_risk_api_request(language, revision_id) + +>>>>>>> 8997b49 (added test package, removed extra arguments from function) print(response) + diff --git a/tests/revertrisk_examplestest.py b/tests/revertrisk_examplestest.py index e69de29..e38bb2d 100644 --- a/tests/revertrisk_examplestest.py +++ b/tests/revertrisk_examplestest.py @@ -0,0 +1,25 @@ +import unittest +from unittest.mock import patch +from examples.revertrisk_examples import revert_risk_api_request + + +class RevertRisk_ExamplesTest(unittest.TestCase): + + @patch('revertrisk_examples.requests.post') + def revert_risk_example_test_200(self, mock_post): + mock_post.return_value.status_code = 200 + mock_post.return_value.json.return_value = {'key': 'value'} + + result = revert_risk_api_request("en", 12345) + + self.assertEqual(result, {'key': 'value'}) + + @patch('revertrisk_examples.requests.post') + def test_revert_risk_api_request_failure(self, mock_post): + mock_post.return_value.status_code = 400 + + with self.assertRaises(ValueError): + revert_risk_api_request("en", 12345) + +if __name__ == '__main__': + unittest.main() \ No newline at end of file From 57c8a37ad388d7b5f4e9eb1cecbff5ec4060fa70 Mon Sep 17 00:00:00 2001 From: WMF2906 Date: Tue, 2 Apr 2024 11:56:25 -0400 Subject: [PATCH 08/17] corrected 2 junit tests --- examples/revertrisk_examples.py | 7 +++---- tests/revertrisk_examplestest.py | 8 ++++---- 2 files changed, 7 insertions(+), 8 deletions(-) diff --git a/examples/revertrisk_examples.py b/examples/revertrisk_examples.py index fd7d87f..429c361 100644 --- a/examples/revertrisk_examples.py +++ b/examples/revertrisk_examples.py @@ -25,11 +25,10 @@ def revert_risk_api_request(language: str, revision_id: int): language = "viwiki" revision_id = 12345 -<<<<<<< HEAD -response = revert_risk_api_request(language, revision_id, use_auth=False, access_token="", user_agent="") -======= + response = revert_risk_api_request(language, revision_id) ->>>>>>> 8997b49 (added test package, removed extra arguments from function) + print(response) + diff --git a/tests/revertrisk_examplestest.py b/tests/revertrisk_examplestest.py index e38bb2d..b6fb377 100644 --- a/tests/revertrisk_examplestest.py +++ b/tests/revertrisk_examplestest.py @@ -5,8 +5,8 @@ class RevertRisk_ExamplesTest(unittest.TestCase): - @patch('revertrisk_examples.requests.post') - def revert_risk_example_test_200(self, mock_post): + @patch('examples.revertrisk_examples.requests.post') + def test_revert_risk_example_test_200(self, mock_post): mock_post.return_value.status_code = 200 mock_post.return_value.json.return_value = {'key': 'value'} @@ -14,7 +14,7 @@ def revert_risk_example_test_200(self, mock_post): self.assertEqual(result, {'key': 'value'}) - @patch('revertrisk_examples.requests.post') + @patch('examples.revertrisk_examples.requests.post') def test_revert_risk_api_request_failure(self, mock_post): mock_post.return_value.status_code = 400 @@ -22,4 +22,4 @@ def test_revert_risk_api_request_failure(self, mock_post): revert_risk_api_request("en", 12345) if __name__ == '__main__': - unittest.main() \ No newline at end of file + unittest.main() From 642e85b912ba1c181aa7e96fcb0f8d1ff1b53788 Mon Sep 17 00:00:00 2001 From: WMF2906 Date: Tue, 2 Apr 2024 17:50:23 -0400 Subject: [PATCH 09/17] added .toml and src package, added one unit test --- pyproject.toml | 0 src/liftwing_api/__init__.py | 0 tests/revertrisk_examplestest.py | 9 +++++++++ 3 files changed, 9 insertions(+) create mode 100644 pyproject.toml create mode 100644 src/liftwing_api/__init__.py diff --git a/pyproject.toml b/pyproject.toml new file mode 100644 index 0000000..e69de29 diff --git a/src/liftwing_api/__init__.py b/src/liftwing_api/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/tests/revertrisk_examplestest.py b/tests/revertrisk_examplestest.py index b6fb377..4ebb52b 100644 --- a/tests/revertrisk_examplestest.py +++ b/tests/revertrisk_examplestest.py @@ -21,5 +21,14 @@ def test_revert_risk_api_request_failure(self, mock_post): with self.assertRaises(ValueError): revert_risk_api_request("en", 12345) + @patch('examples.revertrisk_examples.requests.post') + def test_revert_risk_api_request_empty_response(self, mock_post): + mock_post.return_value.status_code = 200 + mock_post.return_value.json.return_value = {} + + result = revert_risk_api_request("en", 12345) + + self.assertEqual(result, {}) + if __name__ == '__main__': unittest.main() From f8fa51455f0c19abef06a4df4d37d595476b2284 Mon Sep 17 00:00:00 2001 From: WMF2906 Date: Wed, 3 Apr 2024 21:49:20 -0400 Subject: [PATCH 10/17] updated .toml file, added models package, added .vscode and .ds_store to .gitignore --- pyproject.toml | 12 ++++++++++++ src/liftwing_api/models/revertrisk.py | 0 2 files changed, 12 insertions(+) create mode 100644 src/liftwing_api/models/revertrisk.py diff --git a/pyproject.toml b/pyproject.toml index e69de29..90cd142 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -0,0 +1,12 @@ +[tool.poetry] +name = "liftwing-python" +version = "0.1.0" +description = "Users will be able to retrieve JSON responses from their respective wiki APIs" + +[tool.poetry.dependencies] +python = "^3.10 || ^3.11 || ^3.12" +requests = "^2.0" + +[build-system] +requires = ["poetry-core>=1.0.0"] +build-backend = "poetry.core.masonry.api" diff --git a/src/liftwing_api/models/revertrisk.py b/src/liftwing_api/models/revertrisk.py new file mode 100644 index 0000000..e69de29 From 21a5235a03cc5a7230302a36bc2a770f8d9cfe35 Mon Sep 17 00:00:00 2001 From: WMF2906 Date: Thu, 4 Apr 2024 09:50:10 -0400 Subject: [PATCH 11/17] added basemodel and revertrisk api --- src/liftwing_api/models/__init__.py | 0 src/liftwing_api/models/base_api_model.py | 0 2 files changed, 0 insertions(+), 0 deletions(-) create mode 100644 src/liftwing_api/models/__init__.py create mode 100644 src/liftwing_api/models/base_api_model.py diff --git a/src/liftwing_api/models/__init__.py b/src/liftwing_api/models/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/src/liftwing_api/models/base_api_model.py b/src/liftwing_api/models/base_api_model.py new file mode 100644 index 0000000..e69de29 From 2a7519a3916363c8381adfe99b5829801fd485ec Mon Sep 17 00:00:00 2001 From: WMF2906 Date: Mon, 15 Apr 2024 10:45:08 -0400 Subject: [PATCH 12/17] added changes to base_api_model --- .gitignore | 8 +++++++- examples/revertrisk_examples.py | 8 ++------ src/liftwing_api/models/base_api_model.py | 11 +++++++++++ src/liftwing_api/models/revertrisk.py | 19 +++++++++++++++++++ tests/revertrisk_examplestest.py | 10 ++++++---- 5 files changed, 45 insertions(+), 11 deletions(-) diff --git a/.gitignore b/.gitignore index 68bc17f..41a6c14 100644 --- a/.gitignore +++ b/.gitignore @@ -48,7 +48,7 @@ coverage.xml *.cover *.py,cover .hypothesis/ -.pytest_cache/ +.pytest_cache cover/ # Translations @@ -158,3 +158,9 @@ cython_debug/ # and can be added to the global gitignore or merged into this file. For a more nuclear # option (not recommended) you can uncomment the following to ignore the entire idea folder. #.idea/ + +# macOS +.DS_Store + +# Visual Studio Code +.vscode/ \ No newline at end of file diff --git a/examples/revertrisk_examples.py b/examples/revertrisk_examples.py index 429c361..2fdb88a 100644 --- a/examples/revertrisk_examples.py +++ b/examples/revertrisk_examples.py @@ -5,7 +5,6 @@ def revert_risk_api_request(language: str, revision_id: int): use_auth = False inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict" if use_auth: - headers = { 'Authorization': f'Bearer {access_token}', 'User-Agent': user_agent, @@ -17,7 +16,7 @@ def revert_risk_api_request(language: str, revision_id: int): data = {"rev_id": revision_id} response = requests.post(inference_url, headers=headers, data=json.dumps(data)) if response.status_code == 200: - return response.json() + return response.json() else: response.status_code == 400 raise ValueError(f"Unexpected error occurred: {response.status_code}") @@ -28,7 +27,4 @@ def revert_risk_api_request(language: str, revision_id: int): response = revert_risk_api_request(language, revision_id) - -print(response) - - +print(response) \ No newline at end of file diff --git a/src/liftwing_api/models/base_api_model.py b/src/liftwing_api/models/base_api_model.py index e69de29..6dcd673 100644 --- a/src/liftwing_api/models/base_api_model.py +++ b/src/liftwing_api/models/base_api_model.py @@ -0,0 +1,11 @@ +import requests + +class BaseAPIModel: + def __init__(self, base_url): + self.base_url = base_url + # this base url will be used across every model + + def request(self, endpoint, method="GET", data=None, headers=None): + # this method will make a request and return a json response + #return response.json() + return "" diff --git a/src/liftwing_api/models/revertrisk.py b/src/liftwing_api/models/revertrisk.py index e69de29..a7f1ec3 100644 --- a/src/liftwing_api/models/revertrisk.py +++ b/src/liftwing_api/models/revertrisk.py @@ -0,0 +1,19 @@ +from .base_api_model import BaseAPIModel +from examples.revertrisk_examples import revert_risk_api_request +from models.base_api_model import BaseAPIModel + +class RevertRiskAPIModel(BaseAPIModel): + def __init__(self, language, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/"): + super().__init__(base_url) + # base url is super because every class that inherits this from the base model will be using it + self.language = language + # language is the language that the post request is retrieving + + def predict_revert_risk(self, revision_id): + method="POST" + # since we have instances that change we are making a post request + endpoint = f"{self.language}-reverted:predict" + # figure out how did this get there and be able to exoplain why it ends in -reverted:predict + data = {"rev_id": revision_id} + # revID is pretty much the revision id that is needed to complete the post requests + return self.request(endpoint, method, data=data) \ No newline at end of file diff --git a/tests/revertrisk_examplestest.py b/tests/revertrisk_examplestest.py index 4ebb52b..5b8ebdf 100644 --- a/tests/revertrisk_examplestest.py +++ b/tests/revertrisk_examplestest.py @@ -10,9 +10,9 @@ def test_revert_risk_example_test_200(self, mock_post): mock_post.return_value.status_code = 200 mock_post.return_value.json.return_value = {'key': 'value'} - result = revert_risk_api_request("en", 12345) + expectedResult = revert_risk_api_request("en", 12345) - self.assertEqual(result, {'key': 'value'}) + self.assertEqual(expectedResult, {'key': 'value'}) @patch('examples.revertrisk_examples.requests.post') def test_revert_risk_api_request_failure(self, mock_post): @@ -23,11 +23,13 @@ def test_revert_risk_api_request_failure(self, mock_post): @patch('examples.revertrisk_examples.requests.post') def test_revert_risk_api_request_empty_response(self, mock_post): + # mocks a 200 response mock_post.return_value.status_code = 200 + # mocks an empty response mock_post.return_value.json.return_value = {} - + # result is the json response result = revert_risk_api_request("en", 12345) - + #check if response is empty self.assertEqual(result, {}) if __name__ == '__main__': From da1c50209b4be8237b9fb9565884ba87e37f5035 Mon Sep 17 00:00:00 2001 From: WMF2906 Date: Mon, 15 Apr 2024 19:12:47 -0400 Subject: [PATCH 13/17] changed basemodelapi to liftwing api and added new test package --- .../{base_api_model.py => liftwing_model.py} | 2 +- src/liftwing_api/models/revertrisk.py | 45 +++++++++++++------ tests/__init__.py | 0 tests/models/revertriskTest.py | 12 +++++ 4 files changed, 44 insertions(+), 15 deletions(-) rename src/liftwing_api/models/{base_api_model.py => liftwing_model.py} (94%) create mode 100644 tests/__init__.py create mode 100644 tests/models/revertriskTest.py diff --git a/src/liftwing_api/models/base_api_model.py b/src/liftwing_api/models/liftwing_model.py similarity index 94% rename from src/liftwing_api/models/base_api_model.py rename to src/liftwing_api/models/liftwing_model.py index 6dcd673..ba4ba1b 100644 --- a/src/liftwing_api/models/base_api_model.py +++ b/src/liftwing_api/models/liftwing_model.py @@ -1,6 +1,6 @@ import requests -class BaseAPIModel: +class LiftwingModel: def __init__(self, base_url): self.base_url = base_url # this base url will be used across every model diff --git a/src/liftwing_api/models/revertrisk.py b/src/liftwing_api/models/revertrisk.py index a7f1ec3..b9a94e8 100644 --- a/src/liftwing_api/models/revertrisk.py +++ b/src/liftwing_api/models/revertrisk.py @@ -1,19 +1,36 @@ -from .base_api_model import BaseAPIModel -from examples.revertrisk_examples import revert_risk_api_request -from models.base_api_model import BaseAPIModel +import requests +import json +from liftwing_model import LiftwingModel -class RevertRiskAPIModel(BaseAPIModel): - def __init__(self, language, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/"): +class RevertRiskAPIModel(LiftwingModel): + def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict"): super().__init__(base_url) # base url is super because every class that inherits this from the base model will be using it - self.language = language - # language is the language that the post request is retrieving - def predict_revert_risk(self, revision_id): - method="POST" - # since we have instances that change we are making a post request - endpoint = f"{self.language}-reverted:predict" - # figure out how did this get there and be able to exoplain why it ends in -reverted:predict + def request_to_revertRiskAPI(self, language: str, revision_id: int): + use_auth = False + inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict" + + if use_auth: + headers = { + 'Authorization': f'Bearer {self.access_token}', # Assuming access_token is an attribute of your class + 'User-Agent': self.user_agent, # Assuming user_agent is an attribute of your class + 'Content-type': 'application/json' + } + else: + headers = {} + data = {"rev_id": revision_id} - # revID is pretty much the revision id that is needed to complete the post requests - return self.request(endpoint, method, data=data) \ No newline at end of file + response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + + if response.status_code == 200: + return response.json() + else: + response.status_code == 400 + raise ValueError(f"Unexpected error occurred: {response.status_code}") + +revertRisk = RevertRiskAPIModel() + +jsonresponse = revertRisk.request_to_revertRiskAPI(language="en", revision_id=12345) + +print(jsonresponse) \ No newline at end of file diff --git a/tests/__init__.py b/tests/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/tests/models/revertriskTest.py b/tests/models/revertriskTest.py new file mode 100644 index 0000000..c821c3d --- /dev/null +++ b/tests/models/revertriskTest.py @@ -0,0 +1,12 @@ +import unittest +from unittest.mock import patch +from src.liftwing_api.models import revertrisk + +@patch('examples.revertrisk_examples.requests.post') +def test_revert_risk_example_test_200(self, mock_post): + mock_post.return_value.status_code = 200 + mock_post.return_value.json.return_value = {'key': 'value'} + + expectedResult = ("en", 12345) + + self.assertEqual(expectedResult, {'key': 'value'}) \ No newline at end of file From 21db4218a79390012cb60cc048c4f9764e923563 Mon Sep 17 00:00:00 2001 From: WMF2906 Date: Tue, 16 Apr 2024 10:23:07 -0400 Subject: [PATCH 14/17] fixed 404 bug by changing language --- src/liftwing_api/models/revertrisk.py | 2 +- tests/models/revertriskTest.py | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/liftwing_api/models/revertrisk.py b/src/liftwing_api/models/revertrisk.py index b9a94e8..3a40365 100644 --- a/src/liftwing_api/models/revertrisk.py +++ b/src/liftwing_api/models/revertrisk.py @@ -31,6 +31,6 @@ def request_to_revertRiskAPI(self, language: str, revision_id: int): revertRisk = RevertRiskAPIModel() -jsonresponse = revertRisk.request_to_revertRiskAPI(language="en", revision_id=12345) +jsonresponse = revertRisk.request_to_revertRiskAPI(language="viwiki", revision_id=12345) print(jsonresponse) \ No newline at end of file diff --git a/tests/models/revertriskTest.py b/tests/models/revertriskTest.py index c821c3d..f263424 100644 --- a/tests/models/revertriskTest.py +++ b/tests/models/revertriskTest.py @@ -7,6 +7,6 @@ def test_revert_risk_example_test_200(self, mock_post): mock_post.return_value.status_code = 200 mock_post.return_value.json.return_value = {'key': 'value'} - expectedResult = ("en", 12345) + expectedResult = ("enwiki", 12345) self.assertEqual(expectedResult, {'key': 'value'}) \ No newline at end of file From d199450e84dcef710c24627d9ed71214b94485f8 Mon Sep 17 00:00:00 2001 From: WMF2906 Date: Wed, 17 Apr 2024 10:24:53 -0400 Subject: [PATCH 15/17] added langid.py,readability.py, and revscoring, added more descriptions --- README.md | 40 ++++++++++++++ src/liftwing_api/models/langid.py | 64 +++++++++++++++++++++++ src/liftwing_api/models/liftwing_model.py | 3 +- src/liftwing_api/models/readability.py | 43 +++++++++++++++ src/liftwing_api/models/revertrisk.py | 11 +++- src/liftwing_api/models/revscoring.py | 44 ++++++++++++++++ 6 files changed, 202 insertions(+), 3 deletions(-) create mode 100644 src/liftwing_api/models/langid.py create mode 100644 src/liftwing_api/models/readability.py create mode 100644 src/liftwing_api/models/revscoring.py diff --git a/README.md b/README.md index c8f580d..ba9ede3 100644 --- a/README.md +++ b/README.md @@ -4,3 +4,43 @@ This is a Python package that acts as a client and allows users to make requests to the LiftWing API. Its purpose is to allow users to interact with the API by writing python code instead of manipulating HTTP requests. +Below is an example of how to make a request. This specific request is being made to the revert_risk API + +import json +import requests + +def revert_risk_api_request(language: str, revision_id: int): + """ + This function makes a request to the RevertRisk API. It takes in two parameters, language and revision_id. Language is the language of the wiki article. + revision_id is the specific version of the article. + """ + if language is None or revision_id is None: + raise ValueError("Both 'language' and 'revision_id' parameters are required.") # this checks if there is a language and rev_id, if not an error is thrown + + + use_auth = False + inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict" # this is the API endpoint + if use_auth: + headers = { + 'Authorization': f'Bearer {access_token}', + 'User-Agent': user_agent, + 'Content-type': 'application/json' + } # headers is a dictionary used to make a HTTP request + else: + headers = {} + + data = {"rev_id": revision_id} + response = requests.post(inference_url, headers=headers, data=json.dumps(data)) # POST request is being made + if response.status_code == 200: + return response.json() # request was successful so return the response + else: + response.status_code == 400 + raise ValueError(f"Unexpected error occurred: {response.status_code}") + + +language = "viwiki" # language has to be in this format, enwiki, arwiki etc... +revision_id = 12345 # rev_id has to be a valid integer, different rev_id gives different response + +response = revert_risk_api_request(language, revision_id) + +print(response) \ No newline at end of file diff --git a/src/liftwing_api/models/langid.py b/src/liftwing_api/models/langid.py new file mode 100644 index 0000000..ee58f87 --- /dev/null +++ b/src/liftwing_api/models/langid.py @@ -0,0 +1,64 @@ +# Python 3 + +import json +import requests + +use_auth = False +inference_url = 'https://api.wikimedia.org/service/lw/inference/v1/models/langid:predict' + +if use_auth: + headers: { + 'Authorization': 'Bearer YOUR_ACCESS_TOKEN', + 'User-Agent': 'YOUR_APP_NAME (YOUR_EMAIL_OR_CONTACT_PAGE)', + 'Content-type': 'application/json' + } +else: + headers = {} +data = {"text": "Some sample text in any language that we want to identify"} +response = requests.post(inference_url, headers=headers, data=json.dumps(data)) +print(response.json()) + +import json +import requests +from liftwing_model import LiftwingModel + +class Revscoring(LiftwingModel): + + def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict"): + super().__init__(base_url) + # base url is super because every class that inherits this from the base model will be using it + + def request_to_revScoringAPI(self, language: str, revision_id: int): + """ + This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/{language}-goodfaith:predict + using the language parameter and returns a JSON + """ + if language is None or revision_id is None: + raise ValueError("Both 'language' and 'revision_id' parameters are required.") + + use_auth = False + inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/{language}-goodfaith:predict" + + if use_auth: + headers = { + 'Authorization': f'Bearer {self.access_token}', # Assuming access_token is an attribute of class + 'User-Agent': self.user_agent, # Assuming user_agent is an attribute of class + 'Content-type': 'application/json' + } + else: + headers = {} + + data = {"rev_id": revision_id} + response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + + if response.status_code == 200: + return response.json() + else: + response.status_code == 400 + raise ValueError(f"Unexpected error occurred: {response.status_code}") + +rev = Revscoring() + +jsonresponse = rev.request_to_revScoringAPI(language="arwiki", revision_id=12345) + +print(jsonresponse) \ No newline at end of file diff --git a/src/liftwing_api/models/liftwing_model.py b/src/liftwing_api/models/liftwing_model.py index ba4ba1b..144db27 100644 --- a/src/liftwing_api/models/liftwing_model.py +++ b/src/liftwing_api/models/liftwing_model.py @@ -5,7 +5,8 @@ def __init__(self, base_url): self.base_url = base_url # this base url will be used across every model - def request(self, endpoint, method="GET", data=None, headers=None): + def request(self, endpoint, method="POST"): # this method will make a request and return a json response + #endpoint = base_url #return response.json() return "" diff --git a/src/liftwing_api/models/readability.py b/src/liftwing_api/models/readability.py new file mode 100644 index 0000000..ac02327 --- /dev/null +++ b/src/liftwing_api/models/readability.py @@ -0,0 +1,43 @@ +import requests +import json +from liftwing_model import LiftwingModel + +class ReadabilityModel(LiftwingModel): + def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/readability:predict"): + super().__init__(base_url) + # base url is super because every class that inherits this from the base model will be using it + + def request_to_readabilityAPI(self, revision_id: int, language: str): + """ + This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/readability:predict + using the language parameter and returns a JSON + """ + if language is None or revision_id is None: + raise ValueError("Both 'language' and 'revision_id' parameters are required.") + + use_auth = False + inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/readability:predict" + + if use_auth: + headers = { + 'Authorization': f'Bearer {self.access_token}', # Assuming access_token is an attribute of class + 'User-Agent': self.user_agent, # Assuming user_agent is an attribute of class + 'Content-type': 'application/json' + } + else: + headers = {} + + data = {"rev_id": revision_id} + response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + + if response.status_code == 200: + return response.json() + else: + response.status_code == 400 + raise ValueError(f"Unexpected error occurred: {response.status_code}") + +readability = ReadabilityModel() + +jsonresponse = readability.request_to_readabilityAPI("rev_id": 123456, "lang": "en") + +print(jsonresponse) \ No newline at end of file diff --git a/src/liftwing_api/models/revertrisk.py b/src/liftwing_api/models/revertrisk.py index 3a40365..da9195a 100644 --- a/src/liftwing_api/models/revertrisk.py +++ b/src/liftwing_api/models/revertrisk.py @@ -8,13 +8,20 @@ def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/m # base url is super because every class that inherits this from the base model will be using it def request_to_revertRiskAPI(self, language: str, revision_id: int): + """ + This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict + using the language parameter and returns a JSON + """ + if language is None or revision_id is None: + raise ValueError("Both 'language' and 'revision_id' parameters are required.") + use_auth = False inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict" if use_auth: headers = { - 'Authorization': f'Bearer {self.access_token}', # Assuming access_token is an attribute of your class - 'User-Agent': self.user_agent, # Assuming user_agent is an attribute of your class + 'Authorization': f'Bearer {self.access_token}', # Assuming access_token is an attribute of class + 'User-Agent': self.user_agent, # Assuming user_agent is an attribute of class 'Content-type': 'application/json' } else: diff --git a/src/liftwing_api/models/revscoring.py b/src/liftwing_api/models/revscoring.py new file mode 100644 index 0000000..f2dd803 --- /dev/null +++ b/src/liftwing_api/models/revscoring.py @@ -0,0 +1,44 @@ +import json +import requests +from liftwing_model import LiftwingModel + +class Revscoring(LiftwingModel): + + def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict"): + super().__init__(base_url) + # base url is super because every class that inherits this from the base model will be using it + + def request_to_revScoringAPI(self, language: str, revision_id: int): + """ + This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/{language}-goodfaith:predict + using the language parameter and returns a JSON + """ + if language is None or revision_id is None: + raise ValueError("Both 'language' and 'revision_id' parameters are required.") + + use_auth = False + inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/{language}-goodfaith:predict" + + if use_auth: + headers = { + 'Authorization': f'Bearer {self.access_token}', # Assuming access_token is an attribute of class + 'User-Agent': self.user_agent, # Assuming user_agent is an attribute of class + 'Content-type': 'application/json' + } + else: + headers = {} + + data = {"rev_id": revision_id} + response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + + if response.status_code == 200: + return response.json() + else: + response.status_code == 400 + raise ValueError(f"Unexpected error occurred: {response.status_code}") + +rev = Revscoring() + +jsonresponse = rev.request_to_revScoringAPI(language="arwiki", revision_id=12345) + +print(jsonresponse) \ No newline at end of file From 29243b4be390b9cafa22381177a8d94bf6131bdf Mon Sep 17 00:00:00 2001 From: WMF2906 Date: Mon, 29 Apr 2024 09:32:01 -0400 Subject: [PATCH 16/17] pyproject toml does not work --- .vscode/settings.json | 5 -- README.md | 1 - examples/revertrisk_examples.py | 22 ++++--- pyproject.toml | 22 ++++--- src/liftwing_api/models/articletopic.py | 39 ++++++++++++ src/liftwing_api/models/draftQuality.py | 13 ++++ src/liftwing_api/models/draftTopic.py | 62 +++++++++++++++++++ src/liftwing_api/models/langid.py | 10 +-- src/liftwing_api/models/liftwing_model.py | 38 ++++++++++-- src/liftwing_api/models/readability.py | 8 +-- src/liftwing_api/models/revScoreGoodfaith.py | 44 +++++++++++++ .../models/revertRiskMultilingual.py | 0 src/liftwing_api/models/revertrisk.py | 1 + src/liftwing_api/models/revscoredamaging.py | 44 +++++++++++++ 14 files changed, 272 insertions(+), 37 deletions(-) delete mode 100644 .vscode/settings.json create mode 100644 src/liftwing_api/models/articletopic.py create mode 100644 src/liftwing_api/models/draftQuality.py create mode 100644 src/liftwing_api/models/draftTopic.py create mode 100644 src/liftwing_api/models/revScoreGoodfaith.py create mode 100644 src/liftwing_api/models/revertRiskMultilingual.py create mode 100644 src/liftwing_api/models/revscoredamaging.py diff --git a/.vscode/settings.json b/.vscode/settings.json deleted file mode 100644 index 71e6517..0000000 --- a/.vscode/settings.json +++ /dev/null @@ -1,5 +0,0 @@ -{ - "python.analysis.extraPaths": [ - "./examples" - ] -} \ No newline at end of file diff --git a/README.md b/README.md index ba9ede3..470b991 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,4 @@ # liftwing-python -

LiftWing-python

This is a Python package that acts as a client and allows users to make requests to the LiftWing API. Its purpose is to allow users to interact with the API by writing python code instead of manipulating HTTP requests. diff --git a/examples/revertrisk_examples.py b/examples/revertrisk_examples.py index 2fdb88a..1ca1380 100644 --- a/examples/revertrisk_examples.py +++ b/examples/revertrisk_examples.py @@ -2,28 +2,36 @@ import requests def revert_risk_api_request(language: str, revision_id: int): + """ + This function makes a request to the RevertRisk API. It takes in two parameters, language and revision_id. Language is the language of the wiki article. + revision_id is the specific version of the article. + """ + if language is None or revision_id is None: + raise ValueError("Both 'language' and 'revision_id' parameters are required.") # this checks if there is a language and rev_id, if not an error is thrown + + use_auth = False - inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict" + inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict" # this is the API endpoint if use_auth: headers = { - 'Authorization': f'Bearer {access_token}', + 'Authorization': f'Bearer {access_token}', 'User-Agent': user_agent, 'Content-type': 'application/json' - } + } # headers is a dictionary used to make a HTTP request else: headers = {} data = {"rev_id": revision_id} - response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + response = requests.post(inference_url, headers=headers, data=json.dumps(data)) # POST request is being made if response.status_code == 200: - return response.json() + return response.json() # request was successful so return the response else: response.status_code == 400 raise ValueError(f"Unexpected error occurred: {response.status_code}") -language = "viwiki" -revision_id = 12345 +language = "viwiki" # language has to be in this format, enwiki, arwiki etc... +revision_id = 12345 # rev_id has to be a valid integer, different rev_id gives different response response = revert_risk_api_request(language, revision_id) diff --git a/pyproject.toml b/pyproject.toml index 90cd142..342703b 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -1,12 +1,16 @@ -[tool.poetry] +[project] name = "liftwing-python" version = "0.1.0" +authors = [ + {name = "Mercelis Vaughan", email = "mercelisvaughan@gmail.com"}, +] description = "Users will be able to retrieve JSON responses from their respective wiki APIs" - -[tool.poetry.dependencies] -python = "^3.10 || ^3.11 || ^3.12" -requests = "^2.0" - -[build-system] -requires = ["poetry-core>=1.0.0"] -build-backend = "poetry.core.masonry.api" +readme = "README.md" +requires-python = ">=3.8" +classifiers = [ + "Programming Language :: Python :: 3", +] +dependencies = [ + "requests", +] +dynamic = ["version"] \ No newline at end of file diff --git a/src/liftwing_api/models/articletopic.py b/src/liftwing_api/models/articletopic.py new file mode 100644 index 0000000..c47889a --- /dev/null +++ b/src/liftwing_api/models/articletopic.py @@ -0,0 +1,39 @@ +import json +import requests +from liftwing_model import LiftwingModel + +class ArticleTopic(LiftwingModel): + + def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/outlink-topic-model:predict"): + super().__init__(base_url) + # base url is super because every class that inherits this from the base model will be using it + + def request_to_articleTopicAPI(self, language: str, revision_id: int): + """ + This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/outlink-topic-model:predict + using the language parameter and returns a JSON + """ + if language is None or revision_id is None: + raise ValueError("Both 'language' and 'revision_id' parameters are required.") + + use_auth = False + inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/outlink-topic-model:predict" + + if use_auth: + headers: { + 'Authorization': 'Bearer YOUR_ACCESS_TOKEN', + 'User-Agent': 'YOUR_APP_NAME (YOUR_EMAIL_OR_CONTACT_PAGE)', + 'Content-type': 'application/json' + } + else: + headers = {} + data = {"page_title": "Douglas_Adams", "lang": "en"} + response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + + + if response.status_code == 200: + return response.json() + else: + response.status_code == 400 + raise ValueError(f"Unexpected error occurred: {response.status_code}") + diff --git a/src/liftwing_api/models/draftQuality.py b/src/liftwing_api/models/draftQuality.py new file mode 100644 index 0000000..8ceea94 --- /dev/null +++ b/src/liftwing_api/models/draftQuality.py @@ -0,0 +1,13 @@ +from liftwing_model import LiftwingModel + +class DraftQuality(LiftwingModel): + def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-draftquality:predict"): + super().__init__(base_url) + + def request_to_draftQualityAPI(self, revision_id: int): + endpoint_url = f"{self.base_url}" + return self.request(endpoint_url, revision_id) + +rev = DraftQuality() +jsonresponse = rev.request_to_draftQualityAPI(revision_id=12345) +print(jsonresponse) \ No newline at end of file diff --git a/src/liftwing_api/models/draftTopic.py b/src/liftwing_api/models/draftTopic.py new file mode 100644 index 0000000..d8a3294 --- /dev/null +++ b/src/liftwing_api/models/draftTopic.py @@ -0,0 +1,62 @@ +import json +import requests + +use_auth = False +inference_url = 'https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-drafttopic:predict' + +if use_auth: + headers: { + 'Authorization': 'Bearer YOUR_ACCESS_TOKEN', + 'User-Agent': 'YOUR_APP_NAME (YOUR_EMAIL_OR_CONTACT_PAGE)', + 'Content-type': 'application/json' + } +else: + headers = {} +data = {"rev_id": 12345 } +response = requests.post(inference_url, headers=headers, data=json.dumps(data)) +print(response.json()) + +import requests +import json +from liftwing_model import LiftwingModel + +class DraftTopicModel(LiftwingModel): + def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/{language}-drafttopic:predict"): + super().__init__(base_url) + # base url is super because every class that inherits this from the base model will be using it + + def request_to_draftTopicAPI(self, revision_id: int): + """ + This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-drafttopic:predict + using the language parameter and returns a JSON + language is for the different wiki languages, rev_id is the specific revisions + """ + if revision_id is None: + raise ValueError("'revision_id' parameter required.") + + use_auth = False + inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-drafttopic:predict" + + if use_auth: + headers = { + 'Authorization': f'Bearer {self.access_token}', # Assuming access_token is an attribute of class + 'User-Agent': self.user_agent, # Assuming user_agent is an attribute of class + 'Content-type': 'application/json' + } + else: + headers = {} + + data = {"rev_id": revision_id} + response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + + if response.status_code == 200: + return response.json() + else: + response.status_code == 400 + raise ValueError(f"Unexpected error occurred: {response.status_code}") + +draftTopic = DraftTopicModel() + +jsonresponse = draftTopic.request_to_draftTopicAPI(revision_id=12345) + +print(jsonresponse) \ No newline at end of file diff --git a/src/liftwing_api/models/langid.py b/src/liftwing_api/models/langid.py index ee58f87..d9fadb4 100644 --- a/src/liftwing_api/models/langid.py +++ b/src/liftwing_api/models/langid.py @@ -22,13 +22,13 @@ import requests from liftwing_model import LiftwingModel -class Revscoring(LiftwingModel): +class LangId(LiftwingModel): def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict"): super().__init__(base_url) - # base url is super because every class that inherits this from the base model will be using it + # The base URL is inherited from the parent class, which is used for making requests to the inference API. - def request_to_revScoringAPI(self, language: str, revision_id: int): + def request_to_langIDAPI(self, language: str, revision_id: int): """ This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/{language}-goodfaith:predict using the language parameter and returns a JSON @@ -57,8 +57,8 @@ def request_to_revScoringAPI(self, language: str, revision_id: int): response.status_code == 400 raise ValueError(f"Unexpected error occurred: {response.status_code}") -rev = Revscoring() +lang = LangId() -jsonresponse = rev.request_to_revScoringAPI(language="arwiki", revision_id=12345) +jsonresponse = lang.request_to_langIDAPI(language="arwiki", revision_id=12345) print(jsonresponse) \ No newline at end of file diff --git a/src/liftwing_api/models/liftwing_model.py b/src/liftwing_api/models/liftwing_model.py index 144db27..8af1f77 100644 --- a/src/liftwing_api/models/liftwing_model.py +++ b/src/liftwing_api/models/liftwing_model.py @@ -1,12 +1,38 @@ import requests +import json class LiftwingModel: def __init__(self, base_url): self.base_url = base_url - # this base url will be used across every model + # bare url - def request(self, endpoint, method="POST"): - # this method will make a request and return a json response - #endpoint = base_url - #return response.json() - return "" + def request(self, endpoint_url: str, revision_id: int): + """ + Makes a POST request to the specified endpoint URL using the given revision ID. + """ + if revision_id is None: + raise ValueError("revision_id parameter required.") + + use_auth = False + + if use_auth: + headers = { + 'Authorization': f'Bearer {self.access_token}', + 'User-Agent': self.user_agent, + 'Content-type': 'application/json' + } + else: + headers = {} + + data = {"rev_id": revision_id} + response = requests.post(endpoint_url, headers=headers, data=json.dumps(data)) + + if response.status_code == 200: + try: + json_response = response.json() + except json.JSONDecodeError: + raise ValueError("Response content is not in JSON format.") + + return json_response + else: + raise ValueError(f"Unexpected error occurred: {response.status_code}") diff --git a/src/liftwing_api/models/readability.py b/src/liftwing_api/models/readability.py index ac02327..a378c8b 100644 --- a/src/liftwing_api/models/readability.py +++ b/src/liftwing_api/models/readability.py @@ -3,11 +3,11 @@ from liftwing_model import LiftwingModel class ReadabilityModel(LiftwingModel): - def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/readability:predict"): + def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/{language}readability:predict"): super().__init__(base_url) # base url is super because every class that inherits this from the base model will be using it - def request_to_readabilityAPI(self, revision_id: int, language: str): + def request_to_readabilityAPI(self, language: str, revision_id: int): """ This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/readability:predict using the language parameter and returns a JSON @@ -16,7 +16,7 @@ def request_to_readabilityAPI(self, revision_id: int, language: str): raise ValueError("Both 'language' and 'revision_id' parameters are required.") use_auth = False - inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/readability:predict" + inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/{language}readability:predict" if use_auth: headers = { @@ -38,6 +38,6 @@ def request_to_readabilityAPI(self, revision_id: int, language: str): readability = ReadabilityModel() -jsonresponse = readability.request_to_readabilityAPI("rev_id": 123456, "lang": "en") +jsonresponse = readability.request_to_readabilityAPI("lang": "en", revision_id=123456) print(jsonresponse) \ No newline at end of file diff --git a/src/liftwing_api/models/revScoreGoodfaith.py b/src/liftwing_api/models/revScoreGoodfaith.py new file mode 100644 index 0000000..5d69eec --- /dev/null +++ b/src/liftwing_api/models/revScoreGoodfaith.py @@ -0,0 +1,44 @@ +import requests +import json +from liftwing_model import LiftwingModel + +class RevScoreGoodFaith(LiftwingModel): + def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-goodfaith:predict"): + super().__init__(base_url) + # base url is super because every class that inherits this from the base model will be using it + + def request_to_revScoreGoodfaithAPI(self, revision_id: int): + """ + This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-goodfaith:predict + using the revision id parameter and returns a JSON + rev_id is the specific revision + """ + if revision_id is None: + raise ValueError("revision_id parameter required.") + + use_auth = False + inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-goodfaith:predict" + + if use_auth: + headers = { + 'Authorization': f'Bearer {self.access_token}', # Assuming access_token is an attribute of class + 'User-Agent': self.user_agent, # Assuming user_agent is an attribute of class + 'Content-type': 'application/json' + } + else: + headers = {} + + data = {"rev_id": revision_id} + response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + + if response.status_code == 200: + return response.json() + else: + response.status_code == 400 + raise ValueError(f"Unexpected error occurred: {response.status_code}") + +rev = RevScoreGoodFaith() + +jsonresponse = rev.request_to_revScoreGoodfaithAPI(revision_id=12345) + +print(jsonresponse) \ No newline at end of file diff --git a/src/liftwing_api/models/revertRiskMultilingual.py b/src/liftwing_api/models/revertRiskMultilingual.py new file mode 100644 index 0000000..e69de29 diff --git a/src/liftwing_api/models/revertrisk.py b/src/liftwing_api/models/revertrisk.py index da9195a..c7f13c8 100644 --- a/src/liftwing_api/models/revertrisk.py +++ b/src/liftwing_api/models/revertrisk.py @@ -11,6 +11,7 @@ def request_to_revertRiskAPI(self, language: str, revision_id: int): """ This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict using the language parameter and returns a JSON + language is for the different wiki languages, rev_id is the specific revisions """ if language is None or revision_id is None: raise ValueError("Both 'language' and 'revision_id' parameters are required.") diff --git a/src/liftwing_api/models/revscoredamaging.py b/src/liftwing_api/models/revscoredamaging.py new file mode 100644 index 0000000..088aed1 --- /dev/null +++ b/src/liftwing_api/models/revscoredamaging.py @@ -0,0 +1,44 @@ +import requests +import json +from liftwing_model import LiftwingModel + +class RevScoreDamaging(LiftwingModel): + def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-damaging:predict"): + super().__init__(base_url) + # base url is super because every class that inherits this from the base model will be using it + + def request_to_revScoreDamagingAPI(self, revision_id: int): + """ + This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-damaging:predict + using the revision id parameter and returns a JSON + rev_id is the specific revision + """ + if revision_id is None: + raise ValueError("revision_id parameter required.") + + use_auth = False + inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-damaging:predict" + + if use_auth: + headers = { + 'Authorization': f'Bearer {self.access_token}', # Assuming access_token is an attribute of class + 'User-Agent': self.user_agent, # Assuming user_agent is an attribute of class + 'Content-type': 'application/json' + } + else: + headers = {} + + data = {"rev_id": revision_id} + response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + + if response.status_code == 200: + return response.json() + else: + response.status_code == 400 + raise ValueError(f"Unexpected error occurred: {response.status_code}") + +rev = RevScoreDamaging() + +jsonresponse = rev.request_to_revScoreDamagingAPI(revision_id=12345) + +print(jsonresponse) \ No newline at end of file From 88f089da1dde05ff78705acfe01b5ef3d5b628ba Mon Sep 17 00:00:00 2001 From: WMF2906 Date: Mon, 10 Jun 2024 00:45:26 -0400 Subject: [PATCH 17/17] added request functions to all child classes --- liftwing/models/draftTopic.py | 45 +++++++++++++ liftwing/models/readability.py | 27 ++++++++ src/liftwing_api/models/articletopic.py | 33 ++++------ src/liftwing_api/models/draftQuality.py | 32 +++++++-- src/liftwing_api/models/draftTopic.py | 66 ++++++------------- src/liftwing_api/models/langid.py | 59 ++++------------- src/liftwing_api/models/readability.py | 42 +++++------- src/liftwing_api/models/revScoreGoodfaith.py | 39 +++++------ .../models/revertRiskMultilingual.py | 34 ++++++++++ src/liftwing_api/models/revertrisk.py | 46 +++++-------- src/liftwing_api/models/revscoredamaging.py | 44 +++++-------- src/liftwing_api/models/revscoring.py | 37 ++++------- 12 files changed, 257 insertions(+), 247 deletions(-) create mode 100644 liftwing/models/draftTopic.py create mode 100644 liftwing/models/readability.py diff --git a/liftwing/models/draftTopic.py b/liftwing/models/draftTopic.py new file mode 100644 index 0000000..95de264 --- /dev/null +++ b/liftwing/models/draftTopic.py @@ -0,0 +1,45 @@ +import requests +import json +from liftwing_model import LiftwingModel +from typing import Any, Dict + +class DraftTopicModel(LiftwingModel): + def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/{language}-drafttopic:predict"): + super().__init__(base_url) + # base url is super because every class that inherits this from the base model will be using it + + def request(self, payload: Dict[str, Any], method: str = "POST", headers: Dict[str, str] = None) -> Dict[str, Any]: + """ + This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-drafttopic:predict + using the language parameter and returns a JSON + language is for the different wiki languages, rev_id is the specific revisions + """ + if revision_id is None: + raise ValueError("'revision_id' parameter required.") + + use_auth = False + inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-drafttopic:predict" + + if use_auth: + headers = { + 'Authorization': f'Bearer {self.access_token}', # Assuming access_token is an attribute of class + 'User-Agent': self.user_agent, # Assuming user_agent is an attribute of class + 'Content-type': 'application/json' + } + else: + headers = {} + + data = {"rev_id": revision_id} + response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + + if response.status_code == 200: + return response.json() + else: + response.status_code == 400 + raise ValueError(f"Unexpected error occurred: {response.status_code}") + +draftTopic = DraftTopicModel() + +jsonresponse = draftTopic.request(revision_id=12345) + +print(jsonresponse) \ No newline at end of file diff --git a/liftwing/models/readability.py b/liftwing/models/readability.py new file mode 100644 index 0000000..95a7ca3 --- /dev/null +++ b/liftwing/models/readability.py @@ -0,0 +1,27 @@ +import requests +from .liftwing_model import LiftwingModel +from typing import Any, Dict + + +class ReadabilityAPIModel(LiftwingModel): + def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/readability:predict"): + super().__init__(base_url) + + def request(self, payload: Dict[str, Any], method: str = "POST", headers: Dict[str, str] = None) -> Dict[str, Any]: + """ + This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/readability:predict + using the language parameter and returns a JSON + language is for the different wiki languages, rev_id is the specific revisions + """ + language = payload.get("lang") + if language is None: + raise ValueError("'lang' parameter is required in the payload.") + rev_id = payload.get("rev_id") + if rev_id is None: + raise ValueError("rev_id is none, add revision id to continue") + + if headers is None: + headers = {} + + response = requests.post(self.base_url, json=payload, headers=headers) + return response.json() diff --git a/src/liftwing_api/models/articletopic.py b/src/liftwing_api/models/articletopic.py index c47889a..df5dd3f 100644 --- a/src/liftwing_api/models/articletopic.py +++ b/src/liftwing_api/models/articletopic.py @@ -1,6 +1,7 @@ import json import requests -from liftwing_model import LiftwingModel +from liftwing_api.models.liftwing_model import LiftwingModel +from typing import Any, Dict class ArticleTopic(LiftwingModel): @@ -8,32 +9,22 @@ def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/m super().__init__(base_url) # base url is super because every class that inherits this from the base model will be using it - def request_to_articleTopicAPI(self, language: str, revision_id: int): + def request(self, method: str = "POST", headers: Dict[str, str] = None) -> Dict[str, Any]: """ - This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/outlink-topic-model:predict - using the language parameter and returns a JSON + This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/langid:predict + using the language parameter and returns a JSON. + The language parameter is for the different wiki languages, and rev_id is for specific revisions. """ - if language is None or revision_id is None: - raise ValueError("Both 'language' and 'revision_id' parameters are required.") + url = "https://api.wikimedia.org/service/lw/inference/v1/models/langid:predict" - use_auth = False - inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/outlink-topic-model:predict" - - if use_auth: - headers: { - 'Authorization': 'Bearer YOUR_ACCESS_TOKEN', - 'User-Agent': 'YOUR_APP_NAME (YOUR_EMAIL_OR_CONTACT_PAGE)', - 'Content-type': 'application/json' - } - else: + if headers is None: headers = {} - data = {"page_title": "Douglas_Adams", "lang": "en"} - response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + data = {"text": "Some sample text in any language that we want to identify"} + + response = requests.post(url, headers=headers, data=json.dumps(data)) if response.status_code == 200: return response.json() else: - response.status_code == 400 - raise ValueError(f"Unexpected error occurred: {response.status_code}") - + raise ValueError(f"Unexpected error occurred: {response.status_code}") \ No newline at end of file diff --git a/src/liftwing_api/models/draftQuality.py b/src/liftwing_api/models/draftQuality.py index 8ceea94..6f0535c 100644 --- a/src/liftwing_api/models/draftQuality.py +++ b/src/liftwing_api/models/draftQuality.py @@ -1,13 +1,35 @@ -from liftwing_model import LiftwingModel +import json +import requests +from liftwing_api.models.liftwing_model import LiftwingModel +from typing import Any, Dict class DraftQuality(LiftwingModel): def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-draftquality:predict"): super().__init__(base_url) - def request_to_draftQualityAPI(self, revision_id: int): - endpoint_url = f"{self.base_url}" - return self.request(endpoint_url, revision_id) + def request(self, revision_id: int, headers: Dict[str, str] = None) -> Dict[str, Any]: + """ + This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-draftquality:predict + using the revision_id parameter and returns a JSON. + + How to use: + rev = DraftQuality() + jsonresponse = rev.request(revision_id=12345) + print(jsonresponse) + + """ + if headers is None: + headers = {} + + data = {"rev_id": revision_id} + + response = requests.post(self.base_url, headers=headers, data=json.dumps(data)) + + if response.status_code == 200: + return response.json() + else: + raise ValueError(f"Unexpected error occurred: {response.status_code}") rev = DraftQuality() -jsonresponse = rev.request_to_draftQualityAPI(revision_id=12345) +jsonresponse = rev.request(revision_id=12345) print(jsonresponse) \ No newline at end of file diff --git a/src/liftwing_api/models/draftTopic.py b/src/liftwing_api/models/draftTopic.py index d8a3294..e016e59 100644 --- a/src/liftwing_api/models/draftTopic.py +++ b/src/liftwing_api/models/draftTopic.py @@ -1,62 +1,38 @@ import json import requests +from liftwing_api.models.liftwing_model import LiftwingModel +from typing import Any, Dict -use_auth = False -inference_url = 'https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-drafttopic:predict' - -if use_auth: - headers: { - 'Authorization': 'Bearer YOUR_ACCESS_TOKEN', - 'User-Agent': 'YOUR_APP_NAME (YOUR_EMAIL_OR_CONTACT_PAGE)', - 'Content-type': 'application/json' - } -else: - headers = {} -data = {"rev_id": 12345 } -response = requests.post(inference_url, headers=headers, data=json.dumps(data)) -print(response.json()) - -import requests -import json -from liftwing_model import LiftwingModel class DraftTopicModel(LiftwingModel): - def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/{language}-drafttopic:predict"): - super().__init__(base_url) - # base url is super because every class that inherits this from the base model will be using it + def __init__(self, language: str = "enwiki", base_url: str = "https://api.wikimedia.org/service/lw/inference/v1/models/{language}-drafttopic:predict"): + super().__init__(base_url.format(language=language)) + self.language = language - def request_to_draftTopicAPI(self, revision_id: int): + def request(self, revision_id: int, headers: Dict[str, str] = None) -> Dict[str, Any]: """ - This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-drafttopic:predict - using the language parameter and returns a JSON - language is for the different wiki languages, rev_id is the specific revisions + This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/{language}-drafttopic:predict + using the revision_id parameter and returns a JSON. + + Example: + + draftTopic = DraftTopicModel() + jsonresponse = draftTopic.request(revision_id=12345) + print(jsonresponse) + + """ if revision_id is None: raise ValueError("'revision_id' parameter required.") - - use_auth = False - inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-drafttopic:predict" - - if use_auth: - headers = { - 'Authorization': f'Bearer {self.access_token}', # Assuming access_token is an attribute of class - 'User-Agent': self.user_agent, # Assuming user_agent is an attribute of class - 'Content-type': 'application/json' - } - else: + + if headers is None: headers = {} data = {"rev_id": revision_id} - response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + + response = requests.post(self.base_url, headers=headers, data=json.dumps(data)) if response.status_code == 200: return response.json() else: - response.status_code == 400 - raise ValueError(f"Unexpected error occurred: {response.status_code}") - -draftTopic = DraftTopicModel() - -jsonresponse = draftTopic.request_to_draftTopicAPI(revision_id=12345) - -print(jsonresponse) \ No newline at end of file + raise ValueError(f"Unexpected error occurred: {response.status_code}") \ No newline at end of file diff --git a/src/liftwing_api/models/langid.py b/src/liftwing_api/models/langid.py index d9fadb4..14f9606 100644 --- a/src/liftwing_api/models/langid.py +++ b/src/liftwing_api/models/langid.py @@ -1,64 +1,31 @@ -# Python 3 - -import json import requests - -use_auth = False -inference_url = 'https://api.wikimedia.org/service/lw/inference/v1/models/langid:predict' - -if use_auth: - headers: { - 'Authorization': 'Bearer YOUR_ACCESS_TOKEN', - 'User-Agent': 'YOUR_APP_NAME (YOUR_EMAIL_OR_CONTACT_PAGE)', - 'Content-type': 'application/json' - } -else: - headers = {} -data = {"text": "Some sample text in any language that we want to identify"} -response = requests.post(inference_url, headers=headers, data=json.dumps(data)) -print(response.json()) - +from liftwing_api.models.liftwing_model import LiftwingModel +from typing import Any, Dict import json -import requests -from liftwing_model import LiftwingModel - -class LangId(LiftwingModel): - def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict"): +class LanguageAPIModel(LiftwingModel): + def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/langid:predict"): super().__init__(base_url) - # The base URL is inherited from the parent class, which is used for making requests to the inference API. - def request_to_langIDAPI(self, language: str, revision_id: int): + def request(self, text: str, headers: Dict[str, str] = None) -> Dict[str, Any]: """ - This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/{language}-goodfaith:predict - using the language parameter and returns a JSON + This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/langid:predict + using the provided text parameter and returns a JSON. """ - if language is None or revision_id is None: - raise ValueError("Both 'language' and 'revision_id' parameters are required.") - - use_auth = False - inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/{language}-goodfaith:predict" - - if use_auth: - headers = { - 'Authorization': f'Bearer {self.access_token}', # Assuming access_token is an attribute of class - 'User-Agent': self.user_agent, # Assuming user_agent is an attribute of class - 'Content-type': 'application/json' - } - else: + if headers is None: headers = {} - data = {"rev_id": revision_id} - response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + data = {"text": text} + + response = requests.post(self.base_url, headers=headers, data=json.dumps(data)) if response.status_code == 200: return response.json() else: - response.status_code == 400 raise ValueError(f"Unexpected error occurred: {response.status_code}") -lang = LangId() +lang = LanguageAPIModel() -jsonresponse = lang.request_to_langIDAPI(language="arwiki", revision_id=12345) +jsonresponse = lang.request("Some sample text in any language that we want to identify") print(jsonresponse) \ No newline at end of file diff --git a/src/liftwing_api/models/readability.py b/src/liftwing_api/models/readability.py index a378c8b..535e887 100644 --- a/src/liftwing_api/models/readability.py +++ b/src/liftwing_api/models/readability.py @@ -1,43 +1,33 @@ import requests import json -from liftwing_model import LiftwingModel +from liftwing_api.models.liftwing_model import LiftwingModel +from typing import Any, Dict class ReadabilityModel(LiftwingModel): - def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/{language}readability:predict"): - super().__init__(base_url) - # base url is super because every class that inherits this from the base model will be using it + def __init__(self, language: str, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-readability:predict"): + super().__init__(base_url.format(language=language)) + self.language = language - def request_to_readabilityAPI(self, language: str, revision_id: int): + def request(self, revision_id: int, headers: Dict[str, str] = None) -> Dict[str, Any]: """ - This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/readability:predict - using the language parameter and returns a JSON + This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/{language}readability:predict + using the provided revision_id parameter and returns a JSON. """ - if language is None or revision_id is None: - raise ValueError("Both 'language' and 'revision_id' parameters are required.") - - use_auth = False - inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/{language}readability:predict" + if revision_id is None: + raise ValueError("'revision_id' parameter required.") - if use_auth: - headers = { - 'Authorization': f'Bearer {self.access_token}', # Assuming access_token is an attribute of class - 'User-Agent': self.user_agent, # Assuming user_agent is an attribute of class - 'Content-type': 'application/json' - } - else: + if headers is None: headers = {} data = {"rev_id": revision_id} - response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + + response = requests.post(self.base_url, headers=headers, data=json.dumps(data)) if response.status_code == 200: return response.json() else: - response.status_code == 400 raise ValueError(f"Unexpected error occurred: {response.status_code}") - -readability = ReadabilityModel() - -jsonresponse = readability.request_to_readabilityAPI("lang": "en", revision_id=123456) -print(jsonresponse) \ No newline at end of file +readability_model = ReadabilityModel(language="enwiki") +json_response = readability_model.request(revision_id=12345) +print(json_response) \ No newline at end of file diff --git a/src/liftwing_api/models/revScoreGoodfaith.py b/src/liftwing_api/models/revScoreGoodfaith.py index 5d69eec..9ebeeef 100644 --- a/src/liftwing_api/models/revScoreGoodfaith.py +++ b/src/liftwing_api/models/revScoreGoodfaith.py @@ -1,44 +1,35 @@ import requests +from liftwing_api.models.liftwing_model import LiftwingModel +from typing import Any, Dict import json -from liftwing_model import LiftwingModel class RevScoreGoodFaith(LiftwingModel): def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-goodfaith:predict"): super().__init__(base_url) - # base url is super because every class that inherits this from the base model will be using it - def request_to_revScoreGoodfaithAPI(self, revision_id: int): + def request(self, revision_id: int, headers: Dict[str, str] = None) -> Dict[str, Any]: """ This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-goodfaith:predict - using the revision id parameter and returns a JSON - rev_id is the specific revision + using the provided revision_id parameter and returns a JSON. + + Example: + rev = RevScoreGoodFaith() + jsonresponse = rev.request(revision_id=12345) + print(jsonresponse) + """ if revision_id is None: - raise ValueError("revision_id parameter required.") - - use_auth = False - inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-goodfaith:predict" + raise ValueError("'revision_id' parameter required.") - if use_auth: - headers = { - 'Authorization': f'Bearer {self.access_token}', # Assuming access_token is an attribute of class - 'User-Agent': self.user_agent, # Assuming user_agent is an attribute of class - 'Content-type': 'application/json' - } - else: + if headers is None: headers = {} data = {"rev_id": revision_id} - response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + + response = requests.post(self.base_url, headers=headers, data=json.dumps(data)) if response.status_code == 200: return response.json() else: - response.status_code == 400 raise ValueError(f"Unexpected error occurred: {response.status_code}") - -rev = RevScoreGoodFaith() - -jsonresponse = rev.request_to_revScoreGoodfaithAPI(revision_id=12345) - -print(jsonresponse) \ No newline at end of file + \ No newline at end of file diff --git a/src/liftwing_api/models/revertRiskMultilingual.py b/src/liftwing_api/models/revertRiskMultilingual.py index e69de29..500f0f6 100644 --- a/src/liftwing_api/models/revertRiskMultilingual.py +++ b/src/liftwing_api/models/revertRiskMultilingual.py @@ -0,0 +1,34 @@ +import json +import requests +from liftwing_api.models.liftwing_model import LiftwingModel +from typing import Any, Dict + +class RevertRiskMultilingual(LiftwingModel): + def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/revertrisk-multilingual:predict"): + super().__init__(base_url) + + def request(self, text: str, headers: Dict[str, str] = None) -> Dict[str, Any]: + """ + This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/revertrisk-multilingual:predict + using the provided text parameter and returns a JSON. + """ + if not text: + raise ValueError("'text' parameter required.") + + if headers is None: + headers = {} + + data = {"text": text} + + response = requests.post(self.base_url, headers=headers, data=json.dumps(data)) + + if response.status_code == 200: + return response.json() + else: + # Print the response content for debugging + print(f"Error response content: {response.content.decode('utf-8')}") + raise ValueError(f"Unexpected error occurred: {response.status_code}") + +revert_risk_multilingual = RevertRiskMultilingual() +json_response = revert_risk_multilingual.request(text="Some sample text in any language that we want to analyze for revert risk.") +print(json_response) \ No newline at end of file diff --git a/src/liftwing_api/models/revertrisk.py b/src/liftwing_api/models/revertrisk.py index c7f13c8..01ba2a2 100644 --- a/src/liftwing_api/models/revertrisk.py +++ b/src/liftwing_api/models/revertrisk.py @@ -1,44 +1,28 @@ import requests -import json -from liftwing_model import LiftwingModel +from .liftwing_model import LiftwingModel +from typing import Any, Dict + class RevertRiskAPIModel(LiftwingModel): - def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict"): + def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/revertrisk-language-agnostic:predict"): super().__init__(base_url) - # base url is super because every class that inherits this from the base model will be using it - def request_to_revertRiskAPI(self, language: str, revision_id: int): + def request(self, payload: Dict[str, Any], method: str = "POST", headers: Dict[str, str] = None) -> Dict[str, Any]: """ - This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict + This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/revertrisk-language-agnostic:predict using the language parameter and returns a JSON language is for the different wiki languages, rev_id is the specific revisions """ - if language is None or revision_id is None: - raise ValueError("Both 'language' and 'revision_id' parameters are required.") - - use_auth = False - inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict" + language = payload.get("lang") + if language is None: + raise ValueError("'lang' parameter is required in the payload.") + rev_id = payload.get("rev_id") + if rev_id is None: + raise ValueError("rev_id is none, add revision id to continue") - if use_auth: - headers = { - 'Authorization': f'Bearer {self.access_token}', # Assuming access_token is an attribute of class - 'User-Agent': self.user_agent, # Assuming user_agent is an attribute of class - 'Content-type': 'application/json' - } - else: + if headers is None: headers = {} - data = {"rev_id": revision_id} - response = requests.post(inference_url, headers=headers, data=json.dumps(data)) - - if response.status_code == 200: - return response.json() - else: - response.status_code == 400 - raise ValueError(f"Unexpected error occurred: {response.status_code}") - -revertRisk = RevertRiskAPIModel() - -jsonresponse = revertRisk.request_to_revertRiskAPI(language="viwiki", revision_id=12345) + response = requests.post(self.base_url, json=payload, headers=headers) -print(jsonresponse) \ No newline at end of file + return response.json() \ No newline at end of file diff --git a/src/liftwing_api/models/revscoredamaging.py b/src/liftwing_api/models/revscoredamaging.py index 088aed1..5224131 100644 --- a/src/liftwing_api/models/revscoredamaging.py +++ b/src/liftwing_api/models/revscoredamaging.py @@ -1,44 +1,36 @@ -import requests +from liftwing_api.models.liftwing_model import LiftwingModel +from typing import Any, Dict import json -from liftwing_model import LiftwingModel +import requests class RevScoreDamaging(LiftwingModel): def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-damaging:predict"): super().__init__(base_url) - # base url is super because every class that inherits this from the base model will be using it - def request_to_revScoreDamagingAPI(self, revision_id: int): + def request(self, revision_id: int, headers: Dict[str, str] = None) -> Dict[str, Any]: """ This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-damaging:predict - using the revision id parameter and returns a JSON - rev_id is the specific revision + using the provided revision_id parameter and returns a JSON. + + Example: + + rev_score_damaging = RevScoreDamaging() + json_response = rev_score_damaging.request(revision_id=12345) + print(json_response) + """ if revision_id is None: - raise ValueError("revision_id parameter required.") - - use_auth = False - inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-damaging:predict" - - if use_auth: - headers = { - 'Authorization': f'Bearer {self.access_token}', # Assuming access_token is an attribute of class - 'User-Agent': self.user_agent, # Assuming user_agent is an attribute of class - 'Content-type': 'application/json' - } - else: + raise ValueError("'revision_id' parameter required.") + + if headers is None: headers = {} data = {"rev_id": revision_id} - response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + + response = requests.post(self.base_url, headers=headers, data=json.dumps(data)) if response.status_code == 200: return response.json() else: - response.status_code == 400 raise ValueError(f"Unexpected error occurred: {response.status_code}") - -rev = RevScoreDamaging() - -jsonresponse = rev.request_to_revScoreDamagingAPI(revision_id=12345) - -print(jsonresponse) \ No newline at end of file + \ No newline at end of file diff --git a/src/liftwing_api/models/revscoring.py b/src/liftwing_api/models/revscoring.py index f2dd803..1410896 100644 --- a/src/liftwing_api/models/revscoring.py +++ b/src/liftwing_api/models/revscoring.py @@ -1,44 +1,35 @@ import json import requests -from liftwing_model import LiftwingModel +from liftwing_api.models.liftwing_model import LiftwingModel +from typing import Any, Dict class Revscoring(LiftwingModel): + def __init__(self, language: str, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/enwiki-reverted:predict"): + super().__init__(base_url.format(language=language)) + self.language = language - def __init__(self, base_url="https://api.wikimedia.org/service/lw/inference/v1/models/{language}-reverted:predict"): - super().__init__(base_url) - # base url is super because every class that inherits this from the base model will be using it - - def request_to_revScoringAPI(self, language: str, revision_id: int): + def request(self, revision_id: int, headers: Dict[str, str] = None) -> Dict[str, Any]: """ This function makes a POST request to https://api.wikimedia.org/service/lw/inference/v1/models/{language}-goodfaith:predict - using the language parameter and returns a JSON + using the provided revision_id parameter and returns a JSON. """ - if language is None or revision_id is None: - raise ValueError("Both 'language' and 'revision_id' parameters are required.") - - use_auth = False - inference_url = f"https://api.wikimedia.org/service/lw/inference/v1/models/{language}-goodfaith:predict" + if revision_id is None: + raise ValueError("'revision_id' parameter required.") - if use_auth: - headers = { - 'Authorization': f'Bearer {self.access_token}', # Assuming access_token is an attribute of class - 'User-Agent': self.user_agent, # Assuming user_agent is an attribute of class - 'Content-type': 'application/json' - } - else: + if headers is None: headers = {} data = {"rev_id": revision_id} - response = requests.post(inference_url, headers=headers, data=json.dumps(data)) + + response = requests.post(self.base_url, headers=headers, data=json.dumps(data)) if response.status_code == 200: return response.json() else: - response.status_code == 400 raise ValueError(f"Unexpected error occurred: {response.status_code}") -rev = Revscoring() +rev = Revscoring(language="enwiki") -jsonresponse = rev.request_to_revScoringAPI(language="arwiki", revision_id=12345) +jsonresponse = rev.request(revision_id=12345) print(jsonresponse) \ No newline at end of file