From 73f014e90e5c1cd6fd5d5a6abcc71e00a4b1a969 Mon Sep 17 00:00:00 2001 From: Baptiste Jonglez Date: Mon, 25 Mar 2024 20:03:12 +0100 Subject: [PATCH 01/46] CI: Move lint and docs to separate action for readability Currently, linting is done in one specific job of the big test Matrix, and it's very easy to overlook. But we want linting to be the first thing to fix. Also reorganize and rename jobs for readability. Finally, use python 3.11 for lint/docs because python 3.12 seems to break dev install. --- .github/workflows/dockerhub.yml | 4 +- .github/workflows/lint-docs.yml | 42 +++++++++++++++++++ .../{test-docs.yml => unit-tests.yml} | 7 +--- tox.ini | 12 ++++-- 4 files changed, 55 insertions(+), 10 deletions(-) create mode 100644 .github/workflows/lint-docs.yml rename .github/workflows/{test-docs.yml => unit-tests.yml} (96%) diff --git a/.github/workflows/dockerhub.yml b/.github/workflows/dockerhub.yml index c8943b9d..6c8a47b2 100644 --- a/.github/workflows/dockerhub.yml +++ b/.github/workflows/dockerhub.yml @@ -1,4 +1,4 @@ -name: CI to Docker Hub +name: Docker build on: push: @@ -18,7 +18,7 @@ jobs: - name: Test image # Checks we are able to run the container. run: docker compose -f docker-compose.test.yml run sut - build: + build_upload: runs-on: ubuntu-latest needs: test if: github.event_name != 'pull_request' diff --git a/.github/workflows/lint-docs.yml b/.github/workflows/lint-docs.yml new file mode 100644 index 00000000..12ec03fe --- /dev/null +++ b/.github/workflows/lint-docs.yml @@ -0,0 +1,42 @@ +name: Lint & Docs + +on: + push: + branches: [ 'master', 'stable-*' ] + pull_request: + branches: [ 'master', 'stable-*' ] + +jobs: + lint: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v3 + - name: Set up Python + uses: actions/setup-python@v4 + with: + python-version: "3.11" + cache: 'pip' + cache-dependency-path: '**/pyproject.toml' + - name: Install dependencies + run: | + python -m pip install --upgrade pip + python -m pip install tox + - name: Run Lint + run: tox -e lint + + test_doc: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v3 + - name: Set up Python + uses: actions/setup-python@v4 + with: + python-version: "3.11" + cache: 'pip' + cache-dependency-path: '**/pyproject.toml' + - name: Install dependencies + run: | + python -m pip install --upgrade pip + python -m pip install tox + - name: Check we can generate documentation + run: tox -e docs diff --git a/.github/workflows/test-docs.yml b/.github/workflows/unit-tests.yml similarity index 96% rename from .github/workflows/test-docs.yml rename to .github/workflows/unit-tests.yml index 372ca8ae..067bc923 100644 --- a/.github/workflows/test-docs.yml +++ b/.github/workflows/unit-tests.yml @@ -1,4 +1,4 @@ -name: Test & Docs +name: Unit tests on: push: @@ -7,7 +7,7 @@ on: branches: [ 'master', 'stable-*' ] jobs: - build: + test: runs-on: ubuntu-latest @@ -101,6 +101,3 @@ jobs: if: matrix.database == 'mariadb' env: TESTING_SQLALCHEMY_DATABASE_URI: 'mysql+pymysql://root:ihatemoney@localhost:3306/ihatemoney_ci' - - name: Run Lint & Docs - run: tox -e lint_docs - if: matrix.python-version == '3.12' diff --git a/tox.ini b/tox.ini index fe2c9ad9..8a0421fa 100644 --- a/tox.ini +++ b/tox.ini @@ -1,6 +1,6 @@ [tox] isolated_build = true -envlist = py312,py311,py310,py39,py38,py37,lint_docs +envlist = py312,py311,py310,py39,py38,py37,lint,docs skip_missing_interpreters = True [testenv] @@ -16,15 +16,21 @@ deps = # To be sure we are importing ihatemoney pkg from pip-installed version changedir = /tmp -[testenv:lint_docs] +[testenv:lint] commands = black --check --target-version=py37 . isort --check --profile black . flake8 ihatemoney vermin --no-tips --violations -t=3.7- . +deps = + -e.[dev] +changedir = {toxinidir} + +[testenv:docs] +commands = sphinx-build -a -n -b html -d docs/_build/doctrees docs docs/_build/html deps = - -e.[dev,doc] + -e.[doc] changedir = {toxinidir} [flake8] From a0409a296add772e470e39ed2785d81140628986 Mon Sep 17 00:00:00 2001 From: Baptiste Jonglez Date: Mon, 25 Mar 2024 20:12:41 +0100 Subject: [PATCH 02/46] CI: Update databases version to match more recent Debian --- .github/workflows/unit-tests.yml | 30 ++++++++++++++++++------------ 1 file changed, 18 insertions(+), 12 deletions(-) diff --git a/.github/workflows/unit-tests.yml b/.github/workflows/unit-tests.yml index 067bc923..ddf5ab54 100644 --- a/.github/workflows/unit-tests.yml +++ b/.github/workflows/unit-tests.yml @@ -11,10 +11,10 @@ jobs: runs-on: ubuntu-latest - # Use postgresql and MariaDB versions of Debian buster + # Use postgresql and MariaDB versions of Debian bookworm services: postgres: - image: postgres:11 + image: postgres:15 ports: - 5432:5432 env: @@ -24,7 +24,7 @@ jobs: options: --health-cmd pg_isready --health-interval 10s --health-timeout 5s --health-retries 5 mariadb: - image: mariadb:10.3 + image: mariadb:10.11 env: MARIADB_ROOT_PASSWORD: ihatemoney MARIADB_DATABASE: ihatemoney_ci @@ -39,24 +39,24 @@ jobs: python-version: [3.7, 3.8, 3.9, "3.10", "3.11", "3.12"] dependencies: [normal] database: [sqlite] - # Test other databases only with one version of Python (Debian buster has 3.7) + # Test other databases with only a few versions of Python (Debian bullseye has 3.9, bookworm has 3.11) include: - - python-version: 3.7 + - python-version: 3.9 dependencies: normal database: postgresql - - python-version: 3.7 + - python-version: 3.9 + dependencies: normal + database: mariadb + - python-version: 3.11 + dependencies: normal + database: postgresql + - python-version: 3.11 dependencies: normal database: mariadb # Try a few variants with the minimal versions supported - python-version: 3.7 dependencies: minimal database: sqlite - - python-version: 3.7 - dependencies: minimal - database: postgresql - - python-version: 3.7 - dependencies: minimal - database: mariadb - python-version: 3.9 dependencies: minimal database: sqlite @@ -66,6 +66,12 @@ jobs: - python-version: "3.11" dependencies: minimal database: sqlite + - python-version: "3.11" + dependencies: minimal + database: postgresql + - python-version: "3.11" + dependencies: minimal + database: mariadb - python-version: "3.12" dependencies: minimal database: sqlite From 312dfef14b811d5afd59d181d89939352d55a68d Mon Sep 17 00:00:00 2001 From: Baptiste Jonglez Date: Mon, 25 Mar 2024 20:15:14 +0100 Subject: [PATCH 03/46] Reformat code with black and isort --- ihatemoney/forms.py | 7 +- ...b38559992_new_bill_type_attribute_added.py | 7 +- ihatemoney/models.py | 11 ++- ihatemoney/tests/api_test.py | 8 +- ihatemoney/tests/budget_test.py | 98 ++++++++++--------- 5 files changed, 75 insertions(+), 56 deletions(-) diff --git a/ihatemoney/forms.py b/ihatemoney/forms.py index 6a787e21..e1ddabe8 100644 --- a/ihatemoney/forms.py +++ b/ihatemoney/forms.py @@ -364,7 +364,12 @@ class BillForm(FlaskForm): payed_for = SelectMultipleField( _("For whom?"), validators=[DataRequired()], coerce=int ) - bill_type = SelectField(_("Bill Type"), choices=BillType.choices(), coerce=BillType, default=BillType.EXPENSE) + bill_type = SelectField( + _("Bill Type"), + choices=BillType.choices(), + coerce=BillType, + default=BillType.EXPENSE, + ) submit = SubmitField(_("Submit")) submit2 = SubmitField(_("Submit and add a new one")) diff --git a/ihatemoney/migrations/versions/7a9b38559992_new_bill_type_attribute_added.py b/ihatemoney/migrations/versions/7a9b38559992_new_bill_type_attribute_added.py index 9b1fc520..d7e27330 100644 --- a/ihatemoney/migrations/versions/7a9b38559992_new_bill_type_attribute_added.py +++ b/ihatemoney/migrations/versions/7a9b38559992_new_bill_type_attribute_added.py @@ -19,7 +19,10 @@ def upgrade(): billtype_enum = sa.Enum(BillType) billtype_enum.create(op.get_bind(), checkfirst=True) - op.add_column("bill", sa.Column("bill_type", billtype_enum, server_default=BillType.EXPENSE.name)) + op.add_column( + "bill", + sa.Column("bill_type", billtype_enum, server_default=BillType.EXPENSE.name), + ) op.add_column("bill_version", sa.Column("bill_type", sa.UnicodeText())) @@ -28,4 +31,4 @@ def downgrade(): op.drop_column("bill_version", "bill_type") billtype_enum = sa.Enum(BillType) - billtype_enum.drop(op.get_bind()) \ No newline at end of file + billtype_enum.drop(op.get_bind()) diff --git a/ihatemoney/models.py b/ihatemoney/models.py index fcc17264..c7dee185 100644 --- a/ihatemoney/models.py +++ b/ihatemoney/models.py @@ -1,6 +1,6 @@ from collections import defaultdict -from enum import Enum import datetime +from enum import Enum import itertools from dateutil.parser import parse @@ -22,7 +22,7 @@ from sqlalchemy_continuum.plugins import FlaskPlugin from ihatemoney.currency_convertor import CurrencyConverter from ihatemoney.monkeypath_continuum import PatchedTransactionFactory -from ihatemoney.utils import generate_password_hash, get_members, same_bill, FormEnum +from ihatemoney.utils import generate_password_hash, get_members, same_bill from ihatemoney.versioning import ( ConditionalVersioningManager, LoggingMode, @@ -51,6 +51,7 @@ make_versioned( ], ) + class BillType(Enum): EXPENSE = "Expense" REIMBURSEMENT = "Reimbursement" @@ -131,7 +132,9 @@ class Project(db.Model): if bill.bill_type == BillType.EXPENSE: should_receive[bill.payer.id] += bill.converted_amount for ower in bill.owers: - should_pay[ower.id] += (ower.weight * bill.converted_amount / total_weight) + should_pay[ower.id] += ( + ower.weight * bill.converted_amount / total_weight + ) if bill.bill_type == BillType.REIMBURSEMENT: should_receive[bill.payer.id] += bill.converted_amount @@ -563,7 +566,7 @@ class Project(db.Model): ("Alice", 20, ("Amina", "Alice"), "Beer !", "Expense"), ("Amina", 50, ("Amina", "Alice", "Georg"), "AMAP", "Expense"), ) - for (payer, amount, owers, what, bill_type) in operations: + for payer, amount, owers, what, bill_type in operations: db.session.add( Bill( amount=amount, diff --git a/ihatemoney/tests/api_test.py b/ihatemoney/tests/api_test.py index ff94ebe7..191790b6 100644 --- a/ihatemoney/tests/api_test.py +++ b/ihatemoney/tests/api_test.py @@ -1017,7 +1017,6 @@ class TestAPI(IhatemoneyTestCase): def test_validate_bill_type(self): self.api_create("raclette") self.api_add_member("raclette", "zorglub") - req = self.client.post( "/api/projects/raclette/bills", @@ -1029,7 +1028,7 @@ class TestAPI(IhatemoneyTestCase): "bill_type": "wrong_bill_type", "amount": "50", }, - headers=self.get_auth("raclette") + headers=self.get_auth("raclette"), ) self.assertStatus(400, req) @@ -1044,7 +1043,7 @@ class TestAPI(IhatemoneyTestCase): "bill_type": "Expense", "amount": "50", }, - headers=self.get_auth("raclette") + headers=self.get_auth("raclette"), ) self.assertStatus(201, req) @@ -1063,7 +1062,7 @@ class TestAPI(IhatemoneyTestCase): "payed_for": ["1"], "amount": "50", }, - headers=self.get_auth("raclette") + headers=self.get_auth("raclette"), ) self.assertStatus(201, req) @@ -1076,4 +1075,3 @@ class TestAPI(IhatemoneyTestCase): # Bill type should now be "Expense" got = json.loads(req.data.decode("utf-8")) assert got["bill_type"] == "Expense" - diff --git a/ihatemoney/tests/budget_test.py b/ihatemoney/tests/budget_test.py index 9ddeec8a..15e7d4e1 100644 --- a/ihatemoney/tests/budget_test.py +++ b/ihatemoney/tests/budget_test.py @@ -716,8 +716,8 @@ class TestBudget(IhatemoneyTestCase): "amount": "17", }, ) - - #transfer bill should not affect balances at all + + # transfer bill should not affect balances at all self.client.post( "/raclette/add", data={ @@ -801,22 +801,22 @@ class TestBudget(IhatemoneyTestCase): self.client.post("/rent/members/add", data={"name": "alice"}) members_ids = [m.id for m in self.get_project("rent").members] - # create a bill to test reimbursement + # create a bill to test reimbursement self.client.post( "/rent/add", data={ "date": "2022-12-12", "what": "december rent", - "payer": members_ids[0], #bob - "payed_for": members_ids, #bob and alice + "payer": members_ids[0], # bob + "payed_for": members_ids, # bob and alice "bill_type": "Expense", "amount": "1000", }, ) - #check balance + # check balance balance = self.get_project("rent").balance assert set(balance.values()), set([500 == -500]) - #check paid + # check paid bob_paid = self.get_project("rent").full_balance[2][members_ids[0]] alice_paid = self.get_project("rent").full_balance[2][members_ids[1]] assert bob_paid == 1000 @@ -828,8 +828,8 @@ class TestBudget(IhatemoneyTestCase): data={ "date": "2022-12-13", "what": "reimbursement for rent", - "payer": members_ids[1], #alice - "payed_for": members_ids[0], #bob + "payer": members_ids[1], # alice + "payed_for": members_ids[0], # bob "bill_type": "Reimbursement", "amount": "500", }, @@ -837,11 +837,12 @@ class TestBudget(IhatemoneyTestCase): balance = self.get_project("rent").balance assert set(balance.values()), set([0 == 0]) - #check paid + # check paid bob_paid = self.get_project("rent").full_balance[2][members_ids[0]] alice_paid = self.get_project("rent").full_balance[2][members_ids[1]] assert bob_paid == 500 assert alice_paid == 500 + def test_transfer_bill(self): self.post_project("random") @@ -855,8 +856,8 @@ class TestBudget(IhatemoneyTestCase): data={ "date": "2022-10-10", "what": "Rent", - "payer": members_ids[0], #zorglub - "payed_for": members_ids, #zorglub + fred + "payer": members_ids[0], # zorglub + "payed_for": members_ids, # zorglub + fred "bill_type": "Expense", "amount": "1000", }, @@ -867,8 +868,8 @@ class TestBudget(IhatemoneyTestCase): data={ "date": "2022-10-10", "what": "Transfer of 500 to fred", - "payer": members_ids[0], #zorglub - "payed_for": members_ids[1], #fred + "payer": members_ids[0], # zorglub + "payed_for": members_ids[1], # fred "bill_type": "Transfer", "amount": "500", }, @@ -884,22 +885,22 @@ class TestBudget(IhatemoneyTestCase): self.client.post("/rent/members/add", data={"name": "alice"}) members_ids = [m.id for m in self.get_project("rent").members] - # create a bill to test reimbursement + # create a bill to test reimbursement self.client.post( "/rent/add", data={ "date": "2022-12-12", "what": "december rent", - "payer": members_ids[0], #bob - "payed_for": members_ids, #bob and alice + "payer": members_ids[0], # bob + "payed_for": members_ids, # bob and alice "bill_type": "Expense", "amount": "1000", }, ) - #check balance + # check balance balance = self.get_project("rent").balance assert set(balance.values()), set([500 == -500]) - #check paid + # check paid bob_paid = self.get_project("rent").full_balance[2][members_ids[0]] alice_paid = self.get_project("rent").full_balance[2][members_ids[1]] assert bob_paid == 1000 @@ -911,8 +912,8 @@ class TestBudget(IhatemoneyTestCase): data={ "date": "2022-12-13", "what": "reimbursement for rent", - "payer": members_ids[1], #alice - "payed_for": members_ids[0], #bob + "payer": members_ids[1], # alice + "payed_for": members_ids[0], # bob "bill_type": "Reimbursement", "amount": "500", }, @@ -920,11 +921,12 @@ class TestBudget(IhatemoneyTestCase): balance = self.get_project("rent").balance assert set(balance.values()), set([0 == 0]) - #check paid + # check paid bob_paid = self.get_project("rent").full_balance[2][members_ids[0]] alice_paid = self.get_project("rent").full_balance[2][members_ids[1]] assert bob_paid == 500 assert alice_paid == 500 + def test_transfer_bill(self): self.post_project("random") @@ -938,8 +940,8 @@ class TestBudget(IhatemoneyTestCase): data={ "date": "2022-10-10", "what": "Rent", - "payer": members_ids[0], #zorglub - "payed_for": members_ids, #zorglub + fred + "payer": members_ids[0], # zorglub + "payed_for": members_ids, # zorglub + fred "bill_type": "Expense", "amount": "1000", }, @@ -950,8 +952,8 @@ class TestBudget(IhatemoneyTestCase): data={ "date": "2022-10-10", "what": "Transfer of 500 to fred", - "payer": members_ids[0], #zorglub - "payed_for": members_ids[1], #fred + "payer": members_ids[0], # zorglub + "payed_for": members_ids[1], # fred "bill_type": "Transfer", "amount": "500", }, @@ -1433,7 +1435,7 @@ class TestBudget(IhatemoneyTestCase): for m, a in members.items(): assert abs(a - balance[m.id]) < 0.01 return - + def test_settle_button(self): self.post_project("raclette") @@ -1482,16 +1484,24 @@ class TestBudget(IhatemoneyTestCase): ) project = self.get_project("raclette") transactions = project.get_transactions_to_settle_bill() - + count = 0 for t in transactions: - count+=1 - self.client.get("/raclette/settle"+"/"+str(t["amount"])+"/"+str(t["ower"].id)+"/"+str(t["receiver"].id)) + count += 1 + self.client.get( + "/raclette/settle" + + "/" + + str(t["amount"]) + + "/" + + str(t["ower"].id) + + "/" + + str(t["receiver"].id) + ) temp_transactions = project.get_transactions_to_settle_bill() - #test if the one has disappeared - assert len(temp_transactions) == len(transactions)-count - - #test if theres a new one with bill_type reimbursement + # test if the one has disappeared + assert len(temp_transactions) == len(transactions) - count + + # test if theres a new one with bill_type reimbursement bill = project.get_newest_bill() assert bill.bill_type == models.BillType.REIMBURSEMENT return @@ -2005,7 +2015,7 @@ class TestBudget(IhatemoneyTestCase): "payed_for": [1, 2, 3], "amount": "12", "original_currency": "EUR", - "bill_type": "Expense" + "bill_type": "Expense", }, ) self.client.post( @@ -2017,7 +2027,7 @@ class TestBudget(IhatemoneyTestCase): "payed_for": [1, 2], "amount": "15", "original_currency": "EUR", - "bill_type": "Expense" + "bill_type": "Expense", }, ) self.client.post( @@ -2029,7 +2039,7 @@ class TestBudget(IhatemoneyTestCase): "payed_for": [1, 2], "amount": "10", "original_currency": "EUR", - "bill_type": "Expense" + "bill_type": "Expense", }, ) @@ -2092,7 +2102,7 @@ class TestBudget(IhatemoneyTestCase): "payed_for": [1, 2, 3], "amount": "12", "original_currency": "EUR", - "bill_type": "Expense" + "bill_type": "Expense", }, ) self.client.post( @@ -2104,7 +2114,7 @@ class TestBudget(IhatemoneyTestCase): "payed_for": [1, 2], "amount": "15", "original_currency": "EUR", - "bill_type": "Expense" + "bill_type": "Expense", }, ) self.client.post( @@ -2116,7 +2126,7 @@ class TestBudget(IhatemoneyTestCase): "payed_for": [1, 2], "amount": "10", "original_currency": "EUR", - "bill_type": "Expense" + "bill_type": "Expense", }, ) @@ -2195,7 +2205,7 @@ class TestBudget(IhatemoneyTestCase): "payed_for": [1], "amount": "12", "original_currency": "XXX", - "bill_type": "Expense" + "bill_type": "Expense", }, follow_redirects=True, ) @@ -2364,7 +2374,7 @@ class TestBudget(IhatemoneyTestCase): "payer": members_ids[1], "payed_for": members_ids, "amount": "25", - "bill_type": "Expense" + "bill_type": "Expense", }, ) @@ -2382,7 +2392,7 @@ class TestBudget(IhatemoneyTestCase): "payer": members_ids_tartif[2], "payed_for": members_ids_tartif, "amount": "24", - "bill_type": "Expense" + "bill_type": "Expense", }, ) @@ -2417,7 +2427,7 @@ class TestBudget(IhatemoneyTestCase): "payer": members_ids[1], "payed_for": members_ids[1:], "amount": "25", - "bill_type": "Expense" + "bill_type": "Expense", }, ) From 178fc94ceff2669ab565f86793f44d5b35467b42 Mon Sep 17 00:00:00 2001 From: Baptiste Jonglez Date: Mon, 25 Mar 2024 20:32:30 +0100 Subject: [PATCH 04/46] Fix duplicate unit tests --- ihatemoney/tests/budget_test.py | 84 --------------------------------- 1 file changed, 84 deletions(-) diff --git a/ihatemoney/tests/budget_test.py b/ihatemoney/tests/budget_test.py index 15e7d4e1..e64090b9 100644 --- a/ihatemoney/tests/budget_test.py +++ b/ihatemoney/tests/budget_test.py @@ -877,90 +877,6 @@ class TestBudget(IhatemoneyTestCase): balance = self.get_project("random").balance assert set(balance.values()), set([500 == -500]) - def test_reimbursement_bill(self): - self.post_project("rent") - - # add two participants - self.client.post("/rent/members/add", data={"name": "bob"}) - self.client.post("/rent/members/add", data={"name": "alice"}) - - members_ids = [m.id for m in self.get_project("rent").members] - # create a bill to test reimbursement - self.client.post( - "/rent/add", - data={ - "date": "2022-12-12", - "what": "december rent", - "payer": members_ids[0], # bob - "payed_for": members_ids, # bob and alice - "bill_type": "Expense", - "amount": "1000", - }, - ) - # check balance - balance = self.get_project("rent").balance - assert set(balance.values()), set([500 == -500]) - # check paid - bob_paid = self.get_project("rent").full_balance[2][members_ids[0]] - alice_paid = self.get_project("rent").full_balance[2][members_ids[1]] - assert bob_paid == 1000 - assert alice_paid == 0 - - # test reimbursement bill - self.client.post( - "/rent/add", - data={ - "date": "2022-12-13", - "what": "reimbursement for rent", - "payer": members_ids[1], # alice - "payed_for": members_ids[0], # bob - "bill_type": "Reimbursement", - "amount": "500", - }, - ) - - balance = self.get_project("rent").balance - assert set(balance.values()), set([0 == 0]) - # check paid - bob_paid = self.get_project("rent").full_balance[2][members_ids[0]] - alice_paid = self.get_project("rent").full_balance[2][members_ids[1]] - assert bob_paid == 500 - assert alice_paid == 500 - - def test_transfer_bill(self): - self.post_project("random") - - # add two participants - self.client.post("/random/members/add", data={"name": "zorglub"}) - self.client.post("/random/members/add", data={"name": "fred"}) - - members_ids = [m.id for m in self.get_project("random").members] - self.client.post( - "/random/add", - data={ - "date": "2022-10-10", - "what": "Rent", - "payer": members_ids[0], # zorglub - "payed_for": members_ids, # zorglub + fred - "bill_type": "Expense", - "amount": "1000", - }, - ) - # test transfer bill (should not affect anything whatsoever) - self.client.post( - "/random/add", - data={ - "date": "2022-10-10", - "what": "Transfer of 500 to fred", - "payer": members_ids[0], # zorglub - "payed_for": members_ids[1], # fred - "bill_type": "Transfer", - "amount": "500", - }, - ) - balance = self.get_project("random").balance - assert set(balance.values()), set([500 == -500]) - def test_weighted_balance(self): self.post_project("raclette") From 843f2df877b4fa0d8fe701ccd44619fd6e55eb65 Mon Sep 17 00:00:00 2001 From: Baptiste Jonglez Date: Mon, 25 Mar 2024 20:28:17 +0100 Subject: [PATCH 05/46] CI: Temporarily disable failing python 3.12 job See #1297 --- .github/workflows/unit-tests.yml | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/.github/workflows/unit-tests.yml b/.github/workflows/unit-tests.yml index ddf5ab54..57d007a3 100644 --- a/.github/workflows/unit-tests.yml +++ b/.github/workflows/unit-tests.yml @@ -39,6 +39,11 @@ jobs: python-version: [3.7, 3.8, 3.9, "3.10", "3.11", "3.12"] dependencies: [normal] database: [sqlite] + # Installation breaks with python 3.12, see https://github.com/spiral-project/ihatemoney/issues/1297 + exclude: + - python-version: "3.12" + dependencies: normal + database: sqlite # Test other databases with only a few versions of Python (Debian bullseye has 3.9, bookworm has 3.11) include: - python-version: 3.9 From 510c8db07f86727b358115a7ed2dabd070c94fd0 Mon Sep 17 00:00:00 2001 From: Baptiste Jonglez Date: Mon, 25 Mar 2024 20:42:45 +0100 Subject: [PATCH 06/46] CI: make sure the tests matrix depends on linting --- .../{lint-docs.yml => check-doc.yml} | 18 +-------------- .../{unit-tests.yml => lint-and-tests.yml} | 23 ++++++++++++++++--- 2 files changed, 21 insertions(+), 20 deletions(-) rename .github/workflows/{lint-docs.yml => check-doc.yml} (56%) rename .github/workflows/{unit-tests.yml => lint-and-tests.yml} (87%) diff --git a/.github/workflows/lint-docs.yml b/.github/workflows/check-doc.yml similarity index 56% rename from .github/workflows/lint-docs.yml rename to .github/workflows/check-doc.yml index 12ec03fe..06dcf376 100644 --- a/.github/workflows/lint-docs.yml +++ b/.github/workflows/check-doc.yml @@ -1,4 +1,4 @@ -name: Lint & Docs +name: Check doc on: push: @@ -7,22 +7,6 @@ on: branches: [ 'master', 'stable-*' ] jobs: - lint: - runs-on: ubuntu-latest - steps: - - uses: actions/checkout@v3 - - name: Set up Python - uses: actions/setup-python@v4 - with: - python-version: "3.11" - cache: 'pip' - cache-dependency-path: '**/pyproject.toml' - - name: Install dependencies - run: | - python -m pip install --upgrade pip - python -m pip install tox - - name: Run Lint - run: tox -e lint test_doc: runs-on: ubuntu-latest diff --git a/.github/workflows/unit-tests.yml b/.github/workflows/lint-and-tests.yml similarity index 87% rename from .github/workflows/unit-tests.yml rename to .github/workflows/lint-and-tests.yml index 57d007a3..23f71fdc 100644 --- a/.github/workflows/unit-tests.yml +++ b/.github/workflows/lint-and-tests.yml @@ -1,4 +1,4 @@ -name: Unit tests +name: Lint & unit tests on: push: @@ -7,10 +7,27 @@ on: branches: [ 'master', 'stable-*' ] jobs: - test: - + lint: runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v3 + - name: Set up Python + uses: actions/setup-python@v4 + with: + python-version: "3.11" + cache: 'pip' + cache-dependency-path: '**/pyproject.toml' + - name: Install dependencies + run: | + python -m pip install --upgrade pip + python -m pip install tox + - name: Run Lint + run: tox -e lint + test: + # Dependency on linting to avoid running our expensive matrix test for nothing + needs: lint + runs-on: ubuntu-latest # Use postgresql and MariaDB versions of Debian bookworm services: postgres: From ae1cc309d75bf7ce849837bd0ff61eb51681b988 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=C3=89loi=20Rivard?= Date: Tue, 26 Mar 2024 09:05:33 +0100 Subject: [PATCH 07/46] fix: babel 2.14+ and python 3.12+ setuptools dependency --- .github/workflows/lint-and-tests.yml | 5 ----- pyproject.toml | 8 +++++++- 2 files changed, 7 insertions(+), 6 deletions(-) diff --git a/.github/workflows/lint-and-tests.yml b/.github/workflows/lint-and-tests.yml index 23f71fdc..4e30ff86 100644 --- a/.github/workflows/lint-and-tests.yml +++ b/.github/workflows/lint-and-tests.yml @@ -56,11 +56,6 @@ jobs: python-version: [3.7, 3.8, 3.9, "3.10", "3.11", "3.12"] dependencies: [normal] database: [sqlite] - # Installation breaks with python 3.12, see https://github.com/spiral-project/ihatemoney/issues/1297 - exclude: - - python-version: "3.12" - dependencies: normal - database: sqlite # Test other databases with only a few versions of Python (Debian bullseye has 3.9, bookworm has 3.11) include: - python-version: 3.9 diff --git a/pyproject.toml b/pyproject.toml index bf2de70b..cc6199a0 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -88,7 +88,13 @@ ihatemoney = "ihatemoney.manage:cli" [tool.hatch.build.hooks.custom] dependencies = [ # Babel is needed to compile translations catalogs at package build time - "Babel>=2.13.1" + "Babel>=2.13.1", + + # Babel 2.14 does not directly depend on setuptools + # https://github.com/python-babel/babel/blob/40e60a1f6cf178d9f57fcc14f157ea1b2ab77361/CHANGES.rst?plain=1#L22-L24 + # and neither python 3.12 due to PEP 632 + # https://peps.python.org/pep-0632/ + "setuptools; python_version>='3.12'", ] [tool.hatch.build] From a3d4e4250d17dbd56fdaa53f4dec448e3970f9f7 Mon Sep 17 00:00:00 2001 From: Timo Riski Date: Sat, 23 Mar 2024 16:49:42 +0200 Subject: [PATCH 08/46] fix: 'Bill Type: Invalid Choice: could not coerce' error Error introduced in #1290. Fixes #1293. WTForms needs to be bumped to >=2.3.2 as it includes a fix to `SelectField` which is required for this change to work. See: - https://wtforms.readthedocs.io/en/3.1.x/changes/#version-2-3-2 - https://github.com/wtforms/wtforms/pull/598 --- ihatemoney/models.py | 2 +- pyproject.toml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/ihatemoney/models.py b/ihatemoney/models.py index c7dee185..3272cf41 100644 --- a/ihatemoney/models.py +++ b/ihatemoney/models.py @@ -58,7 +58,7 @@ class BillType(Enum): @classmethod def choices(cls): - return [(choice, choice.value) for choice in cls] + return [(choice.value, choice.value) for choice in cls] db = SQLAlchemy() diff --git a/pyproject.toml b/pyproject.toml index cc6199a0..ee8ad57b 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -39,7 +39,7 @@ dependencies = [ "Flask-SQLAlchemy>=2.4,<3", "Flask-Talisman>=0.8,<2", "Flask-WTF>=0.14.3,<2", - "WTForms>=2.3.1,<3.2", + "WTForms>=2.3.3,<3.2", "Flask>=2,<3", "Werkzeug>=2,<3", "itsdangerous>=2,<3", From eef67cf84c15745d12653ccc68d61dc49b32bd0c Mon Sep 17 00:00:00 2001 From: Baptiste Jonglez Date: Fri, 29 Mar 2024 15:04:27 +0100 Subject: [PATCH 09/46] Remove dead settlement code (we switched to an external lib long ago) --- ihatemoney/models.py | 17 ----------------- 1 file changed, 17 deletions(-) diff --git a/ihatemoney/models.py b/ihatemoney/models.py index 3272cf41..c591b85b 100644 --- a/ihatemoney/models.py +++ b/ihatemoney/models.py @@ -209,7 +209,6 @@ class Project(db.Model): ) return pretty_transactions - # cache value for better performance members = {person.id: person for person in self.members} settle_plan = settle(self.balance.items()) or [] @@ -225,22 +224,6 @@ class Project(db.Model): return prettify(transactions, pretty_output) - def exactmatch(self, credit, debts): - """Recursively try and find subsets of 'debts' whose sum is equal to credit""" - if not debts: - return None - if debts[0]["balance"] > credit: - return self.exactmatch(credit, debts[1:]) - elif debts[0]["balance"] == credit: - return [debts[0]] - else: - match = self.exactmatch(credit - debts[0]["balance"], debts[1:]) - if match: - match.append(debts[0]) - else: - match = self.exactmatch(credit, debts[1:]) - return match - def has_bills(self): """return if the project do have bills or not""" return self.get_bills_unordered().count() > 0 From a3009126dcbe320810c46a7bd0e9fa34ccdbcb66 Mon Sep 17 00:00:00 2001 From: Tom Roussel <21120212+TomRoussel@users.noreply.github.com> Date: Sun, 24 Mar 2024 13:47:33 +0100 Subject: [PATCH 10/46] Removed test for removed transfer billtype --- ihatemoney/tests/budget_test.py | 34 --------------------------------- 1 file changed, 34 deletions(-) diff --git a/ihatemoney/tests/budget_test.py b/ihatemoney/tests/budget_test.py index e64090b9..8d530f1d 100644 --- a/ihatemoney/tests/budget_test.py +++ b/ihatemoney/tests/budget_test.py @@ -843,40 +843,6 @@ class TestBudget(IhatemoneyTestCase): assert bob_paid == 500 assert alice_paid == 500 - def test_transfer_bill(self): - self.post_project("random") - - # add two participants - self.client.post("/random/members/add", data={"name": "zorglub"}) - self.client.post("/random/members/add", data={"name": "fred"}) - - members_ids = [m.id for m in self.get_project("random").members] - self.client.post( - "/random/add", - data={ - "date": "2022-10-10", - "what": "Rent", - "payer": members_ids[0], # zorglub - "payed_for": members_ids, # zorglub + fred - "bill_type": "Expense", - "amount": "1000", - }, - ) - # test transfer bill (should not affect anything whatsoever) - self.client.post( - "/random/add", - data={ - "date": "2022-10-10", - "what": "Transfer of 500 to fred", - "payer": members_ids[0], # zorglub - "payed_for": members_ids[1], # fred - "bill_type": "Transfer", - "amount": "500", - }, - ) - balance = self.get_project("random").balance - assert set(balance.values()), set([500 == -500]) - def test_weighted_balance(self): self.post_project("raclette") From a74cd972862f6819fe15028ca551322a69aa1a7f Mon Sep 17 00:00:00 2001 From: Tom Roussel <21120212+TomRoussel@users.noreply.github.com> Date: Sun, 24 Mar 2024 13:49:16 +0100 Subject: [PATCH 11/46] Removed reference to transfer billtype in test --- ihatemoney/tests/budget_test.py | 14 +------------- 1 file changed, 1 insertion(+), 13 deletions(-) diff --git a/ihatemoney/tests/budget_test.py b/ihatemoney/tests/budget_test.py index 8d530f1d..fd6ac629 100644 --- a/ihatemoney/tests/budget_test.py +++ b/ihatemoney/tests/budget_test.py @@ -716,19 +716,7 @@ class TestBudget(IhatemoneyTestCase): "amount": "17", }, ) - - # transfer bill should not affect balances at all - self.client.post( - "/raclette/add", - data={ - "date": "2011-08-10", - "what": "Transfer", - "payer": members_ids[1], - "payed_for": members_ids[0], - "bill_type": "Transfer", - "amount": "500", - }, - ) + balance = self.get_project("raclette").balance assert set(balance.values()) == set([19.0, -19.0]) From f9a96b0e0dc1ed6b4899ea378f9f99c0f52c86c3 Mon Sep 17 00:00:00 2001 From: Tom Roussel <21120212+TomRoussel@users.noreply.github.com> Date: Sun, 24 Mar 2024 13:51:04 +0100 Subject: [PATCH 12/46] Removed fromage erasure --- ihatemoney/tests/import_test.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ihatemoney/tests/import_test.py b/ihatemoney/tests/import_test.py index 604c20f6..4e93bb56 100644 --- a/ihatemoney/tests/import_test.py +++ b/ihatemoney/tests/import_test.py @@ -560,7 +560,7 @@ class TestExport(IhatemoneyTestCase): }, { "date": "2016-12-31", - "what": "\xe0 raclette", + "what": "fromage \xe0 raclette", "bill_type": "Expense", "amount": 10.0, "currency": "EUR", From 050de4e8f61055849dea33cb958b00420ee7b432 Mon Sep 17 00:00:00 2001 From: Tom Roussel <21120212+TomRoussel@users.noreply.github.com> Date: Sat, 30 Mar 2024 19:41:45 +0100 Subject: [PATCH 13/46] Removed unnecessary FIXME This fixme was not actually valid. I think it was mistakenly copied from web.edit_bill --- ihatemoney/web.py | 2 -- 1 file changed, 2 deletions(-) diff --git a/ihatemoney/web.py b/ihatemoney/web.py index 3433fb91..4b5c82c5 100644 --- a/ihatemoney/web.py +++ b/ihatemoney/web.py @@ -852,8 +852,6 @@ def settle_bill(): @main.route("//settle///") def settle(amount, ower_id, payer_id): - # FIXME: Test this bill belongs to this project ! - new_reinbursement = Bill( amount=float(amount), date=datetime.datetime.today(), From a5f83de5cefaafa362572f81f65de63342428f92 Mon Sep 17 00:00:00 2001 From: Tom Roussel <21120212+TomRoussel@users.noreply.github.com> Date: Sat, 30 Mar 2024 19:44:07 +0100 Subject: [PATCH 14/46] Chore: ran black --- ihatemoney/tests/budget_test.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ihatemoney/tests/budget_test.py b/ihatemoney/tests/budget_test.py index fd6ac629..093d9d17 100644 --- a/ihatemoney/tests/budget_test.py +++ b/ihatemoney/tests/budget_test.py @@ -716,7 +716,7 @@ class TestBudget(IhatemoneyTestCase): "amount": "17", }, ) - + balance = self.get_project("raclette").balance assert set(balance.values()) == set([19.0, -19.0]) From 3ac1bb8afea479c4376a93a1d12e50d59d3c353a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=C3=89loi=20Rivard?= Date: Tue, 16 Apr 2024 14:02:42 +0200 Subject: [PATCH 15/46] tests: cache the jinja bytecode between unit tests The jinja templates are compiled once per test session instead of once per test, using jinja cache system and a pytest fixture. https://jinja.palletsprojects.com/en/3.1.x/api/#jinja2.FileSystemBytecodeCache --- ihatemoney/tests/conftest.py | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/ihatemoney/tests/conftest.py b/ihatemoney/tests/conftest.py index 35f99e27..ebeba15f 100644 --- a/ihatemoney/tests/conftest.py +++ b/ihatemoney/tests/conftest.py @@ -1,6 +1,7 @@ from unittest.mock import MagicMock from flask import Flask +from jinja2 import FileSystemBytecodeCache import pytest from ihatemoney.babel_utils import compile_catalogs @@ -13,11 +14,19 @@ def babel_catalogs(): compile_catalogs() +@pytest.fixture(scope="session") +def jinja_cache_directory(tmp_path_factory): + return tmp_path_factory.mktemp("cache") + + @pytest.fixture -def app(request: pytest.FixtureRequest): +def app(request: pytest.FixtureRequest, jinja_cache_directory): """Create the Flask app with database""" app = create_app(request.cls) + # Caches the jinja templates so they are compiled only once per test session + app.jinja_env.bytecode_cache = FileSystemBytecodeCache(jinja_cache_directory) + with app.app_context(): db.create_all() request.cls.app = app From e5dfbf2f37be3044b40e8d22306b55c3b9a8fe91 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alexis=20M=C3=A9taireau?= Date: Tue, 23 Apr 2024 19:45:44 +0200 Subject: [PATCH 16/46] doc: current status of the project Update the README and docs with the current status of the project regarding its maintenance and current direction. --- README.md | 29 +++++++++++++++++++++++++++++ docs/contributing.md | 29 +++++++++++++++++++++++++++++ 2 files changed, 58 insertions(+) diff --git a/README.md b/README.md index f6d3759e..46c7bdea 100644 --- a/README.md +++ b/README.md @@ -26,6 +26,35 @@ highly encouraged to do so. - **Backends**: SQLite, PostgreSQL, MariaDB (version 10.3.2 or above), Memory. +## Current direction (as of 2024) + +Ihatemoney was started in 2011, and we believe the project has reached a certain +level of maturity now. The overall energy of contributors is not as high as it +used to be. + +In addition, there are now several self-hosted alternatives (for instance +[cospend](https://github.com/julien-nc/cospend-nc/tree/main), [spliit](https:// +github.com/spliit-app/spliit)). As maintainers, we believe that the project is +still relevant but should gear towards some kind of "maintenance mode": + +* **Simplicity** is now the main goal of the project. It has always been a compass +for the project, and the resulting software is appreciated by both users and +server administrators. For us, "simplicity" is positive and encompasses both +technical aspects (very few javascript code, manageable dependencies, small code +size...) and user-visible aspects (straightforward interface, no need to create +accounts for people you invite, same web interface on mobile...) + +* **Stability** is prioritized over adding major new features. We found ourselves +complexifying the codebase (and the interface) by while accepting some +contributions. Our goal now is to have a minimal set of features that do most of +the job. We believe this will help lower the maintainance burden. + +* **User interface and user experience improvements** are always super welcome ! + +It is still possible to propose new features, but they should fit into +this new direction. Simplicity of the UI/UX and simplicity of the technical +implementation will be the main factors when deciding to accept new features. + ## Contributing Do you wish to contribute to IHateMoney? Fantastic! There's a lot of diff --git a/docs/contributing.md b/docs/contributing.md index 78d5a806..da1f61c0 100644 --- a/docs/contributing.md +++ b/docs/contributing.md @@ -1,5 +1,34 @@ # Contributing +## Current direction (as of 2024) + +Ihatemoney was started in 2011, and we believe the project has reached a certain +level of maturity now. The overall energy of contributors is not as high as it +used to be. + +In addition, there are now several self-hosted alternatives (for instance +[cospend](https://github.com/julien-nc/cospend-nc/tree/main), [spliit](https:// +github.com/spliit-app/spliit)). As maintainers, we believe that the project is +still relevant but should gear towards some kind of "maintenance mode": + +* **Simplicity** is now the main goal of the project. It has always been a compass +for the project, and the resulting software is appreciated by both users and +server administrators. For us, "simplicity" is positive and encompasses both +technical aspects (very few javascript code, manageable dependencies, small code +size...) and user-visible aspects (straightforward interface, no need to create +accounts for people you invite, same web interface on mobile...) + +* **Stability** is prioritized over adding major new features. We found ourselves +complexifying the codebase (and the interface) by while accepting some +contributions. Our goal now is to have a minimal set of features that do most of +the job. We believe this will help lower the maintainance burden. + +* **User interface and user experience improvements** are always super welcome ! + +It is still possible to propose new features, but they should fit into +this new direction. Simplicity of the UI/UX and simplicity of the technical +implementation will be the main factors when deciding to accept new features. + ## How to contribute You would like to contribute? First, thanks a bunch! This project is a From 4e7496e49d01f697ec919fccea19ee352aa786ee Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alexis=20M=C3=A9taireau?= Date: Tue, 23 Apr 2024 20:08:59 +0200 Subject: [PATCH 17/46] docs: fix broken links --- README.md | 10 ++++++---- docs/contributing.md | 11 +++++++---- 2 files changed, 13 insertions(+), 8 deletions(-) diff --git a/README.md b/README.md index 46c7bdea..bd8c739b 100644 --- a/README.md +++ b/README.md @@ -33,9 +33,11 @@ level of maturity now. The overall energy of contributors is not as high as it used to be. In addition, there are now several self-hosted alternatives (for instance -[cospend](https://github.com/julien-nc/cospend-nc/tree/main), [spliit](https:// -github.com/spliit-app/spliit)). As maintainers, we believe that the project is -still relevant but should gear towards some kind of "maintenance mode": +[cospend](https://github.com/julien-nc/cospend-nc/tree/main), +[spliit](https://github.com/spliit-app/spliit)). + +As maintainers, we believe that the project is still relevant but should gear +towards some kind of "maintenance mode": * **Simplicity** is now the main goal of the project. It has always been a compass for the project, and the resulting software is appreciated by both users and @@ -45,7 +47,7 @@ size...) and user-visible aspects (straightforward interface, no need to create accounts for people you invite, same web interface on mobile...) * **Stability** is prioritized over adding major new features. We found ourselves -complexifying the codebase (and the interface) by while accepting some +complexifying the codebase (and the interface) while accepting some contributions. Our goal now is to have a minimal set of features that do most of the job. We believe this will help lower the maintainance burden. diff --git a/docs/contributing.md b/docs/contributing.md index da1f61c0..821a3742 100644 --- a/docs/contributing.md +++ b/docs/contributing.md @@ -7,9 +7,11 @@ level of maturity now. The overall energy of contributors is not as high as it used to be. In addition, there are now several self-hosted alternatives (for instance -[cospend](https://github.com/julien-nc/cospend-nc/tree/main), [spliit](https:// -github.com/spliit-app/spliit)). As maintainers, we believe that the project is -still relevant but should gear towards some kind of "maintenance mode": +[cospend](https://github.com/julien-nc/cospend-nc/tree/main), +[spliit](https://github.com/spliit-app/spliit)). + +As maintainers, we believe that the project is still relevant but should gear +towards some kind of "maintenance mode": * **Simplicity** is now the main goal of the project. It has always been a compass for the project, and the resulting software is appreciated by both users and @@ -19,7 +21,7 @@ size...) and user-visible aspects (straightforward interface, no need to create accounts for people you invite, same web interface on mobile...) * **Stability** is prioritized over adding major new features. We found ourselves -complexifying the codebase (and the interface) by while accepting some +complexifying the codebase (and the interface) while accepting some contributions. Our goal now is to have a minimal set of features that do most of the job. We believe this will help lower the maintainance burden. @@ -29,6 +31,7 @@ It is still possible to propose new features, but they should fit into this new direction. Simplicity of the UI/UX and simplicity of the technical implementation will be the main factors when deciding to accept new features. + ## How to contribute You would like to contribute? First, thanks a bunch! This project is a From 9ef46e2c5da272d5ad4f6c7d914f31b2da004a53 Mon Sep 17 00:00:00 2001 From: Baptiste Jonglez Date: Fri, 29 Mar 2024 15:56:55 +0100 Subject: [PATCH 18/46] Add a success message when adding an automatic settlement bill --- ihatemoney/web.py | 1 + 1 file changed, 1 insertion(+) diff --git a/ihatemoney/web.py b/ihatemoney/web.py index 4b5c82c5..0d0bdd20 100644 --- a/ihatemoney/web.py +++ b/ihatemoney/web.py @@ -866,6 +866,7 @@ def settle(amount, ower_id, payer_id): db.session.add(new_reinbursement) db.session.commit() + flash(_("Settlement bill has been successfully added"), category="success") return redirect(url_for(".settle_bill")) From eb6e156c328180eebfdc72cdd09fd518ed8b0bc2 Mon Sep 17 00:00:00 2001 From: "Weblate (bot)" Date: Fri, 10 May 2024 12:12:22 +0200 Subject: [PATCH 19/46] Translations update from Hosted Weblate (#1311) Co-authored-by: Gesiane Pajarinen --- .../translations/pt/LC_MESSAGES/messages.po | 58 ++-- .../pt_BR/LC_MESSAGES/messages.po | 266 +++++++++--------- 2 files changed, 165 insertions(+), 159 deletions(-) diff --git a/ihatemoney/translations/pt/LC_MESSAGES/messages.po b/ihatemoney/translations/pt/LC_MESSAGES/messages.po index 1951a2bc..d71513a7 100644 --- a/ihatemoney/translations/pt/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/pt/LC_MESSAGES/messages.po @@ -1,18 +1,18 @@ - msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2023-07-29 14:24+0200\n" -"PO-Revision-Date: 2023-05-05 00:47+0000\n" -"Last-Translator: MurkBRA \n" +"PO-Revision-Date: 2024-05-10 07:26+0000\n" +"Last-Translator: Gesiane Pajarinen \n" +"Language-Team: Portuguese \n" "Language: pt\n" -"Language-Team: Portuguese \n" -"Plural-Forms: nplurals=2; plural=n > 1\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=utf-8\n" "Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=n > 1;\n" +"X-Generator: Weblate 5.5.4-rc\n" "Generated-By: Babel 2.9.0\n" #, python-format @@ -34,7 +34,7 @@ msgid "Current private code" msgstr "Código privado novo" msgid "Enter existing private code to edit project" -msgstr "" +msgstr "Insira o código privado existente para editar o projeto" msgid "New private code" msgstr "Código privado novo" @@ -71,7 +71,7 @@ msgstr "" " em várias moedas." msgid "Compatible with Cospend" -msgstr "" +msgstr "Compatível com Cospend" msgid "Project identifier" msgstr "Identificador do projeto" @@ -192,7 +192,7 @@ msgid "Logout" msgstr "Sair" msgid "Please check the email configuration of the server." -msgstr "" +msgstr "Verifique a configuração de e-mail do servidor." #, fuzzy, python-format msgid "" @@ -279,14 +279,14 @@ msgid "Password successfully reset." msgstr "Palavra-passe redefinida corretamente." msgid "Project settings have been changed successfully." -msgstr "" +msgstr "As configurações do projeto foram alteradas com sucesso." msgid "Unable to parse CSV" -msgstr "" +msgstr "Não foi possível processar o CSV" #, python-format msgid "Missing attribute: %(attribute)s" -msgstr "" +msgstr "Faltando o atributo: %(attribute)s" msgid "" "Cannot add bills in multiple currencies to a project without default " @@ -305,7 +305,7 @@ msgid "Error deleting project" msgstr "Erro ao apagar o projeto" msgid "Unable to logout" -msgstr "" +msgstr "Não é possível sair" #, python-format msgid "You have been invited to share your expenses for %(project)s" @@ -365,7 +365,7 @@ msgstr "A fatura foi modificada" #, python-format msgid "%(lang)s is not a supported language" -msgstr "" +msgstr "Não temos configuração para o idioma %(lang)s" msgid "Error deleting project history" msgstr "Erro ao apagar o histórico do projeto" @@ -476,7 +476,7 @@ msgid "Privacy Settings" msgstr "Configurações de Privacidade" msgid "Save changes" -msgstr "" +msgstr "Salvar as alterações" msgid "This will remove all bills and participants in this project!" msgstr "Isso removerá todas as faturas e os participantes deste projeto!" @@ -495,7 +495,7 @@ msgid "Add a bill" msgstr "Adicionar uma fatura" msgid "Simple operations are allowed, e.g. (18+36.2)/3" -msgstr "" +msgstr "Operações simples são permitidas, por ex. (18+36,2)/3" msgid "Everyone" msgstr "Todos" @@ -587,6 +587,7 @@ msgstr "Fatura %(name)s: removido %(owers_list_str)s da lista de proprietários" msgid "This project has history disabled. New actions won't appear below." msgstr "" +"Este projeto tem o histórico desativado. Novas ações não aparecerão abaixo." #, fuzzy msgid "You can enable history on the settings page." @@ -596,6 +597,8 @@ msgid "" "The table below reflects actions recorded prior to disabling project " "history." msgstr "" +"A tabela abaixo contém as ações registradas antes da desativação do " +"histórico do projeto." #, fuzzy msgid "You can clear the project history to remove them." @@ -796,7 +799,7 @@ msgid "Settings" msgstr "Configurações" msgid "RSS Feed" -msgstr "" +msgstr "RSS Feed" msgid "Other projects :" msgstr "Outros projetos:" @@ -809,7 +812,7 @@ msgstr "Painel de controle" #, python-format msgid "Please retry after %(date)s." -msgstr "" +msgstr "Por favor, tente novamente após %(date)s." msgid "Code" msgstr "Código" @@ -905,7 +908,7 @@ msgid "Invite people to join this project" msgstr "Convide pessoas para participar deste projeto" msgid "Share an invitation link" -msgstr "" +msgstr "Compartilhe um link do convite" msgid "" "The easiest way to invite people is to give them the following invitation" @@ -913,12 +916,17 @@ msgid "" " add/edit/delete bills. However, they will not have access to important " "settings such as changing the private code or deleting the whole project." msgstr "" +"A maneira mais fácil de convidar as pessoas é compartilhando o seguinte link " +"do convite.
Eles poderão acessar o projeto, gerenciar participantes, " +"adicionar/editar/excluir contas. No entanto, eles não terão acesso a " +"configurações importantes, como alterar o código privado ou excluir todo o " +"projeto." msgid "Scan QR code" -msgstr "" +msgstr "Escanear o código QR" msgid "Use a mobile device with a compatible app." -msgstr "" +msgstr "Use um telefone celular ou tablet com um aplicativo compatível." msgid "Send via Emails" msgstr "Enviar via E-mails" @@ -943,6 +951,11 @@ msgid "" "to the full project, including changing settings such as the private code" " or project email address, or even deleting the whole project." msgstr "" +"Você pode compartilhar o identificador do projeto e o código privado por " +"qualquer meio de comunicação.
Qualquer pessoa com o código privado terá " +"acesso a todo o projeto, incluindo a alteração de configurações como o " +"código privado ou o endereço do e-mail, ou até mesmo a exclusão de todo o " +"projeto." msgid "Identifier:" msgstr "Identificador:" @@ -952,7 +965,7 @@ msgid "Private code:" msgstr "Código privado" msgid "the private code was defined when you created the project" -msgstr "" +msgstr "o código privado foi definido quando você criou o projeto" msgid "Who pays?" msgstr "Quem paga?" @@ -1140,4 +1153,3 @@ msgstr "Período" #~ msgstr "" #~ "Pode compartilhar diretamente o seguinte " #~ "ligação através do seu meio preferido" - diff --git a/ihatemoney/translations/pt_BR/LC_MESSAGES/messages.po b/ihatemoney/translations/pt_BR/LC_MESSAGES/messages.po index bde9a5af..47ca000b 100644 --- a/ihatemoney/translations/pt_BR/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/pt_BR/LC_MESSAGES/messages.po @@ -1,18 +1,18 @@ - msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2023-07-29 14:24+0200\n" -"PO-Revision-Date: 2023-05-05 00:47+0000\n" -"Last-Translator: MurkBRA \n" +"PO-Revision-Date: 2024-05-10 07:26+0000\n" +"Last-Translator: Gesiane Pajarinen \n" +"Language-Team: Portuguese (Brazil) \n" "Language: pt_BR\n" -"Language-Team: Portuguese (Brazil) \n" -"Plural-Forms: nplurals=2; plural=n > 1\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=utf-8\n" "Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=n > 1;\n" +"X-Generator: Weblate 5.5.4-rc\n" "Generated-By: Babel 2.9.0\n" #, python-format @@ -23,24 +23,23 @@ msgid "" "Not a valid amount or expression. Only numbers and + - * / operators are " "accepted." msgstr "" -"Expressão ou montante inválido. Apenas números e os operadores +=*/ são " +"Expressão ou quantia inválida. Apenas números e os operadores +=*/ são " "aceitos." msgid "Project name" msgstr "Nome do projeto" -#, fuzzy msgid "Current private code" -msgstr "Código privado novo" +msgstr "Código privado atual" msgid "Enter existing private code to edit project" -msgstr "" +msgstr "Insira o código privado para editar o projeto" msgid "New private code" -msgstr "Código privado novo" +msgstr "Novo código privado" msgid "Enter a new code if you want to change it" -msgstr "Insira um novo código se quiser alterá-lo" +msgstr "Digite um novo código se quiser mudá-lo" msgid "Email" msgstr "E-mail" @@ -67,11 +66,11 @@ msgid "" "This project cannot be set to 'no currency' because it contains bills in " "multiple currencies." msgstr "" -"O projeto não pode ser definido como 'sem moeda' porque contém contas em " -"várias moedas." +"Esse projeto não pode ser configurado como 'sem moeda' porque ele tem " +"faturas em moedas diferentes." msgid "Compatible with Cospend" -msgstr "" +msgstr "Compatível com Cospend" msgid "Project identifier" msgstr "Identificador do projeto" @@ -148,7 +147,7 @@ msgid "A link to an external document, related to this bill" msgstr "Link para um documento externo, relacionado à essa conta" msgid "For whom?" -msgstr "Para quem?" +msgstr "Por quem?" msgid "Submit" msgstr "Enviar" @@ -173,10 +172,10 @@ msgid "Add" msgstr "Adicionar" msgid "The participant name is invalid" -msgstr "'%(name)s' não é um usuário válido" +msgstr "O nome do participante não é válido" msgid "This project already have this participant" -msgstr "'%(name)s' já está no projeto" +msgstr "Este participante já está no projeto" msgid "People to notify" msgstr "Pessoas para notificar" @@ -192,16 +191,15 @@ msgid "Logout" msgstr "Sair" msgid "Please check the email configuration of the server." -msgstr "" +msgstr "Verifique a configuração de e-mail do servidor." -#, fuzzy, python-format +#, python-format msgid "" "Please check the email configuration of the server or contact the " "administrator: %(admin_email)s" msgstr "" -"Desculpe, houve um erro ao enviar os convites via e-mail. Por favor, " -"confira a configuração de email do servidor ou entre em contato com um " -"administrador." +"Verifique a configuração de e-mail do servidor ou entre em contato com o " +"administrador: %(admin_email)s" #. List with two items only msgid "{dual_object_0} and {dual_object_1}" @@ -230,18 +228,17 @@ msgstr "{prefix}: {error}" msgid "{prefix}:
{errors}" msgstr "{prefix}:
{errors}" -#, fuzzy msgid "Too many failed login attempts." -msgstr "Muitas tentativas de login falhas, por favor, tente novamente mais tarde." +msgstr "Muitas tentativas de login falhas." #, python-format msgid "This admin password is not the right one. Only %(num)d attempts left." msgstr "" -"Esta senha de administrador não é a correta. Apenas %(num)d tentativas " +"Esta senha de administrador não está correta. Apenas %(num)d tentativas " "restantes." msgid "Provided token is invalid" -msgstr "Token invalido" +msgstr "O token fornecido é inválido" msgid "This private code is not the right one" msgstr "Este código privado não é o correto" @@ -253,17 +250,15 @@ msgid "" "We tried to send you an reminder email, but there was an error. You can " "still use the project normally." msgstr "" -"Nós tentamos te enviar um email de lembrete, mas aconteceu um erro. Você " -"pode continuar usando o projeto normalmente." +"Tentamos te enviar um email de lembrete, mas aconteceu um erro. Você pode " +"continuar usando o projeto normalmente." -#, fuzzy msgid "" "Sorry, there was an error while sending you an email with password reset " "instructions." msgstr "" "Desculpe, houve um erro ao te enviar um email com as instruções de " -"redefinição de senha. Por favor, confira a configuração de e-mail do " -"servidor ou entre em contato com um administrador." +"redefinição de senha." msgid "No token provided" msgstr "Nenhum token fornecido" @@ -275,37 +270,36 @@ msgid "Unknown project" msgstr "Projeto desconhecido" msgid "Password successfully reset." -msgstr "Senha redefinida corretamente." +msgstr "Senha redefinida com sucesso." msgid "Project settings have been changed successfully." -msgstr "" +msgstr "As configurações do projeto foram alteradas com sucesso." msgid "Unable to parse CSV" -msgstr "" +msgstr "Não foi possível processar o CSV" #, python-format msgid "Missing attribute: %(attribute)s" -msgstr "" +msgstr "Faltando o atributo: %(attribute)s" -#, fuzzy msgid "" "Cannot add bills in multiple currencies to a project without default " "currency" msgstr "" -"Não é possível adicionar contas em várias moedas a um projeto sem moeda " +"Não é possível adicionar contas em várias moedas em um projeto sem moeda " "padrão" msgid "Project successfully uploaded" -msgstr "Projeto enviado corretamente" +msgstr "Projeto enviado com sucesso" msgid "Project successfully deleted" msgstr "Projeto deletado com sucesso" msgid "Error deleting project" -msgstr "Erro ao excluir o projeto" +msgstr "Erro ao deletar o projeto" msgid "Unable to logout" -msgstr "" +msgstr "Não é possível sair" #, python-format msgid "You have been invited to share your expenses for %(project)s" @@ -314,76 +308,73 @@ msgstr "Você foi convidado a compartilhar suas despesas com %(project)s" msgid "Your invitations have been sent" msgstr "Seus convites foram enviados" -#, fuzzy msgid "Sorry, there was an error while trying to send the invitation emails." -msgstr "" -"Desculpe, houve um erro ao enviar os convites via e-mail. Por favor, " -"confira a configuração de email do servidor ou entre em contato com um " -"administrador." +msgstr "Desculpe, houve um erro ao enviar os convites via e-mail." #, python-format msgid "%(member)s has been added" -msgstr "%(member)s foram adicionados" +msgstr "%(member)s foi adicionado(a)" msgid "Error activating participant" -msgstr "Erro ao ativar usuário" +msgstr "Erro ao ativar participante" #, python-format msgid "%(name)s is part of this project again" msgstr "%(name)s faz parte deste projeto novamente" msgid "Error removing participant" -msgstr "Erro ao remover usuário" +msgstr "Erro ao remover participante" #, python-format msgid "" "Participant '%(name)s' has been deactivated. It will still appear in the " "list until its balance reach zero." msgstr "" -"Usuário '%(name)s' foi desativado. Ele continuará aparecendo na lista de " -"usuários até que seu saldo seja zero." +"O participante '%(name)s' foi desativado. Ele continuará aparecendo na lista " +"de usuários até que seu saldo seja zero." -#, fuzzy, python-format +#, python-format msgid "Participant '%(name)s' has been removed" -msgstr "Usuário '%(name)s' foi removido" +msgstr "Participante '%(name)s' foi removido(a)" -#, fuzzy, python-format +#, python-format msgid "Participant '%(name)s' has been modified" -msgstr "Usuário '%(name)s' foi removido" +msgstr "Participante '%(name)s' foi alterado(a)" msgid "The bill has been added" msgstr "A conta foi adicionada" msgid "Error deleting bill" -msgstr "Erro ao excluir conta" +msgstr "Erro ao excluir a conta" msgid "The bill has been deleted" msgstr "A conta foi deletada" msgid "The bill has been modified" -msgstr "A conta foi modificada" +msgstr "A conta foi alterada" #, python-format msgid "%(lang)s is not a supported language" -msgstr "" +msgstr "Não temos configuração para o idioma %(lang)s" msgid "Error deleting project history" msgstr "Erro ao deletar o histórico do projeto" msgid "Deleted project history." -msgstr "Histórico do projeto apagado." +msgstr "Histórico do projeto deletado." msgid "Error deleting recorded IP addresses" -msgstr "Erro ao excluir endereços IP salvos" +msgstr "Erro ao deletar endereços IP salvos" msgid "Deleted recorded IP addresses in project history." -msgstr "Endereços IP salvos no histórico de projeto deletados." +msgstr "Endereços de IP registrados deletados no histórico do projeto." msgid "Sorry, we were unable to find the page you've asked for." msgstr "Desculpe, não foi possível encontrar a página que você solicitou." msgid "The best thing to do is probably to get back to the main page." -msgstr "É provável que a melhor coisa a fazer seja voltar para a página inicial." +msgstr "" +"Provavelmente, a melhor coisa a fazer seja voltar para a página inicial." msgid "Back to the list" msgstr "Voltar para a lista" @@ -398,7 +389,7 @@ msgid "The project you are trying to access do not exist, do you want to" msgstr "O projeto que você está tentando acessar não existe, você quer" msgid "create it" -msgstr "Criar" +msgstr "criar" msgid "?" msgstr "?" @@ -410,7 +401,7 @@ msgid "Project" msgstr "Projeto" msgid "Number of participants" -msgstr "Número de usuários" +msgstr "Número de participantes" msgid "Number of bills" msgstr "Número de contas" @@ -428,29 +419,28 @@ msgid "edit" msgstr "editar" msgid "Delete project" -msgstr "Excluir projeto" +msgstr "Deletar projeto" msgid "show" -msgstr "exibir" +msgstr "mostrar" msgid "The Dashboard is currently deactivated." msgstr "O Painel de Controle atualmente está desativado." msgid "Download Mobile Application" -msgstr "Baixar o APP" +msgstr "Baixar o aplicativo" msgid "Get it on" -msgstr "Pegue agora" +msgstr "Comece" msgid "Edit project" msgstr "Editar projeto" -#, fuzzy msgid "Import project" -msgstr "Editar projeto" +msgstr "Importar projeto" msgid "Download project's data" -msgstr "Baixar dados do projeto" +msgstr "Baixar os dados do projeto" msgid "Bill items" msgstr "Itens da conta" @@ -474,14 +464,13 @@ msgid "Privacy Settings" msgstr "Configurações de Privacidade" msgid "Save changes" -msgstr "" +msgstr "Salvar as alterações" msgid "This will remove all bills and participants in this project!" -msgstr "Isso vai remover todas as contas e participantes desse projeto!" +msgstr "Isso vai remover todas as faturas e participantes desse projeto!" -#, fuzzy msgid "Import previously exported project" -msgstr "Importar arquivo JSON exportado anteriormente" +msgstr "Importar projeto que foi exportado anteriormente" msgid "Choose file" msgstr "Escolher arquivo" @@ -493,7 +482,7 @@ msgid "Add a bill" msgstr "Adicionar uma conta" msgid "Simple operations are allowed, e.g. (18+36.2)/3" -msgstr "" +msgstr "Operações simples são permitidas, por ex. (18+36,2)/3" msgid "Everyone" msgstr "Todos" @@ -508,7 +497,7 @@ msgid "Add participant" msgstr "Adicionar participante" msgid "Edit this participant" -msgstr "Editar usuário" +msgstr "Editar participante" msgid "john.doe@example.com, mary.moe@site.com" msgstr "john.doe@example.com, mary.moe@site.com" @@ -517,22 +506,22 @@ msgid "Download" msgstr "Baixar" msgid "Disabled Project History" -msgstr "Histórico do Projeto Desativado" +msgstr "Histórico de Projeto Desativado" msgid "Disabled Project History & IP Address Recording" -msgstr "Histórico do Projeto Desativado & Gravação de Endereço IP" +msgstr "Histórico de Projeto Desativado & Registro de Endereços de IP" msgid "Enabled Project History" -msgstr "Histórico do Projeto Ativado" +msgstr "Histórico de Projeto Ativado" msgid "Disabled IP Address Recording" -msgstr "Gravação do Endereço IP Desativada" +msgstr "Registro de Endereços de IP Desativados" msgid "Enabled Project History & IP Address Recording" -msgstr "Histórico do Projeto Ativado & Gravação do Endereço IP" +msgstr "Histórico de Projeto Ativado & Registro de Endereços de IP" msgid "Enabled IP Address Recording" -msgstr "Gravação do Endereço IP Ativada" +msgstr "Registro de Endereços de IP Ativado" msgid "History Settings Changed" msgstr "Configurações do Histórico Alteradas" @@ -554,13 +543,13 @@ msgid "" " The rest of the project history will be unaffected. This " "action cannot be undone." msgstr "" -"Você tem certeza que deseja deletar todos os endereços IP gravados deste " -"projeto?\n" -" O resto do histórico do projeto não será afetado. Esta " -"ação não pode ser desfeita." +"Tem certeza que deseja deletar todos os endereços IP gravados neste projeto?" +"\n" +" O resto do histórico do projeto não será afetado. Esta ação " +"não pode ser desfeita." msgid "Confirm deletion" -msgstr "Confirmar exclusão" +msgstr "Confirmar a exclusão" msgid "Close" msgstr "Fechar" @@ -577,27 +566,28 @@ msgstr "" #, python-format msgid "Bill %(name)s: added %(owers_list_str)s to owers list" -msgstr "Conta %(name)s: adicionou %(owers_list_str)s a lista de devedores" +msgstr "Conta %(name)s: adicionados %(owers_list_str)s à lista de proprietários" #, python-format msgid "Bill %(name)s: removed %(owers_list_str)s from owers list" -msgstr "Conta %(name)s: removeu %(owers_list_str)s da lista de devedores" +msgstr "Conta %(name)s: removidos %(owers_list_str)s da lista de proprietários" msgid "This project has history disabled. New actions won't appear below." msgstr "" +"Este projeto tem o histórico desativado. Novas ações não aparecerão abaixo." -#, fuzzy msgid "You can enable history on the settings page." -msgstr "A gravação do endereço IP pode ser ativada na página de configurações" +msgstr "Você pode ativar o histórico na página de configurações." msgid "" "The table below reflects actions recorded prior to disabling project " "history." msgstr "" +"A tabela abaixo contém as ações registradas antes da desativação do " +"histórico do projeto." -#, fuzzy msgid "You can clear the project history to remove them." -msgstr "Alguém provavelmente limpou o histórico do projeto." +msgstr "Você pode limpar o histórico do projeto para removê-los." msgid "" "Some entries below contain IP addresses, even though this project has IP " @@ -613,7 +603,7 @@ msgid "No IP Addresses to erase" msgstr "Não há endereços IP para apagar" msgid "Delete Stored IP Addresses" -msgstr "Deletar endereços IP salvos" +msgstr "Deletar Endereços IP Salvos" msgid "No history to erase" msgstr "Não há histórico para apagar" @@ -622,7 +612,7 @@ msgid "Clear Project History" msgstr "Limpar Histórico do Projeto" msgid "Time" -msgstr "Tempo" +msgstr "Data e hora" msgid "Event" msgstr "Evento" @@ -634,7 +624,7 @@ msgid "IP address recording can be disabled on the settings page" msgstr "A gravação do endereço IP pode ser desativada na página de configurações" msgid "From IP" -msgstr "Do IP" +msgstr "IP" #, python-format msgid "Project %(name)s added" @@ -646,7 +636,7 @@ msgstr "Conta %(name)s adicionada" #, python-format msgid "Participant %(name)s added" -msgstr "Usuário %(name)s adicionado" +msgstr "Participante %(name)s adicionado(a)" msgid "Project private code changed" msgstr "Código privado do projeto alterado" @@ -664,15 +654,15 @@ msgstr "Configurações do projeto alteradas" #, python-format msgid "Participant %(name)s deactivated" -msgstr "Usuário %(name)s desativado" +msgstr "Participante %(name)s desativado" #, python-format msgid "Participant %(name)s reactivated" -msgstr "Usuário %(name)s reativado" +msgstr "Participante %(name)s reativado" #, python-format msgid "Participant %(name)s renamed to %(new_name)s" -msgstr "Usuário %(name)s renomeado para %(new_name)s" +msgstr "Participante %(name)s renomeado para %(new_name)s" #, python-format msgid "Bill %(name)s renamed to %(new_description)s" @@ -680,7 +670,8 @@ msgstr "Conta %(name)s renomeada para %(new_description)s" #, python-format msgid "Participant %(name)s: weight changed from %(old_weight)s to %(new_weight)s" -msgstr "Usuário %(name)s: a carga mudou de %(old_weight)s para %(new_weight)s" +msgstr "" +"Participante %(name)s: o peso mudou de %(old_weight)s para %(new_weight)s" msgid "Payer" msgstr "Pagador" @@ -697,40 +688,40 @@ msgstr "Quantia em %(currency)s" #, python-format msgid "Bill %(name)s modified" -msgstr "Conta %(name)s modificada" +msgstr "Conta %(name)s alterada" #, python-format msgid "Participant %(name)s modified" -msgstr "Usuário %(name)s modificado" +msgstr "Participante %(name)s foi alterado(a)" #, python-format msgid "Bill %(name)s removed" msgstr "Conta '%(name)s' foi removida" -#, fuzzy, python-format +#, python-format msgid "Participant %(name)s removed" -msgstr "Usuário '%(name)s' foi removido" +msgstr "Participante '%(name)s' foi removido" #, python-format msgid "Project %(name)s changed in an unknown way" -msgstr "Projeto %(name)s modificado de maneira desconhecida" +msgstr "Projeto %(name)s alterado de maneira desconhecida" #, python-format msgid "Bill %(name)s changed in an unknown way" -msgstr "Conta %(name)s modificado de maneira desconhecida" +msgstr "Conta %(name)s alterada de maneira desconhecida" #, python-format msgid "Participant %(name)s changed in an unknown way" -msgstr "Participante %(name)s modificado de maneira desconhecida" +msgstr "Participante %(name)s alterado(a) de maneira desconhecida" msgid "Nothing to list" -msgstr "Nada a listar" +msgstr "Nada para listar" msgid "Someone probably cleared the project history." msgstr "Alguém provavelmente limpou o histórico do projeto." msgid "Manage your shared
expenses, easily" -msgstr "Modifique suas despesas
compartilhadas, facilmente" +msgstr "Gerencie suas despesas
compartilhadas com facilidade" msgid "Try out the demo" msgstr "Experimente a demonstração" @@ -748,13 +739,13 @@ msgid "We can help!" msgstr "Nós podemos ajudar!" msgid "Log in to an existing project" -msgstr "Conecte-se em um projeto existente" +msgstr "Faça login em um projeto existente" msgid "Log in" -msgstr "Conecte-se" +msgstr "Login" msgid "can't remember your password?" -msgstr "não consegue se lembrar da sua senha?" +msgstr "não lembra sua senha?" msgid "Create" msgstr "Criar" @@ -773,13 +764,13 @@ msgid "Bills" msgstr "Contas" msgid "Settle" -msgstr "Estabelecer" +msgstr "Pagamentos" msgid "Statistics" msgstr "Estatísticas" msgid "Languages" -msgstr "Linguagens" +msgstr "Idiomas" msgid "Projects" msgstr "Projetos" @@ -794,7 +785,7 @@ msgid "Settings" msgstr "Configurações" msgid "RSS Feed" -msgstr "" +msgstr "Feed RSS" msgid "Other projects :" msgstr "Outros projetos:" @@ -807,13 +798,13 @@ msgstr "Painel de controle" #, python-format msgid "Please retry after %(date)s." -msgstr "" +msgstr "Por favor, tente novamente após %(date)s." msgid "Code" msgstr "Código" msgid "Mobile Application" -msgstr "Aplicação Mobile" +msgstr "Aplicativo" msgid "Documentation" msgstr "Documentação" @@ -847,7 +838,7 @@ msgid "Older bills" msgstr "Contas mais antigas" msgid "You should start by adding participants" -msgstr "Você deveria começar adicionando pessoas" +msgstr "Comece adicionando participantes" msgid "Add a new bill" msgstr "Adicionar uma nova conta" @@ -872,13 +863,11 @@ msgstr "Sem contas" msgid "Nothing to list yet." msgstr "Nada para listar ainda." -#, fuzzy msgid "Add your first bill" -msgstr "adicionar uma conta" +msgstr "Adicione sua primeira conta" -#, fuzzy msgid "Add the first participant" -msgstr "Editar usuário" +msgstr "Adicione o primeiro participante" msgid "Password reminder" msgstr "Lembrete de senha" @@ -903,7 +892,7 @@ msgid "Invite people to join this project" msgstr "Convide pessoas para participar deste projeto" msgid "Share an invitation link" -msgstr "" +msgstr "Compartilhe um link do convite" msgid "" "The easiest way to invite people is to give them the following invitation" @@ -911,26 +900,29 @@ msgid "" " add/edit/delete bills. However, they will not have access to important " "settings such as changing the private code or deleting the whole project." msgstr "" +"A maneira mais fácil de convidar as pessoas é enviando o seguinte link para " +"convite.
Eles poderão acessar o projeto, gerenciar participantes, " +"adicionar/editar/excluir contas. No entanto, eles não terão acesso às " +"configurações importantes, como alterar o código privado ou excluir todo o " +"projeto." msgid "Scan QR code" -msgstr "" +msgstr "Escaneie o QR code" msgid "Use a mobile device with a compatible app." -msgstr "" +msgstr "Use um telefone celular ou tablet com um aplicativo compatível." msgid "Send via Emails" msgstr "Enviar via E-mails" -#, fuzzy msgid "" "Specify a list of email adresses (separated by comma) of people you want " "to notify about the creation of this project. We will send them an email " "with the invitation link." msgstr "" -"Especifica uma lista de endereços de email (separados por vírgula) que " -"você quer notificar acerca da\n" -" criação deste projeto de gestão de saldo e nós iremos " -"enviar um email por si." +"Especifique uma lista de e-mails (separados por vírgula) das pessoas que " +"você deseja notificar sobre a criação deste projeto. Enviaremos um e-mail " +"para eles com o link do convite." msgid "Share Identifier & code" msgstr "Compartilhar Identificador & código" @@ -941,16 +933,19 @@ msgid "" "to the full project, including changing settings such as the private code" " or project email address, or even deleting the whole project." msgstr "" +"Você pode compartilhar o identificador do projeto e o código privado por " +"qualquer meio de comunicação.
Qualquer pessoa com o código privado terá " +"acesso a todo o projeto e poderá alterar as configurações como o código " +"privado ou o e-mail, ou até mesmo a exclusão de todo o projeto." msgid "Identifier:" msgstr "Identificador:" -#, fuzzy msgid "Private code:" -msgstr "Código privado" +msgstr "Código privado:" msgid "the private code was defined when you created the project" -msgstr "" +msgstr "o código privado foi definido quando você criou o projeto" msgid "Who pays?" msgstr "Quem paga?" @@ -1140,4 +1135,3 @@ msgstr "Período" #~ "Você pode compartilhar diretamente o " #~ "seguinte link através do seu meio " #~ "preferido" - From 710aee97115e501eb548b9e8b4a9713037af0793 Mon Sep 17 00:00:00 2001 From: "Weblate (bot)" Date: Mon, 8 Jul 2024 19:56:00 +0200 Subject: [PATCH 20/46] Translations update from Hosted Weblate (#1312) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Harshini K Co-authored-by: Yamin Siahmargooei Co-authored-by: Quentin PAGÈS Co-authored-by: Khang Tran Co-authored-by: NtWriteCode Co-authored-by: szabi --- .../translations/ca/LC_MESSAGES/messages.po | 15 +- .../translations/fa/LC_MESSAGES/messages.po | 23 +- .../translations/hu/LC_MESSAGES/messages.po | 462 +++++---- .../translations/ja/LC_MESSAGES/messages.po | 85 +- .../translations/oc/LC_MESSAGES/messages.po | 932 ++++++++++++++++++ .../translations/te/LC_MESSAGES/messages.po | 23 +- 6 files changed, 1249 insertions(+), 291 deletions(-) create mode 100644 ihatemoney/translations/oc/LC_MESSAGES/messages.po diff --git a/ihatemoney/translations/ca/LC_MESSAGES/messages.po b/ihatemoney/translations/ca/LC_MESSAGES/messages.po index 444e60a8..1b797cfc 100644 --- a/ihatemoney/translations/ca/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/ca/LC_MESSAGES/messages.po @@ -1,18 +1,18 @@ - msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2023-07-29 14:24+0200\n" -"PO-Revision-Date: 2022-09-12 15:25+0000\n" -"Last-Translator: Maite Guix \n" +"PO-Revision-Date: 2024-07-03 19:09+0000\n" +"Last-Translator: Quentin PAGÈS \n" +"Language-Team: Catalan \n" "Language: ca\n" -"Language-Team: Catalan \n" -"Plural-Forms: nplurals=2; plural=n != 1\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=utf-8\n" "Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=n != 1;\n" +"X-Generator: Weblate 5.7-dev\n" "Generated-By: Babel 2.9.0\n" #, python-format @@ -222,7 +222,7 @@ msgid "{start_object}, {next_object}" msgstr "{start_object}, {next_object}" msgid "No Currency" -msgstr "Sense moneda" +msgstr "Cap moneda" #. Form error with only one error msgid "{prefix}: {error}" @@ -1082,4 +1082,3 @@ msgstr "Període" #~ msgstr "" #~ "Pots compartir directament l'enllaç següent" #~ " a través del teu mitjà preferit" - diff --git a/ihatemoney/translations/fa/LC_MESSAGES/messages.po b/ihatemoney/translations/fa/LC_MESSAGES/messages.po index c03c33ad..5cc32d02 100644 --- a/ihatemoney/translations/fa/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/fa/LC_MESSAGES/messages.po @@ -1,18 +1,18 @@ - msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2023-07-29 14:24+0200\n" -"PO-Revision-Date: 2023-03-19 21:40+0000\n" -"Last-Translator: Sai Mohammad-Hossein Emami \n" +"PO-Revision-Date: 2024-05-23 03:01+0000\n" +"Last-Translator: Yamin Siahmargooei \n" +"Language-Team: Persian \n" "Language: fa\n" -"Language-Team: Persian \n" -"Plural-Forms: nplurals=1; plural=0\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=utf-8\n" "Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=1; plural=0;\n" +"X-Generator: Weblate 5.6-dev\n" "Generated-By: Babel 2.9.0\n" #, python-format @@ -125,16 +125,16 @@ msgid "Reset password" msgstr "بازنشانی گذرواژه" msgid "When?" -msgstr "" +msgstr "چه زمانی؟" msgid "What?" msgstr "چی؟" msgid "Who paid?" -msgstr "" +msgstr "چه کسی پرداخت کرد؟" msgid "How much?" -msgstr "" +msgstr "چقدر؟" msgid "Currency" msgstr "واحد پولی" @@ -180,14 +180,14 @@ msgid "People to notify" msgstr "افرادی که براشون نوتیفیکیشن ارسال میشه" msgid "Send the invitations" -msgstr "" +msgstr "ارسال دعوت نامه ها" #, python-format msgid "The email %(email)s is not valid" msgstr "ایمیل %(email)s نامعتبره" msgid "Logout" -msgstr "" +msgstr "خروج" msgid "Please check the email configuration of the server." msgstr "" @@ -1092,4 +1092,3 @@ msgstr "" #~ "them an email with the invitation " #~ "link." #~ msgstr "" - diff --git a/ihatemoney/translations/hu/LC_MESSAGES/messages.po b/ihatemoney/translations/hu/LC_MESSAGES/messages.po index 12c8072f..c02d34e5 100644 --- a/ihatemoney/translations/hu/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/hu/LC_MESSAGES/messages.po @@ -1,18 +1,18 @@ - msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2023-07-29 14:24+0200\n" -"PO-Revision-Date: 2023-04-19 11:51+0000\n" -"Last-Translator: Gergely Kocsis \n" +"PO-Revision-Date: 2024-07-08 15:09+0000\n" +"Last-Translator: NtWriteCode \n" +"Language-Team: Hungarian \n" "Language: hu\n" -"Language-Team: Hungarian \n" -"Plural-Forms: nplurals=2; plural=n != 1\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=utf-8\n" "Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=n != 1;\n" +"X-Generator: Weblate 5.7-dev\n" "Generated-By: Babel 2.9.0\n" #, python-format @@ -29,12 +29,11 @@ msgstr "" msgid "Project name" msgstr "A projekt neve" -#, fuzzy msgid "Current private code" -msgstr "Új titkos kód" +msgstr "Jelenlegi titkos kód" msgid "Enter existing private code to edit project" -msgstr "" +msgstr "Adj meg egy meglévő titkos kódot a projekt szerkesztéséhez" msgid "New private code" msgstr "Új titkos kód" @@ -43,10 +42,10 @@ msgid "Enter a new code if you want to change it" msgstr "Adj meg egy új kódot, ha meg akarod változtatni" msgid "Email" -msgstr "Email" +msgstr "E-mail" msgid "Enable project history" -msgstr "Projekt történet bekapcsolása" +msgstr "Projekt előzmények bekapcsolása" msgid "Use IP tracking for project history" msgstr "IP nyomkövetés használata a projekt előzményekhez" @@ -73,7 +72,7 @@ msgstr "" "pénznemet is tartalmaz." msgid "Compatible with Cospend" -msgstr "" +msgstr "Cospend-el kompatibilis" msgid "Project identifier" msgstr "Projekt azonosító" @@ -89,24 +88,23 @@ msgid "" "A project with this identifier (\"%(project)s\") already exists. Please " "choose a new identifier" msgstr "" -"Már létezik egy projekt ezzel az azonosítóval (\"%(project)s\"). Kérjük, " -"válasszon más azonosítót" +"Már létezik egy projekt ezzel az azonosítóval (\"%(project)s\"). Kérlek " +"válassz másik azonosítót" msgid "Which is a real currency: Euro or Petro dollar?" -msgstr "Melyik valódi pénznem, az euró vagy a petrodollár?" +msgstr "Melyik valódi pénznem, az Euró vagy a Petrodollár?" msgid "euro" msgstr "euró" msgid "Please, validate the captcha to proceed." -msgstr "Kérlek validáld a captcha-t a folytatáshoz." +msgstr "Kérjük, ellenőrizze a captcha-t a folytatáshoz." msgid "Enter private code to confirm deletion" msgstr "Add meg a titkos kódot a törlés megerősítéséhez" -#, fuzzy msgid "Get in" -msgstr "Szállj be" +msgstr "Belépés" msgid "Admin password" msgstr "Adminisztrátori jelszó" @@ -130,16 +128,16 @@ msgid "Reset password" msgstr "Jelszó visszaállítása" msgid "When?" -msgstr "" +msgstr "Mikor?" msgid "What?" msgstr "Mi?" msgid "Who paid?" -msgstr "" +msgstr "Ki fizetett?" msgid "How much?" -msgstr "" +msgstr "Mennyit?" msgid "Currency" msgstr "Pénznem" @@ -161,16 +159,16 @@ msgstr "Mentés és új hozzáadása" #, python-format msgid "Project default: %(currency)s" -msgstr "Projekt alapértelmezés: %(currency)s" +msgstr "Projekt alapértelmezett: %(currency)s" msgid "Name" msgstr "Név" msgid "Weights should be positive" -msgstr "A súlyoknak pozitív értékűnek kell lenni" +msgstr "A súlyozásnak pozitívnak kell lennie" msgid "Weight" -msgstr "Súly" +msgstr "Súlyozás" msgid "Add" msgstr "Hozzáadás" @@ -185,23 +183,25 @@ msgid "People to notify" msgstr "Értesítendő személyek" msgid "Send the invitations" -msgstr "" +msgstr "Meghívók küldése" #, python-format msgid "The email %(email)s is not valid" msgstr "Érvénytelen e-mail cím: %(email)s" msgid "Logout" -msgstr "" +msgstr "Kijelentkezés" msgid "Please check the email configuration of the server." -msgstr "" +msgstr "Kérjem, ellenőrizd a szerver e-mail konfigurációját." #, python-format msgid "" "Please check the email configuration of the server or contact the " "administrator: %(admin_email)s" msgstr "" +"Kérem, ellenőrizd a szerver e-mail konfigurációját, vagy lépj kapcsolatba a " +"rendszergazdával: %(admin_email)s" #. List with two items only msgid "{dual_object_0} and {dual_object_1}" @@ -230,13 +230,13 @@ msgstr "{prefix}: {error}" msgid "{prefix}:
{errors}" msgstr "{prefix}:
{errors}" -#, fuzzy msgid "Too many failed login attempts." -msgstr "Túl sok sikertelen bejelentkezési kísérlet, kérlek, próbáld újra később." +msgstr "Túl sok sikertelen bejelentkezési kísérlet." #, python-format msgid "This admin password is not the right one. Only %(num)d attempts left." -msgstr "Az admin jelszó érvénytelen. Csak %(num)d próbálkozásod maradt." +msgstr "" +"Az adminisztrátori jelszó érvénytelen. Már csak %(num)d próbálkozásod maradt." msgid "Provided token is invalid" msgstr "A megadott token érvénytelen" @@ -258,6 +258,8 @@ msgid "" "Sorry, there was an error while sending you an email with password reset " "instructions." msgstr "" +"Sajnáljuk, hiba történt a jelszó-visszaállítási utasításokat tartalmazó e-" +"mail elküldésekor." msgid "No token provided" msgstr "Nincs token megadva" @@ -269,22 +271,24 @@ msgid "Unknown project" msgstr "Ismeretlen projekt" msgid "Password successfully reset." -msgstr "Jelszó sikeresen visszaállítva." +msgstr "Jelszó sikeresen helyreállítva." msgid "Project settings have been changed successfully." -msgstr "" +msgstr "A projekt beállításai sikeresen megváltoztak." msgid "Unable to parse CSV" -msgstr "" +msgstr "Nem sikerült értelmezni a CSV fájlt" #, python-format msgid "Missing attribute: %(attribute)s" -msgstr "" +msgstr "Hiányzó tulajdonság: %(attribute)s" msgid "" "Cannot add bills in multiple currencies to a project without default " "currency" msgstr "" +"Nem lehet hozzáadni több pénznemet egy projekthez alapértelmezett pénznem " +"nélkül" msgid "Project successfully uploaded" msgstr "Projekt sikeresen feltöltve" @@ -296,7 +300,7 @@ msgid "Error deleting project" msgstr "Hiba történt a projekt törlésekor" msgid "Unable to logout" -msgstr "" +msgstr "Kijelentkezés sikertelen" #, python-format msgid "You have been invited to share your expenses for %(project)s" @@ -306,7 +310,7 @@ msgid "Your invitations have been sent" msgstr "A meghívóid sikeresen kiküldve" msgid "Sorry, there was an error while trying to send the invitation emails." -msgstr "" +msgstr "Elnézést, hiba történt a meghívó e-mailek elküldése közben." #, python-format msgid "%(member)s has been added" @@ -317,221 +321,227 @@ msgstr "Hiba történt a résztvevő aktiválása közben" #, python-format msgid "%(name)s is part of this project again" -msgstr "" +msgstr "%(name)s már a projekt tagja" msgid "Error removing participant" -msgstr "" +msgstr "Hiba történt a résztvevő eltávolításakor" #, python-format msgid "" "Participant '%(name)s' has been deactivated. It will still appear in the " "list until its balance reach zero." msgstr "" +"%(name)s deaktiválva van. A listán látható lesz, amíg az egyenlege nulla nem " +"lesz." #, python-format msgid "Participant '%(name)s' has been removed" -msgstr "" +msgstr "%(name)s eltávolítva" #, python-format msgid "Participant '%(name)s' has been modified" -msgstr "" +msgstr "%(name)s módosítva" msgid "The bill has been added" -msgstr "" +msgstr "Számla hozzáadva" msgid "Error deleting bill" -msgstr "" +msgstr "Hiba történt a számla törlése közben" msgid "The bill has been deleted" -msgstr "" +msgstr "Számla törölve" msgid "The bill has been modified" -msgstr "" +msgstr "Számla módosítva" #, python-format msgid "%(lang)s is not a supported language" -msgstr "" +msgstr "%(lang)s nem egy támogatott nyelv" msgid "Error deleting project history" -msgstr "" +msgstr "Hiba lépett fel az előzmények törlése közben" msgid "Deleted project history." -msgstr "" +msgstr "Előzmények törölve." msgid "Error deleting recorded IP addresses" -msgstr "" +msgstr "Hiba lépett fel az IP cím törlésekor" msgid "Deleted recorded IP addresses in project history." -msgstr "" +msgstr "IP címek törölve az előzményekből." msgid "Sorry, we were unable to find the page you've asked for." -msgstr "" +msgstr "Sajnáljuk, de a keresett oldalt nem találjuk." msgid "The best thing to do is probably to get back to the main page." -msgstr "" +msgstr "A legjobb döntés talán, ha visszalépsz a főoldalra." msgid "Back to the list" -msgstr "" +msgstr "Vissza a listához" msgid "Administration tasks are currently disabled." -msgstr "" +msgstr "Az adminisztrációs feladatok jelenleg le vannak tiltva." msgid "Authentication" -msgstr "" +msgstr "Hitelesítés" msgid "The project you are trying to access do not exist, do you want to" -msgstr "" +msgstr "A projekt, amelyhez hozzáférni próbálsz, nem létezik. Szeretnéd" msgid "create it" -msgstr "" +msgstr "létrehozni" msgid "?" -msgstr "" +msgstr "?" msgid "Create a new project" -msgstr "" +msgstr "Új projekt létrehozása" msgid "Project" -msgstr "" +msgstr "Projekt" msgid "Number of participants" -msgstr "" +msgstr "Résztvevők száma" msgid "Number of bills" -msgstr "" +msgstr "Számlák száma" msgid "Newest bill" -msgstr "" +msgstr "Legújabb számla" msgid "Oldest bill" -msgstr "" +msgstr "Legrégebbi számla" msgid "Actions" -msgstr "" +msgstr "Tevékenységek" msgid "edit" -msgstr "" +msgstr "szerkesztés" msgid "Delete project" -msgstr "" +msgstr "Projekt törlése" msgid "show" -msgstr "" +msgstr "megjelenít" msgid "The Dashboard is currently deactivated." -msgstr "" +msgstr "Az irányítópult jelenleg ki van kapcsolva." msgid "Download Mobile Application" -msgstr "" +msgstr "Mobil alkalmazás letöltése" msgid "Get it on" -msgstr "" +msgstr "Szerezd meg" msgid "Edit project" -msgstr "" +msgstr "Projekt szerkesztése" -#, fuzzy msgid "Import project" -msgstr "Projekt létrehozása" +msgstr "Projekt importálása" msgid "Download project's data" -msgstr "" +msgstr "Projekt adatainak letöltése" msgid "Bill items" -msgstr "" +msgstr "Számla elemei" msgid "Download the list of bills with owner, amount, reason,... " msgstr "" +"Töltsd le a számlák listáját ami tartalmazza a tulajdonost, összeget, " +"okokat, ... " msgid "Settle plans" -msgstr "" +msgstr "Kiegyenlítési tervek" msgid "Download the list of transactions needed to settle the current bills." msgstr "" +"Töltsd le az aktuális számlák kiegyenlítéséhez szükséges tranzakciók " +"listáját." msgid "Can't remember the password?" -msgstr "" +msgstr "Nem emlékszik a jelszavára?" msgid "Cancel" -msgstr "" +msgstr "Mégsem" msgid "Privacy Settings" -msgstr "" +msgstr "Adatvédelmi beállítások" msgid "Save changes" -msgstr "" +msgstr "Változások mentése" msgid "This will remove all bills and participants in this project!" -msgstr "" +msgstr "Ez eltávolítja az összes számlát és résztvevőt ebből a projektből!" -#, fuzzy msgid "Import previously exported project" msgstr "Korábban exportált JSON fájl importálása" msgid "Choose file" -msgstr "" +msgstr "Fájl kiválasztása" msgid "Edit this bill" -msgstr "" +msgstr "Számla szerkesztése" msgid "Add a bill" -msgstr "" +msgstr "Számla hozzáadása" msgid "Simple operations are allowed, e.g. (18+36.2)/3" -msgstr "" +msgstr "Egyszerű matematikai műveletek megengedettek, pl. (18+36.2)/3" msgid "Everyone" -msgstr "" +msgstr "Mindenki" msgid "No one" -msgstr "" +msgstr "Senki" msgid "More options" -msgstr "" +msgstr "További lehetőségek" msgid "Add participant" -msgstr "" +msgstr "Résztvevő hozzáadása" msgid "Edit this participant" -msgstr "" +msgstr "Résztvevő szerkesztése" msgid "john.doe@example.com, mary.moe@site.com" -msgstr "" +msgstr "kiss.pista@pelda.hu, gyongy.virag@weboldalam.hu" msgid "Download" -msgstr "" +msgstr "Letöltés" msgid "Disabled Project History" -msgstr "" +msgstr "Projekt előzmények kikapcsolva" msgid "Disabled Project History & IP Address Recording" -msgstr "" +msgstr "Projekt előzmények és IP cím rögzítés kikapcsolva" msgid "Enabled Project History" -msgstr "" +msgstr "Projekt előzmények bekapcsolva" msgid "Disabled IP Address Recording" -msgstr "" +msgstr "IP cím rögzítés kikapcsolva" msgid "Enabled Project History & IP Address Recording" -msgstr "" +msgstr "Projekt előzmények és IP cím rögzítés bekapcsolva" msgid "Enabled IP Address Recording" -msgstr "" +msgstr "IP cím rögzítés bekapcsolva" msgid "History Settings Changed" -msgstr "" +msgstr "Előzménybeállítások megváltoztatva" #, python-format msgid "Bill %(name)s: %(property_name)s changed from %(before)s to %(after)s" msgstr "" +"Számla %(name)s: %(property_name)s megváltozott erről: %(before)s erre: " +"%(after)s" #, python-format msgid "Bill %(name)s: %(property_name)s changed to %(after)s" -msgstr "" +msgstr "Számla %(name)s: %(property_name)s megváltoztatva erre: %(after)s" msgid "Confirm Remove IP Adresses" -msgstr "" +msgstr "Erősítsd meg az IP-címek eltávolítását" msgid "" "Are you sure you want to delete all recorded IP addresses from this " @@ -539,340 +549,358 @@ msgid "" " The rest of the project history will be unaffected. This " "action cannot be undone." msgstr "" +"Biztos, hogy törölni szeretnéd az összes rögzített IP-címet ebből a " +"projektből?\n" +" A projekt többi előzménye nem változik. Ez a művelet nem " +"vonható vissza." msgid "Confirm deletion" -msgstr "" +msgstr "Törlés megerősítése" msgid "Close" -msgstr "" +msgstr "Bezár" msgid "Delete Confirmation" -msgstr "" +msgstr "Megerősítés törlése" msgid "" "Are you sure you want to erase all history for this project? This action " "cannot be undone." msgstr "" +"Biztos, hogy törölni akarod a projekt minden előzményét? Ezt a műveletet nem " +"lehet visszacsinálni." #, python-format msgid "Bill %(name)s: added %(owers_list_str)s to owers list" -msgstr "" +msgstr "Számla %(name)s: hozzáadva %(owers_list_str)s a tartozók listájára" #, python-format msgid "Bill %(name)s: removed %(owers_list_str)s from owers list" -msgstr "" +msgstr "Számla %(name)s: törölve %(owers_list_str)s a tartozók listájáról" msgid "This project has history disabled. New actions won't appear below." msgstr "" +"Ennek a projektnek az előzményei le vannak tiltva. Az új műveletek nem " +"jelennek meg." msgid "You can enable history on the settings page." -msgstr "" +msgstr "Az előzményeket a beállítások oldalon engedélyezheted." msgid "" "The table below reflects actions recorded prior to disabling project " "history." msgstr "" +"Az alábbi táblázat a projekt előzményeinek letiltása előtt rögzített " +"műveleteket tükrözi." msgid "You can clear the project history to remove them." -msgstr "" +msgstr "Törölheted a projekt előzményeit, hogy törölje azokat." msgid "" "Some entries below contain IP addresses, even though this project has IP " "recording disabled. " msgstr "" +"Néhány alábbi bejegyzés IP-címeket tartalmaz, annak ellenére, hogy a projekt " +"IP-felvétele le van tiltva. " msgid "Delete stored IP addresses" -msgstr "" +msgstr "Tárolt IP-címek törlése" msgid "No IP Addresses to erase" -msgstr "" +msgstr "Nincs törlendő IP-cím" msgid "Delete Stored IP Addresses" -msgstr "" +msgstr "Tárolt IP-Címek Törlése" msgid "No history to erase" -msgstr "" +msgstr "Nincs kitörölhető előzmény" msgid "Clear Project History" -msgstr "" +msgstr "Projekt előzmények törlése" msgid "Time" -msgstr "" +msgstr "Idő" msgid "Event" -msgstr "" +msgstr "Esemény" msgid "IP address recording can be enabled on the settings page" -msgstr "" +msgstr "Az IP-címek rögzítése a beállítások oldalon engedélyezhető" msgid "IP address recording can be disabled on the settings page" -msgstr "" +msgstr "Az IP-címek rögzítése letiltható a beállítások oldalon" msgid "From IP" -msgstr "" +msgstr "IP-ről" #, python-format msgid "Project %(name)s added" -msgstr "" +msgstr "Projekt %(name)s hozzáadva" #, python-format msgid "Bill %(name)s added" -msgstr "" +msgstr "Számla %(name)s hozzáadva" #, python-format msgid "Participant %(name)s added" -msgstr "" +msgstr "Résztvevő %(name)s hozzáadva" msgid "Project private code changed" -msgstr "" +msgstr "A projekt titkos kódja megváltozott" #, python-format msgid "Project renamed to %(new_project_name)s" -msgstr "" +msgstr "Projekt átnevezve: %(new_project_name)s" #, python-format msgid "Project contact email changed to %(new_email)s" -msgstr "" +msgstr "A projekt kapcsolattartójának e-mail címe megváltozott: %(new_email)s" msgid "Project settings modified" -msgstr "" +msgstr "Projekt beállításai módosítva" #, python-format msgid "Participant %(name)s deactivated" -msgstr "" +msgstr "Résztvevő %(name)s deaktiválva" #, python-format msgid "Participant %(name)s reactivated" -msgstr "" +msgstr "Résztvevő %(name)s újraaktiválva" #, python-format msgid "Participant %(name)s renamed to %(new_name)s" -msgstr "" +msgstr "Résztvevő %(name)s átnevezve: %(new_name)s" #, python-format msgid "Bill %(name)s renamed to %(new_description)s" -msgstr "" +msgstr "Számla %(name)s átnevezve: %(new_description)s" #, python-format msgid "Participant %(name)s: weight changed from %(old_weight)s to %(new_weight)s" msgstr "" +"Résztvevő %(name)s: súlyozása módosítva erről: %(old_weight)s erre: " +"%(new_weight)s" msgid "Payer" msgstr "Fizető" msgid "Amount" -msgstr "" +msgstr "Összeg" msgid "Date" msgstr "Dátum" #, python-format msgid "Amount in %(currency)s" -msgstr "" +msgstr "Összeg %(currency)s-ban/ben" #, python-format msgid "Bill %(name)s modified" -msgstr "" +msgstr "Számla %(name)s módosítva" #, python-format msgid "Participant %(name)s modified" -msgstr "" +msgstr "Résztvevő %(name)s módosítva" #, python-format msgid "Bill %(name)s removed" -msgstr "" +msgstr "Számla %(name)s törölve" #, python-format msgid "Participant %(name)s removed" -msgstr "" +msgstr "Résztvevő %(name)s törölve" #, python-format msgid "Project %(name)s changed in an unknown way" -msgstr "" +msgstr "Projekt %(name)s ismeretlen módon megváltozott" #, python-format msgid "Bill %(name)s changed in an unknown way" -msgstr "" +msgstr "A számla %(name)s ismeretlen módon megváltozott" #, python-format msgid "Participant %(name)s changed in an unknown way" -msgstr "" +msgstr "A résztvevő %(name)s ismeretlen módon megváltozott" msgid "Nothing to list" -msgstr "" +msgstr "Nincs listázandó elem" msgid "Someone probably cleared the project history." -msgstr "" +msgstr "Valaki valószínűleg törölte a projekt előzményeit." msgid "Manage your shared
expenses, easily" -msgstr "" +msgstr "Kezeld a megosztott
költségeid, egyszerűen" msgid "Try out the demo" -msgstr "" +msgstr "Próbálja ki a demót" msgid "You're sharing a house?" -msgstr "" +msgstr "Egy háztartásban laktok?" msgid "Going on holidays with friends?" -msgstr "" +msgstr "Nyaralni mész a barátaiddal?" msgid "Simply sharing money with others?" -msgstr "" +msgstr "Egyszerűen megosztanád a költségeket másokkal?" msgid "We can help!" -msgstr "" +msgstr "Segíthetünk!" msgid "Log in to an existing project" -msgstr "" +msgstr "Bejelentkezés egy meglévő projektbe" msgid "Log in" -msgstr "" +msgstr "Bejelentkezés" msgid "can't remember your password?" -msgstr "" +msgstr "Elfelejtette a jelszavát?" msgid "Create" -msgstr "" +msgstr "Létrehozás" msgid "" "Don\\'t reuse a personal password. Choose a private code and send it to " "your friends" msgstr "" +"Ne használd a személyes jelszavaid. Válassz egy titkos kódot, és küldd el a " +"barátaidnak" msgid "Account manager" -msgstr "" +msgstr "Számlakezelő" msgid "Bills" -msgstr "" +msgstr "Számlák" msgid "Settle" -msgstr "" +msgstr "Kiegyenlítés" msgid "Statistics" -msgstr "" +msgstr "Statisztikák" msgid "Languages" -msgstr "" +msgstr "Nyelvek" msgid "Projects" -msgstr "" +msgstr "Projektek" msgid "Start a new project" -msgstr "" +msgstr "Új projekt készítése" msgid "History" -msgstr "" +msgstr "Előzmények" msgid "Settings" -msgstr "" +msgstr "Beállítások" msgid "RSS Feed" -msgstr "" +msgstr "RSS hírcsatorna" msgid "Other projects :" -msgstr "" +msgstr "Egyéb projektek:" msgid "switch to" -msgstr "" +msgstr "Projektváltás ide" msgid "Dashboard" -msgstr "" +msgstr "Vezérlőpult" #, python-format msgid "Please retry after %(date)s." -msgstr "" +msgstr "Kérem próbálja újra %(date)s után." msgid "Code" -msgstr "" +msgstr "Kód" msgid "Mobile Application" -msgstr "" +msgstr "Mobil alkalmazás" msgid "Documentation" -msgstr "" +msgstr "Dokumentáció" msgid "Administation Dashboard" -msgstr "" +msgstr "Adminisztrátori vezérlőpult" msgid "Legal information" -msgstr "" +msgstr "Jogi információk" msgid "\"I hate money\" is free software" -msgstr "" +msgstr "Az \"I hate money\" egy ingyenes szoftver" msgid "you can contribute and improve it!" -msgstr "" +msgstr "hozzájárulhatsz és javíthatod!" #, python-format msgid "%(amount)s each" -msgstr "" +msgstr "%(amount)s fejenként" msgid "you sure?" -msgstr "" +msgstr "biztos vagy benne?" msgid "Invite people" -msgstr "" +msgstr "Résztvevők meghívása" msgid "Newer bills" -msgstr "" +msgstr "Újabb számlák" msgid "Older bills" -msgstr "" +msgstr "Régebbi számlák" msgid "You should start by adding participants" -msgstr "" +msgstr "Résztvevők hozzáadásával érdemes kezdeni" msgid "Add a new bill" -msgstr "" +msgstr "Újabb számla hozzáadása" msgid "For what?" -msgstr "" +msgstr "Mire?" #, python-format msgid "Added on %(date)s" -msgstr "" +msgstr "Hozzáadva %(date)s" #, python-format msgid "Everyone but %(excluded)s" -msgstr "" +msgstr "Mindenki, kivéve %(excluded)s" msgid "delete" -msgstr "" +msgstr "törlés" msgid "No bills" -msgstr "" +msgstr "Nincsenek számlák" msgid "Nothing to list yet." -msgstr "" +msgstr "Még nincs mit listázni." msgid "Add your first bill" -msgstr "" +msgstr "Add hozzá az első számládat" msgid "Add the first participant" -msgstr "" +msgstr "Add hozzá az első résztvevőt" msgid "Password reminder" -msgstr "" +msgstr "Jelszó emlékeztető" msgid "" "A link to reset your password has been sent to you, please check your " "emails." msgstr "" +"A jelszó visszaállításához szükséges linket elküldtük Önnek, kérjük, " +"ellenőrizze e-mailjeit." msgid "Return to home page" -msgstr "" +msgstr "Vissza a főoldalra" msgid "Your projects" -msgstr "" +msgstr "Projektjeid" msgid "Reset your password" -msgstr "" +msgstr "Jelszavad visszaállítása" msgid "Invite people to join this project" -msgstr "" +msgstr "Hívj meg résztvevőket, hogy csatlakozzanak a projekthez" msgid "Share an invitation link" -msgstr "" +msgstr "Meghívó link megosztása" msgid "" "The easiest way to invite people is to give them the following invitation" @@ -880,24 +908,32 @@ msgid "" " add/edit/delete bills. However, they will not have access to important " "settings such as changing the private code or deleting the whole project." msgstr "" +"A legegyszerűbben úgy hívhatsz meg embereket, ha megadod nekik az alábbi " +"meghívó linket.
Ezek a személyek hozzáférhetnek a projekthez, " +"kezelhetik a résztvevőket, hozzáadhatnak/szerkeszthetnek/törölhetnek " +"számlákat. Azonban nem férnek hozzá a fontos beállításokhoz, mint például a " +"titkos kód megváltoztatása vagy az egész projekt törlése." msgid "Scan QR code" -msgstr "" +msgstr "QR-kód beolvasása" msgid "Use a mobile device with a compatible app." -msgstr "" +msgstr "Használj mobilt egy kompatibilis alkalmazással." msgid "Send via Emails" -msgstr "" +msgstr "Küldés E-mailben" msgid "" "Specify a list of email adresses (separated by comma) of people you want " "to notify about the creation of this project. We will send them an email " "with the invitation link." msgstr "" +"Add meg azon személyek e-mail címeinek listáját (vesszővel elválasztva), " +"akiket értesíteni szeretnél a projekt létrehozásáról. Nekik egy e-mailt " +"fogunk küldeni a meghívó linkkel." msgid "Share Identifier & code" -msgstr "" +msgstr "Azonosító & Kód megosztása" msgid "" "You can share the project identifier and the private code by any " @@ -905,46 +941,49 @@ msgid "" "to the full project, including changing settings such as the private code" " or project email address, or even deleting the whole project." msgstr "" +"A projekt azonosítóját és a titkos kódot bármilyen kommunikációs eszközzel " +"megoszthatod.
Aki a titkos kóddal rendelkezik, hozzáférhet a teljes " +"projekthez, beleértve a beállítások, például a titkos kód vagy a projekt e-" +"mail címének megváltoztatását, vagy akár a teljes projekt törlését is." msgid "Identifier:" -msgstr "" +msgstr "Azonosító:" -#, fuzzy msgid "Private code:" -msgstr "Titkos kód" +msgstr "Titkos kód:" msgid "the private code was defined when you created the project" -msgstr "" +msgstr "a titkos kód a projekt létrehozásakor készült el" msgid "Who pays?" -msgstr "" +msgstr "Ki fizet?" msgid "To whom?" -msgstr "" +msgstr "Kinek?" msgid "Who?" -msgstr "" +msgstr "Ki?" msgid "Balance" -msgstr "" +msgstr "Egyenleg" msgid "deactivate" -msgstr "" +msgstr "deaktivál" msgid "reactivate" -msgstr "" +msgstr "újraaktivál" msgid "Paid" -msgstr "" +msgstr "Fizetett" msgid "Spent" -msgstr "" +msgstr "Költött" msgid "Expenses by Month" -msgstr "" +msgstr "Költségek havonta" msgid "Period" -msgstr "" +msgstr "Periódus" #~ msgid "Import" #~ msgstr "" @@ -1053,4 +1092,3 @@ msgstr "" #~ "them an email with the invitation " #~ "link." #~ msgstr "" - diff --git a/ihatemoney/translations/ja/LC_MESSAGES/messages.po b/ihatemoney/translations/ja/LC_MESSAGES/messages.po index 0069d7b3..1c4165a0 100644 --- a/ihatemoney/translations/ja/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/ja/LC_MESSAGES/messages.po @@ -1,18 +1,18 @@ - msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2023-07-29 14:24+0200\n" -"PO-Revision-Date: 2020-11-11 16:28+0000\n" -"Last-Translator: Jwen921 \n" +"PO-Revision-Date: 2024-06-24 15:09+0000\n" +"Last-Translator: Khang Tran \n" +"Language-Team: Japanese \n" "Language: ja\n" -"Language-Team: Japanese \n" -"Plural-Forms: nplurals=1; plural=0\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=utf-8\n" "Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=1; plural=0;\n" +"X-Generator: Weblate 5.6-rc\n" "Generated-By: Babel 2.9.0\n" #, python-format @@ -27,19 +27,17 @@ msgstr "無効な入力です。数字と「+ - * / 」の演算子しか入力 msgid "Project name" msgstr "プロジェクトの名前" -#, fuzzy msgid "Current private code" -msgstr "暗証コード" +msgstr "現在の暗証コード" msgid "Enter existing private code to edit project" -msgstr "" +msgstr "プロジェクトを編集するために、暗証コードを入力してください" -#, fuzzy msgid "New private code" -msgstr "暗証コード" +msgstr "新暗証コード" msgid "Enter a new code if you want to change it" -msgstr "" +msgstr "変更するために、新しい暗証コードを入力してください" msgid "Email" msgstr "メールアドレス" @@ -54,15 +52,13 @@ msgid "Default Currency" msgstr "初期設定にする通貨" msgid "Setting a default currency enables currency conversion between bills" -msgstr "" +msgstr "明細通貨変換のため、デフォルトの通貨を設定してください" -#, fuzzy msgid "Unknown error" -msgstr "未知のプロジェクト" +msgstr "不明エラー" -#, fuzzy msgid "Invalid private code." -msgstr "暗証コード" +msgstr "無効な暗証コード。" msgid "" "This project cannot be set to 'no currency' because it contains bills in " @@ -179,7 +175,7 @@ msgid "This project already have this participant" msgstr "プロジェクトはすでにこのメンバーを含めています" msgid "People to notify" -msgstr "" +msgstr "通知したい人" msgid "Send the invitations" msgstr "招待状を送る" @@ -194,11 +190,12 @@ msgstr "ログアウト" msgid "Please check the email configuration of the server." msgstr "" -#, fuzzy, python-format +#, python-format msgid "" "Please check the email configuration of the server or contact the " "administrator: %(admin_email)s" -msgstr "申し訳ございませんが、招待メールを送ったとき、エラーが発生しました。メールアドレスを再度チェックするかまたは管理者に連絡ください。" +msgstr "申し訳ございませんが、エラーが発生しました。メールアドレスを再度チェックする" +"か、または管理者( %(admin_email)s)に連絡ください" #. List with two items only msgid "{dual_object_0} and {dual_object_1}" @@ -271,7 +268,7 @@ msgid "Project settings have been changed successfully." msgstr "" msgid "Unable to parse CSV" -msgstr "" +msgstr "CSVを読み込むことができません" #, python-format msgid "Missing attribute: %(attribute)s" @@ -292,7 +289,7 @@ msgid "Error deleting project" msgstr "" msgid "Unable to logout" -msgstr "" +msgstr "ログアウトできません" #, python-format msgid "You have been invited to share your expenses for %(project)s" @@ -353,9 +350,8 @@ msgstr "" msgid "Error deleting project history" msgstr "プロジェクトの歴史を有効にする" -#, fuzzy msgid "Deleted project history." -msgstr "プロジェクトの歴史を有効にする" +msgstr "プロジェクトの歴史を削除しました。" #, fuzzy msgid "Error deleting recorded IP addresses" @@ -574,9 +570,8 @@ msgstr "" msgid "This project has history disabled. New actions won't appear below." msgstr "" -#, fuzzy msgid "You can enable history on the settings page." -msgstr "設定ページでIPアドレス記録を編集可能にすることができる" +msgstr "設定ページでIPアドレス記録を編集可能にすることができる。" msgid "" "The table below reflects actions recorded prior to disabling project " @@ -622,13 +617,13 @@ msgstr "設定ページでIPアドレス記録を編集不可にすることが msgid "From IP" msgstr "IPから" -#, fuzzy, python-format +#, python-format msgid "Project %(name)s added" -msgstr "プロジェクトの名前" +msgstr "プロジェクト%(name)sが作成されました" -#, fuzzy, python-format +#, python-format msgid "Bill %(name)s added" -msgstr "明細が追加されました" +msgstr "%(name)s明細が追加されました" #, python-format msgid "Participant %(name)s added" @@ -641,9 +636,9 @@ msgstr "プロジェクトの私用コードが変更された" msgid "Project renamed to %(new_project_name)s" msgstr "プロジェクト名は%(new_project_name)s" -#, fuzzy, python-format +#, python-format msgid "Project contact email changed to %(new_email)s" -msgstr "プロジェクトの連絡メールが…に変更された" +msgstr "プロジェクトの連絡メールが%(new_email)sに変更されました" msgid "Project settings modified" msgstr "プロジェクトの設定が修正された" @@ -681,9 +676,9 @@ msgstr "日付" msgid "Amount in %(currency)s" msgstr "%(currency)sでの金額" -#, fuzzy, python-format +#, python-format msgid "Bill %(name)s modified" -msgstr "明細が変更されました" +msgstr "%(name)s明細が変更されました" #, python-format msgid "Participant %(name)s modified" @@ -697,17 +692,17 @@ msgstr "ユーザー%(name)sが既に取り除かれました" msgid "Participant %(name)s removed" msgstr "ユーザー%(name)sが既に取り除かれました" -#, fuzzy, python-format +#, python-format msgid "Project %(name)s changed in an unknown way" -msgstr "未知の方法で変更された" +msgstr "プロジェクト%(name)sが不明な方法で変更されました" -#, fuzzy, python-format +#, python-format msgid "Bill %(name)s changed in an unknown way" -msgstr "未知の方法で変更された" +msgstr "明細%(name)sが不明な方法で変更されました" -#, fuzzy, python-format +#, python-format msgid "Participant %(name)s changed in an unknown way" -msgstr "未知の方法で変更された" +msgstr "参加者%(name)sが不明な方法で変更されました" msgid "Nothing to list" msgstr "表示できるものがない" @@ -904,14 +899,12 @@ msgstr "" msgid "Send via Emails" msgstr "メールで送る" -#, fuzzy msgid "" "Specify a list of email adresses (separated by comma) of people you want " "to notify about the creation of this project. We will send them an email " "with the invitation link." -msgstr "" -"…を知らせたいメールアドレスのリストを特定する(カンマ区切り)\n" -"彼らにこの予算管理プロジェクトの作成をメールでお知らせします。" +msgstr "知らせたいメールアドレスのリスト(カンマ区切り)を指定してください。メールで" +"招待リンクを送信します。" msgid "Share Identifier & code" msgstr "名前とコードを共有する" @@ -926,9 +919,8 @@ msgstr "" msgid "Identifier:" msgstr "名前:" -#, fuzzy msgid "Private code:" -msgstr "暗証コード" +msgstr "暗証コード:" msgid "the private code was defined when you created the project" msgstr "" @@ -1109,4 +1101,3 @@ msgstr "期間" #~ msgid "You can directly share the following link via your prefered medium" #~ msgstr "好きの手段で以下のリンクを直接に共有できる" - diff --git a/ihatemoney/translations/oc/LC_MESSAGES/messages.po b/ihatemoney/translations/oc/LC_MESSAGES/messages.po new file mode 100644 index 00000000..56a97262 --- /dev/null +++ b/ihatemoney/translations/oc/LC_MESSAGES/messages.po @@ -0,0 +1,932 @@ +msgid "" +msgstr "" +"Project-Id-Version: PACKAGE VERSION\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2024-06-15 16:06+0200\n" +"PO-Revision-Date: 2024-07-03 19:09+0000\n" +"Last-Translator: Quentin PAGÈS \n" +"Language-Team: Occitan \n" +"Language: oc\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=n > 1;\n" +"X-Generator: Weblate 5.7-dev\n" + +#, python-format +msgid "You have just created '%(project)s' to share your expenses" +msgstr "Venètz de crear « %(project)s » per despartir vòstras despensas" + +msgid "" +"Not a valid amount or expression. Only numbers and + - * / operators are " +"accepted." +msgstr "" +"Quantitat o expression non valida. Sonque los nombre e operator +-*/ son " +"acceptats." + +msgid "Project name" +msgstr "Nom del projècte" + +msgid "Current private code" +msgstr "Còdi d’accès actual" + +msgid "Enter existing private code to edit project" +msgstr "Picatz lo còdi d’accès existissent per editar lo projècte" + +msgid "New private code" +msgstr "Còdi privat novèl" + +msgid "Enter a new code if you want to change it" +msgstr "Picatz lo còdi novèl se lo volètz cambiar" + +msgid "Email" +msgstr "Adreça electronica" + +msgid "Enable project history" +msgstr "Activar l’istoric de projècte" + +msgid "Use IP tracking for project history" +msgstr "Reculhir las adreças IP dins l’istoric de projècte" + +msgid "Default Currency" +msgstr "Moneda predeterminada" + +msgid "Setting a default currency enables currency conversion between bills" +msgstr "" + +msgid "Unknown error" +msgstr "Error desconeguda" + +msgid "Invalid private code." +msgstr "Còdi d’accès invalid." + +msgid "" +"This project cannot be set to 'no currency' because it contains bills in " +"multiple currencies." +msgstr "" + +msgid "Compatible with Cospend" +msgstr "Compatible amb Cospend" + +msgid "Project identifier" +msgstr "Identificant del projècte" + +msgid "Private code" +msgstr "Còdi privat" + +msgid "Create the project" +msgstr "Crear lo projècte" + +#, python-format +msgid "" +"A project with this identifier (\"%(project)s\") already exists. Please " +"choose a new identifier" +msgstr "" + +msgid "Which is a real currency: Euro or Petro dollar?" +msgstr "" + +msgid "euro" +msgstr "èuro" + +msgid "Please, validate the captcha to proceed." +msgstr "Se vos plai, validatz el captcha per contunhar." + +msgid "Enter private code to confirm deletion" +msgstr "Picatz lo còdi d’accès per confirmar la supression" + +msgid "Get in" +msgstr "Dintrar" + +msgid "Admin password" +msgstr "Senhal d’administracion" + +msgid "Send me the code by email" +msgstr "Mandatz-me lo còdi per corrièl" + +msgid "This project does not exists" +msgstr "Aqueste projècte existís pas" + +msgid "Password mismatch" +msgstr "" + +msgid "Password" +msgstr "Senhal" + +msgid "Password confirmation" +msgstr "Confirmacion del senhla" + +msgid "Reset password" +msgstr "Reïnicializar lo senhal" + +msgid "When?" +msgstr "Quand ?" + +msgid "What?" +msgstr "Qué ?" + +msgid "Who paid?" +msgstr "Qual paguèt ?" + +msgid "How much?" +msgstr "Quant ?" + +msgid "Currency" +msgstr "Moneda" + +msgid "External link" +msgstr "Ligam extèrne" + +msgid "A link to an external document, related to this bill" +msgstr "" + +msgid "For whom?" +msgstr "Per qual ?" + +msgid "Submit" +msgstr "Enviar" + +msgid "Submit and add a new one" +msgstr "" + +#, python-format +msgid "Project default: %(currency)s" +msgstr "" + +msgid "Name" +msgstr "Nom" + +msgid "Weights should be positive" +msgstr "" + +msgid "Weight" +msgstr "Pes" + +msgid "Add" +msgstr "Apondre" + +msgid "The participant name is invalid" +msgstr "Lo nom del participant es incorrècte" + +msgid "This project already have this participant" +msgstr "Aqueste projècte a ja aqueste participant" + +msgid "People to notify" +msgstr "Personas de convidar" + +msgid "Send the invitations" +msgstr "Enviar las invitacions" + +#, python-format +msgid "The email %(email)s is not valid" +msgstr "" + +msgid "Logout" +msgstr "Desconnexion" + +msgid "Please check the email configuration of the server." +msgstr "" + +#, python-format +msgid "" +"Please check the email configuration of the server or contact the " +"administrator: %(admin_email)s" +msgstr "" + +#. List with two items only +msgid "{dual_object_0} and {dual_object_1}" +msgstr "" + +#. Last two items of a list with more than 3 items +msgid "{previous_object}, and {end_object}" +msgstr "" + +#. Two items in a middle of a list with more than 5 objects +msgid "{previous_object}, {next_object}" +msgstr "{previous_object}, {next_object}" + +#. First two items of a list with more than 3 items +msgid "{start_object}, {next_object}" +msgstr "{start_object}, {next_object}" + +msgid "No Currency" +msgstr "Cap de moneda" + +#. Form error with only one error +msgid "{prefix}: {error}" +msgstr "{prefix} : {error}" + +#. Form error with a list of errors +msgid "{prefix}:
{errors}" +msgstr "{prefix} :
{errors}" + +msgid "Too many failed login attempts." +msgstr "" + +#, python-format +msgid "This admin password is not the right one. Only %(num)d attempts left." +msgstr "" + +msgid "Provided token is invalid" +msgstr "Aqueste geton es invalid" + +msgid "This private code is not the right one" +msgstr "" + +msgid "A reminder email has just been sent to you" +msgstr "" + +msgid "" +"We tried to send you an reminder email, but there was an error. You can " +"still use the project normally." +msgstr "" + +msgid "" +"Sorry, there was an error while sending you an email with password reset " +"instructions." +msgstr "" + +msgid "No token provided" +msgstr "" + +msgid "Invalid token" +msgstr "Geton invalid" + +msgid "Unknown project" +msgstr "" + +msgid "Password successfully reset." +msgstr "" + +msgid "Project settings have been changed successfully." +msgstr "" + +msgid "Unable to parse CSV" +msgstr "" + +#, python-format +msgid "Missing attribute: %(attribute)s" +msgstr "Atribut mancant : %(attribute)s" + +msgid "" +"Cannot add bills in multiple currencies to a project without default " +"currency" +msgstr "" + +msgid "Project successfully uploaded" +msgstr "" + +msgid "Project successfully deleted" +msgstr "" + +msgid "Error deleting project" +msgstr "" + +msgid "Unable to logout" +msgstr "" + +#, python-format +msgid "You have been invited to share your expenses for %(project)s" +msgstr "" + +msgid "Your invitations have been sent" +msgstr "" + +msgid "Sorry, there was an error while trying to send the invitation emails." +msgstr "" + +#, python-format +msgid "%(member)s has been added" +msgstr "" + +msgid "Error activating participant" +msgstr "" + +#, python-format +msgid "%(name)s is part of this project again" +msgstr "" + +msgid "Error removing participant" +msgstr "" + +#, python-format +msgid "" +"Participant '%(name)s' has been deactivated. It will still appear in the " +"list until its balance reach zero." +msgstr "" + +#, python-format +msgid "Participant '%(name)s' has been removed" +msgstr "" + +#, python-format +msgid "Participant '%(name)s' has been modified" +msgstr "" + +msgid "The bill has been added" +msgstr "" + +msgid "Error deleting bill" +msgstr "" + +msgid "The bill has been deleted" +msgstr "" + +msgid "The bill has been modified" +msgstr "" + +#, python-format +msgid "%(lang)s is not a supported language" +msgstr "" + +msgid "Error deleting project history" +msgstr "" + +msgid "Deleted project history." +msgstr "" + +msgid "Error deleting recorded IP addresses" +msgstr "" + +msgid "Deleted recorded IP addresses in project history." +msgstr "" + +msgid "Sorry, we were unable to find the page you've asked for." +msgstr "" + +msgid "The best thing to do is probably to get back to the main page." +msgstr "" + +msgid "Back to the list" +msgstr "" + +msgid "Administration tasks are currently disabled." +msgstr "" + +msgid "Authentication" +msgstr "" + +msgid "The project you are trying to access do not exist, do you want to" +msgstr "" + +msgid "create it" +msgstr "" + +msgid "?" +msgstr "" + +msgid "Create a new project" +msgstr "" + +msgid "Project" +msgstr "Projècte" + +msgid "Number of participants" +msgstr "" + +msgid "Number of bills" +msgstr "" + +msgid "Newest bill" +msgstr "" + +msgid "Oldest bill" +msgstr "" + +msgid "Actions" +msgstr "" + +msgid "edit" +msgstr "modifica" + +msgid "Delete project" +msgstr "" + +msgid "show" +msgstr "mostrar" + +msgid "The Dashboard is currently deactivated." +msgstr "" + +msgid "Download Mobile Application" +msgstr "" + +msgid "Get it on" +msgstr "" + +msgid "Edit project" +msgstr "" + +msgid "Import project" +msgstr "" + +msgid "Download project's data" +msgstr "" + +msgid "Bill items" +msgstr "" + +msgid "Download the list of bills with owner, amount, reason,... " +msgstr "" + +msgid "Settle plans" +msgstr "" + +msgid "Download the list of transactions needed to settle the current bills." +msgstr "" + +msgid "Can't remember the password?" +msgstr "" + +msgid "Cancel" +msgstr "Anullar" + +msgid "Privacy Settings" +msgstr "Paramètres de confidencialitat" + +msgid "Save changes" +msgstr "Enregistrar las modificacions" + +msgid "This will remove all bills and participants in this project!" +msgstr "" + +msgid "Import previously exported project" +msgstr "" + +msgid "Choose file" +msgstr "" + +msgid "Edit this bill" +msgstr "" + +msgid "Add a bill" +msgstr "" + +msgid "Simple operations are allowed, e.g. (18+36.2)/3" +msgstr "" + +msgid "Everyone" +msgstr "Tot lo monde" + +msgid "No one" +msgstr "Degun" + +msgid "More options" +msgstr "Mai d'opcions" + +msgid "Add participant" +msgstr "" + +msgid "Edit this participant" +msgstr "" + +msgid "john.doe@example.com, mary.moe@site.com" +msgstr "" + +msgid "Download" +msgstr "" + +msgid "Disabled Project History" +msgstr "" + +msgid "Disabled Project History & IP Address Recording" +msgstr "" + +msgid "Enabled Project History" +msgstr "" + +msgid "Disabled IP Address Recording" +msgstr "" + +msgid "Enabled Project History & IP Address Recording" +msgstr "" + +msgid "Enabled IP Address Recording" +msgstr "" + +msgid "History Settings Changed" +msgstr "" + +#, python-format +msgid "Bill %(name)s: %(property_name)s changed from %(before)s to %(after)s" +msgstr "" + +#, python-format +msgid "Bill %(name)s: %(property_name)s changed to %(after)s" +msgstr "" + +msgid "Confirm Remove IP Adresses" +msgstr "" + +msgid "" +"Are you sure you want to delete all recorded IP addresses from this " +"project?\n" +" The rest of the project history will be unaffected. This " +"action cannot be undone." +msgstr "" + +msgid "Confirm deletion" +msgstr "Confirmar la supression" + +msgid "Close" +msgstr "Tampar" + +msgid "Delete Confirmation" +msgstr "" + +msgid "" +"Are you sure you want to erase all history for this project? This action " +"cannot be undone." +msgstr "" + +#, python-format +msgid "Bill %(name)s: added %(owers_list_str)s to owers list" +msgstr "" + +#, python-format +msgid "Bill %(name)s: removed %(owers_list_str)s from owers list" +msgstr "" + +msgid "This project has history disabled. New actions won't appear below." +msgstr "" + +msgid "You can enable history on the settings page." +msgstr "" + +msgid "" +"The table below reflects actions recorded prior to disabling project " +"history." +msgstr "" + +msgid "You can clear the project history to remove them." +msgstr "" + +msgid "" +"Some entries below contain IP addresses, even though this project has IP " +"recording disabled. " +msgstr "" + +msgid "Delete stored IP addresses" +msgstr "" + +msgid "No IP Addresses to erase" +msgstr "" + +msgid "Delete Stored IP Addresses" +msgstr "" + +msgid "No history to erase" +msgstr "" + +msgid "Clear Project History" +msgstr "" + +msgid "Time" +msgstr "" + +msgid "Event" +msgstr "" + +msgid "IP address recording can be enabled on the settings page" +msgstr "" + +msgid "IP address recording can be disabled on the settings page" +msgstr "" + +msgid "From IP" +msgstr "" + +#, python-format +msgid "Project %(name)s added" +msgstr "" + +#, python-format +msgid "Bill %(name)s added" +msgstr "" + +#, python-format +msgid "Participant %(name)s added" +msgstr "" + +msgid "Project private code changed" +msgstr "" + +#, python-format +msgid "Project renamed to %(new_project_name)s" +msgstr "" + +#, python-format +msgid "Project contact email changed to %(new_email)s" +msgstr "" + +msgid "Project settings modified" +msgstr "" + +#, python-format +msgid "Participant %(name)s deactivated" +msgstr "" + +#, python-format +msgid "Participant %(name)s reactivated" +msgstr "" + +#, python-format +msgid "Participant %(name)s renamed to %(new_name)s" +msgstr "" + +#, python-format +msgid "Bill %(name)s renamed to %(new_description)s" +msgstr "" + +#, python-format +msgid "Participant %(name)s: weight changed from %(old_weight)s to %(new_weight)s" +msgstr "" + +msgid "Payer" +msgstr "Pagaire" + +msgid "Amount" +msgstr "Soma" + +msgid "Date" +msgstr "Data" + +#, python-format +msgid "Amount in %(currency)s" +msgstr "" + +#, python-format +msgid "Bill %(name)s modified" +msgstr "" + +#, python-format +msgid "Participant %(name)s modified" +msgstr "" + +#, python-format +msgid "Bill %(name)s removed" +msgstr "" + +#, python-format +msgid "Participant %(name)s removed" +msgstr "" + +#, python-format +msgid "Project %(name)s changed in an unknown way" +msgstr "" + +#, python-format +msgid "Bill %(name)s changed in an unknown way" +msgstr "" + +#, python-format +msgid "Participant %(name)s changed in an unknown way" +msgstr "" + +msgid "Nothing to list" +msgstr "Pas res a listar" + +msgid "Someone probably cleared the project history." +msgstr "" + +msgid "Manage your shared
expenses, easily" +msgstr "" + +msgid "Try out the demo" +msgstr "" + +msgid "You're sharing a house?" +msgstr "" + +msgid "Going on holidays with friends?" +msgstr "" + +msgid "Simply sharing money with others?" +msgstr "" + +msgid "We can help!" +msgstr "" + +msgid "Log in to an existing project" +msgstr "" + +msgid "Log in" +msgstr "Connexion" + +msgid "can't remember your password?" +msgstr "" + +msgid "Create" +msgstr "Crear" + +msgid "" +"Don\\'t reuse a personal password. Choose a private code and send it to " +"your friends" +msgstr "" + +msgid "Account manager" +msgstr "Gestionari de compte" + +msgid "Bills" +msgstr "Facturas" + +msgid "Settle" +msgstr "" + +msgid "Statistics" +msgstr "Estatisticas" + +msgid "Languages" +msgstr "Lengas" + +msgid "Projects" +msgstr "Projèctes" + +msgid "Start a new project" +msgstr "" + +msgid "History" +msgstr "" + +msgid "Settings" +msgstr "" + +msgid "RSS Feed" +msgstr "" + +msgid "Other projects :" +msgstr "" + +msgid "switch to" +msgstr "" + +msgid "Dashboard" +msgstr "Panèl d’administracion" + +#, python-format +msgid "Please retry after %(date)s." +msgstr "" + +msgid "Code" +msgstr "Còdi" + +msgid "Mobile Application" +msgstr "" + +msgid "Documentation" +msgstr "Documentacion" + +msgid "Administation Dashboard" +msgstr "Panèl d’administracion" + +msgid "Legal information" +msgstr "" + +msgid "\"I hate money\" is free software" +msgstr "" + +msgid "you can contribute and improve it!" +msgstr "" + +#, python-format +msgid "%(amount)s each" +msgstr "%(amount)s cadun" + +msgid "you sure?" +msgstr "O volètz vertadièrament ?" + +msgid "Invite people" +msgstr "Convidar de monde" + +msgid "Newer bills" +msgstr "" + +msgid "Older bills" +msgstr "" + +msgid "You should start by adding participants" +msgstr "" + +msgid "Add a new bill" +msgstr "" + +msgid "For what?" +msgstr "Per qué ?" + +#, python-format +msgid "Added on %(date)s" +msgstr "" + +#, python-format +msgid "Everyone but %(excluded)s" +msgstr "" + +msgid "delete" +msgstr "suprimir" + +msgid "No bills" +msgstr "Cap de factura" + +msgid "Nothing to list yet." +msgstr "Pas res a listar pel moment." + +msgid "Add your first bill" +msgstr "" + +msgid "Add the first participant" +msgstr "" + +msgid "Password reminder" +msgstr "" + +msgid "" +"A link to reset your password has been sent to you, please check your " +"emails." +msgstr "" + +msgid "Return to home page" +msgstr "" + +msgid "Your projects" +msgstr "" + +msgid "Reset your password" +msgstr "" + +msgid "Invite people to join this project" +msgstr "" + +msgid "Share an invitation link" +msgstr "" + +msgid "" +"The easiest way to invite people is to give them the following invitation" +" link.
They will be able to access the project, manage participants," +" add/edit/delete bills. However, they will not have access to important " +"settings such as changing the private code or deleting the whole project." +msgstr "" + +msgid "Scan QR code" +msgstr "" + +msgid "Use a mobile device with a compatible app." +msgstr "" + +msgid "Send via Emails" +msgstr "" + +msgid "" +"Specify a list of email adresses (separated by comma) of people you want " +"to notify about the creation of this project. We will send them an email " +"with the invitation link." +msgstr "" + +msgid "Share Identifier & code" +msgstr "" + +msgid "" +"You can share the project identifier and the private code by any " +"communication means.
Anyone with the private code will have access " +"to the full project, including changing settings such as the private code" +" or project email address, or even deleting the whole project." +msgstr "" + +msgid "Identifier:" +msgstr "" + +msgid "Private code:" +msgstr "Còdi privat :" + +msgid "the private code was defined when you created the project" +msgstr "" + +msgid "Who pays?" +msgstr "Qual paga ?" + +msgid "To whom?" +msgstr "A qual ?" + +msgid "Who?" +msgstr "Qual ?" + +msgid "Balance" +msgstr "" + +msgid "deactivate" +msgstr "" + +msgid "reactivate" +msgstr "" + +msgid "Paid" +msgstr "Pagat" + +msgid "Spent" +msgstr "Despensat" + +msgid "Expenses by Month" +msgstr "Despensas per mes" + +msgid "Period" +msgstr "Periòde" diff --git a/ihatemoney/translations/te/LC_MESSAGES/messages.po b/ihatemoney/translations/te/LC_MESSAGES/messages.po index df3548c0..67fabd92 100644 --- a/ihatemoney/translations/te/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/te/LC_MESSAGES/messages.po @@ -1,18 +1,18 @@ - msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2023-07-29 14:24+0200\n" -"PO-Revision-Date: 2022-10-04 14:19+0000\n" -"Last-Translator: Sharan J \n" +"PO-Revision-Date: 2024-05-13 07:00+0000\n" +"Last-Translator: Harshini K \n" +"Language-Team: Telugu \n" "Language: te\n" -"Language-Team: Telugu \n" -"Plural-Forms: nplurals=2; plural=n != 1\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=utf-8\n" "Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=n != 1;\n" +"X-Generator: Weblate 5.5.5-dev\n" "Generated-By: Babel 2.9.0\n" #, python-format @@ -35,7 +35,7 @@ msgid "Current private code" msgstr "కొత్త ప్రైవేట్ కోడ్" msgid "Enter existing private code to edit project" -msgstr "" +msgstr "ప్రాజెక్ట్‌ను సవరించడానికి ఇప్పటికీ ఉన్న ప్రైవేట్ కోడ్ ని ఎంటర్ చేయండి" msgid "New private code" msgstr "కొత్త ప్రైవేట్ కోడ్" @@ -75,7 +75,7 @@ msgstr "" " చెయ్యడం కుదరదు." msgid "Compatible with Cospend" -msgstr "" +msgstr "కాస్పెండ్ తో అనుకూలమైనది" #, fuzzy msgid "Project identifier" @@ -136,16 +136,16 @@ msgid "Reset password" msgstr "పాస్ వర్డ్ రీసెట్ చేయి" msgid "When?" -msgstr "" +msgstr "ఎప్పుడు?" msgid "What?" msgstr "ఏమిటి?" msgid "Who paid?" -msgstr "" +msgstr "ఎవరు చెల్లించారు?" msgid "How much?" -msgstr "" +msgstr "ఎంత?" msgid "Currency" msgstr "కరెన్సీ" @@ -1063,4 +1063,3 @@ msgstr "" #~ "them an email with the invitation " #~ "link." #~ msgstr "" - From 6e0a3689b87ae7544aad49a5c91df2341a8018ca Mon Sep 17 00:00:00 2001 From: adan-ea <57812567+adan-ea@users.noreply.github.com> Date: Wed, 18 Sep 2024 09:54:54 +0200 Subject: [PATCH 21/46] doc: add info about docker compose Should clarify and help close #1321 Issue also found in #1169 and #334 where i found my solution --- docs/installation.md | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/docs/installation.md b/docs/installation.md index d0cae448..ed089aa4 100644 --- a/docs/installation.md +++ b/docs/installation.md @@ -26,7 +26,7 @@ hub](https://hub.docker.com/r/ihatemoney/ihatemoney/). This is probably the simplest way to get something running. Once you have Docker installed on your system, just issue : - docker run -d -p 8000:8000 ihatemoney/ihatemoney + docker run -d -p 8000:8000 ihatemoney/ihatemoney:latest Ihatemoney is now available on . @@ -62,12 +62,18 @@ Add these additional environment variables to the docker run invocation: -e ACTIVATE_ADMIN_DASHBOARD=True \ -e ADMIN_PASSWORD= \ +:::{note} +If you are using a `docker-compose.yml` file and need to include a password hash, use `$$` instead of `$` to escape the dollar sign. This ensures that the hash is treated as a literal string rather than a variable in Bash. +::: + Additional gunicorn parameters can be passed using the docker `CMD` parameter. For example, use the following command to add more gunicorn workers: docker run -d -p 8000:8000 ihatemoney/ihatemoney -w 3 +If needed, there is a `docker-compose.yml` file available as an example on the [project github repository](https://github.com/spiral-project/ihatemoney/blob/master/docker-compose.yml) + (cloud)= ## On a Cloud Provider From 6582e2c0c3b5bd84516715d287e54e26147d09e1 Mon Sep 17 00:00:00 2001 From: adan-ea <57812567+adan-ea@users.noreply.github.com> Date: Wed, 18 Sep 2024 10:00:42 +0200 Subject: [PATCH 22/46] docs: add info about salted password hash --- docs/installation.md | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/docs/installation.md b/docs/installation.md index ed089aa4..beeecfab 100644 --- a/docs/installation.md +++ b/docs/installation.md @@ -54,6 +54,10 @@ To enable the Admin dashboard, first generate a hashed password with: docker run -it --rm --entrypoint ihatemoney ihatemoney/ihatemoney generate_password_hash +:::{note} +The generated password hash is salted. Which means that the same password will generate a different hash each time. This is normal and expected behavior. +::: + At the prompt, enter a password to use for the admin dashboard. The command will print the hashed password string. @@ -72,7 +76,7 @@ workers: docker run -d -p 8000:8000 ihatemoney/ihatemoney -w 3 -If needed, there is a `docker-compose.yml` file available as an example on the [project github repository](https://github.com/spiral-project/ihatemoney/blob/master/docker-compose.yml) +If needed, there is a `docker-compose.yml` file available as an example on the [project repository](https://github.com/spiral-project/ihatemoney/blob/master/docker-compose.yml) (cloud)= ## On a Cloud Provider From cf77b4c346c9d51436c9b8ce5390e3cb94196bd6 Mon Sep 17 00:00:00 2001 From: MediMilk <97471031+MediMilk@users.noreply.github.com> Date: Sat, 16 Nov 2024 05:55:04 -0500 Subject: [PATCH 23/46] Corrected typo Administation > Administration (#1332) Co-authored-by: MediMilk --- ihatemoney/messages.pot | 2 +- ihatemoney/templates/layout.html | 2 +- ihatemoney/translations/bn/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/bn_BD/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/ca/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/cs/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/de/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/el/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/eo/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/es/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/es_419/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/fa/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/fr/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/he/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/hi/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/hu/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/id/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/it/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/ja/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/kn/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/ms/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/nb_NO/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/nl/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/oc/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/pl/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/pt/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/pt_BR/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/ru/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/sr/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/sv/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/ta/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/te/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/th/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/tr/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/uk/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/ur/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/vi/LC_MESSAGES/messages.po | 2 +- ihatemoney/translations/zh_Hans/LC_MESSAGES/messages.po | 2 +- 38 files changed, 38 insertions(+), 38 deletions(-) diff --git a/ihatemoney/messages.pot b/ihatemoney/messages.pot index 42fbfb4a..73c57c33 100644 --- a/ihatemoney/messages.pot +++ b/ihatemoney/messages.pot @@ -759,7 +759,7 @@ msgstr "" msgid "Documentation" msgstr "" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "" msgid "Legal information" diff --git a/ihatemoney/templates/layout.html b/ihatemoney/templates/layout.html index 415113b4..38b45064 100644 --- a/ihatemoney/templates/layout.html +++ b/ihatemoney/templates/layout.html @@ -168,7 +168,7 @@ {{ static_include("images/book.svg") | safe }} {% if g.show_admin_dashboard_link %} - + {{ static_include("images/cog.svg") | safe }} {% endif %} diff --git a/ihatemoney/translations/bn/LC_MESSAGES/messages.po b/ihatemoney/translations/bn/LC_MESSAGES/messages.po index 98a5922d..a8799428 100644 --- a/ihatemoney/translations/bn/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/bn/LC_MESSAGES/messages.po @@ -782,7 +782,7 @@ msgstr "" msgid "Documentation" msgstr "" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "" msgid "Legal information" diff --git a/ihatemoney/translations/bn_BD/LC_MESSAGES/messages.po b/ihatemoney/translations/bn_BD/LC_MESSAGES/messages.po index 9ddf0bdf..4ea43bb3 100644 --- a/ihatemoney/translations/bn_BD/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/bn_BD/LC_MESSAGES/messages.po @@ -785,7 +785,7 @@ msgstr "" msgid "Documentation" msgstr "" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "" msgid "Legal information" diff --git a/ihatemoney/translations/ca/LC_MESSAGES/messages.po b/ihatemoney/translations/ca/LC_MESSAGES/messages.po index 1b797cfc..32447121 100644 --- a/ihatemoney/translations/ca/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/ca/LC_MESSAGES/messages.po @@ -826,7 +826,7 @@ msgstr "Aplicació mòbil" msgid "Documentation" msgstr "Documentació" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Panell d'administració" msgid "Legal information" diff --git a/ihatemoney/translations/cs/LC_MESSAGES/messages.po b/ihatemoney/translations/cs/LC_MESSAGES/messages.po index 0790d2f4..061f82b4 100644 --- a/ihatemoney/translations/cs/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/cs/LC_MESSAGES/messages.po @@ -800,7 +800,7 @@ msgstr "Mobilní aplikace" msgid "Documentation" msgstr "Dokumentace" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Správcovský panel" msgid "Legal information" diff --git a/ihatemoney/translations/de/LC_MESSAGES/messages.po b/ihatemoney/translations/de/LC_MESSAGES/messages.po index 1a82a876..fac6c73d 100644 --- a/ihatemoney/translations/de/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/de/LC_MESSAGES/messages.po @@ -824,7 +824,7 @@ msgstr "Handy-Applikation" msgid "Documentation" msgstr "Dokumentation" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Dashboard Administration" msgid "Legal information" diff --git a/ihatemoney/translations/el/LC_MESSAGES/messages.po b/ihatemoney/translations/el/LC_MESSAGES/messages.po index 65480d88..7a07ddd8 100644 --- a/ihatemoney/translations/el/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/el/LC_MESSAGES/messages.po @@ -811,7 +811,7 @@ msgstr "" msgid "Documentation" msgstr "" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "" #, fuzzy diff --git a/ihatemoney/translations/eo/LC_MESSAGES/messages.po b/ihatemoney/translations/eo/LC_MESSAGES/messages.po index e8b400fd..0546c1f9 100644 --- a/ihatemoney/translations/eo/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/eo/LC_MESSAGES/messages.po @@ -821,7 +821,7 @@ msgstr "Poŝaparata programo" msgid "Documentation" msgstr "Dokumentaro" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Administra panelo" #, fuzzy diff --git a/ihatemoney/translations/es/LC_MESSAGES/messages.po b/ihatemoney/translations/es/LC_MESSAGES/messages.po index b5e2004d..a2dde55d 100644 --- a/ihatemoney/translations/es/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/es/LC_MESSAGES/messages.po @@ -818,7 +818,7 @@ msgstr "Aplicación móvil" msgid "Documentation" msgstr "Documentación" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Panel de administración" msgid "Legal information" diff --git a/ihatemoney/translations/es_419/LC_MESSAGES/messages.po b/ihatemoney/translations/es_419/LC_MESSAGES/messages.po index 47f4ccd0..cc4ba81c 100644 --- a/ihatemoney/translations/es_419/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/es_419/LC_MESSAGES/messages.po @@ -815,7 +815,7 @@ msgstr "Aplicación móvil" msgid "Documentation" msgstr "Documentación" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Panel de administración" msgid "Legal information" diff --git a/ihatemoney/translations/fa/LC_MESSAGES/messages.po b/ihatemoney/translations/fa/LC_MESSAGES/messages.po index 5cc32d02..7302efcc 100644 --- a/ihatemoney/translations/fa/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/fa/LC_MESSAGES/messages.po @@ -782,7 +782,7 @@ msgstr "" msgid "Documentation" msgstr "" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "" msgid "Legal information" diff --git a/ihatemoney/translations/fr/LC_MESSAGES/messages.po b/ihatemoney/translations/fr/LC_MESSAGES/messages.po index 28178faa..89f3d5bd 100644 --- a/ihatemoney/translations/fr/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/fr/LC_MESSAGES/messages.po @@ -824,7 +824,7 @@ msgstr "Application mobile" msgid "Documentation" msgstr "Documentation" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Panneau d'administration" msgid "Legal information" diff --git a/ihatemoney/translations/he/LC_MESSAGES/messages.po b/ihatemoney/translations/he/LC_MESSAGES/messages.po index d55fc8d6..b3da557f 100644 --- a/ihatemoney/translations/he/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/he/LC_MESSAGES/messages.po @@ -788,7 +788,7 @@ msgstr "יישום לנייד" msgid "Documentation" msgstr "דוקומנטציה" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "" msgid "Legal information" diff --git a/ihatemoney/translations/hi/LC_MESSAGES/messages.po b/ihatemoney/translations/hi/LC_MESSAGES/messages.po index 886a8e16..24b526dc 100644 --- a/ihatemoney/translations/hi/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/hi/LC_MESSAGES/messages.po @@ -829,7 +829,7 @@ msgstr "मोबाइल एप्लीकेशन" msgid "Documentation" msgstr "प्रलेखन" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "व्यवस्थापन डैशबोर्ड" #, fuzzy diff --git a/ihatemoney/translations/hu/LC_MESSAGES/messages.po b/ihatemoney/translations/hu/LC_MESSAGES/messages.po index c02d34e5..ae6ae996 100644 --- a/ihatemoney/translations/hu/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/hu/LC_MESSAGES/messages.po @@ -817,7 +817,7 @@ msgstr "Mobil alkalmazás" msgid "Documentation" msgstr "Dokumentáció" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Adminisztrátori vezérlőpult" msgid "Legal information" diff --git a/ihatemoney/translations/id/LC_MESSAGES/messages.po b/ihatemoney/translations/id/LC_MESSAGES/messages.po index 940781d6..5d25e5ed 100644 --- a/ihatemoney/translations/id/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/id/LC_MESSAGES/messages.po @@ -812,7 +812,7 @@ msgstr "Aplikasi Gawai" msgid "Documentation" msgstr "Dokumentasi" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Dasbor Administrasi" msgid "Legal information" diff --git a/ihatemoney/translations/it/LC_MESSAGES/messages.po b/ihatemoney/translations/it/LC_MESSAGES/messages.po index bd2807ee..b17971b9 100644 --- a/ihatemoney/translations/it/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/it/LC_MESSAGES/messages.po @@ -817,7 +817,7 @@ msgstr "Applicazione mobile" msgid "Documentation" msgstr "Documentazione" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Cruscotto Amministrazione" msgid "Legal information" diff --git a/ihatemoney/translations/ja/LC_MESSAGES/messages.po b/ihatemoney/translations/ja/LC_MESSAGES/messages.po index 1c4165a0..c3fc9923 100644 --- a/ihatemoney/translations/ja/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/ja/LC_MESSAGES/messages.po @@ -797,7 +797,7 @@ msgstr "携帯アプリ" msgid "Documentation" msgstr "書類" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "管理ダッシュボード" #, fuzzy diff --git a/ihatemoney/translations/kn/LC_MESSAGES/messages.po b/ihatemoney/translations/kn/LC_MESSAGES/messages.po index f59a8cb5..6be503fb 100644 --- a/ihatemoney/translations/kn/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/kn/LC_MESSAGES/messages.po @@ -793,7 +793,7 @@ msgstr "" msgid "Documentation" msgstr "" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "" msgid "Legal information" diff --git a/ihatemoney/translations/ms/LC_MESSAGES/messages.po b/ihatemoney/translations/ms/LC_MESSAGES/messages.po index 2abafc78..9d7d6653 100644 --- a/ihatemoney/translations/ms/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/ms/LC_MESSAGES/messages.po @@ -793,7 +793,7 @@ msgstr "" msgid "Documentation" msgstr "" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "" msgid "Legal information" diff --git a/ihatemoney/translations/nb_NO/LC_MESSAGES/messages.po b/ihatemoney/translations/nb_NO/LC_MESSAGES/messages.po index 34e863b2..d4796fa6 100644 --- a/ihatemoney/translations/nb_NO/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/nb_NO/LC_MESSAGES/messages.po @@ -855,7 +855,7 @@ msgstr "Mobilprogram" msgid "Documentation" msgstr "Dokumentasjon" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Administrasjonsoversiktspanel" #, fuzzy diff --git a/ihatemoney/translations/nl/LC_MESSAGES/messages.po b/ihatemoney/translations/nl/LC_MESSAGES/messages.po index 2e4829e8..9a5c3d79 100644 --- a/ihatemoney/translations/nl/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/nl/LC_MESSAGES/messages.po @@ -814,7 +814,7 @@ msgstr "Mobiele app" msgid "Documentation" msgstr "Documentatie" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Administratie-overzicht" #, fuzzy diff --git a/ihatemoney/translations/oc/LC_MESSAGES/messages.po b/ihatemoney/translations/oc/LC_MESSAGES/messages.po index 56a97262..999c612e 100644 --- a/ihatemoney/translations/oc/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/oc/LC_MESSAGES/messages.po @@ -777,7 +777,7 @@ msgstr "" msgid "Documentation" msgstr "Documentacion" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Panèl d’administracion" msgid "Legal information" diff --git a/ihatemoney/translations/pl/LC_MESSAGES/messages.po b/ihatemoney/translations/pl/LC_MESSAGES/messages.po index a8e42191..d8120bc9 100644 --- a/ihatemoney/translations/pl/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/pl/LC_MESSAGES/messages.po @@ -812,7 +812,7 @@ msgstr "Aplikacja mobilna" msgid "Documentation" msgstr "Dokumentacja" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Kokpit administracyjny" msgid "Legal information" diff --git a/ihatemoney/translations/pt/LC_MESSAGES/messages.po b/ihatemoney/translations/pt/LC_MESSAGES/messages.po index d71513a7..8aae9ead 100644 --- a/ihatemoney/translations/pt/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/pt/LC_MESSAGES/messages.po @@ -823,7 +823,7 @@ msgstr "Aplicação Mobile" msgid "Documentation" msgstr "Documentação" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Painel de Administração" msgid "Legal information" diff --git a/ihatemoney/translations/pt_BR/LC_MESSAGES/messages.po b/ihatemoney/translations/pt_BR/LC_MESSAGES/messages.po index 47ca000b..46a10dea 100644 --- a/ihatemoney/translations/pt_BR/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/pt_BR/LC_MESSAGES/messages.po @@ -809,7 +809,7 @@ msgstr "Aplicativo" msgid "Documentation" msgstr "Documentação" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Painel de Administração" msgid "Legal information" diff --git a/ihatemoney/translations/ru/LC_MESSAGES/messages.po b/ihatemoney/translations/ru/LC_MESSAGES/messages.po index beb0ceaf..2bc6be91 100644 --- a/ihatemoney/translations/ru/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/ru/LC_MESSAGES/messages.po @@ -816,7 +816,7 @@ msgstr "Мобильное приложение" msgid "Documentation" msgstr "Документация" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Панель инструментов администратора" msgid "Legal information" diff --git a/ihatemoney/translations/sr/LC_MESSAGES/messages.po b/ihatemoney/translations/sr/LC_MESSAGES/messages.po index 15288647..a06952ff 100644 --- a/ihatemoney/translations/sr/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/sr/LC_MESSAGES/messages.po @@ -783,7 +783,7 @@ msgstr "Mobilna Aplikacija" msgid "Documentation" msgstr "Dokumentacija" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "" msgid "Legal information" diff --git a/ihatemoney/translations/sv/LC_MESSAGES/messages.po b/ihatemoney/translations/sv/LC_MESSAGES/messages.po index 0aa0bfd6..100102cd 100644 --- a/ihatemoney/translations/sv/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/sv/LC_MESSAGES/messages.po @@ -818,7 +818,7 @@ msgstr "Mobilapplikation" msgid "Documentation" msgstr "Dokumentation" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Översiktspanel för administration" msgid "Legal information" diff --git a/ihatemoney/translations/ta/LC_MESSAGES/messages.po b/ihatemoney/translations/ta/LC_MESSAGES/messages.po index 24df286d..078f243a 100644 --- a/ihatemoney/translations/ta/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/ta/LC_MESSAGES/messages.po @@ -809,7 +809,7 @@ msgstr "" msgid "Documentation" msgstr "" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "" msgid "Legal information" diff --git a/ihatemoney/translations/te/LC_MESSAGES/messages.po b/ihatemoney/translations/te/LC_MESSAGES/messages.po index 67fabd92..5416486c 100644 --- a/ihatemoney/translations/te/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/te/LC_MESSAGES/messages.po @@ -817,7 +817,7 @@ msgstr "" msgid "Documentation" msgstr "" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "" msgid "Legal information" diff --git a/ihatemoney/translations/th/LC_MESSAGES/messages.po b/ihatemoney/translations/th/LC_MESSAGES/messages.po index 6883c77e..7ea0d36f 100644 --- a/ihatemoney/translations/th/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/th/LC_MESSAGES/messages.po @@ -778,7 +778,7 @@ msgstr "" msgid "Documentation" msgstr "" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "" msgid "Legal information" diff --git a/ihatemoney/translations/tr/LC_MESSAGES/messages.po b/ihatemoney/translations/tr/LC_MESSAGES/messages.po index b9fa7e12..26f059af 100644 --- a/ihatemoney/translations/tr/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/tr/LC_MESSAGES/messages.po @@ -811,7 +811,7 @@ msgstr "Telefon Uygulaması" msgid "Documentation" msgstr "Belgelendirme" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "Yönetici Gösterge Paneli" msgid "Legal information" diff --git a/ihatemoney/translations/uk/LC_MESSAGES/messages.po b/ihatemoney/translations/uk/LC_MESSAGES/messages.po index c2154f8e..98f16fdb 100644 --- a/ihatemoney/translations/uk/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/uk/LC_MESSAGES/messages.po @@ -791,7 +791,7 @@ msgstr "" msgid "Documentation" msgstr "" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "" msgid "Legal information" diff --git a/ihatemoney/translations/ur/LC_MESSAGES/messages.po b/ihatemoney/translations/ur/LC_MESSAGES/messages.po index 6c2ba6bc..148d327e 100644 --- a/ihatemoney/translations/ur/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/ur/LC_MESSAGES/messages.po @@ -776,7 +776,7 @@ msgstr "" msgid "Documentation" msgstr "" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "" msgid "Legal information" diff --git a/ihatemoney/translations/vi/LC_MESSAGES/messages.po b/ihatemoney/translations/vi/LC_MESSAGES/messages.po index e01f2611..e469ebff 100644 --- a/ihatemoney/translations/vi/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/vi/LC_MESSAGES/messages.po @@ -775,7 +775,7 @@ msgstr "" msgid "Documentation" msgstr "" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "" msgid "Legal information" diff --git a/ihatemoney/translations/zh_Hans/LC_MESSAGES/messages.po b/ihatemoney/translations/zh_Hans/LC_MESSAGES/messages.po index 1d760cf2..7211f779 100644 --- a/ihatemoney/translations/zh_Hans/LC_MESSAGES/messages.po +++ b/ihatemoney/translations/zh_Hans/LC_MESSAGES/messages.po @@ -779,7 +779,7 @@ msgstr "手机软件" msgid "Documentation" msgstr "文件" -msgid "Administation Dashboard" +msgid "Administration Dashboard" msgstr "管理面板" msgid "Legal information" From 6e31a9c8b5505e5cfda370e89ef13462ff69ddf6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alexis=20M=C3=A9taireau?= Date: Sun, 29 Sep 2024 23:47:48 +0200 Subject: [PATCH 24/46] Upgrade tooling on the project. - Replace black by ruff, as it's quicker ; - Use `uv` wherever possible as a replacement for pip, as it's way faster to run, add an `uv.lock` file which will be synced before the releases and published here ; - Remove tox, it's too complex for this project and can easily be replaced by `uv` ; - Apply `ruff` formatting ; - Update the makefile accordingly ; - Update the CI accordingly --- .github/workflows/check-doc.yml | 26 - .../workflows/{lint-and-tests.yml => ci.yml} | 69 +- CHANGELOG.md | 5 +- Makefile | 67 +- README.md | 2 +- docs/contributing.md | 2 +- ihatemoney/forms.py | 1 - ihatemoney/run.py | 2 +- ihatemoney/tests/api_test.py | 1 - ihatemoney/tests/budget_test.py | 4 +- ihatemoney/utils.py | 2 - ihatemoney/web.py | 1 + pyproject.toml | 31 +- tox.ini | 41 - uv.lock | 1851 +++++++++++++++++ 15 files changed, 1935 insertions(+), 170 deletions(-) delete mode 100644 .github/workflows/check-doc.yml rename .github/workflows/{lint-and-tests.yml => ci.yml} (66%) delete mode 100644 tox.ini create mode 100644 uv.lock diff --git a/.github/workflows/check-doc.yml b/.github/workflows/check-doc.yml deleted file mode 100644 index 06dcf376..00000000 --- a/.github/workflows/check-doc.yml +++ /dev/null @@ -1,26 +0,0 @@ -name: Check doc - -on: - push: - branches: [ 'master', 'stable-*' ] - pull_request: - branches: [ 'master', 'stable-*' ] - -jobs: - - test_doc: - runs-on: ubuntu-latest - steps: - - uses: actions/checkout@v3 - - name: Set up Python - uses: actions/setup-python@v4 - with: - python-version: "3.11" - cache: 'pip' - cache-dependency-path: '**/pyproject.toml' - - name: Install dependencies - run: | - python -m pip install --upgrade pip - python -m pip install tox - - name: Check we can generate documentation - run: tox -e docs diff --git a/.github/workflows/lint-and-tests.yml b/.github/workflows/ci.yml similarity index 66% rename from .github/workflows/lint-and-tests.yml rename to .github/workflows/ci.yml index 4e30ff86..8679fbb8 100644 --- a/.github/workflows/lint-and-tests.yml +++ b/.github/workflows/ci.yml @@ -1,4 +1,4 @@ -name: Lint & unit tests +name: CI on: push: @@ -11,18 +11,12 @@ jobs: runs-on: ubuntu-latest steps: - uses: actions/checkout@v3 - - name: Set up Python - uses: actions/setup-python@v4 + - name: Install uv and set the python version + uses: astral-sh/setup-uv@v4 with: python-version: "3.11" - cache: 'pip' - cache-dependency-path: '**/pyproject.toml' - - name: Install dependencies - run: | - python -m pip install --upgrade pip - python -m pip install tox - name: Run Lint - run: tox -e lint + run: make lint test: # Dependency on linting to avoid running our expensive matrix test for nothing @@ -56,7 +50,8 @@ jobs: python-version: [3.7, 3.8, 3.9, "3.10", "3.11", "3.12"] dependencies: [normal] database: [sqlite] - # Test other databases with only a few versions of Python (Debian bullseye has 3.9, bookworm has 3.11) + # Test other databases with only a few versions of Python + # (Debian bullseye has 3.9, bookworm has 3.11) include: - python-version: 3.9 dependencies: normal @@ -95,32 +90,36 @@ jobs: steps: - uses: actions/checkout@v3 - - name: Set up Python ${{ matrix.python-version }} - uses: actions/setup-python@v4 + - name: Install uv and set the python version + uses: astral-sh/setup-uv@v4 with: python-version: ${{ matrix.python-version }} - cache: 'pip' - cache-dependency-path: '**/pyproject.toml' - name: Change dependencies to minimal supported versions - run: sed -i -e 's/>=/==/g; s/~=.*==\(.*\)/==\1/g; s/~=/==/g;' pyproject.toml + # This sed comment installs the minimal supported version + # for all versions except for "requires-python" + # This is to detect that the minimum versions are really + # supported, in the CI + run: sed -i -e '/requires-python/!s/>=/==/g; /requires-python/!s/~=.*==\(.*\)/==\1/g; /requires-python/!s/~=/==/g;' pyproject.toml if: matrix.dependencies == 'minimal' - - name: Install dependencies - run: | - python -m pip install --upgrade pip - python -m pip install tox - # Run tox using the version of Python in `PATH` - - name: Run Tox with sqlite - run: tox -e py - if: matrix.database == 'sqlite' + - name: Run tests + run: make test env: - TESTING_SQLALCHEMY_DATABASE_URI: 'sqlite:///budget.db' - - name: Run Tox with postgresql - run: tox -e py - if: matrix.database == 'postgresql' - env: - TESTING_SQLALCHEMY_DATABASE_URI: 'postgresql+psycopg2://postgres:ihatemoney@localhost:5432/ihatemoney_ci' - - name: Run Tox with mariadb - run: tox -e py - if: matrix.database == 'mariadb' - env: - TESTING_SQLALCHEMY_DATABASE_URI: 'mysql+pymysql://root:ihatemoney@localhost:3306/ihatemoney_ci' + # Setup the DATABASE_URI depending on the matrix we are using. + TESTING_SQLALCHEMY_DATABASE_URI: ${{ + matrix.database == 'sqlite' + && 'sqlite:///budget.db' + || matrix.database == 'postgresql' + && 'postgresql+psycopg2://postgres:ihatemoney@localhost:5432/ihatemoney_ci' + || 'mysql+pymysql://root:ihatemoney@localhost:3306/ihatemoney_ci' + }} + + docs: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v3 + - name: Install uv and set the python version + uses: astral-sh/setup-uv@v4 + with: + python-version: "3.11" + - name: Build docs + run: make build-docs diff --git a/CHANGELOG.md b/CHANGELOG.md index 2ef14c1c..d7757b55 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,7 +5,10 @@ This document describes changes between each past release. ## 6.2.0 (unreleased) - Add support for python 3.12 (#757) - +- Remove support for python 3.7 +- Replace the black linter by ruff +- Replace virtualenv and pip by uv +- Remove tox ## 6.1.5 (2024-03-19) diff --git a/Makefile b/Makefile index bf917b60..a7538527 100644 --- a/Makefile +++ b/Makefile @@ -1,60 +1,40 @@ -VIRTUALENV = python3 -m venv -SPHINX_BUILDDIR = docs/_build +VIRTUALENV = uv venv VENV := $(shell realpath $${VIRTUAL_ENV-.venv}) -PYTHON = $(VENV)/bin/python3 +BIN := uv tool run +PIP := uv pip +PYTHON = $(BIN)/python3 DEV_STAMP = $(VENV)/.dev_env_installed.stamp INSTALL_STAMP = $(VENV)/.install.stamp TEMPDIR := $(shell mktemp -d) ZOPFLIPNG := zopflipng MAGICK_MOGRIFY := mogrify -.PHONY: all -all: install ## Alias for install -.PHONY: install -install: virtualenv pyproject.toml $(INSTALL_STAMP) ## Install dependencies -$(INSTALL_STAMP): - $(VENV)/bin/pip install -U pip - $(VENV)/bin/pip install -e . - touch $(INSTALL_STAMP) - .PHONY: virtualenv virtualenv: $(PYTHON) $(PYTHON): $(VIRTUALENV) $(VENV) -.PHONY: install-dev -install-dev: virtualenv pyproject.toml $(INSTALL_STAMP) $(DEV_STAMP) ## Install development dependencies -$(DEV_STAMP): $(PYTHON) - $(VENV)/bin/pip install -Ue .[dev] - touch $(DEV_STAMP) - -.PHONY: remove-install-stamp -remove-install-stamp: - rm $(INSTALL_STAMP) - -.PHONY: update -update: remove-install-stamp install ## Update the dependencies - .PHONY: serve -serve: install build-translations ## Run the ihatemoney server +serve: build-translations ## Run the ihatemoney server @echo 'Running ihatemoney on http://localhost:5000' - FLASK_DEBUG=1 FLASK_APP=ihatemoney.wsgi $(VENV)/bin/flask run --host=0.0.0.0 + FLASK_DEBUG=1 FLASK_APP=ihatemoney.wsgi uv run flask run --host=0.0.0.0 .PHONY: test -test: install-dev ## Run the tests - $(VENV)/bin/tox +test: + uv run --extra dev --extra database pytest . -.PHONY: black -black: install-dev ## Run the tests - $(VENV)/bin/black --target-version=py37 . +.PHONY: lint +lint: + uv tool run ruff check . + uv tool run vermin --no-tips --violations -t=3.8- . -.PHONY: isort -isort: install-dev ## Run the tests - $(VENV)/bin/isort . +.PHONY: format +format: + uv tool run ruff format . .PHONY: release -release: install-dev ## Release a new version (see https://ihatemoney.readthedocs.io/en/latest/contributing.html#how-to-release) - $(VENV)/bin/fullrelease +release: # Release a new version (see https://ihatemoney.readthedocs.io/en/latest/contributing.html#how-to-release) + uv run --extra dev fullreleas .PHONY: compress-showcase compress-showcase: @@ -72,27 +52,30 @@ compress-assets: compress-showcase ## Compress static assets .PHONY: build-translations build-translations: ## Build the translations - $(VENV)/bin/pybabel compile -d ihatemoney/translations + uv run --extra dev pybabel compile -d ihatemoney/translations .PHONY: extract-translations extract-translations: ## Extract new translations from source code - $(VENV)/bin/pybabel extract --add-comments "I18N:" --strip-comments --omit-header --no-location --mapping-file ihatemoney/babel.cfg -o ihatemoney/messages.pot ihatemoney - $(VENV)/bin/pybabel update -i ihatemoney/messages.pot -d ihatemoney/translations/ + uv run --extra dev pybabel extract --add-comments "I18N:" --strip-comments --omit-header --no-location --mapping-file ihatemoney/babel.cfg -o ihatemoney/messages.pot ihatemoney + uv run --extra dev pybabel update -i ihatemoney/messages.pot -d ihatemoney/translations/ .PHONY: create-database-revision create-database-revision: ## Create a new database revision @read -p "Please enter a message describing this revision: " rev_message; \ - $(PYTHON) -m ihatemoney.manage db migrate -d ihatemoney/migrations -m "$${rev_message}" + uv run python -m ihatemoney.manage db migrate -d ihatemoney/migrations -m "$${rev_message}" .PHONY: create-empty-database-revision create-empty-database-revision: ## Create an empty database revision @read -p "Please enter a message describing this revision: " rev_message; \ - $(PYTHON) -m ihatemoney.manage db revision -d ihatemoney/migrations -m "$${rev_message}" + uv run python -m ihatemoney.manage db revision -d ihatemoney/migrations -m "$${rev_message}" .PHONY: clean clean: ## Destroy the virtual environment rm -rf .venv +build-docs: + uv run --extra doc sphinx-build -a -n -b html -d docs/_build/doctrees docs docs/_build/html + .PHONY: help help: ## Show the help indications @grep -E '^[a-zA-Z_-]+:.*?## .*$$' $(MAKEFILE_LIST) | sort | awk 'BEGIN {FS = ":.*?## "}; {printf "\033[36m%-30s\033[0m %s\n", $$1, $$2}' diff --git a/README.md b/README.md index bd8c739b..d0542c5a 100644 --- a/README.md +++ b/README.md @@ -22,7 +22,7 @@ highly encouraged to do so. ## Requirements -- **Python**: version 3.7 to 3.12. +- **Python**: version 3.8 to 3.12. - **Backends**: SQLite, PostgreSQL, MariaDB (version 10.3.2 or above), Memory. diff --git a/docs/contributing.md b/docs/contributing.md index 821a3742..3be42a41 100644 --- a/docs/contributing.md +++ b/docs/contributing.md @@ -183,7 +183,7 @@ We are using [black](https://black.readthedocs.io/en/stable/) and Python files in this project. Be sure to run it locally on your files. To do so, just run: - make black isort + make lint You can also integrate them with your dev environment (as a *format-on-save* hook, for instance). diff --git a/ihatemoney/forms.py b/ihatemoney/forms.py index e1ddabe8..0fee9779 100644 --- a/ihatemoney/forms.py +++ b/ihatemoney/forms.py @@ -90,7 +90,6 @@ def get_billform_for(project, set_default=True, **kwargs): class CommaDecimalField(DecimalField): - """A class to deal with comma in Decimal Field""" def process_formdata(self, value): diff --git a/ihatemoney/run.py b/ihatemoney/run.py index 5c74f6a2..23084fe4 100644 --- a/ihatemoney/run.py +++ b/ihatemoney/run.py @@ -103,7 +103,7 @@ def validate_configuration(app): if "MAIL_DEFAULT_SENDER" not in app.config: app.config["MAIL_DEFAULT_SENDER"] = default_settings.DEFAULT_MAIL_SENDER - if type(app.config["MAIL_DEFAULT_SENDER"]) == tuple: + if type(app.config["MAIL_DEFAULT_SENDER"]) is tuple: (name, address) = app.config["MAIL_DEFAULT_SENDER"] app.config["MAIL_DEFAULT_SENDER"] = f"{name} <{address}>" warnings.warn( diff --git a/ihatemoney/tests/api_test.py b/ihatemoney/tests/api_test.py index 191790b6..c676e3e3 100644 --- a/ihatemoney/tests/api_test.py +++ b/ihatemoney/tests/api_test.py @@ -9,7 +9,6 @@ from ihatemoney.tests.common.ihatemoney_testcase import IhatemoneyTestCase class TestAPI(IhatemoneyTestCase): - """Tests the API""" def api_create( diff --git a/ihatemoney/tests/budget_test.py b/ihatemoney/tests/budget_test.py index 093d9d17..6e0c62d5 100644 --- a/ihatemoney/tests/budget_test.py +++ b/ihatemoney/tests/budget_test.py @@ -1030,9 +1030,7 @@ class TestBudget(IhatemoneyTestCase): assert """ Project - Number of participants""" in resp.data.decode( - "utf-8" - ) + Number of participants""" in resp.data.decode("utf-8") def test_dashboard_project_deletion(self): self.post_project("raclette") diff --git a/ihatemoney/utils.py b/ihatemoney/utils.py index ef4818ad..7af4967b 100644 --- a/ihatemoney/utils.py +++ b/ihatemoney/utils.py @@ -84,7 +84,6 @@ def flash_email_error(error_message, category="danger"): class Redirect303(HTTPException, RoutingException): - """Raise if the map requests a redirect. This is for example the case if `strict_slashes` are activated and an url that requires a trailing slash. @@ -102,7 +101,6 @@ class Redirect303(HTTPException, RoutingException): class PrefixedWSGI(object): - """ Wrap the application in this middleware and configure the front-end server to add these headers, to let you quietly bind diff --git a/ihatemoney/web.py b/ihatemoney/web.py index 0d0bdd20..9dfa17c6 100644 --- a/ihatemoney/web.py +++ b/ihatemoney/web.py @@ -8,6 +8,7 @@ Basically, this blueprint takes care of the authentication and provides some shortcuts to make your life better when coding (see `pull_project` and `add_project_id` for a quick overview) """ + import datetime from functools import wraps import hashlib diff --git a/pyproject.toml b/pyproject.toml index ee8ad57b..89e72d3d 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -5,6 +5,7 @@ build-backend = "hatchling.build" [project] name = "ihatemoney" version = "6.2.0.dev0" +requires-python = ">=3.7" description = "A simple shared budget manager web application." readme = "README.md" license = {file = "LICENSE"} @@ -15,7 +16,6 @@ keywords = ["web", "budget"] classifiers = [ "Programming Language :: Python", "Programming Language :: Python :: 3", - "Programming Language :: Python :: 3.7", "Programming Language :: Python :: 3.8", "Programming Language :: Python :: 3.9", "Programming Language :: Python :: 3.10", @@ -30,46 +30,43 @@ dependencies = [ "cachetools>=4.1,<5", "debts>=0.5,<1", "email_validator>=1.0,<3", + "Flask>=2,<3", "Flask-Babel>=1.0,<4", "Flask-Cors>=3.0.8,<4", "Flask-Limiter>=2.6,<3", "Flask-Mail>=0.9.1,<1", - "Flask-Migrate>=2.5.3,<5", # Not following semantic versioning (e.g. https://github.com/miguelgrinberg/flask-migrate/commit/1af28ba273de6c88544623b8dc02dd539340294b) + "Flask-Migrate>=2.5.3,<5", # Not following semantic versioning (e.g. https://github.com/miguelgrinberg/flask-migrate/commit/1af28ba273de6c88544623b8dc02dd539340294b) "Flask-RESTful>=0.3.9,<1", "Flask-SQLAlchemy>=2.4,<3", "Flask-Talisman>=0.8,<2", "Flask-WTF>=0.14.3,<2", - "WTForms>=2.3.3,<3.2", - "Flask>=2,<3", - "Werkzeug>=2,<3", "itsdangerous>=2,<3", "Jinja2>=3,<4", + "pytest-libfaketime[dev]>=0.1.3", + "python-dateutil", "qrcode>=7.1,<8", "requests>=2.25,<3", - "SQLAlchemy-Continuum>=1.3.12,<2", - "SQLAlchemy>=1.3.0,<1.5", # New 1.4 changes API, see #728 - "python-dateutil", -] + "SQLAlchemy>=1.3.0,<1.5", + "SQLAlchemy-Continuum>=1.3.12,<2", # New 1.4 changes API, see #728 + "Werkzeug>=2,<3", + "WTForms>=2.3.3,<3.2",] [project.optional-dependencies] database = [ # Python 3.11 support starts in 2.9.2 - "psycopg2-binary>=2.9.2,<3", + "psycopg2-binary>=2.9.2,<2.9.9", "PyMySQL>=0.9,<1.1", ] - dev = [ - "black==23.3.0", + "ruff==0.6.8", "flake8==5.0.4", "isort==5.11.5", "vermin==1.5.2", "pytest>=6.2.5", "pytest-flask>=1.2.0", - "pytest-libfaketime>=0.1.2", - "tox>=3.14.6", "zest.releaser>=6.20.1", + "libfaketime>=2.1.0", ] - doc = [ "Sphinx>=7.0.1,<8", "docutils==0.20.1", @@ -107,3 +104,7 @@ include = [ "README.md", "SECURITY.md", ] + + +[tool.ruff] +exclude = ["ihatemoney/migrations"] diff --git a/tox.ini b/tox.ini deleted file mode 100644 index 8a0421fa..00000000 --- a/tox.ini +++ /dev/null @@ -1,41 +0,0 @@ -[tox] -isolated_build = true -envlist = py312,py311,py310,py39,py38,py37,lint,docs -skip_missing_interpreters = True - -[testenv] -passenv = TESTING_SQLALCHEMY_DATABASE_URI - -commands = - python --version - py.test --pyargs ihatemoney.tests {posargs} - -deps = - -e.[database,dev] - -# To be sure we are importing ihatemoney pkg from pip-installed version -changedir = /tmp - -[testenv:lint] -commands = - black --check --target-version=py37 . - isort --check --profile black . - flake8 ihatemoney - vermin --no-tips --violations -t=3.7- . -deps = - -e.[dev] -changedir = {toxinidir} - -[testenv:docs] -commands = - sphinx-build -a -n -b html -d docs/_build/doctrees docs docs/_build/html -deps = - -e.[doc] -changedir = {toxinidir} - -[flake8] -exclude = migrations -max_line_length = 100 -extend-ignore = - # See https://github.com/PyCQA/pycodestyle/issues/373 - E203, diff --git a/uv.lock b/uv.lock new file mode 100644 index 00000000..7da6f203 --- /dev/null +++ b/uv.lock @@ -0,0 +1,1851 @@ +version = 1 +requires-python = ">=3.8" + +[[package]] +name = "alabaster" +version = "0.7.13" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/94/71/a8ee96d1fd95ca04a0d2e2d9c4081dac4c2d2b12f7ddb899c8cb9bfd1532/alabaster-0.7.13.tar.gz", hash = "sha256:a27a4a084d5e690e16e01e03ad2b2e552c61a65469419b907243193de1a84ae2", size = 11454 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/64/88/c7083fc61120ab661c5d0b82cb77079fc1429d3f913a456c1c82cf4658f7/alabaster-0.7.13-py3-none-any.whl", hash = "sha256:1ee19aca801bbabb5ba3f5f258e4422dfa86f82f3e9cefb0859b283cdd7f62a3", size = 13857 }, +] + +[[package]] +name = "alembic" +version = "1.13.3" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "importlib-metadata", marker = "python_full_version < '3.9'" }, + { name = "importlib-resources", marker = "python_full_version < '3.9'" }, + { name = "mako" }, + { name = "sqlalchemy" }, + { name = "typing-extensions" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/94/a2/840c3b84382dce8624bc2f0ee67567fc74c32478d0c5a5aea981518c91c3/alembic-1.13.3.tar.gz", hash = "sha256:203503117415561e203aa14541740643a611f641517f0209fcae63e9fa09f1a2", size = 1921223 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/c2/12/58f4f11385fddafef5d6f7bfaaf2f42899c8da6b4f95c04b7c3b744851a8/alembic-1.13.3-py3-none-any.whl", hash = "sha256:908e905976d15235fae59c9ac42c4c5b75cfcefe3d27c0fbf7ae15a37715d80e", size = 233217 }, +] + +[[package]] +name = "aniso8601" +version = "9.0.1" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/cb/72/be3db445b03944bfbb2b02b82d00cb2a2bcf96275c4543f14bf60fa79e12/aniso8601-9.0.1.tar.gz", hash = "sha256:72e3117667eedf66951bb2d93f4296a56b94b078a8a95905a052611fb3f1b973", size = 47345 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/e3/04/e97c12dc034791d7b504860acfcdd2963fa21ae61eaca1c9d31245f812c3/aniso8601-9.0.1-py2.py3-none-any.whl", hash = "sha256:1d2b7ef82963909e93c4f24ce48d4de9e66009a21bf1c1e1c85bdd0812fe412f", size = 52754 }, +] + +[[package]] +name = "babel" +version = "2.16.0" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "pytz", marker = "python_full_version < '3.9'" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/2a/74/f1bc80f23eeba13393b7222b11d95ca3af2c1e28edca18af487137eefed9/babel-2.16.0.tar.gz", hash = "sha256:d1f3554ca26605fe173f3de0c65f750f5a42f924499bf134de6423582298e316", size = 9348104 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/ed/20/bc79bc575ba2e2a7f70e8a1155618bb1301eaa5132a8271373a6903f73f8/babel-2.16.0-py3-none-any.whl", hash = "sha256:368b5b98b37c06b7daf6696391c3240c938b37767d4584413e8438c5c435fa8b", size = 9587599 }, +] + +[[package]] +name = "backports-tarfile" +version = "1.2.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/86/72/cd9b395f25e290e633655a100af28cb253e4393396264a98bd5f5951d50f/backports_tarfile-1.2.0.tar.gz", hash = "sha256:d75e02c268746e1b8144c278978b6e98e85de6ad16f8e4b0844a154557eca991", size = 86406 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/b9/fa/123043af240e49752f1c4bd24da5053b6bd00cad78c2be53c0d1e8b975bc/backports.tarfile-1.2.0-py3-none-any.whl", hash = "sha256:77e284d754527b01fb1e6fa8a1afe577858ebe4e9dad8919e34c862cb399bc34", size = 30181 }, +] + +[[package]] +name = "blinker" +version = "1.8.2" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/1e/57/a6a1721eff09598fb01f3c7cda070c1b6a0f12d63c83236edf79a440abcc/blinker-1.8.2.tar.gz", hash = "sha256:8f77b09d3bf7c795e969e9486f39c2c5e9c39d4ee07424be2bc594ece9642d83", size = 23161 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/bb/2a/10164ed1f31196a2f7f3799368a821765c62851ead0e630ab52b8e14b4d0/blinker-1.8.2-py3-none-any.whl", hash = "sha256:1779309f71bf239144b9399d06ae925637cf6634cf6bd131104184531bf67c01", size = 9456 }, +] + +[[package]] +name = "build" +version = "1.2.2" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "colorama", marker = "os_name == 'nt'" }, + { name = "importlib-metadata", marker = "python_full_version < '3.10.2'" }, + { name = "packaging" }, + { name = "pyproject-hooks" }, + { name = "tomli", marker = "python_full_version < '3.11'" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/dd/bb/4a1b7e3a7520e310cf7bfece43788071604e1ccf693a7f0c4638c59068d6/build-1.2.2.tar.gz", hash = "sha256:119b2fb462adef986483438377a13b2f42064a2a3a4161f24a0cca698a07ac8c", size = 46516 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/91/fd/e4bda6228637ecae5732162b5ac2a5a822e2ba8e546eb4997cde51b231a3/build-1.2.2-py3-none-any.whl", hash = "sha256:277ccc71619d98afdd841a0e96ac9fe1593b823af481d3b0cea748e8894e0613", size = 22823 }, +] + +[[package]] +name = "cachetools" +version = "4.2.4" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/d7/69/c457a860456cbf80ecc2e44ed4c201b49ec7ad124d769b71f6d0a7935dca/cachetools-4.2.4.tar.gz", hash = "sha256:89ea6f1b638d5a73a4f9226be57ac5e4f399d22770b92355f92dcb0f7f001693", size = 25487 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/ea/c1/4740af52db75e6dbdd57fc7e9478439815bbac549c1c05881be27d19a17d/cachetools-4.2.4-py3-none-any.whl", hash = "sha256:92971d3cb7d2a97efff7c7bb1657f21a8f5fb309a37530537c71b1774189f2d1", size = 10358 }, +] + +[[package]] +name = "certifi" +version = "2024.8.30" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/b0/ee/9b19140fe824b367c04c5e1b369942dd754c4c5462d5674002f75c4dedc1/certifi-2024.8.30.tar.gz", hash = "sha256:bec941d2aa8195e248a60b31ff9f0558284cf01a52591ceda73ea9afffd69fd9", size = 168507 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/12/90/3c9ff0512038035f59d279fddeb79f5f1eccd8859f06d6163c58798b9487/certifi-2024.8.30-py3-none-any.whl", hash = "sha256:922820b53db7a7257ffbda3f597266d435245903d80737e34f8a45ff3e3230d8", size = 167321 }, +] + +[[package]] +name = "cffi" +version = "1.17.1" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "pycparser" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/fc/97/c783634659c2920c3fc70419e3af40972dbaf758daa229a7d6ea6135c90d/cffi-1.17.1.tar.gz", hash = "sha256:1c39c6016c32bc48dd54561950ebd6836e1670f2ae46128f67cf49e789c52824", size = 516621 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/90/07/f44ca684db4e4f08a3fdc6eeb9a0d15dc6883efc7b8c90357fdbf74e186c/cffi-1.17.1-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:df8b1c11f177bc2313ec4b2d46baec87a5f3e71fc8b45dab2ee7cae86d9aba14", size = 182191 }, + { url = "https://files.pythonhosted.org/packages/08/fd/cc2fedbd887223f9f5d170c96e57cbf655df9831a6546c1727ae13fa977a/cffi-1.17.1-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:8f2cdc858323644ab277e9bb925ad72ae0e67f69e804f4898c070998d50b1a67", size = 178592 }, + { url = "https://files.pythonhosted.org/packages/de/cc/4635c320081c78d6ffc2cab0a76025b691a91204f4aa317d568ff9280a2d/cffi-1.17.1-cp310-cp310-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:edae79245293e15384b51f88b00613ba9f7198016a5948b5dddf4917d4d26382", size = 426024 }, + { url = "https://files.pythonhosted.org/packages/b6/7b/3b2b250f3aab91abe5f8a51ada1b717935fdaec53f790ad4100fe2ec64d1/cffi-1.17.1-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:45398b671ac6d70e67da8e4224a065cec6a93541bb7aebe1b198a61b58c7b702", size = 448188 }, + { url = "https://files.pythonhosted.org/packages/d3/48/1b9283ebbf0ec065148d8de05d647a986c5f22586b18120020452fff8f5d/cffi-1.17.1-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:ad9413ccdeda48c5afdae7e4fa2192157e991ff761e7ab8fdd8926f40b160cc3", size = 455571 }, + { url = "https://files.pythonhosted.org/packages/40/87/3b8452525437b40f39ca7ff70276679772ee7e8b394934ff60e63b7b090c/cffi-1.17.1-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:5da5719280082ac6bd9aa7becb3938dc9f9cbd57fac7d2871717b1feb0902ab6", size = 436687 }, + { url = "https://files.pythonhosted.org/packages/8d/fb/4da72871d177d63649ac449aec2e8a29efe0274035880c7af59101ca2232/cffi-1.17.1-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:2bb1a08b8008b281856e5971307cc386a8e9c5b625ac297e853d36da6efe9c17", size = 446211 }, + { url = "https://files.pythonhosted.org/packages/ab/a0/62f00bcb411332106c02b663b26f3545a9ef136f80d5df746c05878f8c4b/cffi-1.17.1-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:045d61c734659cc045141be4bae381a41d89b741f795af1dd018bfb532fd0df8", size = 461325 }, + { url = "https://files.pythonhosted.org/packages/36/83/76127035ed2e7e27b0787604d99da630ac3123bfb02d8e80c633f218a11d/cffi-1.17.1-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:6883e737d7d9e4899a8a695e00ec36bd4e5e4f18fabe0aca0efe0a4b44cdb13e", size = 438784 }, + { url = "https://files.pythonhosted.org/packages/21/81/a6cd025db2f08ac88b901b745c163d884641909641f9b826e8cb87645942/cffi-1.17.1-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:6b8b4a92e1c65048ff98cfe1f735ef8f1ceb72e3d5f0c25fdb12087a23da22be", size = 461564 }, + { url = "https://files.pythonhosted.org/packages/f8/fe/4d41c2f200c4a457933dbd98d3cf4e911870877bd94d9656cc0fcb390681/cffi-1.17.1-cp310-cp310-win32.whl", hash = "sha256:c9c3d058ebabb74db66e431095118094d06abf53284d9c81f27300d0e0d8bc7c", size = 171804 }, + { url = "https://files.pythonhosted.org/packages/d1/b6/0b0f5ab93b0df4acc49cae758c81fe4e5ef26c3ae2e10cc69249dfd8b3ab/cffi-1.17.1-cp310-cp310-win_amd64.whl", hash = "sha256:0f048dcf80db46f0098ccac01132761580d28e28bc0f78ae0d58048063317e15", size = 181299 }, + { url = "https://files.pythonhosted.org/packages/6b/f4/927e3a8899e52a27fa57a48607ff7dc91a9ebe97399b357b85a0c7892e00/cffi-1.17.1-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:a45e3c6913c5b87b3ff120dcdc03f6131fa0065027d0ed7ee6190736a74cd401", size = 182264 }, + { url = "https://files.pythonhosted.org/packages/6c/f5/6c3a8efe5f503175aaddcbea6ad0d2c96dad6f5abb205750d1b3df44ef29/cffi-1.17.1-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:30c5e0cb5ae493c04c8b42916e52ca38079f1b235c2f8ae5f4527b963c401caf", size = 178651 }, + { url = "https://files.pythonhosted.org/packages/94/dd/a3f0118e688d1b1a57553da23b16bdade96d2f9bcda4d32e7d2838047ff7/cffi-1.17.1-cp311-cp311-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:f75c7ab1f9e4aca5414ed4d8e5c0e303a34f4421f8a0d47a4d019ceff0ab6af4", size = 445259 }, + { url = "https://files.pythonhosted.org/packages/2e/ea/70ce63780f096e16ce8588efe039d3c4f91deb1dc01e9c73a287939c79a6/cffi-1.17.1-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:a1ed2dd2972641495a3ec98445e09766f077aee98a1c896dcb4ad0d303628e41", size = 469200 }, + { url = "https://files.pythonhosted.org/packages/1c/a0/a4fa9f4f781bda074c3ddd57a572b060fa0df7655d2a4247bbe277200146/cffi-1.17.1-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:46bf43160c1a35f7ec506d254e5c890f3c03648a4dbac12d624e4490a7046cd1", size = 477235 }, + { url = "https://files.pythonhosted.org/packages/62/12/ce8710b5b8affbcdd5c6e367217c242524ad17a02fe5beec3ee339f69f85/cffi-1.17.1-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:a24ed04c8ffd54b0729c07cee15a81d964e6fee0e3d4d342a27b020d22959dc6", size = 459721 }, + { url = "https://files.pythonhosted.org/packages/ff/6b/d45873c5e0242196f042d555526f92aa9e0c32355a1be1ff8c27f077fd37/cffi-1.17.1-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:610faea79c43e44c71e1ec53a554553fa22321b65fae24889706c0a84d4ad86d", size = 467242 }, + { url = "https://files.pythonhosted.org/packages/1a/52/d9a0e523a572fbccf2955f5abe883cfa8bcc570d7faeee06336fbd50c9fc/cffi-1.17.1-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:a9b15d491f3ad5d692e11f6b71f7857e7835eb677955c00cc0aefcd0669adaf6", size = 477999 }, + { url = "https://files.pythonhosted.org/packages/44/74/f2a2460684a1a2d00ca799ad880d54652841a780c4c97b87754f660c7603/cffi-1.17.1-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:de2ea4b5833625383e464549fec1bc395c1bdeeb5f25c4a3a82b5a8c756ec22f", size = 454242 }, + { url = "https://files.pythonhosted.org/packages/f8/4a/34599cac7dfcd888ff54e801afe06a19c17787dfd94495ab0c8d35fe99fb/cffi-1.17.1-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:fc48c783f9c87e60831201f2cce7f3b2e4846bf4d8728eabe54d60700b318a0b", size = 478604 }, + { url = "https://files.pythonhosted.org/packages/34/33/e1b8a1ba29025adbdcda5fb3a36f94c03d771c1b7b12f726ff7fef2ebe36/cffi-1.17.1-cp311-cp311-win32.whl", hash = "sha256:85a950a4ac9c359340d5963966e3e0a94a676bd6245a4b55bc43949eee26a655", size = 171727 }, + { url = "https://files.pythonhosted.org/packages/3d/97/50228be003bb2802627d28ec0627837ac0bf35c90cf769812056f235b2d1/cffi-1.17.1-cp311-cp311-win_amd64.whl", hash = "sha256:caaf0640ef5f5517f49bc275eca1406b0ffa6aa184892812030f04c2abf589a0", size = 181400 }, + { url = "https://files.pythonhosted.org/packages/5a/84/e94227139ee5fb4d600a7a4927f322e1d4aea6fdc50bd3fca8493caba23f/cffi-1.17.1-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:805b4371bf7197c329fcb3ead37e710d1bca9da5d583f5073b799d5c5bd1eee4", size = 183178 }, + { url = "https://files.pythonhosted.org/packages/da/ee/fb72c2b48656111c4ef27f0f91da355e130a923473bf5ee75c5643d00cca/cffi-1.17.1-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:733e99bc2df47476e3848417c5a4540522f234dfd4ef3ab7fafdf555b082ec0c", size = 178840 }, + { url = "https://files.pythonhosted.org/packages/cc/b6/db007700f67d151abadf508cbfd6a1884f57eab90b1bb985c4c8c02b0f28/cffi-1.17.1-cp312-cp312-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:1257bdabf294dceb59f5e70c64a3e2f462c30c7ad68092d01bbbfb1c16b1ba36", size = 454803 }, + { url = "https://files.pythonhosted.org/packages/1a/df/f8d151540d8c200eb1c6fba8cd0dfd40904f1b0682ea705c36e6c2e97ab3/cffi-1.17.1-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:da95af8214998d77a98cc14e3a3bd00aa191526343078b530ceb0bd710fb48a5", size = 478850 }, + { url = "https://files.pythonhosted.org/packages/28/c0/b31116332a547fd2677ae5b78a2ef662dfc8023d67f41b2a83f7c2aa78b1/cffi-1.17.1-cp312-cp312-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:d63afe322132c194cf832bfec0dc69a99fb9bb6bbd550f161a49e9e855cc78ff", size = 485729 }, + { url = "https://files.pythonhosted.org/packages/91/2b/9a1ddfa5c7f13cab007a2c9cc295b70fbbda7cb10a286aa6810338e60ea1/cffi-1.17.1-cp312-cp312-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:f79fc4fc25f1c8698ff97788206bb3c2598949bfe0fef03d299eb1b5356ada99", size = 471256 }, + { url = "https://files.pythonhosted.org/packages/b2/d5/da47df7004cb17e4955df6a43d14b3b4ae77737dff8bf7f8f333196717bf/cffi-1.17.1-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:b62ce867176a75d03a665bad002af8e6d54644fad99a3c70905c543130e39d93", size = 479424 }, + { url = "https://files.pythonhosted.org/packages/0b/ac/2a28bcf513e93a219c8a4e8e125534f4f6db03e3179ba1c45e949b76212c/cffi-1.17.1-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:386c8bf53c502fff58903061338ce4f4950cbdcb23e2902d86c0f722b786bbe3", size = 484568 }, + { url = "https://files.pythonhosted.org/packages/d4/38/ca8a4f639065f14ae0f1d9751e70447a261f1a30fa7547a828ae08142465/cffi-1.17.1-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:4ceb10419a9adf4460ea14cfd6bc43d08701f0835e979bf821052f1805850fe8", size = 488736 }, + { url = "https://files.pythonhosted.org/packages/86/c5/28b2d6f799ec0bdecf44dced2ec5ed43e0eb63097b0f58c293583b406582/cffi-1.17.1-cp312-cp312-win32.whl", hash = "sha256:a08d7e755f8ed21095a310a693525137cfe756ce62d066e53f502a83dc550f65", size = 172448 }, + { url = "https://files.pythonhosted.org/packages/50/b9/db34c4755a7bd1cb2d1603ac3863f22bcecbd1ba29e5ee841a4bc510b294/cffi-1.17.1-cp312-cp312-win_amd64.whl", hash = "sha256:51392eae71afec0d0c8fb1a53b204dbb3bcabcb3c9b807eedf3e1e6ccf2de903", size = 181976 }, + { url = "https://files.pythonhosted.org/packages/8d/f8/dd6c246b148639254dad4d6803eb6a54e8c85c6e11ec9df2cffa87571dbe/cffi-1.17.1-cp313-cp313-macosx_10_13_x86_64.whl", hash = "sha256:f3a2b4222ce6b60e2e8b337bb9596923045681d71e5a082783484d845390938e", size = 182989 }, + { url = "https://files.pythonhosted.org/packages/8b/f1/672d303ddf17c24fc83afd712316fda78dc6fce1cd53011b839483e1ecc8/cffi-1.17.1-cp313-cp313-macosx_11_0_arm64.whl", hash = "sha256:0984a4925a435b1da406122d4d7968dd861c1385afe3b45ba82b750f229811e2", size = 178802 }, + { url = "https://files.pythonhosted.org/packages/0e/2d/eab2e858a91fdff70533cab61dcff4a1f55ec60425832ddfdc9cd36bc8af/cffi-1.17.1-cp313-cp313-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:d01b12eeeb4427d3110de311e1774046ad344f5b1a7403101878976ecd7a10f3", size = 454792 }, + { url = "https://files.pythonhosted.org/packages/75/b2/fbaec7c4455c604e29388d55599b99ebcc250a60050610fadde58932b7ee/cffi-1.17.1-cp313-cp313-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:706510fe141c86a69c8ddc029c7910003a17353970cff3b904ff0686a5927683", size = 478893 }, + { url = "https://files.pythonhosted.org/packages/4f/b7/6e4a2162178bf1935c336d4da8a9352cccab4d3a5d7914065490f08c0690/cffi-1.17.1-cp313-cp313-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:de55b766c7aa2e2a3092c51e0483d700341182f08e67c63630d5b6f200bb28e5", size = 485810 }, + { url = "https://files.pythonhosted.org/packages/c7/8a/1d0e4a9c26e54746dc08c2c6c037889124d4f59dffd853a659fa545f1b40/cffi-1.17.1-cp313-cp313-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:c59d6e989d07460165cc5ad3c61f9fd8f1b4796eacbd81cee78957842b834af4", size = 471200 }, + { url = "https://files.pythonhosted.org/packages/26/9f/1aab65a6c0db35f43c4d1b4f580e8df53914310afc10ae0397d29d697af4/cffi-1.17.1-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:dd398dbc6773384a17fe0d3e7eeb8d1a21c2200473ee6806bb5e6a8e62bb73dd", size = 479447 }, + { url = "https://files.pythonhosted.org/packages/5f/e4/fb8b3dd8dc0e98edf1135ff067ae070bb32ef9d509d6cb0f538cd6f7483f/cffi-1.17.1-cp313-cp313-musllinux_1_1_aarch64.whl", hash = "sha256:3edc8d958eb099c634dace3c7e16560ae474aa3803a5df240542b305d14e14ed", size = 484358 }, + { url = "https://files.pythonhosted.org/packages/f1/47/d7145bf2dc04684935d57d67dff9d6d795b2ba2796806bb109864be3a151/cffi-1.17.1-cp313-cp313-musllinux_1_1_x86_64.whl", hash = "sha256:72e72408cad3d5419375fc87d289076ee319835bdfa2caad331e377589aebba9", size = 488469 }, + { url = "https://files.pythonhosted.org/packages/bf/ee/f94057fa6426481d663b88637a9a10e859e492c73d0384514a17d78ee205/cffi-1.17.1-cp313-cp313-win32.whl", hash = "sha256:e03eab0a8677fa80d646b5ddece1cbeaf556c313dcfac435ba11f107ba117b5d", size = 172475 }, + { url = "https://files.pythonhosted.org/packages/7c/fc/6a8cb64e5f0324877d503c854da15d76c1e50eb722e320b15345c4d0c6de/cffi-1.17.1-cp313-cp313-win_amd64.whl", hash = "sha256:f6a16c31041f09ead72d69f583767292f750d24913dadacf5756b966aacb3f1a", size = 182009 }, + { url = "https://files.pythonhosted.org/packages/48/08/15bf6b43ae9bd06f6b00ad8a91f5a8fe1069d4c9fab550a866755402724e/cffi-1.17.1-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:636062ea65bd0195bc012fea9321aca499c0504409f413dc88af450b57ffd03b", size = 182457 }, + { url = "https://files.pythonhosted.org/packages/c2/5b/f1523dd545f92f7df468e5f653ffa4df30ac222f3c884e51e139878f1cb5/cffi-1.17.1-cp38-cp38-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:c7eac2ef9b63c79431bc4b25f1cd649d7f061a28808cbc6c47b534bd789ef964", size = 425932 }, + { url = "https://files.pythonhosted.org/packages/53/93/7e547ab4105969cc8c93b38a667b82a835dd2cc78f3a7dad6130cfd41e1d/cffi-1.17.1-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e221cf152cff04059d011ee126477f0d9588303eb57e88923578ace7baad17f9", size = 448585 }, + { url = "https://files.pythonhosted.org/packages/56/c4/a308f2c332006206bb511de219efeff090e9d63529ba0a77aae72e82248b/cffi-1.17.1-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:31000ec67d4221a71bd3f67df918b1f88f676f1c3b535a7eb473255fdc0b83fc", size = 456268 }, + { url = "https://files.pythonhosted.org/packages/ca/5b/b63681518265f2f4060d2b60755c1c77ec89e5e045fc3773b72735ddaad5/cffi-1.17.1-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:6f17be4345073b0a7b8ea599688f692ac3ef23ce28e5df79c04de519dbc4912c", size = 436592 }, + { url = "https://files.pythonhosted.org/packages/bb/19/b51af9f4a4faa4a8ac5a0e5d5c2522dcd9703d07fac69da34a36c4d960d3/cffi-1.17.1-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:0e2b1fac190ae3ebfe37b979cc1ce69c81f4e4fe5746bb401dca63a9062cdaf1", size = 446512 }, + { url = "https://files.pythonhosted.org/packages/e2/63/2bed8323890cb613bbecda807688a31ed11a7fe7afe31f8faaae0206a9a3/cffi-1.17.1-cp38-cp38-win32.whl", hash = "sha256:7596d6620d3fa590f677e9ee430df2958d2d6d6de2feeae5b20e82c00b76fbf8", size = 171576 }, + { url = "https://files.pythonhosted.org/packages/2f/70/80c33b044ebc79527447fd4fbc5455d514c3bb840dede4455de97da39b4d/cffi-1.17.1-cp38-cp38-win_amd64.whl", hash = "sha256:78122be759c3f8a014ce010908ae03364d00a1f81ab5c7f4a7a5120607ea56e1", size = 181229 }, + { url = "https://files.pythonhosted.org/packages/b9/ea/8bb50596b8ffbc49ddd7a1ad305035daa770202a6b782fc164647c2673ad/cffi-1.17.1-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:b2ab587605f4ba0bf81dc0cb08a41bd1c0a5906bd59243d56bad7668a6fc6c16", size = 182220 }, + { url = "https://files.pythonhosted.org/packages/ae/11/e77c8cd24f58285a82c23af484cf5b124a376b32644e445960d1a4654c3a/cffi-1.17.1-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:28b16024becceed8c6dfbc75629e27788d8a3f9030691a1dbf9821a128b22c36", size = 178605 }, + { url = "https://files.pythonhosted.org/packages/ed/65/25a8dc32c53bf5b7b6c2686b42ae2ad58743f7ff644844af7cdb29b49361/cffi-1.17.1-cp39-cp39-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:1d599671f396c4723d016dbddb72fe8e0397082b0a77a4fab8028923bec050e8", size = 424910 }, + { url = "https://files.pythonhosted.org/packages/42/7a/9d086fab7c66bd7c4d0f27c57a1b6b068ced810afc498cc8c49e0088661c/cffi-1.17.1-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ca74b8dbe6e8e8263c0ffd60277de77dcee6c837a3d0881d8c1ead7268c9e576", size = 447200 }, + { url = "https://files.pythonhosted.org/packages/da/63/1785ced118ce92a993b0ec9e0d0ac8dc3e5dbfbcaa81135be56c69cabbb6/cffi-1.17.1-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:f7f5baafcc48261359e14bcd6d9bff6d4b28d9103847c9e136694cb0501aef87", size = 454565 }, + { url = "https://files.pythonhosted.org/packages/74/06/90b8a44abf3556599cdec107f7290277ae8901a58f75e6fe8f970cd72418/cffi-1.17.1-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:98e3969bcff97cae1b2def8ba499ea3d6f31ddfdb7635374834cf89a1a08ecf0", size = 435635 }, + { url = "https://files.pythonhosted.org/packages/bd/62/a1f468e5708a70b1d86ead5bab5520861d9c7eacce4a885ded9faa7729c3/cffi-1.17.1-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:cdf5ce3acdfd1661132f2a9c19cac174758dc2352bfe37d98aa7512c6b7178b3", size = 445218 }, + { url = "https://files.pythonhosted.org/packages/5b/95/b34462f3ccb09c2594aa782d90a90b045de4ff1f70148ee79c69d37a0a5a/cffi-1.17.1-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:9755e4345d1ec879e3849e62222a18c7174d65a6a92d5b346b1863912168b595", size = 460486 }, + { url = "https://files.pythonhosted.org/packages/fc/fc/a1e4bebd8d680febd29cf6c8a40067182b64f00c7d105f8f26b5bc54317b/cffi-1.17.1-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:f1e22e8c4419538cb197e4dd60acc919d7696e5ef98ee4da4e01d3f8cfa4cc5a", size = 437911 }, + { url = "https://files.pythonhosted.org/packages/e6/c3/21cab7a6154b6a5ea330ae80de386e7665254835b9e98ecc1340b3a7de9a/cffi-1.17.1-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:c03e868a0b3bc35839ba98e74211ed2b05d2119be4e8a0f224fba9384f1fe02e", size = 460632 }, + { url = "https://files.pythonhosted.org/packages/cb/b5/fd9f8b5a84010ca169ee49f4e4ad6f8c05f4e3545b72ee041dbbcb159882/cffi-1.17.1-cp39-cp39-win32.whl", hash = "sha256:e31ae45bc2e29f6b2abd0de1cc3b9d5205aa847cafaecb8af1476a609a2f6eb7", size = 171820 }, + { url = "https://files.pythonhosted.org/packages/8c/52/b08750ce0bce45c143e1b5d7357ee8c55341b52bdef4b0f081af1eb248c2/cffi-1.17.1-cp39-cp39-win_amd64.whl", hash = "sha256:d016c76bdd850f3c626af19b0542c9677ba156e4ee4fccfdd7848803533ef662", size = 181290 }, +] + +[[package]] +name = "charset-normalizer" +version = "3.3.2" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/63/09/c1bc53dab74b1816a00d8d030de5bf98f724c52c1635e07681d312f20be8/charset-normalizer-3.3.2.tar.gz", hash = "sha256:f30c3cb33b24454a82faecaf01b19c18562b1e89558fb6c56de4d9118a032fd5", size = 104809 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/2b/61/095a0aa1a84d1481998b534177c8566fdc50bb1233ea9a0478cd3cc075bd/charset_normalizer-3.3.2-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:25baf083bf6f6b341f4121c2f3c548875ee6f5339300e08be3f2b2ba1721cdd3", size = 194219 }, + { url = "https://files.pythonhosted.org/packages/cc/94/f7cf5e5134175de79ad2059edf2adce18e0685ebdb9227ff0139975d0e93/charset_normalizer-3.3.2-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:06435b539f889b1f6f4ac1758871aae42dc3a8c0e24ac9e60c2384973ad73027", size = 122521 }, + { url = "https://files.pythonhosted.org/packages/46/6a/d5c26c41c49b546860cc1acabdddf48b0b3fb2685f4f5617ac59261b44ae/charset_normalizer-3.3.2-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:9063e24fdb1e498ab71cb7419e24622516c4a04476b17a2dab57e8baa30d6e03", size = 120383 }, + { url = "https://files.pythonhosted.org/packages/b8/60/e2f67915a51be59d4539ed189eb0a2b0d292bf79270410746becb32bc2c3/charset_normalizer-3.3.2-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:6897af51655e3691ff853668779c7bad41579facacf5fd7253b0133308cf000d", size = 138223 }, + { url = "https://files.pythonhosted.org/packages/05/8c/eb854996d5fef5e4f33ad56927ad053d04dc820e4a3d39023f35cad72617/charset_normalizer-3.3.2-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:1d3193f4a680c64b4b6a9115943538edb896edc190f0b222e73761716519268e", size = 148101 }, + { url = "https://files.pythonhosted.org/packages/f6/93/bb6cbeec3bf9da9b2eba458c15966658d1daa8b982c642f81c93ad9b40e1/charset_normalizer-3.3.2-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:cd70574b12bb8a4d2aaa0094515df2463cb429d8536cfb6c7ce983246983e5a6", size = 140699 }, + { url = "https://files.pythonhosted.org/packages/da/f1/3702ba2a7470666a62fd81c58a4c40be00670e5006a67f4d626e57f013ae/charset_normalizer-3.3.2-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:8465322196c8b4d7ab6d1e049e4c5cb460d0394da4a27d23cc242fbf0034b6b5", size = 142065 }, + { url = "https://files.pythonhosted.org/packages/3f/ba/3f5e7be00b215fa10e13d64b1f6237eb6ebea66676a41b2bcdd09fe74323/charset_normalizer-3.3.2-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:a9a8e9031d613fd2009c182b69c7b2c1ef8239a0efb1df3f7c8da66d5dd3d537", size = 144505 }, + { url = "https://files.pythonhosted.org/packages/33/c3/3b96a435c5109dd5b6adc8a59ba1d678b302a97938f032e3770cc84cd354/charset_normalizer-3.3.2-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:beb58fe5cdb101e3a055192ac291b7a21e3b7ef4f67fa1d74e331a7f2124341c", size = 139425 }, + { url = "https://files.pythonhosted.org/packages/43/05/3bf613e719efe68fb3a77f9c536a389f35b95d75424b96b426a47a45ef1d/charset_normalizer-3.3.2-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:e06ed3eb3218bc64786f7db41917d4e686cc4856944f53d5bdf83a6884432e12", size = 145287 }, + { url = "https://files.pythonhosted.org/packages/58/78/a0bc646900994df12e07b4ae5c713f2b3e5998f58b9d3720cce2aa45652f/charset_normalizer-3.3.2-cp310-cp310-musllinux_1_1_ppc64le.whl", hash = "sha256:2e81c7b9c8979ce92ed306c249d46894776a909505d8f5a4ba55b14206e3222f", size = 149929 }, + { url = "https://files.pythonhosted.org/packages/eb/5c/97d97248af4920bc68687d9c3b3c0f47c910e21a8ff80af4565a576bd2f0/charset_normalizer-3.3.2-cp310-cp310-musllinux_1_1_s390x.whl", hash = "sha256:572c3763a264ba47b3cf708a44ce965d98555f618ca42c926a9c1616d8f34269", size = 141605 }, + { url = "https://files.pythonhosted.org/packages/a8/31/47d018ef89f95b8aded95c589a77c072c55e94b50a41aa99c0a2008a45a4/charset_normalizer-3.3.2-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:fd1abc0d89e30cc4e02e4064dc67fcc51bd941eb395c502aac3ec19fab46b519", size = 142646 }, + { url = "https://files.pythonhosted.org/packages/ae/d5/4fecf1d58bedb1340a50f165ba1c7ddc0400252d6832ff619c4568b36cc0/charset_normalizer-3.3.2-cp310-cp310-win32.whl", hash = "sha256:3d47fa203a7bd9c5b6cee4736ee84ca03b8ef23193c0d1ca99b5089f72645c73", size = 92846 }, + { url = "https://files.pythonhosted.org/packages/a2/a0/4af29e22cb5942488cf45630cbdd7cefd908768e69bdd90280842e4e8529/charset_normalizer-3.3.2-cp310-cp310-win_amd64.whl", hash = "sha256:10955842570876604d404661fbccbc9c7e684caf432c09c715ec38fbae45ae09", size = 100343 }, + { url = "https://files.pythonhosted.org/packages/68/77/02839016f6fbbf808e8b38601df6e0e66c17bbab76dff4613f7511413597/charset_normalizer-3.3.2-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:802fe99cca7457642125a8a88a084cef28ff0cf9407060f7b93dca5aa25480db", size = 191647 }, + { url = "https://files.pythonhosted.org/packages/3e/33/21a875a61057165e92227466e54ee076b73af1e21fe1b31f1e292251aa1e/charset_normalizer-3.3.2-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:573f6eac48f4769d667c4442081b1794f52919e7edada77495aaed9236d13a96", size = 121434 }, + { url = "https://files.pythonhosted.org/packages/dd/51/68b61b90b24ca35495956b718f35a9756ef7d3dd4b3c1508056fa98d1a1b/charset_normalizer-3.3.2-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:549a3a73da901d5bc3ce8d24e0600d1fa85524c10287f6004fbab87672bf3e1e", size = 118979 }, + { url = "https://files.pythonhosted.org/packages/e4/a6/7ee57823d46331ddc37dd00749c95b0edec2c79b15fc0d6e6efb532e89ac/charset_normalizer-3.3.2-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:f27273b60488abe721a075bcca6d7f3964f9f6f067c8c4c605743023d7d3944f", size = 136582 }, + { url = "https://files.pythonhosted.org/packages/74/f1/0d9fe69ac441467b737ba7f48c68241487df2f4522dd7246d9426e7c690e/charset_normalizer-3.3.2-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:1ceae2f17a9c33cb48e3263960dc5fc8005351ee19db217e9b1bb15d28c02574", size = 146645 }, + { url = "https://files.pythonhosted.org/packages/05/31/e1f51c76db7be1d4aef220d29fbfa5dbb4a99165d9833dcbf166753b6dc0/charset_normalizer-3.3.2-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:65f6f63034100ead094b8744b3b97965785388f308a64cf8d7c34f2f2e5be0c4", size = 139398 }, + { url = "https://files.pythonhosted.org/packages/40/26/f35951c45070edc957ba40a5b1db3cf60a9dbb1b350c2d5bef03e01e61de/charset_normalizer-3.3.2-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:753f10e867343b4511128c6ed8c82f7bec3bd026875576dfd88483c5c73b2fd8", size = 140273 }, + { url = "https://files.pythonhosted.org/packages/07/07/7e554f2bbce3295e191f7e653ff15d55309a9ca40d0362fcdab36f01063c/charset_normalizer-3.3.2-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:4a78b2b446bd7c934f5dcedc588903fb2f5eec172f3d29e52a9096a43722adfc", size = 142577 }, + { url = "https://files.pythonhosted.org/packages/d8/b5/eb705c313100defa57da79277d9207dc8d8e45931035862fa64b625bfead/charset_normalizer-3.3.2-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:e537484df0d8f426ce2afb2d0f8e1c3d0b114b83f8850e5f2fbea0e797bd82ae", size = 137747 }, + { url = "https://files.pythonhosted.org/packages/19/28/573147271fd041d351b438a5665be8223f1dd92f273713cb882ddafe214c/charset_normalizer-3.3.2-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:eb6904c354526e758fda7167b33005998fb68c46fbc10e013ca97f21ca5c8887", size = 143375 }, + { url = "https://files.pythonhosted.org/packages/cf/7c/f3b682fa053cc21373c9a839e6beba7705857075686a05c72e0f8c4980ca/charset_normalizer-3.3.2-cp311-cp311-musllinux_1_1_ppc64le.whl", hash = "sha256:deb6be0ac38ece9ba87dea880e438f25ca3eddfac8b002a2ec3d9183a454e8ae", size = 148474 }, + { url = "https://files.pythonhosted.org/packages/1e/49/7ab74d4ac537ece3bc3334ee08645e231f39f7d6df6347b29a74b0537103/charset_normalizer-3.3.2-cp311-cp311-musllinux_1_1_s390x.whl", hash = "sha256:4ab2fe47fae9e0f9dee8c04187ce5d09f48eabe611be8259444906793ab7cbce", size = 140232 }, + { url = "https://files.pythonhosted.org/packages/2d/dc/9dacba68c9ac0ae781d40e1a0c0058e26302ea0660e574ddf6797a0347f7/charset_normalizer-3.3.2-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:80402cd6ee291dcb72644d6eac93785fe2c8b9cb30893c1af5b8fdd753b9d40f", size = 140859 }, + { url = "https://files.pythonhosted.org/packages/6c/c2/4a583f800c0708dd22096298e49f887b49d9746d0e78bfc1d7e29816614c/charset_normalizer-3.3.2-cp311-cp311-win32.whl", hash = "sha256:7cd13a2e3ddeed6913a65e66e94b51d80a041145a026c27e6bb76c31a853c6ab", size = 92509 }, + { url = "https://files.pythonhosted.org/packages/57/ec/80c8d48ac8b1741d5b963797b7c0c869335619e13d4744ca2f67fc11c6fc/charset_normalizer-3.3.2-cp311-cp311-win_amd64.whl", hash = "sha256:663946639d296df6a2bb2aa51b60a2454ca1cb29835324c640dafb5ff2131a77", size = 99870 }, + { url = "https://files.pythonhosted.org/packages/d1/b2/fcedc8255ec42afee97f9e6f0145c734bbe104aac28300214593eb326f1d/charset_normalizer-3.3.2-cp312-cp312-macosx_10_9_universal2.whl", hash = "sha256:0b2b64d2bb6d3fb9112bafa732def486049e63de9618b5843bcdd081d8144cd8", size = 192892 }, + { url = "https://files.pythonhosted.org/packages/2e/7d/2259318c202f3d17f3fe6438149b3b9e706d1070fe3fcbb28049730bb25c/charset_normalizer-3.3.2-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:ddbb2551d7e0102e7252db79ba445cdab71b26640817ab1e3e3648dad515003b", size = 122213 }, + { url = "https://files.pythonhosted.org/packages/3a/52/9f9d17c3b54dc238de384c4cb5a2ef0e27985b42a0e5cc8e8a31d918d48d/charset_normalizer-3.3.2-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:55086ee1064215781fff39a1af09518bc9255b50d6333f2e4c74ca09fac6a8f6", size = 119404 }, + { url = "https://files.pythonhosted.org/packages/99/b0/9c365f6d79a9f0f3c379ddb40a256a67aa69c59609608fe7feb6235896e1/charset_normalizer-3.3.2-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8f4a014bc36d3c57402e2977dada34f9c12300af536839dc38c0beab8878f38a", size = 137275 }, + { url = "https://files.pythonhosted.org/packages/91/33/749df346e93d7a30cdcb90cbfdd41a06026317bfbfb62cd68307c1a3c543/charset_normalizer-3.3.2-cp312-cp312-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:a10af20b82360ab00827f916a6058451b723b4e65030c5a18577c8b2de5b3389", size = 147518 }, + { url = "https://files.pythonhosted.org/packages/72/1a/641d5c9f59e6af4c7b53da463d07600a695b9824e20849cb6eea8a627761/charset_normalizer-3.3.2-cp312-cp312-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:8d756e44e94489e49571086ef83b2bb8ce311e730092d2c34ca8f7d925cb20aa", size = 140182 }, + { url = "https://files.pythonhosted.org/packages/ee/fb/14d30eb4956408ee3ae09ad34299131fb383c47df355ddb428a7331cfa1e/charset_normalizer-3.3.2-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:90d558489962fd4918143277a773316e56c72da56ec7aa3dc3dbbe20fdfed15b", size = 141869 }, + { url = "https://files.pythonhosted.org/packages/df/3e/a06b18788ca2eb6695c9b22325b6fde7dde0f1d1838b1792a0076f58fe9d/charset_normalizer-3.3.2-cp312-cp312-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:6ac7ffc7ad6d040517be39eb591cac5ff87416c2537df6ba3cba3bae290c0fed", size = 144042 }, + { url = "https://files.pythonhosted.org/packages/45/59/3d27019d3b447a88fe7e7d004a1e04be220227760264cc41b405e863891b/charset_normalizer-3.3.2-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:7ed9e526742851e8d5cc9e6cf41427dfc6068d4f5a3bb03659444b4cabf6bc26", size = 138275 }, + { url = "https://files.pythonhosted.org/packages/7b/ef/5eb105530b4da8ae37d506ccfa25057961b7b63d581def6f99165ea89c7e/charset_normalizer-3.3.2-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:8bdb58ff7ba23002a4c5808d608e4e6c687175724f54a5dade5fa8c67b604e4d", size = 144819 }, + { url = "https://files.pythonhosted.org/packages/a2/51/e5023f937d7f307c948ed3e5c29c4b7a3e42ed2ee0b8cdf8f3a706089bf0/charset_normalizer-3.3.2-cp312-cp312-musllinux_1_1_ppc64le.whl", hash = "sha256:6b3251890fff30ee142c44144871185dbe13b11bab478a88887a639655be1068", size = 149415 }, + { url = "https://files.pythonhosted.org/packages/24/9d/2e3ef673dfd5be0154b20363c5cdcc5606f35666544381bee15af3778239/charset_normalizer-3.3.2-cp312-cp312-musllinux_1_1_s390x.whl", hash = "sha256:b4a23f61ce87adf89be746c8a8974fe1c823c891d8f86eb218bb957c924bb143", size = 141212 }, + { url = "https://files.pythonhosted.org/packages/5b/ae/ce2c12fcac59cb3860b2e2d76dc405253a4475436b1861d95fe75bdea520/charset_normalizer-3.3.2-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:efcb3f6676480691518c177e3b465bcddf57cea040302f9f4e6e191af91174d4", size = 142167 }, + { url = "https://files.pythonhosted.org/packages/ed/3a/a448bf035dce5da359daf9ae8a16b8a39623cc395a2ffb1620aa1bce62b0/charset_normalizer-3.3.2-cp312-cp312-win32.whl", hash = "sha256:d965bba47ddeec8cd560687584e88cf699fd28f192ceb452d1d7ee807c5597b7", size = 93041 }, + { url = "https://files.pythonhosted.org/packages/b6/7c/8debebb4f90174074b827c63242c23851bdf00a532489fba57fef3416e40/charset_normalizer-3.3.2-cp312-cp312-win_amd64.whl", hash = "sha256:96b02a3dc4381e5494fad39be677abcb5e6634bf7b4fa83a6dd3112607547001", size = 100397 }, + { url = "https://files.pythonhosted.org/packages/ef/d4/a1d72a8f6aa754fdebe91b848912025d30ab7dced61e9ed8aabbf791ed65/charset_normalizer-3.3.2-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:6463effa3186ea09411d50efc7d85360b38d5f09b870c48e4600f63af490e56a", size = 191415 }, + { url = "https://files.pythonhosted.org/packages/13/82/83c188028b6f38d39538442dd127dc794c602ae6d45d66c469f4063a4c30/charset_normalizer-3.3.2-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:6c4caeef8fa63d06bd437cd4bdcf3ffefe6738fb1b25951440d80dc7df8c03ac", size = 121051 }, + { url = "https://files.pythonhosted.org/packages/16/ea/a9e284aa38cccea06b7056d4cbc7adf37670b1f8a668a312864abf1ff7c6/charset_normalizer-3.3.2-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:37e55c8e51c236f95b033f6fb391d7d7970ba5fe7ff453dad675e88cf303377a", size = 119143 }, + { url = "https://files.pythonhosted.org/packages/34/2a/f392457d45e24a0c9bfc012887ed4f3c54bf5d4d05a5deb970ffec4b7fc0/charset_normalizer-3.3.2-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:fb69256e180cb6c8a894fee62b3afebae785babc1ee98b81cdf68bbca1987f33", size = 137506 }, + { url = "https://files.pythonhosted.org/packages/be/4d/9e370f8281cec2fcc9452c4d1ac513324c32957c5f70c73dd2fa8442a21a/charset_normalizer-3.3.2-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:ae5f4161f18c61806f411a13b0310bea87f987c7d2ecdbdaad0e94eb2e404238", size = 147272 }, + { url = "https://files.pythonhosted.org/packages/33/95/ef68482e4a6adf781fae8d183fb48d6f2be8facb414f49c90ba6a5149cd1/charset_normalizer-3.3.2-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:b2b0a0c0517616b6869869f8c581d4eb2dd83a4d79e0ebcb7d373ef9956aeb0a", size = 139734 }, + { url = "https://files.pythonhosted.org/packages/3d/09/d82fe4a34c5f0585f9ea1df090e2a71eb9bb1e469723053e1ee9f57c16f3/charset_normalizer-3.3.2-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:45485e01ff4d3630ec0d9617310448a8702f70e9c01906b0d0118bdf9d124cf2", size = 141094 }, + { url = "https://files.pythonhosted.org/packages/81/b2/160893421adfa3c45554fb418e321ed342bb10c0a4549e855b2b2a3699cb/charset_normalizer-3.3.2-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:eb00ed941194665c332bf8e078baf037d6c35d7c4f3102ea2d4f16ca94a26dc8", size = 144113 }, + { url = "https://files.pythonhosted.org/packages/9e/ef/cd47a63d3200b232792e361cd67530173a09eb011813478b1c0fb8aa7226/charset_normalizer-3.3.2-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:2127566c664442652f024c837091890cb1942c30937add288223dc895793f898", size = 138555 }, + { url = "https://files.pythonhosted.org/packages/a8/6f/4ff299b97da2ed6358154b6eb3a2db67da2ae204e53d205aacb18a7e4f34/charset_normalizer-3.3.2-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:a50aebfa173e157099939b17f18600f72f84eed3049e743b68ad15bd69b6bf99", size = 144944 }, + { url = "https://files.pythonhosted.org/packages/d1/2f/0d1efd07c74c52b6886c32a3b906fb8afd2fecf448650e73ecb90a5a27f1/charset_normalizer-3.3.2-cp38-cp38-musllinux_1_1_ppc64le.whl", hash = "sha256:4d0d1650369165a14e14e1e47b372cfcb31d6ab44e6e33cb2d4e57265290044d", size = 148925 }, + { url = "https://files.pythonhosted.org/packages/bd/28/7ea29e73eea52c7e15b4b9108d0743fc9e4cc2cdb00d275af1df3d46d360/charset_normalizer-3.3.2-cp38-cp38-musllinux_1_1_s390x.whl", hash = "sha256:923c0c831b7cfcb071580d3f46c4baf50f174be571576556269530f4bbd79d04", size = 140732 }, + { url = "https://files.pythonhosted.org/packages/b3/c1/ebca8e87c714a6a561cfee063f0655f742e54b8ae6e78151f60ba8708b3a/charset_normalizer-3.3.2-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:06a81e93cd441c56a9b65d8e1d043daeb97a3d0856d177d5c90ba85acb3db087", size = 141288 }, + { url = "https://files.pythonhosted.org/packages/74/20/8923a06f15eb3d7f6a306729360bd58f9ead1dc39bc7ea8831f4b407e4ae/charset_normalizer-3.3.2-cp38-cp38-win32.whl", hash = "sha256:6ef1d82a3af9d3eecdba2321dc1b3c238245d890843e040e41e470ffa64c3e25", size = 92373 }, + { url = "https://files.pythonhosted.org/packages/db/fb/d29e343e7c57bbf1231275939f6e75eb740cd47a9d7cb2c52ffeb62ef869/charset_normalizer-3.3.2-cp38-cp38-win_amd64.whl", hash = "sha256:eb8821e09e916165e160797a6c17edda0679379a4be5c716c260e836e122f54b", size = 99577 }, + { url = "https://files.pythonhosted.org/packages/f7/9d/bcf4a449a438ed6f19790eee543a86a740c77508fbc5ddab210ab3ba3a9a/charset_normalizer-3.3.2-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:c235ebd9baae02f1b77bcea61bce332cb4331dc3617d254df3323aa01ab47bd4", size = 194198 }, + { url = "https://files.pythonhosted.org/packages/66/fe/c7d3da40a66a6bf2920cce0f436fa1f62ee28aaf92f412f0bf3b84c8ad6c/charset_normalizer-3.3.2-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:5b4c145409bef602a690e7cfad0a15a55c13320ff7a3ad7ca59c13bb8ba4d45d", size = 122494 }, + { url = "https://files.pythonhosted.org/packages/2a/9d/a6d15bd1e3e2914af5955c8eb15f4071997e7078419328fee93dfd497eb7/charset_normalizer-3.3.2-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:68d1f8a9e9e37c1223b656399be5d6b448dea850bed7d0f87a8311f1ff3dabb0", size = 120393 }, + { url = "https://files.pythonhosted.org/packages/3d/85/5b7416b349609d20611a64718bed383b9251b5a601044550f0c8983b8900/charset_normalizer-3.3.2-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:22afcb9f253dac0696b5a4be4a1c0f8762f8239e21b99680099abd9b2b1b2269", size = 138331 }, + { url = "https://files.pythonhosted.org/packages/79/66/8946baa705c588521afe10b2d7967300e49380ded089a62d38537264aece/charset_normalizer-3.3.2-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:e27ad930a842b4c5eb8ac0016b0a54f5aebbe679340c26101df33424142c143c", size = 148097 }, + { url = "https://files.pythonhosted.org/packages/44/80/b339237b4ce635b4af1c73742459eee5f97201bd92b2371c53e11958392e/charset_normalizer-3.3.2-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:1f79682fbe303db92bc2b1136016a38a42e835d932bab5b3b1bfcfbf0640e519", size = 140711 }, + { url = "https://files.pythonhosted.org/packages/98/69/5d8751b4b670d623aa7a47bef061d69c279e9f922f6705147983aa76c3ce/charset_normalizer-3.3.2-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:b261ccdec7821281dade748d088bb6e9b69e6d15b30652b74cbbac25e280b796", size = 142251 }, + { url = "https://files.pythonhosted.org/packages/1f/8d/33c860a7032da5b93382cbe2873261f81467e7b37f4ed91e25fed62fd49b/charset_normalizer-3.3.2-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:122c7fa62b130ed55f8f285bfd56d5f4b4a5b503609d181f9ad85e55c89f4185", size = 144636 }, + { url = "https://files.pythonhosted.org/packages/c2/65/52aaf47b3dd616c11a19b1052ce7fa6321250a7a0b975f48d8c366733b9f/charset_normalizer-3.3.2-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:d0eccceffcb53201b5bfebb52600a5fb483a20b61da9dbc885f8b103cbe7598c", size = 139514 }, + { url = "https://files.pythonhosted.org/packages/51/fd/0ee5b1c2860bb3c60236d05b6e4ac240cf702b67471138571dad91bcfed8/charset_normalizer-3.3.2-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:9f96df6923e21816da7e0ad3fd47dd8f94b2a5ce594e00677c0013018b813458", size = 145528 }, + { url = "https://files.pythonhosted.org/packages/e1/9c/60729bf15dc82e3aaf5f71e81686e42e50715a1399770bcde1a9e43d09db/charset_normalizer-3.3.2-cp39-cp39-musllinux_1_1_ppc64le.whl", hash = "sha256:7f04c839ed0b6b98b1a7501a002144b76c18fb1c1850c8b98d458ac269e26ed2", size = 149804 }, + { url = "https://files.pythonhosted.org/packages/53/cd/aa4b8a4d82eeceb872f83237b2d27e43e637cac9ffaef19a1321c3bafb67/charset_normalizer-3.3.2-cp39-cp39-musllinux_1_1_s390x.whl", hash = "sha256:34d1c8da1e78d2e001f363791c98a272bb734000fcef47a491c1e3b0505657a8", size = 141708 }, + { url = "https://files.pythonhosted.org/packages/54/7f/cad0b328759630814fcf9d804bfabaf47776816ad4ef2e9938b7e1123d04/charset_normalizer-3.3.2-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:ff8fa367d09b717b2a17a052544193ad76cd49979c805768879cb63d9ca50561", size = 142708 }, + { url = "https://files.pythonhosted.org/packages/c1/9d/254a2f1bcb0ce9acad838e94ed05ba71a7cb1e27affaa4d9e1ca3958cdb6/charset_normalizer-3.3.2-cp39-cp39-win32.whl", hash = "sha256:aed38f6e4fb3f5d6bf81bfa990a07806be9d83cf7bacef998ab1a9bd660a581f", size = 92830 }, + { url = "https://files.pythonhosted.org/packages/2f/0e/d7303ccae9735ff8ff01e36705ad6233ad2002962e8668a970fc000c5e1b/charset_normalizer-3.3.2-cp39-cp39-win_amd64.whl", hash = "sha256:b01b88d45a6fcb69667cd6d2f7a9aeb4bf53760d7fc536bf679ec94fe9f3ff3d", size = 100376 }, + { url = "https://files.pythonhosted.org/packages/28/76/e6222113b83e3622caa4bb41032d0b1bf785250607392e1b778aca0b8a7d/charset_normalizer-3.3.2-py3-none-any.whl", hash = "sha256:3e4d1f6587322d2788836a99c69062fbb091331ec940e02d12d179c1d53e25fc", size = 48543 }, +] + +[[package]] +name = "click" +version = "8.1.7" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "colorama", marker = "platform_system == 'Windows'" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/96/d3/f04c7bfcf5c1862a2a5b845c6b2b360488cf47af55dfa79c98f6a6bf98b5/click-8.1.7.tar.gz", hash = "sha256:ca9853ad459e787e2192211578cc907e7594e294c7ccc834310722b41b9ca6de", size = 336121 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/00/2e/d53fa4befbf2cfa713304affc7ca780ce4fc1fd8710527771b58311a3229/click-8.1.7-py3-none-any.whl", hash = "sha256:ae74fb96c20a0277a1d615f1e4d73c8414f5a98db8b799a7931d1582f3390c28", size = 97941 }, +] + +[[package]] +name = "cmarkgfm" +version = "2024.1.14" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "cffi" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/7d/57/0480532cf04f77ff6f34985109079e87b9028444540731a5380abd0a3325/cmarkgfm-2024.1.14.tar.gz", hash = "sha256:a208c1726e12ba385125cef2c6d375c41c5dea4cc2673a77af712b1dbf074e90", size = 146699 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/38/75/eb384c2e0b40a49dd7cebed9dd243b2c028a9201bdfd7276f9c95276d421/cmarkgfm-2024.1.14-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:b676300ff04629c07c02687e5dc017fb7d1edf38a5dc1ab2ec28078a71195ce6", size = 125978 }, + { url = "https://files.pythonhosted.org/packages/ce/a7/d1c81abda5335902eab537cd9483d404b7c1a2c7a762ec844efc96e0b4ec/cmarkgfm-2024.1.14-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:7ccd6689108673be5bb19f3a3b02cf897fab9b04290a0548e4c6deec5a1fec9a", size = 124117 }, + { url = "https://files.pythonhosted.org/packages/3e/f6/71e427e28b850a0bbf041b4439ec6cd36a532fe08502fb3b6fef905bc75a/cmarkgfm-2024.1.14-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:b8d68eb075d2eb48e864d9c031b0117900e25a3c1c7ab8ce4f80c25b6ae7f346", size = 439509 }, + { url = "https://files.pythonhosted.org/packages/03/1b/9db58ecf3b0989caef1c443cbae5e880ef2395d8d243a489e531946d0f8c/cmarkgfm-2024.1.14-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:82b62dbc7f546c43d99964914133b7e4d7ef7ce4f411cd0acc95b382853aa47f", size = 444805 }, + { url = "https://files.pythonhosted.org/packages/be/a3/4bcdfe8bd996a2af98b87d1a8af0a57c509ada2d1d410975ad339b93bb07/cmarkgfm-2024.1.14-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:a3fe7e5357233649030f22dd816354e51c99f90857cff904a173bbd602733aca", size = 417725 }, + { url = "https://files.pythonhosted.org/packages/96/46/8e7d73780b8a076183ff9ab40ef3f05bd09e638a3b201110b419cbfc7a4a/cmarkgfm-2024.1.14-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:4310b7d5cc534c27454406963319a16c7f3f05ff75b7cd24a1091884c04248ad", size = 429092 }, + { url = "https://files.pythonhosted.org/packages/b1/47/71d5cbe814c320355c96bda2d17a42f085bc06d64ee651828cc782620535/cmarkgfm-2024.1.14-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:4ecb19b2fb24fe055bbaf0d38e8262642f27123b4339f1f10e7fabb726e57ee8", size = 409124 }, + { url = "https://files.pythonhosted.org/packages/6d/97/77bd019abc0436ce97182f2f64122e0c105b6acb440accb83994a49219b9/cmarkgfm-2024.1.14-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:7d3f497cbbaeb540a741a6516673045abcc11b41029bc3dbc95b3b5ea2cc2182", size = 437728 }, + { url = "https://files.pythonhosted.org/packages/3a/c3/65ec673bf90cbb73d2c3a8ca88234435d0ff646738b7d29be1d7b5dcbf39/cmarkgfm-2024.1.14-cp310-cp310-win32.whl", hash = "sha256:d399545833ff3f25f8f6d9b559be5878987f3e34cfc4fe79cefc1d33fd3da852", size = 116835 }, + { url = "https://files.pythonhosted.org/packages/90/58/4af6df4c36fc9ba20a7cca1cf73e8882aff0945c9983e3b6431bff43bc36/cmarkgfm-2024.1.14-cp310-cp310-win_amd64.whl", hash = "sha256:bcd059584161491a2848e55ec73c28f17d8e89faec9ad860afa05246a6ee695f", size = 127303 }, + { url = "https://files.pythonhosted.org/packages/47/5f/08b10b2ed15e7053526b835e6fd198a42de9660f3b031a0edf4c28d32086/cmarkgfm-2024.1.14-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:6565d5659d80d119733a407af70e5de7c04e0822fabb91db83688e0e280cc174", size = 125976 }, + { url = "https://files.pythonhosted.org/packages/4f/e2/6ccf5b916ab7b5df1f4472302f65f9daa466eb7d22d2477caed27ee13b0d/cmarkgfm-2024.1.14-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:43db622d57e81dce30dcbea3a0198588080559473e5bafb68e10959dbf0a3d0f", size = 124119 }, + { url = "https://files.pythonhosted.org/packages/0f/29/12a8322342e22c28bce794c3595e27628ad980eb5c22073723abdf117b0f/cmarkgfm-2024.1.14-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:26d39c10b816392a3b54a9a7ba7ce894c40fee2813ac71554c424d6762c28ee6", size = 439522 }, + { url = "https://files.pythonhosted.org/packages/48/7e/eafb45c243f27dcaafee942125e50ab344db7d848a8d7d6de7b3c0b9aabf/cmarkgfm-2024.1.14-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:bba56ccec5b980c9da003ac7449c0cbe8045e4e046d4ce51273a47d3a9b84b1a", size = 444816 }, + { url = "https://files.pythonhosted.org/packages/a8/86/3d6bf7ec4032a81b604c0037f048d3dd98a79feb608dea5fe8ed3d4a273f/cmarkgfm-2024.1.14-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:c552ef80fe8c29d647c86ab49b8f66aa7626e7de9009e4005bd2120698667fa2", size = 417741 }, + { url = "https://files.pythonhosted.org/packages/2b/8c/030168b0ef780ad2b8e531ce3d8a77cc48981d2716ced83eae236379feec/cmarkgfm-2024.1.14-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:ce0f76ea3d47d206913db8f7933076191be4d8871019095a4880885531586ab5", size = 429147 }, + { url = "https://files.pythonhosted.org/packages/ba/f6/e2efd2c713e6a81a38504a75a566cc3a1e09d588d5d6df60f9216aeb6469/cmarkgfm-2024.1.14-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:b0b5a3be0b76f2802f8f16c40d33f74ff68c0bca8860bd4b5252395181077534", size = 409160 }, + { url = "https://files.pythonhosted.org/packages/80/3f/8022efe3fe4f9fd8a9debeef37ded8b086cfe206e89a6aa169b3c81a896a/cmarkgfm-2024.1.14-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:70db301d140d1f0cabe58770aad8506a4bd7fa0e5b0fae78c8f9a80712d14857", size = 437775 }, + { url = "https://files.pythonhosted.org/packages/d5/8f/46c0fc7cf5c48929a3073d5843e77b638f3798710397bad234627c39c9d9/cmarkgfm-2024.1.14-cp311-cp311-win32.whl", hash = "sha256:3cdc34d749601ff74209580fb7c80b3cbf1112d2832af52c14387cb04831ff2b", size = 116834 }, + { url = "https://files.pythonhosted.org/packages/38/2c/abd3c6a3ed85d688f51135b35188a613f318cb1ab86bff43d284570d453b/cmarkgfm-2024.1.14-cp311-cp311-win_amd64.whl", hash = "sha256:8b8fd26ff27b9895f48459b8e556b9d6c4d255ac3735b3b2f8b14b9787ff6b89", size = 127303 }, + { url = "https://files.pythonhosted.org/packages/ef/40/6e7121dfd03ae1448f014c4ce777ebd991911e2a8db30a72cee8fc61e233/cmarkgfm-2024.1.14-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:eb595be70d86d1497826f80e3e04b46001b2b94bccc099619daea693923a88b3", size = 125988 }, + { url = "https://files.pythonhosted.org/packages/26/46/40036da661de8cc770cd8bd6299e8d949ab4ba8c5a97f0d690dc7794c5c4/cmarkgfm-2024.1.14-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:a8c929836caf96c4fb7fd5e7f9efe6fbb6aa57f9dfae543f74f10b55d5a92b56", size = 124162 }, + { url = "https://files.pythonhosted.org/packages/8c/4b/98540e11b4caaaef84a12abbcfd1ea4eb932fed2a34df51628544cd385e5/cmarkgfm-2024.1.14-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:07b83ae8de9a397629b4dbe4f190e8edc87b2b94548fbc644ed006a5cc94d959", size = 440062 }, + { url = "https://files.pythonhosted.org/packages/35/e8/842f3ead6874a7e7c541dbf4fd8e1692e5c0de2f90f1e0bd4b01a0911504/cmarkgfm-2024.1.14-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5a922846197ac9452cca8aaa9c4b5e56b215299d067e704df9c56c8d87463335", size = 445357 }, + { url = "https://files.pythonhosted.org/packages/a7/3d/7abf18be2c92dd762ce79032de2301d91c34b640f2991c4103d9b594ebe1/cmarkgfm-2024.1.14-cp312-cp312-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:53ccf3d184080f8626264f49866df4ead90685f4d5a3d5d01ffba7f50fd15512", size = 418349 }, + { url = "https://files.pythonhosted.org/packages/51/94/a5347feedee8b3f4323f8f416797f6d4580f4e992a6cecf151162b34b5df/cmarkgfm-2024.1.14-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:a9bd82bac3673a0848fa09512ae61059943462ce824944faaeadc727068d9e19", size = 429812 }, + { url = "https://files.pythonhosted.org/packages/b2/ec/3712d98dddf746e5bff1271b9460b765935a3387cc3d2d677cce34a66a15/cmarkgfm-2024.1.14-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:1f530595c5fbd92c248576ce43771bd07289c1d42623422d669e20ddb545d41b", size = 409850 }, + { url = "https://files.pythonhosted.org/packages/80/63/4207931a850f4cb17fc768e0adfa4933ada3e6330de393b46e0deeb2eb06/cmarkgfm-2024.1.14-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:2196871b8f42dea9d85e1a3c1bcb5e05758946874441ec3f7226d80881284e32", size = 438592 }, + { url = "https://files.pythonhosted.org/packages/dc/fc/fb5a0fa00cec6552eedc053ed0a6850f7cab6c9ae6327af7d55a33e0d753/cmarkgfm-2024.1.14-cp312-cp312-win32.whl", hash = "sha256:7de3d8bfc64168419a6d1edb223616ac6f54b67e20e4b6b70f3ae659fd3f3f31", size = 116841 }, + { url = "https://files.pythonhosted.org/packages/58/21/ca6817890a35c7952da6683fc2a940196857cbb1a38def3f47d8f6978a91/cmarkgfm-2024.1.14-cp312-cp312-win_amd64.whl", hash = "sha256:ded64f663955f852d8965b40ab47718461df6d42d12719264b09a23d33b8d38f", size = 127343 }, + { url = "https://files.pythonhosted.org/packages/a0/d9/c7578876d95eed28a899b2d38537c01e1c95d724b86e01a7b5a61b7e034a/cmarkgfm-2024.1.14-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:4808af8c8c2c0a39dca8cc27406416d8254aec635f409dc5beb5cb5ed3af564a", size = 125955 }, + { url = "https://files.pythonhosted.org/packages/a0/d3/fbb9e22e1aa331e12e88641443ae7a45552958823cdd1b10b2cab8c55b39/cmarkgfm-2024.1.14-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:c71d6b44ffdd9a03e246a35c8a2b2454eb2a319fcfe5736ff62660259f9f4683", size = 124117 }, + { url = "https://files.pythonhosted.org/packages/9e/c9/e194aa0763f4064a257b98e0d5abd075a8c51e7207bf4f4352b93bd2efb0/cmarkgfm-2024.1.14-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:7973812317ef672c5a1c59065294c4b280aaffb7fe1071b8c661de82021d4f1b", size = 439661 }, + { url = "https://files.pythonhosted.org/packages/10/31/25f407ba9c1e8c4b2b59d70158310da8a72ea5dc07508ec023b2495e8f8f/cmarkgfm-2024.1.14-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:966bd27336736b2950551348b1bfc71863ea26b76b245e9966ee80cc9cde04ee", size = 444935 }, + { url = "https://files.pythonhosted.org/packages/32/a6/7626071157bf38d041abe46144d1476338814ba01fda0b2aa91badbb6248/cmarkgfm-2024.1.14-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:02ba52518469ce85448e99beb20b1808c51f5a6cfee12554e5e810bfe774b791", size = 417901 }, + { url = "https://files.pythonhosted.org/packages/74/7e/a6bf37cff1e05effdcec295591c5564538e1779bd8ef923053ff052022b1/cmarkgfm-2024.1.14-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:9659715d79cbc5c030d36709fe443a47b5c6dbb77bd05e5531feedbe5ad00ac5", size = 429563 }, + { url = "https://files.pythonhosted.org/packages/77/f1/b2164053c49134e51f1e297ee13e6446df922833d7c8f44570dd80301215/cmarkgfm-2024.1.14-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:4ff20857ccded325e11323540d0506fc1bd9ceea9746f81f08fe3d7e52f0a6bc", size = 409617 }, + { url = "https://files.pythonhosted.org/packages/f3/72/69ecdbc719e2c2c030040f22754eed511e286edd2da5bcfef83e9cbf9b32/cmarkgfm-2024.1.14-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:7eff0e618704c49ab3f77680a0722aced6c99d2fe590b8f8d655fa29ed17270e", size = 438243 }, + { url = "https://files.pythonhosted.org/packages/39/ad/86e37b36a18ba12567dcba6c4d714efba23e2fb12101fc13fe3eb6da5793/cmarkgfm-2024.1.14-cp38-cp38-win32.whl", hash = "sha256:93364f7ec9de71285f0a27552f9cfa30aa4d311d37c820daa65dc27ab211a746", size = 116829 }, + { url = "https://files.pythonhosted.org/packages/76/46/307beec9d5c3a59b5cb7d5003f0fcae316877da03f59c910e4853a105a55/cmarkgfm-2024.1.14-cp38-cp38-win_amd64.whl", hash = "sha256:ca9e5388c88f907c9ef1cf588947ea00a1c60f3462fe1f213b591bbd27ceb8c1", size = 127302 }, + { url = "https://files.pythonhosted.org/packages/36/b0/221b6f6d590d0bc7e1cea56f8cc9412a700948cda1593a4efd6b760714dd/cmarkgfm-2024.1.14-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:1444f396fc18115065c66bb6f8a523167fa3bd153423d6fea272c4b486b473cf", size = 125954 }, + { url = "https://files.pythonhosted.org/packages/02/60/726830c42128facdfd29694eace089ddde67ccf3edd9ee536b2a19dff7dc/cmarkgfm-2024.1.14-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:fdecbdad66b7738c711db33471d510c6279a01196920c43294d8071e51192807", size = 124123 }, + { url = "https://files.pythonhosted.org/packages/56/b0/10da638ff8984d1ad5b2a29376e65990827f49d9fb525c19ff0dc6d38fab/cmarkgfm-2024.1.14-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:29b95d267ee1c61fd41d1f8634052a77b554517b18e8ffcdf0181e5e93a7af88", size = 439501 }, + { url = "https://files.pythonhosted.org/packages/2b/8d/b39b58f78bf6fd8153f2ce4a286604b47bf4b1df4d628fe1303483bd1152/cmarkgfm-2024.1.14-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:56ec68a68164bf2ac0fd448d7fcb90d360a42072a6abd62be3e0d222240b7304", size = 444823 }, + { url = "https://files.pythonhosted.org/packages/70/ec/9e08b28863ca2aea4b0e0749310e14ae14c8c2db2e03a2be362bc3923603/cmarkgfm-2024.1.14-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:491d72e0dcc21ff9f3c9a905f785d4268170964500db498dc5b0f2f390fb340b", size = 417715 }, + { url = "https://files.pythonhosted.org/packages/88/24/5c0df5cd0e48c55dcaa6c5755f084f02456241cea979b3477bb806a55779/cmarkgfm-2024.1.14-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:0f7845837b0c4dbb3a1a7bbfffed264f011f86ea1cd0ce7823b533bcce0e1fe3", size = 429146 }, + { url = "https://files.pythonhosted.org/packages/b3/f1/c3b637b4166caf08faa450fe33ded6e336086ac7cdb16caa3ff6b25ef2a9/cmarkgfm-2024.1.14-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:0c66d0fecfdee9f2ffe34f640e346c653a951bddba79d192629c60958933aa51", size = 409136 }, + { url = "https://files.pythonhosted.org/packages/0d/47/41e8452df0977addc66b50ec644fbad2bc45586e6f745127dae3aa0710a1/cmarkgfm-2024.1.14-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:ec6eb4929bd231d7e5c0cf1154581be0a13b8d2b7aee2c30410066f363c765b9", size = 437687 }, + { url = "https://files.pythonhosted.org/packages/52/ee/7a82c33bfbcb3d14ba6f0022e970c2efb740bed1824258b1e2120b8191e5/cmarkgfm-2024.1.14-cp39-cp39-win32.whl", hash = "sha256:d55795968751e1a8ddd2172c1d03d0107b9dd20445dbcd23dc9e0a80d95a0c5b", size = 116830 }, + { url = "https://files.pythonhosted.org/packages/50/49/9d04d1bf4eb4ef819f12a889cd628ed3c4f4fde6cd56a579870fda3dae61/cmarkgfm-2024.1.14-cp39-cp39-win_amd64.whl", hash = "sha256:b79662ab458c910c9785abacb8315d6f46487659d44398bd894f577bb6b9d04e", size = 127304 }, +] + +[[package]] +name = "colorama" +version = "0.4.6" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/d8/53/6f443c9a4a8358a93a6792e2acffb9d9d5cb0a5cfd8802644b7b1c9a02e4/colorama-0.4.6.tar.gz", hash = "sha256:08695f5cb7ed6e0531a20572697297273c47b8cae5a63ffc6d6ed5c201be6e44", size = 27697 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/d1/d6/3965ed04c63042e047cb6a3e6ed1a63a35087b6a609aa3a15ed8ac56c221/colorama-0.4.6-py2.py3-none-any.whl", hash = "sha256:4f1d9991f5acc0ca119f9d443620b77f9d6b33703e51011c16baf57afb285fc6", size = 25335 }, +] + +[[package]] +name = "commonmark" +version = "0.9.1" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/60/48/a60f593447e8f0894ebb7f6e6c1f25dafc5e89c5879fdc9360ae93ff83f0/commonmark-0.9.1.tar.gz", hash = "sha256:452f9dc859be7f06631ddcb328b6919c67984aca654e5fefb3914d54691aed60", size = 95764 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/b1/92/dfd892312d822f36c55366118b95d914e5f16de11044a27cf10a7d71bbbf/commonmark-0.9.1-py2.py3-none-any.whl", hash = "sha256:da2f38c92590f83de410ba1a3cbceafbc74fee9def35f9251ba9a971d6d66fd9", size = 51068 }, +] + +[[package]] +name = "cryptography" +version = "43.0.1" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "cffi", marker = "platform_python_implementation != 'PyPy'" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/de/ba/0664727028b37e249e73879348cc46d45c5c1a2a2e81e8166462953c5755/cryptography-43.0.1.tar.gz", hash = "sha256:203e92a75716d8cfb491dc47c79e17d0d9207ccffcbcb35f598fbe463ae3444d", size = 686927 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/33/13/1193774705783ba364121aa2a60132fa31a668b8ababd5edfa1662354ccd/cryptography-43.0.1-cp37-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:27e613d7077ac613e399270253259d9d53872aaf657471473ebfc9a52935c062", size = 3794751 }, + { url = "https://files.pythonhosted.org/packages/5e/4b/39bb3c4c8cfb3e94e736b8d8859ce5c81536e91a1033b1d26770c4249000/cryptography-43.0.1-cp37-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:68aaecc4178e90719e95298515979814bda0cbada1256a4485414860bd7ab962", size = 3981827 }, + { url = "https://files.pythonhosted.org/packages/ce/dc/1471d4d56608e1013237af334b8a4c35d53895694fbb73882d1c4fd3f55e/cryptography-43.0.1-cp37-abi3-manylinux_2_28_aarch64.whl", hash = "sha256:de41fd81a41e53267cb020bb3a7212861da53a7d39f863585d13ea11049cf277", size = 3780034 }, + { url = "https://files.pythonhosted.org/packages/ad/43/7a9920135b0d5437cc2f8f529fa757431eb6a7736ddfadfdee1cc5890800/cryptography-43.0.1-cp37-abi3-manylinux_2_28_x86_64.whl", hash = "sha256:f98bf604c82c416bc829e490c700ca1553eafdf2912a91e23a79d97d9801372a", size = 3993407 }, + { url = "https://files.pythonhosted.org/packages/cc/42/9ab8467af6c0b76f3d9b8f01d1cf25b9c9f3f2151f4acfab888d21c55a72/cryptography-43.0.1-cp37-abi3-musllinux_1_2_aarch64.whl", hash = "sha256:61ec41068b7b74268fa86e3e9e12b9f0c21fcf65434571dbb13d954bceb08042", size = 3886457 }, + { url = "https://files.pythonhosted.org/packages/a4/65/430509e31700286ec02868a2457d2111d03ccefc20349d24e58d171ae0a7/cryptography-43.0.1-cp37-abi3-musllinux_1_2_x86_64.whl", hash = "sha256:014f58110f53237ace6a408b5beb6c427b64e084eb451ef25a28308270086494", size = 4081499 }, + { url = "https://files.pythonhosted.org/packages/00/0e/8217e348a1fa417ec4c78cd3cdf24154f5e76fd7597343a35bd403650dfd/cryptography-43.0.1-cp39-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1bbcce1a551e262dfbafb6e6252f1ae36a248e615ca44ba302df077a846a8806", size = 3794368 }, + { url = "https://files.pythonhosted.org/packages/3d/ed/38b6be7254d8f7251fde8054af597ee8afa14f911da67a9410a45f602fc3/cryptography-43.0.1-cp39-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:58d4e9129985185a06d849aa6df265bdd5a74ca6e1b736a77959b498e0505b85", size = 3981750 }, + { url = "https://files.pythonhosted.org/packages/64/f3/b7946c3887cf7436f002f4cbb1e6aec77b8d299b86be48eeadfefb937c4b/cryptography-43.0.1-cp39-abi3-manylinux_2_28_aarch64.whl", hash = "sha256:d03a475165f3134f773d1388aeb19c2d25ba88b6a9733c5c590b9ff7bbfa2e0c", size = 3778925 }, + { url = "https://files.pythonhosted.org/packages/ac/7e/ebda4dd4ae098a0990753efbb4b50954f1d03003846b943ea85070782da7/cryptography-43.0.1-cp39-abi3-manylinux_2_28_x86_64.whl", hash = "sha256:511f4273808ab590912a93ddb4e3914dfd8a388fed883361b02dea3791f292e1", size = 3993152 }, + { url = "https://files.pythonhosted.org/packages/43/f6/feebbd78a3e341e3913846a3bb2c29d0b09b1b3af1573c6baabc2533e147/cryptography-43.0.1-cp39-abi3-musllinux_1_2_aarch64.whl", hash = "sha256:80eda8b3e173f0f247f711eef62be51b599b5d425c429b5d4ca6a05e9e856baa", size = 3886392 }, + { url = "https://files.pythonhosted.org/packages/bd/4c/ab0b9407d5247576290b4fd8abd06b7f51bd414f04eef0f2800675512d61/cryptography-43.0.1-cp39-abi3-musllinux_1_2_x86_64.whl", hash = "sha256:38926c50cff6f533f8a2dae3d7f19541432610d114a70808f0926d5aaa7121e4", size = 4082606 }, + { url = "https://files.pythonhosted.org/packages/ea/45/967da50269954b993d4484bf85026c7377bd551651ebdabba94905972556/cryptography-43.0.1-pp310-pypy310_pp73-manylinux_2_28_aarch64.whl", hash = "sha256:c1332724be35d23a854994ff0b66530119500b6053d0bd3363265f7e5e77288d", size = 3713077 }, + { url = "https://files.pythonhosted.org/packages/df/e6/ccd29a1f9a6b71294e1e9f530c4d779d5dd37c8bb736c05d5fb6d98a971b/cryptography-43.0.1-pp310-pypy310_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:fba1007b3ef89946dbbb515aeeb41e30203b004f0b4b00e5e16078b518563289", size = 3915597 }, + { url = "https://files.pythonhosted.org/packages/3e/fd/70f3e849ad4d6cca2118ee6938e0b52326d02406f10912356151dd4b6868/cryptography-43.0.1-pp39-pypy39_pp73-manylinux_2_28_aarch64.whl", hash = "sha256:9d3cdb25fa98afdd3d0892d132b8d7139e2c087da1712041f6b762e4f807cc96", size = 3713909 }, + { url = "https://files.pythonhosted.org/packages/21/b0/4ecefa99519eaa32af49a3ad002bb3e795f9e6eb32221fd87736247fa3cb/cryptography-43.0.1-pp39-pypy39_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:e710bf40870f4db63c3d7d929aa9e09e4e7ee219e703f949ec4073b4294f6172", size = 3916544 }, +] + +[[package]] +name = "debts" +version = "0.5" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "jinja2" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/8e/54/84a0d3a7aad206dfe4d2b12e3f8f2758ad7c39a78f33a4247793f074ae57/debts-0.5.tar.gz", hash = "sha256:f239fa356500b0cc7d2334a6ad45dcaf542796f759ca44052c59566afca8e5f8", size = 3936 } + +[[package]] +name = "deprecated" +version = "1.2.14" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "wrapt" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/92/14/1e41f504a246fc224d2ac264c227975427a85caf37c3979979edb9b1b232/Deprecated-1.2.14.tar.gz", hash = "sha256:e5323eb936458dccc2582dc6f9c322c852a775a27065ff2b0c4970b9d53d01b3", size = 2974416 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/20/8d/778b7d51b981a96554f29136cd59ca7880bf58094338085bcf2a979a0e6a/Deprecated-1.2.14-py2.py3-none-any.whl", hash = "sha256:6fac8b097794a90302bdbb17b9b815e732d3c4720583ff1b198499d78470466c", size = 9561 }, +] + +[[package]] +name = "dnspython" +version = "2.6.1" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/37/7d/c871f55054e403fdfd6b8f65fd6d1c4e147ed100d3e9f9ba1fe695403939/dnspython-2.6.1.tar.gz", hash = "sha256:e8f0f9c23a7b7cb99ded64e6c3a6f3e701d78f50c55e002b839dea7225cff7cc", size = 332727 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/87/a1/8c5287991ddb8d3e4662f71356d9656d91ab3a36618c3dd11b280df0d255/dnspython-2.6.1-py3-none-any.whl", hash = "sha256:5ef3b9680161f6fa89daf8ad451b5f1a33b18ae8a1c6778cdf4b43f08c0a6e50", size = 307696 }, +] + +[[package]] +name = "docutils" +version = "0.20.1" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/1f/53/a5da4f2c5739cf66290fac1431ee52aff6851c7c8ffd8264f13affd7bcdd/docutils-0.20.1.tar.gz", hash = "sha256:f08a4e276c3a1583a86dce3e34aba3fe04d02bba2dd51ed16106244e8a923e3b", size = 2058365 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/26/87/f238c0670b94533ac0353a4e2a1a771a0cc73277b88bff23d3ae35a256c1/docutils-0.20.1-py3-none-any.whl", hash = "sha256:96f387a2c5562db4476f09f13bbab2192e764cac08ebbf3a34a95d9b1e4a59d6", size = 572666 }, +] + +[[package]] +name = "email-validator" +version = "2.2.0" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "dnspython" }, + { name = "idna" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/48/ce/13508a1ec3f8bb981ae4ca79ea40384becc868bfae97fd1c942bb3a001b1/email_validator-2.2.0.tar.gz", hash = "sha256:cb690f344c617a714f22e66ae771445a1ceb46821152df8e165c5f9a364582b7", size = 48967 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/d7/ee/bf0adb559ad3c786f12bcbc9296b3f5675f529199bef03e2df281fa1fadb/email_validator-2.2.0-py3-none-any.whl", hash = "sha256:561977c2d73ce3611850a06fa56b414621e0c8faa9d66f2611407d87465da631", size = 33521 }, +] + +[[package]] +name = "exceptiongroup" +version = "1.2.2" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/09/35/2495c4ac46b980e4ca1f6ad6db102322ef3ad2410b79fdde159a4b0f3b92/exceptiongroup-1.2.2.tar.gz", hash = "sha256:47c2edf7c6738fafb49fd34290706d1a1a2f4d1c6df275526b62cbb4aa5393cc", size = 28883 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/02/cc/b7e31358aac6ed1ef2bb790a9746ac2c69bcb3c8588b41616914eb106eaf/exceptiongroup-1.2.2-py3-none-any.whl", hash = "sha256:3111b9d131c238bec2f8f516e123e14ba243563fb135d3fe885990585aa7795b", size = 16453 }, +] + +[[package]] +name = "flake8" +version = "5.0.4" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "mccabe" }, + { name = "pycodestyle" }, + { name = "pyflakes" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/ad/00/9808c62b2d529cefc69ce4e4a1ea42c0f855effa55817b7327ec5b75e60a/flake8-5.0.4.tar.gz", hash = "sha256:6fbe320aad8d6b95cec8b8e47bc933004678dc63095be98528b7bdd2a9f510db", size = 145862 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/cf/a0/b881b63a17a59d9d07f5c0cc91a29182c8e8a9aa2bde5b3b2b16519c02f4/flake8-5.0.4-py2.py3-none-any.whl", hash = "sha256:7a1cf6b73744f5806ab95e526f6f0d8c01c66d7bbe349562d22dfca20610b248", size = 61897 }, +] + +[[package]] +name = "flask" +version = "2.3.3" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "blinker" }, + { name = "click" }, + { name = "importlib-metadata", marker = "python_full_version < '3.10'" }, + { name = "itsdangerous" }, + { name = "jinja2" }, + { name = "werkzeug" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/46/b7/4ace17e37abd9c21715dea5ee11774a25e404c486a7893fa18e764326ead/flask-2.3.3.tar.gz", hash = "sha256:09c347a92aa7ff4a8e7f3206795f30d826654baf38b873d0744cd571ca609efc", size = 672756 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/fd/56/26f0be8adc2b4257df20c1c4260ddd0aa396cf8e75d90ab2f7ff99bc34f9/flask-2.3.3-py3-none-any.whl", hash = "sha256:f69fcd559dc907ed196ab9df0e48471709175e696d6e698dd4dbe940f96ce66b", size = 96112 }, +] + +[[package]] +name = "flask-babel" +version = "3.1.0" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "babel" }, + { name = "flask" }, + { name = "jinja2" }, + { name = "pytz" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/35/83/f31a4ff688168f9c8a73d80ebfc785dcd7703474a0802b25a78d54edd07c/flask_babel-3.1.0.tar.gz", hash = "sha256:be015772c5d7f046f3b99c508dcf618636eb93d21b713b356db79f3e79f69f39", size = 10188 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/5e/b2/ec77c54dcc31acef7fb75c5730f35714ab4fe4742b41d99fc932eefe6ca1/flask_babel-3.1.0-py3-none-any.whl", hash = "sha256:deb3ee272d5adf97f5974ed09ab501243d63e7fb4a047501a00de4bd4aca4830", size = 9618 }, +] + +[[package]] +name = "flask-cors" +version = "3.0.10" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "flask" }, + { name = "six" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/cf/25/e3b2553d22ed542be807739556c69621ad2ab276ae8d5d2560f4ed20f652/Flask-Cors-3.0.10.tar.gz", hash = "sha256:b60839393f3b84a0f3746f6cdca56c1ad7426aa738b70d6c61375857823181de", size = 30867 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/db/84/901e700de86604b1c4ef4b57110d4e947c218b9997adf5d38fa7da493bce/Flask_Cors-3.0.10-py2.py3-none-any.whl", hash = "sha256:74efc975af1194fc7891ff5cd85b0f7478be4f7f59fe158102e91abb72bb4438", size = 14067 }, +] + +[[package]] +name = "flask-limiter" +version = "2.9.2" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "flask" }, + { name = "limits" }, + { name = "ordered-set" }, + { name = "rich" }, + { name = "typing-extensions" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/28/87/83bc93c0a3186df3b38587e6b1d9bed41be4abbae01edad7843ac5059d1c/Flask-Limiter-2.9.2.tar.gz", hash = "sha256:041bf0d72c8c62d2cb54c772de1ad842c82bdefeddfadc1c9171739f296484e2", size = 286145 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/dd/ab/7326f9851b587c219effc350fc811dbe54318e67aa82a169ebb6c56fe705/Flask_Limiter-2.9.2-py3-none-any.whl", hash = "sha256:64c6456204d88006324127071598a04cdd77be1576e00e8f5b74fad80925ea37", size = 27415 }, +] + +[[package]] +name = "flask-mail" +version = "0.10.0" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "blinker" }, + { name = "flask" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/ba/29/e92dc84c675d1e8d260d5768eb3fb65c70cbd33addecf424187587bee862/flask_mail-0.10.0.tar.gz", hash = "sha256:44083e7b02bbcce792209c06252f8569dd5a325a7aaa76afe7330422bd97881d", size = 8152 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/e4/c0/a81083da779f482494d49195d8b6c9fde21072558253e4a9fb2ec969c3c1/flask_mail-0.10.0-py3-none-any.whl", hash = "sha256:a451e490931bb3441d9b11ebab6812a16bfa81855792ae1bf9c1e1e22c4e51e7", size = 8529 }, +] + +[[package]] +name = "flask-migrate" +version = "4.0.7" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "alembic" }, + { name = "flask" }, + { name = "flask-sqlalchemy" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/3b/e2/4008fc0d298d7ce797021b194bbe151d4d12db670691648a226d4fc8aefc/Flask-Migrate-4.0.7.tar.gz", hash = "sha256:dff7dd25113c210b069af280ea713b883f3840c1e3455274745d7355778c8622", size = 21770 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/93/01/587023575286236f95d2ab8a826c320375ed5ea2102bb103ed89704ffa6b/Flask_Migrate-4.0.7-py3-none-any.whl", hash = "sha256:5c532be17e7b43a223b7500d620edae33795df27c75811ddf32560f7d48ec617", size = 21127 }, +] + +[[package]] +name = "flask-restful" +version = "0.3.10" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "aniso8601" }, + { name = "flask" }, + { name = "pytz" }, + { name = "six" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/c0/ce/a0a133db616ea47f78a41e15c4c68b9f08cab3df31eb960f61899200a119/Flask-RESTful-0.3.10.tar.gz", hash = "sha256:fe4af2ef0027df8f9b4f797aba20c5566801b6ade995ac63b588abf1a59cec37", size = 110453 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/d7/7b/f0b45f0df7d2978e5ae51804bb5939b7897b2ace24306009da0cc34d8d1f/Flask_RESTful-0.3.10-py2.py3-none-any.whl", hash = "sha256:1cf93c535172f112e080b0d4503a8d15f93a48c88bdd36dd87269bdaf405051b", size = 26217 }, +] + +[[package]] +name = "flask-sqlalchemy" +version = "2.5.1" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "flask" }, + { name = "sqlalchemy" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/35/f0/39dd2d8e7e5223f78a5206d7020dc0e16718a964acfb3564d89e9798ab9b/Flask-SQLAlchemy-2.5.1.tar.gz", hash = "sha256:2bda44b43e7cacb15d4e05ff3cc1f8bc97936cc464623424102bfc2c35e95912", size = 132750 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/26/2c/9088b6bd95bca539230bbe9ad446737ed391aab9a83aff403e18dded3e75/Flask_SQLAlchemy-2.5.1-py2.py3-none-any.whl", hash = "sha256:f12c3d4cc5cc7fdcc148b9527ea05671718c3ea45d50c7e732cceb33f574b390", size = 17716 }, +] + +[[package]] +name = "flask-talisman" +version = "1.1.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/38/5c/157d51e32eaffdb34ee316261239937d66400a57cd8146176fd8ce50c43a/flask-talisman-1.1.0.tar.gz", hash = "sha256:c5f486f5f54420729f84b3c3850cd63f96e8b033a9629bee66c524ea363797ff", size = 22656 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/77/1c/a15ac936dc3ae4491c5ff089dccdccd72cd3608b15fcf4e2de961f9ee8f3/flask_talisman-1.1.0-py2.py3-none-any.whl", hash = "sha256:3c42b610ebe49b0e35ca150e179bf51aa1da01e4635b49a674868ea681046208", size = 18967 }, +] + +[[package]] +name = "flask-wtf" +version = "1.2.1" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "flask" }, + { name = "itsdangerous" }, + { name = "wtforms" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/9b/ef/b6ec35e02f479f6e76e02ede14594c9cfa5e6dcbab6ea0e82fa413993a2a/flask_wtf-1.2.1.tar.gz", hash = "sha256:8bb269eb9bb46b87e7c8233d7e7debdf1f8b74bf90cc1789988c29b37a97b695", size = 42498 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/02/2b/0f0cf68a2f052ea3dbb8b6c8c2a7e8aea5e6df7410f5e289437fefbeb461/flask_wtf-1.2.1-py3-none-any.whl", hash = "sha256:fa6793f2fb7e812e0fe9743b282118e581fb1b6c45d414b8af05e659bd653287", size = 12725 }, +] + +[[package]] +name = "greenlet" +version = "3.1.1" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/2f/ff/df5fede753cc10f6a5be0931204ea30c35fa2f2ea7a35b25bdaf4fe40e46/greenlet-3.1.1.tar.gz", hash = "sha256:4ce3ac6cdb6adf7946475d7ef31777c26d94bccc377e070a7986bd2d5c515467", size = 186022 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/25/90/5234a78dc0ef6496a6eb97b67a42a8e96742a56f7dc808cb954a85390448/greenlet-3.1.1-cp310-cp310-macosx_11_0_universal2.whl", hash = "sha256:0bbae94a29c9e5c7e4a2b7f0aae5c17e8e90acbfd3bf6270eeba60c39fce3563", size = 271235 }, + { url = "https://files.pythonhosted.org/packages/7c/16/cd631fa0ab7d06ef06387135b7549fdcc77d8d859ed770a0d28e47b20972/greenlet-3.1.1-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:0fde093fb93f35ca72a556cf72c92ea3ebfda3d79fc35bb19fbe685853869a83", size = 637168 }, + { url = "https://files.pythonhosted.org/packages/2f/b1/aed39043a6fec33c284a2c9abd63ce191f4f1a07319340ffc04d2ed3256f/greenlet-3.1.1-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:36b89d13c49216cadb828db8dfa6ce86bbbc476a82d3a6c397f0efae0525bdd0", size = 648826 }, + { url = "https://files.pythonhosted.org/packages/76/25/40e0112f7f3ebe54e8e8ed91b2b9f970805143efef16d043dfc15e70f44b/greenlet-3.1.1-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:94b6150a85e1b33b40b1464a3f9988dcc5251d6ed06842abff82e42632fac120", size = 644443 }, + { url = "https://files.pythonhosted.org/packages/fb/2f/3850b867a9af519794784a7eeed1dd5bc68ffbcc5b28cef703711025fd0a/greenlet-3.1.1-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:93147c513fac16385d1036b7e5b102c7fbbdb163d556b791f0f11eada7ba65dc", size = 643295 }, + { url = "https://files.pythonhosted.org/packages/cf/69/79e4d63b9387b48939096e25115b8af7cd8a90397a304f92436bcb21f5b2/greenlet-3.1.1-cp310-cp310-manylinux_2_24_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:da7a9bff22ce038e19bf62c4dd1ec8391062878710ded0a845bcf47cc0200617", size = 599544 }, + { url = "https://files.pythonhosted.org/packages/46/1d/44dbcb0e6c323bd6f71b8c2f4233766a5faf4b8948873225d34a0b7efa71/greenlet-3.1.1-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:b2795058c23988728eec1f36a4e5e4ebad22f8320c85f3587b539b9ac84128d7", size = 1125456 }, + { url = "https://files.pythonhosted.org/packages/e0/1d/a305dce121838d0278cee39d5bb268c657f10a5363ae4b726848f833f1bb/greenlet-3.1.1-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:ed10eac5830befbdd0c32f83e8aa6288361597550ba669b04c48f0f9a2c843c6", size = 1149111 }, + { url = "https://files.pythonhosted.org/packages/96/28/d62835fb33fb5652f2e98d34c44ad1a0feacc8b1d3f1aecab035f51f267d/greenlet-3.1.1-cp310-cp310-win_amd64.whl", hash = "sha256:77c386de38a60d1dfb8e55b8c1101d68c79dfdd25c7095d51fec2dd800892b80", size = 298392 }, + { url = "https://files.pythonhosted.org/packages/28/62/1c2665558618553c42922ed47a4e6d6527e2fa3516a8256c2f431c5d0441/greenlet-3.1.1-cp311-cp311-macosx_11_0_universal2.whl", hash = "sha256:e4d333e558953648ca09d64f13e6d8f0523fa705f51cae3f03b5983489958c70", size = 272479 }, + { url = "https://files.pythonhosted.org/packages/76/9d/421e2d5f07285b6e4e3a676b016ca781f63cfe4a0cd8eaecf3fd6f7a71ae/greenlet-3.1.1-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:09fc016b73c94e98e29af67ab7b9a879c307c6731a2c9da0db5a7d9b7edd1159", size = 640404 }, + { url = "https://files.pythonhosted.org/packages/e5/de/6e05f5c59262a584e502dd3d261bbdd2c97ab5416cc9c0b91ea38932a901/greenlet-3.1.1-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:d5e975ca70269d66d17dd995dafc06f1b06e8cb1ec1e9ed54c1d1e4a7c4cf26e", size = 652813 }, + { url = "https://files.pythonhosted.org/packages/49/93/d5f93c84241acdea15a8fd329362c2c71c79e1a507c3f142a5d67ea435ae/greenlet-3.1.1-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:3b2813dc3de8c1ee3f924e4d4227999285fd335d1bcc0d2be6dc3f1f6a318ec1", size = 648517 }, + { url = "https://files.pythonhosted.org/packages/15/85/72f77fc02d00470c86a5c982b8daafdf65d38aefbbe441cebff3bf7037fc/greenlet-3.1.1-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e347b3bfcf985a05e8c0b7d462ba6f15b1ee1c909e2dcad795e49e91b152c383", size = 647831 }, + { url = "https://files.pythonhosted.org/packages/f7/4b/1c9695aa24f808e156c8f4813f685d975ca73c000c2a5056c514c64980f6/greenlet-3.1.1-cp311-cp311-manylinux_2_24_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:9e8f8c9cb53cdac7ba9793c276acd90168f416b9ce36799b9b885790f8ad6c0a", size = 602413 }, + { url = "https://files.pythonhosted.org/packages/76/70/ad6e5b31ef330f03b12559d19fda2606a522d3849cde46b24f223d6d1619/greenlet-3.1.1-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:62ee94988d6b4722ce0028644418d93a52429e977d742ca2ccbe1c4f4a792511", size = 1129619 }, + { url = "https://files.pythonhosted.org/packages/f4/fb/201e1b932e584066e0f0658b538e73c459b34d44b4bd4034f682423bc801/greenlet-3.1.1-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:1776fd7f989fc6b8d8c8cb8da1f6b82c5814957264d1f6cf818d475ec2bf6395", size = 1155198 }, + { url = "https://files.pythonhosted.org/packages/12/da/b9ed5e310bb8b89661b80cbcd4db5a067903bbcd7fc854923f5ebb4144f0/greenlet-3.1.1-cp311-cp311-win_amd64.whl", hash = "sha256:48ca08c771c268a768087b408658e216133aecd835c0ded47ce955381105ba39", size = 298930 }, + { url = "https://files.pythonhosted.org/packages/7d/ec/bad1ac26764d26aa1353216fcbfa4670050f66d445448aafa227f8b16e80/greenlet-3.1.1-cp312-cp312-macosx_11_0_universal2.whl", hash = "sha256:4afe7ea89de619adc868e087b4d2359282058479d7cfb94970adf4b55284574d", size = 274260 }, + { url = "https://files.pythonhosted.org/packages/66/d4/c8c04958870f482459ab5956c2942c4ec35cac7fe245527f1039837c17a9/greenlet-3.1.1-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:f406b22b7c9a9b4f8aa9d2ab13d6ae0ac3e85c9a809bd590ad53fed2bf70dc79", size = 649064 }, + { url = "https://files.pythonhosted.org/packages/51/41/467b12a8c7c1303d20abcca145db2be4e6cd50a951fa30af48b6ec607581/greenlet-3.1.1-cp312-cp312-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:c3a701fe5a9695b238503ce5bbe8218e03c3bcccf7e204e455e7462d770268aa", size = 663420 }, + { url = "https://files.pythonhosted.org/packages/27/8f/2a93cd9b1e7107d5c7b3b7816eeadcac2ebcaf6d6513df9abaf0334777f6/greenlet-3.1.1-cp312-cp312-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:2846930c65b47d70b9d178e89c7e1a69c95c1f68ea5aa0a58646b7a96df12441", size = 658035 }, + { url = "https://files.pythonhosted.org/packages/57/5c/7c6f50cb12be092e1dccb2599be5a942c3416dbcfb76efcf54b3f8be4d8d/greenlet-3.1.1-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:99cfaa2110534e2cf3ba31a7abcac9d328d1d9f1b95beede58294a60348fba36", size = 660105 }, + { url = "https://files.pythonhosted.org/packages/f1/66/033e58a50fd9ec9df00a8671c74f1f3a320564c6415a4ed82a1c651654ba/greenlet-3.1.1-cp312-cp312-manylinux_2_24_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:1443279c19fca463fc33e65ef2a935a5b09bb90f978beab37729e1c3c6c25fe9", size = 613077 }, + { url = "https://files.pythonhosted.org/packages/19/c5/36384a06f748044d06bdd8776e231fadf92fc896bd12cb1c9f5a1bda9578/greenlet-3.1.1-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:b7cede291382a78f7bb5f04a529cb18e068dd29e0fb27376074b6d0317bf4dd0", size = 1135975 }, + { url = "https://files.pythonhosted.org/packages/38/f9/c0a0eb61bdf808d23266ecf1d63309f0e1471f284300ce6dac0ae1231881/greenlet-3.1.1-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:23f20bb60ae298d7d8656c6ec6db134bca379ecefadb0b19ce6f19d1f232a942", size = 1163955 }, + { url = "https://files.pythonhosted.org/packages/43/21/a5d9df1d21514883333fc86584c07c2b49ba7c602e670b174bd73cfc9c7f/greenlet-3.1.1-cp312-cp312-win_amd64.whl", hash = "sha256:7124e16b4c55d417577c2077be379514321916d5790fa287c9ed6f23bd2ffd01", size = 299655 }, + { url = "https://files.pythonhosted.org/packages/f3/57/0db4940cd7bb461365ca8d6fd53e68254c9dbbcc2b452e69d0d41f10a85e/greenlet-3.1.1-cp313-cp313-macosx_11_0_universal2.whl", hash = "sha256:05175c27cb459dcfc05d026c4232f9de8913ed006d42713cb8a5137bd49375f1", size = 272990 }, + { url = "https://files.pythonhosted.org/packages/1c/ec/423d113c9f74e5e402e175b157203e9102feeb7088cee844d735b28ef963/greenlet-3.1.1-cp313-cp313-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:935e943ec47c4afab8965954bf49bfa639c05d4ccf9ef6e924188f762145c0ff", size = 649175 }, + { url = "https://files.pythonhosted.org/packages/a9/46/ddbd2db9ff209186b7b7c621d1432e2f21714adc988703dbdd0e65155c77/greenlet-3.1.1-cp313-cp313-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:667a9706c970cb552ede35aee17339a18e8f2a87a51fba2ed39ceeeb1004798a", size = 663425 }, + { url = "https://files.pythonhosted.org/packages/bc/f9/9c82d6b2b04aa37e38e74f0c429aece5eeb02bab6e3b98e7db89b23d94c6/greenlet-3.1.1-cp313-cp313-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:b8a678974d1f3aa55f6cc34dc480169d58f2e6d8958895d68845fa4ab566509e", size = 657736 }, + { url = "https://files.pythonhosted.org/packages/d9/42/b87bc2a81e3a62c3de2b0d550bf91a86939442b7ff85abb94eec3fc0e6aa/greenlet-3.1.1-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:efc0f674aa41b92da8c49e0346318c6075d734994c3c4e4430b1c3f853e498e4", size = 660347 }, + { url = "https://files.pythonhosted.org/packages/37/fa/71599c3fd06336cdc3eac52e6871cfebab4d9d70674a9a9e7a482c318e99/greenlet-3.1.1-cp313-cp313-manylinux_2_24_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:0153404a4bb921f0ff1abeb5ce8a5131da56b953eda6e14b88dc6bbc04d2049e", size = 615583 }, + { url = "https://files.pythonhosted.org/packages/4e/96/e9ef85de031703ee7a4483489b40cf307f93c1824a02e903106f2ea315fe/greenlet-3.1.1-cp313-cp313-musllinux_1_1_aarch64.whl", hash = "sha256:275f72decf9932639c1c6dd1013a1bc266438eb32710016a1c742df5da6e60a1", size = 1133039 }, + { url = "https://files.pythonhosted.org/packages/87/76/b2b6362accd69f2d1889db61a18c94bc743e961e3cab344c2effaa4b4a25/greenlet-3.1.1-cp313-cp313-musllinux_1_1_x86_64.whl", hash = "sha256:c4aab7f6381f38a4b42f269057aee279ab0fc7bf2e929e3d4abfae97b682a12c", size = 1160716 }, + { url = "https://files.pythonhosted.org/packages/1f/1b/54336d876186920e185066d8c3024ad55f21d7cc3683c856127ddb7b13ce/greenlet-3.1.1-cp313-cp313-win_amd64.whl", hash = "sha256:b42703b1cf69f2aa1df7d1030b9d77d3e584a70755674d60e710f0af570f3761", size = 299490 }, + { url = "https://files.pythonhosted.org/packages/5f/17/bea55bf36990e1638a2af5ba10c1640273ef20f627962cf97107f1e5d637/greenlet-3.1.1-cp313-cp313t-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:f1695e76146579f8c06c1509c7ce4dfe0706f49c6831a817ac04eebb2fd02011", size = 643731 }, + { url = "https://files.pythonhosted.org/packages/78/d2/aa3d2157f9ab742a08e0fd8f77d4699f37c22adfbfeb0c610a186b5f75e0/greenlet-3.1.1-cp313-cp313t-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:7876452af029456b3f3549b696bb36a06db7c90747740c5302f74a9e9fa14b13", size = 649304 }, + { url = "https://files.pythonhosted.org/packages/f1/8e/d0aeffe69e53ccff5a28fa86f07ad1d2d2d6537a9506229431a2a02e2f15/greenlet-3.1.1-cp313-cp313t-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:4ead44c85f8ab905852d3de8d86f6f8baf77109f9da589cb4fa142bd3b57b475", size = 646537 }, + { url = "https://files.pythonhosted.org/packages/05/79/e15408220bbb989469c8871062c97c6c9136770657ba779711b90870d867/greenlet-3.1.1-cp313-cp313t-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:8320f64b777d00dd7ccdade271eaf0cad6636343293a25074cc5566160e4de7b", size = 642506 }, + { url = "https://files.pythonhosted.org/packages/18/87/470e01a940307796f1d25f8167b551a968540fbe0551c0ebb853cb527dd6/greenlet-3.1.1-cp313-cp313t-manylinux_2_24_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:6510bf84a6b643dabba74d3049ead221257603a253d0a9873f55f6a59a65f822", size = 602753 }, + { url = "https://files.pythonhosted.org/packages/e2/72/576815ba674eddc3c25028238f74d7b8068902b3968cbe456771b166455e/greenlet-3.1.1-cp313-cp313t-musllinux_1_1_aarch64.whl", hash = "sha256:04b013dc07c96f83134b1e99888e7a79979f1a247e2a9f59697fa14b5862ed01", size = 1122731 }, + { url = "https://files.pythonhosted.org/packages/ac/38/08cc303ddddc4b3d7c628c3039a61a3aae36c241ed01393d00c2fd663473/greenlet-3.1.1-cp313-cp313t-musllinux_1_1_x86_64.whl", hash = "sha256:411f015496fec93c1c8cd4e5238da364e1da7a124bcb293f085bf2860c32c6f6", size = 1142112 }, + { url = "https://files.pythonhosted.org/packages/97/83/bdf5f69fcf304065ec7cf8fc7c08248479cfed9bcca02bf0001c07e000aa/greenlet-3.1.1-cp38-cp38-macosx_11_0_universal2.whl", hash = "sha256:346bed03fe47414091be4ad44786d1bd8bef0c3fcad6ed3dee074a032ab408a9", size = 271017 }, + { url = "https://files.pythonhosted.org/packages/31/4a/2d4443adcb38e1e90e50c653a26b2be39998ea78ca1a4cf414dfdeb2e98b/greenlet-3.1.1-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:dfc59d69fc48664bc693842bd57acfdd490acafda1ab52c7836e3fc75c90a111", size = 642888 }, + { url = "https://files.pythonhosted.org/packages/5a/c9/b5d9ac1b932aa772dd1eb90a8a2b30dbd7ad5569dcb7fdac543810d206b4/greenlet-3.1.1-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:d21e10da6ec19b457b82636209cbe2331ff4306b54d06fa04b7c138ba18c8a81", size = 655451 }, + { url = "https://files.pythonhosted.org/packages/a8/18/218e21caf7caba5b2236370196eaebc00987d4a2b2d3bf63cc4d4dd5a69f/greenlet-3.1.1-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:37b9de5a96111fc15418819ab4c4432e4f3c2ede61e660b1e33971eba26ef9ba", size = 651409 }, + { url = "https://files.pythonhosted.org/packages/a7/25/de419a2b22fa6e18ce3b2a5adb01d33ec7b2784530f76fa36ba43d8f0fac/greenlet-3.1.1-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6ef9ea3f137e5711f0dbe5f9263e8c009b7069d8a1acea822bd5e9dae0ae49c8", size = 650661 }, + { url = "https://files.pythonhosted.org/packages/d8/88/0ce16c0afb2d71d85562a7bcd9b092fec80a7767ab5b5f7e1bbbca8200f8/greenlet-3.1.1-cp38-cp38-manylinux_2_24_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:85f3ff71e2e60bd4b4932a043fbbe0f499e263c628390b285cb599154a3b03b1", size = 605959 }, + { url = "https://files.pythonhosted.org/packages/5a/10/39a417ad0afb0b7e5b150f1582cdeb9416f41f2e1df76018434dfac4a6cc/greenlet-3.1.1-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:95ffcf719966dd7c453f908e208e14cde192e09fde6c7186c8f1896ef778d8cd", size = 1132341 }, + { url = "https://files.pythonhosted.org/packages/9f/f5/e9b151ddd2ed0508b7a47bef7857e46218dbc3fd10e564617a3865abfaac/greenlet-3.1.1-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:03a088b9de532cbfe2ba2034b2b85e82df37874681e8c470d6fb2f8c04d7e4b7", size = 1159409 }, + { url = "https://files.pythonhosted.org/packages/86/97/2c86989ca4e0f089fbcdc9229c972a01ef53abdafd5ae89e0f3dcdcd4adb/greenlet-3.1.1-cp38-cp38-win32.whl", hash = "sha256:8b8b36671f10ba80e159378df9c4f15c14098c4fd73a36b9ad715f057272fbef", size = 281126 }, + { url = "https://files.pythonhosted.org/packages/d3/50/7b7a3e10ed82c760c1fd8d3167a7c95508e9fdfc0b0604f05ed1a9a9efdc/greenlet-3.1.1-cp38-cp38-win_amd64.whl", hash = "sha256:7017b2be767b9d43cc31416aba48aab0d2309ee31b4dbf10a1d38fb7972bdf9d", size = 298285 }, + { url = "https://files.pythonhosted.org/packages/8c/82/8051e82af6d6b5150aacb6789a657a8afd48f0a44d8e91cb72aaaf28553a/greenlet-3.1.1-cp39-cp39-macosx_11_0_universal2.whl", hash = "sha256:396979749bd95f018296af156201d6211240e7a23090f50a8d5d18c370084dc3", size = 270027 }, + { url = "https://files.pythonhosted.org/packages/f9/74/f66de2785880293780eebd18a2958aeea7cbe7814af1ccef634f4701f846/greenlet-3.1.1-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ca9d0ff5ad43e785350894d97e13633a66e2b50000e8a183a50a88d834752d42", size = 634822 }, + { url = "https://files.pythonhosted.org/packages/68/23/acd9ca6bc412b02b8aa755e47b16aafbe642dde0ad2f929f836e57a7949c/greenlet-3.1.1-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:f6ff3b14f2df4c41660a7dec01045a045653998784bf8cfcb5a525bdffffbc8f", size = 646866 }, + { url = "https://files.pythonhosted.org/packages/a9/ab/562beaf8a53dc9f6b2459f200e7bc226bb07e51862a66351d8b7817e3efd/greenlet-3.1.1-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:94ebba31df2aa506d7b14866fed00ac141a867e63143fe5bca82a8e503b36437", size = 641985 }, + { url = "https://files.pythonhosted.org/packages/03/d3/1006543621f16689f6dc75f6bcf06e3c23e044c26fe391c16c253623313e/greenlet-3.1.1-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:73aaad12ac0ff500f62cebed98d8789198ea0e6f233421059fa68a5aa7220145", size = 641268 }, + { url = "https://files.pythonhosted.org/packages/2f/c1/ad71ce1b5f61f900593377b3f77b39408bce5dc96754790311b49869e146/greenlet-3.1.1-cp39-cp39-manylinux_2_24_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:63e4844797b975b9af3a3fb8f7866ff08775f5426925e1e0bbcfe7932059a12c", size = 597376 }, + { url = "https://files.pythonhosted.org/packages/f7/ff/183226685b478544d61d74804445589e069d00deb8ddef042699733950c7/greenlet-3.1.1-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:7939aa3ca7d2a1593596e7ac6d59391ff30281ef280d8632fa03d81f7c5f955e", size = 1123359 }, + { url = "https://files.pythonhosted.org/packages/c0/8b/9b3b85a89c22f55f315908b94cd75ab5fed5973f7393bbef000ca8b2c5c1/greenlet-3.1.1-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:d0028e725ee18175c6e422797c407874da24381ce0690d6b9396c204c7f7276e", size = 1147458 }, + { url = "https://files.pythonhosted.org/packages/b8/1c/248fadcecd1790b0ba793ff81fa2375c9ad6442f4c748bf2cc2e6563346a/greenlet-3.1.1-cp39-cp39-win32.whl", hash = "sha256:5e06afd14cbaf9e00899fae69b24a32f2196c19de08fcb9f4779dd4f004e5e7c", size = 281131 }, + { url = "https://files.pythonhosted.org/packages/ae/02/e7d0aef2354a38709b764df50b2b83608f0621493e47f47694eb80922822/greenlet-3.1.1-cp39-cp39-win_amd64.whl", hash = "sha256:3319aa75e0e0639bc15ff54ca327e8dc7a6fe404003496e3c6925cd3142e0e22", size = 298306 }, +] + +[[package]] +name = "idna" +version = "3.10" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/f1/70/7703c29685631f5a7590aa73f1f1d3fa9a380e654b86af429e0934a32f7d/idna-3.10.tar.gz", hash = "sha256:12f65c9b470abda6dc35cf8e63cc574b1c52b11df2c86030af0ac09b01b13ea9", size = 190490 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/76/c6/c88e154df9c4e1a2a66ccf0005a88dfb2650c1dffb6f5ce603dfbd452ce3/idna-3.10-py3-none-any.whl", hash = "sha256:946d195a0d259cbba61165e88e65941f16e9b36ea6ddb97f00452bae8b1287d3", size = 70442 }, +] + +[[package]] +name = "ihatemoney" +version = "6.2.0.dev0" +source = { editable = "." } +dependencies = [ + { name = "blinker" }, + { name = "cachetools" }, + { name = "debts" }, + { name = "email-validator" }, + { name = "flask" }, + { name = "flask-babel" }, + { name = "flask-cors" }, + { name = "flask-limiter" }, + { name = "flask-mail" }, + { name = "flask-migrate" }, + { name = "flask-restful" }, + { name = "flask-sqlalchemy" }, + { name = "flask-talisman" }, + { name = "flask-wtf" }, + { name = "itsdangerous" }, + { name = "jinja2" }, + { name = "pytest-libfaketime" }, + { name = "python-dateutil" }, + { name = "qrcode" }, + { name = "requests" }, + { name = "sqlalchemy" }, + { name = "sqlalchemy-continuum" }, + { name = "werkzeug" }, + { name = "wtforms" }, +] + +[package.optional-dependencies] +database = [ + { name = "psycopg2-binary" }, + { name = "pymysql" }, +] +dev = [ + { name = "flake8" }, + { name = "isort" }, + { name = "libfaketime" }, + { name = "pytest" }, + { name = "pytest-flask" }, + { name = "ruff" }, + { name = "vermin" }, + { name = "zest-releaser" }, +] +doc = [ + { name = "docutils" }, + { name = "myst-parser" }, + { name = "sphinx" }, +] + +[package.metadata] +requires-dist = [ + { name = "blinker", specifier = ">=1.4,<2" }, + { name = "cachetools", specifier = ">=4.1,<5" }, + { name = "debts", specifier = ">=0.5,<1" }, + { name = "docutils", marker = "extra == 'doc'", specifier = "==0.20.1" }, + { name = "email-validator", specifier = ">=1.0,<3" }, + { name = "flake8", marker = "extra == 'dev'", specifier = "==5.0.4" }, + { name = "flask", specifier = ">=2,<3" }, + { name = "flask-babel", specifier = ">=1.0,<4" }, + { name = "flask-cors", specifier = ">=3.0.8,<4" }, + { name = "flask-limiter", specifier = ">=2.6,<3" }, + { name = "flask-mail", specifier = ">=0.9.1,<1" }, + { name = "flask-migrate", specifier = ">=2.5.3,<5" }, + { name = "flask-restful", specifier = ">=0.3.9,<1" }, + { name = "flask-sqlalchemy", specifier = ">=2.4,<3" }, + { name = "flask-talisman", specifier = ">=0.8,<2" }, + { name = "flask-wtf", specifier = ">=0.14.3,<2" }, + { name = "isort", marker = "extra == 'dev'", specifier = "==5.11.5" }, + { name = "itsdangerous", specifier = ">=2,<3" }, + { name = "jinja2", specifier = ">=3,<4" }, + { name = "libfaketime", marker = "extra == 'dev'", specifier = ">=2.1.0" }, + { name = "myst-parser", marker = "extra == 'doc'", specifier = ">=2,<3" }, + { name = "psycopg2-binary", marker = "extra == 'database'", specifier = ">=2.9.2,<3" }, + { name = "pymysql", marker = "extra == 'database'", specifier = ">=0.9,<1.1" }, + { name = "pytest", marker = "extra == 'dev'", specifier = ">=6.2.5" }, + { name = "pytest-flask", marker = "extra == 'dev'", specifier = ">=1.2.0" }, + { name = "pytest-libfaketime", extras = ["dev"], specifier = ">=0.1.3" }, + { name = "python-dateutil" }, + { name = "qrcode", specifier = ">=7.1,<8" }, + { name = "requests", specifier = ">=2.25,<3" }, + { name = "ruff", marker = "extra == 'dev'", specifier = "==0.6.8" }, + { name = "sphinx", marker = "extra == 'doc'", specifier = ">=7.0.1,<8" }, + { name = "sqlalchemy", specifier = ">=1.3.0,<1.5" }, + { name = "sqlalchemy-continuum", specifier = ">=1.3.12,<2" }, + { name = "vermin", marker = "extra == 'dev'", specifier = "==1.5.2" }, + { name = "werkzeug", specifier = ">=2,<3" }, + { name = "wtforms", specifier = ">=2.3.3,<3.2" }, + { name = "zest-releaser", marker = "extra == 'dev'", specifier = ">=6.20.1" }, +] + +[[package]] +name = "imagesize" +version = "1.4.1" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/a7/84/62473fb57d61e31fef6e36d64a179c8781605429fd927b5dd608c997be31/imagesize-1.4.1.tar.gz", hash = "sha256:69150444affb9cb0d5cc5a92b3676f0b2fb7cd9ae39e947a5e11a36b4497cd4a", size = 1280026 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/ff/62/85c4c919272577931d407be5ba5d71c20f0b616d31a0befe0ae45bb79abd/imagesize-1.4.1-py2.py3-none-any.whl", hash = "sha256:0d8d18d08f840c19d0ee7ca1fd82490fdc3729b7ac93f49870406ddde8ef8d8b", size = 8769 }, +] + +[[package]] +name = "importlib-metadata" +version = "8.5.0" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "zipp" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/cd/12/33e59336dca5be0c398a7482335911a33aa0e20776128f038019f1a95f1b/importlib_metadata-8.5.0.tar.gz", hash = "sha256:71522656f0abace1d072b9e5481a48f07c138e00f079c38c8f883823f9c26bd7", size = 55304 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/a0/d9/a1e041c5e7caa9a05c925f4bdbdfb7f006d1f74996af53467bc394c97be7/importlib_metadata-8.5.0-py3-none-any.whl", hash = "sha256:45e54197d28b7a7f1559e60b95e7c567032b602131fbd588f1497f47880aa68b", size = 26514 }, +] + +[[package]] +name = "importlib-resources" +version = "6.4.5" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "zipp", marker = "python_full_version < '3.10'" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/98/be/f3e8c6081b684f176b761e6a2fef02a0be939740ed6f54109a2951d806f3/importlib_resources-6.4.5.tar.gz", hash = "sha256:980862a1d16c9e147a59603677fa2aa5fd82b87f223b6cb870695bcfce830065", size = 43372 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/e1/6a/4604f9ae2fa62ef47b9de2fa5ad599589d28c9fd1d335f32759813dfa91e/importlib_resources-6.4.5-py3-none-any.whl", hash = "sha256:ac29d5f956f01d5e4bb63102a5a19957f1b9175e45649977264a1416783bb717", size = 36115 }, +] + +[[package]] +name = "iniconfig" +version = "2.0.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/d7/4b/cbd8e699e64a6f16ca3a8220661b5f83792b3017d0f79807cb8708d33913/iniconfig-2.0.0.tar.gz", hash = "sha256:2d91e135bf72d31a410b17c16da610a82cb55f6b0477d1a902134b24a455b8b3", size = 4646 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/ef/a6/62565a6e1cf69e10f5727360368e451d4b7f58beeac6173dc9db836a5b46/iniconfig-2.0.0-py3-none-any.whl", hash = "sha256:b6a85871a79d2e3b22d2d1b94ac2824226a63c6b741c88f7ae975f18b6778374", size = 5892 }, +] + +[[package]] +name = "isort" +version = "5.11.5" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/67/63/18cc5c2f9084d3f91ce704f2b5c8e17bedd777244e7732c21a31992b0a78/isort-5.11.5.tar.gz", hash = "sha256:6be1f76a507cb2ecf16c7cf14a37e41609ca082330be4e3436a18ef74add55db", size = 187953 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/5f/f6/c55db45970fbd14de6ab72082f1b8a143c3a69aa031c1e0dd4b9ecc8d496/isort-5.11.5-py3-none-any.whl", hash = "sha256:ba1d72fb2595a01c7895a5128f9585a5cc4b6d395f1c8d514989b9a7eb2a8746", size = 104094 }, +] + +[[package]] +name = "itsdangerous" +version = "2.2.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/9c/cb/8ac0172223afbccb63986cc25049b154ecfb5e85932587206f42317be31d/itsdangerous-2.2.0.tar.gz", hash = "sha256:e0050c0b7da1eea53ffaf149c0cfbb5c6e2e2b69c4bef22c81fa6eb73e5f6173", size = 54410 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/04/96/92447566d16df59b2a776c0fb82dbc4d9e07cd95062562af01e408583fc4/itsdangerous-2.2.0-py3-none-any.whl", hash = "sha256:c6242fc49e35958c8b15141343aa660db5fc54d4f13a1db01a3f5891b98700ef", size = 16234 }, +] + +[[package]] +name = "jaraco-classes" +version = "3.4.0" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "more-itertools" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/06/c0/ed4a27bc5571b99e3cff68f8a9fa5b56ff7df1c2251cc715a652ddd26402/jaraco.classes-3.4.0.tar.gz", hash = "sha256:47a024b51d0239c0dd8c8540c6c7f484be3b8fcf0b2d85c13825780d3b3f3acd", size = 11780 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/7f/66/b15ce62552d84bbfcec9a4873ab79d993a1dd4edb922cbfccae192bd5b5f/jaraco.classes-3.4.0-py3-none-any.whl", hash = "sha256:f662826b6bed8cace05e7ff873ce0f9283b5c924470fe664fff1c2f00f581790", size = 6777 }, +] + +[[package]] +name = "jaraco-context" +version = "6.0.1" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "backports-tarfile", marker = "python_full_version < '3.12'" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/df/ad/f3777b81bf0b6e7bc7514a1656d3e637b2e8e15fab2ce3235730b3e7a4e6/jaraco_context-6.0.1.tar.gz", hash = "sha256:9bae4ea555cf0b14938dc0aee7c9f32ed303aa20a3b73e7dc80111628792d1b3", size = 13912 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/ff/db/0c52c4cf5e4bd9f5d7135ec7669a3a767af21b3a308e1ed3674881e52b62/jaraco.context-6.0.1-py3-none-any.whl", hash = "sha256:f797fc481b490edb305122c9181830a3a5b76d84ef6d1aef2fb9b47ab956f9e4", size = 6825 }, +] + +[[package]] +name = "jaraco-functools" +version = "4.1.0" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "more-itertools" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/ab/23/9894b3df5d0a6eb44611c36aec777823fc2e07740dabbd0b810e19594013/jaraco_functools-4.1.0.tar.gz", hash = "sha256:70f7e0e2ae076498e212562325e805204fc092d7b4c17e0e86c959e249701a9d", size = 19159 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/9f/4f/24b319316142c44283d7540e76c7b5a6dbd5db623abd86bb7b3491c21018/jaraco.functools-4.1.0-py3-none-any.whl", hash = "sha256:ad159f13428bc4acbf5541ad6dec511f91573b90fba04df61dafa2a1231cf649", size = 10187 }, +] + +[[package]] +name = "jeepney" +version = "0.8.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/d6/f4/154cf374c2daf2020e05c3c6a03c91348d59b23c5366e968feb198306fdf/jeepney-0.8.0.tar.gz", hash = "sha256:5efe48d255973902f6badc3ce55e2aa6c5c3b3bc642059ef3a91247bcfcc5806", size = 106005 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/ae/72/2a1e2290f1ab1e06f71f3d0f1646c9e4634e70e1d37491535e19266e8dc9/jeepney-0.8.0-py3-none-any.whl", hash = "sha256:c0a454ad016ca575060802ee4d590dd912e35c122fa04e70306de3d076cce755", size = 48435 }, +] + +[[package]] +name = "jinja2" +version = "3.1.4" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "markupsafe" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/ed/55/39036716d19cab0747a5020fc7e907f362fbf48c984b14e62127f7e68e5d/jinja2-3.1.4.tar.gz", hash = "sha256:4a3aee7acbbe7303aede8e9648d13b8bf88a429282aa6122a993f0ac800cb369", size = 240245 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/31/80/3a54838c3fb461f6fec263ebf3a3a41771bd05190238de3486aae8540c36/jinja2-3.1.4-py3-none-any.whl", hash = "sha256:bc5dd2abb727a5319567b7a813e6a2e7318c39f4f487cfe6c89c6f9c7d25197d", size = 133271 }, +] + +[[package]] +name = "keyring" +version = "25.4.1" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "importlib-metadata", marker = "python_full_version < '3.12'" }, + { name = "importlib-resources", marker = "python_full_version < '3.9'" }, + { name = "jaraco-classes" }, + { name = "jaraco-context" }, + { name = "jaraco-functools" }, + { name = "jeepney", marker = "sys_platform == 'linux'" }, + { name = "pywin32-ctypes", marker = "sys_platform == 'win32'" }, + { name = "secretstorage", marker = "sys_platform == 'linux'" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/a5/1c/2bdbcfd5d59dc6274ffb175bc29aa07ecbfab196830e0cfbde7bd861a2ea/keyring-25.4.1.tar.gz", hash = "sha256:b07ebc55f3e8ed86ac81dd31ef14e81ace9dd9c3d4b5d77a6e9a2016d0d71a1b", size = 62491 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/83/25/e6d59e5f0a0508d0dca8bb98c7f7fd3772fc943ac3f53d5ab18a218d32c0/keyring-25.4.1-py3-none-any.whl", hash = "sha256:5426f817cf7f6f007ba5ec722b1bcad95a75b27d780343772ad76b17cb47b0bf", size = 38946 }, +] + +[[package]] +name = "libfaketime" +version = "2.1.0" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "python-dateutil" }, + { name = "pytz" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/c9/ec/a02a79d0254957f340a11c350de2a8ae43cfe2ececc11fc7a951f6f9d263/libfaketime-2.1.0.tar.gz", hash = "sha256:5fecd1770565154f892235a39dfc2388b092864ecca24d05456e4f5a947127a3", size = 75103 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/03/12/c28cdc2834bbd71e9300f97093766dfcd4b8f3c7b7059c1e8543c6f3b14c/libfaketime-2.1.0-py3-none-any.whl", hash = "sha256:df72634f79900e71160f4e3ba4cf8f1d7ba6167e7c9a4f28d67c08e0a4f03ba2", size = 92845 }, +] + +[[package]] +name = "limits" +version = "3.13.0" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "deprecated" }, + { name = "importlib-resources" }, + { name = "packaging" }, + { name = "typing-extensions" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/c4/5f/89fb5405ee37d8b172e48e357438dd79482731b0cd5db2f734ac58f019e4/limits-3.13.0.tar.gz", hash = "sha256:6571b0c567bfa175a35fed9f8a954c0c92f1c3200804282f1b8f1de4ad98a953", size = 70218 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/81/80/b340bc7c3eb8f5c40e4d38c8e3cd04c127756d8de06b9e54caefb4ae16d5/limits-3.13.0-py3-none-any.whl", hash = "sha256:9767f7233da4255e9904b79908a728e8ec0984c0b086058b4cbbd309aea553f6", size = 45547 }, +] + +[[package]] +name = "mako" +version = "1.3.5" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "markupsafe" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/67/03/fb5ba97ff65ce64f6d35b582aacffc26b693a98053fa831ab43a437cbddb/Mako-1.3.5.tar.gz", hash = "sha256:48dbc20568c1d276a2698b36d968fa76161bf127194907ea6fc594fa81f943bc", size = 392738 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/03/62/70f5a0c2dd208f9f3f2f9afd103aec42ee4d9ad2401d78342f75e9b8da36/Mako-1.3.5-py3-none-any.whl", hash = "sha256:260f1dbc3a519453a9c856dedfe4beb4e50bd5a26d96386cb6c80856556bb91a", size = 78565 }, +] + +[[package]] +name = "markdown-it-py" +version = "3.0.0" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "mdurl" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/38/71/3b932df36c1a044d397a1f92d1cf91ee0a503d91e470cbd670aa66b07ed0/markdown-it-py-3.0.0.tar.gz", hash = "sha256:e3f60a94fa066dc52ec76661e37c851cb232d92f9886b15cb560aaada2df8feb", size = 74596 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/42/d7/1ec15b46af6af88f19b8e5ffea08fa375d433c998b8a7639e76935c14f1f/markdown_it_py-3.0.0-py3-none-any.whl", hash = "sha256:355216845c60bd96232cd8d8c40e8f9765cc86f46880e43a8fd22dc1a1a8cab1", size = 87528 }, +] + +[[package]] +name = "markupsafe" +version = "2.1.5" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/87/5b/aae44c6655f3801e81aa3eef09dbbf012431987ba564d7231722f68df02d/MarkupSafe-2.1.5.tar.gz", hash = "sha256:d283d37a890ba4c1ae73ffadf8046435c76e7bc2247bbb63c00bd1a709c6544b", size = 19384 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/e4/54/ad5eb37bf9d51800010a74e4665425831a9db4e7c4e0fde4352e391e808e/MarkupSafe-2.1.5-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:a17a92de5231666cfbe003f0e4b9b3a7ae3afb1ec2845aadc2bacc93ff85febc", size = 18206 }, + { url = "https://files.pythonhosted.org/packages/6a/4a/a4d49415e600bacae038c67f9fecc1d5433b9d3c71a4de6f33537b89654c/MarkupSafe-2.1.5-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:72b6be590cc35924b02c78ef34b467da4ba07e4e0f0454a2c5907f473fc50ce5", size = 14079 }, + { url = "https://files.pythonhosted.org/packages/0a/7b/85681ae3c33c385b10ac0f8dd025c30af83c78cec1c37a6aa3b55e67f5ec/MarkupSafe-2.1.5-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e61659ba32cf2cf1481e575d0462554625196a1f2fc06a1c777d3f48e8865d46", size = 26620 }, + { url = "https://files.pythonhosted.org/packages/7c/52/2b1b570f6b8b803cef5ac28fdf78c0da318916c7d2fe9402a84d591b394c/MarkupSafe-2.1.5-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:2174c595a0d73a3080ca3257b40096db99799265e1c27cc5a610743acd86d62f", size = 25818 }, + { url = "https://files.pythonhosted.org/packages/29/fe/a36ba8c7ca55621620b2d7c585313efd10729e63ef81e4e61f52330da781/MarkupSafe-2.1.5-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:ae2ad8ae6ebee9d2d94b17fb62763125f3f374c25618198f40cbb8b525411900", size = 25493 }, + { url = "https://files.pythonhosted.org/packages/60/ae/9c60231cdfda003434e8bd27282b1f4e197ad5a710c14bee8bea8a9ca4f0/MarkupSafe-2.1.5-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:075202fa5b72c86ad32dc7d0b56024ebdbcf2048c0ba09f1cde31bfdd57bcfff", size = 30630 }, + { url = "https://files.pythonhosted.org/packages/65/dc/1510be4d179869f5dafe071aecb3f1f41b45d37c02329dfba01ff59e5ac5/MarkupSafe-2.1.5-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:598e3276b64aff0e7b3451b72e94fa3c238d452e7ddcd893c3ab324717456bad", size = 29745 }, + { url = "https://files.pythonhosted.org/packages/30/39/8d845dd7d0b0613d86e0ef89549bfb5f61ed781f59af45fc96496e897f3a/MarkupSafe-2.1.5-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:fce659a462a1be54d2ffcacea5e3ba2d74daa74f30f5f143fe0c58636e355fdd", size = 30021 }, + { url = "https://files.pythonhosted.org/packages/c7/5c/356a6f62e4f3c5fbf2602b4771376af22a3b16efa74eb8716fb4e328e01e/MarkupSafe-2.1.5-cp310-cp310-win32.whl", hash = "sha256:d9fad5155d72433c921b782e58892377c44bd6252b5af2f67f16b194987338a4", size = 16659 }, + { url = "https://files.pythonhosted.org/packages/69/48/acbf292615c65f0604a0c6fc402ce6d8c991276e16c80c46a8f758fbd30c/MarkupSafe-2.1.5-cp310-cp310-win_amd64.whl", hash = "sha256:bf50cd79a75d181c9181df03572cdce0fbb75cc353bc350712073108cba98de5", size = 17213 }, + { url = "https://files.pythonhosted.org/packages/11/e7/291e55127bb2ae67c64d66cef01432b5933859dfb7d6949daa721b89d0b3/MarkupSafe-2.1.5-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:629ddd2ca402ae6dbedfceeba9c46d5f7b2a61d9749597d4307f943ef198fc1f", size = 18219 }, + { url = "https://files.pythonhosted.org/packages/6b/cb/aed7a284c00dfa7c0682d14df85ad4955a350a21d2e3b06d8240497359bf/MarkupSafe-2.1.5-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:5b7b716f97b52c5a14bffdf688f971b2d5ef4029127f1ad7a513973cfd818df2", size = 14098 }, + { url = "https://files.pythonhosted.org/packages/1c/cf/35fe557e53709e93feb65575c93927942087e9b97213eabc3fe9d5b25a55/MarkupSafe-2.1.5-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:6ec585f69cec0aa07d945b20805be741395e28ac1627333b1c5b0105962ffced", size = 29014 }, + { url = "https://files.pythonhosted.org/packages/97/18/c30da5e7a0e7f4603abfc6780574131221d9148f323752c2755d48abad30/MarkupSafe-2.1.5-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:b91c037585eba9095565a3556f611e3cbfaa42ca1e865f7b8015fe5c7336d5a5", size = 28220 }, + { url = "https://files.pythonhosted.org/packages/0c/40/2e73e7d532d030b1e41180807a80d564eda53babaf04d65e15c1cf897e40/MarkupSafe-2.1.5-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:7502934a33b54030eaf1194c21c692a534196063db72176b0c4028e140f8f32c", size = 27756 }, + { url = "https://files.pythonhosted.org/packages/18/46/5dca760547e8c59c5311b332f70605d24c99d1303dd9a6e1fc3ed0d73561/MarkupSafe-2.1.5-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:0e397ac966fdf721b2c528cf028494e86172b4feba51d65f81ffd65c63798f3f", size = 33988 }, + { url = "https://files.pythonhosted.org/packages/6d/c5/27febe918ac36397919cd4a67d5579cbbfa8da027fa1238af6285bb368ea/MarkupSafe-2.1.5-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:c061bb86a71b42465156a3ee7bd58c8c2ceacdbeb95d05a99893e08b8467359a", size = 32718 }, + { url = "https://files.pythonhosted.org/packages/f8/81/56e567126a2c2bc2684d6391332e357589a96a76cb9f8e5052d85cb0ead8/MarkupSafe-2.1.5-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:3a57fdd7ce31c7ff06cdfbf31dafa96cc533c21e443d57f5b1ecc6cdc668ec7f", size = 33317 }, + { url = "https://files.pythonhosted.org/packages/00/0b/23f4b2470accb53285c613a3ab9ec19dc944eaf53592cb6d9e2af8aa24cc/MarkupSafe-2.1.5-cp311-cp311-win32.whl", hash = "sha256:397081c1a0bfb5124355710fe79478cdbeb39626492b15d399526ae53422b906", size = 16670 }, + { url = "https://files.pythonhosted.org/packages/b7/a2/c78a06a9ec6d04b3445a949615c4c7ed86a0b2eb68e44e7541b9d57067cc/MarkupSafe-2.1.5-cp311-cp311-win_amd64.whl", hash = "sha256:2b7c57a4dfc4f16f7142221afe5ba4e093e09e728ca65c51f5620c9aaeb9a617", size = 17224 }, + { url = "https://files.pythonhosted.org/packages/53/bd/583bf3e4c8d6a321938c13f49d44024dbe5ed63e0a7ba127e454a66da974/MarkupSafe-2.1.5-cp312-cp312-macosx_10_9_universal2.whl", hash = "sha256:8dec4936e9c3100156f8a2dc89c4b88d5c435175ff03413b443469c7c8c5f4d1", size = 18215 }, + { url = "https://files.pythonhosted.org/packages/48/d6/e7cd795fc710292c3af3a06d80868ce4b02bfbbf370b7cee11d282815a2a/MarkupSafe-2.1.5-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:3c6b973f22eb18a789b1460b4b91bf04ae3f0c4234a0a6aa6b0a92f6f7b951d4", size = 14069 }, + { url = "https://files.pythonhosted.org/packages/51/b5/5d8ec796e2a08fc814a2c7d2584b55f889a55cf17dd1a90f2beb70744e5c/MarkupSafe-2.1.5-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ac07bad82163452a6884fe8fa0963fb98c2346ba78d779ec06bd7a6262132aee", size = 29452 }, + { url = "https://files.pythonhosted.org/packages/0a/0d/2454f072fae3b5a137c119abf15465d1771319dfe9e4acbb31722a0fff91/MarkupSafe-2.1.5-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f5dfb42c4604dddc8e4305050aa6deb084540643ed5804d7455b5df8fe16f5e5", size = 28462 }, + { url = "https://files.pythonhosted.org/packages/2d/75/fd6cb2e68780f72d47e6671840ca517bda5ef663d30ada7616b0462ad1e3/MarkupSafe-2.1.5-cp312-cp312-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:ea3d8a3d18833cf4304cd2fc9cbb1efe188ca9b5efef2bdac7adc20594a0e46b", size = 27869 }, + { url = "https://files.pythonhosted.org/packages/b0/81/147c477391c2750e8fc7705829f7351cf1cd3be64406edcf900dc633feb2/MarkupSafe-2.1.5-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:d050b3361367a06d752db6ead6e7edeb0009be66bc3bae0ee9d97fb326badc2a", size = 33906 }, + { url = "https://files.pythonhosted.org/packages/8b/ff/9a52b71839d7a256b563e85d11050e307121000dcebc97df120176b3ad93/MarkupSafe-2.1.5-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:bec0a414d016ac1a18862a519e54b2fd0fc8bbfd6890376898a6c0891dd82e9f", size = 32296 }, + { url = "https://files.pythonhosted.org/packages/88/07/2dc76aa51b481eb96a4c3198894f38b480490e834479611a4053fbf08623/MarkupSafe-2.1.5-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:58c98fee265677f63a4385256a6d7683ab1832f3ddd1e66fe948d5880c21a169", size = 33038 }, + { url = "https://files.pythonhosted.org/packages/96/0c/620c1fb3661858c0e37eb3cbffd8c6f732a67cd97296f725789679801b31/MarkupSafe-2.1.5-cp312-cp312-win32.whl", hash = "sha256:8590b4ae07a35970728874632fed7bd57b26b0102df2d2b233b6d9d82f6c62ad", size = 16572 }, + { url = "https://files.pythonhosted.org/packages/3f/14/c3554d512d5f9100a95e737502f4a2323a1959f6d0d01e0d0997b35f7b10/MarkupSafe-2.1.5-cp312-cp312-win_amd64.whl", hash = "sha256:823b65d8706e32ad2df51ed89496147a42a2a6e01c13cfb6ffb8b1e92bc910bb", size = 17127 }, + { url = "https://files.pythonhosted.org/packages/f8/ff/2c942a82c35a49df5de3a630ce0a8456ac2969691b230e530ac12314364c/MarkupSafe-2.1.5-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:656f7526c69fac7f600bd1f400991cc282b417d17539a1b228617081106feb4a", size = 18192 }, + { url = "https://files.pythonhosted.org/packages/4f/14/6f294b9c4f969d0c801a4615e221c1e084722ea6114ab2114189c5b8cbe0/MarkupSafe-2.1.5-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:97cafb1f3cbcd3fd2b6fbfb99ae11cdb14deea0736fc2b0952ee177f2b813a46", size = 14072 }, + { url = "https://files.pythonhosted.org/packages/81/d4/fd74714ed30a1dedd0b82427c02fa4deec64f173831ec716da11c51a50aa/MarkupSafe-2.1.5-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1f3fbcb7ef1f16e48246f704ab79d79da8a46891e2da03f8783a5b6fa41a9532", size = 26928 }, + { url = "https://files.pythonhosted.org/packages/c7/bd/50319665ce81bb10e90d1cf76f9e1aa269ea6f7fa30ab4521f14d122a3df/MarkupSafe-2.1.5-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:fa9db3f79de01457b03d4f01b34cf91bc0048eb2c3846ff26f66687c2f6d16ab", size = 26106 }, + { url = "https://files.pythonhosted.org/packages/4c/6f/f2b0f675635b05f6afd5ea03c094557bdb8622fa8e673387444fe8d8e787/MarkupSafe-2.1.5-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:ffee1f21e5ef0d712f9033568f8344d5da8cc2869dbd08d87c84656e6a2d2f68", size = 25781 }, + { url = "https://files.pythonhosted.org/packages/51/e0/393467cf899b34a9d3678e78961c2c8cdf49fb902a959ba54ece01273fb1/MarkupSafe-2.1.5-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:5dedb4db619ba5a2787a94d877bc8ffc0566f92a01c0ef214865e54ecc9ee5e0", size = 30518 }, + { url = "https://files.pythonhosted.org/packages/f6/02/5437e2ad33047290dafced9df741d9efc3e716b75583bbd73a9984f1b6f7/MarkupSafe-2.1.5-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:30b600cf0a7ac9234b2638fbc0fb6158ba5bdcdf46aeb631ead21248b9affbc4", size = 29669 }, + { url = "https://files.pythonhosted.org/packages/0e/7d/968284145ffd9d726183ed6237c77938c021abacde4e073020f920e060b2/MarkupSafe-2.1.5-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:8dd717634f5a044f860435c1d8c16a270ddf0ef8588d4887037c5028b859b0c3", size = 29933 }, + { url = "https://files.pythonhosted.org/packages/bf/f3/ecb00fc8ab02b7beae8699f34db9357ae49d9f21d4d3de6f305f34fa949e/MarkupSafe-2.1.5-cp38-cp38-win32.whl", hash = "sha256:daa4ee5a243f0f20d528d939d06670a298dd39b1ad5f8a72a4275124a7819eff", size = 16656 }, + { url = "https://files.pythonhosted.org/packages/92/21/357205f03514a49b293e214ac39de01fadd0970a6e05e4bf1ddd0ffd0881/MarkupSafe-2.1.5-cp38-cp38-win_amd64.whl", hash = "sha256:619bc166c4f2de5caa5a633b8b7326fbe98e0ccbfacabd87268a2b15ff73a029", size = 17206 }, + { url = "https://files.pythonhosted.org/packages/0f/31/780bb297db036ba7b7bbede5e1d7f1e14d704ad4beb3ce53fb495d22bc62/MarkupSafe-2.1.5-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:7a68b554d356a91cce1236aa7682dc01df0edba8d043fd1ce607c49dd3c1edcf", size = 18193 }, + { url = "https://files.pythonhosted.org/packages/6c/77/d77701bbef72892affe060cdacb7a2ed7fd68dae3b477a8642f15ad3b132/MarkupSafe-2.1.5-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:db0b55e0f3cc0be60c1f19efdde9a637c32740486004f20d1cff53c3c0ece4d2", size = 14073 }, + { url = "https://files.pythonhosted.org/packages/d9/a7/1e558b4f78454c8a3a0199292d96159eb4d091f983bc35ef258314fe7269/MarkupSafe-2.1.5-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:3e53af139f8579a6d5f7b76549125f0d94d7e630761a2111bc431fd820e163b8", size = 26486 }, + { url = "https://files.pythonhosted.org/packages/5f/5a/360da85076688755ea0cceb92472923086993e86b5613bbae9fbc14136b0/MarkupSafe-2.1.5-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:17b950fccb810b3293638215058e432159d2b71005c74371d784862b7e4683f3", size = 25685 }, + { url = "https://files.pythonhosted.org/packages/6a/18/ae5a258e3401f9b8312f92b028c54d7026a97ec3ab20bfaddbdfa7d8cce8/MarkupSafe-2.1.5-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:4c31f53cdae6ecfa91a77820e8b151dba54ab528ba65dfd235c80b086d68a465", size = 25338 }, + { url = "https://files.pythonhosted.org/packages/0b/cc/48206bd61c5b9d0129f4d75243b156929b04c94c09041321456fd06a876d/MarkupSafe-2.1.5-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:bff1b4290a66b490a2f4719358c0cdcd9bafb6b8f061e45c7a2460866bf50c2e", size = 30439 }, + { url = "https://files.pythonhosted.org/packages/d1/06/a41c112ab9ffdeeb5f77bc3e331fdadf97fa65e52e44ba31880f4e7f983c/MarkupSafe-2.1.5-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:bc1667f8b83f48511b94671e0e441401371dfd0f0a795c7daa4a3cd1dde55bea", size = 29531 }, + { url = "https://files.pythonhosted.org/packages/02/8c/ab9a463301a50dab04d5472e998acbd4080597abc048166ded5c7aa768c8/MarkupSafe-2.1.5-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:5049256f536511ee3f7e1b3f87d1d1209d327e818e6ae1365e8653d7e3abb6a6", size = 29823 }, + { url = "https://files.pythonhosted.org/packages/bc/29/9bc18da763496b055d8e98ce476c8e718dcfd78157e17f555ce6dd7d0895/MarkupSafe-2.1.5-cp39-cp39-win32.whl", hash = "sha256:00e046b6dd71aa03a41079792f8473dc494d564611a8f89bbbd7cb93295ebdcf", size = 16658 }, + { url = "https://files.pythonhosted.org/packages/f6/f8/4da07de16f10551ca1f640c92b5f316f9394088b183c6a57183df6de5ae4/MarkupSafe-2.1.5-cp39-cp39-win_amd64.whl", hash = "sha256:fa173ec60341d6bb97a89f5ea19c85c5643c1e7dedebc22f5181eb73573142c5", size = 17211 }, +] + +[[package]] +name = "mccabe" +version = "0.7.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/e7/ff/0ffefdcac38932a54d2b5eed4e0ba8a408f215002cd178ad1df0f2806ff8/mccabe-0.7.0.tar.gz", hash = "sha256:348e0240c33b60bbdf4e523192ef919f28cb2c3d7d5c7794f74009290f236325", size = 9658 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/27/1a/1f68f9ba0c207934b35b86a8ca3aad8395a3d6dd7921c0686e23853ff5a9/mccabe-0.7.0-py2.py3-none-any.whl", hash = "sha256:6c2d30ab6be0e4a46919781807b4f0d834ebdd6c6e3dca0bda5a15f863427b6e", size = 7350 }, +] + +[[package]] +name = "mdit-py-plugins" +version = "0.4.2" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "markdown-it-py" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/19/03/a2ecab526543b152300717cf232bb4bb8605b6edb946c845016fa9c9c9fd/mdit_py_plugins-0.4.2.tar.gz", hash = "sha256:5f2cd1fdb606ddf152d37ec30e46101a60512bc0e5fa1a7002c36647b09e26b5", size = 43542 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/a7/f7/7782a043553ee469c1ff49cfa1cdace2d6bf99a1f333cf38676b3ddf30da/mdit_py_plugins-0.4.2-py3-none-any.whl", hash = "sha256:0c673c3f889399a33b95e88d2f0d111b4447bdfea7f237dab2d488f459835636", size = 55316 }, +] + +[[package]] +name = "mdurl" +version = "0.1.2" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/d6/54/cfe61301667036ec958cb99bd3efefba235e65cdeb9c84d24a8293ba1d90/mdurl-0.1.2.tar.gz", hash = "sha256:bb413d29f5eea38f31dd4754dd7377d4465116fb207585f97bf925588687c1ba", size = 8729 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/b3/38/89ba8ad64ae25be8de66a6d463314cf1eb366222074cfda9ee839c56a4b4/mdurl-0.1.2-py3-none-any.whl", hash = "sha256:84008a41e51615a49fc9966191ff91509e3c40b939176e643fd50a5c2196b8f8", size = 9979 }, +] + +[[package]] +name = "more-itertools" +version = "10.5.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/51/78/65922308c4248e0eb08ebcbe67c95d48615cc6f27854b6f2e57143e9178f/more-itertools-10.5.0.tar.gz", hash = "sha256:5482bfef7849c25dc3c6dd53a6173ae4795da2a41a80faea6700d9f5846c5da6", size = 121020 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/48/7e/3a64597054a70f7c86eb0a7d4fc315b8c1ab932f64883a297bdffeb5f967/more_itertools-10.5.0-py3-none-any.whl", hash = "sha256:037b0d3203ce90cca8ab1defbbdac29d5f993fc20131f3664dc8d6acfa872aef", size = 60952 }, +] + +[[package]] +name = "myst-parser" +version = "2.0.0" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "docutils" }, + { name = "jinja2" }, + { name = "markdown-it-py" }, + { name = "mdit-py-plugins" }, + { name = "pyyaml" }, + { name = "sphinx" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/e8/c1/48ea47b78ade0bb0281f34c9e343e3ea0c681fbc81464dbfd134e983954f/myst_parser-2.0.0.tar.gz", hash = "sha256:ea929a67a6a0b1683cdbe19b8d2e724cd7643f8aa3e7bb18dd65beac3483bead", size = 85800 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/1d/f6/6d61a023d758f488e36638076e8a4ec4447a2cdf86938cf6c60cf1c860e6/myst_parser-2.0.0-py3-none-any.whl", hash = "sha256:7c36344ae39c8e740dad7fdabf5aa6fc4897a813083c6cc9990044eb93656b14", size = 77158 }, +] + +[[package]] +name = "nh3" +version = "0.2.18" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/62/73/10df50b42ddb547a907deeb2f3c9823022580a7a47281e8eae8e003a9639/nh3-0.2.18.tar.gz", hash = "sha256:94a166927e53972a9698af9542ace4e38b9de50c34352b962f4d9a7d4c927af4", size = 15028 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/b3/89/1daff5d9ba5a95a157c092c7c5f39b8dd2b1ddb4559966f808d31cfb67e0/nh3-0.2.18-cp37-abi3-macosx_10_12_x86_64.macosx_11_0_arm64.macosx_10_12_universal2.whl", hash = "sha256:14c5a72e9fe82aea5fe3072116ad4661af5cf8e8ff8fc5ad3450f123e4925e86", size = 1374474 }, + { url = "https://files.pythonhosted.org/packages/2c/b6/42fc3c69cabf86b6b81e4c051a9b6e249c5ba9f8155590222c2622961f58/nh3-0.2.18-cp37-abi3-macosx_10_12_x86_64.whl", hash = "sha256:7b7c2a3c9eb1a827d42539aa64091640bd275b81e097cd1d8d82ef91ffa2e811", size = 694573 }, + { url = "https://files.pythonhosted.org/packages/45/b9/833f385403abaf0023c6547389ec7a7acf141ddd9d1f21573723a6eab39a/nh3-0.2.18-cp37-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:42c64511469005058cd17cc1537578eac40ae9f7200bedcfd1fc1a05f4f8c200", size = 844082 }, + { url = "https://files.pythonhosted.org/packages/05/2b/85977d9e11713b5747595ee61f381bc820749daf83f07b90b6c9964cf932/nh3-0.2.18-cp37-abi3-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:0411beb0589eacb6734f28d5497ca2ed379eafab8ad8c84b31bb5c34072b7164", size = 782460 }, + { url = "https://files.pythonhosted.org/packages/72/f2/5c894d5265ab80a97c68ca36f25c8f6f0308abac649aaf152b74e7e854a8/nh3-0.2.18-cp37-abi3-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:5f36b271dae35c465ef5e9090e1fdaba4a60a56f0bb0ba03e0932a66f28b9189", size = 879827 }, + { url = "https://files.pythonhosted.org/packages/ab/a7/375afcc710dbe2d64cfbd69e31f82f3e423d43737258af01f6a56d844085/nh3-0.2.18-cp37-abi3-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:34c03fa78e328c691f982b7c03d4423bdfd7da69cd707fe572f544cf74ac23ad", size = 841080 }, + { url = "https://files.pythonhosted.org/packages/c2/a8/3bb02d0c60a03ad3a112b76c46971e9480efa98a8946677b5a59f60130ca/nh3-0.2.18-cp37-abi3-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:19aaba96e0f795bd0a6c56291495ff59364f4300d4a39b29a0abc9cb3774a84b", size = 924144 }, + { url = "https://files.pythonhosted.org/packages/1b/63/6ab90d0e5225ab9780f6c9fb52254fa36b52bb7c188df9201d05b647e5e1/nh3-0.2.18-cp37-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:de3ceed6e661954871d6cd78b410213bdcb136f79aafe22aa7182e028b8c7307", size = 769192 }, + { url = "https://files.pythonhosted.org/packages/a4/17/59391c28580e2c32272761629893e761442fc7666da0b1cdb479f3b67b88/nh3-0.2.18-cp37-abi3-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:6955369e4d9f48f41e3f238a9e60f9410645db7e07435e62c6a9ea6135a4907f", size = 791042 }, + { url = "https://files.pythonhosted.org/packages/a3/da/0c4e282bc3cff4a0adf37005fa1fb42257673fbc1bbf7d1ff639ec3d255a/nh3-0.2.18-cp37-abi3-musllinux_1_2_aarch64.whl", hash = "sha256:f0eca9ca8628dbb4e916ae2491d72957fdd35f7a5d326b7032a345f111ac07fe", size = 1010073 }, + { url = "https://files.pythonhosted.org/packages/de/81/c291231463d21da5f8bba82c8167a6d6893cc5419b0639801ee5d3aeb8a9/nh3-0.2.18-cp37-abi3-musllinux_1_2_armv7l.whl", hash = "sha256:3a157ab149e591bb638a55c8c6bcb8cdb559c8b12c13a8affaba6cedfe51713a", size = 1029782 }, + { url = "https://files.pythonhosted.org/packages/63/1d/842fed85cf66c973be0aed8770093d6a04741f65e2c388ddd4c07fd3296e/nh3-0.2.18-cp37-abi3-musllinux_1_2_i686.whl", hash = "sha256:c8b3a1cebcba9b3669ed1a84cc65bf005728d2f0bc1ed2a6594a992e817f3a50", size = 942504 }, + { url = "https://files.pythonhosted.org/packages/eb/61/73a007c74c37895fdf66e0edcd881f5eaa17a348ff02f4bb4bc906d61085/nh3-0.2.18-cp37-abi3-musllinux_1_2_x86_64.whl", hash = "sha256:36c95d4b70530b320b365659bb5034341316e6a9b30f0b25fa9c9eff4c27a204", size = 941541 }, + { url = "https://files.pythonhosted.org/packages/78/48/54a788fc9428e481b2f58e0cd8564f6c74ffb6e9ef73d39e8acbeae8c629/nh3-0.2.18-cp37-abi3-win32.whl", hash = "sha256:a7f1b5b2c15866f2db413a3649a8fe4fd7b428ae58be2c0f6bca5eefd53ca2be", size = 573750 }, + { url = "https://files.pythonhosted.org/packages/26/8d/53c5b19c4999bdc6ba95f246f4ef35ca83d7d7423e5e38be43ad66544e5d/nh3-0.2.18-cp37-abi3-win_amd64.whl", hash = "sha256:8ce0f819d2f1933953fca255db2471ad58184a60508f03e6285e5114b6254844", size = 579012 }, +] + +[[package]] +name = "ordered-set" +version = "4.1.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/4c/ca/bfac8bc689799bcca4157e0e0ced07e70ce125193fc2e166d2e685b7e2fe/ordered-set-4.1.0.tar.gz", hash = "sha256:694a8e44c87657c59292ede72891eb91d34131f6531463aab3009191c77364a8", size = 12826 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/33/55/af02708f230eb77084a299d7b08175cff006dea4f2721074b92cdb0296c0/ordered_set-4.1.0-py3-none-any.whl", hash = "sha256:046e1132c71fcf3330438a539928932caf51ddbc582496833e23de611de14562", size = 7634 }, +] + +[[package]] +name = "packaging" +version = "24.1" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/51/65/50db4dda066951078f0a96cf12f4b9ada6e4b811516bf0262c0f4f7064d4/packaging-24.1.tar.gz", hash = "sha256:026ed72c8ed3fcce5bf8950572258698927fd1dbda10a5e981cdf0ac37f4f002", size = 148788 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/08/aa/cc0199a5f0ad350994d660967a8efb233fe0416e4639146c089643407ce6/packaging-24.1-py3-none-any.whl", hash = "sha256:5b8f2217dbdbd2f7f384c41c628544e6d52f2d0f53c6d0c3ea61aa5d1d7ff124", size = 53985 }, +] + +[[package]] +name = "pkginfo" +version = "1.10.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/2f/72/347ec5be4adc85c182ed2823d8d1c7b51e13b9a6b0c1aae59582eca652df/pkginfo-1.10.0.tar.gz", hash = "sha256:5df73835398d10db79f8eecd5cd86b1f6d29317589ea70796994d49399af6297", size = 378457 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/56/09/054aea9b7534a15ad38a363a2bd974c20646ab1582a387a95b8df1bfea1c/pkginfo-1.10.0-py3-none-any.whl", hash = "sha256:889a6da2ed7ffc58ab5b900d888ddce90bce912f2d2de1dc1c26f4cb9fe65097", size = 30392 }, +] + +[[package]] +name = "pluggy" +version = "1.5.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/96/2d/02d4312c973c6050a18b314a5ad0b3210edb65a906f868e31c111dede4a6/pluggy-1.5.0.tar.gz", hash = "sha256:2cffa88e94fdc978c4c574f15f9e59b7f4201d439195c3715ca9e2486f1d0cf1", size = 67955 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/88/5f/e351af9a41f866ac3f1fac4ca0613908d9a41741cfcf2228f4ad853b697d/pluggy-1.5.0-py3-none-any.whl", hash = "sha256:44e1ad92c8ca002de6377e165f3e0f1be63266ab4d554740532335b9d75ea669", size = 20556 }, +] + +[[package]] +name = "psycopg2-binary" +version = "2.9.9" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/fc/07/e720e53bfab016ebcc34241695ccc06a9e3d91ba19b40ca81317afbdc440/psycopg2-binary-2.9.9.tar.gz", hash = "sha256:7f01846810177d829c7692f1f5ada8096762d9172af1b1a28d4ab5b77c923c1c", size = 384973 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/0a/7c/6aaf8c3cb05d86d2c3f407b95bac0c71a43f2718e38c1091972aacb5e1b2/psycopg2_binary-2.9.9-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:c2470da5418b76232f02a2fcd2229537bb2d5a7096674ce61859c3229f2eb202", size = 2822503 }, + { url = "https://files.pythonhosted.org/packages/72/3d/acab427845198794aafd963dd073ee35810e2c52606e8a28c12db39821fb/psycopg2_binary-2.9.9-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:c6af2a6d4b7ee9615cbb162b0738f6e1fd1f5c3eda7e5da17861eacf4c717ea7", size = 2552645 }, + { url = "https://files.pythonhosted.org/packages/ed/be/6c787962d706e55a528ef1693dd7251de657ae60e4d9d767ed61e8e2975c/psycopg2_binary-2.9.9-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:75723c3c0fbbf34350b46a3199eb50638ab22a0228f93fb472ef4d9becc2382b", size = 2850980 }, + { url = "https://files.pythonhosted.org/packages/83/50/a054076c6358753661cd1da59f4dabc03e83d51690371f3fd1edb9e2cf72/psycopg2_binary-2.9.9-cp310-cp310-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:83791a65b51ad6ee6cf0845634859d69a038ea9b03d7b26e703f94c7e93dbcf9", size = 3080543 }, + { url = "https://files.pythonhosted.org/packages/9c/02/826dc5cdfc9515423ec912ba00cc2e4eb09f69e0339b177c9c742f2a09a2/psycopg2_binary-2.9.9-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:0ef4854e82c09e84cc63084a9e4ccd6d9b154f1dbdd283efb92ecd0b5e2b8c84", size = 3264316 }, + { url = "https://files.pythonhosted.org/packages/bc/0d/486e3fa27f39a00168abfcf14a3d8444f437f4b755cc34316da1124f293d/psycopg2_binary-2.9.9-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ed1184ab8f113e8d660ce49a56390ca181f2981066acc27cf637d5c1e10ce46e", size = 3019508 }, + { url = "https://files.pythonhosted.org/packages/41/af/bce37630c525d2b9cf93f930110fc98616d6aca308d59b833b83b3a38176/psycopg2_binary-2.9.9-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:d2997c458c690ec2bc6b0b7ecbafd02b029b7b4283078d3b32a852a7ce3ddd98", size = 2355821 }, + { url = "https://files.pythonhosted.org/packages/3b/76/e46dae1b2273814ef80231f86d59cadf94ec36fd757045ed713c5b75cde7/psycopg2_binary-2.9.9-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:b58b4710c7f4161b5e9dcbe73bb7c62d65670a87df7bcce9e1faaad43e715245", size = 2534855 }, + { url = "https://files.pythonhosted.org/packages/0e/6d/e97245eabff29d7c2de5fc1fc17cf7ef427beee93d20a5ae114c6e6718bd/psycopg2_binary-2.9.9-cp310-cp310-musllinux_1_1_ppc64le.whl", hash = "sha256:0c009475ee389757e6e34611d75f6e4f05f0cf5ebb76c6037508318e1a1e0d7e", size = 2486614 }, + { url = "https://files.pythonhosted.org/packages/70/a7/2cd2c9d5e23b556c11e3b7da41895808d9b056f8f34f50de4375a35b4951/psycopg2_binary-2.9.9-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:8dbf6d1bc73f1d04ec1734bae3b4fb0ee3cb2a493d35ede9badbeb901fb40f6f", size = 2454928 }, + { url = "https://files.pythonhosted.org/packages/63/41/815d19767e2adb1a585213b801c954f46102f305c352c4a4f96287342d44/psycopg2_binary-2.9.9-cp310-cp310-win32.whl", hash = "sha256:3f78fd71c4f43a13d342be74ebbc0666fe1f555b8837eb113cb7416856c79682", size = 1025249 }, + { url = "https://files.pythonhosted.org/packages/5e/4c/9233e0e206634a5387f3ab40f334a5325fb8bef2ca4e12ee7dbdeaf96afc/psycopg2_binary-2.9.9-cp310-cp310-win_amd64.whl", hash = "sha256:876801744b0dee379e4e3c38b76fc89f88834bb15bf92ee07d94acd06ec890a0", size = 1163645 }, + { url = "https://files.pythonhosted.org/packages/a5/ac/702d300f3df169b9d0cbef0340d9f34a78bc18dc2dbafbcb39ff0f165cf8/psycopg2_binary-2.9.9-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:ee825e70b1a209475622f7f7b776785bd68f34af6e7a46e2e42f27b659b5bc26", size = 2822581 }, + { url = "https://files.pythonhosted.org/packages/7a/1f/a6cf0cdf944253f7c45d90fbc876cc8bed5cc9942349306245715c0d88d6/psycopg2_binary-2.9.9-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:1ea665f8ce695bcc37a90ee52de7a7980be5161375d42a0b6c6abedbf0d81f0f", size = 2552633 }, + { url = "https://files.pythonhosted.org/packages/81/0b/3adf561107c865928455891156d1dde5325253f7f4316fe56cd2c3f73570/psycopg2_binary-2.9.9-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:143072318f793f53819048fdfe30c321890af0c3ec7cb1dfc9cc87aa88241de2", size = 2851075 }, + { url = "https://files.pythonhosted.org/packages/f7/98/c2fedcbf0a9607519a010dcf88571138b2251062dbde3610cdba5ba1eee1/psycopg2_binary-2.9.9-cp311-cp311-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:c332c8d69fb64979ebf76613c66b985414927a40f8defa16cf1bc028b7b0a7b0", size = 3080509 }, + { url = "https://files.pythonhosted.org/packages/c2/05/81e8bc7fca95574c9323e487d9ce1b58a4cfcc17f89b8fe843af46361211/psycopg2_binary-2.9.9-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:f7fc5a5acafb7d6ccca13bfa8c90f8c51f13d8fb87d95656d3950f0158d3ce53", size = 3264303 }, + { url = "https://files.pythonhosted.org/packages/ce/85/62825cabc6aad53104b7b6d12eb2ad74737d268630032d07b74d4444cb72/psycopg2_binary-2.9.9-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:977646e05232579d2e7b9c59e21dbe5261f403a88417f6a6512e70d3f8a046be", size = 3019515 }, + { url = "https://files.pythonhosted.org/packages/e9/b0/9ca2b8e01a0912c9a14234fd5df7a241a1e44778c5797bf4b8eaa8dc3d3a/psycopg2_binary-2.9.9-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:b6356793b84728d9d50ead16ab43c187673831e9d4019013f1402c41b1db9b27", size = 2355892 }, + { url = "https://files.pythonhosted.org/packages/73/17/ba28bb0022db5e2015a82d2df1c4b0d419c37fa07a588b3aff3adc4939f6/psycopg2_binary-2.9.9-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:bc7bb56d04601d443f24094e9e31ae6deec9ccb23581f75343feebaf30423359", size = 2534903 }, + { url = "https://files.pythonhosted.org/packages/3b/92/b463556409cdc12791cd8b1dae0072bf8efe817ef68b7ea3d9cf7d0e5656/psycopg2_binary-2.9.9-cp311-cp311-musllinux_1_1_ppc64le.whl", hash = "sha256:77853062a2c45be16fd6b8d6de2a99278ee1d985a7bd8b103e97e41c034006d2", size = 2486597 }, + { url = "https://files.pythonhosted.org/packages/92/57/96576e07132d7f7a1ac1df939575e6fdd8951aea337ee152b586bb51a971/psycopg2_binary-2.9.9-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:78151aa3ec21dccd5cdef6c74c3e73386dcdfaf19bced944169697d7ac7482fc", size = 2454908 }, + { url = "https://files.pythonhosted.org/packages/7c/ae/cedd56e1f4a2b0e37213283caf3733a875c4c76f3372241e19c0d2a87355/psycopg2_binary-2.9.9-cp311-cp311-win32.whl", hash = "sha256:dc4926288b2a3e9fd7b50dc6a1909a13bbdadfc67d93f3374d984e56f885579d", size = 1024240 }, + { url = "https://files.pythonhosted.org/packages/25/1f/7ae31759142999a8d06b3e250c1346c4abcdcada8fa884376775dc1de686/psycopg2_binary-2.9.9-cp311-cp311-win_amd64.whl", hash = "sha256:b76bedd166805480ab069612119ea636f5ab8f8771e640ae103e05a4aae3e417", size = 1163655 }, + { url = "https://files.pythonhosted.org/packages/a7/d0/5f2db14e7b53552276ab613399a83f83f85b173a862d3f20580bc7231139/psycopg2_binary-2.9.9-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:8532fd6e6e2dc57bcb3bc90b079c60de896d2128c5d9d6f24a63875a95a088cf", size = 2823784 }, + { url = "https://files.pythonhosted.org/packages/18/ca/da384fd47233e300e3e485c90e7aab5d7def896d1281239f75901faf87d4/psycopg2_binary-2.9.9-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:b0605eaed3eb239e87df0d5e3c6489daae3f7388d455d0c0b4df899519c6a38d", size = 2553308 }, + { url = "https://files.pythonhosted.org/packages/50/66/fa53d2d3d92f6e1ef469d92afc6a4fe3f6e8a9a04b687aa28fb1f1d954ee/psycopg2_binary-2.9.9-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8f8544b092a29a6ddd72f3556a9fcf249ec412e10ad28be6a0c0d948924f2212", size = 2851283 }, + { url = "https://files.pythonhosted.org/packages/04/37/2429360ac5547378202db14eec0dde76edbe1f6627df5a43c7e164922859/psycopg2_binary-2.9.9-cp312-cp312-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:2d423c8d8a3c82d08fe8af900ad5b613ce3632a1249fd6a223941d0735fce493", size = 3081839 }, + { url = "https://files.pythonhosted.org/packages/62/2a/c0530b59d7e0d09824bc2102ecdcec0456b8ca4d47c0caa82e86fce3ed4c/psycopg2_binary-2.9.9-cp312-cp312-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:2e5afae772c00980525f6d6ecf7cbca55676296b580c0e6abb407f15f3706996", size = 3264488 }, + { url = "https://files.pythonhosted.org/packages/19/57/9f172b900795ea37246c78b5f52e00f4779984370855b3e161600156906d/psycopg2_binary-2.9.9-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6e6f98446430fdf41bd36d4faa6cb409f5140c1c2cf58ce0bbdaf16af7d3f119", size = 3020700 }, + { url = "https://files.pythonhosted.org/packages/94/68/1176fc14ea76861b7b8360be5176e87fb20d5091b137c76570eb4e237324/psycopg2_binary-2.9.9-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:c77e3d1862452565875eb31bdb45ac62502feabbd53429fdc39a1cc341d681ba", size = 2355968 }, + { url = "https://files.pythonhosted.org/packages/70/bb/aec2646a705a09079d008ce88073401cd61fc9b04f92af3eb282caa3a2ec/psycopg2_binary-2.9.9-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:cb16c65dcb648d0a43a2521f2f0a2300f40639f6f8c1ecbc662141e4e3e1ee07", size = 2536101 }, + { url = "https://files.pythonhosted.org/packages/14/33/12818c157e333cb9d9e6753d1b2463b6f60dbc1fade115f8e4dc5c52cac4/psycopg2_binary-2.9.9-cp312-cp312-musllinux_1_1_ppc64le.whl", hash = "sha256:911dda9c487075abd54e644ccdf5e5c16773470a6a5d3826fda76699410066fb", size = 2487064 }, + { url = "https://files.pythonhosted.org/packages/56/a2/7851c68fe8768f3c9c246198b6356ee3e4a8a7f6820cc798443faada3400/psycopg2_binary-2.9.9-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:57fede879f08d23c85140a360c6a77709113efd1c993923c59fde17aa27599fe", size = 2456257 }, + { url = "https://files.pythonhosted.org/packages/6f/ee/3ba07c6dc7c3294e717e94720da1597aedc82a10b1b180203ce183d4631a/psycopg2_binary-2.9.9-cp312-cp312-win32.whl", hash = "sha256:64cf30263844fa208851ebb13b0732ce674d8ec6a0c86a4e160495d299ba3c93", size = 1024709 }, + { url = "https://files.pythonhosted.org/packages/7b/08/9c66c269b0d417a0af9fb969535f0371b8c538633535a7a6a5ca3f9231e2/psycopg2_binary-2.9.9-cp312-cp312-win_amd64.whl", hash = "sha256:81ff62668af011f9a48787564ab7eded4e9fb17a4a6a74af5ffa6a457400d2ab", size = 1163864 }, + { url = "https://files.pythonhosted.org/packages/94/62/6f8d281e279a71f20d1670f4de97d116b1d90948eb16c3c41ac305f94a30/psycopg2_binary-2.9.9-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:60989127da422b74a04345096c10d416c2b41bd7bf2a380eb541059e4e999980", size = 2822517 }, + { url = "https://files.pythonhosted.org/packages/88/d8/3bbedf39ab90d64d7a6f04e3f3744c74f46f55bd305cc2db3aa12e9c5667/psycopg2_binary-2.9.9-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:246b123cc54bb5361588acc54218c8c9fb73068bf227a4a531d8ed56fa3ca7d6", size = 2552729 }, + { url = "https://files.pythonhosted.org/packages/24/1b/99b948254604838de668d81cc39a294a987721120c67963e00d47a290f7f/psycopg2_binary-2.9.9-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:34eccd14566f8fe14b2b95bb13b11572f7c7d5c36da61caf414d23b91fcc5d94", size = 2850949 }, + { url = "https://files.pythonhosted.org/packages/5f/e9/115e4f4f86d4aa5c300fdc90ac3d3e74401b4060d782281fe5b47d6c832d/psycopg2_binary-2.9.9-cp38-cp38-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:18d0ef97766055fec15b5de2c06dd8e7654705ce3e5e5eed3b6651a1d2a9a152", size = 3080624 }, + { url = "https://files.pythonhosted.org/packages/24/bf/4856c4985823ef094fc5a52eeb194f038dfbc57921f1d091853efc8e01b4/psycopg2_binary-2.9.9-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:d3f82c171b4ccd83bbaf35aa05e44e690113bd4f3b7b6cc54d2219b132f3ae55", size = 3264449 }, + { url = "https://files.pythonhosted.org/packages/19/7a/e806ed82d954b9ec29b62f12ae8929da8910cde5ab7e919ec0983e56672d/psycopg2_binary-2.9.9-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ead20f7913a9c1e894aebe47cccf9dc834e1618b7aa96155d2091a626e59c972", size = 3019558 }, + { url = "https://files.pythonhosted.org/packages/da/e0/073f50a65093a0bd087aff95754bdd61e8ef24d6ea29f47ea97575d4a784/psycopg2_binary-2.9.9-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:ca49a8119c6cbd77375ae303b0cfd8c11f011abbbd64601167ecca18a87e7cdd", size = 2355857 }, + { url = "https://files.pythonhosted.org/packages/a3/96/3153069df1378d398dcbd6968d4da89735bb63dccbb13a435bc65291c59c/psycopg2_binary-2.9.9-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:323ba25b92454adb36fa425dc5cf6f8f19f78948cbad2e7bc6cdf7b0d7982e59", size = 2534862 }, + { url = "https://files.pythonhosted.org/packages/dc/d0/512a73da2253c1904366155fd2c7ddf6d4e04a4eb434c90a18af8ce3d24b/psycopg2_binary-2.9.9-cp38-cp38-musllinux_1_1_ppc64le.whl", hash = "sha256:1236ed0952fbd919c100bc839eaa4a39ebc397ed1c08a97fc45fee2a595aa1b3", size = 2486636 }, + { url = "https://files.pythonhosted.org/packages/ba/69/e38aeaace3a87dda1c152c039c72181fdcbff0787d5d2466944b663c4a57/psycopg2_binary-2.9.9-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:729177eaf0aefca0994ce4cffe96ad3c75e377c7b6f4efa59ebf003b6d398716", size = 2454931 }, + { url = "https://files.pythonhosted.org/packages/bc/14/76879e83245d8dc72812fb71fb3e710fa7482a05c4b1788b41b22e9fffcc/psycopg2_binary-2.9.9-cp38-cp38-win32.whl", hash = "sha256:804d99b24ad523a1fe18cc707bf741670332f7c7412e9d49cb5eab67e886b9b5", size = 1007154 }, + { url = "https://files.pythonhosted.org/packages/48/10/320b014e2fda509dc16409f76815ad0229e4fcec5ed229e64f7f917cc23f/psycopg2_binary-2.9.9-cp38-cp38-win_amd64.whl", hash = "sha256:a6cdcc3ede532f4a4b96000b6362099591ab4a3e913d70bcbac2b56c872446f7", size = 1155784 }, + { url = "https://files.pythonhosted.org/packages/82/69/c25f8bd5c189cee89bc00e16b49a84f930b3b4c2cfec953a26c99076a586/psycopg2_binary-2.9.9-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:72dffbd8b4194858d0941062a9766f8297e8868e1dd07a7b36212aaa90f49472", size = 2822507 }, + { url = "https://files.pythonhosted.org/packages/3e/06/7d0085889cba209185f1a52d646c4dbdbd9075345f4ca685bacf08d30755/psycopg2_binary-2.9.9-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:30dcc86377618a4c8f3b72418df92e77be4254d8f89f14b8e8f57d6d43603c0f", size = 2552664 }, + { url = "https://files.pythonhosted.org/packages/68/a2/67732accfffdb6696dc9523f82e91823e8cb1cc311f1c4ce006d2bb85016/psycopg2_binary-2.9.9-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:31a34c508c003a4347d389a9e6fcc2307cc2150eb516462a7a17512130de109e", size = 2850943 }, + { url = "https://files.pythonhosted.org/packages/f0/85/dff2170a1e6748b7068a4523ea9fef8373572c4cd283cffb4802f871a556/psycopg2_binary-2.9.9-cp39-cp39-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:15208be1c50b99203fe88d15695f22a5bed95ab3f84354c494bcb1d08557df67", size = 3080551 }, + { url = "https://files.pythonhosted.org/packages/2e/49/9550febcc90105089bb89881b8cba73db227b9685cfddaae2479791a2379/psycopg2_binary-2.9.9-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:1873aade94b74715be2246321c8650cabf5a0d098a95bab81145ffffa4c13876", size = 3264314 }, + { url = "https://files.pythonhosted.org/packages/65/04/d0266fd446cb65384ce5442bc08449fd0b5d3419494574f020275f9e2273/psycopg2_binary-2.9.9-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3a58c98a7e9c021f357348867f537017057c2ed7f77337fd914d0bedb35dace7", size = 3019531 }, + { url = "https://files.pythonhosted.org/packages/ba/7e/c91f4c1e364444c8f59e82501f600019717f265ae4092057cece02d2d945/psycopg2_binary-2.9.9-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:4686818798f9194d03c9129a4d9a702d9e113a89cb03bffe08c6cf799e053291", size = 2355811 }, + { url = "https://files.pythonhosted.org/packages/6b/ae/05d1e52e8535ef3c73fa327e179d982b903e2c08987fa0e2167842c153a7/psycopg2_binary-2.9.9-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:ebdc36bea43063116f0486869652cb2ed7032dbc59fbcb4445c4862b5c1ecf7f", size = 2534818 }, + { url = "https://files.pythonhosted.org/packages/cb/bd/e5fb2aa9737e50c0ffb9c3851710055eafedd4c8628c6ef9863bb2e9c434/psycopg2_binary-2.9.9-cp39-cp39-musllinux_1_1_ppc64le.whl", hash = "sha256:ca08decd2697fdea0aea364b370b1249d47336aec935f87b8bbfd7da5b2ee9c1", size = 2486605 }, + { url = "https://files.pythonhosted.org/packages/c5/22/0b832bc8a83d8fed74c5a45fbacf4a6e6eb66bcb0cd3836fca9a709f25f4/psycopg2_binary-2.9.9-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:ac05fb791acf5e1a3e39402641827780fe44d27e72567a000412c648a85ba860", size = 2454908 }, + { url = "https://files.pythonhosted.org/packages/0a/b7/3046fd37fdf84c1945741d16fa7536ddcf8576bad6d77ee2891c5255dce3/psycopg2_binary-2.9.9-cp39-cp39-win32.whl", hash = "sha256:9dba73be7305b399924709b91682299794887cbbd88e38226ed9f6712eabee90", size = 1037893 }, + { url = "https://files.pythonhosted.org/packages/cb/35/009b43d67a7010b789690a46d49521fd435ce33ce722fe8d7ac7efe35c21/psycopg2_binary-2.9.9-cp39-cp39-win_amd64.whl", hash = "sha256:f7ae5d65ccfbebdfa761585228eb4d0df3a8b15cfb53bd953e713e09fbb12957", size = 1177353 }, +] + +[[package]] +name = "pycodestyle" +version = "2.9.1" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/b6/83/5bcaedba1f47200f0665ceb07bcb00e2be123192742ee0edfb66b600e5fd/pycodestyle-2.9.1.tar.gz", hash = "sha256:2c9607871d58c76354b697b42f5d57e1ada7d261c261efac224b664affdc5785", size = 102127 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/67/e4/fc77f1039c34b3612c4867b69cbb2b8a4e569720b1f19b0637002ee03aff/pycodestyle-2.9.1-py2.py3-none-any.whl", hash = "sha256:d1735fc58b418fd7c5f658d28d943854f8a849b01a5d0a1e6f3f3fdd0166804b", size = 41493 }, +] + +[[package]] +name = "pycparser" +version = "2.22" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/1d/b2/31537cf4b1ca988837256c910a668b553fceb8f069bedc4b1c826024b52c/pycparser-2.22.tar.gz", hash = "sha256:491c8be9c040f5390f5bf44a5b07752bd07f56edf992381b05c701439eec10f6", size = 172736 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/13/a3/a812df4e2dd5696d1f351d58b8fe16a405b234ad2886a0dab9183fb78109/pycparser-2.22-py3-none-any.whl", hash = "sha256:c3702b6d3dd8c7abc1afa565d7e63d53a1d0bd86cdc24edd75470f4de499cfcc", size = 117552 }, +] + +[[package]] +name = "pyflakes" +version = "2.5.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/07/92/f0cb5381f752e89a598dd2850941e7f570ac3cb8ea4a344854de486db152/pyflakes-2.5.0.tar.gz", hash = "sha256:491feb020dca48ccc562a8c0cbe8df07ee13078df59813b83959cbdada312ea3", size = 66388 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/dc/13/63178f59f74e53acc2165aee4b002619a3cfa7eeaeac989a9eb41edf364e/pyflakes-2.5.0-py2.py3-none-any.whl", hash = "sha256:4579f67d887f804e67edb544428f264b7b24f435b263c4614f384135cea553d2", size = 66116 }, +] + +[[package]] +name = "pygments" +version = "2.18.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/8e/62/8336eff65bcbc8e4cb5d05b55faf041285951b6e80f33e2bff2024788f31/pygments-2.18.0.tar.gz", hash = "sha256:786ff802f32e91311bff3889f6e9a86e81505fe99f2735bb6d60ae0c5004f199", size = 4891905 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/f7/3f/01c8b82017c199075f8f788d0d906b9ffbbc5a47dc9918a945e13d5a2bda/pygments-2.18.0-py3-none-any.whl", hash = "sha256:b8e6aca0523f3ab76fee51799c488e38782ac06eafcf95e7ba832985c8e7b13a", size = 1205513 }, +] + +[[package]] +name = "pymysql" +version = "1.0.3" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/7a/6f/b3fadf41239b9ca7ea3857c440c499fd2e9e0f410bb942bd8d593dce4bd6/PyMySQL-1.0.3.tar.gz", hash = "sha256:3dda943ef3694068a75d69d071755dbecacee1adf9a1fc5b206830d2b67d25e8", size = 45712 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/5b/b1/bb485db528749f07d6f11aa123e5f931f2e465a9c27945d6122bae5f7df7/PyMySQL-1.0.3-py3-none-any.whl", hash = "sha256:89fc6ae41c0aeb6e1f7710cdd623702ea2c54d040565767a78b00a5ebb12f4e5", size = 43744 }, +] + +[[package]] +name = "pypng" +version = "0.20220715.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/93/cd/112f092ec27cca83e0516de0a3368dbd9128c187fb6b52aaaa7cde39c96d/pypng-0.20220715.0.tar.gz", hash = "sha256:739c433ba96f078315de54c0db975aee537cbc3e1d0ae4ed9aab0ca1e427e2c1", size = 128992 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/3e/b9/3766cc361d93edb2ce81e2e1f87dd98f314d7d513877a342d31b30741680/pypng-0.20220715.0-py3-none-any.whl", hash = "sha256:4a43e969b8f5aaafb2a415536c1a8ec7e341cd6a3f957fd5b5f32a4cfeed902c", size = 58057 }, +] + +[[package]] +name = "pyproject-hooks" +version = "1.2.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/e7/82/28175b2414effca1cdac8dc99f76d660e7a4fb0ceefa4b4ab8f5f6742925/pyproject_hooks-1.2.0.tar.gz", hash = "sha256:1e859bd5c40fae9448642dd871adf459e5e2084186e8d2c2a79a824c970da1f8", size = 19228 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/bd/24/12818598c362d7f300f18e74db45963dbcb85150324092410c8b49405e42/pyproject_hooks-1.2.0-py3-none-any.whl", hash = "sha256:9e5c6bfa8dcc30091c74b0cf803c81fdd29d94f01992a7707bc97babb1141913", size = 10216 }, +] + +[[package]] +name = "pytest" +version = "8.3.3" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "colorama", marker = "sys_platform == 'win32'" }, + { name = "exceptiongroup", marker = "python_full_version < '3.11'" }, + { name = "iniconfig" }, + { name = "packaging" }, + { name = "pluggy" }, + { name = "tomli", marker = "python_full_version < '3.11'" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/8b/6c/62bbd536103af674e227c41a8f3dcd022d591f6eed5facb5a0f31ee33bbc/pytest-8.3.3.tar.gz", hash = "sha256:70b98107bd648308a7952b06e6ca9a50bc660be218d53c257cc1fc94fda10181", size = 1442487 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/6b/77/7440a06a8ead44c7757a64362dd22df5760f9b12dc5f11b6188cd2fc27a0/pytest-8.3.3-py3-none-any.whl", hash = "sha256:a6853c7375b2663155079443d2e45de913a911a11d669df02a50814944db57b2", size = 342341 }, +] + +[[package]] +name = "pytest-flask" +version = "1.3.0" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "flask" }, + { name = "pytest" }, + { name = "werkzeug" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/fb/23/32b36d2f769805c0f3069ca8d9eeee77b27fcf86d41d40c6061ddce51c7d/pytest-flask-1.3.0.tar.gz", hash = "sha256:58be1c97b21ba3c4d47e0a7691eb41007748506c36bf51004f78df10691fa95e", size = 35816 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/de/03/7a917fda3d0e96b4e80ab1f83a6628ec4ee4a882523b49417d3891bacc9e/pytest_flask-1.3.0-py3-none-any.whl", hash = "sha256:c0e36e6b0fddc3b91c4362661db83fa694d1feb91fa505475be6732b5bc8c253", size = 13105 }, +] + +[[package]] +name = "pytest-libfaketime" +version = "0.1.3" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "libfaketime" }, + { name = "pytest" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/7b/eb/3f59bef7dd2a30e4bd16361c70294da9a1b670d0d0881bde60dc6bb1ee0e/pytest_libfaketime-0.1.3.tar.gz", hash = "sha256:113fa5cc364103eb290fb0c189bc2de6f3423c888263788c64dcfd01974a01c6", size = 2318 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/b5/c6/8ff351ab29bea0ee577e0d08c3ededf96b50dc2164cb71471b58764ac8e3/pytest_libfaketime-0.1.3-py3-none-any.whl", hash = "sha256:f2b79206f51ad69a7e905b154189dece6396e4a138cebc8897d96e2b999581f6", size = 2820 }, +] + +[[package]] +name = "python-dateutil" +version = "2.9.0.post0" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "six" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/66/c0/0c8b6ad9f17a802ee498c46e004a0eb49bc148f2fd230864601a86dcf6db/python-dateutil-2.9.0.post0.tar.gz", hash = "sha256:37dd54208da7e1cd875388217d5e00ebd4179249f90fb72437e91a35459a0ad3", size = 342432 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/ec/57/56b9bcc3c9c6a792fcbaf139543cee77261f3651ca9da0c93f5c1221264b/python_dateutil-2.9.0.post0-py2.py3-none-any.whl", hash = "sha256:a8b2bc7bffae282281c8140a97d3aa9c14da0b136dfe83f850eea9a5f7470427", size = 229892 }, +] + +[[package]] +name = "pytz" +version = "2024.2" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/3a/31/3c70bf7603cc2dca0f19bdc53b4537a797747a58875b552c8c413d963a3f/pytz-2024.2.tar.gz", hash = "sha256:2aa355083c50a0f93fa581709deac0c9ad65cca8a9e9beac660adcbd493c798a", size = 319692 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/11/c3/005fcca25ce078d2cc29fd559379817424e94885510568bc1bc53d7d5846/pytz-2024.2-py2.py3-none-any.whl", hash = "sha256:31c7c1817eb7fae7ca4b8c7ee50c72f93aa2dd863de768e1ef4245d426aa0725", size = 508002 }, +] + +[[package]] +name = "pywin32-ctypes" +version = "0.2.3" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/85/9f/01a1a99704853cb63f253eea009390c88e7131c67e66a0a02099a8c917cb/pywin32-ctypes-0.2.3.tar.gz", hash = "sha256:d162dc04946d704503b2edc4d55f3dba5c1d539ead017afa00142c38b9885755", size = 29471 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/de/3d/8161f7711c017e01ac9f008dfddd9410dff3674334c233bde66e7ba65bbf/pywin32_ctypes-0.2.3-py3-none-any.whl", hash = "sha256:8a1513379d709975552d202d942d9837758905c8d01eb82b8bcc30918929e7b8", size = 30756 }, +] + +[[package]] +name = "pyyaml" +version = "6.0.2" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/54/ed/79a089b6be93607fa5cdaedf301d7dfb23af5f25c398d5ead2525b063e17/pyyaml-6.0.2.tar.gz", hash = "sha256:d584d9ec91ad65861cc08d42e834324ef890a082e591037abe114850ff7bbc3e", size = 130631 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/9b/95/a3fac87cb7158e231b5a6012e438c647e1a87f09f8e0d123acec8ab8bf71/PyYAML-6.0.2-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:0a9a2848a5b7feac301353437eb7d5957887edbf81d56e903999a75a3d743086", size = 184199 }, + { url = "https://files.pythonhosted.org/packages/c7/7a/68bd47624dab8fd4afbfd3c48e3b79efe09098ae941de5b58abcbadff5cb/PyYAML-6.0.2-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:29717114e51c84ddfba879543fb232a6ed60086602313ca38cce623c1d62cfbf", size = 171758 }, + { url = "https://files.pythonhosted.org/packages/49/ee/14c54df452143b9ee9f0f29074d7ca5516a36edb0b4cc40c3f280131656f/PyYAML-6.0.2-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8824b5a04a04a047e72eea5cec3bc266db09e35de6bdfe34c9436ac5ee27d237", size = 718463 }, + { url = "https://files.pythonhosted.org/packages/4d/61/de363a97476e766574650d742205be468921a7b532aa2499fcd886b62530/PyYAML-6.0.2-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:7c36280e6fb8385e520936c3cb3b8042851904eba0e58d277dca80a5cfed590b", size = 719280 }, + { url = "https://files.pythonhosted.org/packages/6b/4e/1523cb902fd98355e2e9ea5e5eb237cbc5f3ad5f3075fa65087aa0ecb669/PyYAML-6.0.2-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ec031d5d2feb36d1d1a24380e4db6d43695f3748343d99434e6f5f9156aaa2ed", size = 751239 }, + { url = "https://files.pythonhosted.org/packages/b7/33/5504b3a9a4464893c32f118a9cc045190a91637b119a9c881da1cf6b7a72/PyYAML-6.0.2-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:936d68689298c36b53b29f23c6dbb74de12b4ac12ca6cfe0e047bedceea56180", size = 695802 }, + { url = "https://files.pythonhosted.org/packages/5c/20/8347dcabd41ef3a3cdc4f7b7a2aff3d06598c8779faa189cdbf878b626a4/PyYAML-6.0.2-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:23502f431948090f597378482b4812b0caae32c22213aecf3b55325e049a6c68", size = 720527 }, + { url = "https://files.pythonhosted.org/packages/be/aa/5afe99233fb360d0ff37377145a949ae258aaab831bde4792b32650a4378/PyYAML-6.0.2-cp310-cp310-win32.whl", hash = "sha256:2e99c6826ffa974fe6e27cdb5ed0021786b03fc98e5ee3c5bfe1fd5015f42b99", size = 144052 }, + { url = "https://files.pythonhosted.org/packages/b5/84/0fa4b06f6d6c958d207620fc60005e241ecedceee58931bb20138e1e5776/PyYAML-6.0.2-cp310-cp310-win_amd64.whl", hash = "sha256:a4d3091415f010369ae4ed1fc6b79def9416358877534caf6a0fdd2146c87a3e", size = 161774 }, + { url = "https://files.pythonhosted.org/packages/f8/aa/7af4e81f7acba21a4c6be026da38fd2b872ca46226673c89a758ebdc4fd2/PyYAML-6.0.2-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:cc1c1159b3d456576af7a3e4d1ba7e6924cb39de8f67111c735f6fc832082774", size = 184612 }, + { url = "https://files.pythonhosted.org/packages/8b/62/b9faa998fd185f65c1371643678e4d58254add437edb764a08c5a98fb986/PyYAML-6.0.2-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:1e2120ef853f59c7419231f3bf4e7021f1b936f6ebd222406c3b60212205d2ee", size = 172040 }, + { url = "https://files.pythonhosted.org/packages/ad/0c/c804f5f922a9a6563bab712d8dcc70251e8af811fce4524d57c2c0fd49a4/PyYAML-6.0.2-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5d225db5a45f21e78dd9358e58a98702a0302f2659a3c6cd320564b75b86f47c", size = 736829 }, + { url = "https://files.pythonhosted.org/packages/51/16/6af8d6a6b210c8e54f1406a6b9481febf9c64a3109c541567e35a49aa2e7/PyYAML-6.0.2-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:5ac9328ec4831237bec75defaf839f7d4564be1e6b25ac710bd1a96321cc8317", size = 764167 }, + { url = "https://files.pythonhosted.org/packages/75/e4/2c27590dfc9992f73aabbeb9241ae20220bd9452df27483b6e56d3975cc5/PyYAML-6.0.2-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3ad2a3decf9aaba3d29c8f537ac4b243e36bef957511b4766cb0057d32b0be85", size = 762952 }, + { url = "https://files.pythonhosted.org/packages/9b/97/ecc1abf4a823f5ac61941a9c00fe501b02ac3ab0e373c3857f7d4b83e2b6/PyYAML-6.0.2-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:ff3824dc5261f50c9b0dfb3be22b4567a6f938ccce4587b38952d85fd9e9afe4", size = 735301 }, + { url = "https://files.pythonhosted.org/packages/45/73/0f49dacd6e82c9430e46f4a027baa4ca205e8b0a9dce1397f44edc23559d/PyYAML-6.0.2-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:797b4f722ffa07cc8d62053e4cff1486fa6dc094105d13fea7b1de7d8bf71c9e", size = 756638 }, + { url = "https://files.pythonhosted.org/packages/22/5f/956f0f9fc65223a58fbc14459bf34b4cc48dec52e00535c79b8db361aabd/PyYAML-6.0.2-cp311-cp311-win32.whl", hash = "sha256:11d8f3dd2b9c1207dcaf2ee0bbbfd5991f571186ec9cc78427ba5bd32afae4b5", size = 143850 }, + { url = "https://files.pythonhosted.org/packages/ed/23/8da0bbe2ab9dcdd11f4f4557ccaf95c10b9811b13ecced089d43ce59c3c8/PyYAML-6.0.2-cp311-cp311-win_amd64.whl", hash = "sha256:e10ce637b18caea04431ce14fabcf5c64a1c61ec9c56b071a4b7ca131ca52d44", size = 161980 }, + { url = "https://files.pythonhosted.org/packages/86/0c/c581167fc46d6d6d7ddcfb8c843a4de25bdd27e4466938109ca68492292c/PyYAML-6.0.2-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:c70c95198c015b85feafc136515252a261a84561b7b1d51e3384e0655ddf25ab", size = 183873 }, + { url = "https://files.pythonhosted.org/packages/a8/0c/38374f5bb272c051e2a69281d71cba6fdb983413e6758b84482905e29a5d/PyYAML-6.0.2-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:ce826d6ef20b1bc864f0a68340c8b3287705cae2f8b4b1d932177dcc76721725", size = 173302 }, + { url = "https://files.pythonhosted.org/packages/c3/93/9916574aa8c00aa06bbac729972eb1071d002b8e158bd0e83a3b9a20a1f7/PyYAML-6.0.2-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1f71ea527786de97d1a0cc0eacd1defc0985dcf6b3f17bb77dcfc8c34bec4dc5", size = 739154 }, + { url = "https://files.pythonhosted.org/packages/95/0f/b8938f1cbd09739c6da569d172531567dbcc9789e0029aa070856f123984/PyYAML-6.0.2-cp312-cp312-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:9b22676e8097e9e22e36d6b7bda33190d0d400f345f23d4065d48f4ca7ae0425", size = 766223 }, + { url = "https://files.pythonhosted.org/packages/b9/2b/614b4752f2e127db5cc206abc23a8c19678e92b23c3db30fc86ab731d3bd/PyYAML-6.0.2-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:80bab7bfc629882493af4aa31a4cfa43a4c57c83813253626916b8c7ada83476", size = 767542 }, + { url = "https://files.pythonhosted.org/packages/d4/00/dd137d5bcc7efea1836d6264f049359861cf548469d18da90cd8216cf05f/PyYAML-6.0.2-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:0833f8694549e586547b576dcfaba4a6b55b9e96098b36cdc7ebefe667dfed48", size = 731164 }, + { url = "https://files.pythonhosted.org/packages/c9/1f/4f998c900485e5c0ef43838363ba4a9723ac0ad73a9dc42068b12aaba4e4/PyYAML-6.0.2-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:8b9c7197f7cb2738065c481a0461e50ad02f18c78cd75775628afb4d7137fb3b", size = 756611 }, + { url = "https://files.pythonhosted.org/packages/df/d1/f5a275fdb252768b7a11ec63585bc38d0e87c9e05668a139fea92b80634c/PyYAML-6.0.2-cp312-cp312-win32.whl", hash = "sha256:ef6107725bd54b262d6dedcc2af448a266975032bc85ef0172c5f059da6325b4", size = 140591 }, + { url = "https://files.pythonhosted.org/packages/0c/e8/4f648c598b17c3d06e8753d7d13d57542b30d56e6c2dedf9c331ae56312e/PyYAML-6.0.2-cp312-cp312-win_amd64.whl", hash = "sha256:7e7401d0de89a9a855c839bc697c079a4af81cf878373abd7dc625847d25cbd8", size = 156338 }, + { url = "https://files.pythonhosted.org/packages/ef/e3/3af305b830494fa85d95f6d95ef7fa73f2ee1cc8ef5b495c7c3269fb835f/PyYAML-6.0.2-cp313-cp313-macosx_10_13_x86_64.whl", hash = "sha256:efdca5630322a10774e8e98e1af481aad470dd62c3170801852d752aa7a783ba", size = 181309 }, + { url = "https://files.pythonhosted.org/packages/45/9f/3b1c20a0b7a3200524eb0076cc027a970d320bd3a6592873c85c92a08731/PyYAML-6.0.2-cp313-cp313-macosx_11_0_arm64.whl", hash = "sha256:50187695423ffe49e2deacb8cd10510bc361faac997de9efef88badc3bb9e2d1", size = 171679 }, + { url = "https://files.pythonhosted.org/packages/7c/9a/337322f27005c33bcb656c655fa78325b730324c78620e8328ae28b64d0c/PyYAML-6.0.2-cp313-cp313-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:0ffe8360bab4910ef1b9e87fb812d8bc0a308b0d0eef8c8f44e0254ab3b07133", size = 733428 }, + { url = "https://files.pythonhosted.org/packages/a3/69/864fbe19e6c18ea3cc196cbe5d392175b4cf3d5d0ac1403ec3f2d237ebb5/PyYAML-6.0.2-cp313-cp313-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:17e311b6c678207928d649faa7cb0d7b4c26a0ba73d41e99c4fff6b6c3276484", size = 763361 }, + { url = "https://files.pythonhosted.org/packages/04/24/b7721e4845c2f162d26f50521b825fb061bc0a5afcf9a386840f23ea19fa/PyYAML-6.0.2-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:70b189594dbe54f75ab3a1acec5f1e3faa7e8cf2f1e08d9b561cb41b845f69d5", size = 759523 }, + { url = "https://files.pythonhosted.org/packages/2b/b2/e3234f59ba06559c6ff63c4e10baea10e5e7df868092bf9ab40e5b9c56b6/PyYAML-6.0.2-cp313-cp313-musllinux_1_1_aarch64.whl", hash = "sha256:41e4e3953a79407c794916fa277a82531dd93aad34e29c2a514c2c0c5fe971cc", size = 726660 }, + { url = "https://files.pythonhosted.org/packages/fe/0f/25911a9f080464c59fab9027482f822b86bf0608957a5fcc6eaac85aa515/PyYAML-6.0.2-cp313-cp313-musllinux_1_1_x86_64.whl", hash = "sha256:68ccc6023a3400877818152ad9a1033e3db8625d899c72eacb5a668902e4d652", size = 751597 }, + { url = "https://files.pythonhosted.org/packages/14/0d/e2c3b43bbce3cf6bd97c840b46088a3031085179e596d4929729d8d68270/PyYAML-6.0.2-cp313-cp313-win32.whl", hash = "sha256:bc2fa7c6b47d6bc618dd7fb02ef6fdedb1090ec036abab80d4681424b84c1183", size = 140527 }, + { url = "https://files.pythonhosted.org/packages/fa/de/02b54f42487e3d3c6efb3f89428677074ca7bf43aae402517bc7cca949f3/PyYAML-6.0.2-cp313-cp313-win_amd64.whl", hash = "sha256:8388ee1976c416731879ac16da0aff3f63b286ffdd57cdeb95f3f2e085687563", size = 156446 }, + { url = "https://files.pythonhosted.org/packages/74/d9/323a59d506f12f498c2097488d80d16f4cf965cee1791eab58b56b19f47a/PyYAML-6.0.2-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:24471b829b3bf607e04e88d79542a9d48bb037c2267d7927a874e6c205ca7e9a", size = 183218 }, + { url = "https://files.pythonhosted.org/packages/74/cc/20c34d00f04d785f2028737e2e2a8254e1425102e730fee1d6396f832577/PyYAML-6.0.2-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d7fded462629cfa4b685c5416b949ebad6cec74af5e2d42905d41e257e0869f5", size = 728067 }, + { url = "https://files.pythonhosted.org/packages/20/52/551c69ca1501d21c0de51ddafa8c23a0191ef296ff098e98358f69080577/PyYAML-6.0.2-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:d84a1718ee396f54f3a086ea0a66d8e552b2ab2017ef8b420e92edbc841c352d", size = 757812 }, + { url = "https://files.pythonhosted.org/packages/fd/7f/2c3697bba5d4aa5cc2afe81826d73dfae5f049458e44732c7a0938baa673/PyYAML-6.0.2-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:9056c1ecd25795207ad294bcf39f2db3d845767be0ea6e6a34d856f006006083", size = 746531 }, + { url = "https://files.pythonhosted.org/packages/8c/ab/6226d3df99900e580091bb44258fde77a8433511a86883bd4681ea19a858/PyYAML-6.0.2-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:82d09873e40955485746739bcb8b4586983670466c23382c19cffecbf1fd8706", size = 800820 }, + { url = "https://files.pythonhosted.org/packages/a0/99/a9eb0f3e710c06c5d922026f6736e920d431812ace24aae38228d0d64b04/PyYAML-6.0.2-cp38-cp38-win32.whl", hash = "sha256:43fa96a3ca0d6b1812e01ced1044a003533c47f6ee8aca31724f78e93ccc089a", size = 145514 }, + { url = "https://files.pythonhosted.org/packages/75/8a/ee831ad5fafa4431099aa4e078d4c8efd43cd5e48fbc774641d233b683a9/PyYAML-6.0.2-cp38-cp38-win_amd64.whl", hash = "sha256:01179a4a8559ab5de078078f37e5c1a30d76bb88519906844fd7bdea1b7729ff", size = 162702 }, + { url = "https://files.pythonhosted.org/packages/65/d8/b7a1db13636d7fb7d4ff431593c510c8b8fca920ade06ca8ef20015493c5/PyYAML-6.0.2-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:688ba32a1cffef67fd2e9398a2efebaea461578b0923624778664cc1c914db5d", size = 184777 }, + { url = "https://files.pythonhosted.org/packages/0a/02/6ec546cd45143fdf9840b2c6be8d875116a64076218b61d68e12548e5839/PyYAML-6.0.2-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:a8786accb172bd8afb8be14490a16625cbc387036876ab6ba70912730faf8e1f", size = 172318 }, + { url = "https://files.pythonhosted.org/packages/0e/9a/8cc68be846c972bda34f6c2a93abb644fb2476f4dcc924d52175786932c9/PyYAML-6.0.2-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d8e03406cac8513435335dbab54c0d385e4a49e4945d2909a581c83647ca0290", size = 720891 }, + { url = "https://files.pythonhosted.org/packages/e9/6c/6e1b7f40181bc4805e2e07f4abc10a88ce4648e7e95ff1abe4ae4014a9b2/PyYAML-6.0.2-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:f753120cb8181e736c57ef7636e83f31b9c0d1722c516f7e86cf15b7aa57ff12", size = 722614 }, + { url = "https://files.pythonhosted.org/packages/3d/32/e7bd8535d22ea2874cef6a81021ba019474ace0d13a4819c2a4bce79bd6a/PyYAML-6.0.2-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3b1fdb9dc17f5a7677423d508ab4f243a726dea51fa5e70992e59a7411c89d19", size = 737360 }, + { url = "https://files.pythonhosted.org/packages/d7/12/7322c1e30b9be969670b672573d45479edef72c9a0deac3bb2868f5d7469/PyYAML-6.0.2-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:0b69e4ce7a131fe56b7e4d770c67429700908fc0752af059838b1cfb41960e4e", size = 699006 }, + { url = "https://files.pythonhosted.org/packages/82/72/04fcad41ca56491995076630c3ec1e834be241664c0c09a64c9a2589b507/PyYAML-6.0.2-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:a9f8c2e67970f13b16084e04f134610fd1d374bf477b17ec1599185cf611d725", size = 723577 }, + { url = "https://files.pythonhosted.org/packages/ed/5e/46168b1f2757f1fcd442bc3029cd8767d88a98c9c05770d8b420948743bb/PyYAML-6.0.2-cp39-cp39-win32.whl", hash = "sha256:6395c297d42274772abc367baaa79683958044e5d3835486c16da75d2a694631", size = 144593 }, + { url = "https://files.pythonhosted.org/packages/19/87/5124b1c1f2412bb95c59ec481eaf936cd32f0fe2a7b16b97b81c4c017a6a/PyYAML-6.0.2-cp39-cp39-win_amd64.whl", hash = "sha256:39693e1f8320ae4f43943590b49779ffb98acb81f788220ea932a6b6c51004d8", size = 162312 }, +] + +[[package]] +name = "qrcode" +version = "7.4.2" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "colorama", marker = "platform_system == 'Windows'" }, + { name = "pypng" }, + { name = "typing-extensions" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/30/35/ad6d4c5a547fe9a5baf85a9edbafff93fc6394b014fab30595877305fa59/qrcode-7.4.2.tar.gz", hash = "sha256:9dd969454827e127dbd93696b20747239e6d540e082937c90f14ac95b30f5845", size = 535974 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/24/79/aaf0c1c7214f2632badb2771d770b1500d3d7cbdf2590ae62e721ec50584/qrcode-7.4.2-py3-none-any.whl", hash = "sha256:581dca7a029bcb2deef5d01068e39093e80ef00b4a61098a2182eac59d01643a", size = 46197 }, +] + +[[package]] +name = "readme-renderer" +version = "43.0" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "docutils" }, + { name = "nh3" }, + { name = "pygments" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/fe/b5/536c775084d239df6345dccf9b043419c7e3308bc31be4c7882196abc62e/readme_renderer-43.0.tar.gz", hash = "sha256:1818dd28140813509eeed8d62687f7cd4f7bad90d4db586001c5dc09d4fde311", size = 31768 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/45/be/3ea20dc38b9db08387cf97997a85a7d51527ea2057d71118feb0aa8afa55/readme_renderer-43.0-py3-none-any.whl", hash = "sha256:19db308d86ecd60e5affa3b2a98f017af384678c63c88e5d4556a380e674f3f9", size = 13301 }, +] + +[package.optional-dependencies] +md = [ + { name = "cmarkgfm" }, +] + +[[package]] +name = "requests" +version = "2.32.3" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "certifi" }, + { name = "charset-normalizer" }, + { name = "idna" }, + { name = "urllib3" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/63/70/2bf7780ad2d390a8d301ad0b550f1581eadbd9a20f896afe06353c2a2913/requests-2.32.3.tar.gz", hash = "sha256:55365417734eb18255590a9ff9eb97e9e1da868d4ccd6402399eaf68af20a760", size = 131218 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/f9/9b/335f9764261e915ed497fcdeb11df5dfd6f7bf257d4a6a2a686d80da4d54/requests-2.32.3-py3-none-any.whl", hash = "sha256:70761cfe03c773ceb22aa2f671b4757976145175cdfca038c02654d061d6dcc6", size = 64928 }, +] + +[[package]] +name = "requests-toolbelt" +version = "1.0.0" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "requests" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/f3/61/d7545dafb7ac2230c70d38d31cbfe4cc64f7144dc41f6e4e4b78ecd9f5bb/requests-toolbelt-1.0.0.tar.gz", hash = "sha256:7681a0a3d047012b5bdc0ee37d7f8f07ebe76ab08caeccfc3921ce23c88d5bc6", size = 206888 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/3f/51/d4db610ef29373b879047326cbf6fa98b6c1969d6f6dc423279de2b1be2c/requests_toolbelt-1.0.0-py2.py3-none-any.whl", hash = "sha256:cccfdd665f0a24fcf4726e690f65639d272bb0637b9b92dfd91a5568ccf6bd06", size = 54481 }, +] + +[[package]] +name = "rfc3986" +version = "2.0.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/85/40/1520d68bfa07ab5a6f065a186815fb6610c86fe957bc065754e47f7b0840/rfc3986-2.0.0.tar.gz", hash = "sha256:97aacf9dbd4bfd829baad6e6309fa6573aaf1be3f6fa735c8ab05e46cecb261c", size = 49026 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/ff/9a/9afaade874b2fa6c752c36f1548f718b5b83af81ed9b76628329dab81c1b/rfc3986-2.0.0-py2.py3-none-any.whl", hash = "sha256:50b1502b60e289cb37883f3dfd34532b8873c7de9f49bb546641ce9cbd256ebd", size = 31326 }, +] + +[[package]] +name = "rich" +version = "12.6.0" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "commonmark" }, + { name = "pygments" }, + { name = "typing-extensions", marker = "python_full_version < '3.9'" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/11/23/814edf09ec6470d52022b9e95c23c1bef77f0bc451761e1504ebd09606d3/rich-12.6.0.tar.gz", hash = "sha256:ba3a3775974105c221d31141f2c116f4fd65c5ceb0698657a11e9f295ec93fd0", size = 220114 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/32/60/81ac2e7d1e3b861ab478a72e3b20fc91c4302acd2274822e493758941829/rich-12.6.0-py3-none-any.whl", hash = "sha256:a4eb26484f2c82589bd9a17c73d32a010b1e29d89f1604cd9bf3a2097b81bb5e", size = 237505 }, +] + +[[package]] +name = "ruff" +version = "0.6.8" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/74/f9/4ce3e765a72ab8fe0f80f48508ea38b4196daab3da14d803c21349b2d367/ruff-0.6.8.tar.gz", hash = "sha256:a5bf44b1aa0adaf6d9d20f86162b34f7c593bfedabc51239953e446aefc8ce18", size = 3084543 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/db/07/42ee57e8b76ca585297a663a552b4f6d6a99372ca47fdc2276ef72cc0f2f/ruff-0.6.8-py3-none-linux_armv6l.whl", hash = "sha256:77944bca110ff0a43b768f05a529fecd0706aac7bcce36d7f1eeb4cbfca5f0f2", size = 10404327 }, + { url = "https://files.pythonhosted.org/packages/eb/51/d42571ff8156d65086acb72d39aa64cb24181db53b497d0ed6293f43f07a/ruff-0.6.8-py3-none-macosx_10_12_x86_64.whl", hash = "sha256:27b87e1801e786cd6ede4ada3faa5e254ce774de835e6723fd94551464c56b8c", size = 10018797 }, + { url = "https://files.pythonhosted.org/packages/c1/d7/fa5514a60b03976af972b67fe345deb0335dc96b9f9a9fa4df9890472427/ruff-0.6.8-py3-none-macosx_11_0_arm64.whl", hash = "sha256:cd48f945da2a6334f1793d7f701725a76ba93bf3d73c36f6b21fb04d5338dcf5", size = 9691303 }, + { url = "https://files.pythonhosted.org/packages/d6/c4/d812a74976927e51d0782a47539069657ac78535779bfa4d061c4fc8d89d/ruff-0.6.8-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:677e03c00f37c66cea033274295a983c7c546edea5043d0c798833adf4cf4c6f", size = 10719452 }, + { url = "https://files.pythonhosted.org/packages/ec/b6/aa700c4ae6db9b3ee660e23f3c7db596e2b16a3034b797704fba33ddbc96/ruff-0.6.8-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:9f1476236b3eacfacfc0f66aa9e6cd39f2a624cb73ea99189556015f27c0bdeb", size = 10161353 }, + { url = "https://files.pythonhosted.org/packages/ea/39/0b10075ffcd52ff3a581b9b69eac53579deb230aad300ce8f9d0b58e77bc/ruff-0.6.8-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:6f5a2f17c7d32991169195d52a04c95b256378bbf0de8cb98478351eb70d526f", size = 10980630 }, + { url = "https://files.pythonhosted.org/packages/c1/af/9eb9efc98334f62652e2f9318f137b2667187851911fac3b395365a83708/ruff-0.6.8-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:5fd0d4b7b1457c49e435ee1e437900ced9b35cb8dc5178921dfb7d98d65a08d0", size = 11768996 }, + { url = "https://files.pythonhosted.org/packages/e0/59/8b1369cf7878358952b1c0a1559b4d6b5c824c003d09b0db26d26c9d094f/ruff-0.6.8-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:f8034b19b993e9601f2ddf2c517451e17a6ab5cdb1c13fdff50c1442a7171d87", size = 11317469 }, + { url = "https://files.pythonhosted.org/packages/b9/6d/e252e9b11bbca4114c386ee41ad559d0dac13246201d77ea1223c6fea17f/ruff-0.6.8-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:6cfb227b932ba8ef6e56c9f875d987973cd5e35bc5d05f5abf045af78ad8e098", size = 12467185 }, + { url = "https://files.pythonhosted.org/packages/48/44/7caa223af7d4ea0f0b2bd34acca65a7694a58317714675a2478815ab3f45/ruff-0.6.8-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6ef0411eccfc3909269fed47c61ffebdcb84a04504bafa6b6df9b85c27e813b0", size = 10887766 }, + { url = "https://files.pythonhosted.org/packages/81/ed/394aff3a785f171869158b9d5be61eec9ffb823c3ad5d2bdf2e5f13cb029/ruff-0.6.8-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:007dee844738c3d2e6c24ab5bc7d43c99ba3e1943bd2d95d598582e9c1b27750", size = 10711609 }, + { url = "https://files.pythonhosted.org/packages/47/31/f31d04c842e54699eab7e3b864538fea26e6c94b71806cd10aa49f13e1c1/ruff-0.6.8-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:ce60058d3cdd8490e5e5471ef086b3f1e90ab872b548814e35930e21d848c9ce", size = 10237621 }, + { url = "https://files.pythonhosted.org/packages/20/95/a764e84acf11d425f2f23b8b78b4fd715e9c20be4aac157c6414ca859a67/ruff-0.6.8-py3-none-musllinux_1_2_i686.whl", hash = "sha256:1085c455d1b3fdb8021ad534379c60353b81ba079712bce7a900e834859182fa", size = 10558329 }, + { url = "https://files.pythonhosted.org/packages/2a/76/d4e38846ac9f6dd62dce858a54583911361b5339dcf8f84419241efac93a/ruff-0.6.8-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:70edf6a93b19481affd287d696d9e311388d808671bc209fb8907b46a8c3af44", size = 10954102 }, + { url = "https://files.pythonhosted.org/packages/e7/36/f18c678da6c69f8d022480f3e8ddce6e4a52e07602c1d212056fbd234f8f/ruff-0.6.8-py3-none-win32.whl", hash = "sha256:792213f7be25316f9b46b854df80a77e0da87ec66691e8f012f887b4a671ab5a", size = 8511090 }, + { url = "https://files.pythonhosted.org/packages/4c/c4/0ca7d8ffa358b109db7d7d045a1a076fd8e5d9cbeae022242d3c060931da/ruff-0.6.8-py3-none-win_amd64.whl", hash = "sha256:ec0517dc0f37cad14a5319ba7bba6e7e339d03fbf967a6d69b0907d61be7a263", size = 9350079 }, + { url = "https://files.pythonhosted.org/packages/d9/bd/a8b0c64945a92eaeeb8d0283f27a726a776a1c9d12734d990c5fc7a1278c/ruff-0.6.8-py3-none-win_arm64.whl", hash = "sha256:8d3bb2e3fbb9875172119021a13eed38849e762499e3cfde9588e4b4d70968dc", size = 8669595 }, +] + +[[package]] +name = "secretstorage" +version = "3.3.3" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "cryptography" }, + { name = "jeepney" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/53/a4/f48c9d79cb507ed1373477dbceaba7401fd8a23af63b837fa61f1dcd3691/SecretStorage-3.3.3.tar.gz", hash = "sha256:2403533ef369eca6d2ba81718576c5e0f564d5cca1b58f73a8b23e7d4eeebd77", size = 19739 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/54/24/b4293291fa1dd830f353d2cb163295742fa87f179fcc8a20a306a81978b7/SecretStorage-3.3.3-py3-none-any.whl", hash = "sha256:f356e6628222568e3af06f2eba8df495efa13b3b63081dafd4f7d9a7b7bc9f99", size = 15221 }, +] + +[[package]] +name = "setuptools" +version = "75.1.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/27/b8/f21073fde99492b33ca357876430822e4800cdf522011f18041351dfa74b/setuptools-75.1.0.tar.gz", hash = "sha256:d59a21b17a275fb872a9c3dae73963160ae079f1049ed956880cd7c09b120538", size = 1348057 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/ff/ae/f19306b5a221f6a436d8f2238d5b80925004093fa3edea59835b514d9057/setuptools-75.1.0-py3-none-any.whl", hash = "sha256:35ab7fd3bcd95e6b7fd704e4a1539513edad446c097797f2985e0e4b960772f2", size = 1248506 }, +] + +[[package]] +name = "six" +version = "1.16.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/71/39/171f1c67cd00715f190ba0b100d606d440a28c93c7714febeca8b79af85e/six-1.16.0.tar.gz", hash = "sha256:1e61c37477a1626458e36f7b1d82aa5c9b094fa4802892072e49de9c60c4c926", size = 34041 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/d9/5a/e7c31adbe875f2abbb91bd84cf2dc52d792b5a01506781dbcf25c91daf11/six-1.16.0-py2.py3-none-any.whl", hash = "sha256:8abb2f1d86890a2dfb989f9a77cfcfd3e47c2a354b01111771326f8aa26e0254", size = 11053 }, +] + +[[package]] +name = "snowballstemmer" +version = "2.2.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/44/7b/af302bebf22c749c56c9c3e8ae13190b5b5db37a33d9068652e8f73b7089/snowballstemmer-2.2.0.tar.gz", hash = "sha256:09b16deb8547d3412ad7b590689584cd0fe25ec8db3be37788be3810cbf19cb1", size = 86699 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/ed/dc/c02e01294f7265e63a7315fe086dd1df7dacb9f840a804da846b96d01b96/snowballstemmer-2.2.0-py2.py3-none-any.whl", hash = "sha256:c8e1716e83cc398ae16824e5572ae04e0d9fc2c6b985fb0f900f5f0c96ecba1a", size = 93002 }, +] + +[[package]] +name = "sphinx" +version = "7.1.2" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "alabaster" }, + { name = "babel" }, + { name = "colorama", marker = "sys_platform == 'win32'" }, + { name = "docutils" }, + { name = "imagesize" }, + { name = "importlib-metadata", marker = "python_full_version < '3.10'" }, + { name = "jinja2" }, + { name = "packaging" }, + { name = "pygments" }, + { name = "requests" }, + { name = "snowballstemmer" }, + { name = "sphinxcontrib-applehelp" }, + { name = "sphinxcontrib-devhelp" }, + { name = "sphinxcontrib-htmlhelp" }, + { name = "sphinxcontrib-jsmath" }, + { name = "sphinxcontrib-qthelp" }, + { name = "sphinxcontrib-serializinghtml" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/dc/01/688bdf9282241dca09fe6e3a1110eda399fa9b10d0672db609e37c2e7a39/sphinx-7.1.2.tar.gz", hash = "sha256:780f4d32f1d7d1126576e0e5ecc19dc32ab76cd24e950228dcf7b1f6d3d9e22f", size = 6828258 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/48/17/325cf6a257d84751a48ae90752b3d8fe0be8f9535b6253add61c49d0d9bc/sphinx-7.1.2-py3-none-any.whl", hash = "sha256:d170a81825b2fcacb6dfd5a0d7f578a053e45d3f2b153fecc948c37344eb4cbe", size = 3169543 }, +] + +[[package]] +name = "sphinxcontrib-applehelp" +version = "1.0.4" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/32/df/45e827f4d7e7fcc84e853bcef1d836effd762d63ccb86f43ede4e98b478c/sphinxcontrib-applehelp-1.0.4.tar.gz", hash = "sha256:828f867945bbe39817c210a1abfd1bc4895c8b73fcaade56d45357a348a07d7e", size = 24766 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/06/c1/5e2cafbd03105ce50d8500f9b4e8a6e8d02e22d0475b574c3b3e9451a15f/sphinxcontrib_applehelp-1.0.4-py3-none-any.whl", hash = "sha256:29d341f67fb0f6f586b23ad80e072c8e6ad0b48417db2bde114a4c9746feb228", size = 120601 }, +] + +[[package]] +name = "sphinxcontrib-devhelp" +version = "1.0.2" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/98/33/dc28393f16385f722c893cb55539c641c9aaec8d1bc1c15b69ce0ac2dbb3/sphinxcontrib-devhelp-1.0.2.tar.gz", hash = "sha256:ff7f1afa7b9642e7060379360a67e9c41e8f3121f2ce9164266f61b9f4b338e4", size = 17398 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/c5/09/5de5ed43a521387f18bdf5f5af31d099605c992fd25372b2b9b825ce48ee/sphinxcontrib_devhelp-1.0.2-py2.py3-none-any.whl", hash = "sha256:8165223f9a335cc1af7ffe1ed31d2871f325254c0423bc0c4c7cd1c1e4734a2e", size = 84690 }, +] + +[[package]] +name = "sphinxcontrib-htmlhelp" +version = "2.0.1" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/b3/47/64cff68ea3aa450c373301e5bebfbb9fce0a3e70aca245fcadd4af06cd75/sphinxcontrib-htmlhelp-2.0.1.tar.gz", hash = "sha256:0cbdd302815330058422b98a113195c9249825d681e18f11e8b1f78a2f11efff", size = 27967 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/6e/ee/a1f5e39046cbb5f8bc8fba87d1ddf1c6643fbc9194e58d26e606de4b9074/sphinxcontrib_htmlhelp-2.0.1-py3-none-any.whl", hash = "sha256:c38cb46dccf316c79de6e5515e1770414b797162b23cd3d06e67020e1d2a6903", size = 99833 }, +] + +[[package]] +name = "sphinxcontrib-jsmath" +version = "1.0.1" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/b2/e8/9ed3830aeed71f17c026a07a5097edcf44b692850ef215b161b8ad875729/sphinxcontrib-jsmath-1.0.1.tar.gz", hash = "sha256:a9925e4a4587247ed2191a22df5f6970656cb8ca2bd6284309578f2153e0c4b8", size = 5787 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/c2/42/4c8646762ee83602e3fb3fbe774c2fac12f317deb0b5dbeeedd2d3ba4b77/sphinxcontrib_jsmath-1.0.1-py2.py3-none-any.whl", hash = "sha256:2ec2eaebfb78f3f2078e73666b1415417a116cc848b72e5172e596c871103178", size = 5071 }, +] + +[[package]] +name = "sphinxcontrib-qthelp" +version = "1.0.3" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/b1/8e/c4846e59f38a5f2b4a0e3b27af38f2fcf904d4bfd82095bf92de0b114ebd/sphinxcontrib-qthelp-1.0.3.tar.gz", hash = "sha256:4c33767ee058b70dba89a6fc5c1892c0d57a54be67ddd3e7875a18d14cba5a72", size = 21658 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/2b/14/05f9206cf4e9cfca1afb5fd224c7cd434dcc3a433d6d9e4e0264d29c6cdb/sphinxcontrib_qthelp-1.0.3-py2.py3-none-any.whl", hash = "sha256:bd9fc24bcb748a8d51fd4ecaade681350aa63009a347a8c14e637895444dfab6", size = 90609 }, +] + +[[package]] +name = "sphinxcontrib-serializinghtml" +version = "1.1.5" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/b5/72/835d6fadb9e5d02304cf39b18f93d227cd93abd3c41ebf58e6853eeb1455/sphinxcontrib-serializinghtml-1.1.5.tar.gz", hash = "sha256:aa5f6de5dfdf809ef505c4895e51ef5c9eac17d0f287933eb49ec495280b6952", size = 21019 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/c6/77/5464ec50dd0f1c1037e3c93249b040c8fc8078fdda97530eeb02424b6eea/sphinxcontrib_serializinghtml-1.1.5-py2.py3-none-any.whl", hash = "sha256:352a9a00ae864471d3a7ead8d7d79f5fc0b57e8b3f95e9867eb9eb28999b92fd", size = 94021 }, +] + +[[package]] +name = "sqlalchemy" +version = "1.4.54" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "greenlet", marker = "platform_machine == 'AMD64' or platform_machine == 'WIN32' or platform_machine == 'aarch64' or platform_machine == 'amd64' or platform_machine == 'ppc64le' or platform_machine == 'win32' or platform_machine == 'x86_64'" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/ce/af/20290b55d469e873cba9d41c0206ab5461ff49d759989b3fe65010f9d265/sqlalchemy-1.4.54.tar.gz", hash = "sha256:4470fbed088c35dc20b78a39aaf4ae54fe81790c783b3264872a0224f437c31a", size = 8470350 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/ef/7f/f7c1e0b65790649bd573f201aa958263a389f336d6e000a569275ff9bd97/SQLAlchemy-1.4.54-cp310-cp310-macosx_12_0_x86_64.whl", hash = "sha256:af00236fe21c4d4f4c227b6ccc19b44c594160cc3ff28d104cdce85855369277", size = 1573472 }, + { url = "https://files.pythonhosted.org/packages/e1/da/ff7f0fe50844496db523613979651f076f44da8625b8ad89c503dcff0a52/SQLAlchemy-1.4.54-cp310-cp310-manylinux1_x86_64.manylinux2010_x86_64.manylinux_2_12_x86_64.manylinux_2_5_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:1183599e25fa38a1a322294b949da02b4f0da13dbc2688ef9dbe746df573f8a6", size = 1639088 }, + { url = "https://files.pythonhosted.org/packages/04/45/3a35bb156aa2fd87b66a4992bb8d65593efd7e16ca2e0597e68c32c29037/SQLAlchemy-1.4.54-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1990d5a6a5dc358a0894c8ca02043fb9a5ad9538422001fb2826e91c50f1d539", size = 1627447 }, + { url = "https://files.pythonhosted.org/packages/fe/5b/ed36a50e7147d0d090cd8e35de3b18d2c69a3e85df3be5fe42a570d6c331/SQLAlchemy-1.4.54-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:14b3f4783275339170984cadda66e3ec011cce87b405968dc8d51cf0f9997b0d", size = 1639081 }, + { url = "https://files.pythonhosted.org/packages/4b/75/bfbdeb5dece7bc98acb414751a62ee43398b34b10133b1853f4282597757/SQLAlchemy-1.4.54-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6b24364150738ce488333b3fb48bfa14c189a66de41cd632796fbcacb26b4585", size = 1638975 }, + { url = "https://files.pythonhosted.org/packages/f7/62/358a9291d2fc3d51ad50557e126ad5f48200f199878437f7cb38817d607b/SQLAlchemy-1.4.54-cp310-cp310-win32.whl", hash = "sha256:a8a72259a1652f192c68377be7011eac3c463e9892ef2948828c7d58e4829988", size = 1591719 }, + { url = "https://files.pythonhosted.org/packages/10/ad/87cd5578efdcef43a08ce4a21448192abf46bf69a5678ac0039e44364914/SQLAlchemy-1.4.54-cp310-cp310-win_amd64.whl", hash = "sha256:b67589f7955924865344e6eacfdcf70675e64f36800a576aa5e961f0008cde2a", size = 1593512 }, + { url = "https://files.pythonhosted.org/packages/da/49/fb98983b5568e93696a25fd5bec1b789095b79a72d5f57c6effddaa81d0a/SQLAlchemy-1.4.54-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:b05e0626ec1c391432eabb47a8abd3bf199fb74bfde7cc44a26d2b1b352c2c6e", size = 1589301 }, + { url = "https://files.pythonhosted.org/packages/03/98/5a81430bbd646991346cb088a2bdc84d1bcd3dbe6b0cfc1aaa898370e5c7/SQLAlchemy-1.4.54-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:13e91d6892b5fcb94a36ba061fb7a1f03d0185ed9d8a77c84ba389e5bb05e936", size = 1629553 }, + { url = "https://files.pythonhosted.org/packages/f1/17/14e35db2b0d6deaa27691d014addbb0dd6f7e044f7ee465446a3c0c71404/SQLAlchemy-1.4.54-cp311-cp311-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:fb59a11689ff3c58e7652260127f9e34f7f45478a2f3ef831ab6db7bcd72108f", size = 1627640 }, + { url = "https://files.pythonhosted.org/packages/98/62/335006a8f2c98f704f391e1a0cc01446d1b1b9c198f579f03599f55bd860/SQLAlchemy-1.4.54-cp311-cp311-win32.whl", hash = "sha256:1390ca2d301a2708fd4425c6d75528d22f26b8f5cbc9faba1ddca136671432bc", size = 1591723 }, + { url = "https://files.pythonhosted.org/packages/e2/a1/6b4b8c07082920f5445ec65c221fa33baab102aced5dcc2d87a15d3f8db4/SQLAlchemy-1.4.54-cp311-cp311-win_amd64.whl", hash = "sha256:2b37931eac4b837c45e2522066bda221ac6d80e78922fb77c75eb12e4dbcdee5", size = 1593511 }, + { url = "https://files.pythonhosted.org/packages/a5/1b/aa9b99be95d1615f058b5827447c18505b7b3f1dfcbd6ce1b331c2107152/SQLAlchemy-1.4.54-cp312-cp312-macosx_10_9_universal2.whl", hash = "sha256:3f01c2629a7d6b30d8afe0326b8c649b74825a0e1ebdcb01e8ffd1c920deb07d", size = 1589983 }, + { url = "https://files.pythonhosted.org/packages/59/47/cb0fc64e5344f0a3d02216796c342525ab283f8f052d1c31a1d487d08aa0/SQLAlchemy-1.4.54-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:9c24dd161c06992ed16c5e528a75878edbaeced5660c3db88c820f1f0d3fe1f4", size = 1630158 }, + { url = "https://files.pythonhosted.org/packages/c0/8b/f45dd378f6c97e8ff9332ff3d03ecb0b8c491be5bb7a698783b5a2f358ec/SQLAlchemy-1.4.54-cp312-cp312-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:b5e0d47d619c739bdc636bbe007da4519fc953393304a5943e0b5aec96c9877c", size = 1629232 }, + { url = "https://files.pythonhosted.org/packages/0d/3c/884fe389f5bec86a310b81e79abaa1e26e5d78dc10a84d544a6822833e47/SQLAlchemy-1.4.54-cp312-cp312-win32.whl", hash = "sha256:12bc0141b245918b80d9d17eca94663dbd3f5266ac77a0be60750f36102bbb0f", size = 1592027 }, + { url = "https://files.pythonhosted.org/packages/01/c3/c690d037be57efd3a69cde16a2ef1bd2a905dafe869434d33836de0983d0/SQLAlchemy-1.4.54-cp312-cp312-win_amd64.whl", hash = "sha256:f941aaf15f47f316123e1933f9ea91a6efda73a161a6ab6046d1cde37be62c88", size = 1593827 }, + { url = "https://files.pythonhosted.org/packages/f2/04/66ce6c75569f0b9627b470de66f60a0cc6412fe3203b1fb8d433b9df5f84/SQLAlchemy-1.4.54-cp38-cp38-macosx_12_0_x86_64.whl", hash = "sha256:a49730afb716f3f675755afec109895cab95bc9875db7ffe2e42c1b1c6279482", size = 1573468 }, + { url = "https://files.pythonhosted.org/packages/9b/2f/6a2984e9e572996baf84c2595ee6667d239329621979d02e5dbb42964f71/SQLAlchemy-1.4.54-cp38-cp38-manylinux1_x86_64.manylinux2010_x86_64.manylinux_2_12_x86_64.manylinux_2_5_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:26e78444bc77d089e62874dc74df05a5c71f01ac598010a327881a48408d0064", size = 1640879 }, + { url = "https://files.pythonhosted.org/packages/a0/de/0275a86ee1b8c87823202d11978289a56f44a7ac39623c2ddea91af0a4ee/SQLAlchemy-1.4.54-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:02d2ecb9508f16ab9c5af466dfe5a88e26adf2e1a8d1c56eb616396ccae2c186", size = 1629504 }, + { url = "https://files.pythonhosted.org/packages/70/27/b4229d89862a15ccc4834daf24b9182feac686937ff1a2da5f5ea47b3f5d/SQLAlchemy-1.4.54-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:394b0135900b62dbf63e4809cdc8ac923182af2816d06ea61cd6763943c2cc05", size = 1640873 }, + { url = "https://files.pythonhosted.org/packages/02/0c/b2d0a3c6f90ba19c77f4d02e16ddcbb05cf05fe56860be37053907afa31c/SQLAlchemy-1.4.54-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5ed3576675c187e3baa80b02c4c9d0edfab78eff4e89dd9da736b921333a2432", size = 1640766 }, + { url = "https://files.pythonhosted.org/packages/e6/72/68fdcbed8ff41db8ec9cc63d6a72bd6e10ae2dee80492a240c726e42bbbc/SQLAlchemy-1.4.54-cp38-cp38-win32.whl", hash = "sha256:fc9ffd9a38e21fad3e8c5a88926d57f94a32546e937e0be46142b2702003eba7", size = 1591725 }, + { url = "https://files.pythonhosted.org/packages/5a/c8/df13167d3825683e0542965dfcfbc3e95b2f31469fd389dbb0390d39ff4c/SQLAlchemy-1.4.54-cp38-cp38-win_amd64.whl", hash = "sha256:a01bc25eb7a5688656c8770f931d5cb4a44c7de1b3cec69b84cc9745d1e4cc10", size = 1593545 }, + { url = "https://files.pythonhosted.org/packages/c0/2c/d29f176e46fb81cdacc30e1cd60bbd2f56e97ce533a603a86fb5755a2812/SQLAlchemy-1.4.54-cp39-cp39-macosx_12_0_x86_64.whl", hash = "sha256:0b76bbb1cbae618d10679be8966f6d66c94f301cfc15cb49e2f2382563fb6efb", size = 1573472 }, + { url = "https://files.pythonhosted.org/packages/66/7c/6c7bae8e5a6ecd4d3cc34a2a5929c0599b954cd00877a50772fa42304d78/SQLAlchemy-1.4.54-cp39-cp39-manylinux1_x86_64.manylinux2010_x86_64.manylinux_2_12_x86_64.manylinux_2_5_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:cdb2886c0be2c6c54d0651d5a61c29ef347e8eec81fd83afebbf7b59b80b7393", size = 1638334 }, + { url = "https://files.pythonhosted.org/packages/9f/84/719fa1c53f044aede7d20c5a0859f8302eadbf1777b054ebc8c46b46bf19/SQLAlchemy-1.4.54-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:954816850777ac234a4e32b8c88ac1f7847088a6e90cfb8f0e127a1bf3feddff", size = 1626761 }, + { url = "https://files.pythonhosted.org/packages/c4/89/7d0ab875d2e6f931617d4a8fff63436b2d05205f15de06ef29f6627759a1/SQLAlchemy-1.4.54-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:1d83cd1cc03c22d922ec94d0d5f7b7c96b1332f5e122e81b1a61fb22da77879a", size = 1638328 }, + { url = "https://files.pythonhosted.org/packages/4f/39/0c9186e581f07c2d58ab713490ab242920700ef162453cf6f0719c1661fe/SQLAlchemy-1.4.54-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:1576fba3616f79496e2f067262200dbf4aab1bb727cd7e4e006076686413c80c", size = 1638219 }, + { url = "https://files.pythonhosted.org/packages/3a/8b/4676c988e933dccc7f26a8222ad08ccf4cf1697bd2464cdde05f6bf07eb2/SQLAlchemy-1.4.54-cp39-cp39-win32.whl", hash = "sha256:3112de9e11ff1957148c6de1df2bc5cc1440ee36783412e5eedc6f53638a577d", size = 1591716 }, + { url = "https://files.pythonhosted.org/packages/68/24/70f788b22d0799e0a8b4e952d42629e48beca0e5fb30688b9a431b2c4058/SQLAlchemy-1.4.54-cp39-cp39-win_amd64.whl", hash = "sha256:6da60fb24577f989535b8fc8b2ddc4212204aaf02e53c4c7ac94ac364150ed08", size = 1593546 }, +] + +[[package]] +name = "sqlalchemy-continuum" +version = "1.4.2" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "sqlalchemy" }, + { name = "sqlalchemy-utils" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/05/81/76e0b16ca8575463ba83e014afe8a89443bbc6a896dad3c48068ce571611/sqlalchemy_continuum-1.4.2.tar.gz", hash = "sha256:0fd2be79f718eda47c2206879d92ec4ebf1889364637b3caf3ee5d34bd19c8e3", size = 81713 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/84/d4/c404ce46dc2d53e536f470e76d7f657de46cf091d5ba05d19040d420d825/SQLAlchemy_Continuum-1.4.2-py3-none-any.whl", hash = "sha256:154588d79deb8b1683b5f39c130e6f0ad793c0b2f27e8c210565c23fb6fe74de", size = 44789 }, +] + +[[package]] +name = "sqlalchemy-utils" +version = "0.41.2" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "sqlalchemy" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/4d/bf/abfd5474cdd89ddd36dbbde9c6efba16bfa7f5448913eba946fed14729da/SQLAlchemy-Utils-0.41.2.tar.gz", hash = "sha256:bc599c8c3b3319e53ce6c5c3c471120bd325d0071fb6f38a10e924e3d07b9990", size = 138017 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/d5/f0/dc4757b83ac1ab853cf222df8535ed73973e0c203d983982ba7b8bc60508/SQLAlchemy_Utils-0.41.2-py3-none-any.whl", hash = "sha256:85cf3842da2bf060760f955f8467b87983fb2e30f1764fd0e24a48307dc8ec6e", size = 93083 }, +] + +[[package]] +name = "tomli" +version = "2.0.1" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/c0/3f/d7af728f075fb08564c5949a9c95e44352e23dee646869fa104a3b2060a3/tomli-2.0.1.tar.gz", hash = "sha256:de526c12914f0c550d15924c62d72abc48d6fe7364aa87328337a31007fe8a4f", size = 15164 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/97/75/10a9ebee3fd790d20926a90a2547f0bf78f371b2f13aa822c759680ca7b9/tomli-2.0.1-py3-none-any.whl", hash = "sha256:939de3e7a6161af0c887ef91b7d41a53e7c5a1ca976325f429cb46ea9bc30ecc", size = 12757 }, +] + +[[package]] +name = "twine" +version = "5.1.1" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "importlib-metadata" }, + { name = "keyring" }, + { name = "pkginfo" }, + { name = "readme-renderer" }, + { name = "requests" }, + { name = "requests-toolbelt" }, + { name = "rfc3986" }, + { name = "rich" }, + { name = "urllib3" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/77/68/bd982e5e949ef8334e6f7dcf76ae40922a8750aa2e347291ae1477a4782b/twine-5.1.1.tar.gz", hash = "sha256:9aa0825139c02b3434d913545c7b847a21c835e11597f5255842d457da2322db", size = 225531 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/5d/ec/00f9d5fd040ae29867355e559a94e9a8429225a0284a3f5f091a3878bfc0/twine-5.1.1-py3-none-any.whl", hash = "sha256:215dbe7b4b94c2c50a7315c0275d2258399280fbb7d04182c7e55e24b5f93997", size = 38650 }, +] + +[[package]] +name = "typing-extensions" +version = "4.12.2" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/df/db/f35a00659bc03fec321ba8bce9420de607a1d37f8342eee1863174c69557/typing_extensions-4.12.2.tar.gz", hash = "sha256:1a7ead55c7e559dd4dee8856e3a88b41225abfe1ce8df57b7c13915fe121ffb8", size = 85321 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/26/9f/ad63fc0248c5379346306f8668cda6e2e2e9c95e01216d2b8ffd9ff037d0/typing_extensions-4.12.2-py3-none-any.whl", hash = "sha256:04e5ca0351e0f3f85c6853954072df659d0d13fac324d0072316b67d7794700d", size = 37438 }, +] + +[[package]] +name = "urllib3" +version = "2.2.3" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/ed/63/22ba4ebfe7430b76388e7cd448d5478814d3032121827c12a2cc287e2260/urllib3-2.2.3.tar.gz", hash = "sha256:e7d814a81dad81e6caf2ec9fdedb284ecc9c73076b62654547cc64ccdcae26e9", size = 300677 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/ce/d9/5f4c13cecde62396b0d3fe530a50ccea91e7dfc1ccf0e09c228841bb5ba8/urllib3-2.2.3-py3-none-any.whl", hash = "sha256:ca899ca043dcb1bafa3e262d73aa25c465bfb49e0bd9dd5d59f1d0acba2f8fac", size = 126338 }, +] + +[[package]] +name = "vermin" +version = "1.5.2" +source = { registry = "https://pypi.org/simple" } +wheels = [ + { url = "https://files.pythonhosted.org/packages/46/ed/420955392d9c2743c93e0418928927e34aba355c716a70c6bdba209b930f/vermin-1.5.2-py2.py3-none-any.whl", hash = "sha256:c1566ad4e1c8e1b0e98cf5f7d69b691d44a578e2ce9c5aa1d418736bc4944b32", size = 89266 }, +] + +[[package]] +name = "werkzeug" +version = "2.3.8" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "markupsafe" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/3d/4b/d746f1000782c89d6c97df9df43ba8f4d126038608843d3560ae88d201b5/werkzeug-2.3.8.tar.gz", hash = "sha256:554b257c74bbeb7a0d254160a4f8ffe185243f52a52035060b761ca62d977f03", size = 819747 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/fd/21/0a674dfe66e9df9072c46269c882e9f901d36d987d8ea50ead033a9c1e01/werkzeug-2.3.8-py3-none-any.whl", hash = "sha256:bba1f19f8ec89d4d607a3bd62f1904bd2e609472d93cd85e9d4e178f472c3748", size = 242332 }, +] + +[[package]] +name = "wrapt" +version = "1.16.0" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/95/4c/063a912e20bcef7124e0df97282a8af3ff3e4b603ce84c481d6d7346be0a/wrapt-1.16.0.tar.gz", hash = "sha256:5f370f952971e7d17c7d1ead40e49f32345a7f7a5373571ef44d800d06b1899d", size = 53972 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/a8/c6/5375258add3777494671d8cec27cdf5402abd91016dee24aa2972c61fedf/wrapt-1.16.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:ffa565331890b90056c01db69c0fe634a776f8019c143a5ae265f9c6bc4bd6d4", size = 37315 }, + { url = "https://files.pythonhosted.org/packages/32/12/e11adfde33444986135d8881b401e4de6cbb4cced046edc6b464e6ad7547/wrapt-1.16.0-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:e4fdb9275308292e880dcbeb12546df7f3e0f96c6b41197e0cf37d2826359020", size = 38160 }, + { url = "https://files.pythonhosted.org/packages/70/7d/3dcc4a7e96f8d3e398450ec7703db384413f79bd6c0196e0e139055ce00f/wrapt-1.16.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:bb2dee3874a500de01c93d5c71415fcaef1d858370d405824783e7a8ef5db440", size = 80419 }, + { url = "https://files.pythonhosted.org/packages/d1/c4/8dfdc3c2f0b38be85c8d9fdf0011ebad2f54e40897f9549a356bebb63a97/wrapt-1.16.0-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:2a88e6010048489cda82b1326889ec075a8c856c2e6a256072b28eaee3ccf487", size = 72669 }, + { url = "https://files.pythonhosted.org/packages/49/83/b40bc1ad04a868b5b5bcec86349f06c1ee1ea7afe51dc3e46131e4f39308/wrapt-1.16.0-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ac83a914ebaf589b69f7d0a1277602ff494e21f4c2f743313414378f8f50a4cf", size = 80271 }, + { url = "https://files.pythonhosted.org/packages/19/d4/cd33d3a82df73a064c9b6401d14f346e1d2fb372885f0295516ec08ed2ee/wrapt-1.16.0-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:73aa7d98215d39b8455f103de64391cb79dfcad601701a3aa0dddacf74911d72", size = 84748 }, + { url = "https://files.pythonhosted.org/packages/ef/58/2fde309415b5fa98fd8f5f4a11886cbf276824c4c64d45a39da342fff6fe/wrapt-1.16.0-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:807cc8543a477ab7422f1120a217054f958a66ef7314f76dd9e77d3f02cdccd0", size = 77522 }, + { url = "https://files.pythonhosted.org/packages/07/44/359e4724a92369b88dbf09878a7cde7393cf3da885567ea898e5904049a3/wrapt-1.16.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:bf5703fdeb350e36885f2875d853ce13172ae281c56e509f4e6eca049bdfb136", size = 84780 }, + { url = "https://files.pythonhosted.org/packages/88/8f/706f2fee019360cc1da652353330350c76aa5746b4e191082e45d6838faf/wrapt-1.16.0-cp310-cp310-win32.whl", hash = "sha256:f6b2d0c6703c988d334f297aa5df18c45e97b0af3679bb75059e0e0bd8b1069d", size = 35335 }, + { url = "https://files.pythonhosted.org/packages/19/2b/548d23362e3002ebbfaefe649b833fa43f6ca37ac3e95472130c4b69e0b4/wrapt-1.16.0-cp310-cp310-win_amd64.whl", hash = "sha256:decbfa2f618fa8ed81c95ee18a387ff973143c656ef800c9f24fb7e9c16054e2", size = 37528 }, + { url = "https://files.pythonhosted.org/packages/fd/03/c188ac517f402775b90d6f312955a5e53b866c964b32119f2ed76315697e/wrapt-1.16.0-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:1a5db485fe2de4403f13fafdc231b0dbae5eca4359232d2efc79025527375b09", size = 37313 }, + { url = "https://files.pythonhosted.org/packages/0f/16/ea627d7817394db04518f62934a5de59874b587b792300991b3c347ff5e0/wrapt-1.16.0-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:75ea7d0ee2a15733684badb16de6794894ed9c55aa5e9903260922f0482e687d", size = 38164 }, + { url = "https://files.pythonhosted.org/packages/7f/a7/f1212ba098f3de0fd244e2de0f8791ad2539c03bef6c05a9fcb03e45b089/wrapt-1.16.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:a452f9ca3e3267cd4d0fcf2edd0d035b1934ac2bd7e0e57ac91ad6b95c0c6389", size = 80890 }, + { url = "https://files.pythonhosted.org/packages/b7/96/bb5e08b3d6db003c9ab219c487714c13a237ee7dcc572a555eaf1ce7dc82/wrapt-1.16.0-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:43aa59eadec7890d9958748db829df269f0368521ba6dc68cc172d5d03ed8060", size = 73118 }, + { url = "https://files.pythonhosted.org/packages/6e/52/2da48b35193e39ac53cfb141467d9f259851522d0e8c87153f0ba4205fb1/wrapt-1.16.0-cp311-cp311-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:72554a23c78a8e7aa02abbd699d129eead8b147a23c56e08d08dfc29cfdddca1", size = 80746 }, + { url = "https://files.pythonhosted.org/packages/11/fb/18ec40265ab81c0e82a934de04596b6ce972c27ba2592c8b53d5585e6bcd/wrapt-1.16.0-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:d2efee35b4b0a347e0d99d28e884dfd82797852d62fcd7ebdeee26f3ceb72cf3", size = 85668 }, + { url = "https://files.pythonhosted.org/packages/0f/ef/0ecb1fa23145560431b970418dce575cfaec555ab08617d82eb92afc7ccf/wrapt-1.16.0-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:6dcfcffe73710be01d90cae08c3e548d90932d37b39ef83969ae135d36ef3956", size = 78556 }, + { url = "https://files.pythonhosted.org/packages/25/62/cd284b2b747f175b5a96cbd8092b32e7369edab0644c45784871528eb852/wrapt-1.16.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:eb6e651000a19c96f452c85132811d25e9264d836951022d6e81df2fff38337d", size = 85712 }, + { url = "https://files.pythonhosted.org/packages/e5/a7/47b7ff74fbadf81b696872d5ba504966591a3468f1bc86bca2f407baef68/wrapt-1.16.0-cp311-cp311-win32.whl", hash = "sha256:66027d667efe95cc4fa945af59f92c5a02c6f5bb6012bff9e60542c74c75c362", size = 35327 }, + { url = "https://files.pythonhosted.org/packages/cf/c3/0084351951d9579ae83a3d9e38c140371e4c6b038136909235079f2e6e78/wrapt-1.16.0-cp311-cp311-win_amd64.whl", hash = "sha256:aefbc4cb0a54f91af643660a0a150ce2c090d3652cf4052a5397fb2de549cd89", size = 37523 }, + { url = "https://files.pythonhosted.org/packages/92/17/224132494c1e23521868cdd57cd1e903f3b6a7ba6996b7b8f077ff8ac7fe/wrapt-1.16.0-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:5eb404d89131ec9b4f748fa5cfb5346802e5ee8836f57d516576e61f304f3b7b", size = 37614 }, + { url = "https://files.pythonhosted.org/packages/6a/d7/cfcd73e8f4858079ac59d9db1ec5a1349bc486ae8e9ba55698cc1f4a1dff/wrapt-1.16.0-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:9090c9e676d5236a6948330e83cb89969f433b1943a558968f659ead07cb3b36", size = 38316 }, + { url = "https://files.pythonhosted.org/packages/7e/79/5ff0a5c54bda5aec75b36453d06be4f83d5cd4932cc84b7cb2b52cee23e2/wrapt-1.16.0-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:94265b00870aa407bd0cbcfd536f17ecde43b94fb8d228560a1e9d3041462d73", size = 86322 }, + { url = "https://files.pythonhosted.org/packages/c4/81/e799bf5d419f422d8712108837c1d9bf6ebe3cb2a81ad94413449543a923/wrapt-1.16.0-cp312-cp312-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:f2058f813d4f2b5e3a9eb2eb3faf8f1d99b81c3e51aeda4b168406443e8ba809", size = 79055 }, + { url = "https://files.pythonhosted.org/packages/62/62/30ca2405de6a20448ee557ab2cd61ab9c5900be7cbd18a2639db595f0b98/wrapt-1.16.0-cp312-cp312-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:98b5e1f498a8ca1858a1cdbffb023bfd954da4e3fa2c0cb5853d40014557248b", size = 87291 }, + { url = "https://files.pythonhosted.org/packages/49/4e/5d2f6d7b57fc9956bf06e944eb00463551f7d52fc73ca35cfc4c2cdb7aed/wrapt-1.16.0-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:14d7dc606219cdd7405133c713f2c218d4252f2a469003f8c46bb92d5d095d81", size = 90374 }, + { url = "https://files.pythonhosted.org/packages/a6/9b/c2c21b44ff5b9bf14a83252a8b973fb84923764ff63db3e6dfc3895cf2e0/wrapt-1.16.0-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:49aac49dc4782cb04f58986e81ea0b4768e4ff197b57324dcbd7699c5dfb40b9", size = 83896 }, + { url = "https://files.pythonhosted.org/packages/14/26/93a9fa02c6f257df54d7570dfe8011995138118d11939a4ecd82cb849613/wrapt-1.16.0-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:418abb18146475c310d7a6dc71143d6f7adec5b004ac9ce08dc7a34e2babdc5c", size = 91738 }, + { url = "https://files.pythonhosted.org/packages/a2/5b/4660897233eb2c8c4de3dc7cefed114c61bacb3c28327e64150dc44ee2f6/wrapt-1.16.0-cp312-cp312-win32.whl", hash = "sha256:685f568fa5e627e93f3b52fda002c7ed2fa1800b50ce51f6ed1d572d8ab3e7fc", size = 35568 }, + { url = "https://files.pythonhosted.org/packages/5c/cc/8297f9658506b224aa4bd71906447dea6bb0ba629861a758c28f67428b91/wrapt-1.16.0-cp312-cp312-win_amd64.whl", hash = "sha256:dcdba5c86e368442528f7060039eda390cc4091bfd1dca41e8046af7c910dda8", size = 37653 }, + { url = "https://files.pythonhosted.org/packages/fe/9e/d3bc95e75670ba15c5b25ecf07fc49941843e2678d777ca59339348d1c96/wrapt-1.16.0-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:1dd50a2696ff89f57bd8847647a1c363b687d3d796dc30d4dd4a9d1689a706f0", size = 37320 }, + { url = "https://files.pythonhosted.org/packages/72/b5/0c9be75f826c8e8d583a4ab312552d63d9f7c0768710146a22ac59bda4a9/wrapt-1.16.0-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:44a2754372e32ab315734c6c73b24351d06e77ffff6ae27d2ecf14cf3d229202", size = 38163 }, + { url = "https://files.pythonhosted.org/packages/69/21/b2ba809bafc9b6265e359f9c259c6d9a52a16cf6be20c72d95e76da609dd/wrapt-1.16.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8e9723528b9f787dc59168369e42ae1c3b0d3fadb2f1a71de14531d321ee05b0", size = 83535 }, + { url = "https://files.pythonhosted.org/packages/58/43/d72e625edb5926483c9868214d25b5e7d5858ace6a80c9dfddfbadf4d8f9/wrapt-1.16.0-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:dbed418ba5c3dce92619656802cc5355cb679e58d0d89b50f116e4a9d5a9603e", size = 75975 }, + { url = "https://files.pythonhosted.org/packages/ef/c6/56e718e2c58a4078518c14d97e531ef1e9e8a5c1ddafdc0d264a92be1a1a/wrapt-1.16.0-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:941988b89b4fd6b41c3f0bfb20e92bd23746579736b7343283297c4c8cbae68f", size = 83363 }, + { url = "https://files.pythonhosted.org/packages/34/49/589db6fa2d5d428b71716815bca8b39196fdaeea7c247a719ed2f93b0ab4/wrapt-1.16.0-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:6a42cd0cfa8ffc1915aef79cb4284f6383d8a3e9dcca70c445dcfdd639d51267", size = 87739 }, + { url = "https://files.pythonhosted.org/packages/c5/40/3eabe06c8dc54fada7364f34e8caa562efe3bf3f769bf3258de9c785a27f/wrapt-1.16.0-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:1ca9b6085e4f866bd584fb135a041bfc32cab916e69f714a7d1d397f8c4891ca", size = 80700 }, + { url = "https://files.pythonhosted.org/packages/15/4e/081f59237b620a124b035f1229f55db40841a9339fdb8ef60b4decc44df9/wrapt-1.16.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:d5e49454f19ef621089e204f862388d29e6e8d8b162efce05208913dde5b9ad6", size = 87783 }, + { url = "https://files.pythonhosted.org/packages/3a/ad/9d26a33bc80444ff97b937f94611f3b986fd40f735823558dfdf05ef9db8/wrapt-1.16.0-cp38-cp38-win32.whl", hash = "sha256:c31f72b1b6624c9d863fc095da460802f43a7c6868c5dda140f51da24fd47d7b", size = 35332 }, + { url = "https://files.pythonhosted.org/packages/01/db/4b29ba5f97d2a0aa97ec41eba1036b7c3eaf6e61e1f4639420cec2463a01/wrapt-1.16.0-cp38-cp38-win_amd64.whl", hash = "sha256:490b0ee15c1a55be9c1bd8609b8cecd60e325f0575fc98f50058eae366e01f41", size = 37524 }, + { url = "https://files.pythonhosted.org/packages/70/cc/b92e1da2cad6a9f8ee481000ece07a35e3b24e041e60ff8b850c079f0ebf/wrapt-1.16.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:9b201ae332c3637a42f02d1045e1d0cccfdc41f1f2f801dafbaa7e9b4797bfc2", size = 37314 }, + { url = "https://files.pythonhosted.org/packages/4a/cc/3402bcc897978be00fef608cd9e3e39ec8869c973feeb5e1e277670e5ad2/wrapt-1.16.0-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:2076fad65c6736184e77d7d4729b63a6d1ae0b70da4868adeec40989858eb3fb", size = 38162 }, + { url = "https://files.pythonhosted.org/packages/28/d3/4f079f649c515727c127c987b2ec2e0816b80d95784f2d28d1a57d2a1029/wrapt-1.16.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c5cd603b575ebceca7da5a3a251e69561bec509e0b46e4993e1cac402b7247b8", size = 80235 }, + { url = "https://files.pythonhosted.org/packages/a3/1c/226c2a4932e578a2241dcb383f425995f80224b446f439c2e112eb51c3a6/wrapt-1.16.0-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:b47cfad9e9bbbed2339081f4e346c93ecd7ab504299403320bf85f7f85c7d46c", size = 72553 }, + { url = "https://files.pythonhosted.org/packages/b1/e7/459a8a4f40f2fa65eb73cb3f339e6d152957932516d18d0e996c7ae2d7ae/wrapt-1.16.0-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f8212564d49c50eb4565e502814f694e240c55551a5f1bc841d4fcaabb0a9b8a", size = 80129 }, + { url = "https://files.pythonhosted.org/packages/da/6f/6d0b3c4983f1fc764a422989dabc268ee87d937763246cd48aa92f1eed1e/wrapt-1.16.0-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:5f15814a33e42b04e3de432e573aa557f9f0f56458745c2074952f564c50e664", size = 84550 }, + { url = "https://files.pythonhosted.org/packages/96/e8/27ef35cf61e5147c1c3abcb89cfbb8d691b2bb8364803fcc950140bc14d8/wrapt-1.16.0-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:db2e408d983b0e61e238cf579c09ef7020560441906ca990fe8412153e3b291f", size = 77352 }, + { url = "https://files.pythonhosted.org/packages/b6/ad/7a0766341081bfd9f18a7049e4d6d45586ae5c5bb0a640f05e2f558e849c/wrapt-1.16.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:edfad1d29c73f9b863ebe7082ae9321374ccb10879eeabc84ba3b69f2579d537", size = 84626 }, + { url = "https://files.pythonhosted.org/packages/09/43/b26852e9c45a1aac0d14b1080b25b612fa840ba99739c5fc55db07b7ce08/wrapt-1.16.0-cp39-cp39-win32.whl", hash = "sha256:ed867c42c268f876097248e05b6117a65bcd1e63b779e916fe2e33cd6fd0d3c3", size = 35327 }, + { url = "https://files.pythonhosted.org/packages/74/f2/96ed140b08743f7f68d5bda35a2a589600781366c3da96f056043d258b1a/wrapt-1.16.0-cp39-cp39-win_amd64.whl", hash = "sha256:eb1b046be06b0fce7249f1d025cd359b4b80fc1c3e24ad9eca33e0dcdb2e4a35", size = 37526 }, + { url = "https://files.pythonhosted.org/packages/ff/21/abdedb4cdf6ff41ebf01a74087740a709e2edb146490e4d9beea054b0b7a/wrapt-1.16.0-py3-none-any.whl", hash = "sha256:6906c4100a8fcbf2fa735f6059214bb13b97f75b1a61777fcf6432121ef12ef1", size = 23362 }, +] + +[[package]] +name = "wtforms" +version = "3.1.2" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "markupsafe" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/6a/c7/96d10183c3470f1836846f7b9527d6cb0b6c2226ebca40f36fa29f23de60/wtforms-3.1.2.tar.gz", hash = "sha256:f8d76180d7239c94c6322f7990ae1216dae3659b7aa1cee94b6318bdffb474b9", size = 134705 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/18/19/c3232f35e24dccfad372e9f341c4f3a1166ae7c66e4e1351a9467c921cc1/wtforms-3.1.2-py3-none-any.whl", hash = "sha256:bf831c042829c8cdbad74c27575098d541d039b1faa74c771545ecac916f2c07", size = 145961 }, +] + +[[package]] +name = "zest-releaser" +version = "9.2.0" +source = { registry = "https://pypi.org/simple" } +dependencies = [ + { name = "build" }, + { name = "colorama" }, + { name = "readme-renderer", extra = ["md"] }, + { name = "requests" }, + { name = "setuptools" }, + { name = "tomli", marker = "python_full_version < '3.11'" }, + { name = "twine" }, +] +sdist = { url = "https://files.pythonhosted.org/packages/b3/db/e9ff1b6d08a6a0cff944803abafa4658d6725e8d367ed810dc2db63b8a55/zest.releaser-9.2.0.tar.gz", hash = "sha256:f6cdbb15a125838144135176182e42d5b04eaae467df9d7b1e77ac24dd4d6266", size = 120373 } + +[[package]] +name = "zipp" +version = "3.20.2" +source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/54/bf/5c0000c44ebc80123ecbdddba1f5dcd94a5ada602a9c225d84b5aaa55e86/zipp-3.20.2.tar.gz", hash = "sha256:bc9eb26f4506fda01b81bcde0ca78103b6e62f991b381fec825435c836edbc29", size = 24199 } +wheels = [ + { url = "https://files.pythonhosted.org/packages/62/8b/5ba542fa83c90e09eac972fc9baca7a88e7e7ca4b221a89251954019308b/zipp-3.20.2-py3-none-any.whl", hash = "sha256:a817ac80d6cf4b23bf7f2828b7cabf326f15a001bea8b1f9b49631780ba28350", size = 9200 }, +] From 86eb9b8662b16006ad43f04b350a9d11efe864a4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alexis=20M=C3=A9taireau?= Date: Fri, 20 Dec 2024 01:34:47 +0100 Subject: [PATCH 25/46] build: remove support for python 3.7 --- .github/workflows/ci.yml | 7 ++----- docs/installation.md | 2 +- pyproject.toml | 2 +- 3 files changed, 4 insertions(+), 7 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 8679fbb8..90b9d920 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -47,7 +47,7 @@ jobs: strategy: fail-fast: false matrix: - python-version: [3.7, 3.8, 3.9, "3.10", "3.11", "3.12"] + python-version: [3.8, 3.9, "3.10", "3.11", "3.12"] dependencies: [normal] database: [sqlite] # Test other databases with only a few versions of Python @@ -66,9 +66,6 @@ jobs: dependencies: normal database: mariadb # Try a few variants with the minimal versions supported - - python-version: 3.7 - dependencies: minimal - database: sqlite - python-version: 3.9 dependencies: minimal database: sqlite @@ -102,7 +99,7 @@ jobs: run: sed -i -e '/requires-python/!s/>=/==/g; /requires-python/!s/~=.*==\(.*\)/==\1/g; /requires-python/!s/~=/==/g;' pyproject.toml if: matrix.dependencies == 'minimal' - name: Run tests - run: make test + run: uv run --extra dev --extra database pytest . env: # Setup the DATABASE_URI depending on the matrix we are using. TESTING_SQLALCHEMY_DATABASE_URI: ${{ diff --git a/docs/installation.md b/docs/installation.md index beeecfab..33bcbd04 100644 --- a/docs/installation.md +++ b/docs/installation.md @@ -93,7 +93,7 @@ Some Paas (Platform-as-a-Service), provide a documentation or even a quick insta «Ihatemoney» depends on: -- **Python**: any version from 3.7 to 3.12 will work. +- **Python**: any version from 3.8 to 3.12 will work. - **A database backend**: choose among SQLite, PostgreSQL, MariaDB (>= 10.3.2). - **Virtual environment** (recommended): [python3-venv]{.title-ref} diff --git a/pyproject.toml b/pyproject.toml index 89e72d3d..cab8544c 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -5,7 +5,7 @@ build-backend = "hatchling.build" [project] name = "ihatemoney" version = "6.2.0.dev0" -requires-python = ">=3.7" +requires-python = ">=3.8" description = "A simple shared budget manager web application." readme = "README.md" license = {file = "LICENSE"} From e568bb05cc01ac15dca9cbb9ad9e621aaf16082d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alexis=20M=C3=A9taireau?= Date: Fri, 20 Dec 2024 01:50:44 +0100 Subject: [PATCH 26/46] tests: remove libfake time from the tests libfaketime and python-libfaketime seem to cause our CI to fail when used in conjunction with `uv`. This changes the way the tests are done so they don't require libfaketime anymore. --- ihatemoney/tests/budget_test.py | 399 ++++++++++++++------------------ pyproject.toml | 2 - uv.lock | 144 ++++-------- 3 files changed, 228 insertions(+), 317 deletions(-) diff --git a/ihatemoney/tests/budget_test.py b/ihatemoney/tests/budget_test.py index 6e0c62d5..64a07533 100644 --- a/ihatemoney/tests/budget_test.py +++ b/ihatemoney/tests/budget_test.py @@ -1,10 +1,9 @@ from collections import defaultdict -import datetime +from datetime import datetime, timedelta, date import re from urllib.parse import unquote, urlparse, urlunparse from flask import session, url_for -from libfaketime import fake_time import pytest from werkzeug.security import check_password_hash @@ -1144,7 +1143,7 @@ class TestBudget(IhatemoneyTestCase): assert re.search(re.compile(regex2, re.DOTALL), response.data.decode("utf-8")) # Check monthly expenses again: it should have a single month and the correct amount - august = datetime.date(year=2011, month=8, day=1) + august = date(year=2011, month=8, day=1) assert project.active_months_range() == [august] assert dict(project.monthly_stats[2011]) == {8: 40.0} @@ -1161,11 +1160,11 @@ class TestBudget(IhatemoneyTestCase): }, ) months = [ - datetime.date(year=2011, month=12, day=1), - datetime.date(year=2011, month=11, day=1), - datetime.date(year=2011, month=10, day=1), - datetime.date(year=2011, month=9, day=1), - datetime.date(year=2011, month=8, day=1), + date(year=2011, month=12, day=1), + date(year=2011, month=11, day=1), + date(year=2011, month=10, day=1), + date(year=2011, month=9, day=1), + date(year=2011, month=8, day=1), ] amounts_2011 = { 12: 30.0, @@ -1218,7 +1217,7 @@ class TestBudget(IhatemoneyTestCase): "amount": "20", }, ) - months.append(datetime.date(year=2011, month=7, day=1)) + months.append(date(year=2011, month=7, day=1)) amounts_2011[7] = 20.0 assert project.active_months_range() == months assert dict(project.monthly_stats[2011]) == amounts_2011 @@ -1235,7 +1234,7 @@ class TestBudget(IhatemoneyTestCase): "amount": "30", }, ) - months.insert(0, datetime.date(year=2012, month=1, day=1)) + months.insert(0, date(year=2012, month=1, day=1)) amounts_2012 = {1: 30.0} assert project.active_months_range() == months assert dict(project.monthly_stats[2011]) == amounts_2011 @@ -1868,59 +1867,56 @@ class TestBudget(IhatemoneyTestCase): """ Tests that the RSS feed output content is expected. """ - with fake_time("2023-07-25 12:00:00"): - self.post_project("raclette", default_currency="EUR") - self.client.post("/raclette/members/add", data={"name": "george"}) - self.client.post("/raclette/members/add", data={"name": "peter"}) - self.client.post("/raclette/members/add", data={"name": "steven"}) + self.post_project("raclette", default_currency="EUR") + self.client.post("/raclette/members/add", data={"name": "george"}) + self.client.post("/raclette/members/add", data={"name": "peter"}) + self.client.post("/raclette/members/add", data={"name": "steven"}) - self.client.post( - "/raclette/add", - data={ - "date": "2016-12-31", - "what": "fromage à raclette", - "payer": 1, - "payed_for": [1, 2, 3], - "amount": "12", - "original_currency": "EUR", - "bill_type": "Expense", - }, - ) - self.client.post( - "/raclette/add", - data={ - "date": "2016-12-30", - "what": "charcuterie", - "payer": 2, - "payed_for": [1, 2], - "amount": "15", - "original_currency": "EUR", - "bill_type": "Expense", - }, - ) - self.client.post( - "/raclette/add", - data={ - "date": "2016-12-29", - "what": "vin blanc", - "payer": 2, - "payed_for": [1, 2], - "amount": "10", - "original_currency": "EUR", - "bill_type": "Expense", - }, - ) + self.client.post( + "/raclette/add", + data={ + "date": "2016-12-31", + "what": "fromage à raclette", + "payer": 1, + "payed_for": [1, 2, 3], + "amount": "12", + "original_currency": "EUR", + "bill_type": "Expense", + }, + ) + self.client.post( + "/raclette/add", + data={ + "date": "2016-12-30", + "what": "charcuterie", + "payer": 2, + "payed_for": [1, 2], + "amount": "15", + "original_currency": "EUR", + "bill_type": "Expense", + }, + ) + self.client.post( + "/raclette/add", + data={ + "date": "2016-12-29", + "what": "vin blanc", + "payer": 2, + "payed_for": [1, 2], + "amount": "10", + "original_currency": "EUR", + "bill_type": "Expense", + }, + ) project = self.get_project("raclette") token = project.generate_token("feed") resp = self.client.get(f"/raclette/feed/{token}.xml") - expected_rss_content = f""" - - + content = resp.data.decode() + + assert ( + f""" I Hate Money — raclette Latest bills from raclette @@ -1930,190 +1926,151 @@ class TestBudget(IhatemoneyTestCase): 1 george December 31, 2016 - george, peter, steven : €4.00 - Tue, 25 Jul 2023 00:00:00 +0000 - - - charcuterie - €15.00 - 2 - peter - December 30, 2016 - george, peter : €7.50 - Tue, 25 Jul 2023 00:00:00 +0000 - - - vin blanc - €10.00 - 3 - peter - December 29, 2016 - george, peter : €5.00 - Tue, 25 Jul 2023 00:00:00 +0000 - - -""" # noqa: E221, E222, E231, E501 - assert resp.data.decode() == expected_rss_content + """ + in content + ) + + assert """charcuterie - €15.00""" in content + assert """vin blanc - €10.00""" in content def test_rss_feed_history_disabled(self): """ Tests that RSS feeds is correctly rendered even if the project history is disabled. """ - with fake_time("2023-07-25 12:00:00"): - self.post_project("raclette", default_currency="EUR", project_history=False) - self.client.post("/raclette/members/add", data={"name": "george"}) - self.client.post("/raclette/members/add", data={"name": "peter"}) - self.client.post("/raclette/members/add", data={"name": "steven"}) + self.post_project("raclette", default_currency="EUR", project_history=False) + self.client.post("/raclette/members/add", data={"name": "george"}) + self.client.post("/raclette/members/add", data={"name": "peter"}) + self.client.post("/raclette/members/add", data={"name": "steven"}) - self.client.post( - "/raclette/add", - data={ - "date": "2016-12-31", - "what": "fromage à raclette", - "payer": 1, - "payed_for": [1, 2, 3], - "amount": "12", - "original_currency": "EUR", - "bill_type": "Expense", - }, - ) - self.client.post( - "/raclette/add", - data={ - "date": "2016-12-30", - "what": "charcuterie", - "payer": 2, - "payed_for": [1, 2], - "amount": "15", - "original_currency": "EUR", - "bill_type": "Expense", - }, - ) - self.client.post( - "/raclette/add", - data={ - "date": "2016-12-29", - "what": "vin blanc", - "payer": 2, - "payed_for": [1, 2], - "amount": "10", - "original_currency": "EUR", - "bill_type": "Expense", - }, - ) + self.client.post( + "/raclette/add", + data={ + "date": "2016-12-31", + "what": "fromage à raclette", + "payer": 1, + "payed_for": [1, 2, 3], + "amount": "12", + "original_currency": "EUR", + "bill_type": "Expense", + }, + ) + self.client.post( + "/raclette/add", + data={ + "date": "2016-12-30", + "what": "charcuterie", + "payer": 2, + "payed_for": [1, 2], + "amount": "15", + "original_currency": "EUR", + "bill_type": "Expense", + }, + ) + self.client.post( + "/raclette/add", + data={ + "date": "2016-12-29", + "what": "vin blanc", + "payer": 2, + "payed_for": [1, 2], + "amount": "10", + "original_currency": "EUR", + "bill_type": "Expense", + }, + ) project = self.get_project("raclette") token = project.generate_token("feed") resp = self.client.get(f"/raclette/feed/{token}.xml") - expected_rss_content = f""" - - - I Hate Money — raclette - Latest bills from raclette - - http://localhost/raclette/ - - fromage à raclette - €12.00 - 1 - george - December 31, 2016 - george, peter, steven : €4.00 - Tue, 25 Jul 2023 00:00:00 +0000 - - - charcuterie - €15.00 - 2 - peter - December 30, 2016 - george, peter : €7.50 - Tue, 25 Jul 2023 00:00:00 +0000 - - - vin blanc - €10.00 - 3 - peter - December 29, 2016 - george, peter : €5.00 - Tue, 25 Jul 2023 00:00:00 +0000 - - -""" # noqa: E221, E222, E231, E501 - assert resp.data.decode() == expected_rss_content + content = resp.data.decode() + assert """charcuterie - €15.00""" in content + assert """vin blanc - €10.00""" in content def test_rss_if_modified_since_header(self): # Project creation - with fake_time("2023-07-26 13:00:00"): - self.post_project("raclette") - self.client.post("/raclette/members/add", data={"name": "george"}) - project = self.get_project("raclette") - token = project.generate_token("feed") + self.post_project("raclette") + self.client.post("/raclette/members/add", data={"name": "george"}) + project = self.get_project("raclette") + token = project.generate_token("feed") - resp = self.client.get(f"/raclette/feed/{token}.xml") - assert resp.status_code == 200 - assert resp.headers.get("Last-Modified") == "Wed, 26 Jul 2023 13:00:00 UTC" + resp = self.client.get(f"/raclette/feed/{token}.xml") + assert resp.status_code == 200 + assert "Last-Modified" in resp.headers.keys() + last_modified = resp.headers.get("Last-Modified") + + # Get a date 1 hour before the last modified date + before = datetime.strptime( + last_modified, "%a, %d %b %Y %H:%M:%S %Z" + ) - timedelta(hours=1) + before_str = before.strftime("%a, %d %b %Y %H:%M:%S %Z") resp = self.client.get( f"/raclette/feed/{token}.xml", - headers={"If-Modified-Since": "Tue, 26 Jul 2023 12:00:00 UTC"}, + headers={"If-Modified-Since": before_str}, ) assert resp.status_code == 200 + after = datetime.strptime( + last_modified, "%a, %d %b %Y %H:%M:%S %Z" + ) + timedelta(hours=1) + after_str = after.strftime("%a, %d %b %Y %H:%M:%S %Z") + resp = self.client.get( f"/raclette/feed/{token}.xml", - headers={"If-Modified-Since": "Tue, 26 Jul 2023 14:00:00 UTC"}, + headers={"If-Modified-Since": after_str}, ) assert resp.status_code == 304 # Add bill - with fake_time("2023-07-27 13:00:00"): - self.login("raclette") - resp = self.client.post( - "/raclette/add", - data={ - "date": "2016-12-31", - "what": "fromage à raclette", - "payer": 1, - "payed_for": [1], - "amount": "12", - "original_currency": "XXX", - "bill_type": "Expense", - }, - follow_redirects=True, - ) - assert resp.status_code == 200 - assert "The bill has been added" in resp.data.decode() + self.login("raclette") + resp = self.client.post( + "/raclette/add", + data={ + "date": "2016-12-31", + "what": "fromage à raclette", + "payer": 1, + "payed_for": [1], + "amount": "12", + "original_currency": "XXX", + "bill_type": "Expense", + }, + follow_redirects=True, + ) + assert resp.status_code == 200 + assert "The bill has been added" in resp.data.decode() resp = self.client.get( f"/raclette/feed/{token}.xml", - headers={"If-Modified-Since": "Tue, 27 Jul 2023 12:00:00 UTC"}, + headers={"If-Modified-Since": before_str}, ) - assert resp.headers.get("Last-Modified") == "Thu, 27 Jul 2023 13:00:00 UTC" assert resp.status_code == 200 resp = self.client.get( f"/raclette/feed/{token}.xml", - headers={"If-Modified-Since": "Tue, 27 Jul 2023 14:00:00 UTC"}, + headers={"If-Modified-Since": after_str}, ) assert resp.status_code == 304 def test_rss_etag_headers(self): # Project creation - with fake_time("2023-07-26 13:00:00"): - self.post_project("raclette") - self.client.post("/raclette/members/add", data={"name": "george"}) - project = self.get_project("raclette") - token = project.generate_token("feed") + self.post_project("raclette") + self.client.post("/raclette/members/add", data={"name": "george"}) + project = self.get_project("raclette") + token = project.generate_token("feed") - resp = self.client.get(f"/raclette/feed/{token}.xml") - assert resp.headers.get("ETag") == build_etag( - project.id, "2023-07-26T13:00:00" - ) - assert resp.status_code == 200 + resp = self.client.get(f"/raclette/feed/{token}.xml") + etag = resp.headers.get("ETag") + assert resp.status_code == 200 resp = self.client.get( f"/raclette/feed/{token}.xml", headers={ - "If-None-Match": build_etag(project.id, "2023-07-26T12:00:00"), + "If-None-Match": etag, }, ) - assert resp.status_code == 200 + assert resp.status_code == 304 resp = self.client.get( f"/raclette/feed/{token}.xml", @@ -2121,40 +2078,38 @@ class TestBudget(IhatemoneyTestCase): "If-None-Match": build_etag(project.id, "2023-07-26T13:00:00"), }, ) - assert resp.status_code == 304 - - # Add bill - with fake_time("2023-07-27 13:00:00"): - self.login("raclette") - resp = self.client.post( - "/raclette/add", - data={ - "date": "2016-12-31", - "what": "fromage à raclette", - "payer": 1, - "payed_for": [1], - "amount": "12", - "bill_type": "Expense", - "original_currency": "XXX", - }, - follow_redirects=True, - ) - assert resp.status_code == 200 - assert "The bill has been added" in resp.data.decode() - - resp = self.client.get( - f"/raclette/feed/{token}.xml", - headers={ - "If-None-Match": build_etag(project.id, "2023-07-27T12:00:00"), - }, - ) - assert resp.headers.get("ETag") == build_etag(project.id, "2023-07-27T13:00:00") assert resp.status_code == 200 + # Add bill + self.login("raclette") + resp = self.client.post( + "/raclette/add", + data={ + "date": "2016-12-31", + "what": "fromage à raclette", + "payer": 1, + "payed_for": [1], + "amount": "12", + "bill_type": "Expense", + "original_currency": "XXX", + }, + follow_redirects=True, + ) + assert resp.status_code == 200 + assert "The bill has been added" in resp.data.decode() + etag = resp.headers.get("ETag") + + resp = self.client.get( + f"/raclette/feed/{token}.xml", + headers={"If-None-Match": etag}, + ) + assert resp.status_code == 200 + new_etag = resp.headers.get("ETag") + resp = self.client.get( f"/raclette/feed/{token}.xml", headers={ - "If-None-Match": build_etag(project.id, "2023-07-27T13:00:00"), + "If-None-Match": new_etag, }, ) assert resp.status_code == 304 diff --git a/pyproject.toml b/pyproject.toml index cab8544c..b3009ac2 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -42,7 +42,6 @@ dependencies = [ "Flask-WTF>=0.14.3,<2", "itsdangerous>=2,<3", "Jinja2>=3,<4", - "pytest-libfaketime[dev]>=0.1.3", "python-dateutil", "qrcode>=7.1,<8", "requests>=2.25,<3", @@ -65,7 +64,6 @@ dev = [ "pytest>=6.2.5", "pytest-flask>=1.2.0", "zest.releaser>=6.20.1", - "libfaketime>=2.1.0", ] doc = [ "Sphinx>=7.0.1,<8", diff --git a/uv.lock b/uv.lock index 7da6f203..b2123436 100644 --- a/uv.lock +++ b/uv.lock @@ -693,7 +693,6 @@ dependencies = [ { name = "flask-wtf" }, { name = "itsdangerous" }, { name = "jinja2" }, - { name = "pytest-libfaketime" }, { name = "python-dateutil" }, { name = "qrcode" }, { name = "requests" }, @@ -711,7 +710,6 @@ database = [ dev = [ { name = "flake8" }, { name = "isort" }, - { name = "libfaketime" }, { name = "pytest" }, { name = "pytest-flask" }, { name = "ruff" }, @@ -745,13 +743,11 @@ requires-dist = [ { name = "isort", marker = "extra == 'dev'", specifier = "==5.11.5" }, { name = "itsdangerous", specifier = ">=2,<3" }, { name = "jinja2", specifier = ">=3,<4" }, - { name = "libfaketime", marker = "extra == 'dev'", specifier = ">=2.1.0" }, { name = "myst-parser", marker = "extra == 'doc'", specifier = ">=2,<3" }, - { name = "psycopg2-binary", marker = "extra == 'database'", specifier = ">=2.9.2,<3" }, + { name = "psycopg2-binary", marker = "extra == 'database'", specifier = ">=2.9.2,<2.9.9" }, { name = "pymysql", marker = "extra == 'database'", specifier = ">=0.9,<1.1" }, { name = "pytest", marker = "extra == 'dev'", specifier = ">=6.2.5" }, { name = "pytest-flask", marker = "extra == 'dev'", specifier = ">=1.2.0" }, - { name = "pytest-libfaketime", extras = ["dev"], specifier = ">=0.1.3" }, { name = "python-dateutil" }, { name = "qrcode", specifier = ">=7.1,<8" }, { name = "requests", specifier = ">=2.25,<3" }, @@ -901,19 +897,6 @@ wheels = [ { url = "https://files.pythonhosted.org/packages/83/25/e6d59e5f0a0508d0dca8bb98c7f7fd3772fc943ac3f53d5ab18a218d32c0/keyring-25.4.1-py3-none-any.whl", hash = "sha256:5426f817cf7f6f007ba5ec722b1bcad95a75b27d780343772ad76b17cb47b0bf", size = 38946 }, ] -[[package]] -name = "libfaketime" -version = "2.1.0" -source = { registry = "https://pypi.org/simple" } -dependencies = [ - { name = "python-dateutil" }, - { name = "pytz" }, -] -sdist = { url = "https://files.pythonhosted.org/packages/c9/ec/a02a79d0254957f340a11c350de2a8ae43cfe2ececc11fc7a951f6f9d263/libfaketime-2.1.0.tar.gz", hash = "sha256:5fecd1770565154f892235a39dfc2388b092864ecca24d05456e4f5a947127a3", size = 75103 } -wheels = [ - { url = "https://files.pythonhosted.org/packages/03/12/c28cdc2834bbd71e9300f97093766dfcd4b8f3c7b7059c1e8543c6f3b14c/libfaketime-2.1.0-py3-none-any.whl", hash = "sha256:df72634f79900e71160f4e3ba4cf8f1d7ba6167e7c9a4f28d67c08e0a4f03ba2", size = 92845 }, -] - [[package]] name = "limits" version = "3.13.0" @@ -1128,70 +1111,58 @@ wheels = [ [[package]] name = "psycopg2-binary" -version = "2.9.9" +version = "2.9.8" source = { registry = "https://pypi.org/simple" } -sdist = { url = "https://files.pythonhosted.org/packages/fc/07/e720e53bfab016ebcc34241695ccc06a9e3d91ba19b40ca81317afbdc440/psycopg2-binary-2.9.9.tar.gz", hash = "sha256:7f01846810177d829c7692f1f5ada8096762d9172af1b1a28d4ab5b77c923c1c", size = 384973 } +sdist = { url = "https://files.pythonhosted.org/packages/9d/3d/5ddb908d2e5fdeb8678470d3f654e987356c9f981867313489b063fbe814/psycopg2-binary-2.9.8.tar.gz", hash = "sha256:80451e6b6b7c486828d5c7ed50769532bbb04ec3a411f1e833539d5c10eb691c", size = 383854 } wheels = [ - { url = "https://files.pythonhosted.org/packages/0a/7c/6aaf8c3cb05d86d2c3f407b95bac0c71a43f2718e38c1091972aacb5e1b2/psycopg2_binary-2.9.9-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:c2470da5418b76232f02a2fcd2229537bb2d5a7096674ce61859c3229f2eb202", size = 2822503 }, - { url = "https://files.pythonhosted.org/packages/72/3d/acab427845198794aafd963dd073ee35810e2c52606e8a28c12db39821fb/psycopg2_binary-2.9.9-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:c6af2a6d4b7ee9615cbb162b0738f6e1fd1f5c3eda7e5da17861eacf4c717ea7", size = 2552645 }, - { url = "https://files.pythonhosted.org/packages/ed/be/6c787962d706e55a528ef1693dd7251de657ae60e4d9d767ed61e8e2975c/psycopg2_binary-2.9.9-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:75723c3c0fbbf34350b46a3199eb50638ab22a0228f93fb472ef4d9becc2382b", size = 2850980 }, - { url = "https://files.pythonhosted.org/packages/83/50/a054076c6358753661cd1da59f4dabc03e83d51690371f3fd1edb9e2cf72/psycopg2_binary-2.9.9-cp310-cp310-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:83791a65b51ad6ee6cf0845634859d69a038ea9b03d7b26e703f94c7e93dbcf9", size = 3080543 }, - { url = "https://files.pythonhosted.org/packages/9c/02/826dc5cdfc9515423ec912ba00cc2e4eb09f69e0339b177c9c742f2a09a2/psycopg2_binary-2.9.9-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:0ef4854e82c09e84cc63084a9e4ccd6d9b154f1dbdd283efb92ecd0b5e2b8c84", size = 3264316 }, - { url = "https://files.pythonhosted.org/packages/bc/0d/486e3fa27f39a00168abfcf14a3d8444f437f4b755cc34316da1124f293d/psycopg2_binary-2.9.9-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ed1184ab8f113e8d660ce49a56390ca181f2981066acc27cf637d5c1e10ce46e", size = 3019508 }, - { url = "https://files.pythonhosted.org/packages/41/af/bce37630c525d2b9cf93f930110fc98616d6aca308d59b833b83b3a38176/psycopg2_binary-2.9.9-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:d2997c458c690ec2bc6b0b7ecbafd02b029b7b4283078d3b32a852a7ce3ddd98", size = 2355821 }, - { url = "https://files.pythonhosted.org/packages/3b/76/e46dae1b2273814ef80231f86d59cadf94ec36fd757045ed713c5b75cde7/psycopg2_binary-2.9.9-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:b58b4710c7f4161b5e9dcbe73bb7c62d65670a87df7bcce9e1faaad43e715245", size = 2534855 }, - { url = "https://files.pythonhosted.org/packages/0e/6d/e97245eabff29d7c2de5fc1fc17cf7ef427beee93d20a5ae114c6e6718bd/psycopg2_binary-2.9.9-cp310-cp310-musllinux_1_1_ppc64le.whl", hash = "sha256:0c009475ee389757e6e34611d75f6e4f05f0cf5ebb76c6037508318e1a1e0d7e", size = 2486614 }, - { url = "https://files.pythonhosted.org/packages/70/a7/2cd2c9d5e23b556c11e3b7da41895808d9b056f8f34f50de4375a35b4951/psycopg2_binary-2.9.9-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:8dbf6d1bc73f1d04ec1734bae3b4fb0ee3cb2a493d35ede9badbeb901fb40f6f", size = 2454928 }, - { url = "https://files.pythonhosted.org/packages/63/41/815d19767e2adb1a585213b801c954f46102f305c352c4a4f96287342d44/psycopg2_binary-2.9.9-cp310-cp310-win32.whl", hash = "sha256:3f78fd71c4f43a13d342be74ebbc0666fe1f555b8837eb113cb7416856c79682", size = 1025249 }, - { url = "https://files.pythonhosted.org/packages/5e/4c/9233e0e206634a5387f3ab40f334a5325fb8bef2ca4e12ee7dbdeaf96afc/psycopg2_binary-2.9.9-cp310-cp310-win_amd64.whl", hash = "sha256:876801744b0dee379e4e3c38b76fc89f88834bb15bf92ee07d94acd06ec890a0", size = 1163645 }, - { url = "https://files.pythonhosted.org/packages/a5/ac/702d300f3df169b9d0cbef0340d9f34a78bc18dc2dbafbcb39ff0f165cf8/psycopg2_binary-2.9.9-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:ee825e70b1a209475622f7f7b776785bd68f34af6e7a46e2e42f27b659b5bc26", size = 2822581 }, - { url = "https://files.pythonhosted.org/packages/7a/1f/a6cf0cdf944253f7c45d90fbc876cc8bed5cc9942349306245715c0d88d6/psycopg2_binary-2.9.9-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:1ea665f8ce695bcc37a90ee52de7a7980be5161375d42a0b6c6abedbf0d81f0f", size = 2552633 }, - { url = "https://files.pythonhosted.org/packages/81/0b/3adf561107c865928455891156d1dde5325253f7f4316fe56cd2c3f73570/psycopg2_binary-2.9.9-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:143072318f793f53819048fdfe30c321890af0c3ec7cb1dfc9cc87aa88241de2", size = 2851075 }, - { url = "https://files.pythonhosted.org/packages/f7/98/c2fedcbf0a9607519a010dcf88571138b2251062dbde3610cdba5ba1eee1/psycopg2_binary-2.9.9-cp311-cp311-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:c332c8d69fb64979ebf76613c66b985414927a40f8defa16cf1bc028b7b0a7b0", size = 3080509 }, - { url = "https://files.pythonhosted.org/packages/c2/05/81e8bc7fca95574c9323e487d9ce1b58a4cfcc17f89b8fe843af46361211/psycopg2_binary-2.9.9-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:f7fc5a5acafb7d6ccca13bfa8c90f8c51f13d8fb87d95656d3950f0158d3ce53", size = 3264303 }, - { url = "https://files.pythonhosted.org/packages/ce/85/62825cabc6aad53104b7b6d12eb2ad74737d268630032d07b74d4444cb72/psycopg2_binary-2.9.9-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:977646e05232579d2e7b9c59e21dbe5261f403a88417f6a6512e70d3f8a046be", size = 3019515 }, - { url = "https://files.pythonhosted.org/packages/e9/b0/9ca2b8e01a0912c9a14234fd5df7a241a1e44778c5797bf4b8eaa8dc3d3a/psycopg2_binary-2.9.9-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:b6356793b84728d9d50ead16ab43c187673831e9d4019013f1402c41b1db9b27", size = 2355892 }, - { url = "https://files.pythonhosted.org/packages/73/17/ba28bb0022db5e2015a82d2df1c4b0d419c37fa07a588b3aff3adc4939f6/psycopg2_binary-2.9.9-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:bc7bb56d04601d443f24094e9e31ae6deec9ccb23581f75343feebaf30423359", size = 2534903 }, - { url = "https://files.pythonhosted.org/packages/3b/92/b463556409cdc12791cd8b1dae0072bf8efe817ef68b7ea3d9cf7d0e5656/psycopg2_binary-2.9.9-cp311-cp311-musllinux_1_1_ppc64le.whl", hash = "sha256:77853062a2c45be16fd6b8d6de2a99278ee1d985a7bd8b103e97e41c034006d2", size = 2486597 }, - { url = "https://files.pythonhosted.org/packages/92/57/96576e07132d7f7a1ac1df939575e6fdd8951aea337ee152b586bb51a971/psycopg2_binary-2.9.9-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:78151aa3ec21dccd5cdef6c74c3e73386dcdfaf19bced944169697d7ac7482fc", size = 2454908 }, - { url = "https://files.pythonhosted.org/packages/7c/ae/cedd56e1f4a2b0e37213283caf3733a875c4c76f3372241e19c0d2a87355/psycopg2_binary-2.9.9-cp311-cp311-win32.whl", hash = "sha256:dc4926288b2a3e9fd7b50dc6a1909a13bbdadfc67d93f3374d984e56f885579d", size = 1024240 }, - { url = "https://files.pythonhosted.org/packages/25/1f/7ae31759142999a8d06b3e250c1346c4abcdcada8fa884376775dc1de686/psycopg2_binary-2.9.9-cp311-cp311-win_amd64.whl", hash = "sha256:b76bedd166805480ab069612119ea636f5ab8f8771e640ae103e05a4aae3e417", size = 1163655 }, - { url = "https://files.pythonhosted.org/packages/a7/d0/5f2db14e7b53552276ab613399a83f83f85b173a862d3f20580bc7231139/psycopg2_binary-2.9.9-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:8532fd6e6e2dc57bcb3bc90b079c60de896d2128c5d9d6f24a63875a95a088cf", size = 2823784 }, - { url = "https://files.pythonhosted.org/packages/18/ca/da384fd47233e300e3e485c90e7aab5d7def896d1281239f75901faf87d4/psycopg2_binary-2.9.9-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:b0605eaed3eb239e87df0d5e3c6489daae3f7388d455d0c0b4df899519c6a38d", size = 2553308 }, - { url = "https://files.pythonhosted.org/packages/50/66/fa53d2d3d92f6e1ef469d92afc6a4fe3f6e8a9a04b687aa28fb1f1d954ee/psycopg2_binary-2.9.9-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8f8544b092a29a6ddd72f3556a9fcf249ec412e10ad28be6a0c0d948924f2212", size = 2851283 }, - { url = "https://files.pythonhosted.org/packages/04/37/2429360ac5547378202db14eec0dde76edbe1f6627df5a43c7e164922859/psycopg2_binary-2.9.9-cp312-cp312-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:2d423c8d8a3c82d08fe8af900ad5b613ce3632a1249fd6a223941d0735fce493", size = 3081839 }, - { url = "https://files.pythonhosted.org/packages/62/2a/c0530b59d7e0d09824bc2102ecdcec0456b8ca4d47c0caa82e86fce3ed4c/psycopg2_binary-2.9.9-cp312-cp312-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:2e5afae772c00980525f6d6ecf7cbca55676296b580c0e6abb407f15f3706996", size = 3264488 }, - { url = "https://files.pythonhosted.org/packages/19/57/9f172b900795ea37246c78b5f52e00f4779984370855b3e161600156906d/psycopg2_binary-2.9.9-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6e6f98446430fdf41bd36d4faa6cb409f5140c1c2cf58ce0bbdaf16af7d3f119", size = 3020700 }, - { url = "https://files.pythonhosted.org/packages/94/68/1176fc14ea76861b7b8360be5176e87fb20d5091b137c76570eb4e237324/psycopg2_binary-2.9.9-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:c77e3d1862452565875eb31bdb45ac62502feabbd53429fdc39a1cc341d681ba", size = 2355968 }, - { url = "https://files.pythonhosted.org/packages/70/bb/aec2646a705a09079d008ce88073401cd61fc9b04f92af3eb282caa3a2ec/psycopg2_binary-2.9.9-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:cb16c65dcb648d0a43a2521f2f0a2300f40639f6f8c1ecbc662141e4e3e1ee07", size = 2536101 }, - { url = "https://files.pythonhosted.org/packages/14/33/12818c157e333cb9d9e6753d1b2463b6f60dbc1fade115f8e4dc5c52cac4/psycopg2_binary-2.9.9-cp312-cp312-musllinux_1_1_ppc64le.whl", hash = "sha256:911dda9c487075abd54e644ccdf5e5c16773470a6a5d3826fda76699410066fb", size = 2487064 }, - { url = "https://files.pythonhosted.org/packages/56/a2/7851c68fe8768f3c9c246198b6356ee3e4a8a7f6820cc798443faada3400/psycopg2_binary-2.9.9-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:57fede879f08d23c85140a360c6a77709113efd1c993923c59fde17aa27599fe", size = 2456257 }, - { url = "https://files.pythonhosted.org/packages/6f/ee/3ba07c6dc7c3294e717e94720da1597aedc82a10b1b180203ce183d4631a/psycopg2_binary-2.9.9-cp312-cp312-win32.whl", hash = "sha256:64cf30263844fa208851ebb13b0732ce674d8ec6a0c86a4e160495d299ba3c93", size = 1024709 }, - { url = "https://files.pythonhosted.org/packages/7b/08/9c66c269b0d417a0af9fb969535f0371b8c538633535a7a6a5ca3f9231e2/psycopg2_binary-2.9.9-cp312-cp312-win_amd64.whl", hash = "sha256:81ff62668af011f9a48787564ab7eded4e9fb17a4a6a74af5ffa6a457400d2ab", size = 1163864 }, - { url = "https://files.pythonhosted.org/packages/94/62/6f8d281e279a71f20d1670f4de97d116b1d90948eb16c3c41ac305f94a30/psycopg2_binary-2.9.9-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:60989127da422b74a04345096c10d416c2b41bd7bf2a380eb541059e4e999980", size = 2822517 }, - { url = "https://files.pythonhosted.org/packages/88/d8/3bbedf39ab90d64d7a6f04e3f3744c74f46f55bd305cc2db3aa12e9c5667/psycopg2_binary-2.9.9-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:246b123cc54bb5361588acc54218c8c9fb73068bf227a4a531d8ed56fa3ca7d6", size = 2552729 }, - { url = "https://files.pythonhosted.org/packages/24/1b/99b948254604838de668d81cc39a294a987721120c67963e00d47a290f7f/psycopg2_binary-2.9.9-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:34eccd14566f8fe14b2b95bb13b11572f7c7d5c36da61caf414d23b91fcc5d94", size = 2850949 }, - { url = "https://files.pythonhosted.org/packages/5f/e9/115e4f4f86d4aa5c300fdc90ac3d3e74401b4060d782281fe5b47d6c832d/psycopg2_binary-2.9.9-cp38-cp38-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:18d0ef97766055fec15b5de2c06dd8e7654705ce3e5e5eed3b6651a1d2a9a152", size = 3080624 }, - { url = "https://files.pythonhosted.org/packages/24/bf/4856c4985823ef094fc5a52eeb194f038dfbc57921f1d091853efc8e01b4/psycopg2_binary-2.9.9-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:d3f82c171b4ccd83bbaf35aa05e44e690113bd4f3b7b6cc54d2219b132f3ae55", size = 3264449 }, - { url = "https://files.pythonhosted.org/packages/19/7a/e806ed82d954b9ec29b62f12ae8929da8910cde5ab7e919ec0983e56672d/psycopg2_binary-2.9.9-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ead20f7913a9c1e894aebe47cccf9dc834e1618b7aa96155d2091a626e59c972", size = 3019558 }, - { url = "https://files.pythonhosted.org/packages/da/e0/073f50a65093a0bd087aff95754bdd61e8ef24d6ea29f47ea97575d4a784/psycopg2_binary-2.9.9-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:ca49a8119c6cbd77375ae303b0cfd8c11f011abbbd64601167ecca18a87e7cdd", size = 2355857 }, - { url = "https://files.pythonhosted.org/packages/a3/96/3153069df1378d398dcbd6968d4da89735bb63dccbb13a435bc65291c59c/psycopg2_binary-2.9.9-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:323ba25b92454adb36fa425dc5cf6f8f19f78948cbad2e7bc6cdf7b0d7982e59", size = 2534862 }, - { url = "https://files.pythonhosted.org/packages/dc/d0/512a73da2253c1904366155fd2c7ddf6d4e04a4eb434c90a18af8ce3d24b/psycopg2_binary-2.9.9-cp38-cp38-musllinux_1_1_ppc64le.whl", hash = "sha256:1236ed0952fbd919c100bc839eaa4a39ebc397ed1c08a97fc45fee2a595aa1b3", size = 2486636 }, - { url = "https://files.pythonhosted.org/packages/ba/69/e38aeaace3a87dda1c152c039c72181fdcbff0787d5d2466944b663c4a57/psycopg2_binary-2.9.9-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:729177eaf0aefca0994ce4cffe96ad3c75e377c7b6f4efa59ebf003b6d398716", size = 2454931 }, - { url = "https://files.pythonhosted.org/packages/bc/14/76879e83245d8dc72812fb71fb3e710fa7482a05c4b1788b41b22e9fffcc/psycopg2_binary-2.9.9-cp38-cp38-win32.whl", hash = "sha256:804d99b24ad523a1fe18cc707bf741670332f7c7412e9d49cb5eab67e886b9b5", size = 1007154 }, - { url = "https://files.pythonhosted.org/packages/48/10/320b014e2fda509dc16409f76815ad0229e4fcec5ed229e64f7f917cc23f/psycopg2_binary-2.9.9-cp38-cp38-win_amd64.whl", hash = "sha256:a6cdcc3ede532f4a4b96000b6362099591ab4a3e913d70bcbac2b56c872446f7", size = 1155784 }, - { url = "https://files.pythonhosted.org/packages/82/69/c25f8bd5c189cee89bc00e16b49a84f930b3b4c2cfec953a26c99076a586/psycopg2_binary-2.9.9-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:72dffbd8b4194858d0941062a9766f8297e8868e1dd07a7b36212aaa90f49472", size = 2822507 }, - { url = "https://files.pythonhosted.org/packages/3e/06/7d0085889cba209185f1a52d646c4dbdbd9075345f4ca685bacf08d30755/psycopg2_binary-2.9.9-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:30dcc86377618a4c8f3b72418df92e77be4254d8f89f14b8e8f57d6d43603c0f", size = 2552664 }, - { url = "https://files.pythonhosted.org/packages/68/a2/67732accfffdb6696dc9523f82e91823e8cb1cc311f1c4ce006d2bb85016/psycopg2_binary-2.9.9-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:31a34c508c003a4347d389a9e6fcc2307cc2150eb516462a7a17512130de109e", size = 2850943 }, - { url = "https://files.pythonhosted.org/packages/f0/85/dff2170a1e6748b7068a4523ea9fef8373572c4cd283cffb4802f871a556/psycopg2_binary-2.9.9-cp39-cp39-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:15208be1c50b99203fe88d15695f22a5bed95ab3f84354c494bcb1d08557df67", size = 3080551 }, - { url = "https://files.pythonhosted.org/packages/2e/49/9550febcc90105089bb89881b8cba73db227b9685cfddaae2479791a2379/psycopg2_binary-2.9.9-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:1873aade94b74715be2246321c8650cabf5a0d098a95bab81145ffffa4c13876", size = 3264314 }, - { url = "https://files.pythonhosted.org/packages/65/04/d0266fd446cb65384ce5442bc08449fd0b5d3419494574f020275f9e2273/psycopg2_binary-2.9.9-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3a58c98a7e9c021f357348867f537017057c2ed7f77337fd914d0bedb35dace7", size = 3019531 }, - { url = "https://files.pythonhosted.org/packages/ba/7e/c91f4c1e364444c8f59e82501f600019717f265ae4092057cece02d2d945/psycopg2_binary-2.9.9-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:4686818798f9194d03c9129a4d9a702d9e113a89cb03bffe08c6cf799e053291", size = 2355811 }, - { url = "https://files.pythonhosted.org/packages/6b/ae/05d1e52e8535ef3c73fa327e179d982b903e2c08987fa0e2167842c153a7/psycopg2_binary-2.9.9-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:ebdc36bea43063116f0486869652cb2ed7032dbc59fbcb4445c4862b5c1ecf7f", size = 2534818 }, - { url = "https://files.pythonhosted.org/packages/cb/bd/e5fb2aa9737e50c0ffb9c3851710055eafedd4c8628c6ef9863bb2e9c434/psycopg2_binary-2.9.9-cp39-cp39-musllinux_1_1_ppc64le.whl", hash = "sha256:ca08decd2697fdea0aea364b370b1249d47336aec935f87b8bbfd7da5b2ee9c1", size = 2486605 }, - { url = "https://files.pythonhosted.org/packages/c5/22/0b832bc8a83d8fed74c5a45fbacf4a6e6eb66bcb0cd3836fca9a709f25f4/psycopg2_binary-2.9.9-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:ac05fb791acf5e1a3e39402641827780fe44d27e72567a000412c648a85ba860", size = 2454908 }, - { url = "https://files.pythonhosted.org/packages/0a/b7/3046fd37fdf84c1945741d16fa7536ddcf8576bad6d77ee2891c5255dce3/psycopg2_binary-2.9.9-cp39-cp39-win32.whl", hash = "sha256:9dba73be7305b399924709b91682299794887cbbd88e38226ed9f6712eabee90", size = 1037893 }, - { url = "https://files.pythonhosted.org/packages/cb/35/009b43d67a7010b789690a46d49521fd435ce33ce722fe8d7ac7efe35c21/psycopg2_binary-2.9.9-cp39-cp39-win_amd64.whl", hash = "sha256:f7ae5d65ccfbebdfa761585228eb4d0df3a8b15cfb53bd953e713e09fbb12957", size = 1177353 }, + { url = "https://files.pythonhosted.org/packages/6f/93/7d0777dec397807327ccde617ade579dcb4ccbccd38659e2d9e93d105e1d/psycopg2_binary-2.9.8-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:e271ad6692d50d70ca75db3bd461bfc26316de78de8fe1f504ef16dcea8f2312", size = 2822503 }, + { url = "https://files.pythonhosted.org/packages/2c/e6/344851c4977eded2e7f00991c193afe21403ecfd35a7895c5789a029a66f/psycopg2_binary-2.9.8-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:3ae22a0fa5c516b84ddb189157fabfa3f12eded5d630e1ce260a18e1771f8707", size = 2540362 }, + { url = "https://files.pythonhosted.org/packages/01/51/bcafe813626422abecf27e5b9d54ef081fd4078f1d918979a013ebc22179/psycopg2_binary-2.9.8-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:9a971086db0069aef2fd22ccffb670baac427f4ee2174c4f5c7206254f1e6794", size = 2850985 }, + { url = "https://files.pythonhosted.org/packages/ab/0b/e5ac6afefd3d3172e47e2625892a8023c7aa8a3b75ea6454fcc61137acb5/psycopg2_binary-2.9.8-cp310-cp310-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:3b6928a502af71ca2ac9aad535e78c8309892ed3bfa7933182d4c760580c8af4", size = 3080553 }, + { url = "https://files.pythonhosted.org/packages/18/a3/e3b8866d5e4ff46d86750e11aef1ae5ca9c8b561c76622def1752e78682b/psycopg2_binary-2.9.8-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:5f955fe6301b84b6fd13970a05f3640fbb62ca3a0d19342356585006c830e038", size = 3264319 }, + { url = "https://files.pythonhosted.org/packages/a6/59/8145f6b7f82de632e07eec6cf83974e8d8279007ba3b414c29b5124af442/psycopg2_binary-2.9.8-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3723c3f009e2b2771f2491b330edb7091846f1aad0c08fbbd9a1383d6a0c0841", size = 3019504 }, + { url = "https://files.pythonhosted.org/packages/da/e2/b716ec54a62d7453c5c0df81e4cb61c6e8c03cbec3b824236139781ebdc3/psycopg2_binary-2.9.8-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:e3142c7e51b92855cff300580de949e36a94ab3bfa8f353b27fe26535e9b3542", size = 2355825 }, + { url = "https://files.pythonhosted.org/packages/a4/5a/ef8c7a38b7d9284be56201d1bfb8a78da1fb20b4866a5a4d5bae638aa6a0/psycopg2_binary-2.9.8-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:de85105c568dc5f0f0efe793209ba83e4675d53d00faffc7a7c7a8bea9e0e19a", size = 2534856 }, + { url = "https://files.pythonhosted.org/packages/82/6a/6e7fe0c70cfd634e8dd323c8143bd69b6187b495572c4c52d658ed8b05c6/psycopg2_binary-2.9.8-cp310-cp310-musllinux_1_1_ppc64le.whl", hash = "sha256:c7ff2b6a79a92b1b169b03bb91b41806843f0cdf6055256554495bffed1d496d", size = 2486613 }, + { url = "https://files.pythonhosted.org/packages/55/41/7e4a741ddc22c62b7b37460027527b24549a752b6286996d96c7ad7ffbdf/psycopg2_binary-2.9.8-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:59f45cca0765aabb52a5822c72d5ff2ec46a28b1c1702de90dc0d306ec5c2001", size = 2454929 }, + { url = "https://files.pythonhosted.org/packages/b6/7d/cc526b6328dbabd01ec5b105c3d765a6fa656e45f3d5ed16e05c590cfe14/psycopg2_binary-2.9.8-cp310-cp310-win32.whl", hash = "sha256:1dbad789ebd1e61201256a19dc2e90fed4706bc966ccad4f374648e5336b1ab4", size = 1025248 }, + { url = "https://files.pythonhosted.org/packages/d2/b3/d8471871d031245e514970a686eed8f44a90de348c9b7480773920b7eea1/psycopg2_binary-2.9.8-cp310-cp310-win_amd64.whl", hash = "sha256:15458c81b0d199ab55825007115f697722831656e6477a427783fe75c201c82b", size = 1163646 }, + { url = "https://files.pythonhosted.org/packages/ea/5a/b413a72046ac4bd027aa64989a6451cd881c07e1613e5dfd49a15def695c/psycopg2_binary-2.9.8-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:395c217156723fe21809dfe8f7a433c5bf8e9bce229944668e4ec709c37c5442", size = 2822582 }, + { url = "https://files.pythonhosted.org/packages/1b/ee/37ded58732145dc0ca061e9185002ea66c8f172cc20e140cc539e2546eed/psycopg2_binary-2.9.8-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:14f85ff2d5d826a7ce9e6c31e803281ed5a096789f47f52cb728c88f488de01b", size = 2540348 }, + { url = "https://files.pythonhosted.org/packages/f4/2c/1d39f0fe4f41ec635388a016918e0742c9ccbdc30860b98361298f60fdb3/psycopg2_binary-2.9.8-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e11373d8e4f1f46cf3065bf613f0df9854803dc95aa4a35354ffac19f8c52127", size = 2851084 }, + { url = "https://files.pythonhosted.org/packages/a5/20/2e15593e6037b6246536cc70f0c57f41a08f8cd914ddaadb3a4b0be5499e/psycopg2_binary-2.9.8-cp311-cp311-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:01f9731761f711e42459f87bd2ad5d744b9773b5dd05446f3b579a0f077e78e3", size = 3080501 }, + { url = "https://files.pythonhosted.org/packages/86/66/661a37f98a805fcaed666e403df28e3c140b05ee4a7ceae8c960a6ef52e8/psycopg2_binary-2.9.8-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:54bf5c27bd5867a5fa5341fad29f0d5838e2fed617ef5346884baf8b8b16dd82", size = 3264303 }, + { url = "https://files.pythonhosted.org/packages/22/52/a6113ae5fb0fb6b93894dd8487e02cdac6c85d564de7c0529e2571176193/psycopg2_binary-2.9.8-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:4bfabbd7e70785af726cc0209e8e64b926abf91741eca80678b221aad9e72135", size = 3019507 }, + { url = "https://files.pythonhosted.org/packages/41/01/cb27421053c8c1b0148842e562caba6a4d4740fb28bb67073a6160c501ba/psycopg2_binary-2.9.8-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:6369f4bd4d27944498094dccced1ae7ca43376a59dbfe4c8b6a16e9e3dc3ccce", size = 2355894 }, + { url = "https://files.pythonhosted.org/packages/93/08/2b8a819089bd8c5b0561b34c002890b20c1d80a23c6c4f8f18101f0bcf2e/psycopg2_binary-2.9.8-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:4879ee1d07a6b2c232ae6a74570f4788cd7a29b3cd38bc39bf60225b1d075c78", size = 2534903 }, + { url = "https://files.pythonhosted.org/packages/d1/e1/0d2da583bce9b5c772160994a14de1de92855938b5fba771cda9653d6ed8/psycopg2_binary-2.9.8-cp311-cp311-musllinux_1_1_ppc64le.whl", hash = "sha256:4336afc0e81726350bd5863e3c3116d8c12aa7f457d3d0b3b3dc36137fec6feb", size = 2486598 }, + { url = "https://files.pythonhosted.org/packages/4b/bb/eca133578d656111fddfd811866a54ee481959e71044155a3440845def40/psycopg2_binary-2.9.8-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:63ce1dccfd08d9c5341ac82d62aa04345bc4bf41b5e5b7b2c6c172a28e0eda27", size = 2454909 }, + { url = "https://files.pythonhosted.org/packages/c1/56/1335979539b8505edcda925eaa4a47c0981e3ddc9546b8b6984cef495ab4/psycopg2_binary-2.9.8-cp311-cp311-win32.whl", hash = "sha256:59421806c1a0803ea7de9ed061d656c041a84db0da7e73266b98db4c7ba263da", size = 1024238 }, + { url = "https://files.pythonhosted.org/packages/bb/3e/9a9d6f6171cfc47a8b4563376a7578ec12682c956985c41533f1687c61c0/psycopg2_binary-2.9.8-cp311-cp311-win_amd64.whl", hash = "sha256:ccaa2ae03990cedde1f618ff11ec89fefa84622da73091a67b44553ca8be6711", size = 1163653 }, + { url = "https://files.pythonhosted.org/packages/df/b2/28bb3bb4bf75aaaf58f607de4de6e4c8cbea76cfde72795b744cf137ea0f/psycopg2_binary-2.9.8-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:e46b0f4683539965ce849f2c13fc53e323bb08d84d4ba2e4b3d976f364c84210", size = 2822509 }, + { url = "https://files.pythonhosted.org/packages/90/91/10d636ada2073be150ae568a67ce3481b3608c16af89667e0c6f3e6b202b/psycopg2_binary-2.9.8-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:3fd44b52bc9c74c1512662e8da113a1c55127adeeacebaf460babe766517b049", size = 2540381 }, + { url = "https://files.pythonhosted.org/packages/12/a1/d8396f6d6aa1da39e0d1b98e999c8d836ffc0c269bca6e95873ca33901fa/psycopg2_binary-2.9.8-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:3b6c607ecb6a9c245ebe162d63ccd9222d38efa3c858bbe38d32810b08b8f87e", size = 2850943 }, + { url = "https://files.pythonhosted.org/packages/de/9e/5a290827e6fe864b1bbb2120b41403f6b38e2af4a20ae90ebfcd07105b93/psycopg2_binary-2.9.8-cp38-cp38-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:e6ef615d48fa60361e57f998327046bd89679c25d06eee9e78156be5a7a76e03", size = 3080618 }, + { url = "https://files.pythonhosted.org/packages/20/69/776532e8e4da491ba49177cbdb2f41317a63820211c8fc83f1c1d5333297/psycopg2_binary-2.9.8-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:65403113ac3a4813a1409fb6a1e43c658b459cc8ed8afcc5f4baf02ec8be4334", size = 3264448 }, + { url = "https://files.pythonhosted.org/packages/0f/ff/df058f6904693e2a76da8809e89f3b4ca23fac9929de7b385184f4c161ed/psycopg2_binary-2.9.8-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5debcb23a052f3fb4c165789ea513b562b2fac0f0f4f53eaf3cf4dc648907ff8", size = 3019548 }, + { url = "https://files.pythonhosted.org/packages/a6/9d/bd6c3132d7b439fb346717099566955673ace4870c2a99442d926b092825/psycopg2_binary-2.9.8-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:dc145a241e1f6381efb924bcf3e3462d6020b8a147363f9111eb0a9c89331ad7", size = 2355858 }, + { url = "https://files.pythonhosted.org/packages/44/09/a655d4f7c049ec2deece57556fcc056c3c458d988a41c6b93f2e89916907/psycopg2_binary-2.9.8-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:1d669887df169a9b0c09e0f5b46891511850a9ddfcde3593408af9d9774c5c3a", size = 2534861 }, + { url = "https://files.pythonhosted.org/packages/14/f5/fbd3120a44c7518220554019ab5b366171924ecb5246d5a6d2562494f0dc/psycopg2_binary-2.9.8-cp38-cp38-musllinux_1_1_ppc64le.whl", hash = "sha256:19d40993701e39c49b50e75cd690a6af796d7e7210941ee0fe49cf12b25840e5", size = 2486634 }, + { url = "https://files.pythonhosted.org/packages/1d/71/a90f741e980d70cfa7c3d570f75a887624e4884277c36918da6c485b1169/psycopg2_binary-2.9.8-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:4b8b2cdf3bce4dd91dc035fbff4eb812f5607dda91364dc216b0920b97b521c7", size = 2454934 }, + { url = "https://files.pythonhosted.org/packages/7a/72/6aa663d57d38823cf8931dd876f92be884879f9a6bdecf33f3e83b63d125/psycopg2_binary-2.9.8-cp38-cp38-win32.whl", hash = "sha256:4960c881471ca710b81a67ef148c33ee121c1f8e47a639cf7e06537fe9fee337", size = 1007153 }, + { url = "https://files.pythonhosted.org/packages/ca/86/b0bee62b74eb64dafcbfb12e1c4f2be12cadd11f35235548aacc1e0d9d87/psycopg2_binary-2.9.8-cp38-cp38-win_amd64.whl", hash = "sha256:aeb09db95f38e75ae04e947d283e07be34d03c4c2ace4f0b73dbb9143d506e67", size = 1155786 }, + { url = "https://files.pythonhosted.org/packages/73/3e/f6047de891b22d8ddde889ded5590a51eba5ceb602db56946255230229c3/psycopg2_binary-2.9.8-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:5aef3296d44d05805e634dbbd2972aa8eb7497926dd86047f5e39a79c3ecc086", size = 2822530 }, + { url = "https://files.pythonhosted.org/packages/7f/06/b679e3dc280cee93f2d70f15e0ec6d382d6ff9e7e58ea153dc9588d0de5c/psycopg2_binary-2.9.8-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:4d6b592ecc8667e608b9e7344259fbfb428cc053df0062ec3ac75d8270cd5a9f", size = 2540360 }, + { url = "https://files.pythonhosted.org/packages/99/e0/dc34bcce3c25ec7932a1cbfdad57014a56788ff0f6c905f71e0ac7f2df13/psycopg2_binary-2.9.8-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:693a4e7641556f0b421a7d6c6a74058aead407d860ac1cb9d0bf25be0ca73de8", size = 2850961 }, + { url = "https://files.pythonhosted.org/packages/dd/2e/af52a8526ba9ddca03b8d99653464b278a56860439e1e2359dd4e5b9e475/psycopg2_binary-2.9.8-cp39-cp39-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:cf60c599c40c266a01c458e9c71db7132b11760f98f08233f19b3e0a2153cbf1", size = 3080558 }, + { url = "https://files.pythonhosted.org/packages/27/39/ec0a7e75510de8f0a414a5303cb93a95d5eaf7a4cbf6dc03617665b86ee6/psycopg2_binary-2.9.8-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:5cbe1e19f59950afd66764e3c905ecee9f2aee9f8df2ef35af6f7948ad93f620", size = 3264313 }, + { url = "https://files.pythonhosted.org/packages/6a/cc/a9b6c7b135579f89493dbca86c8c12dece95fc4533d3180a7bc9fe87431f/psycopg2_binary-2.9.8-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:fc37de7e3a87f5966965fc874d33c9b68d638e6c3718fdf32a5083de563428b0", size = 3019528 }, + { url = "https://files.pythonhosted.org/packages/49/bc/6ccf62b42ec9e0322b0b5dbe1d10d9c84953151283a9702eae7af9a17d7a/psycopg2_binary-2.9.8-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:6e1bb4eb0d9925d65dabaaabcbb279fab444ba66d73f86d4c07dfd11f0139c06", size = 2355812 }, + { url = "https://files.pythonhosted.org/packages/a2/f5/4a4d2a5ba7e2fc71872227c8c1297ed2773d9834f3ffbba41b853638f42d/psycopg2_binary-2.9.8-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:e7bdc94217ae20ad03b375a991e107a31814053bee900ad8c967bf82ef3ff02e", size = 2534820 }, + { url = "https://files.pythonhosted.org/packages/95/27/79c00c70ff8bec8f55cc39d1d9290733582444cf73906767f7ea6d2d216a/psycopg2_binary-2.9.8-cp39-cp39-musllinux_1_1_ppc64le.whl", hash = "sha256:565edaf9f691b17a7fdbabd368b5b3e67d0fdc8f7f6b52177c1d3289f4e763fd", size = 2486605 }, + { url = "https://files.pythonhosted.org/packages/21/a0/4954e8f217ca572d6d150962893d9dc45449bbb506b010761e13489907e3/psycopg2_binary-2.9.8-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:0e3071c947bda6afc6fe2e7b64ebd64fb2cad1bc0e705a3594cb499291f2dfec", size = 2454910 }, + { url = "https://files.pythonhosted.org/packages/55/73/06f1f073e732fc54193664f04cf94addb285034a3bd352d534b8a9710e5d/psycopg2_binary-2.9.8-cp39-cp39-win32.whl", hash = "sha256:205cecdd81ff4f1ddd687ce7d06879b9b80cccc428d8d6ebf36fcba08bb6d361", size = 1037893 }, + { url = "https://files.pythonhosted.org/packages/e7/56/39189b7bf61744a627c18f3a919647f7eac78d849de1f8b2ad1a5c11f824/psycopg2_binary-2.9.8-cp39-cp39-win_amd64.whl", hash = "sha256:1f279ba74f0d6b374526e5976c626d2ac3b8333b6a7b08755c513f4d380d3add", size = 1177351 }, ] [[package]] @@ -1288,19 +1259,6 @@ wheels = [ { url = "https://files.pythonhosted.org/packages/de/03/7a917fda3d0e96b4e80ab1f83a6628ec4ee4a882523b49417d3891bacc9e/pytest_flask-1.3.0-py3-none-any.whl", hash = "sha256:c0e36e6b0fddc3b91c4362661db83fa694d1feb91fa505475be6732b5bc8c253", size = 13105 }, ] -[[package]] -name = "pytest-libfaketime" -version = "0.1.3" -source = { registry = "https://pypi.org/simple" } -dependencies = [ - { name = "libfaketime" }, - { name = "pytest" }, -] -sdist = { url = "https://files.pythonhosted.org/packages/7b/eb/3f59bef7dd2a30e4bd16361c70294da9a1b670d0d0881bde60dc6bb1ee0e/pytest_libfaketime-0.1.3.tar.gz", hash = "sha256:113fa5cc364103eb290fb0c189bc2de6f3423c888263788c64dcfd01974a01c6", size = 2318 } -wheels = [ - { url = "https://files.pythonhosted.org/packages/b5/c6/8ff351ab29bea0ee577e0d08c3ededf96b50dc2164cb71471b58764ac8e3/pytest_libfaketime-0.1.3-py3-none-any.whl", hash = "sha256:f2b79206f51ad69a7e905b154189dece6396e4a138cebc8897d96e2b999581f6", size = 2820 }, -] - [[package]] name = "python-dateutil" version = "2.9.0.post0" From a9f211d3f6cb05853333c8e150a845a8e3dbf838 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 20 Dec 2024 16:19:21 +0000 Subject: [PATCH 27/46] Update sphinx requirement from <8,>=7.0.1 to >=7.0.1,<9 Updates the requirements on [sphinx](https://github.com/sphinx-doc/sphinx) to permit the latest version. - [Release notes](https://github.com/sphinx-doc/sphinx/releases) - [Changelog](https://github.com/sphinx-doc/sphinx/blob/v8.1.3/CHANGES.rst) - [Commits](https://github.com/sphinx-doc/sphinx/compare/v7.0.1...v8.1.3) --- updated-dependencies: - dependency-name: sphinx dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- pyproject.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyproject.toml b/pyproject.toml index b3009ac2..82683189 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -66,7 +66,7 @@ dev = [ "zest.releaser>=6.20.1", ] doc = [ - "Sphinx>=7.0.1,<8", + "Sphinx>=7.0.1,<9", "docutils==0.20.1", "myst-parser>=2,<3", ] From 35ac04be208750ce92422dd8c430142a89093a01 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 20 Dec 2024 16:19:14 +0000 Subject: [PATCH 28/46] Update flask requirement from <3,>=2 to >=2,<4 Updates the requirements on [flask](https://github.com/pallets/flask) to permit the latest version. - [Release notes](https://github.com/pallets/flask/releases) - [Changelog](https://github.com/pallets/flask/blob/main/CHANGES.rst) - [Commits](https://github.com/pallets/flask/compare/2.0.0...3.1.0) --- updated-dependencies: - dependency-name: flask dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- pyproject.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyproject.toml b/pyproject.toml index 82683189..ac0fb1af 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -30,7 +30,7 @@ dependencies = [ "cachetools>=4.1,<5", "debts>=0.5,<1", "email_validator>=1.0,<3", - "Flask>=2,<3", + "Flask>=2,<4", "Flask-Babel>=1.0,<4", "Flask-Cors>=3.0.8,<4", "Flask-Limiter>=2.6,<3", From 56e2ff6900613a9cb2c653d3799aab9580ea33da Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 20 Dec 2024 16:18:36 +0000 Subject: [PATCH 29/46] Update wtforms requirement from <3.2,>=2.3.3 to >=2.3.3,<3.3 Updates the requirements on [wtforms](https://github.com/pallets-eco/wtforms) to permit the latest version. - [Release notes](https://github.com/pallets-eco/wtforms/releases) - [Changelog](https://github.com/pallets-eco/wtforms/blob/main/CHANGES.rst) - [Commits](https://github.com/pallets-eco/wtforms/compare/2.3.3...3.2.1) --- updated-dependencies: - dependency-name: wtforms dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- pyproject.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyproject.toml b/pyproject.toml index ac0fb1af..181dbe44 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -48,7 +48,7 @@ dependencies = [ "SQLAlchemy>=1.3.0,<1.5", "SQLAlchemy-Continuum>=1.3.12,<2", # New 1.4 changes API, see #728 "Werkzeug>=2,<3", - "WTForms>=2.3.3,<3.2",] + "WTForms>=2.3.3,<3.3",] [project.optional-dependencies] database = [ From 62fbeee15c954c788d3f3f4b80a14f73966f58c0 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 20 Dec 2024 16:18:35 +0000 Subject: [PATCH 30/46] Update pymysql requirement from <1.1,>=0.9 to >=0.9,<1.2 Updates the requirements on [pymysql](https://github.com/PyMySQL/PyMySQL) to permit the latest version. - [Release notes](https://github.com/PyMySQL/PyMySQL/releases) - [Changelog](https://github.com/PyMySQL/PyMySQL/blob/main/CHANGELOG.md) - [Commits](https://github.com/PyMySQL/PyMySQL/compare/v0.9.0...v1.1.1) --- updated-dependencies: - dependency-name: pymysql dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- pyproject.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyproject.toml b/pyproject.toml index 181dbe44..1419b249 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -54,7 +54,7 @@ dependencies = [ database = [ # Python 3.11 support starts in 2.9.2 "psycopg2-binary>=2.9.2,<2.9.9", - "PyMySQL>=0.9,<1.1", + "PyMySQL>=0.9,<1.2", ] dev = [ "ruff==0.6.8", From 0b0947686554fd701e2cdaf28884a2a14807faf8 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 20 Dec 2024 16:18:33 +0000 Subject: [PATCH 31/46] Bump vermin from 1.5.2 to 1.6.0 Bumps [vermin](https://github.com/netromdk/vermin) from 1.5.2 to 1.6.0. - [Release notes](https://github.com/netromdk/vermin/releases) - [Commits](https://github.com/netromdk/vermin/compare/v1.5.2...v1.6.0) --- updated-dependencies: - dependency-name: vermin dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] --- pyproject.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyproject.toml b/pyproject.toml index 1419b249..f22d242b 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -60,7 +60,7 @@ dev = [ "ruff==0.6.8", "flake8==5.0.4", "isort==5.11.5", - "vermin==1.5.2", + "vermin==1.6.0", "pytest>=6.2.5", "pytest-flask>=1.2.0", "zest.releaser>=6.20.1", From 2b21795e945bcd065876dc98f395065c91e5a672 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alexis=20M=C3=A9taireau?= Date: Fri, 20 Dec 2024 00:44:35 +0100 Subject: [PATCH 32/46] ci: Pin runners to ubuntu 22.04 --- .github/workflows/ci.yml | 6 +++--- .github/workflows/dockerhub.yml | 4 ++-- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 90b9d920..ee1492ed 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -8,7 +8,7 @@ on: jobs: lint: - runs-on: ubuntu-latest + runs-on: ubuntu-22.04 steps: - uses: actions/checkout@v3 - name: Install uv and set the python version @@ -21,7 +21,7 @@ jobs: test: # Dependency on linting to avoid running our expensive matrix test for nothing needs: lint - runs-on: ubuntu-latest + runs-on: ubuntu-22.04 # Use postgresql and MariaDB versions of Debian bookworm services: postgres: @@ -111,7 +111,7 @@ jobs: }} docs: - runs-on: ubuntu-latest + runs-on: ubuntu-22.04 steps: - uses: actions/checkout@v3 - name: Install uv and set the python version diff --git a/.github/workflows/dockerhub.yml b/.github/workflows/dockerhub.yml index 6c8a47b2..11ab270c 100644 --- a/.github/workflows/dockerhub.yml +++ b/.github/workflows/dockerhub.yml @@ -10,7 +10,7 @@ on: jobs: test: - runs-on: ubuntu-latest + runs-on: ubuntu-22.04 steps: - name: Checkout uses: actions/checkout@v2 @@ -19,7 +19,7 @@ jobs: run: docker compose -f docker-compose.test.yml run sut build_upload: - runs-on: ubuntu-latest + runs-on: ubuntu-22.04 needs: test if: github.event_name != 'pull_request' steps: From ce20f9adeabda760e770c50935f6e606144375b3 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 20 Dec 2024 16:34:50 +0000 Subject: [PATCH 33/46] Update myst-parser requirement from <3,>=2 to >=2,<5 Updates the requirements on [myst-parser](https://github.com/executablebooks/MyST-Parser) to permit the latest version. - [Release notes](https://github.com/executablebooks/MyST-Parser/releases) - [Changelog](https://github.com/executablebooks/MyST-Parser/blob/master/CHANGELOG.md) - [Commits](https://github.com/executablebooks/MyST-Parser/compare/v2.0.0...v4.0.0) --- updated-dependencies: - dependency-name: myst-parser dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- pyproject.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyproject.toml b/pyproject.toml index f22d242b..57f18d0c 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -68,7 +68,7 @@ dev = [ doc = [ "Sphinx>=7.0.1,<9", "docutils==0.20.1", - "myst-parser>=2,<3", + "myst-parser>=2,<5", ] [project.urls] From 83a60b12891b42b59a9ffe9f5e9cf1ecf2fe3fce Mon Sep 17 00:00:00 2001 From: jjspill1 Date: Mon, 12 Dec 2022 23:13:15 -0500 Subject: [PATCH 34/46] Add a cli to count the number of active projects --- ihatemoney/manage.py | 27 +++++++++++++ ihatemoney/tests/main_test.py | 71 ++++++++++++++++++++++++++++++++--- 2 files changed, 93 insertions(+), 5 deletions(-) diff --git a/ihatemoney/manage.py b/ihatemoney/manage.py index 69563f0d..d94a1dd4 100755 --- a/ihatemoney/manage.py +++ b/ihatemoney/manage.py @@ -4,6 +4,7 @@ import getpass import os import random import sys +import datetime import click from flask.cli import FlaskGroup @@ -93,5 +94,31 @@ def delete_project(project_name): db.session.commit() +@cli.command() +@click.argument("print_emails", default=False) +@click.argument("bills", default=0) # default values will get total projects +@click.argument("days", default=73000) # approximately 200 years +def get_project_count(print_emails, bills, days): + """Count projets with at least x bills and at less than x days old""" + projects = [ + pr + for pr in Project.query.all() + if pr.get_bills().count() > bills + and pr.get_bills()[0].date + > datetime.date.today() - datetime.timedelta(days=days) + ] + click.secho("Number of projects: " + str(len(projects))) + + if print_emails: + emails = set([pr.contact_email for pr in projects]) + emails_str = ", ".join(emails) + if len(emails) > 1: + click.secho("Contact emails: " + emails_str) + elif len(emails) == 1: + click.secho("Contact email: " + emails_str) + else: + click.secho("No contact emails found") + + if __name__ == "__main__": cli() diff --git a/ihatemoney/tests/main_test.py b/ihatemoney/tests/main_test.py index 843385f9..4d131e0a 100644 --- a/ihatemoney/tests/main_test.py +++ b/ihatemoney/tests/main_test.py @@ -3,13 +3,17 @@ import smtplib import socket from unittest.mock import MagicMock, patch -import pytest from sqlalchemy import orm from werkzeug.security import check_password_hash from ihatemoney import models from ihatemoney.currency_convertor import CurrencyConverter -from ihatemoney.manage import delete_project, generate_config, password_hash +from ihatemoney.manage import ( + delete_project, + generate_config, + get_project_count, + password_hash, +) from ihatemoney.run import load_configuration from ihatemoney.tests.common.ihatemoney_testcase import BaseTestCase, IhatemoneyTestCase @@ -229,6 +233,65 @@ class TestModels(IhatemoneyTestCase): pay_each_expected = 10 / 3 assert bill.pay_each() == pay_each_expected + def test_demo_project_count(self): + """Test command the get-project-count""" + self.post_project("raclette") + + # add members + self.client.post("/raclette/members/add", data={"name": "zorglub", "weight": 2}) + self.client.post("/raclette/members/add", data={"name": "fred"}) + self.client.post("/raclette/members/add", data={"name": "tata"}) + self.client.post("/raclette/members/add", data={"name": "pépé"}) + + # create bills + self.client.post( + "/raclette/add", + data={ + "date": "2011-08-10", + "what": "fromage à raclette", + "payer": 1, + "payed_for": [1, 2, 3], + "amount": "10.0", + }, + ) + + self.client.post( + "/raclette/add", + data={ + "date": "2011-08-10", + "what": "red wine", + "payer": 2, + "payed_for": [1], + "amount": "20", + }, + ) + + assert self.get_project("raclette").has_bills() + + # Now check the different parameters + runner = self.app.test_cli_runner() + result0 = runner.invoke(get_project_count) + assert result0.output.strip() == "Number of projects: 1" + + # With more than 1 bill, without printing emails + result1 = runner.invoke(get_project_count, "False 1") + assert result1.output.strip() == "Number of projects: 1" + + # With more than 2 bill, without printing emails + result2 = runner.invoke(get_project_count, "False 2") + assert result2.output.strip() == "Number of projects: 0" + + # With more than 0 days old + result3 = runner.invoke(get_project_count, "False 0 0") + assert result3.output.strip() == "Number of projects: 0" + + result4 = runner.invoke(get_project_count, "False 0 20000") + assert result4.output.strip() == "Number of projects: 1" + + # Print emails + result5 = runner.invoke(get_project_count, "True") + assert "raclette@notmyidea.org" in result5.output + class TestEmailFailure(IhatemoneyTestCase): def test_creation_email_failure_smtp(self): @@ -401,9 +464,7 @@ class TestCurrencyConverter: def test_failing_remote(self): rates = {} - with patch("requests.Response.json", new=lambda _: {}), pytest.warns( - UserWarning - ): + with patch("requests.Response.json", new=lambda _: {}): # we need a non-patched converter, but it seems that MagickMock # is mocking EVERY instance of the class method. Too bad. rates = CurrencyConverter.get_rates(self.converter) From 7505cbe25a5dfd87ce6f1a3dbe5a0f7c77bf146f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micka=C3=ABl=20Schoentgen?= Date: Fri, 15 Nov 2024 20:46:20 +0100 Subject: [PATCH 35/46] feat: Add a `SITE_NAME` setting and use it everywhere. --- docs/configuration.md | 8 ++++++++ ihatemoney/default_settings.py | 1 + ihatemoney/templates/layout.html | 2 +- ihatemoney/tests/budget_test.py | 5 ++++- ihatemoney/tests/ihatemoney.cfg | 1 + ihatemoney/web.py | 5 +++++ 6 files changed, 20 insertions(+), 2 deletions(-) diff --git a/docs/configuration.md b/docs/configuration.md index a6cc5d21..bf588471 100644 --- a/docs/configuration.md +++ b/docs/configuration.md @@ -173,6 +173,14 @@ URL you want. - **Default value:** `""` (empty string) - **Production value:** The URL of your chosing. +## SITE_NAME + +It is possible to change the name of the site to something at your liking. + +- **Default value:** `"I Hate Money"` (empty string) +- **Production value:** The name of your choosing + + ## Configuring email sending By default, Ihatemoney sends emails using a local SMTP server, but it's diff --git a/ihatemoney/default_settings.py b/ihatemoney/default_settings.py index 48112afb..64857378 100644 --- a/ihatemoney/default_settings.py +++ b/ihatemoney/default_settings.py @@ -3,6 +3,7 @@ DEBUG = SQLACHEMY_ECHO = False SQLALCHEMY_DATABASE_URI = "sqlite:////tmp/ihatemoney.db" SQLALCHEMY_TRACK_MODIFICATIONS = False SECRET_KEY = "tralala" +SITE_NAME = "I Hate Money" MAIL_DEFAULT_SENDER = "Budget manager " SHOW_ADMIN_EMAIL = True ACTIVATE_DEMO_PROJECT = True diff --git a/ihatemoney/templates/layout.html b/ihatemoney/templates/layout.html index 38b45064..5c04fb2e 100644 --- a/ihatemoney/templates/layout.html +++ b/ihatemoney/templates/layout.html @@ -20,7 +20,7 @@ - {{ _("Account manager") }}{% block title %}{% endblock %} + {{ SITE_NAME }} — {{ _("Account manager") }}{% block title %}{% endblock %} diff --git a/ihatemoney/tests/budget_test.py b/ihatemoney/tests/budget_test.py index 64a07533..a3fc813f 100644 --- a/ihatemoney/tests/budget_test.py +++ b/ihatemoney/tests/budget_test.py @@ -238,7 +238,10 @@ class TestBudget(IhatemoneyTestCase): url, data={"password": "pass", "password_confirmation": "pass"} ) resp = self.login("raclette", password="pass") - assert "Account manager - raclette" in resp.data.decode("utf-8") + assert ( + "I Hate Money — Account manager - raclette" + in resp.data.decode("utf-8") + ) # Test empty and null tokens resp = self.client.get("/reset-password") assert "No token provided" in resp.data.decode("utf-8") diff --git a/ihatemoney/tests/ihatemoney.cfg b/ihatemoney/tests/ihatemoney.cfg index 16c7534e..cba83608 100644 --- a/ihatemoney/tests/ihatemoney.cfg +++ b/ihatemoney/tests/ihatemoney.cfg @@ -3,6 +3,7 @@ DEBUG = False SQLALCHEMY_DATABASE_URI = 'sqlite:///budget.db' SQLACHEMY_ECHO = DEBUG +SITE_NAME = "I Hate Money" SECRET_KEY = "supersecret" diff --git a/ihatemoney/web.py b/ihatemoney/web.py index 9dfa17c6..43b04c21 100644 --- a/ihatemoney/web.py +++ b/ihatemoney/web.py @@ -137,6 +137,11 @@ def set_show_admin_dashboard_link(endpoint, values): g.logout_form = LogoutForm() +@main.context_processor +def add_template_variables(): + return {"SITE_NAME": current_app.config.get("SITE_NAME")} + + @main.url_value_preprocessor def pull_project(endpoint, values): """When a request contains a project_id value, transform it directly From 2aa410c68f37f6747aa9d6ceae6fccd5f3fc3e8f Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Mon, 23 Dec 2024 04:27:52 +0000 Subject: [PATCH 36/46] Update cachetools requirement from <5,>=4.1 to >=4.1,<6 Updates the requirements on [cachetools](https://github.com/tkem/cachetools) to permit the latest version. - [Changelog](https://github.com/tkem/cachetools/blob/master/CHANGELOG.rst) - [Commits](https://github.com/tkem/cachetools/compare/v4.1.0...v5.5.0) --- updated-dependencies: - dependency-name: cachetools dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- pyproject.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyproject.toml b/pyproject.toml index 57f18d0c..3c217184 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -27,7 +27,7 @@ classifiers = [ dependencies = [ "blinker>=1.4,<2", - "cachetools>=4.1,<5", + "cachetools>=4.1,<6", "debts>=0.5,<1", "email_validator>=1.0,<3", "Flask>=2,<4", From 4e9ff9b1ac2f89c6b8f29ac8196ba1d74835fced Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Mon, 23 Dec 2024 04:27:47 +0000 Subject: [PATCH 37/46] Update qrcode requirement from <8,>=7.1 to >=7.1,<9 Updates the requirements on [qrcode](https://github.com/lincolnloop/python-qrcode) to permit the latest version. - [Changelog](https://github.com/lincolnloop/python-qrcode/blob/main/CHANGES.rst) - [Commits](https://github.com/lincolnloop/python-qrcode/compare/v7.1...v8.0) --- updated-dependencies: - dependency-name: qrcode dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- pyproject.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyproject.toml b/pyproject.toml index 3c217184..6555c939 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -43,7 +43,7 @@ dependencies = [ "itsdangerous>=2,<3", "Jinja2>=3,<4", "python-dateutil", - "qrcode>=7.1,<8", + "qrcode>=7.1,<9", "requests>=2.25,<3", "SQLAlchemy>=1.3.0,<1.5", "SQLAlchemy-Continuum>=1.3.12,<2", # New 1.4 changes API, see #728 From 299c3849087c4ef073b8e3bb6b750ba2bcff0098 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Mon, 23 Dec 2024 04:27:41 +0000 Subject: [PATCH 38/46] Bump ruff from 0.6.8 to 0.8.4 Bumps [ruff](https://github.com/astral-sh/ruff) from 0.6.8 to 0.8.4. - [Release notes](https://github.com/astral-sh/ruff/releases) - [Changelog](https://github.com/astral-sh/ruff/blob/main/CHANGELOG.md) - [Commits](https://github.com/astral-sh/ruff/compare/0.6.8...0.8.4) --- updated-dependencies: - dependency-name: ruff dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] --- pyproject.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyproject.toml b/pyproject.toml index 6555c939..9d23cbc0 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -57,7 +57,7 @@ database = [ "PyMySQL>=0.9,<1.2", ] dev = [ - "ruff==0.6.8", + "ruff==0.8.4", "flake8==5.0.4", "isort==5.11.5", "vermin==1.6.0", From 61ea1f54d2404cd90f8f8df3299affb558ed2fab Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Mon, 23 Dec 2024 04:28:01 +0000 Subject: [PATCH 39/46] Update psycopg2-binary requirement Updates the requirements on [psycopg2-binary](https://github.com/psycopg/psycopg2) to permit the latest version. - [Changelog](https://github.com/psycopg/psycopg2/blob/master/NEWS) - [Commits](https://github.com/psycopg/psycopg2/compare/2.9.6...2.9.10) --- updated-dependencies: - dependency-name: psycopg2-binary dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- pyproject.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyproject.toml b/pyproject.toml index 9d23cbc0..c8087b31 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -53,7 +53,7 @@ dependencies = [ [project.optional-dependencies] database = [ # Python 3.11 support starts in 2.9.2 - "psycopg2-binary>=2.9.2,<2.9.9", + "psycopg2-binary>=2.9.2,<2.9.11", "PyMySQL>=0.9,<1.2", ] dev = [ From 752c80d29f9405bad8fe4e15993aa2cc6c649c5a Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 24 Dec 2024 04:29:48 +0000 Subject: [PATCH 40/46] Update flask-cors requirement from <4,>=3.0.8 to >=3.0.8,<6 Updates the requirements on [flask-cors](https://github.com/corydolphin/flask-cors) to permit the latest version. - [Release notes](https://github.com/corydolphin/flask-cors/releases) - [Changelog](https://github.com/corydolphin/flask-cors/blob/main/CHANGELOG.md) - [Commits](https://github.com/corydolphin/flask-cors/compare/3.0.8...5.0.0) --- updated-dependencies: - dependency-name: flask-cors dependency-type: direct:production ... Signed-off-by: dependabot[bot] --- pyproject.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pyproject.toml b/pyproject.toml index c8087b31..485f34c6 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -32,7 +32,7 @@ dependencies = [ "email_validator>=1.0,<3", "Flask>=2,<4", "Flask-Babel>=1.0,<4", - "Flask-Cors>=3.0.8,<4", + "Flask-Cors>=3.0.8,<6", "Flask-Limiter>=2.6,<3", "Flask-Mail>=0.9.1,<1", "Flask-Migrate>=2.5.3,<5", # Not following semantic versioning (e.g. https://github.com/miguelgrinberg/flask-migrate/commit/1af28ba273de6c88544623b8dc02dd539340294b) From 2f099674ed518bcaf2147a26edcddf0b448b900f Mon Sep 17 00:00:00 2001 From: Jojo144 Date: Wed, 25 Dec 2024 18:14:28 +0100 Subject: [PATCH 41/46] Workaround to avoid history bug #1324 --- ihatemoney/history.py | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/ihatemoney/history.py b/ihatemoney/history.py index 4fed53ea..90d6d6e5 100644 --- a/ihatemoney/history.py +++ b/ihatemoney/history.py @@ -38,7 +38,10 @@ def history_sort_key(history_item_dict): def describe_version(version_obj): """Use the base model str() function to describe a version object""" - return parent_class(type(version_obj)).__str__(version_obj) + if version_obj is None: + return "" + else: + return parent_class(type(version_obj)).__str__(version_obj) def describe_owers_change(version, human_readable_names): From e00c39a62c56f16b9e6a07086c134b5cba1bf449 Mon Sep 17 00:00:00 2001 From: Jojo144 Date: Wed, 25 Dec 2024 23:21:10 +0100 Subject: [PATCH 42/46] Update ihatemoney/history.py MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Alexis Métaireau --- ihatemoney/history.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ihatemoney/history.py b/ihatemoney/history.py index 90d6d6e5..273cffb8 100644 --- a/ihatemoney/history.py +++ b/ihatemoney/history.py @@ -38,7 +38,7 @@ def history_sort_key(history_item_dict): def describe_version(version_obj): """Use the base model str() function to describe a version object""" - if version_obj is None: + if not version_obj: return "" else: return parent_class(type(version_obj)).__str__(version_obj) From dcb61b62b11695fc1a77927994e73da5893018dd Mon Sep 17 00:00:00 2001 From: Jojo144 Date: Wed, 25 Dec 2024 17:54:40 +0100 Subject: [PATCH 43/46] Update contibuting.md with uv dependency --- docs/contributing.md | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/docs/contributing.md b/docs/contributing.md index 3be42a41..cf01c8ae 100644 --- a/docs/contributing.md +++ b/docs/contributing.md @@ -78,6 +78,15 @@ Thanks again! (setup-dev-environment)= ## Set up a dev environment +### Requirements + +In addition to general {ref}`requirements`, you will need +**uv**. It recommended to install uv [system +wide](https://docs.astral.sh/uv/getting-started/installation/#standalone-installer) +as it is a kind of replacement for pip. + +### Getting the sources + You must develop on top of the Git master branch: git clone https://github.com/spiral-project/ihatemoney.git From 4b96e894222c727725d6b0fb86f1fe05dfbc3edb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alexis=20M=C3=A9taireau?= Date: Fri, 20 Dec 2024 18:12:27 +0100 Subject: [PATCH 44/46] Remove flake8 --- pyproject.toml | 1 - uv.lock | 60 ++++++++------------------------------------------ 2 files changed, 9 insertions(+), 52 deletions(-) diff --git a/pyproject.toml b/pyproject.toml index 485f34c6..ec22dd46 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -58,7 +58,6 @@ database = [ ] dev = [ "ruff==0.8.4", - "flake8==5.0.4", "isort==5.11.5", "vermin==1.6.0", "pytest>=6.2.5", diff --git a/uv.lock b/uv.lock index b2123436..4a1fcc26 100644 --- a/uv.lock +++ b/uv.lock @@ -439,20 +439,6 @@ wheels = [ { url = "https://files.pythonhosted.org/packages/02/cc/b7e31358aac6ed1ef2bb790a9746ac2c69bcb3c8588b41616914eb106eaf/exceptiongroup-1.2.2-py3-none-any.whl", hash = "sha256:3111b9d131c238bec2f8f516e123e14ba243563fb135d3fe885990585aa7795b", size = 16453 }, ] -[[package]] -name = "flake8" -version = "5.0.4" -source = { registry = "https://pypi.org/simple" } -dependencies = [ - { name = "mccabe" }, - { name = "pycodestyle" }, - { name = "pyflakes" }, -] -sdist = { url = "https://files.pythonhosted.org/packages/ad/00/9808c62b2d529cefc69ce4e4a1ea42c0f855effa55817b7327ec5b75e60a/flake8-5.0.4.tar.gz", hash = "sha256:6fbe320aad8d6b95cec8b8e47bc933004678dc63095be98528b7bdd2a9f510db", size = 145862 } -wheels = [ - { url = "https://files.pythonhosted.org/packages/cf/a0/b881b63a17a59d9d07f5c0cc91a29182c8e8a9aa2bde5b3b2b16519c02f4/flake8-5.0.4-py2.py3-none-any.whl", hash = "sha256:7a1cf6b73744f5806ab95e526f6f0d8c01c66d7bbe349562d22dfca20610b248", size = 61897 }, -] - [[package]] name = "flask" version = "2.3.3" @@ -708,7 +694,6 @@ database = [ { name = "pymysql" }, ] dev = [ - { name = "flake8" }, { name = "isort" }, { name = "pytest" }, { name = "pytest-flask" }, @@ -729,8 +714,7 @@ requires-dist = [ { name = "debts", specifier = ">=0.5,<1" }, { name = "docutils", marker = "extra == 'doc'", specifier = "==0.20.1" }, { name = "email-validator", specifier = ">=1.0,<3" }, - { name = "flake8", marker = "extra == 'dev'", specifier = "==5.0.4" }, - { name = "flask", specifier = ">=2,<3" }, + { name = "flask", specifier = ">=2,<4" }, { name = "flask-babel", specifier = ">=1.0,<4" }, { name = "flask-cors", specifier = ">=3.0.8,<4" }, { name = "flask-limiter", specifier = ">=2.6,<3" }, @@ -743,21 +727,21 @@ requires-dist = [ { name = "isort", marker = "extra == 'dev'", specifier = "==5.11.5" }, { name = "itsdangerous", specifier = ">=2,<3" }, { name = "jinja2", specifier = ">=3,<4" }, - { name = "myst-parser", marker = "extra == 'doc'", specifier = ">=2,<3" }, + { name = "myst-parser", marker = "extra == 'doc'", specifier = ">=2,<5" }, { name = "psycopg2-binary", marker = "extra == 'database'", specifier = ">=2.9.2,<2.9.9" }, - { name = "pymysql", marker = "extra == 'database'", specifier = ">=0.9,<1.1" }, + { name = "pymysql", marker = "extra == 'database'", specifier = ">=0.9,<1.2" }, { name = "pytest", marker = "extra == 'dev'", specifier = ">=6.2.5" }, { name = "pytest-flask", marker = "extra == 'dev'", specifier = ">=1.2.0" }, { name = "python-dateutil" }, { name = "qrcode", specifier = ">=7.1,<8" }, { name = "requests", specifier = ">=2.25,<3" }, { name = "ruff", marker = "extra == 'dev'", specifier = "==0.6.8" }, - { name = "sphinx", marker = "extra == 'doc'", specifier = ">=7.0.1,<8" }, + { name = "sphinx", marker = "extra == 'doc'", specifier = ">=7.0.1,<9" }, { name = "sqlalchemy", specifier = ">=1.3.0,<1.5" }, { name = "sqlalchemy-continuum", specifier = ">=1.3.12,<2" }, - { name = "vermin", marker = "extra == 'dev'", specifier = "==1.5.2" }, + { name = "vermin", marker = "extra == 'dev'", specifier = "==1.6.0" }, { name = "werkzeug", specifier = ">=2,<3" }, - { name = "wtforms", specifier = ">=2.3.3,<3.2" }, + { name = "wtforms", specifier = ">=2.3.3,<3.3" }, { name = "zest-releaser", marker = "extra == 'dev'", specifier = ">=6.20.1" }, ] @@ -994,15 +978,6 @@ wheels = [ { url = "https://files.pythonhosted.org/packages/f6/f8/4da07de16f10551ca1f640c92b5f316f9394088b183c6a57183df6de5ae4/MarkupSafe-2.1.5-cp39-cp39-win_amd64.whl", hash = "sha256:fa173ec60341d6bb97a89f5ea19c85c5643c1e7dedebc22f5181eb73573142c5", size = 17211 }, ] -[[package]] -name = "mccabe" -version = "0.7.0" -source = { registry = "https://pypi.org/simple" } -sdist = { url = "https://files.pythonhosted.org/packages/e7/ff/0ffefdcac38932a54d2b5eed4e0ba8a408f215002cd178ad1df0f2806ff8/mccabe-0.7.0.tar.gz", hash = "sha256:348e0240c33b60bbdf4e523192ef919f28cb2c3d7d5c7794f74009290f236325", size = 9658 } -wheels = [ - { url = "https://files.pythonhosted.org/packages/27/1a/1f68f9ba0c207934b35b86a8ca3aad8395a3d6dd7921c0686e23853ff5a9/mccabe-0.7.0-py2.py3-none-any.whl", hash = "sha256:6c2d30ab6be0e4a46919781807b4f0d834ebdd6c6e3dca0bda5a15f863427b6e", size = 7350 }, -] - [[package]] name = "mdit-py-plugins" version = "0.4.2" @@ -1165,15 +1140,6 @@ wheels = [ { url = "https://files.pythonhosted.org/packages/e7/56/39189b7bf61744a627c18f3a919647f7eac78d849de1f8b2ad1a5c11f824/psycopg2_binary-2.9.8-cp39-cp39-win_amd64.whl", hash = "sha256:1f279ba74f0d6b374526e5976c626d2ac3b8333b6a7b08755c513f4d380d3add", size = 1177351 }, ] -[[package]] -name = "pycodestyle" -version = "2.9.1" -source = { registry = "https://pypi.org/simple" } -sdist = { url = "https://files.pythonhosted.org/packages/b6/83/5bcaedba1f47200f0665ceb07bcb00e2be123192742ee0edfb66b600e5fd/pycodestyle-2.9.1.tar.gz", hash = "sha256:2c9607871d58c76354b697b42f5d57e1ada7d261c261efac224b664affdc5785", size = 102127 } -wheels = [ - { url = "https://files.pythonhosted.org/packages/67/e4/fc77f1039c34b3612c4867b69cbb2b8a4e569720b1f19b0637002ee03aff/pycodestyle-2.9.1-py2.py3-none-any.whl", hash = "sha256:d1735fc58b418fd7c5f658d28d943854f8a849b01a5d0a1e6f3f3fdd0166804b", size = 41493 }, -] - [[package]] name = "pycparser" version = "2.22" @@ -1183,15 +1149,6 @@ wheels = [ { url = "https://files.pythonhosted.org/packages/13/a3/a812df4e2dd5696d1f351d58b8fe16a405b234ad2886a0dab9183fb78109/pycparser-2.22-py3-none-any.whl", hash = "sha256:c3702b6d3dd8c7abc1afa565d7e63d53a1d0bd86cdc24edd75470f4de499cfcc", size = 117552 }, ] -[[package]] -name = "pyflakes" -version = "2.5.0" -source = { registry = "https://pypi.org/simple" } -sdist = { url = "https://files.pythonhosted.org/packages/07/92/f0cb5381f752e89a598dd2850941e7f570ac3cb8ea4a344854de486db152/pyflakes-2.5.0.tar.gz", hash = "sha256:491feb020dca48ccc562a8c0cbe8df07ee13078df59813b83959cbdada312ea3", size = 66388 } -wheels = [ - { url = "https://files.pythonhosted.org/packages/dc/13/63178f59f74e53acc2165aee4b002619a3cfa7eeaeac989a9eb41edf364e/pyflakes-2.5.0-py2.py3-none-any.whl", hash = "sha256:4579f67d887f804e67edb544428f264b7b24f435b263c4614f384135cea553d2", size = 66116 }, -] - [[package]] name = "pygments" version = "2.18.0" @@ -1695,10 +1652,11 @@ wheels = [ [[package]] name = "vermin" -version = "1.5.2" +version = "1.6.0" source = { registry = "https://pypi.org/simple" } +sdist = { url = "https://files.pythonhosted.org/packages/3d/26/7b871396c33006c445c25ef7da605ecbd6cef830d577b496d2b73a554f9d/vermin-1.6.0.tar.gz", hash = "sha256:6266ca02f55d1c2aa189a610017c132eb2d1934f09e72a955b1eb3820ee6d4ef", size = 93181 } wheels = [ - { url = "https://files.pythonhosted.org/packages/46/ed/420955392d9c2743c93e0418928927e34aba355c716a70c6bdba209b930f/vermin-1.5.2-py2.py3-none-any.whl", hash = "sha256:c1566ad4e1c8e1b0e98cf5f7d69b691d44a578e2ce9c5aa1d418736bc4944b32", size = 89266 }, + { url = "https://files.pythonhosted.org/packages/2e/98/1a2ca43e6d646421eea16ec19977e2e6d1ea9079bd9d873bfae513d43f1c/vermin-1.6.0-py2.py3-none-any.whl", hash = "sha256:f1fa9ee40f59983dc40e0477eb2b1fa8061a3df4c3b2bcf349add462a5610efb", size = 90845 }, ] [[package]] From 85eccb74b286e8982d8af137951ee7c5f3409971 Mon Sep 17 00:00:00 2001 From: ferid333 <135500346+ferid333@users.noreply.github.com> Date: Fri, 29 Nov 2024 21:35:03 +0400 Subject: [PATCH 45/46] I added Azerbaijani Translation I added Azerbaijani Translation Co-Authored-By: qurbanov <10328930+qurbanov@users.noreply.github.com> --- .../translations/az/LC_MESSAGES/messages.po | 1155 +++++++++++++++++ 1 file changed, 1155 insertions(+) create mode 100644 ihatemoney/translations/az/LC_MESSAGES/messages.po diff --git a/ihatemoney/translations/az/LC_MESSAGES/messages.po b/ihatemoney/translations/az/LC_MESSAGES/messages.po new file mode 100644 index 00000000..cade095b --- /dev/null +++ b/ihatemoney/translations/az/LC_MESSAGES/messages.po @@ -0,0 +1,1155 @@ +msgid "" +msgstr "" +"Project-Id-Version: PACKAGE VERSION\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2024-11-29 14:24+0200\n" +"Last-Translator: Farid Gurbanov \n" +"i-hate-money/az/>\n" +"Language: az\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=utf-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=n != 1;\n" +"X-Generator: Weblate 5.3-dev\n" +"Generated-By: Babel 2.9.0\n" + +#, python-format +msgid "You have just created '%(project)s' to share your expenses" +msgstr "Xərclərinizi bölüşmək üçün '%(project)s' yaratdınız" + +msgid "" +"Not a valid amount or expression. Only numbers and + - * / operators are " +"accepted." +msgstr "" +"Etibarlı məbləğ və ya ifadə deyil. Yalnız rəqəmlər və + - * / operatorları qəbul edilir." + +msgid "Project name" +msgstr "Layihə adı" + +msgid "Current private code" +msgstr "Cari gizli kod" + +msgid "Enter existing private code to edit project" +msgstr "Layihəni redaktə etmək üçün mövcud gizli kodu daxil edin" + +msgid "New private code" +msgstr "Yeni gizli kod" + +msgid "Enter a new code if you want to change it" +msgstr "Kodu dəyişmək istəyirsinizsə, yenisini daxil edin" + +msgid "Email" +msgstr "E-poçt" + +msgid "Enable project history" +msgstr "Layihə tarixçəsini aktiv edin" + +msgid "Use IP tracking for project history" +msgstr "Layihə tarixçəsi üçün IP izləmədən istifadə edin" + +msgid "Default Currency" +msgstr "Susmaya görə valyuta" + +msgid "Setting a default currency enables currency conversion between bills" +msgstr "" +"Susmaya görə valyutanın təyin edilməsi, fakturalar arasında valyuta çevrilməsini aktivləşdirir" + +msgid "Unknown error" +msgstr "Naməlum səhv" + +msgid "Invalid private code." +msgstr "Yanlış gizli kod." + +msgid "" +"This project cannot be set to 'no currency' because it contains bills in " +"multiple currencies." +msgstr "" +"Bu layihə bir neçə valyutada fakturalar olduğu üçün 'valyuta yoxdur' olaraq təyin edilə bilməz." + +msgid "Compatible with Cospend" +msgstr "Cospend ilə uyğundur" + +msgid "Project identifier" +msgstr "Layihə identifikatoru" + +msgid "Private code" +msgstr "Gizli kod" + +msgid "Create the project" +msgstr "Layihə yaradın" + +#, python-format +msgid "" +"A project with this identifier (\"%(project)s\") already exists. Please " +"choose a new identifier" +msgstr "" +"Bu identifikatora malik bir layihə (\"%(project)s\") artıq mövcuddur. Zəhmət olmasa yeni bir identifikator seçin" + +msgid "Which is a real currency: Euro or Petro dollar?" +msgstr "Hansını gerçək valyutadır: Avro yoxsa Petro dollar?" + +msgid "euro" +msgstr "avro" + +msgid "Please, validate the captcha to proceed." +msgstr "Zəhmət olmasa, davam etmək üçün captchadan keçin." + +msgid "Enter private code to confirm deletion" +msgstr "Silmə əməliyyatını təsdiqləmək üçün gizli kodu daxil edin" + +msgid "Get in" +msgstr "Daxil olun" + +msgid "Admin password" +msgstr "Admin parolu" + +msgid "Send me the code by email" +msgstr "Kodu mənə e-poçtla göndərin" + +msgid "This project does not exists" +msgstr "Bu layihə mövcud deyil" + +msgid "Password mismatch" +msgstr "Parollar uyğun gəlmir" + +msgid "Password" +msgstr "Parol" + +msgid "Password confirmation" +msgstr "Parol təsdiqi" + +msgid "Reset password" +msgstr "Parolu sıfırlayın" + +msgid "When?" +msgstr "Nə vaxt?" + +msgid "What?" +msgstr "Nə?" + +msgid "Who paid?" +msgstr "Kim ödəyib?" + +msgid "How much?" +msgstr "Nə qədər?" + +msgid "Currency" +msgstr "Valyuta" + +msgid "External link" +msgstr "Xarici bağlantı" + +msgid "A link to an external document, related to this bill" +msgstr "Bu faktura ilə bağlı xarici sənədə keçid" + +msgid "For whom?" +msgstr "Kim üçün?" + +msgid "Submit" +msgstr "Təsdiqlə" + +msgid "Submit and add a new one" +msgstr "Təsdiqlə və yenisini əlavə et" + +#, python-format +msgid "Project default: %(currency)s" +msgstr "Layihənin susmaya görə dəyəri: %(currency)s" + +msgid "Name" +msgstr "Ad" + +msgid "Weights should be positive" +msgstr "Çəki müsbət olmalıdır" + +msgid "Weight" +msgstr "Çəki" + +msgid "Add" +msgstr "Əlavə et" + +msgid "The participant name is invalid" +msgstr "İştirakçı adı etibarsızdır" + +msgid "This project already have this participant" +msgstr "Bu layihədə bu iştirakçı artıq mövcuddur" + +msgid "People to notify" +msgstr "Xəbər veriləcək şəxslər" + +msgid "Send the invitations" +msgstr "Dəvətləri göndərin" + +#, python-format +msgid "The email %(email)s is not valid" +msgstr "%(email)s e-poçt ünvanı etibarlı deyil" + +msgid "Logout" +msgstr "Çıxış et" + +msgid "Please check the email configuration of the server." +msgstr "Zəhmət olmasa, serverin e-poçt konfiqurasiyasını yoxlayın." + +#, python-format +msgid "" +"Please check the email configuration of the server or contact the " +"administrator: %(admin_email)s" +msgstr "" +"Zəhmət olmasa, serverin e-poçt konfiqurasiyasını yoxlayın və ya administratorla əlaqə saxlayın: %(admin_email)s" + +#. List with two items only +msgid "{dual_object_0} and {dual_object_1}" +msgstr "{dual_object_0} və {dual_object_1}" + +#. Last two items of a list with more than 3 items +msgid "{previous_object}, and {end_object}" +msgstr "{previous_object} və {end_object}" + +#. Two items in a middle of a list with more than 5 objects +msgid "{previous_object}, {next_object}" +msgstr "{previous_object}, {next_object}" + +#. First two items of a list with more than 3 items +msgid "{start_object}, {next_object}" +msgstr "{start_object}, {next_object}" + +msgid "No Currency" +msgstr "Valyuta yoxdur" + +#. Form error with only one error +msgid "{prefix}: {error}" +msgstr "{prefix}: {error}" + +#. Form error with a list of errors +msgid "{prefix}:
{errors}" +msgstr "{prefix}:
{errors}" + +msgid "Too many failed login attempts." +msgstr "Çox sayda uğursuz giriş cəhdi." + +#, python-format +msgid "This admin password is not the right one. Only %(num)d attempts left." +msgstr "Bu admin parolu düzgün deyil. Yalnız %(num)d cəhd qaldı." + +msgid "Provided token is invalid" +msgstr "Təqdim edilən token etibarsızdır" + +msgid "This private code is not the right one" +msgstr "Bu gizli kod düzgün deyil" + +msgid "A reminder email has just been sent to you" +msgstr "Sizə yeni bir xatırlatma e-poçtu göndərildi" + +msgid "" +"We tried to send you an reminder email, but there was an error. You can " +"still use the project normally." +msgstr "" +"Sizə xatırlatma e-poçtu göndərməyə çalışdıq, lakin bir səhv baş verdi. Layihədən normal istifadə etməyə davam edə bilərsiniz." + +msgid "" +"Sorry, there was an error while sending you an email with password reset " +"instructions." +msgstr "" +"Bağışlayın, parolun sıfırlanması ilə bağlı təlimatları ehtiva edən e-poçtu göndərərkən səhv baş verdi." + +msgid "No token provided" +msgstr "Token təqdim edilməyib" + +msgid "Invalid token" +msgstr "Etibarsız token" + +msgid "Unknown project" +msgstr "Naməlum layihə" + +msgid "Password successfully reset." +msgstr "Parol uğurla sıfırlandı." + +msgid "Project settings have been changed successfully." +msgstr "Layihə parametrləri uğurla dəyişdirildi." + +msgid "Unable to parse CSV" +msgstr "CSV analiz edilə bilmədi" + +#, python-format +msgid "Missing attribute: %(attribute)s" +msgstr "Əskik xüsusiyyət: %(attribute)s" + +msgid "" +"Cannot add bills in multiple currencies to a project without default " +"currency" +msgstr "" +"Susmaya görə valyutası olmayan layihəyə müxtəlif valyutalarda fakturalar əlavə edilə bilməz" + +msgid "Project successfully uploaded" +msgstr "Layihə uğurla yükləndi" + +msgid "Project successfully deleted" +msgstr "Layihə uğurla silindi" + +msgid "Error deleting project" +msgstr "Layihə silinərkən səhv baş verdi" + +msgid "Unable to logout" +msgstr "Çıxış edilə bilmədi" + +#, python-format +msgid "You have been invited to share your expenses for %(project)s" +msgstr "%(project)s üçün xərclərinizi bölüşməyə dəvət olunmusunuz" + +msgid "Your invitations have been sent" +msgstr "Dəvətləriniz göndərildi" + +msgid "Sorry, there was an error while trying to send the invitation emails." +msgstr "Bağışlayın, dəvət e-poçtlarını göndərməyə çalışarkən səhv baş verdi." + +#, python-format +msgid "%(member)s has been added" +msgstr "%(member)s əlavə edildi" + +msgid "Error activating participant" +msgstr "İştirakçı aktivləşdirilərkən səhv baş verdi" + +#, python-format +msgid "%(name)s is part of this project again" +msgstr "%(name)s yenidən bu layihənin bir hissəsidir" + +msgid "Error removing participant" +msgstr "İştirakçı silinərkən səhv baş verdi" + +#, python-format +msgid "" +"Participant '%(name)s' has been deactivated. It will still appear in the " +"list until its balance reach zero." +msgstr "" +"'%(name)s' iştirakçısı deaktiv edildi. Onun balansı sıfıra enənə qədər siyahıda görünməyə davam edəcək." + +#, python-format +msgid "Participant '%(name)s' has been removed" +msgstr "'%(name)s' iştirakçısı silindi" + +#, python-format +msgid "Participant '%(name)s' has been modified" +msgstr "'%(name)s' iştirakçısı dəyişdirildi" + +msgid "The bill has been added" +msgstr "Faktura əlavə edildi" + +msgid "Error deleting bill" +msgstr "Faktura silinərkən səhv baş verdi" + +msgid "The bill has been deleted" +msgstr "Faktura silindi" + +msgid "The bill has been modified" +msgstr "Faktura dəyişdirildi" + +#, python-format +msgid "%(lang)s is not a supported language" +msgstr "%(lang)s dili dəstəklənmir" + +msgid "Error deleting project history" +msgstr "Layihə tarixi silinərkən səhv baş verdi" + +msgid "Deleted project history." +msgstr "Layihə tarixi silindi." + +msgid "Error deleting recorded IP addresses" +msgstr "Qeyd olunan IP ünvanlar silinərkən səhv baş verdi" + +msgid "Deleted recorded IP addresses in project history." +msgstr "Layihə tarixində qeyd olunan IP ünvanlar silindi." + +msgid "Sorry, we were unable to find the page you've asked for." +msgstr "Bağışlayın, soruşduğunuz səhifəni tapa bilmədik." + +msgid "The best thing to do is probably to get back to the main page." +msgstr "Ən yaxşı seçim yəqin ki, əsas səhifəyə qayıtmaqdır." + +msgid "Back to the list" +msgstr "Siyahıya qayıt" + +msgid "Administration tasks are currently disabled." +msgstr "İdarəetmə vəzifələri hazırda deaktivdir." + +msgid "Authentication" +msgstr "Doğrulama" + +msgid "The project you are trying to access do not exist, do you want to" +msgstr "Erişməyə çalışdığınız layihə mövcud deyil, istəyirsinizmi" + +msgid "create it" +msgstr "onu yaratmaq" + +msgid "?" +msgstr "?" + +msgid "Create a new project" +msgstr "Yeni layihə yarat" + +msgid "Project" +msgstr "Layihə" + +msgid "Number of participants" +msgstr "İştirakçı sayı" + +msgid "Number of bills" +msgstr "Faktura sayı" + +msgid "Newest bill" +msgstr "Ən yeni faktura" + +msgid "Oldest bill" +msgstr "Ən köhnə faktura" + +msgid "Actions" +msgstr "Hərəkətlər" + +msgid "edit" +msgstr "düzəlt" + +msgid "Delete project" +msgstr "Layihəni sil" + +msgid "show" +msgstr "göstər" + +msgid "The Dashboard is currently deactivated." +msgstr "İdarəetmə paneli hazırda deaktivdir." + +msgid "Download Mobile Application" +msgstr "Mobil Tətbiqi Yükləyin" + +msgid "Get it on" +msgstr "Yükləyin" + +msgid "Edit project" +msgstr "Layihəni düzəlt" + +msgid "Import project" +msgstr "Layihəni idxal et" + +msgid "Download project's data" +msgstr "Layihənin məlumatlarını yüklə" + +msgid "Bill items" +msgstr "Faktura maddələri" + +msgid "Download the list of bills with owner, amount, reason,... " +msgstr "Sahibi, məbləği, səbəbi,... ilə fakturaların siyahısını yüklə" + +msgid "Settle plans" +msgstr "Planları ödə" + +msgid "Download the list of transactions needed to settle the current bills." +msgstr "Cari fakturaların ödənməsi üçün lazım olan əməliyyatların siyahısını yüklə." + +msgid "Can't remember the password?" +msgstr "Şifrəni xatırlaya bilmirsiniz?" + +msgid "Cancel" +msgstr "Ləğv et" + +msgid "Privacy Settings" +msgstr "Məxfilik Parametrləri" + +msgid "Save changes" +msgstr "Dəyişiklikləri yadda saxla" + +msgid "This will remove all bills and participants in this project!" +msgstr "Bu, bu layihədəki bütün fakturaları və iştirakçıları siləcək!" + +msgid "Import previously exported project" +msgstr "Əvvəl ixrac edilmiş layihəni idxal et" + +msgid "Choose file" +msgstr "Faylı seçin" + +msgid "Edit this bill" +msgstr "Bu fakturanı düzəlt" + +msgid "Add a bill" +msgstr "Faktura əlavə et" + +msgid "Simple operations are allowed, e.g. (18+36.2)/3" +msgstr "Sadə əməliyyatlara icazə verilir, məsələn (18+36.2)/3" + +msgid "Everyone" +msgstr "Hər kəs" + +msgid "No one" +msgstr "Heç kim" + +msgid "More options" +msgstr "Daha çox seçim" + +msgid "Add participant" +msgstr "İştirakçı əlavə et" + +msgid "Edit this participant" +msgstr "Bu iştirakçını düzəlt" + +msgid "john.doe@example.com, mary.moe@site.com" +msgstr "john.doe@example.com, mary.moe@site.com" + +msgid "Download" +msgstr "Yüklə" + +msgid "Disabled Project History" +msgstr "Layihə Tarixi Deaktivdir" + +msgid "Disabled Project History & IP Address Recording" +msgstr "Layihə Tarixi və IP Ünvan Qeydiyyatı Deaktivdir" + +msgid "Enabled Project History" +msgstr "Layihə Tarixi Aktivdir" + +msgid "Disabled IP Address Recording" +msgstr "IP Ünvan Qeydiyyatı Deaktivdir" + +msgid "Enabled Project History & IP Address Recording" +msgstr "Layihə Tarixi və IP Ünvan Qeydiyyatı Aktivdir" + +msgid "Enabled IP Address Recording" +msgstr "IP Ünvan Qeydiyyatı Aktivdir" + +msgid "History Settings Changed" +msgstr "Tarix Parametrləri Dəyişdirildi" + +#, python-format +msgid "Bill %(name)s: %(property_name)s changed from %(before)s to %(after)s" +msgstr "" +"Hesab %(name)s: %(property_name)s %(before)s-dən %(after)s-ə dəyişdirildi" + +#, python-format +msgid "Bill %(name)s: %(property_name)s changed to %(after)s" +msgstr "Hesab %(name)s: %(property_name)s, %(after)s olaraq dəyişdirildi" + +msgid "Confirm Remove IP Adresses" +msgstr "IP ünvanlarının silinməsini təsdiqləyin" + +msgid "" +"Are you sure you want to delete all recorded IP addresses from this " +"project?\n" +" The rest of the project history will be unaffected. This " +"action cannot be undone." +msgstr "" +"Bu layihədə qeyd olunan bütün IP ünvanlarını silmək istədiyinizdən " +"əminsiniz?\n" +" Layihənin qalan tarixi dəyişməyəcək. Bu əməliyyatı " +"geri qaytarmaq mümkün deyil." + +msgid "Confirm deletion" +msgstr "Silinməni təsdiqləyin" + +msgid "Close" +msgstr "Bağla" + +msgid "Delete Confirmation" +msgstr "Silinməni Təsdiqləyin" + +msgid "" +"Are you sure you want to erase all history for this project? This action " +"cannot be undone." +msgstr "" +"Bu layihənin bütün tarixçəsini silmək istədiyinizdən əminsiniz? Bu əməliyyat " +"geri qaytarıla bilməz." + +#, python-format +msgid "Bill %(name)s: added %(owers_list_str)s to owers list" +msgstr "Hesab %(name)s: %(owers_list_str)s borclular siyahısına əlavə edildi" + +#, python-format +msgid "Bill %(name)s: removed %(owers_list_str)s from owers list" +msgstr "Hesab %(name)s: %(owers_list_str)s borclular siyahısından çıxarıldı" + +msgid "This project has history disabled. New actions won't appear below." +msgstr "" +"Bu layihənin tarixçəsi söndürülüb. Yeni əməliyyatlar aşağıda görünməyəcək." + +msgid "You can enable history on the settings page." +msgstr "Tarixçəni ayarlar səhifəsindən aktivləşdirə bilərsiniz." + +msgid "" +"The table below reflects actions recorded prior to disabling project " +"history." +msgstr "" +"Aşağıdakı cədvəl, layihə tarixçəsi söndürülməzdən əvvəl qeyd olunan " +"əməliyyatları göstərir." + +msgid "You can clear the project history to remove them." +msgstr "Onları silmək üçün layihə tarixçəsini təmizləyə bilərsiniz." + +msgid "" +"Some entries below contain IP addresses, even though this project has IP " +"recording disabled. " +msgstr "" +"Bu layihədə IP ünvanlarının qeyd edilməsi söndürülsə də, aşağıdakı bəzi " +"girişlər IP ünvanlarını ehtiva edir. " + +msgid "Delete stored IP addresses" +msgstr "Saxlanılan IP ünvanlarını sil" + +msgid "No IP Addresses to erase" +msgstr "Silinməsi üçün IP ünvanı yoxdur" + +msgid "Delete Stored IP Addresses" +msgstr "Saxlanılan IP Ünvanlarını Sil" + +msgid "No history to erase" +msgstr "Silinməsi üçün tarixçə yoxdur" + +msgid "Clear Project History" +msgstr "Layihə Tarixçəsini Təmizlə" + +msgid "Time" +msgstr "Vaxt" + +msgid "Event" +msgstr "Hadisə" + +msgid "IP address recording can be enabled on the settings page" +msgstr "IP ünvanlarının qeyd edilməsi ayarlar səhifəsindən aktivləşdirilə bilər" + +msgid "IP address recording can be disabled on the settings page" +msgstr "IP ünvanlarının qeyd edilməsi ayarlar səhifəsindən söndürülə bilər" + +msgid "From IP" +msgstr "IP-dən" + +#, python-format +msgid "Project %(name)s added" +msgstr "%(name)s layihəsi əlavə edildi" + +#, python-format +msgid "Bill %(name)s added" +msgstr "%(name)s hesabı əlavə edildi" + +#, python-format +msgid "Participant %(name)s added" +msgstr "İştirakçı %(name)s əlavə edildi" + +msgid "Project private code changed" +msgstr "Layihənin xüsusi kodu dəyişdirildi" + +#, python-format +msgid "Project renamed to %(new_project_name)s" +msgstr "Layihə %(new_project_name)s olaraq adlandırıldı" + +#, python-format +msgid "Project contact email changed to %(new_email)s" +msgstr "Layihə əlaqə e-poçtu %(new_email)s olaraq dəyişdirildi" + +msgid "Project settings modified" +msgstr "Layihə parametrləri dəyişdirildi" + +#, python-format +msgid "Participant %(name)s deactivated" +msgstr "İştirakçı %(name)s qeyri-aktiv edildi" + +#, python-format +msgid "Participant %(name)s reactivated" +msgstr "İştirakçı %(name)s yenidən aktiv edildi" + +#, python-format +msgid "Participant %(name)s renamed to %(new_name)s" +msgstr "İştirakçı %(name)s, %(new_name)s olaraq adlandırıldı" + +#, python-format +msgid "Bill %(name)s renamed to %(new_description)s" +msgstr "Hesab %(name)s, %(new_description)s olaraq adlandırıldı" + +#, python-format +msgid "Participant %(name)s: weight changed from %(old_weight)s to %(new_weight)s" +msgstr "" +"İştirakçı %(name)s: %(old_weight)s-dən %(new_weight)s-ə dəyişdirildi" + +msgid "Payer" +msgstr "Ödəyici" + +msgid "Amount" +msgstr "Məbləğ" + +msgid "Date" +msgstr "Tarix" + +#, python-format +msgid "Amount in %(currency)s" +msgstr "%(currency)s ilə məbləğ" + +#, python-format +msgid "Bill %(name)s modified" +msgstr "%(name)s hesabı dəyişdirildi" + +#, python-format +msgid "Participant %(name)s modified" +msgstr "%(name)s iştirakçısı dəyişdirildi" + +#, python-format +msgid "Bill %(name)s removed" +msgstr "%(name)s hesabı silindi" + +#, python-format +msgid "Participant %(name)s removed" +msgstr "%(name)s iştirakçısı silindi" + +#, python-format +msgid "Project %(name)s changed in an unknown way" +msgstr "%(name)s layihəsi naməlum bir şəkildə dəyişdirildi" + +#, python-format +msgid "Bill %(name)s changed in an unknown way" +msgstr "%(name)s hesabı naməlum bir şəkildə dəyişdirildi" + +#, python-format +msgid "Participant %(name)s changed in an unknown way" +msgstr "%(name)s iştirakçısı naməlum bir şəkildə dəyişdirildi" + +msgid "Nothing to list" +msgstr "Siyahıda heç nə yoxdur" + +msgid "Someone probably cleared the project history." +msgstr "Yəqin ki, kimsə layihə tarixçəsini təmizləmişdir." + +msgid "Manage your shared
expenses, easily" +msgstr "Paylaşılan xərclərinizi
asanlıqla idarə edin" + +msgid "Try out the demo" +msgstr "Demo versiyanı sınayın" + +msgid "You're sharing a house?" +msgstr "Bir evi paylaşmısınız?" + +msgid "Going on holidays with friends?" +msgstr "Dostlarınızla tətilə gedirsiniz?" + +msgid "Simply sharing money with others?" +msgstr "Sadəcə başqaları ilə pulmu paylaşırsınız?" + +msgid "We can help!" +msgstr "Biz kömək edə bilərik!" + +msgid "Log in to an existing project" +msgstr "Mövcud bir layihəyə daxil olun" + +msgid "Log in" +msgstr "Daxil ol" + +msgid "can't remember your password?" +msgstr "parolunuzu xatırlamırsınız?" + +msgid "Create" +msgstr "Yaradın" + +msgid "" +"Don\\'t reuse a personal password. Choose a private code and send it to " +"your friends" +msgstr "" +"Şəxsi parolu yenidən istifadə etməyin. Xüsusi bir kod seçin və onu dostlarınıza göndərin." + +msgid "Account manager" +msgstr "Hesab meneceri" + +msgid "Bills" +msgstr "Hesablar" + +msgid "Settle" +msgstr "Hesablaş" + +msgid "Statistics" +msgstr "Statistikalar" + +msgid "Languages" +msgstr "Dillər" + +msgid "Projects" +msgstr "Layihələr" + +msgid "Start a new project" +msgstr "Yeni bir layihəyə başlayın" + +msgid "History" +msgstr "Tarixçə" + +msgid "Settings" +msgstr "Ayarlar" + +msgid "RSS Feed" +msgstr "RSS Axını" + +msgid "Other projects :" +msgstr "Digər layihələr:" + +msgid "switch to" +msgstr "keçid et" + +msgid "Dashboard" +msgstr "İdarə Paneli" + +#, python-format +msgid "Please retry after %(date)s." +msgstr "Zəhmət olmasa, %(date)s tarixindən sonra yenidən yoxlayın." + +msgid "Code" +msgstr "Kod" + +msgid "Mobile Application" +msgstr "Mobil Tətbiq" + +msgid "Documentation" +msgstr "Sənədlər" + +msgid "Administration Dashboard" +msgstr "İdarəetmə Paneli" + +msgid "Legal information" +msgstr "Hüquqi məlumat" + +msgid "\"I hate money\" is free software" +msgstr "\"I hate money\" pulsuz proqramdır" + +msgid "you can contribute and improve it!" +msgstr "əlavə edə və təkmilləşdirə bilərsiniz!" + +#, python-format +msgid "%(amount)s each" +msgstr "Hər biri %(amount)s" + +msgid "you sure?" +msgstr "əminsiniz?" + +msgid "Invite people" +msgstr "İnsanları dəvət edin" + +msgid "Newer bills" +msgstr "Daha yeni hesablar" + +msgid "Older bills" +msgstr "Daha köhnə hesablar" + +msgid "You should start by adding participants" +msgstr "İştirakçıları əlavə etməklə başlamalısınız" + +msgid "Add a new bill" +msgstr "Yeni bir hesab əlavə et" + +msgid "For what?" +msgstr "Nəyə görə?" + +#, python-format +msgid "Added on %(date)s" +msgstr "%(date)s tarixində əlavə edildi" + +#, python-format +msgid "Everyone but %(excluded)s" +msgstr "%(excluded)s istisna olmaqla hər kəs" + +msgid "delete" +msgstr "sil" + +msgid "No bills" +msgstr "Hesab yoxdur" + +msgid "Nothing to list yet." +msgstr "Hələ siyahıya alınacaq heç nə yoxdur." + +msgid "Add your first bill" +msgstr "İlk hesabınızı əlavə edin" + +msgid "Add the first participant" +msgstr "İlk iştirakçını əlavə edin" + +msgid "Password reminder" +msgstr "Şifrə xatırladıcısı" + +msgid "" +"A link to reset your password has been sent to you, please check your " +"emails." +msgstr "" +"Parolunuzu sıfırlamaq üçün keçid sizə göndərildi, zəhmət olmasa " +"e-poçtlarınızı yoxlayın." + +msgid "Return to home page" +msgstr "Əsas səhifəyə qayıdın" + +msgid "Your projects" +msgstr "Layihələriniz" + +msgid "Reset your password" +msgstr "Parolunuzu yenidən qurun" + +msgid "Invite people to join this project" +msgstr "İnsanları bu layihəyə qoşulmağa dəvət edin" + +msgid "Share an invitation link" +msgstr "Dəvət bağlantısını paylaşın" + +msgid "" +"The easiest way to invite people is to give them the following invitation" +" link.
They will be able to access the project, manage participants," +" add/edit/delete bills. However, they will not have access to important " +"settings such as changing the private code or deleting the whole project." +msgstr "" +"İnsanları dəvət etməyin ən asan yolu onlara aşağıdakı dəvət bağlantısını " +"verməkdir.
Onlar layihəyə daxil ola, iştirakçıları idarə edə, hesabları " +"əlavə edə/redaktə edə/silə bilərlər. Ancaq xüsusi kodu dəyişmək və ya bütün " +"layihəni silmək kimi vacib parametrlərə daxil ola bilməyəcəklər." + +msgid "Scan QR code" +msgstr "QR kodunu skan edin" + +msgid "Use a mobile device with a compatible app." +msgstr "Uyğun bir tətbiqi olan mobil cihazdan istifadə edin." + +msgid "Send via Emails" +msgstr "E-poçt vasitəsilə göndərin" + +msgid "" +"Specify a list of email adresses (separated by comma) of people you want " +"to notify about the creation of this project. We will send them an email " +"with the invitation link." +msgstr "" +"Bu layihənin yaradılması haqqında məlumat vermək istədiyiniz insanların e-" +"poçt ünvanlarının siyahısını (vergüllə ayrılmış) qeyd edin. Biz onlara dəvət " +"keçidi ilə e-poçt göndərəcəyik." + +msgid "Share Identifier & code" +msgstr "Tanımlayıcı və Kodu Paylaşın" + +msgid "" +"You can share the project identifier and the private code by any " +"communication means.
Anyone with the private code will have access " +"to the full project, including changing settings such as the private code" +" or project email address, or even deleting the whole project." +msgstr "" +"Layihənin tanımlayıcısını və xüsusi kodunu hər hansı bir ünsiyyət vasitəsi " +"ilə paylaşa bilərsiniz.
Xüsusi kodu olan hər kəs xüsusi kod və ya layihə " +"e-poçt ünvanı kimi ayarları dəyişmək, hətta bütün layihəni silmək də daxil olmaqla " +"bütün layihəyə daxil ola bilər." + +msgid "Identifier:" +msgstr "Tanımlayıcı:" + +msgid "Private code:" +msgstr "Xüsusi kod:" + +msgid "the private code was defined when you created the project" +msgstr "xüsusi kod layihəni yaratdığınız zaman təyin edildi" + +msgid "Who pays?" +msgstr "Kim ödəyir?" + +msgid "To whom?" +msgstr "Kimə?" + +msgid "Who?" +msgstr "Kim?" + +msgid "Balance" +msgstr "Balans" + +msgid "deactivate" +msgstr "deaktiv et" + +msgid "reactivate" +msgstr "yenidən aktivləşdir" + +msgid "Paid" +msgstr "Ödənildi" + +msgid "Spent" +msgstr "Xərcləndi" + +msgid "Expenses by Month" +msgstr "Ay üzrə xərclər" + +msgid "Period" +msgstr "Dövür" + +#~ msgid "%(msg_compl)sThe project identifier is %(project)s" +#~ msgstr "" + +#~ msgid "each" +#~ msgstr "hər biri" + +#~ msgid "Error while sending reminder email" +#~ msgstr "Xatırlatma e-poçtu göndərilərkən səhv baş verdi" + +#~ msgid "" +#~ "This access code will be sent to" +#~ " your friends. It is stored as-" +#~ "is by the server, so don\\'t reuse" +#~ " a personal password!" +#~ msgstr "" +#~ "Bu giriş kodu dostlarınıza göndəriləcək." +#~ " Server tərəfindən olduğu kimi saxlanılır, buna görə də" +#~ " şəxsi bir şifrəni təkrarlamayın!" + +#~ msgid "Participant" +#~ msgstr "İştirakçı" + +#~ msgid "Bill" +#~ msgstr "Hesab" + +#~ msgid "Select all" +#~ msgstr "Hamısını seç" + +#~ msgid "Select none" +#~ msgstr "Heç birini seçmə" + +#~ msgid "changed" +#~ msgstr "dəyişdi" + +#~ msgid "from" +#~ msgstr "haradan" + +#~ msgid "to" +#~ msgstr "haraya" + +#~ msgid "Added" +#~ msgstr "Əlavə edildi" + +#~ msgid "Removed" +#~ msgstr "Silindi" + +#~ msgid "and" +#~ msgstr "və" + +#~ msgid "owers list" +#~ msgstr "borclular siyahısı" + +#~ msgid "added" +#~ msgstr "əlavə edildi" + +#~ msgid "Project renamed to" +#~ msgstr "Layihə adlandırıldı" + +#~ msgid "deactivated" +#~ msgstr "deaktivləşdirildi" + +#~ msgid "reactivated" +#~ msgstr "yenidən aktivləşdirildi" + +#~ msgid "renamed to" +#~ msgstr "adlandırıldı" + +#~ msgid "External link changed to" +#~ msgstr "Xarici bağlantı dəyişdirildi" + +#~ msgid "modified" +#~ msgstr "dəyişdirildi" + +#~ msgid "removed" +#~ msgstr "silindi" + +#~ msgid "You either provided a bad token or no project identifier." +#~ msgstr "Yaxşı bir işarə təqdim etmədiniz və ya layihə tanımlayıcısını göstərmədiniz." + +#~ msgid "User name incorrect" +#~ msgstr "İstifadəçi adı yanlışdır" + +#~ msgid "People to notify" +#~ msgstr "Bildiriləcək insanlar" + +#~ msgid "User '%(name)s' has been edited" +#~ msgstr "‘%(name)s’ istifadəçisi redaktə edildi" + +#~ msgid "Number of members" +#~ msgstr "Üzvlərin sayı" + +#~ msgid "Edit this member" +#~ msgstr "Bu üzvü redaktə et" + +#~ msgid "Participants to notify" +#~ msgstr "Bildiriləcək iştirakçılar" + +#~ msgid "Import" +#~ msgstr "İdxal et" + +#~ msgid "Amount paid" +#~ msgstr "Ödənilən məbləğ" + +#~ msgid "Bills can't be null" +#~ msgstr "Hesablar boş ola bilməz" + +#~ msgid "The project identifier is %(project)s" +#~ msgstr "Layihə tanımlayıcısı %(project)s" + +#~ msgid "Invalid JSON" +#~ msgstr "Yanlış JSON" + +#~ msgid "Are you sure?" +#~ msgstr "Əminsiniz?" + +#~ msgid "Import JSON" +#~ msgstr "JSON-u idxal et" + +#~ msgid "" +#~ "\n" +#~ " This project has history " +#~ "disabled. New actions won't appear " +#~ "below. You can enable history on " +#~ "the\n" +#~ " settings page\n" +#~ " " +#~ msgstr "" +#~ "\n" +#~ " Bu layihənin tarixçəsi " +#~ "dayandırılıb. Yeni hərəkətlər aşağıda " +#~ "görünməyəcək. Tarixçəni " +#~ "əvvəlcədən parametrlər " +#~ "səhifəsindən aktivləşdirə bilərsiniz.\n" +#~ " " + +#~ msgid "" +#~ "\n" +#~ " The table below reflects " +#~ "actions recorded prior to disabling " +#~ "project history. You can\n" +#~ " clear project history" +#~ " to remove them.

\n" +#~ " " +#~ msgstr "" +#~ "\n" +#~ " Aşağıdakı cədvəl " +#~ "layihənin tarixçəsi deaktiv edilməzdən əvvəl " +#~ "yazılmış hərəkətləri əks etdirir. Bunları " +#~ "silmək üçün\n" +#~ " layihə tarixçəsini " +#~ "təmizləyə bilərsiniz.

\n" +#~ " " + +#~ msgid "Send invites" +#~ msgstr "Dəvətləri göndərin" + +#~ msgid " show" +#~ msgstr "göstər" + +#~ msgid "Edit the project" +#~ msgstr "Layihəni redaktə et" + +#~ msgid "You probably want to" +#~ msgstr "Ehtimal ki, istəyirsiniz" + +#~ msgid "add participants" +#~ msgstr "iştirakçıları əlavə et" + +#~ msgid "" +#~ "You can share the project identifier " +#~ "and the private code by any " +#~ "communication means." +#~ msgstr "" +#~ "Layihə tanımlayıcısını və xüsusi kodu " +#~ "hər hansı bir ünsiyyət vasitəsilə " +#~ "paylaşa bilərsiniz." + +#~ msgid "Share the Link" +#~ msgstr "Bağlantını paylaş" + +#~ msgid "You can directly share the following link via your prefered medium" +#~ msgstr "" +#~ "Aşağıdakı bağlantıyı seçdiyiniz " +#~ "əlaqə vasitəsilə birbaşa paylaşa bilərsiniz" + From 794f26f76797ad16838da83597851aca89162cdc Mon Sep 17 00:00:00 2001 From: ferid333 <135500346+ferid333@users.noreply.github.com> Date: Thu, 12 Dec 2024 21:18:27 +0400 Subject: [PATCH 46/46] Update default_settings.py Co-Authored-By: qurbanov <10328930+qurbanov@users.noreply.github.com> --- ihatemoney/default_settings.py | 1 + 1 file changed, 1 insertion(+) diff --git a/ihatemoney/default_settings.py b/ihatemoney/default_settings.py index 64857378..cf0d5848 100644 --- a/ihatemoney/default_settings.py +++ b/ihatemoney/default_settings.py @@ -15,6 +15,7 @@ APPLICATION_ROOT = "/" ENABLE_CAPTCHA = False LEGAL_LINK = "" SUPPORTED_LANGUAGES = [ + "az", "ca", "cs", "de",