![](/img/trans.png)
[英]How to prevent user from opening the application in multiple browser tabs?
[英]How do you detect and prevent a user from accessing a web app from multiple browser tabs using php/javascript?
我有一个Web应用程序,我想限制为单个浏览器选项卡或窗口。 因此,想法是用户登录,并且如果他们在选项卡/窗口中打开链接或打开新的浏览器选项卡/窗口,则会终止其会话。 我知道很多人对此表示反对,但这就是应用程序需要的方式。
控制器检查用户是否通过以下方式登录:
if (!isset($_SESSION['user_logged_in'])) {
Session::destroy();
header('location: '.URL.'login');
}
我曾尝试将$ _SESSION ['user_logged_in']设置为false(如果为true),但是显然您只需要一页就可以了。
打开新的浏览器选项卡或窗口时,是否可以破坏会话? 我猜大概是jquery / javascript,但没有跨过那一面。
不幸的是,这是非常复杂的。
几乎不可能做到真正的跨浏览器并得到每个浏览器的支持。
从技术上讲,从服务器的角度来看,每个新的浏览器选项卡都与后者没有区别。 他们也共享cookie和会话。
唯一不同的是JavaScript会话。 举个例子:一个完全基于AJAX的站点。 第一页面始终是登录页面。 然后,AJAX改变了一切。 例如,如果您敢于用此站点打开另一个选项卡,它将打开第一页,该页面总是默认注销。 这样可以实现,但是非常复杂。
诸如localStorage
类的新技术堆栈可能使之成为可能,您可以在其中在localStorage
发送消息的选项卡之间进行通信。 但这不是完全跨浏览器的,并非所有浏览器版本都支持。
因此,如果您只能选择有限的最新浏览器,那么请使用localStorage
和postMessage
。
仅仅背诵Oleg所说的话,这将是非常困难的,因为HTTP是无状态的并且浏览器选项卡共享数据。 一种可能的实现方式可能是在前端,但是需要提供一组非常具体的情况,并且可以轻松地绕开它们。 如果应用程序是SPA,并且主体仅加载一次,则可能会在主体加载上生成密钥,并在每次请求时发送该密钥。 然后,如果重新加载了正文(例如在新选项卡或新窗口中),则可以生成一个新密钥,该密钥将启动一个新会话。
但是,真正的问题是为什么您要这样做。 您的用户体验将受到损害,并且不存在真正的安全性提升。
我有一些解决方案,希望与您分享。
要将用户限制为每个会话一个选项卡,可以使用cookie。 我在这里描述了如何构建Web应用程序以实现该目标。
下面是实现我所说的示例。
Map<String, Object> v$params = new TreeMap<>(); v$params.put("path", "/"); FacesContext.getCurrentInstance() .getExternalContext() .addResponseCookie("browserName", UUID.randomUUID().toString(), v$params);
/** * http://stackoverflow.com/questions/5639346/shortest-function-for-reading-a-cookie-in-javascript */ (function() { function readCookie(name, c, C, i) { if (cookies) { return cookies[name]; } c = document.cookie.split('; '); cookies = {}; for (i = c.length - 1; i >= 0; i--) { C = c[i].split('='); cookies[C[0]] = C[1]; } return cookies[name]; } window.readCookie = readCookie; // or expose it however you want })(); // function read_cookie(k,r){return(r=RegExp('(^|; // )'+encodeURIComponent(k)+'=([^;]*)').exec(document.cookie))?r[2]:null;} function read_cookie(k) { return (document.cookie.match('(^|; )' + k + '=([^;]*)') || 0)[2]; } /** * To be called in login page only */ function setupWebPage(){ window.name = read_cookie("browserName"); } /** * To be called in another pages */ function checkWebPageSettings(){ var curWinName = window.name; var setWinName = read_cookie("browserName"); if( curWinName != setWinName){ /** * You may redirect the user to a proper page telling him that * your application doesn't support multi tab/window. From this page, * the user may decide to go back to the previous page ou loggout in * other to have a new session in the current browser's tab or window */ alert('Please go back to your previous page !'); } }
<script type="text/javascript"> setupWebPage(); </script>
<script type="text/javascript"> checkWebPageSettings(); </script>
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.