Explicit parameter list in function documentation

Wow, that’s a great improvement. Real world examples really helps visualising potential improvement.

7 Likes

I agree wholeheartedly! We have type annotations for years already. Other ways of conveying types could be very confusing.

Could we consider to show the types without round brackets so the displayed form is more aligned with the real syntax?

These I would still show inside the round brackets (or marked some other way) to communicate that it is not a precise type. This way some complex types could be shown by an approximate type annotation without causing a confusion.

2 Likes

I have reservations, in the case of more complex types. Type annotations can be very verbose and unreadable when describing something like “optional async generator taking an int and returning strings”.

Readability should always be the priority here, and type annotations, while readable for simple cases, can hinder that in complex ones.

2 Likes

I don’t think anyone intends to create a super rigid format here; a pragmatic approach is almost always useful. Quoting Steve, earlier in this thread:

If type annotations in the docs can make things clear and easily understood, apply them. If they end up being too verbose, thus creating (more) confusion, don’t apply them. Readability counts.

We all strive towards the same goal: improving the docs.

7 Likes

Since I got quoted… yes, reusing the type annotation syntax where it makes things clearer is fine by me. We can argue about whether one is “too complex” on a case-by-case basis.

Worth keeping in mind that most of our standard library was built around the idea of functions “doing what I mean” rather than being designed for concrete types (as it may have been designed in another language). So we widely use anti-typing-patterns throughout the stdlib, and won’t be redesigning them to become type-first APIs. I expect a significant amount of cases where the “correct” annotation is too complex to be readable or helpful, so planning and explicitly allowing a fallback (since some authors will appreciate the explicit allowance) now will make things smoother.

This approach (parentheses for “not a machine-readable type annotation”) seems perfectly fine to me. Bonus points if we can also (easily) show it in a different font.

3 Likes

Indeed, as I’ve emphasized throughout. The main balance here is between making the guidance simple, unambiguous and consistent to apply, such that we don’t have to analyze and debate every individual case :smiley: and the end product is coherent and useful to readers, while allowing ample flexibility for the classes of cases where it doesn’t make sense and those that are otherwise special/exceptional in some way.

I also am not advocating these become hard requirements or anything for merging docs PRs, as opposed to a basis for guidance, suggestions and improvements.

I figure most have read this, but just to include the full quote to make clear that we’re all on the same page here (emphasis added, with a slight wording tweak to simplify):

4 Likes

Some updates: @erlendaasland merged python/cpython#94629 which added the explicit parameter list suggested above, with further refinements by Erlend, to the docs for sqlite3.connect, which is live now.

Also, I’ve opened an issue, python/cpython#94700, and a PR, python/cpython#94701, to do the same for the logging.Formatter class, following the preview above, with the intent to continue this work for the other sufficiently complex functions in the logging module reference in the near future.

Additionally, I plan to also bring this up at the Python Docs Community meeting, which we’d welcome anyone interested to join. Thanks!

7 Likes

Together with CAM, I’ve now applied parameter list improvements to the following sqlite3 functions and class methods:

  • sqlite3.connect
  • sqlite3.Connection.backup
  • sqlite3.Connection.blobopen
  • sqlite3.Connection.create_aggregate
  • sqlite3.Connection.create_function
  • sqlite3.Connection.create_window_function

I’m very pleased with the results[1]. As I see it, these improvements align with several[2] of Diátaxis’s reference guidelines:

  • be accurate: the parameter format makes it very easy to provide accurate information regarding parameter types, return values, and exceptions raised.
  • be consistent: the format is given, which also implies I need to think less about phrasing and wording, thus resulting in improved consistency in structure and language.
  • do nothing but describe: a result of the above; I find it a lot easier word myself consistent and to the point, avoiding digressions and discussions.

While adding these improvements, I’ve now noticed that several sqlite3 class methods lack information about their return values and exceptions raised! I’m tempted to apply this format all across the sqlite3 module docs in order to a) force myself to document all return values and raised exceptions, b) be consistent :wink:


  1. I also hope others are ↩︎

  2. 3 == several if you count as an orc: “one… two… many…” :japanese_ogre: ↩︎

7 Likes

Indeed—filling in implicit gaps in the reference information provided is a big motivation for this change, as this structure really helps doc writers find and clarify them, as well as avoid them in the first place. Especially as someone who’s likely experienced with whatever you’re writing about, when writing free-form prose its easy to leave implicit critical details that are obvious to oneself but not so much to a beginner reading about a function for the first time, whereas a consistent structure ensures we think about and add these key points every time.

3 Likes

If using a parameter list, I’d say always, because:

  • it improves consistency
  • it improves accuracy
  • it makes the reviewers and the writers jobs easier
3 Likes