Page MenuHomePhabricator

Inconsistent placement between classes/modules/namespaces
Open, HighPublic

Description

  • Under "Namespaces" we see mw.util, which points to mediawiki.util under "Modules".
  • Under "Modules" we see mediawiki.ForeignApi, which points to mw.ForeignApi under "Classes".
  • Things related to mediawiki.storage are scattered on three pages in three different sections: mediawiki.storage under "Modules", mw under "Namespaces", and mediawiki.storage~SafeStorage under "Classes".
  • mediawiki.inspect is in "Classes" even though it's not a class.
  • Some jQuery plugins are under the namespace jQueryPlugins, others are under modules. (Work in progress as part of T353357: Document jQuery plugins as modules)

All this is confusing and reader-hostile.

The vast, vast majority of developers are going to use the global mw.util (you can find lots of such uses even in core) so that's where one expects to find the documentation.

The ResourceLoader module mediawiki.ForeignApi doesn't even export anything so one wonders why this is in "Modules" at all.

No one uses mw.storage.local.

Overall, if something is accessible via both require('mediawiki.foo') and global mw.foo, it should be documented only at the latter.

Event Timeline

apaskulin moved this task from Backlog to Migration of core docs on the JSDoc WMF theme board.
apaskulin subscribed.

Thanks for opening this, @Nardog!

There is not per-se a way to settle this, as this task may be conflating two things that actually exist.

The namespace that our classes and functions exist under is called mw. There exists no variable called mediawiki. There is only mw. Our public functions are mw.now(), mw.msg(), etc, an example of a class is mw.Title, a singleton is mw.util, and mw.storage. The dot here is referring to how inside the JavaScript runtime, you can execute property access. mw exists and has a property called util which has a property called getUrl, which can be accessed as mw.util.getUrl.

Modules are typically named in our ecosystem with a dot in their name. For example, ext.visualEditor, mediawiki.base, mediawiki.util, mediawiki.storage. These can be loaded via ResourceLoader dependencies, or via mw.loader.using(). For the handful of modules that have public exports, these can be accessed via require( "name" ). In that case, we document those exports as a module. The dot here is part of the name. It is not something that exists in the JavaScript runtime.

In order to allow access via require(), some modules export and define the same API both ways. For example mw.util = { getUrl: function... }; module.exports = mw.util;. In that case, we can document one of them fully, and the other should probably just be a pointer to it for discovery.

The above describes what actually exists, and thus what we can choose to document.

As for that is actually documented, there are some issues indeed:

  1. If there are classes or singletons defined as mediawiki.. then that is cleary a bug, since no such variable exists. Code trying to use that experience an error immediately. It looks like mediawiki.storage might have been misnamed during an attempt to migrate its comments to JSDoc.
  2. For cases where an API is available both as a class/singleton, and as module, we need to decide whether and how we want to standardise that.

For the second point, I lean slightly toward standardising on class/singleton. This for a few reasons:

  1. It means we can increase adoption of module exports without breaking permalinks and cross-doc references.
  2. Especially for permalinks to individual methods e.g. for the latest/master branch of a codebase on doc.wikimedia.org.
  3. Simpler type documentation for returns and params. e.g. @param {mw.Title} seems preferred over one way @param {module:mediawiki.Title} which seems tedious and unlikely to be typed. This would also match loosely how TypeScript typically pretends to define all its types in a shared namespace, rather than bound to specific files or modules.
  4. Pointing to mw.Title when it is only a stub, would lead to subpar UX as you'd need to manually click-through to get to your destination.
  5. There is a tendency for modules to get renamed and consolidated/combined over time. This is easy to create runtime compat aliasees for, with logged deprecation. However, this would be very messy to try to document. E.g. imagine moving mw.Title to mediawiki.util. This would be trivial if mediawiki.Title was merely documented as exporting mw.Title.
Nardog renamed this task from Settle on `mw` vs `mediawiki` to Inconsistent placement between classes/modules/namespaces.May 30 2024, 9:13 AM
Nardog updated the task description. (Show Details)

I am also confused by module vs namespace vs class vs globals in the MW core JS docs.

At the moment my hypothesis based on reading some of Krinkle's posts and reading the readme.md files in docs.wikimedia.org is that modules are anything you can load in mw.loader.using(), and globals are global variables such as mw.*

If that's correct, then we are missing some modules such as mediawiki.Api and should probably do an audit to cross-reference all the available mw.loader.using() modules in core to what is on doc.wikimedia.org.

Is the folder list at the top level of https://gerrit.wikimedia.org/r/plugins/gitiles/mediawiki/core/+/refs/heads/master/resources/src/ basically the list of modules that you can load using mw.loader.using()?

I also noticed some stuff missing in globals -> mw -> mw.util, which has no methods (see https://doc.wikimedia.org/mediawiki-core/master/js/mw.util.html). I have attempted to fix that in https://gerrit.wikimedia.org/r/c/mediawiki/core/+/1040765. Reviewers welcome.

Change #1042383 had a related patch set uploaded (by Alex Paskulin; author: Alex Paskulin):

[mediawiki/core@master] docs: Remove classdesc tag from namespace

https://gerrit.wikimedia.org/r/1042383

Change #1042383 merged by jenkins-bot:

[mediawiki/core@master] docs: Remove classdesc tag from namespace

https://gerrit.wikimedia.org/r/1042383