690

今天早上有一篇帖子询问有多少人禁用了 JavaScript。然后我开始想知道可以使用哪些技术来确定用户是否禁用了它。

有谁知道一些简短/简单的方法来检测 JavaScript 是否被禁用?我的意图是发出警告,如果没有启用 JS 的浏览器,该站点将无法正常运行。

最终我想将它们重定向到能够在没有 JS 的情况下工作的内容,但我需要这个检测作为一个占位符才能开始。

4

39 回答 39

379

我想在这里添加我的 .02。它不是 100% 防弹的,但我认为它已经足够好了。

对我来说,问题是,最好使用放置某种“如果没有 Javascript,此站点无法正常运行”消息的示例,您需要确保您的站点在没有 Javascript 的情况下可以正常运行。一旦你开始了这条路,你就会开始意识到网站应该在关闭 JS 的情况下是防弹的,这是一大块额外的工作。

所以,你真正想要的是一个“重定向”到一个页面,上面写着“打开 JS,傻”。但是,当然,您不能可靠地进行元重定向。所以,这里的建议是:

<noscript>
    <style type="text/css">
        .pagecontainer {display:none;}
    </style>
    <div class="noscriptmsg">
    You don't have javascript enabled.  Good luck with that.
    </div>
</noscript>

...您网站中的所有内容都用“pagecontainer”类的 div 包装。noscript 标记内的 CSS 将隐藏您的所有页面内容,而是显示您想要显示的任何“无 JS”消息。这实际上是 Gmail 似乎要做的……如果它对 Google 来说足够好,那么对于我的小网站来说也足够好了。

于 2010-10-13T18:24:20.763 回答
299

我假设您正在尝试决定是否提供 JavaScript 增强的内容。最好的实现完全降级,这样网站仍然可以在没有 JavaScript 的情况下运行。我还假设您的意思是服务器端检测,而不是<noscript>出于无法解释的原因使用该元素。

没有执行服务器端 JavaScript 检测的好方法。作为替代方案,可以使用 JavaScript 设置 cookie,然后在后续页面查看时使用服务器端脚本测试该 cookie。但是,这不适合决定要交付什么内容,因为它无法区分没有 cookie 的访问者与新访问者或不接受 JavaScript 设置 cookie 的访问者。

于 2008-09-23T14:16:38.053 回答
204

noscript块在禁用 JavaScript 时执行,通常用于显示您在 JavaScript 中生成的替代内容,例如

<script type="javascript">
    ... construction of ajaxy-link,  setting of "js-enabled" cookie flag, etc..
</script>
<noscript>
    <a href="next_page.php?nojs=1">Next Page</a>
</noscript>

没有 js 的用户将获得next_page链接 - 您可以在此处添加参数,以便在下一页上知道他们是通过 JS/非 JS 链接来的,还是尝试通过 JS 设置 cookie,没有这意味着 JS被禁用。这两个例子都相当琐碎并且容易被操纵,但你明白了。

如果您想了解有多少用户禁用了 javascript,您可以执行以下操作:

<noscript>
    <img src="no_js.gif" alt="Javascript not enabled" />
</noscript>

然后检查您的访问日志以查看该图像被点击了多少次。一个稍微粗略的解决方案,但它会为您的用户群提供一个好主意。

上述方法(图像跟踪)不适用于纯文本浏览器或根本不支持 js 的浏览器,因此如果您的用户群主要转向该区域,这可能不是最佳方法。

于 2008-09-23T14:08:33.797 回答
47

这对我有用:如果禁用 javascript,它会重定向访问者

<noscript><meta http-equiv="refresh" content="0; url=whatyouwant.html" /></noscript>
于 2009-03-04T01:07:33.103 回答
46

我建议您通过编写不显眼的 JavaScript 来反其道而行之。

让您的项目功能适用于禁用 JavaScript 的用户,完成后,实施 JavaScript UI 增强功能。

https://en.wikipedia.org/wiki/Unobtrusive_JavaScript

于 2008-09-23T14:12:54.520 回答
44

如果您的用例是您有一个表单(例如,一个登录表单)并且您的服务器端脚本需要知道用户是否启用了 JavaScript,您可以执行以下操作:

<form onsubmit="this.js_enabled.value=1;return true;">
    <input type="hidden" name="js_enabled" value="0">
    <input type="submit" value="go">
</form>

这将在提交表单之前将 js_enabled 的值更改为 1。如果您的服务器端脚本得到 0,则没有 JS。如果它得到一个 1,JS!

于 2008-09-24T07:06:05.193 回答
39

