Note: After saving, you have to bypass your browser's cache to see the changes. Google Chrome, Firefox, Microsoft Edge and Safari: Hold down the ⇧ Shift key and click the Reload toolbar button. For details and instructions about other browsers, see Wikipedia:Bypass your cache.
/*
  <section begin=status/>Experimental<section end=status/>
  <section begin=last_update/>June 7, 2019<section end=last_update/>
  <section begin=version/>1.0<section end=version/>
*/
$(function() {
  var count = {
    striked: 0,
    processed: 0
  };

  function strikeMainFunction() {
    count.striked = 0;
    count.processed = 0;
    let users = [];
    $("a").each(function() {
      /* get usernames from the current page */
      let link_regex = /\/(w|wiki)\/(User:[^&\/\\]+|index\.php\?title=User:[^&\/\\]+&action=edit&redlink=1)[^\/\\]*$/i;
      if (link_regex.test($(this).attr("href"))) {
        $(this).attr("strikeable-username", $(this).text());
        users.push($(this).text());
      }
    });

    let uniqueUsers = [...new Set(users)];
    /* filter out IPs */
    uniqueUsers = uniqueUsers.filter(username => {
      /* regex from StackOverflow: https://stackoverflow.com/questions/4460586/javascript-regular-expression-to-check-for-ip-addresses */
      return !/^(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)$/.test(username);
    });

    var splitted_users = [];
    while (uniqueUsers.length > 0) {
      splitted_users.push(uniqueUsers.splice(0, 50));
      /* split by 50 because it is the max limit for normal users (https://en.wikipedia.org/w/api.php?action=help&modules=query%2Busers) */
    }

    if (splitted_users.length >= 2) {
      /* if there are more than 50 usernames, show a confirmation message */
      let count = 0;
      splitted_users.forEach(chunk => {
        count += chunk.length;
      });
      if (!confirm(`There are ${count} userlinks on this page. The script will have to make ${splitted_users.length} different API requests; continue?`)) {
        console.log("strikeBlocked: cancelled.");
        return;
      }
    }
    var requests = [];

    splitted_users.forEach((chunk, i) => {
      requests.push(requestUserInfo(chunk));
    });
    $.when.apply($, requests).done(function() {
      $.each(arguments, function(i, data) {
        var last_request = false;
        if ((i + 1) == arguments.length) last_request = true;

        if (Array.isArray(data)) {
          strikeUsers(data[0], last_request);
        } else {
          last_request = true;
          if (typeof data.query !== "undefined") {
            /* "when.apply" acts weird when only one request is made */
            strikeUsers(data, last_request);
          }
        }
      });

    });
  }

  function requestUserInfo(users) {
    return $.get("/w/api.php?action=query&list=users&usprop=blockinfo&format=json&ususers=" + users.join("|"));
  }

  function strikeUsers(response, last_request) {
    let users = response.query.users;
    count.processed += users.length;
    users = users.filter(e => {
      return typeof e.blockid !== "undefined";
    });
    users.forEach(user => {
      count.striked++;
      $("a[strikeable-username='" + user.name + "']").css("text-decoration", "line-through");
    });
    if (last_request) {
      if (count.striked > 0) {
        mw.notify('Processed ' + count.processed + ' users on this page; striked ' + count.striked + ' blocked user(s).');
      } else {
        mw.notify('Processed ' + count.processed + ' users on this page; no blocked user found.');
      }
    }
  }
  mw.util.addPortletLink("p-cactions", "#", "Strike blocked users", "strike_blocked");
  $("#strike_blocked").click(function(ev) {
    ev.preventDefault();
    strikeMainFunction();
  });
});