Skip to content

Fancier IPython-like eval command#3

Merged
gdude2002 merged 12 commits into
python-discord:masterfrom
Martmists-GH:patch-1
Feb 16, 2018
Merged

Fancier IPython-like eval command#3
gdude2002 merged 12 commits into
python-discord:masterfrom
Martmists-GH:patch-1

Conversation

@Martmists-GH
Copy link
Copy Markdown
Contributor

  • Supports Embeds
  • Pretty-print
  • Shortens if too long
  • Supports catching stdout
  • Supports async code
  • Automatically awaits awaitables if they are the return value
  • Some other misc changes

- Supports Embeds
- Pretty-prints
- Shortens
- Supports catching stdout
Copy link
Copy Markdown
Contributor

@gdude2002 gdude2002 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You've got a bunch of linting errors.

./bot/cogs/eval.py:12:1: F401 'discord.ext.commands.Context' imported but unused
./bot/cogs/eval.py:140:0: P101 format string does contain unindexed parameters
./bot/cogs/eval.py:143:1: B102 Use of exec detected.
./bot/cogs/eval.py:171:1: E303 too many blank lines (3)
./bot/cogs/eval.py:22:1: W293 blank line contains whitespace
./bot/cogs/eval.py:30:23: F821 undefined name 'io'
./bot/cogs/eval.py:33:1: W293 blank line contains whitespace
./bot/cogs/eval.py:4:1: F401 'io.StringIO' imported but unused
./bot/cogs/eval.py:5:1: I100 Import statements are in the wrong order. import inspect should be before from io
./bot/cogs/eval.py:65:23: F821 undefined name 'io'
./bot/cogs/eval.py:7:1: I100 Import statements are in the wrong order. import pprint should be before import textwrap
./bot/cogs/eval.py:9:1: I100 Import statements are in the wrong order. import re should be before import traceback

Comment thread .travis.yml
email:
on_success: never
on_failure: never No newline at end of file
on_failure: never
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This file is out of scope of the PR, please remove it.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't even know where that line came from, probably my auto-travis-lint?

Comment thread bot/cogs/eval.py Outdated
elif code.startswith("`") and code.endswith("`"):
code = code[1:-1]
# Indent the 3 dots correctly
s = (f"{{:<{len(str(self.ln))+2}}}...: ").format("")
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you comment this better? It's very unclear what this would do for a beginner