<noscript>甚至没有必要,更不用说XHTML 不支持

工作示例

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Frameset//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-frameset.dtd">
<html>
<head>
    <title>My website</title>
    <style>
      #site {
          display: none;
      }
    </style>
    <script src="http://code.jquery.com/jquery-latest.min.js "></script>
    <script>
      $(document).ready(function() {
          $("#noJS").hide();
          $("#site").show();
      });
    </script>
</head>
<body>
    <div id="noJS">Please enable JavaScript...</div>
    <div id="site">JavaScript dependent content here...</div>
</body>
</html>

在此示例中,如果启用了 JavaScript,则您会看到该站点。如果没有,那么您会看到“请启用 JavaScript”消息。测试 JavaScript 是否启用的最佳方法是简单地尝试使用 JavaScript!如果有效,则已启用,如果无效,则不是...

于 2014-02-07T06:08:55.370 回答
37

在 body 上使用 .no-js 类并基于 .no-js 父类创建非 javascript 样式。如果禁用了 javascript,您将获得所有非 javascript 样式,如果有 JS 支持,则 .no-js 类将被替换,为您提供所有样式。

 document.body.className = document.body.className.replace("no-js","js");

通过modernizr在HTML5样板http://html5boilerplate.com/中使用的技巧,但你可以使用一行javascript来替换类

noscript 标签是可以的,但是当它可以用 css 完成时,为什么在你的 html 中有额外的东西

于 2012-04-25T15:05:36.497 回答
15

只是有点难,但是(hairbo 给了我这个想法)

CSS:

.pagecontainer {
  display: none;
}

JS:

function load() {
  document.getElementById('noscriptmsg').style.display = "none";
  document.getElementById('load').style.display = "block";
  /* rest of js*/
}

HTML:

<body onload="load();">

  <div class="pagecontainer" id="load">
    Page loading....
  </div>
  <div id="noscriptmsg">
    You don't have javascript enabled. Good luck with that.
  </div>

</body>

在任何情况下都可以工作吗?即使不支持 noscript 标签(只需要一些 css),任何人都知道非 css 解决方案吗?

于 2010-12-08T23:36:06.053 回答
13

您可以使用一个简单的 JS 片段来设置隐藏字段的值。回帖时,您知道 JS 是否已启用。

或者您可以尝试打开一个快速关闭的弹出窗口(但它可能是可见的)。

此外,您还有 NOSCRIPT 标记,可用于为禁用 JS 的浏览器显示文本。

于 2008-09-23T14:08:28.633 回答
13

你会想看看 noscript 标签。

<script type="text/javascript">
...some javascript script to insert data...
</script>
<noscript>
   <p>Access the <a href="http://someplace.com/data">data.</a></p>
</noscript>
于 2008-09-23T14:10:11.313 回答
13

因为我总是想给浏览器一些值得一看的东西,所以我经常使用这个技巧:

首先,页面的任何需要 JavaScript 才能正常运行的部分(包括通过 getElementById 调用等修改的被动 HTML 元素)都被设计为可以按原样使用,前提是没有可用的 JavaScript。(设计得好像它不存在)

任何需要 JavaScript 的元素,我都放在一个标签中,例如:

<span name="jsOnly" style="display: none;"></span>

然后在我的文档的开头,我使用.onloaddocument.ready在一个循环中getElementsByName('jsOnly')设置.style.display = "";重新打开 JS 相关元素。这样,非 JS 浏览器就不必查看站点的 JS 相关部分,如果有,它会在准备好时立即显示。

一旦你习惯了这种方法,就很容易混合你的代码来处理这两种情况,尽管我现在只是在试验这个noscript标签,并期望它会有一些额外的优势。

于 2010-07-16T13:53:02.620 回答
12

noscript 标签运行良好,但需要每个额外的页面请求才能继续提供无用的 JS 文件,因为 noscript 本质上是客户端检查。

您可以使用 JS 设置 cookie,但正如其他人指出的那样,这可能会失败。理想情况下,您希望能够检测 JS 客户端,并且在不使用 cookie 的情况下,为该用户设置一个会话服务器端,表明 JS 已启用。

一种可能性是使用 JavaScript 动态添加 1x1 图像,其中 src 属性实际上是服务器端脚本。这个脚本所做的只是保存到启用 JS 的当前用户会话($_SESSION['js_enabled'])。然后,您可以将 1x1 空白图像输出回浏览器。该脚本不会为禁用 JS 的用户运行,因此不会设置 $_SESSION['js_enabled']。然后对于提供给该用户的其他页面,您可以决定是否包含所有外部 JS 文件,但您总是希望包含检查,因为您的某些用户可能正在使用 NoScript Firefox 插件或拥有 JS由于其他原因暂时禁用。

