Detect Types

Register a function to generate runtime window type definitions.

You will need to install an extension such as Tampermonkey, Greasemonkey or Violentmonkey to install this script.

You will need to install an extension such as Tampermonkey to install this script.

You will need to install an extension such as Tampermonkey or Violentmonkey to install this script.

You will need to install an extension such as Tampermonkey or Userscripts to install this script.

You will need to install an extension such as Tampermonkey to install this script.

You will need to install a user script manager extension to install this script.

(Tôi đã có Trình quản lý tập lệnh người dùng, hãy cài đặt nó!)

You will need to install an extension such as Stylus to install this style.

You will need to install an extension such as Stylus to install this style.

You will need to install an extension such as Stylus to install this style.

You will need to install a user style manager extension to install this style.

You will need to install a user style manager extension to install this style.

You will need to install a user style manager extension to install this style.

(I already have a user style manager, let me install it!)

// ==UserScript==
// @name            Detect Types
// @namespace       https://github.com/SlashNephy
// @version         0.1.0
// @author          SlashNephy
// @description     Register a function to generate runtime window type definitions.
// @description:ja  window の型定義を生成する関数を登録します。
// @homepage        https://scrapbox.io/slashnephy
// @homepageURL     https://scrapbox.io/slashnephy
// @icon            https://www.google.com/s2/favicons?sz=64&domain=*
// @supportURL      https://github.com/SlashNephy/userscripts/issues
// @match           https://*/*
// @grant           unsafeWindow
// @license         MIT license
// ==/UserScript==

(function () {
    'use strict';

    const escapeKey = (key) => {
        if (key.includes('.')) {
            return `'${key}'`;
        }
        return key;
    };
    const getTypeString = (value) => {
        if (value === null) {
            return 'null';
        }
        if (Array.isArray(value)) {
            if (value.length === 0) {
                return 'unknown[]';
            }
            const types = Array.from(new Set(value.map(getTypeString)));
            if (types.length > 1) {
                return `(${types.join(' | ')})[]`;
            }
            return `${types.at(0)}[]`;
        }
        switch (typeof value) {
            case 'object': {
                const entries = Object.entries(value);
                if (entries.length === 0) {
                    return 'Record<string, unknown>';
                }
                return `{${entries.map(([k, v]) => `${escapeKey(k)}: ${getTypeString(v)}`).join(', ')}}`;
            }
            case 'function':
                return 'Function';
            default:
                return typeof value;
        }
    };
    unsafeWindow.getTypeString = getTypeString;
    unsafeWindow.printTypeString = (value) => {
        console.log(getTypeString(value));
    };

})();