diff --git a/.github/dependabot.yml b/.github/dependabot.yml new file mode 100644 index 0000000..83dd982 --- /dev/null +++ b/.github/dependabot.yml @@ -0,0 +1,11 @@ +version: 2 +updates: + - package-ecosystem: "pip" + directory: "/" + schedule: + interval: "weekly" + + - package-ecosystem: "github-actions" + directory: "/" + schedule: + interval: "weekly" diff --git a/.github/workflows/on-push.yml b/.github/workflows/on-push.yml new file mode 100644 index 0000000..d41befe --- /dev/null +++ b/.github/workflows/on-push.yml @@ -0,0 +1,38 @@ +name: CI + +on: + pull_request: + branches: [ main ] + schedule: + - cron: '15 10 * * *' + +jobs: + build: + runs-on: ubuntu-latest + strategy: + matrix: + python-version: [3.8, 3.12.2] + steps: + - uses: actions/checkout@v4 + - name: Set up Python ${{ matrix.python-version }} with Robot Framework ${{ matrix.rf-version }} + uses: actions/setup-python@v5 + with: + python-version: ${{ matrix.python-version }} + - name: Install dependencies + run: | + pip install uv + uv pip install -r requirements-dev.txt --python ${{ matrix.python-version }} --system + uv pip install robotframework-seleniumlibrary --python ${{ matrix.python-version }} --system + - name: Lint files + run: | + inv lint + - name: Run unit tests + run: inv utest + - name: Run acceptance tests + run: | + inv atest + - uses: actions/upload-artifact@v4 + if: ${{ always() }} + with: + name: Test_results_${{ matrix.python-version }} + path: atest/output \ No newline at end of file diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml new file mode 100644 index 0000000..470bdd3 --- /dev/null +++ b/.github/workflows/release.yml @@ -0,0 +1,53 @@ +name: SemanticRelease + +on: + push: + branches: + - main + +jobs: + release: + runs-on: ubuntu-latest + concurrency: release + permissions: + id-token: write + contents: write + + steps: + - uses: actions/checkout@v4 + with: + fetch-depth: 0 + - name: Set up Python 3.12 with Robot Framework 7 + uses: actions/setup-python@v5 + with: + python-version: 3.12 + - name: Install dependencies + run: | + pip install uv + uv pip install -r requirements-dev.txt --python 3.23 --system + uv pip install robotframework-seleniumlibrary --python 3.23 --system + - name: Lint files + run: inv lint + - name: Run unit tests + run: | + inv utest + - name: Run acceptance tests + run: | + inv atest + - name: Python Semantic Release + id: release + uses: python-semantic-release/python-semantic-release@v9.7.2 + with: + github_token: ${{ secrets.GITHUB_TOKEN }} + - name: Build package + run: python -m build + if: steps.release.outputs.released == 'true' + - name: Publish package to PyPI + uses: pypa/gh-action-pypi-publish@release/v1 + if: steps.release.outputs.released == 'true' + - name: Publish package to GitHub Release + uses: python-semantic-release/upload-to-gh-release@main + if: steps.release.outputs.released == 'true' + with: + github_token: ${{ secrets.GITHUB_TOKEN }} + tag: ${{ steps.release.outputs.tag }} diff --git a/pyproject.toml b/pyproject.toml new file mode 100644 index 0000000..117141d --- /dev/null +++ b/pyproject.toml @@ -0,0 +1,126 @@ +[build-system] +requires = ["setuptools>=61.0"] +build-backend = "setuptools.build_meta" + +[project] +name = "robotframework-seleniumlibrary-translation-fi" +version = "0.0.1" +authors = [ + { name="Tatu Aalto", email="aalto.tatu@gmail.com" }, +] +license = {file = "LICENSE"} +description = "Robot Framework SeleniumLibrary translation to Finnish languege" +readme = "README.md" +requires-python = ">=3.8" +classifiers = [ + "Development Status :: 5 - Production/Stable", + "Framework :: Robot Framework :: Library", + "Topic :: Software Development :: Testing :: Acceptance", + "Programming Language :: Python :: 3", + "Programming Language :: Python :: 3.8", + "Programming Language :: Python :: 3.9", + "Programming Language :: Python :: 3.10", + "Programming Language :: Python :: 3.11", + "Programming Language :: Python :: 3.12", + "License :: OSI Approved :: Apache Software License", + "Operating System :: OS Independent", +] +keywords = ["Robot Framework", "SeleniumLibrary"] + +dependencies = ["robotframework-seleniumlibrary >= 6.4.0"] + +[project.urls] +Homepage = "https://github.com/MarketSquare/robotframework-seleniumlibrary-translation-fi" +Issues = "https://github.com/MarketSquare/robotframework-seleniumlibrary-translation-fi/issues" +Changelog = "https://github.com/MarketSquare/robotframework-seleniumlibrary-translation-fi/blob/main/CHANGELOG.md" + +[tool.setuptools] +packages = ["robotframework_seleniumlibrary_translation_fi"] + +[tool.setuptools.package-data] +robotframework_seleniumlibrary_translation_fi = ["*.json"] + +[tool.semantic_release] +version_toml = [ + "pyproject.toml:project.version", +] +version_variables = [ + "robotframework_seleniumlibrary_translation_fi/__init__.py:__version__", +] + +[tool.black] +target-version = ['py38'] +exclude = ''' +/( + \.eggs + | \.git + | \.mypy_cache + | \.venv + | _build + | buck-out + | build + | dist + | generated + | wrapper + | browser\.pyi +)/ +''' + +[tool.ruff] +lint.unfixable = [] +exclude = [ + "__pycache__", +] +target-version = "py38" +lint.select = [ + "E", + "F", + "W", + "C90", + "I", + "N", + "B", + "PYI", + "PL", + "PTH", + "UP", + "A", + "C4", + "DTZ", + "ISC", + "ICN", + "INP", + "PIE", + "T20", + "PYI", + "PT", + "RSE", + "RET", + "SIM", + "RUF" +] + +[tool.ruff.lint.per-file-ignores] +"tasks.py" = ["T201"] +"utest/*" = ["INP001"] +"atest/*" = ["INP001"] + +[tool.pytest.ini_options] +testpaths = ["utest"] +log_format = "%(asctime)s %(levelname)s %(message)s" +log_date_format = "%Y-%m-%d %H:%M:%S" + +[tool.robotidy] +lineseparator = "unix" +configure = [ + "NormalizeAssignments:equal_sign_type=space_and_equal_sign", + "NormalizeAssignments:equal_sign_type_variables=space_and_equal_sign", + "NormalizeNewLines:section_lines=1", + "RenameTestCases:enabled=True:capitalize_each_word=True", + "RenameKeywords:enabled=True", +] + +[tool.mypy] +exclude = [ + "utest/*", +] diff --git a/requirements-dev.txt b/requirements-dev.txt new file mode 100644 index 0000000..ea62ade --- /dev/null +++ b/requirements-dev.txt @@ -0,0 +1,10 @@ +black >= 24.1.1 +ruff >= 0.2.1 +invoke >= 2.2.0 +pytest >= 7.4.2 +approvaltests == 12.0.0 +robotframework-tidy >= 4.9.0 +python-semantic-release >= 9.3.1 +setuptools >= 61.0 +build >= 1.2.1 +mypy >= 1.9.0 diff --git a/tasks.py b/tasks.py new file mode 100644 index 0000000..73ba57e --- /dev/null +++ b/tasks.py @@ -0,0 +1,61 @@ +import os +import shutil +from pathlib import Path + +from invoke import task + +ROOT_FOLDER = Path(__file__).parent.absolute() +ATEST_OUTPUT = ROOT_FOLDER / "atest" / "output" +DIST_DIR = ROOT_FOLDER / "dist" +RUFF_CACHE = ROOT_FOLDER / ".ruff_cache" +PYTEST_CACHE = ROOT_FOLDER / ".pytest_cache" +MYPY_CACHE = ROOT_FOLDER / ".mypy_cache" +BUILD_DIR = ROOT_FOLDER / "build" + + +@task +def lint(ctx, fix=False): + in_ci = os.getenv("GITHUB_WORKFLOW") + print("Run mypy:") + ctx.run("mypy --exclude .venv .") + print("Run black:") + black_cmd = ["black", "."] + if in_ci: + black_cmd.insert(1, "--check") + ctx.run(" ".join(black_cmd)) + print("Run ruff:") + ruff_cmd = "ruff check " + if fix: + ruff_cmd = f"{ruff_cmd} --fix" + ctx.run(ruff_cmd) + print(f"Lint Robot files {'in ci' if in_ci else ''}") + cmd = ["robotidy", "atest"] + if in_ci: + cmd.insert(1, "--check") + cmd.insert(1, "--diff") + ctx.run(" ".join(cmd)) + + +@task +def utest(ctx): + ctx.run("python -m pytest .") + + +@task +def atest(ctx): + ctx.run("python -m robot -L debug --outputdir atest/output atest") + + +@task +def clean(ctx): + for target in [ + DIST_DIR, + ATEST_OUTPUT, + RUFF_CACHE, + PYTEST_CACHE, + MYPY_CACHE, + BUILD_DIR, + ]: + print(target) + if target.exists(): + shutil.rmtree(target)