您可能希望在页面末尾附近的某处包含此检查,以便额外的 HTTP 请求不会减慢页面的呈现速度。

于 2008-09-27T06:53:18.153 回答
12

将此添加到每个页面的 HEAD 标记中。

<noscript>
        <meta http-equiv="refresh" runat="server" id="mtaJSCheck" content="0;logon.aspx" />
</noscript>

所以你有了:

<head>
    <noscript>
        <meta http-equiv="refresh" runat="server" id="mtaJSCheck" content="0;logon.aspx" />
    </noscript>
</head>

感谢杰。

于 2011-04-01T09:42:45.120 回答
11

一个常见的解决方案是元标记结合 noscript 来刷新页面并在 JavaScript 被禁用时通知服务器,如下所示:

<!DOCTYPE html>
<html lang="en">
    <head>
        <noscript>
            <meta http-equiv="refresh" content="0; /?javascript=false">
        </noscript>
        <meta charset="UTF-8"/>
        <title></title>
    </head>
</html>

在上面的示例中,当 JavaScript 被禁用时,浏览器将在 0 秒内重定向到网站的主页。此外,它还会将参数 javascript=false 发送到服务器。

然后,诸如 node.js 或 PHP 之类的服务器端脚本可以解析参数并知道 JavaScript 已禁用。然后它可以向客户端发送一个特殊的非 JavaScript 版本的网站。

于 2013-02-22T15:49:22.393 回答
10

这是“最干净”的解决方案 id 使用:

<noscript>
    <style>
        body *{ /*hides all elements inside the body*/
            display: none;
        }
        h1{ /* even if this h1 is inside head tags it will be first hidden, so we have to display it again after all body elements are hidden*/
            display: block;
        }
    </style>
    <h1>JavaScript is not enabled, please check your browser settings.</h1>
</noscript>
于 2015-04-02T14:04:23.883 回答
8

如果禁用了 javascript,您的客户端代码无论如何都不会运行,所以我假设您的意思是您希望该信息在服务器端可用。在这种情况下,noscript的帮助较小。相反,我有一个隐藏的输入并使用 javascript 来填写一个值。在您的下一个请求或回发之后,如果该值在那里,您就知道 javascript 已打开。

小心诸如 noscript 之类的东西,第一个请求可能会显示 javascript 已禁用,但以后的请求会将其打开。

于 2008-09-23T14:10:47.757 回答
5

例如,您可以使用类似 document.location = 'java_page.html' 的东西将浏览器重定向到一个新的、包含脚本的页面。重定向失败意味着 JavaScript 不可用,在这种情况下,您可以求助于 CGI 例程或在标记之间插入适当的代码。(注意:NOSCRIPT 仅在 Netscape Navigator 3.0 及更高版本中可用。)

信用 http://www.intranetjournal.com/faqs/jsfaq/how12.html

于 2008-09-23T14:16:39.550 回答
4

我过去使用的一种技术是使用 JavaScript 编写一个会话 cookie,它只是作为一个标志来表示 JavaScript 已启用。然后服务器端代码查找此 cookie,如果未找到,则采取适当的措施。当然,这种技术确实依赖于启用 cookie!

于 2008-09-23T14:10:48.643 回答
4

我认为您可以将图像标记插入 noscript 标记,然后查看统计信息您的网站的次数以及该图像的加载频率。

于 2008-09-23T14:14:32.723 回答
4

人们已经发布了一些很好的检测选项示例,但基于您的要求“发出警告,如果没有启用 JS 的浏览器,该站点将无法正常运行”。您基本上添加了一个以某种方式出现在页面上的元素,例如当您获得徽章时 Stack Overflow 上的“弹出窗口”,带有适当的消息,然后使用一些在页面加载后立即运行的 Javascript 将其删除(我的意思是 DOM,而不是整个页面)。

于 2008-09-23T21:54:29.840 回答
4

标签内<noscript>的代码将在浏览器中未启用 js 时执行。我们可以使用noscript标签显示 msg 来打开 JS,如下所示。<noscript> <h1 style="text-align: center;">enable java script and reload the page</h1> </noscript> 同时将我们的网站内容隐藏在正文中。如下

<body>
<div id="main_body" style="display: none;">
website content.
</div>
</body>

现在,如果打开 JS,您可以让 main_body 中的内容如下所示

<script type="text/javascript">
document.getElementById("main_body").style.display="block";
</script>

