这是去年的一个需求,没事儿整理了一下;因公司业务需求,需要判断用户首次进入的站点在页面显示相应的电话,由于站点不同所以显示的电话也是不一样的,具体需求如下:
用户首次进入公司网站,判断用户浏览器客户端是否存在电话切换所需的 cookie;如果存在,则直接将页面中的电话显示为该 cookie 所对应的电话;如果不存在,则判断当前站点域名,根据域名对应的客服风格显示对应的电话,同时在用户客户端设置电话切换所需 cookie,cookie有效期为7天;
每个域名可能对应对个客服风格,每个客服风格在 cookie 中有一个唯一值,通过判断这个唯一值来切换显示电话,同时电话切换的 cookie 和客服风格的 cookie 的有效期要保持同步,同时失效;
客服风格的唯一 cookie 值存在指定的主站点之下,该值是移动存在的;
功能点:
- 封装 cookie 设置/获取/删除方法;
- 判断 cookie/域名/客服风格,显示对应的电话;
- 跨域同步 cookie,由于公司有多个站点,不同的网站主域不同,必须要保证用户首次进入网站后,在随后其他站点浏览时显示的是同一个电话,所以就需要跨域同步 cookie;
方案:
1、现有3个不同域名的站点:www.aaa.com(A站/主站)、www.bbb.com(B站)、www.ccc.com(C站);每个站点有对应的电话和 cookie 值;
2、用户进入网站,首先判断用户客户端 cookie 是否存在;
- 若存在,判断 cookie 值对应修改页面中显示的电话;
- 若不存在,请求服务器,通过服务器获取主站点下客服风格的唯一值以及客服风格 cookie 的失效日期;
- 根据服务器获取的 cookie 判断页面中显示的电话,并在当前域名下设置 cookie 及失效日期;
小二儿,上代码~
服务端(php):
<?php
/**
* @跨域获取Cookie分析 http://varyu.com/notes/54.html
* @网站头部按 指定类型 "$_COOKIE['xiaoma_tel_cookie']",换电话号码 400-0123-267
* @2014.08.20 js 调用客户端的 cookie 信息
*/
header("content-type:text/html;charset=utf-8");
$cb=$_GET['callback']; //getJSON('xxx.com?callback=?') 中的callback
if($_COOKIE['xiaoma_tel_cookie']==""){
$_COOKIE['xiaoma_tel_cookie'] = "404";
}
if($_COOKIE['tel_cookie_overdue'] == ""){
$_COOKIE['tel_cookie_overdue'] = "404";
}
$result = "{".xiaoma_tel_cookie.":".$_COOKIE['xiaoma_tel_cookie'].",".tel_cookie_overdue.":".$_COOKIE['tel_cookie_overdue']."}";
echo($cb."(".$result.")");
exit();
?>
切换脚本:重构之后的电话切换功能[续]
// 封装 cookie 设置/获取/删除 方法
var CookieUtil = {
get: function(name) {
var cookie = document.cookie;
var cookieName = encodeURIComponent(name) + "=";
var start = cookie.indexOf(cookieName);
var value = null;
if (start > -1)
{
var end = cookie.indexOf(";", start);
if (end == -1)
end = cookie.length;
value = decodeURIComponent(cookie.substring(start + cookieName.length, end));
}
return value;
},
set: function(name, value, expires, path, domain, secure) {
var cookieText = encodeURIComponent(name) + "=" + encodeURIComponent(value);
if (expires instanceof Date)
cookieText += "; expires=" + expires.toGMTString();
if (path)
cookieText += "; path=" + path;
if (domain)
cookieText += "; domain=" + domain;
if (secure)
cookieText += "; secure";
document.cookie = cookieText;
},
unset: function(name, path, domain, secure) {
this.set(name, "", new Date(0), path, domain, secure);
}
};
function getReferrer() {
windowAlias = window;
documentAlias = document;
var referrer = '';
try {
referrer = windowAlias.top.document.referrer;
} catch (e) {
if(windowAlias.parent) {
try {
referrer = windowAlias.parent.document.referrer;
} catch (e2) {
referrer = '';
}
}
}
if(referrer === '') {
referrer = documentAlias.referrer;
}
return referrer;
}
function getHostName(url) {
// scheme : // [username [: password] @] hostame [: port] [/ [path] [? query] [# fragment]]
var e = new RegExp('^(?:(?:https?|ftp):)/*(?:[^@]+@)?([^:/#]+)'),
matches = e.exec(url);
return matches ? matches[1] : url;
}
function changeTelToSemWithTagName(ag_obj,sourceNum,targetNum) {
if(ag_obj){
ag_length = ag_obj.length;
for(i = 0; i<ag_length; i++) {
var ag_phone_html=ag_obj[i].innerHTML;
if(ag_phone_html.indexOf(sourceNum) == 0) {
ag_obj[i].innerHTML=ag_phone_html.replace(sourceNum,targetNum);
}
}
}
}
function changeTelNoToFreeWithTagName(ag_obj,sourceNum,targetNum){
if(ag_obj){
ag_length = ag_obj.length;
for (i = 0; i<ag_length; i++){
var ag_phone_html=ag_obj[i].innerHTML;
if (ag_phone_html.indexOf(sourceNum) == 0){
ag_obj[i].innerHTML=ag_phone_html.replace(sourceNum,targetNum);
}
}
}
}
function changeTelNo(){
var ag_obj = document.getElementsByTagName("span");
changeTelToSemWithTagName(ag_obj,agrantsemPPC.freeNo,agrantsemPPC.semNo);
var ag_obj2 = document.getElementsByTagName("b");
changeTelToSemWithTagName(ag_obj2,agrantsemPPC.freeNo,agrantsemPPC.semNo);
}
function changeTelNoToFree(){
var ag_obj = document.getElementsByTagName("span");
changeTelNoToFreeWithTagName(ag_obj,agrantsemPPC.semNo, agrantsemPPC.freeNo);
var ag_obj2 = document.getElementsByTagName("b");
changeTelNoToFreeWithTagName(ag_obj2,agrantsemPPC.semNo, agrantsemPPC.freeNo);
}
// 按
function getElementByClass (className, parent) {
parent || (parent = document);
var descendants= parent.getElementsByTagName('*'), i=-1, e, result=[];
while (e=descendants[++i]) {
((' '+(e['class']||e.className)+' ').indexOf(' '+className+' ') > -1) && result.push(e);
}
return result;
}
// 电话/域名/客服风格
temlist = new Array("400-663-1986","400-6969-256", "400-0123-267", "400-663-1986", "4008-116-356", "4008-118-059", "4006-025-056", "4000-256-029", "4006-123-226", "400-0699-025", "400-6969-256", "4000-289-015", "400-6969-256", "400-6969-256", "4008-116-069")
reg_xsat = new RegExp("www\.xuesat\.com");
reg_xm = new RegExp(".*.\.xiaoma\.com");
reg_cg = new RegExp("www\.xiaomachuguo\.com");
cook_seo = new RegExp("103608619|103609219|103609522");
cook_bbs = new RegExp("103608719|103609019|103609520|103609521|103609622|103609623");
cook_kc = new RegExp("103608819|103609119|103609319|103609419|103609519|103609588|103609589");
cook_ys = new RegExp("103608919");
cook_zt = new RegExp("103609540");
cook_sh = new RegExp("103609549|103609533");
cook_xsat = new RegExp("103609543");
cook_yd = new RegExp("103609523");
cook_cg = new RegExp("103609552|103609553|103609554|103609581");
cook_wm = new RegExp("103609524");
cook_wk1 = new RegExp("103609525");
cook_wk = new RegExp("103609575");
cook_360 = new RegExp("103609527|103609537|103609538|103609582|103609586|103609587");
cook_sg = new RegExp("103609529|103609530|103609531|103609536");
function changeElementTelFromList(taglist, type) {
for(var i = 0; i < taglist.length; i++){
var eml = taglist[i]
var eml_tag = eml.tagName;
if (eml_tag == 'img' || eml_tag == 'IMG') {
var img_src = eml.src
var fileName = img_src.substring(img_src.lastIndexOf('\/')+1,img_src.lastIndexOf('.'));
// 修改最后一个值
var tmpname = fileName.substring(0,fileName.length-1)
tmpname = tmpname + type
// 替换掉原来的名字
img_src = img_src.replace(fileName, tmpname)
eml.src = img_src +'?'+Math.random()
} else if (eml_tag == 'span' || eml_tag == 'SPAN' || eml_tag == 'em' || eml_tag == 'EM' || eml_tag == 'i' || eml_tag == 'I') {
eml.innerHTML = temlist[type]
}
}
}
function changeElementTelBGFromList(taglist, type) {
for(var i = 0; i < taglist.length; i++){
var eml = taglist[i]
eml_style = eml.currentStyle || window.getComputedStyle(eml, false);
img_src = eml_style.backgroundImage
var fileName = img_src.substring(img_src.lastIndexOf('\/')+1,img_src.lastIndexOf('.'));
var tmpname = fileName.substring(0,fileName.length-1)
tmpname = tmpname + type
// 替换掉原来的名字
img_src = img_src.replace(fileName, tmpname)
eml.style.backgroundImage=img_src
}
}
function changeElementTelkf(taglist, type) {
for(var i = 0; i < taglist.length; i++){
var eml = taglist[i]
var href_val = eml.href;
var tmpname = href_val.substring(0,href_val.length-1)
tmpname = tmpname + type
eml.href=tmpname
}
}
// 按指定的类型换电话号码 1 对应sem 2对应seo 3对应bbs
function changeTelByType(teltype){
changeElementTelFromList(getElementByClass('telnumbcls'), teltype);
changeElementTelBGFromList(getElementByClass('telnumbclsbg'), teltype);
}
// 判断客服风格
function kefuStyle(kefu_cookie_type) {
var tel_type = 1;
if(cook_kc.test(kefu_cookie_type)){
tel_type = 1;
}else if(cook_ys.test(kefu_cookie_type)){
tel_type = 4;
}else if(cook_zt.test(kefu_cookie_type)){
tel_type = 5;
}else if(cook_sh.test(kefu_cookie_type)){
tel_type = 6;
}else if(cook_xsat.test(kefu_cookie_type)){
tel_type = 7;
}else if(cook_yd.test(kefu_cookie_type)){
tel_type = 8;
}else if(cook_cg.test(kefu_cookie_type)){
tel_type = 9;
}else if(cook_wm.test(kefu_cookie_type)){
tel_type = 10;
}else if(cook_wk1.test(kefu_cookie_type)){
tel_type = 11;
}else if(cook_360.test(kefu_cookie_type)){
tel_type = 12;
}else if(cook_sg.test(kefu_cookie_type)){
tel_type = 13;
}else if(cook_wk.test(kefu_cookie_type)){
tel_type = 14;
}else{
tel_type = 1;
}
return tel_type;
}
function changeTelNumAll(){
cookie_tel_type = CookieUtil.get("xiaoma_tel_cookie");
if(cookie_tel_type != null && cookie_tel_type != undefined && cookie_tel_type != '' && cookie_tel_type != '0'){
// cookie存在 ,换电话
changeTelByType(cookie_tel_type);
}else{
// cookie 不存在
var fulldomain = window.location.host;
if(reg_xm.test(fulldomain)){ // 判断主机名:xiaoma.com
var kefu_cookie_type = CookieUtil.get("xiaoma_style_id");
var tel_cookie_overdue = parseInt(CookieUtil.get("xiaoma_style_id_overdue") + "000");
var tel_type = kefuStyle(kefu_cookie_type);
changeTelByType(tel_type);
var tel_expires = new Date(tel_cookie_overdue);
CookieUtil.set("xiaoma_tel_cookie", tel_type, tel_expires, "/", "xiaoma.com");
}else{
$.getJSON("http://www.xiaoma.com/didiadmin/test_telchange.php?callback=?", function(data){
var kefu_cookie_num = data.xiaoma_style_id;
var date_now = parseInt(data.xiaoma_style_id_overdue + "000");
var tel_type = kefuStyle(kefu_cookie_num);
changeTelByType(tel_type);
var tel_expires = new Date(date_now);
if(reg_xsat.test(fulldomain)) {
domain_url = "xuesat.com";
// }else if(reg_jy.test(fulldomain)) {
// domain_url = "xiaomajiaoyu.com";
}else if(reg_cg.test(fulldomain)) {
domain_url = "xiaomachuguo.com";
}else{
domain_url = "xiaoma.com";
};
CookieUtil.set("xiaoma_tel_cookie", tel_type, tel_expires, "/", domain_url);
})
}
}
}
/*
* 传递函数给whenReady()
* 当文档解析完毕且为操作准备就绪时,函数作为document的方法调用
*/
var whenReady = (function() { //这个函数返回whenReady()函数
var funcs = []; //当获得事件时,要运行的函数
var ready = false; //当触发事件处理程序时,切换为true
//当文档就绪时,调用事件处理程序
function handler(e) {
if(ready) return; //确保事件处理程序只完整运行一次
//如果发生onreadystatechange事件,但其状态不是complete的话,那么文档尚未准备好
if(e.type === 'onreadystatechange' && document.readyState !== 'complete') {
return;
}
//运行所有注册函数
//注意每次都要计算funcs.length
//以防这些函数的调用可能会导致注册更多的函数
for(var i=0; i<funcs.length; i++) {
funcs[i].call(document);
}
//事件处理函数完整执行,切换ready状态, 并移除所有函数
ready = true;
funcs = null;
}
//为接收到的任何事件注册处理程序
if(document.addEventListener) {
document.addEventListener('DOMContentLoaded', handler, false);
document.addEventListener('readystatechange', handler, false); //IE9+
window.addEventListener('load', handler, false);
}else if(document.attachEvent) {
document.attachEvent('onreadystatechange', handler);
window.attachEvent('onload', handler);
}
//返回whenReady()函数
return function whenReady(fn) {
if(ready) { fn.call(document); }
else { funcs.push(fn); }
}
})();
whenReady(changeTelNumAll);
页面结构:
<!-- 文字形式--固定标签包含 -->
<span class="telnumbcls">400-6969-256</span>
<em class="telnumbcls">400-6969-256</em>
<i class="telnumbcls">400-6969-256</i>
<!-- 图片形式 -->
<img class="telnumbcls" src="tel_01.png" alt="" />
<!-- 背景图片形式 -->
<div class="telnumbclsbg" style="background:url(tel_01.png) no-repeat;">内容内容内容内容内容</div>