I’m a big fan of good documentation. I have always enjoyed reading extensive, well-written and engaging readmes, manuals and other forms of docs. Which is why, over the years, I have come to produce quite a bit of (technical) documentation myself.
Considering code, I absolutely prefer (both writing and reading) scoped documentation such as file-level comments, class or function documentation, or annotations for constants and fields. What I don’t like to see a lot of is inline comments, especially if they are telling me in plain English what the code directly below actually does.
Don’t get me wrong! For more complex or exotic pieces of logic, it may be super helpful to provide more context. The right way to do that is to abstract the logic to a dedicated place like a (private) function, and then add as much documentation as necessary. There is no good reason to have a long multi-line comment in between larger blocks of code, in my opinion.
And when there are inline comments, I’d much rather learn about the Why, and not about the What. Using clear and meaningful names for variables, constants, functions and classes, and applying principles to split up and organise your codebase into individual logical pieces, there shouldn’t be a need for massive inline docs.
So, here goes the most elaborate comment I may ever have written, and am thinking of every now and then:
/**
* DISCLAIMER: Yes, this is ugly. Don't tell me about it. :(
*
* The following code hides the row in the "Status & visibility" panel that includes the "Pending review" checkbox.
*
* The reason for this being that the Publishing Workflow plugin is using the "pending" status as well, but will break
* if the status gets updated via the checkbox. This is because the plugin disallows editing pending posts.
*
* Ideally, the "Pending review" checkbox should not be visible. But sadly, this is not possible for various reasons.
* The component is hard-coded in the "Status & visibility" panel in the Document sidebar. While there is a check to
* determine whether the component should get rendered, this is not really checking the context of the post. Instead, it
* only checks if the current post has the `wp:action-publish` rel set, that is, if the current user is allowed to
* publish the post. I first tried to remove the link from the REST API response, which resulted in the checkbox no
* longer being rendered. However, the same link is being used for various other components, and so removing the link
* had several unintended side effects. And really, we don't want to mess with the REST API response, we want to hide
* the checkbox.
*
* Accepting that the control cannot be hidden programmatically, I then thought about updating the Publishing Workflow
* plugin to stop it from breaking. I first tried to allow editing a pending post for the post author. But since the
* checkbox is not only visible to the author, this still breaks for anyone else.
*
* Then I tried to allow editing a pending post if no approver has been assigned yet. While this works fine for the
* first time, it'll break for any subsequent change to the post. This is because the previous approver is stored in a
* dedicated post meta field, and will not be removed (for tracking purposes). Without introducing yet another piece of
* data, it's not possible to differentiate a post has been submitted for review from one that once was submitted, then
* got reviewed, changed a second time, and the checkbox ticked.
*
* In the end, all I could do was to retroactively hide the panel row with the checkbox, every time it gets re-rendered.
* This is only possible by targeting the sidebar and looking for a label that contains the (translated!) string
* "Pending review". If found, climb up to the panel row component, and hide it.
*
* Since the component will get re-rendered if the panel re-renders, the above process needs to happen in a subscriber.
* In order to not cause any performance penalty, there are various checks in place that bail as early as possible, and
* only search and manipulate the DOM if necessary.
*
* Sorry,
* Thorsten
*/
import { select, subscribe } from '@wordpress/data';
import { __ } from '@wordpress/i18n';
const { jQuery } = window;
const { getActiveGeneralSidebarName, isEditorPanelOpened } = select( 'core/edit-post' );
const LABEL_TEXT = __( 'Pending review' );
const PANEL_NAME = 'post-status';
const SIDEBAR_NAME = 'edit-post/document';
let isHidden = false;
subscribe( () => {
if (
getActiveGeneralSidebarName() !== SIDEBAR_NAME
|| ! isEditorPanelOpened( PANEL_NAME )
) {
isHidden = false;
return;
}
if ( isHidden ) {
return;
}
const label = jQuery( `.edit-post-post-status label:contains('${ LABEL_TEXT }')` );
if ( ! label.length ) {
return;
}
label.closest( '.components-panel__row' ).hide();
isHidden = true;
} );
And just in case you are wondering, comparing the number of characters, the ratio of code and comment is 1:3.5. 😆
Leave a Reply