于 2018-06-18T11:12:28.987 回答
3

为什么不直接放置一个仅在启用 JS 时才会触发的劫持 onClick() 事件处理程序,并使用它来将参数 (js=true) 附加到单击/选择的 URL(您还可以检测到一个下拉列表并更改添加隐藏表单字段的值)。所以现在当服务器看到这个参数 (js=true) 时,它知道 JS 已启用,然后在服务器端执行您的花哨逻辑。
不利的一面是,用户第一次访问您的网站、书签、URL、搜索引擎生成的 URL - 您需要检测这是一个新用户,所以不要寻找附加到 URL 中的 NVP,并且服务器必须等待下一次单击才能确定用户是否启用/禁用了 JS。此外,另一个缺点是 URL 将在浏览器 URL 上结束,如果此用户随后将此 URL 加入书签,即使用户没有启用 JS,它也会有 js=true NVP,尽管在下一次单击时服务器会明智地知道用户是否仍然启用了 JS。叹息。。这很有趣。。

于 2009-08-13T21:16:36.050 回答
3

为了强制用户启用 JavaScript,我将每个链接的“href”属性设置为同一个文档,通知用户启用 JavaScript 或下载 Firefox(如果他们不知道如何启用 JavaScript)。我将实际链接 url 存储到链接的“名称”属性中,并定义了一个全局 onclick 事件,该事件读取“名称”属性并将页面重定向到那里。

这对我的用户群很有效,虽然有点法西斯主义;)。

于 2010-07-26T14:12:58.570 回答
3

您没有检测到用户是否禁用了 javascript(服务器端或客户端)。相反,您假设 javascript 已禁用,并在禁用 javascript 的情况下构建您的网页。这消除了对 的需要noscript,无论如何您都应该避免使用它,因为它不能完全正确地工作并且是不必要的。

例如,只是建立你的网站说<div id="nojs">This website doesn't work without JS</div>

然后,您的脚本将简单地执行document.getElementById('nojs').style.display = 'none';其正常的 JS 业务。

于 2011-08-31T15:03:12.100 回答
3

使用我在此处介绍的纯服务器端解决方案检查 cookie,然后通过使用 Jquery.Cookie 删除 cookie 来检查 javascript,然后通过这种方式检查 cookie,您可以同时检查 cookie 和 javascript

于 2012-02-09T05:25:27.633 回答
3

在某些情况下,向后执行可能就足够了。使用 javascript 添加一个类:

// Jquery
$('body').addClass('js-enabled');

/* CSS */
.menu-mobile {display:none;}
body.js-enabled .menu-mobile {display:block;}

这可能会在任何复杂的事情上产生维护问题,但它是对某些事情的简单修复。与其尝试检测何时未加载,不如根据加载时间设置样式。

于 2013-01-13T09:52:06.187 回答
3

我想添加我的解决方案,以获得关于有多少真实用户在禁用 javascript 的情况下访问我的网站的可靠统计数据。每次会话仅进行一次检查,具有以下好处:

  • 访问 100 个页面或仅访问 1 个页面的用户每人计为 1 个。这允许专注于单个用户,而不是页面。
  • 无论如何都不会破坏页面流、结构或语义
  • 可以记录用户代理。这允许从统计数据中排除机器人,例如通常禁用 JS 的 google bot 和 bing bot!还可以记录IP、时间等...
  • 每个会话只需检查一次(最小过载)

我的代码使用带有 ajax 的 PHP、mysql 和 jquery,但可以适应其他语言:

在您的数据库中创建一个表,如下所示:

CREATE TABLE IF NOT EXISTS `log_JS` (
  `logJS_id` int(11) NOT NULL AUTO_INCREMENT,
  `data_ins` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
  `session_id` varchar(50) NOT NULL,
  `JS_ON` tinyint(1) NOT NULL DEFAULT '0',
  `agent` varchar(255) DEFAULT NULL,
  PRIMARY KEY (`logJS_id`)
) ENGINE=MyISAM  DEFAULT CHARSET=utf8;

使用 session_start() 或等效项(需要 jquery)后将其添加到每个页面:

<?  if (!isset($_SESSION["JSTest"]))
    { 
        mysql_query("INSERT INTO log_JS (session_id, agent) VALUES ('" . mysql_real_escape_string(session_id()) . "', '" . mysql_real_escape_string($_SERVER['HTTP_USER_AGENT']). "')"); 
        $_SESSION["JSTest"] = 1; // One time per session
        ?>
        <script type="text/javascript">
            $(document).ready(function() { $.get('JSOK.php'); });
        </script>
        <?
    }
