tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

IssueItem.js (6100B)


      1 /* This Source Code Form is subject to the terms of the Mozilla Public
      2 * License, v. 2.0. If a copy of the MPL was not distributed with this
      3 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
      4 
      5 "use strict";
      6 
      7 const {
      8  createFactory,
      9  PureComponent,
     10 } = require("resource://devtools/client/shared/vendor/react.mjs");
     11 const dom = require("resource://devtools/client/shared/vendor/react-dom-factories.js");
     12 const PropTypes = require("resource://devtools/client/shared/vendor/react-prop-types.mjs");
     13 
     14 const FluentReact = require("resource://devtools/client/shared/vendor/fluent-react.js");
     15 const Localized = createFactory(FluentReact.Localized);
     16 
     17 loader.lazyRequireGetter(
     18  this,
     19  "openDocLink",
     20  "resource://devtools/client/shared/link.js",
     21  true
     22 );
     23 
     24 const UnsupportedBrowserList = createFactory(
     25  require("resource://devtools/client/inspector/compatibility/components/UnsupportedBrowserList.js")
     26 );
     27 
     28 const Types = require("resource://devtools/client/inspector/compatibility/types.js");
     29 
     30 const NodePane = createFactory(
     31  require("resource://devtools/client/inspector/compatibility/components/NodePane.js")
     32 );
     33 
     34 // For test
     35 loader.lazyRequireGetter(
     36  this,
     37  "toSnakeCase",
     38  "resource://devtools/client/inspector/compatibility/utils/cases.js",
     39  true
     40 );
     41 
     42 const { getMdnLinkParams } = ChromeUtils.importESModule(
     43  "resource://devtools/shared/mdn.mjs"
     44 );
     45 const MDN_LINK_PARAMS = getMdnLinkParams("inspector-compatibility");
     46 
     47 class IssueItem extends PureComponent {
     48  static get propTypes() {
     49    return {
     50      ...Types.issue,
     51      dispatch: PropTypes.func.isRequired,
     52      setSelectedNode: PropTypes.func.isRequired,
     53    };
     54  }
     55 
     56  constructor(props) {
     57    super(props);
     58    this._onLinkClicked = this._onLinkClicked.bind(this);
     59  }
     60 
     61  _onLinkClicked(e) {
     62    e.preventDefault();
     63    e.stopPropagation();
     64 
     65    const isMacOS = Services.appinfo.OS === "Darwin";
     66 
     67    openDocLink(e.target.href, {
     68      relatedToCurrent: true,
     69      inBackground: isMacOS ? e.metaKey : e.ctrlKey,
     70    });
     71  }
     72 
     73  _getTestDataAttributes() {
     74    const testDataSet = {};
     75 
     76    if (Services.prefs.getBoolPref("devtools.testing", false)) {
     77      for (const [key, value] of Object.entries(this.props)) {
     78        if (key === "nodes") {
     79          continue;
     80        }
     81        const datasetKey = `data-qa-${toSnakeCase(key)}`;
     82        testDataSet[datasetKey] = JSON.stringify(value);
     83      }
     84    }
     85 
     86    return testDataSet;
     87  }
     88 
     89  _renderAliases() {
     90    const { property } = this.props;
     91    let { aliases } = this.props;
     92 
     93    if (!aliases) {
     94      return null;
     95    }
     96 
     97    aliases = aliases.filter(alias => alias !== property);
     98 
     99    if (aliases.length === 0) {
    100      return null;
    101    }
    102 
    103    return dom.ul(
    104      {
    105        className: "compatibility-issue-item__aliases",
    106      },
    107      aliases.map(alias =>
    108        dom.li(
    109          {
    110            key: alias,
    111            className: "compatibility-issue-item__alias",
    112          },
    113          alias
    114        )
    115      )
    116    );
    117  }
    118 
    119  _renderCauses() {
    120    const { deprecated, experimental, prefixNeeded } = this.props;
    121 
    122    if (!deprecated && !experimental && !prefixNeeded) {
    123      return null;
    124    }
    125 
    126    let localizationId = "";
    127 
    128    if (deprecated && experimental && prefixNeeded) {
    129      localizationId =
    130        "compatibility-issue-deprecated-experimental-prefixneeded";
    131    } else if (deprecated && experimental) {
    132      localizationId = "compatibility-issue-deprecated-experimental";
    133    } else if (deprecated && prefixNeeded) {
    134      localizationId = "compatibility-issue-deprecated-prefixneeded";
    135    } else if (experimental && prefixNeeded) {
    136      localizationId = "compatibility-issue-experimental-prefixneeded";
    137    } else if (deprecated) {
    138      localizationId = "compatibility-issue-deprecated";
    139    } else if (experimental) {
    140      localizationId = "compatibility-issue-experimental";
    141    } else if (prefixNeeded) {
    142      localizationId = "compatibility-issue-prefixneeded";
    143    }
    144 
    145    return Localized(
    146      {
    147        id: localizationId,
    148      },
    149      dom.span(
    150        { className: "compatibility-issue-item__causes" },
    151        localizationId
    152      )
    153    );
    154  }
    155 
    156  _renderPropertyEl() {
    157    const { property, url, specUrl } = this.props;
    158    const baseCls = "compatibility-issue-item__property devtools-monospace";
    159    if (!url && !specUrl) {
    160      return dom.span({ className: baseCls }, property);
    161    }
    162 
    163    const href = url ? `${url}?${MDN_LINK_PARAMS}` : specUrl;
    164 
    165    return dom.a(
    166      {
    167        className: `${baseCls} ${
    168          url
    169            ? "compatibility-issue-item__mdn-link"
    170            : "compatibility-issue-item__spec-link"
    171        }`,
    172        href,
    173        title: href,
    174        onClick: e => this._onLinkClicked(e),
    175      },
    176      property
    177    );
    178  }
    179 
    180  _renderDescription() {
    181    return dom.div(
    182      {
    183        className: "compatibility-issue-item__description",
    184      },
    185      this._renderPropertyEl(),
    186      this._renderCauses(),
    187      this._renderUnsupportedBrowserList()
    188    );
    189  }
    190 
    191  _renderNodeList() {
    192    const { dispatch, nodes, setSelectedNode } = this.props;
    193 
    194    if (!nodes) {
    195      return null;
    196    }
    197 
    198    return NodePane({
    199      dispatch,
    200      nodes,
    201      setSelectedNode,
    202    });
    203  }
    204 
    205  _renderUnsupportedBrowserList() {
    206    const { unsupportedBrowsers } = this.props;
    207 
    208    return unsupportedBrowsers.length
    209      ? UnsupportedBrowserList({ browsers: unsupportedBrowsers })
    210      : null;
    211  }
    212 
    213  render() {
    214    const { deprecated, experimental, property, unsupportedBrowsers } =
    215      this.props;
    216 
    217    const classes = ["compatibility-issue-item"];
    218 
    219    if (deprecated) {
    220      classes.push("compatibility-issue-item--deprecated");
    221    }
    222 
    223    if (experimental) {
    224      classes.push("compatibility-issue-item--experimental");
    225    }
    226 
    227    if (unsupportedBrowsers.length) {
    228      classes.push("compatibility-issue-item--unsupported");
    229    }
    230 
    231    return dom.li(
    232      {
    233        className: classes.join(" "),
    234        key: property,
    235        ...this._getTestDataAttributes(),
    236      },
    237      this._renderDescription(),
    238      this._renderAliases(),
    239      this._renderNodeList()
    240    );
    241  }
    242 }
    243 
    244 module.exports = IssueItem;