65.9K
CodeProject 正在变化。 阅读更多。
Home

如何在后端服务器中检测客户端是否启用了/禁用了 JavaScript

starIconstarIconstarIconstarIconstarIcon

5.00/5 (13投票s)

2017 年 11 月 27 日

CPOL

4分钟阅读

viewsIcon

45983

学习如何在你的后端 Web 服务器上检测客户端是否启用了 JavaScript 或禁用了 JavaScript

引言

在这篇文章中,我将向您展示如何在后端 Web 服务器(任何平台)上检测客户端是否启用了 JavaScript,以便您可以在后端代码中使用它,并将其用作布尔值。

不幸的是,没有现成的方法可以检测到这一点。浏览器不会向 Web 服务器发送指示浏览器是否启用了 JavaScript 的 HTTP 标头/元数据。

因此,要检测它,我们需要做一些手动工作。

如何操作

后端代码

检测的技巧是,在客户端浏览器中设置一个标志(一个 cookie),指示浏览器是否启用了/禁用了 JavaScript。

然后服务器可以查看该 cookie,并检查客户端是否通过 JavaScript 指示其 JavaScript 已启用/禁用。

在此示例中,我们将其称为 cookie hasjs=false。因此,如果客户端拥有名为 hasjs 的 cookie 且其值为 false,则表示客户端指示 JavaScript 已关闭,否则 JavaScript 已开启。

因此,对于每个 webrequest,在您的后端服务器中创建一个布尔变量,并将其命名为 IsJavascriptOn,如果客户端拥有 cookie hasjs=false,则将其设置为 false,否则将其设置为 true

我将使用 ASP.NET MVC 作为代码示例,但概念对于所有平台都相同。

下面是一个函数示例,如果客户端拥有 cookie hasjs=false,则返回 false,否则返回 true

bool GetIsJavascriptOn()
{
    //If client has the cookie with name and value: hasjs=false
    if (Request.Cookies.ContainsKey("hasjs") &&
        Request.Cookies["hasjs"] == "false")
        return false;
    else //Client doesn't have the cookie: hasjs=false
        return true;
}

然后,在我们的代码中的某个位置,我们可以像下面这样设置我们的 IsJavascriptOn 变量

this.IsJavascriptOn = GetIsJavascriptOn();

现在,我们有了确定客户端是否启用了/禁用了 JavaScript 的布尔变量,所以现在我们可以在后端代码的任何地方使用这个变量了。

渲染 HTML

因此,现在我们需要在 JavaScript 被禁用时设置 hasjs=false cookie,在 JavaScript 被启用时删除 hasjs=false cookie。这在渲染 HTML 时完成。

我们需要根据客户端指示 JavaScript 是否启用/禁用来渲染一些 HTML。下面显示了这一点。

我们将此代码放在 <head> 中

<!--If client indicates that javascript is enabled (cookie "hasjs=false" doesn't exist)-->
@if (Model.IsJavascriptOn == true)
{
    <noscript>
        <meta http-equiv="Set-Cookie" content="hasjs=false; path=/">
        <meta http-equiv="Refresh" content="0">
    </noscript>
}
else //Client indicates javascript is disabled (cookie "hasjs=false" exists)
{
    <script>
        document.cookie = "hasjs=; expires=Thu, 01 Jan 1970 00:00:00 UTC; path=/";
        location.reload(true); //Refreshes the page
    </script>
}

现在我们完成了。如果您只想测试它而不想要任何解释,可以跳过其余部分。

在这里,如果我们的变量 IsJavascriptOn 等于 true,我们则绘制 <noscript> 块,否则我们绘制 <script> 块。

<noscript> 块将设置 cookie hasjs=false,然后刷新页面(是的,您可以在没有 JavaScript 的情况下设置 cookie 并刷新页面)。

<script> 块将删除 cookie hasjs=false,然后刷新页面。

所以这里发生的是,如果客户端指示 JavaScript 已开启,那么我们绘制 <noscript> 块。但客户端不会运行 <noscript> 块,除非它实际上被禁用了。

所以,如果它运行了 <noscript> 块,那么这意味着客户端告诉服务器它启用了 JavaScript,但这是错误的,需要将 hasjs 更新/设置为 false,然后刷新页面。

完成后,服务器将改为渲染 <script> 块,然后直到客户端再次启用 JavaScript,客户端才会运行 <script> 块。

因此,当客户端再次启用 JavaScript 时,客户端将运行 <script> 块,删除 cookie hasjs 并刷新页面。

然后,服务器将绘制 <noscript> 块,然后直到客户端再次禁用 JavaScript,客户端才会运行该块。

这就是循环的过程。

ASP.NET MVC 完整示例

这是 ASP.NET Core MVC(.NET Framework)中的完整示例。它非常直接,所以希望非 ASP.NET 程序员也能理解它,因为它几乎就像伪代码。

在此示例中,我将展示一个具有 3 个页面(index(主页)、contact 和 about)的最小网站,不带 CSS。

HomeController.cs

当客户端请求特定路径的页面时,此文件是代码开始的地方。它将检查客户端是否拥有 hasjs=false cookie,如果存在,则将我们的 IsJavascriptOn 变量设置为 false,否则设置为 true

using Microsoft.AspNetCore.Mvc;

namespace WebApplication1
{
    public class ViewDataModel
    {
        public bool IsJavascriptOn;
    }
}

namespace WebApplication1.Controllers
{
    public class HomeController : Controller
    {
        public ViewDataModel ViewDataModel;

        bool GetIsJavascriptOn()
        {
            //If client has the cookie with name and value: hasjs=false
            if (Request.Cookies.ContainsKey("hasjs") &&
                Request.Cookies["hasjs"] == "false")
                return false;
            else //Client doesn't have the cookie: hasjs=false
                return true;
        }

        //Executed if path is: "/" or "/home"
        public IActionResult Index()
        {
            this.ViewDataModel = new ViewDataModel();
            this.ViewDataModel.IsJavascriptOn = this.GetIsJavascriptOn();

            //draws the Index.cshtml in @RenderBody inside _Layout.cshtml
            return View(this.ViewDataModel); 
        }

        //Executed if path is: "/home/about"
        public IActionResult About()
        {
            this.ViewDataModel = new ViewDataModel();
            this.ViewDataModel.IsJavascriptOn = this.GetIsJavascriptOn();

            //draws the About.cshtml in @RenderBody inside _Layout.cshtml
            return View(this.ViewDataModel);
        }

        //Executed if path is: "/home/about"
        public IActionResult Contact()
        {
            this.ViewDataModel = new ViewDataModel();
            this.ViewDataModel.IsJavascriptOn = this.GetIsJavascriptOn();
            
            //draws the Contact.cshtml in @RenderBody inside _Layout.cshtml
            return View(this.ViewDataModel);
        }
    }
}

_Layout.cshtml

这是渲染 HTML 的起点。_Layout 是无论我们在哪个页面都会被渲染的内容,然后它会触发 @RenderBody(),这是一个 ASP.NET MVC 函数,它将渲染我们所在的页面。在本例中,这将渲染 index.cshtmlcontact.cshtmlabout.cshtml

@model ViewDataModel

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>Detect_Javascript</title>

   <!--If client indicates that javascript is enabled (cookie "hasjs=false" doesn't exist)-->
    @if (Model.IsJavascriptOn == true)
    {
        <noscript>
            <meta http-equiv="Set-Cookie" content="hasjs=false; path=/">
            <meta http-equiv="Refresh" content="0">
        </noscript>
    }
    else //Client indicates javascript is disabled (cookie "hasjs=false" exists)
    {
        <script>
            document.cookie = "hasjs=; expires=Thu, 01 Jan 1970 00:00:00 UTC; path=/";
            location.reload(true); //Refreshes the page
        </script>
    }
</head>
<body>
    <ul>
        <li><a href="/home">Home</a></li>
        <li><a href="/home/about">About</a></li>
        <li><a href="/home/contact">Contact</a></li>
    </ul>
    @RenderBody()
</body>
</html>

Index.cshtml

@model ViewDataModel

<h1>Home page</h1>
<p>This is the home page</p>

@if (Model.IsJavascriptOn == true)
{
    <p>Javascript  is enabled</p>
}
else
{
    <p>Javascript is disabled</p>
}

Contact.cshtml

@model ViewDataModel

<h1>Contact page</h1>
<p>This is the contact page</p>

@if (Model.IsJavascriptOn == true)
{
    <p>Javascript  is enabled</p>
}
else
{
    <p>Javascript  is disabled</p>
}

About.cshtml

@model ViewDataModel

<h1>About page</h1>
<p>This is the about page</p>

@if (Model.IsJavascriptOn == true)
{
    <p>Javascript is enabled</p>
}
else
{
    <p>Javascript is disabled</p>
}

所以,在这里,如果您启用了 JavaScript,它将显示 是的,JavaScript 已启用,否则显示 否,JavaScript 已禁用

下面是两个示例,展示了它应该是什么样子:

最后说明

<noscript> 标签内,<meta http-equiv="Set-Cookie" content="hasjs=false; path=/">,将 path 设置为 "/" 非常重要,因为 cookie 可以有路径,所以如果您导航到网站上的不同路径/站点,客户端可能会创建许多不同的 hasjs=false cookie,具体取决于客户端所在的路径。

感谢阅读,希望这对大家有所帮助。:-)

© . All rights reserved.