如何检测JavaScript是否被禁用?

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

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

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

497270 次浏览

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

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

您还可以使用NOSCRIPT标记来显示禁用JS的浏览器的文本。

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意味着JS被禁用。这两个例子都相当琐碎,容易操作,但你明白了。

如果您想纯粹统计您的用户中有多少禁用了javascript,您可以这样做:

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

然后检查您的访问日志以查看此图像被击中的次数。一个稍微粗糙的解决方案,但它会为您的用户群提供一个百分比明智的好主意。

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

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

您需要看一下nocript标签。

<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>

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

要小心像nocript这样的东西,第一个请求可能会显示javascript已禁用,但未来的请求会打开它。

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

我建议你反过来写不显眼的JavaScript。

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

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

我认为您可以将图像标记插入到noScript标记中,并查看您的网站的统计数据以及加载此图像的频率。

我假设您正在尝试决定是否交付JavaScript增强的内容。最好的实现会干净地降级,因此站点仍然可以在没有JavaScript的情况下运行。我还假设您指的是服务端检测,而不是出于不明原因使用<noscript>元素。

没有执行服务器端JavaScript检测的好方法。作为替代方案,可以使用JavaScript设置cookie,然后在随后的页面浏览量中使用服务器端脚本测试该cookie。然而,这不适合决定要交付的内容,因为它无法将没有cookie的访问者与新访问者或不接受JavaScript设置cookie的访问者区分开来。

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

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

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

如果您的用例是您有一个表单(例如,登录表单),并且您的服务器端脚本需要知道用户是否启用了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!

nocript标签工作得很好,但需要每个额外的页面请求继续提供无用的JS文件,因为本质上nocript是客户端检查。

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

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

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

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

<noscript><meta http-equiv="refresh" content="0; url=whatyouwant.html" /></noscript>

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

  1. 因为nocript标签不兼容XHTML

  2. 属性值“刷新”是不标准的,不应该使用。“刷新”从用户手中夺走了对页面的控制权。使用“刷新”将导致W3C Web内容无障碍指南失败 http://www.w3schools.com/TAGS/att_meta_http_equiv.asp.

你为什么不放一个劫持的onClick()事件处理程序,只有在启用JS时才会触发,并使用它将参数(js=true)附加到单击/选定的URL(你也可以检测下拉列表并更改添加隐藏表单字段的值)。所以现在当服务器看到这个参数(js=true)时,它知道JS已启用,然后在服务器端做你的花哨逻辑。
缺点是用户第一次访问您的网站,书签,URL,搜索引擎生成的URL-您需要检测这是一个新用户,因此不要在URL中查找附加的NVP,服务器将不得不等待下一次单击以确定用户是否启用/禁用JS。此外,另一个缺点是URL最终会出现在浏览器URL上,如果该用户然后将此URL添加书签,它将具有js=true NVP,即使用户没有启用JS,但在下一次单击时,服务器将明智地知道用户是否仍然启用了JS。很好玩啊…

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

首先,页面中需要JavaScript正常运行的任何部分(包括通过getElementById调用等修改的被动超文本标记语言元素)都被设计为按原样使用,假设没有可用的javaScript。

任何需要JavaScript的元素,我都会在标签中放置如下内容:

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

然后在我的文档开始时,我在getElementsByName('jsOnly')的循环中使用.onloaddocument.ready来设置.style.display = "";重新打开JS依赖元素。这样,非JS浏览器不必看到站点的JS依赖部分,如果他们有它,它会在准备好时立即出现。

一旦您习惯了这种方法,就很容易混合您的代码来处理这两种情况,尽管我现在才尝试使用noscript标记,并期望它会有一些额外的优势。

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

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

我想在这里加上我的.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>

…其中所有的网站内容用类“页面容器”的div包装。然后,nocript标签中的CSS将隐藏您的所有页面内容,而是显示您想显示的任何“无JS”消息。这实际上是Gmail似乎在做的事情…如果它对谷歌足够好,它对我的小网站也足够好。

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

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

css:

.pagecontainer {
display: none;
}

js:

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

超文本标记语言:

<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>

在任何情况下都可以吗? 即使不支持nocript标记(只需要一些css) 有没有人知道非css解决方案?

将其添加到每个页面的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>

感谢杰伊。

我昨天不得不解决同样的问题,所以我只是在这里添加我的.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>

希望这对任何人都有帮助。最好的问候。

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

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

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

使用纯服务器端解决方案检查cookie,我已经介绍了这里,然后通过使用JQuery. Cookie删除cookie来检查javascript,然后通过这种方式检查cookie,您检查cookie和javascript

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

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

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

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

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

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


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

这可能会在任何复杂的东西上产生维护问题,但这是对某些事情的简单修复。而不是试图检测它何时未加载,只需根据它何时加载样式。

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

<?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。

希望这将有助于

一个常见的解决方案是将meta标记与nocript结合使用,以刷新页面并在禁用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版本发送到客户端。

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

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

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

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

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()) . "'");

我想出了另一种使用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函数'setAtium',更改BODY元素ID属性的值。

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

超文本标记语言部分。 1.将BODY元素属性命名为#jsDis。
2.使用函数名称添加onLoad事件。(jsOn())。

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

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

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

希望这能帮助你找到答案

这是一个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;
}
?>

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

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

<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!如果有效,则已启用,如果无效,则未启用…

这是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>

<noscript>标签内的代码将在浏览器中没有启用js时执行。 我们可以使用noscript标签来显示msg以打开JS,如下所示。 启用java脚本和重新加载页面 同时将我们的网站内容隐藏在正文中。如下

<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>

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

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

--

我使用下面的代码为超文本标记语言元素本身设置一个class属性,因此我的CSS几乎可以处理所有其他显示类型逻辑。

方法:

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

警告!!!! 这个方法,将覆盖所有<html>类属性,更不用说可能不是“有效的”超文本标记语言,但适用于所有浏览器,我已经测试过了。

*注意:由于脚本运行的时间,在处理<html>标记之前,它最终会获得一个没有节点的空类列表集合,因此在脚本完成时,<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><html>之后 需要两次,因为我注入了一个CMS的header.tpl文件,我没有后端访问权限,但想为no-js片段提供样式选项。

第一遍,将设置启用. js的类,允许任何全局样式启动,并防止大多数进一步的拒绝。第二遍,是对任何后来包含的内容的总称。

理由:

主要原因,我关心JS是否启用是为了“造型”目的,隐藏/显示表单,启用/禁用按钮或重新设计滑块,表格和其他演示文稿的演示文稿和布局,这些演示文稿需要JS“正确”运行,如果没有JS来动画或处理交互,将是无用的或无法使用的。

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

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

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

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

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

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

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

2022年更新

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

  • 使用的服务器端框架-ASP.NET核心
  • 客户端-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();