?>

像这样创建页面 JSOK.php:

<?
include_once("[DB connection file].php");   
mysql_query("UPDATE log_JS SET JS_ON = 1 WHERE session_id = '" . mysql_real_escape_string(session_id()) . "'");
于 2013-08-23T07:50:39.333 回答
3

我想出了另一种使用 css 和 javascript 本身的方法。
这只是开始修补类和 id。

CSS 片段:
1. 创建一个 css ID 规则,并将其命名为 #jsDis。
2. 使用“content”属性在 BODY 元素之后生成文本。(您可以根据需要设置此样式)。
3 创建第二个 css ID 规则并将其命名为#jsEn,并对其进行样式化。(为了简单起见,我给我的#jsEn 规则赋予了不同的背景颜色。

<style>
#jsDis:after {
    content:"Javascript is Disable. Please turn it ON!";
    font:bold 11px Verdana;
    color:#FF0000;
}

#jsEn {
    background-color:#dedede;
}

#jsEn:after {
    content:"Javascript is Enable. Well Done!";
    font:bold 11px Verdana;
    color:#333333;
}
</style>

JavaScript 片段:
1. 创建一个函数。
2. 使用 getElementById 获取 BODY ID 并将其分配给变量。
3. 使用JS函数'setAttribute',改变BODY元素的ID属性值。

<script>
function jsOn() {
    var chgID = document.getElementById('jsDis');
    chgID.setAttribute('id', 'jsEn');
}
</script>

HTML 部分。
1. 使用 ID 为#jsDis 命名 BODY 元素属性。
2. 添加带有函数名的onLoad事件。(jsOn())。

<body id="jsDis" onLoad="jsOn()">

因为 BODY 标签被赋予了#jsDis 的 ID:
- 如果 Javascript 被启用,它会自己改变 BODY 标签的属性。
- 如果禁用 Javascript,它将显示 css 'content:' 规则文本。

您可以使用#wrapper 容器或使用 JS 的任何 DIV。

希望这有助于理解。

于 2013-09-12T03:17:20.923 回答
2

检测到什么?JavaScript?那是不可能的。如果您只是希望它用于记录目的,您可以使用某种跟踪方案,其中每个页面都有 JavaScript 来请求特殊资源(可能非常小gif或类似)。这样,您就可以区分唯一页面请求和跟踪文件请求。

于 2008-09-23T14:09:45.200 回答
2

在 noscript 内的 meta 中添加刷新不是一个好主意。

  1. 因为 noscript 标签不符合 XHTML

  2. 属性值“刷新”是非标准的,不应使用。“刷新”将页面的控制权从用户手中夺走。使用“刷新”将导致 W3C 的 Web 内容可访问性指南 --- 参考http://www.w3schools.com/TAGS/att_meta_http_equiv.asp失败。

于 2009-04-03T03:06:19.177 回答
2

对于那些只想跟踪 js 是否启用的人来说,使用 ajax 例程来存储状态怎么样?例如,我将所有访问者/访问记录在一组表中。JSenabled 字段可以设置为默认值 FALSE,如果启用了 JS,ajax 例程会将其设置为 TRUE。

于 2010-11-18T22:14:50.253 回答
1

这是一个 PHP 脚本,可以在生成任何输出之前包含一次。它并不完美,但它在大多数情况下运行良好,可以避免交付客户端不会使用的内容或代码。标题注释解释了它是如何工作的。

<?php
/*****************************************************************************
 * JAVASCRIPT DETECTION                                                      *
 *****************************************************************************/

// Progressive enhancement and graceful degradation are not sufficient if we
// want to avoid sending HTML or JavaScript code that won't be useful on the
// client side.  A normal HTTP request will not include any explicit indicator
// that JavaScript is enabled in the client.  So a "preflight response" is
// needed to prompt the client to provide an indicator in a follow-up request.
// Once the state of JavaScript availability has been received the state of
// data received in the original request must be restored before proceding.
// To the user, this handshake should be as invisible as possible.
// 
// The most convenient place to store the original data is in a PHP session.
// The PHP session extension will try to use a cookie to pass the session ID
// but if cookies are not enabled it will insert it into the query string.
// This violates our preference for invisibility.  When Javascript is not
// enabled the only way to effect a client side redirect is with a "meta"
// element with its "http-equiv" attribute set to "refresh".  In this case
// modifying the URL is the only way to pass the session ID back.
//
// But when cookies are disabled and JavaScript is enabled then a client side
// redirect can be effected by setting the "window.onload" method to a function
// which submits a form.  The form has a "method" attribute of "post" and an
// "action" attribute set to the original URL.  The form contains two hidden
// input elements, one in which the session ID is stored and one in which the
// state of JavaScript availability is stored.  Both values are thereby passed
// back to the server in a POST request while the URL remains unchanged.  The
// follow-up request will be a POST even if the original request was a GET, but
// since the original request data is restored, the containing script ought to
// process the request as though it were a GET.