Comment thread bot/cogs/eval.py
_code = """
async def func():
try:
with contextlib.redirect_stdout(self.stdout):
Copy link
Copy Markdown
Contributor

@gdude2002 gdude2002 Feb 9, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Will doing this mess up printing stuff to stdout from the rest of the bot while the eval is being processed?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Contextlib should handle that. I've personally never had such issue.

Comment thread bot/cogs/eval.py Outdated
# far enough to align them.
# we first `str()` the line number
# then we get the length
# and do a simple {:<LENGHT}
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Typo! \o/

@gdude2002
Copy link
Copy Markdown
Contributor

This is from one of your other bots originally, right? What's the license on that bot?

@gdude2002
Copy link
Copy Markdown
Contributor

./bot/cogs/eval.py:57:18: W291 trailing whitespace
./bot/cogs/eval.py:58:30: W291 trailing whitespace
./bot/cogs/eval.py:6:1: I100 Import statements are in the wrong order. import pprint should be before from io
./bot/cogs/eval.py:61:18: W291 trailing whitespace

@gdude2002 gdude2002 self-assigned this Feb 9, 2018
@gdude2002 gdude2002 added the t: feature New feature or request label Feb 9, 2018
@Martmists-GH
Copy link
Copy Markdown
Contributor Author

The license on said bot makes contributors unable to share it without permission, and I'm giving permission by adding it myself.

I will fix those issues in a second.

@gdude2002
Copy link
Copy Markdown
Contributor

Alright, that's fine.

Really the only other thing I'd like to address in this PR is readability - there's lots of overly-short variable names, one-liners and somewhat opaque string concatenations.

We'd prefer if you could deal with that, but we can otherwise try to do it ourselves.

Copy link
Copy Markdown
Contributor

@lemonsaurus lemonsaurus left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The code is good, but readability is quite poor. I'd like to see the readability improved before we merge this. there are too many single-letter variable names, too many convoluted one-liners, too much nesting.. If we can get a version of this that follows the Zen of Python, I'd probably be willing to merge it.

Comment thread bot/cogs/eval.py Outdated
elif code.startswith("`") and code.endswith("`"):
code = code[1:-1]
# Indent the 3 dots correctly
s = (f"{{:<{len(str(self.ln))+2}}}...: ").format("")
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Poor readability.

Comment thread bot/cogs/eval.py Outdated
if len(lines) != 1:
lines += [""]

# Create the inpit dialog
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

inpit?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What?

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

should it say input?

Comment thread bot/cogs/eval.py Outdated
# Create the inpit dialog
for i, line in enumerate(lines):
if i == 0:
s = f"In [{self.ln}]: "
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

single letter variable names

Comment thread bot/cogs/eval.py Outdated
if line.startswith("return"):
line = line[6:].strip()

res += s + line + "\n"
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

convoluted string concatenation

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Using f-strings or str.format here would seem unneeded to me.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

if res and s had better variable names, it would probably be okay.

Copy link
Copy Markdown
Contributor

@lemonsaurus lemonsaurus left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

some more readability concerns.

Comment thread bot/cogs/eval.py Outdated
func = self.env['func']
res = await func()

except: # noqa pylint: disable=bare-except
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

would bare-except trigger if this was except Exception:? if not, isn't that better than disabling a pylint rule?

Comment thread bot/cogs/eval.py Outdated
if pretty.count("\n") > 20:
# Text too long, shorten
li = pretty.split("\n")
pretty = "\n".join(li[:3]) + "\n ...\n" + "\n".join(li[-3:])
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

too dense.

Comment thread bot/cogs/eval.py Outdated
inp = inp[4:]

code = string.strip()
lines = [l for l in inp.split("\n") if l.strip()]
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

for this to be beginner friendly, listcomps should have an accompanying comment. the meaning of the if l.strip() in this context may not be immediately obvious.

Comment thread bot/cogs/eval.py Outdated

self.interpreter = Interpreter(bot)

def _format(self, inp, out):
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this function needs a docstring so it will be obvious what exactly it's used for.

Comment thread bot/cogs/eval.py Outdated
if line.startswith("return"):
line = line[6:].strip()

res += s + line + "\n"
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

if res and s had better variable names, it would probably be okay.

Comment thread bot/cogs/eval.py Outdated
if len(lines) != 1:
lines += [""]

# Create the inpit dialog
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

should it say input?

Comment thread bot/cogs/eval.py

res += s + line + "\n"

self.stdout.seek(0)
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

maybe block comment this part to explain why you're doing it. generally speaking, the code could use many such comments explaining the flow of this method. Ideally we want people who are moderately new to python to be able to skim through this method and understand the flow without necessarily understanding all the code.

Comment thread bot/cogs/eval.py
if (isinstance(out, str) and
out.startswith("Traceback (most recent call last):\n")):
# Leave out the traceback message
out = "\n" + "\n".join(out.split("\n")[1:])
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

it's got string concatenation, a .split nested inside a .join, and a container slice, all in one line. it's too dense. it'd be better to split this into more lines if it can't be simplified.

Comment thread bot/cogs/eval.py Outdated
out = "\n" + "\n".join(out.split("\n")[1:])

pretty = (pprint.pformat(out, compact=True, width=60)
if not isinstance(out, str) else str(out))
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

readability suffers because of the ternary - instead of reading the logic in semantic order (if this then that), the reader has to parse it as (that if this). And why do we need to cast out to a str when the isinstance clearly establishes that it is already a str?

the far simpler

if not isinstance(out, str):
    pretty = pprint.pformat(out, compact=True, width=60)
else:
    pretty = out

would be better.

@lemonsaurus
Copy link
Copy Markdown
Contributor

for the record, I've left comments for absolutely all my readability concerns now. if they were all adressed, I'd approve.

@gdude2002
Copy link
Copy Markdown
Contributor

Has there been any movement on this?

@Martmists-GH
Copy link
Copy Markdown
Contributor Author

Not yet, it's been a busy week so far. I'll probably push a fix tomorrow

@Martmists-GH
Copy link
Copy Markdown
Contributor Author

@gdude2002 @1mn

@lemonsaurus
Copy link
Copy Markdown
Contributor

That's a lot better. Thanks!

@gdude2002
Copy link
Copy Markdown
Contributor

This is a considerable improvement. Good work.

@gdude2002 gdude2002 merged commit 47136cf into python-discord:master Feb 16, 2018
@Martmists-GH Martmists-GH deleted the patch-1 branch February 16, 2018 20:07
ChrisLovering pushed a commit that referenced this pull request Apr 30, 2021
Merge pull request #1028 from dolphingarlic/master
TizzySaurus added a commit that referenced this pull request Sep 25, 2021
This commit should be squashed upon PR merge.

- Another fix in `windows-path.md`
TizzySaurus added a commit that referenced this pull request Sep 25, 2021
This commit should be squashed upon PR merge.

- Another fix in `windows-path.md`
TizzySaurus added a commit that referenced this pull request Oct 14, 2021
This commit should be squashed upon PR merge.

- Another fix in `windows-path.md`
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

t: feature New feature or request

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants