如何在Safari 7中禁用自动填充

时间:2014-04-02 16:41:33

标签: html safari

我试图找到一种方法来使Safari 7(使用版本7.0.2,7.0.3进行测试)尊重autocomplete =" off"属性。无论我尝试什么,它都会继续自动填充。

对于我们设置新用户的管理页面,这是一个问题。我们的用户使用自己的用户名/密码保存。

这是我们正在使用的表单的缩写版本。我已经尝试将字段重命名为" xxu"和" xxp"但自动填充似乎读取标签标题。我被各种不同的标签所欺骗,但它仍然以某种方式触发了自动填充。

<form novalidate autocomplete="off">
     <div class="control-group">
          <label class="control-label">Username</label>
          <div class="controls">
               <input type="text" name="xxu" autocomplete="off" required="required">
        </div>
     </div>
     <div class="control-group">
          <label class="control-label">Username</label>
          <div class="controls">
               <input type="password" name="xxp" autocomplete="off" required="required">
        </div>
     </div>
</form>

我在Apple网站上发现了这篇描述这个问题的文章。 https://discussions.apple.com/message/25080203#25080203

有没有人知道在Safari 7中禁用表单自动填充的任何其他方法? (唉,这是我们对IE的期望)

感谢您的帮助。

10 个答案:

答案 0 :(得分:11)

我们最近遇到了同样的问题。最重要的是,我们对我们的表格进行了AJAX验证。由于一些奇怪的原因,这将触发safari再次自动填充我们的电子邮件输入字段。因此,每次您填写所需的电子邮件时,Safari都会填写一封它首选的电子邮件。无法通过我们的表格。

我们的解决方案

几乎打破了Safaris(和Chromes)自动填充算法。

HTML:

<div class="douchebag_safari">
    <input class="js-clear_field" tabindex="-1" name="e-mail" type="email">
    <input class="js-clear_field" tabindex="-1" name="Ecom_User_Password" type="password">
</div>

CSS:

.douchebag_safari {
    position: fixed;
    width: 1px;
    left: -50px;
}
.douchebag_safari input {
    width: 1%;
}

JS:

$('#form').on('submit', function () {
    "use strict";
    $('.js-clear_field').attr('disabled', 'disabled');
}

它的主旨是:我们在Safaris自动填充算法中输入电子邮件和密码类型的输入字段,其名称将更高(或相同?)并隐藏在屏幕外。 OnSubmit,这些字段将被禁用,因此将从POST排除到我们的后端。

缺点是用户在我们的表单上没有自动填充功能,但我们认为在我们的情况下这是值得的。

注意(假设你关心):禁用了Javascript的用户仍会将这些字段包含在他们的POST中。根据您的设置,您需要允许这两个字段进入后端以防止出错。为了安全起见,请确保您不对这些字段做任何事情!

作为奖励,这解决了Chrome(35)假设密码字段上方的输入字段是用户名的错误。在我们的例子中,它是一个数字字段,给出了奇怪的用户体验和错误。

答案 1 :(得分:5)

我选择了@Skurpi提出的douchebag_safari方法的简化版本。它只是HTML而且位于表单的底部。

<!-- http://stackoverflow.com/questions/22817801/how-to-disable-auto-fill-in-safari-7 -->
<div class="douchebag_safari" style="left: -9999px; position: fixed; width: 1px;">
    <input type="password">
</div>

答案 2 :(得分:3)

我找到了一种更快捷,更简单的方法来避免表单自动填充。它适用于Mac上的FF 27,Chrome 36和Safari 7.0.5。我还没有在其他操作系统中测试它。

我只是在我的表单中放置一个假字段,不需要标签或id和name属性。我把它隐藏在例如内联样式和voilà

<input type="password" style="display: none">

我的表单中的电子邮件和密码字段按预期填充了数据库中的值,并且不再自动完成。

说实话,我也不喜欢这个解决方案......我很想找到一个兼容的标准解决方案,但似乎autocomplete =“off”不再起作用了。

答案 3 :(得分:2)

遇到同样的问题并尝试了前面提到的两个HTML / CSS解决方案。

他们不适合我(或Safari 9.0.3 :))所以我实现了这样的解决方案

<div style="overflow: hidden;width: 0px;height: 0px;">
  <input id="password" type="password" name="password" />
</div>

在实际表单输入字段之上。

在OS X El Capitan上运行的Safari,Firefox(44.0.2)和Chrome(48.0.2564.109)上进行了测试。

答案 4 :(得分:1)

我使用了一个随机数并将其合并到每个字段名称中,以便浏览器永远不会识别该字段的名称。

答案 5 :(得分:1)

上面给出的解决方案对我不起作用。经过调查,我可以评估Safari启用自动填充的决定取决于以下因素:

  • &#34; id&#34;输入的属性包含&#34; name&#34;?
  • &#34; name&#34;输入的属性包含&#34; name&#34;?
  • 输入的标签是否包含&#34; name&#34;?

然后,我可以使用以下代码禁用Safari的自动填充功能,最后我将其包装到jQuery插件中,以方便:

&#13;
&#13;
$(document).ready(function () {
	$('input').disableAutoFill();
});
&#13;
&#13;
&#13;

&#13;
&#13;
(function($) {

	$.fn.disableAutoFill = function() {

		"use strict";

		var self = {

			/**
			 * Disable autofill for one input
			 * @param {Object} $input jQuery element
			 */
			disableAutoFill: function($input) {
				if (self.isBrowser('safari')) {
					self.alterLabel($input);
					self.alterName($input);
					self.alterId($input);
				}
				$input.attr('autocomplete', 'off');
			},

			/**
			 * Change input's name
			 * Make sure Safari wont detect the word "name" in the name attribute
			 * otherwise Safari will enable autofill
			 * @param {Object} $input jQuery element
			 */
			alterName: function ($input) {
				$input.attr('data-original-name', $input.attr('name'));

				// Find unique name attribute value
				var new_name = false;
				var iteration = 0;
				while (iteration < 10 && !new_name) {
					new_name = self.random();
					if (self.checkAttributeExists('name', new_name)) {
						new_name = false;
					}
				}

				if (new_name) {
					$input.attr('name', new_name);
					self.setFormSubmitHandler($input);
				}
			},

			/**
			 * Change input's id
			 * Make sure Safari wont detect the word "name" in the id attribute
			 * otherwise Safari will enable autofill
			 * @param {Object} $input jQuery element
			 */
			alterId: function ($input) {
				$input.attr('data-original-id', $input.attr('id'));

				// Find unique id attribute value
				var new_id = false;
				var iteration = 0;
				while (iteration < 10 && !new_id) {
					new_id = self.random();
					if (self.checkAttributeExists('id', new_id)) {
						new_id = false;
					}
				}

				if (new_id) {
					$input.attr('id', new_id);
					self.setFormSubmitHandler($input);
				}
			},

			/**
			 * Reset input's name and id to its initial values before submitting the form
			 * @param {Object} $input jQuery element
			 */
			setFormSubmitHandler: function ($input) {
				var $form = $input.closest('form');
				if ($form.length > 0) {
					$form.submit(function() {
						var id = $input.attr('data-original-id');
						if (id) {
							$input.attr('id', id);
						}
						var name = $input.attr('data-original-name');
						if (name) {
							$input.attr('name', name);
						}
					});
				}
			},

			/**
			 * Make sure Safari wont detect the word "name" in the label
			 * otherwise Safari will enable autofill
			 * @param {Object} $input jQuery element
			 */
			alterLabel: function ($input) {
				var $label = self.findLabel($input);
				if ($label && $label.length > 0) {
					var text = $label.text();
					var array = text.split('');
					text = array.join('<span></span>');
					$label.html(text);
				}
			},

			/**
			 * Find label element of an input
			 * see http://stackoverflow.com/questions/4844594/jquery-select-the-associated-label-element-of-a-input-field
			 * @param $input
			 * @returns {*}
			 */
			findLabel: function ($input) {
				var $label = $('label[for="'+$input.attr('id')+'"]');

				if ($label.length > 0) {
					return $label;
				}
				var $parentElem = $input.parent();
				var $parentTagName = parentElem.get(0).tagName.toLowerCase();

				if ($parentTagName == "label") {
					return $parentElem;
				}
				return null;
			},

			/**
			 * Generate a random string
			 * @returns {string}
			 */
			random: function () {
				var text = '';
				var possible = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";
				for (var i=0; i < 5; i++) {
					text += possible.charAt(Math.floor(Math.random() * possible.length));
				}
				return text;
			},

			/**
			 * Check if there is an existing DOM element with a given attribute matching a given value
			 * @param {string} attributeName
			 * @param {string} attributeValue
			 * @returns {boolean}
			 */
			checkAttributeExists: function (attributeName, attributeValue) {
				return $('['+attributeName+'='+attributeValue+']').length > 0;
			},

			/**
			 * Detect current Web browser
			 * @param {string} browser
			 * @returns {boolean}
			 */
			isBrowser: function (browser) {
				// http://stackoverflow.com/questions/5899783/detect-safari-using-jquery
				var is_chrome = navigator.userAgent.indexOf('Chrome') > -1;
				var is_explorer = navigator.userAgent.indexOf('MSIE') > -1;
				var is_firefox = navigator.userAgent.indexOf('Firefox') > -1;
				var is_safari = navigator.userAgent.indexOf("Safari") > -1;
				var is_opera = navigator.userAgent.toLowerCase().indexOf("op") > -1;
				if ((is_chrome)&&(is_safari)) {is_safari=false;}
				if ((is_chrome)&&(is_opera)) {is_chrome=false;}

				if (browser === 'chrome') {
					return is_chrome;
				}
				if (browser === 'explorer') {
					return is_explorer;
				}
				if (browser === 'firefox') {
					return is_firefox;
				}
				if (browser === 'safari') {
					return is_safari;
				}
				if (browser === 'opera') {
					return is_opera;
				}
				return false;
			}

		};

		self.disableAutoFill(this);

		return this;
	};



}(jQuery));
&#13;
&#13;
&#13;

您也可以下载或查看文件here

答案 6 :(得分:0)

我采用了一种更简单的解决方案,适合我们管理员维护用户帐户并偶尔设置密码,只需将用户的密码输入类型更改为:

<input type="text" name="password" />

简单但有效。

答案 7 :(得分:-3)

你可以试试这个:

如果你能够使用JavaScript和jQuery,你可以在加载html(body onload)时加载它:

$('#theform input').val('');

此问题类似于:Is autocomplete="off" compatible with all modern browsers?

有些浏览器不再支持autocomplete="off"

答案 8 :(得分:-3)

您可以使用此javascript代码:

if (document.getElementsByTagName) {

var inputElements = document.getElementsByTagName(“input”);

for (i=0; inputElements[i]; i++) {

if (inputElements[i].className && (inputElements[i].className.indexOf(“disableAutoComplete”) != -1)) {

inputElements[i].setAttribute(“autocomplete”,”off”);

}

}

}

答案 9 :(得分:-5)

我尝试了一切,让它工作,然后更新版本的Safari再次破坏了我的网站。我即将尝试额外的表单字段(感谢Skurpi)。与此同时,这是我的新解决方案(在PHP中)

if(strpos($_SERVER['HTTP_USER_AGENT'],'Safari') !== false)
{
?>
    <div style="background:#ffff66;border:1px solid #ff9900;font-size:1.5em;padding:1em;">
        The Safari browser has a known bug: autocomplete replaces required data in our form with incorrect values. Unfortunately this may prevent you from adding products to the shopping cart. <br /><br />Please try a different browser or go to your browser settings and turn off autocomplete and refresh the page.
    </div>
<?php
}

如果有足够的网站这样做,Safari团队可能会得到一个提示并修复他们的浏览器以遵守autocomplete =“off”属性。