// In order to ensure that the constant SID is defined as the caller of this
// script would expect, call session_start if it hasn't already been called.
$session = isset($_SESSION);
if (!$session) session_start();

// Use a separate session for Javascript detection.  Save the caller's session
// name and ID.  If this is the followup request then close the caller's
// session and reopen the Javascript detection session.  Otherwise, generate a
// new session ID, close the caller's session and create a new session for
// Javascript detection.
$session_name = session_name();
$session_id = session_id();
session_write_close();
session_name('JS_DETECT');
if (isset($_COOKIE['JS_DETECT'])) {
    session_id($_COOKIE['JS_DETECT']);
} elseif (isset($_REQUEST['JS_DETECT'])) {
    session_id($_REQUEST['JS_DETECT']);
} else {
    session_id(sha1(mt_rand()));
}
session_start();

if (isset($_SESSION['_SERVER'])) {
    // Preflight response already sent.
    // Store the JavaScript availability status in a constant.
    define('JS_ENABLED', 0+$_REQUEST['JS_ENABLED']);
    // Store the cookie availability status in a constant.
    define('COOKIES_ENABLED', isset($_COOKIE['JS_DETECT']));
    // Expire the cookies if they exist.
    setcookie('JS_DETECT', 0, time()-3600);
    setcookie('JS_ENABLED', 0, time()-3600);
    // Restore the original request data.
    $_GET = $_SESSION['_GET'];
    $_POST = $_SESSION['_POST'];
    $_FILES = $_SESSION['_FILES'];
    $_COOKIE = $_SESSION['_COOKIE'];
    $_SERVER = $_SESSION['_SERVER'];
    $_REQUEST = $_SESSION['_REQUEST'];
    // Ensure that uploaded files will be deleted if they are not moved or renamed.
    function unlink_uploaded_files () {
        foreach (array_keys($_FILES) as $k)
            if (file_exists($_FILES[$k]['tmp_name']))
                unlink($_FILES[$k]['tmp_name']);
    }
    register_shutdown_function('unlink_uploaded_files');
    // Reinitialize the superglobal.
    $_SESSION = array();
    // Destroy the Javascript detection session.
    session_destroy();
    // Reopen the caller's session.
    session_name($session_name);
    session_id($session_id);
    if ($session) session_start();
    unset($session, $session_name, $session_id, $tmp_name);
    // Complete the request.
} else {
    // Preflight response not sent so send it.
    // To cover the case where cookies are enabled but JavaScript is disabled,
    // initialize the cookie to indicate that JavaScript is disabled.
    setcookie('JS_ENABLED', 0);
    // Prepare the client side redirect used when JavaScript is disabled.
    $content = '0; url='.$_SERVER['REQUEST_URI'];
    if (!$_GET['JS_DETECT']) {
        $content .= empty($_SERVER['QUERY_STRING']) ? '?' : '&';
        $content .= 'JS_DETECT='.session_id();
    }
    // Remove request data which should only be used here.
    unset($_GET['JS_DETECT'],$_GET['JS_ENABLED'],
            $_POST['JS_DETECT'],$_POST['JS_ENABLED'],
            $_COOKIE['JS_DETECT'],$_COOKIE['JS_ENABLED'],
            $_REQUEST['JS_DETECT'],$_REQUEST['JS_ENABLED']);
    // Save all remaining request data in session data.
    $_SESSION['_GET'] = $_GET;
    $_SESSION['_POST'] = $_POST;
    $_SESSION['_FILES'] = $_FILES;
    $_SESSION['_COOKIE'] = $_COOKIE;
    $_SESSION['_SERVER'] = $_SERVER;
    $_SESSION['_REQUEST'] = $_REQUEST;
    // Rename any uploaded files so they won't be deleted by PHP.  When using
    // a clustered web server, upload_tmp_dir must point to shared storage.
    foreach (array_keys($_FILES) as $k) {
        $tmp_name = $_FILES[$k]['tmp_name'].'x';
        if (move_uploaded_file($_FILES[$k]['tmp_name'], $tmp_name))
            $_SESSION['_FILES'][$k]['tmp_name'] = $tmp_name;
    }
// Have the client inform the server as to the status of Javascript.
?>
<!DOCTYPE html>
<html>
<head>
    <script>
        document.cookie = 'JS_ENABLED=1';
// location.reload causes a confirm box in FireFox
//      if (document.cookie) { location.reload(true); }
        if (document.cookie) { location.href = location; }
    </script>
    <meta http-equiv="refresh" content="<?=$content?>" />
</head>
<body>
    <form id="formid" method="post" action="" >
        <input type="hidden" name="<?=$session_name?>" value="<?=$session_id?>" />
        <input type="hidden" name="JS_DETECT" value="<?=session_id()?>" />
        <input type="hidden" name="JS_ENABLED" value="1" />
    </form>
    <script>
        document.getElementById('formid').submit();
    </script>
</body>
</html>
<?php
    exit;
}
?>
于 2013-09-16T17:38:49.690 回答
1

