diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index ed0123b..74aff2a 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -47,8 +47,7 @@ jobs: uses: jupyterlab/maintainer-tools/.github/actions/base-setup@v1 - name: Install the Python dependencies run: | - pip install -r requirements.txt - pip install pytest + pip install -r requirements-test.txt - name: Run the tests run: python -m pytest -vv -raXs || python -m pytest -vv -raXs --lf - name: Start the App diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index 15245f4..0fa8b58 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -12,16 +12,6 @@ repos: - id: forbid-new-submodules - id: trailing-whitespace -- repo: https://gitlab.com/pycqa/flake8 - rev: 3.8.4 - hooks: - - id: flake8 - additional_dependencies: [ - 'flake8-bugbear==20.1.4', - 'flake8-logging-format==0.6.0', - 'flake8-implicit-str-concat==0.2.0', - ] - - repo: https://github.com/psf/black rev: 22.1.0 hooks: @@ -35,6 +25,16 @@ repos: files: \.py$ args: [--profile=black] +- repo: https://gitlab.com/pycqa/flake8 + rev: 3.8.4 + hooks: + - id: flake8 + additional_dependencies: [ + 'flake8-bugbear==20.1.4', + 'flake8-logging-format==0.6.0', + 'flake8-implicit-str-concat==0.2.0', + ] + - repo: https://github.com/sirosen/check-jsonschema rev: 0.10.2 hooks: diff --git a/README.md b/README.md index ccb6fec..6b2a786 100644 --- a/README.md +++ b/README.md @@ -99,6 +99,8 @@ likely be killed. I haven't implemented a queue yet. If issued from a PR, will apply black to commits made in this PR and push the updated commits. +You can also use "blackify" as an alias. + Repo admins only, we plan to make it available to PR authors as well. MeeseeksDev Bot needs to be installed on the PR source repository for this to work. @@ -110,6 +112,8 @@ If issued from a PR, will apply pre-commit to this PR and push a commit with the changes made. If no changes are made, or the changes cannot be automatically fixed, it will show a comment in the PR and bail. +You can also use "precommit" as an alias. + Repo admins only, we plan to make it available to PR authors as well. MeeseeksDev Bot needs to be installed on the PR source repository for this to work. @@ -161,6 +165,11 @@ Issuer needs at least write permission. If Mergeable, Merge current PR using said methods (`merge` if no arguments) +## Command Extras + +You can be polite and use "please" with any of the commands, e.g. "@Meeseeksdev please close". + +You can optionally use the word "run" in the command, e.g. "@Meeseeksdev please run pre-commit". ## Simple extension. diff --git a/meeseeksdev/__init__.py b/meeseeksdev/__init__.py index 8540e91..60a80d7 100644 --- a/meeseeksdev/__init__.py +++ b/meeseeksdev/__init__.py @@ -161,6 +161,7 @@ def main(): "autopep8": blackify, "reformat": blackify, "black": blackify, + "blackify": blackify, "suggestions": black_suggest, "pre-commit": precommit, "precommit": precommit, diff --git a/meeseeksdev/meeseeksbox/commands.py b/meeseeksdev/meeseeksbox/commands.py index 5c52dc3..1108c46 100644 --- a/meeseeksdev/meeseeksbox/commands.py +++ b/meeseeksdev/meeseeksbox/commands.py @@ -339,6 +339,7 @@ def prep_for_command(name, session, payload, arguments, local_config=None): if target_session: print("installed on target repository") atk = target_session.token() + session.post_comment(comment_url, body=f"Running {name} on this Pull Request...") else: print("use allow edit as maintainer") atk = session.token() @@ -442,29 +443,39 @@ def precommit(*, session, payload, arguments, local_config=None): return # Add any changed files. - run('git commit -a -m "Apply pre-commit"') + process = run('git commit -a -m "Apply pre-commit"') + made_changes = process.returncode == 0 # Run again to see if we've auto-fixed process = run(cmd) - # If that fails, then we can't auto-fix + # Clean up the pre-commit files + run("pre-commit clean") + + # If second run fails, then we can't auto-fix if process.returncode != 0: - # Clean up the pre-commit files - run("pre-commit clean") - # Alert the caller and bail. + if not made_changes: + # Alert the caller and bail. + session.post_comment( + comment_url, + body=dedent( + """ + I was unable to fix pre-commit errors automatically. + Try running `pre-commit run --all-files` locally. + """ + ), + ) + return + session.post_comment( comment_url, body=dedent( """ - I was unable to run "pre-commit" due to an error, changes must be made manually. - """ + I was unable to fix all of the pre-commit errors automatically. Try running `pre-commit run --all-files` locally. + """ ), ) - return - - # Clean up the pre-commit files - run("pre-commit run clean") push_the_work(session, payload, arguments, local_config=local_config) diff --git a/meeseeksdev/meeseeksbox/core.py b/meeseeksdev/meeseeksbox/core.py index b7fef62..cc2e56b 100644 --- a/meeseeksdev/meeseeksbox/core.py +++ b/meeseeksdev/meeseeksbox/core.py @@ -71,11 +71,12 @@ def get(self): self.finish("No") -def _strip_please(c): +def _strip_extras(c): if c.startswith("please "): - return c[6:].lstrip() - else: - return c + c = c[6:].lstrip() + if c.startswith("run "): + c = c[4:].lstrip() + return c def process_mentionning_comment(body, bot_re): @@ -99,7 +100,7 @@ def process_mentionning_comment(body, bot_re): else: nl.append(bot_re.split(l)[-1].strip()) - command_args = [_strip_please(l).split(" ", 1) for l in nl] + command_args = [_strip_extras(l).split(" ", 1) for l in nl] command_args = [c if len(c) > 1 else [c[0], None] for c in command_args] return command_args @@ -112,7 +113,7 @@ def initialize(self, actions, config, auth, *args, **kwargs): super().initialize(*args, **kwargs) def get(self): - self.getfinish("Webhook alive and listening") + self.finish("Webhook alive and listening") def post(self): if self.config.forward_staging_url: diff --git a/meeseeksdev/tests/test_misc.py b/meeseeksdev/tests/test_misc.py index 925caf3..bc6c7f6 100644 --- a/meeseeksdev/tests/test_misc.py +++ b/meeseeksdev/tests/test_misc.py @@ -15,11 +15,19 @@ def test1(): @meeseeksdev nothing @meeseeksdev[bot] do nothing meeseeksdev[bot] do something + @meeseeksdev please nothing + @meeseeksdev run something """ ), reg, ) - == [["nothing", None], ["do", "nothing"], ["do", "something"]] + == [ + ["nothing", None], + ["do", "nothing"], + ["do", "something"], + ["nothing", None], + ["something", None], + ] ) diff --git a/meeseeksdev/tests/test_webhook.py b/meeseeksdev/tests/test_webhook.py new file mode 100644 index 0000000..29edab3 --- /dev/null +++ b/meeseeksdev/tests/test_webhook.py @@ -0,0 +1,55 @@ +import hmac + +import pytest +import tornado.web + +from ..meeseeksbox.core import Authenticator, Config, WebHookHandler + +commands = {} + +config = Config( + integration_id=100, + key=None, + personal_account_token="foo", + personal_account_name="bar", + forward_staging_url="", + webhook_secret="foo", +) + +auth = Authenticator( + config.integration_id, config.key, config.personal_account_token, config.personal_account_name +) + +application = tornado.web.Application( + [ + ( + r"/", + WebHookHandler, + { + "actions": commands, + "config": config, + "auth": auth, + }, + ), + ] +) + + +@pytest.fixture +def app(): + return application + + +async def test_get(http_server_client): + response = await http_server_client.fetch("/") + assert response.code == 200 + + +async def test_post(http_server_client): + body = "{}" + secret = config.webhook_secret + assert secret is not None + sig = "sha1=" + hmac.new(secret.encode("utf8"), body.encode("utf8"), "sha1").hexdigest() + headers = {"X-Hub-Signature": sig} + response = await http_server_client.fetch("/", method="POST", body=body, headers=headers) + assert response.code == 200 diff --git a/requirements-test.txt b/requirements-test.txt new file mode 100644 index 0000000..f410c11 --- /dev/null +++ b/requirements-test.txt @@ -0,0 +1,3 @@ +-r ./requirements.txt +pytest>=6.0 +pytest-tornasync