这里是转折!可能有客户端浏览器启用了 Javascript 并且使用 JS 兼容的浏览器。但是出于什么原因 Javascript 在浏览器中不起作用(例如:防火墙设置)。据统计,这发生在每 93 个场景中的 1 个。所以服务器检测到客户端能够执行 Javascript,但实际上它没有!

作为一种解决方案,我建议我们在客户端站点中设置一个 cookie,然后从服务器读取它。如果设置了 cookie,那么 JS 可以正常工作。有什么想法吗 ?

于 2013-12-18T10:42:47.650 回答
1

当然,Cookie 和 HTTP 标头是很好的解决方案,但两者都需要明确的服务器端参与。

对于简单的站点,或者我没有后端访问权限的站点,我更喜欢客户端解决方案。

--

我使用以下内容为 HTML 元素本身设置类属性,因此我的 CSS 可以处理几乎所有其他显示类型逻辑。

方法:

1)放置在元素<script>document.getElementsByTagName('html')[0].classList.add('js-enabled');</script> 上方。<html>

警告!!!!此方法将覆盖所有<html>类属性,更不用说可能不是“有效”HTML,但适用于所有浏览器,我已经对其进行了测试。

*注意:由于脚本运行的时间,在<html>处理标记之前,它最终会得到一个没有节点的空 classList 集合,所以在脚本完成时,<html>元素将只被赋予你添加的类.

2)保留所有其他<html>类属性,只需将脚本<script>document.getElementsByTagName('html')[0].classList.add('js-enabled');</script>放在开始<html>标记之后。

在这两种情况下,如果 JS 被禁用,则不会更改<html>类属性。

备择方案

多年来,我使用了其他一些方法:

    <script type="text/javascript">
    <!-- 
        (function(d, a, b){ 
            let x = function(){
                // Select and swap
                let hits = d.getElementsByClassName(a);
                for( let i = hits.length - 1; i >= 0; i-- ){
                    hits[i].classList.add(b);
                    hits[i].classList.remove(a);
                }
            };
            // Initialize Second Pass...
            setTimeout(function(){ x(); },0);
            x();
        })(document, 'no-js', 'js-enabled' );
    -->
</script>

// 缩小为:

<script type="text/javascript">
    <!-- 
        (function(d, a, b, x, hits, i){x=function(){hits=d.getElementsByClassName(a);for(i=hits.length-1;i>=0;i--){hits[i].classList.add(b);hits[i].classList.remove(a);}};setTimeout(function(){ x(); },0);x();})(document, 'no-js', 'js-enabled' );
    -->
</script>
  • 这将在页面中循环两次,一次是在页面中的位置,通常是在<html>页面加载之后和页面加载之后。需要两次,因为我注入了我没有后端访问权限的 CMS 的 header.tpl 文件,但想为 no-js 片段提供样式选项。

第一遍,将设置 .js-enabled 类允许任何全局样式启动,并阻止大多数进一步的重排。第二遍,是任何后来包含的内容的统称。

理由:

主要原因,我关心是否启用 JS 是出于“样式”目的,隐藏/显示表单,启用/禁用按钮或重新设置滑块、表格和其他需要 JS 功能的演示文稿的演示和布局“正确”,如果没有 JS 来动画或处理交互,它将是无用的或无法使用的。

此外,你不能直接用javascript检测,如果javascript被“禁用”......只有当它被“启用”时,通过执行一些javascript,所以你要么依赖<meta http-equiv="refresh" content="2;url=/url/to/no-js/content.html" />或者你可以依赖css来切换样式,如果javascript执行,切换到“js-enabled”模式。

于 2020-06-19T18:10:31.680 回答
1

如果启用了 JavaScript ,为什么需要知道服务器端?浏览器支持哪种变体是否重要?例如,它是否需要理解关键字let或者就可以了var

我建议发送不需要任何 JavaScript 即可访问的可读内容,然后尝试加载 JS 文件以添加您想要的所有 JS 行为。

例如,如果未启用 JS,UI 可能最终会丢失登录或修改按钮,并且它可能在底部包含一个小文本(使用<noscript>或带有 CSS 的某些元素,animation如果 JS 代码未删除,则在一小段延迟后显示文本整个元素很快)说“要登录/修改此内容,您必须在浏览器中启用 JavaScript 支持。” 如果你做得好,除非他或她尝试登录或修改内容,否则读者甚至可能不会注意到缺少任何内容。

作为一种优化,您可以使用 JavaScript 设置 cookie,如果您出于某种原因希望异步获取它,服务器可以避免发送非 JavaScript 可读内容。只需确保仅在 JS 代码运行完成至少一次后才设置此 cookie,而不是在 JS 代码开始运行时立即设置它,以确保最终用户在 (不是如果!)JS代码因任何原因失败。

(请注意,异步加载初始页面状态不会更快地将该内容提供给最终用户。但是,您只能在没有 JavaScript 的情况下发送全部内容的一部分。这可以允许更快地呈现“首屏”,然后异步加载其余内容页面使用 JS 代码。)

作为额外的好处,搜索引擎仍然可以在不启用任何 JavaScript 的情况下为您的网站编制索引。

于 2021-06-23T14:32:34.120 回答
0

我昨天不得不解决同样的问题,所以我只是在这里添加我的 .001。该解决方案至少在主页上对我有用(index.php)

我喜欢在根文件夹中只有一个文件: index.php 。然后我使用文件夹来构建整个项目(代码、css、js 等)。所以 index.php 的代码如下:

<head>
    <title>Please Activate Javascript</title>
    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
    <script type="text/javascript" src="js/jquery-1.3.2.min.js"></script> 
</head>

<body>

<script language="JavaScript">
    $(document).ready(function() {
        location.href = "code/home.php";
    });   
</script>

<noscript>
    <h2>This web site needs javascript activated to work properly. Please activate it. Thanks!</h2>
</noscript>

</body>

</html>

希望这对任何人都有帮助。最好的祝福。

于 2011-04-08T07:01:56.047 回答
0

2022 年更新

这个问题已经有 30 多个答案,但似乎没有一个明确或准确地说明必须做什么。

  • 使用的服务器端框架 - ASP.NET Core
  • 客户端 - vanilla js

BaseController应用程序的第一个入口点上,OnActionExecutionAsync我有这个逻辑。

  • 基本上默认情况下,我假设客户端没有启用 javascript 并设置此标志。
Response.Cookies.Append("jsEnabled", "false");
  • 现在,在客户端初始加载后,我有一个 javascript 函数将此标志更新为true.
  • 这个函数只有在环境有的时候才会运行javascript

所以完整的解决方案就在这里。

客户

在初始加载时添加此功能

function detectIfJavascriptIsEnabled() {
    // if this function run's which means js is enabled
    var jsEnabled = getCookie('jsEnabled');
    if (jsEnabled === 'false') {
        setCookie('jsEnabled', 'true');
        location.reload();
    }
}

服务器

private bool ValidateIfEnvironmentHasJavascript() {
  if (HttpContext.Request.Cookies != null && HttpContext.Request.Cookies.Count > 0) {
    Boolean.TryParse(HttpContext.Request.Cookies["jsEnabled"], out
      var hasJavascriptEnabled);
    return hasJavascriptEnabled;
  } else {
    Response.Cookies.Append("jsEnabled", "false",
      new CookieOptions() {
        IsEssential = true, Expires = DateTime.UtcNow.AddHours(24)
      });
  }

  return false;
}

这就是你得到结果的方式

var environmentHasJavascript = ValidateIfEnvironmentHasJavascript();
于 2022-01-28T11:46:18.733 回答
-4

听起来可能是一个奇怪的解决方案,但您可以尝试一下:

<?php $jsEnabledVar = 0; ?>    

<script type="text/javascript">
var jsenabled = 1;
if(jsenabled == 1)
{
   <?php $jsEnabledVar = 1; ?>
}
</script>

<noscript>
var jsenabled = 0;
if(jsenabled == 0)
{
   <?php $jsEnabledVar = 0; ?>
}
</noscript>

现在在整个页面中使用“$jsEnabledVar”的值。您也可以使用它来显示一个块,指示用户 JS 已关闭。

希望这会有所帮助

于 2013-02-06T15:53:37.107 回答