技術改變生活–自動簽到升級版(定時簽到)

公司規定每日簽到兩次;日子太安逸瞭,有時候中午居然會忘記簽到……
於是,筆者尋思寫一個自動簽到的腳本;每天指定兩個簽到時段,每次打開頁面,先檢測當前是否為簽到時段,如果在簽到時段,則檢查cookie中記錄的值,確認該時段是否已經簽到過瞭,巴拉巴拉…… 具體細節見流程圖:

其中第一步調用的getCheckTime用來檢測當前是否為簽到時間,並返回當前時間距下一個時段的毫秒數,具體請見下面的流程圖:

整個頁面的代碼如下,其中用到瞭筆者《JavaScript類庫/組件/框架封裝的總體結構》一文中提到的框架,封裝瞭一個定時運行器,具體用法見註釋:
[html] 
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "https://www.w3.org/TR/html4/loose.dtd"> 
<html> 
    <head> 
        <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"> 
        <meta name="author" content ="https://blog.csdn.net/NearEast"/> 
        <title>check in page</title> 
        <style type="text/css"> 
            .clear{ 
                clear:both; 
            } 
            .float{ 
                float:left; 
            } 
        </style> 
    </head> 
    <body> 
        <p id="dInfo" class="float"></p> 
        <p class="clear"></p> 
        <p id="wrap"> 
          <iframe class="float" id='i_iframe1' name="n_iframe1" frameborder="0"></iframe> 
          <iframe class="float" id='i_iframe2' name="n_iframe2" frameborder="0"></iframe> 
            <form target="n_iframe1" name="loginform" method="post" action="https://192.168.19.11:8010/signin/signin.jsp"> 
            <input name="name" type='hidden' value='nidong' /> 
            <input name="passwd" type='hidden' value='11111111' /> 
        </form> 
      </p> 
    </body> 
    <script type="text/javascript"> 
<span style="white-space:pre">      </span>//封裝一個定時運行器 
        (function( window, undefined ) { 
            var doc = window.document; 
            var _checkTime, _func, _tip, _print; 
            /** 
            初始化參數checkTime指定功能執行的時段,默認時間為'8:15'到'9:00',以及'12:35'到'14:00'兩個時段 
            checkTime應該是24小時制的,並且前面的絕對時間小於後面的絕對時間,例如'00:00:10'在'23:59'的前面 
            func:在該時間段要執行的功能 
            printFunc:日志信息的打印方法,默認為console.log方法打日志 
            tip:要執行的功能的描述,tip可以是html語句,與printFunc結合可能達到各種效果,如例子所示 
            */ 
        var checkUtil = function(conf) { 
            _checkTime = conf.checkTime || ['8:15', '9:00', '12:35','14:00']; 
            _func = conf.func; 
            _tip = conf.tip || '功能執行'; 
            _print = conf.printFunc || console.log; 
            _checkAndSet(); 
        }; 
        window.checkUtil= checkUtil; 
         
            /**基於一個指定日期的時間base,通過'hh:mm:ss'格式的時間字符串,獲取其毫秒時間 
            默認秒數為0 
            */ 
            function _getMillisecond(base, str){ 
                var slices = str.split(':'); 
                if(!base instanceof Date || slices.length<2){ 
                    alert('param error'); 
                    return; 
                } 
                base.setHours(parseInt(slices[0])); 
                base.setMinutes(parseInt(slices[1])); 
                base.setSeconds(parseInt(slices[2]||'0')); 
                return base.getTime(); 
            } 
             
            /**計算是否處在簽到時間段(flag==true),並返回距離下一次簽到還有多久(毫秒) 
            */ 
            function _getCheckTime(){ 
                var split = [], d = new Date(), curTime = new Date(d); 
                d.setMilliseconds(0); 
                for(var i=0;i<_checkTime.length;i++){ 
                    split[i] = _getMillisecond(d, _checkTime[i]); 
                } 
                //最後一個元素為第一個元素加上24小時,意為循環到第二天 
                split.push(24*3600*1000 + split[0]); 
                split.unshift(_getMillisecond(d, '00:00:00')); 
                 
                var start, end; 
                for(var i=0;i<split.length;i++){ 
                    start = split[i]; 
                    end = split[(i+1)%split.length]; 
                    if(start<=curTime && curTime<=end){ 
                        return{ 
                            eclipse:end – curTime, 
                            flag:i%2==1/*第奇數個元素*/ 
                        } 
                    } 
                } 
                 
                return 'error'; 
            } 
             
            function _addCookie(name, value) { 
                var hours = 2; 
                var exp = new Date(); 
                exp.setTime(exp.getTime() + hours * 60 * 60 * 1000); 
                doc.cookie = name + "=" + escape(value) + ";expires="+ exp.toGMTString(); 
            } 
            function _getCookie(name) { 
                var arr, reg = new RegExp("(^| )" + name + "=([^;]*)(;|$)"); 
                if (arr = doc.cookie.match(reg)) 
                    return unescape(arr[2]); 
                else 
                    return null; 
            } 
            function _delCookie(name) { 
                doc.cookie = name + "=n;expires=Thu, 01-Jan-70 00:00:01 GMT"; 
            } 
             
            function _checkAndSet(){ 
                var ret = _getCheckTime(); 
                if(ret.flag){ 
                    _print('當前為' + _tip + '時段'); 
                    var checked = _getCookie('_checked'); 
                    if(checked == 'true'){ 
                        _print('本時段已' + _tip); 
                    }else{ 
                        _print('現在執行' + _tip); 
                        _func(); 
                        //////////////////////////print some information 
                        _addCookie('_checked', 'true'); 
                    } 
                }else{ 
                    _print('當前非' + _tip + '時段'); 
                    _delCookie('_checked'); 
                } 
                 
                setTimeout(function(){ 
                    _checkAndSet(); 
                }, ret.eclipse); 
                _print('將於' + ret.eclipse/1000 + '秒之後,執行_checkAndSet()'); 
            }; 
     
        })(window); 
         
        window.onresize = function(){ 
            var frm = document.getElementById('i_iframe1'); 
            var frm2 = document.getElementById('i_iframe2'); 
            document.getElementById('wrap').style.height = document.documentElement.clientHeight+'px'; 
            frm.width=frm2.width='50%';//document.documentElement.clientWidth/2; 
            frm.height=frm2.height='100%';//document.documentElement.clientHeight; 
        }; 
 
        window.onload = function(){ 
            window.onresize(); 
            ///////////////////////////////As a single page 
            checkUtil({func:function(){ 
                    checkon(); 
                }, tip:'<a href="javascript:checkon();">簽到</a>' 
                , checkTime:['15:50', '15:50:10', '15:50:20','15:50:30'] 
                , printFunc:function(txt){ 
                    document.getElementById('dInfo').innerHTML += txt+'<br>'; 
                } 
            }); 
        } 
         
        function checkon(){ 
            loginform.childNodes[1].value='nidong'; 
            loginform.target="n_iframe1"; 
            loginform.submit(); 
            loginform.childNodes[1].value='gengap'; 
            loginform.target="n_iframe2"; 
            loginform.submit(); 
        } 
 
    </script> 
</html> 
以上頁面的js代碼中,封裝瞭一個checkUtil組件,可以用來定期執行任務。初始化參數checkTime中可以給出一天之內的多個時段,隻要瀏覽器頁面是打開狀態,到瞭一定時間就將運行func參數指定的函數;如果天天不關機,就可以一勞永逸,不用操心func函數的運行瞭。不過雖然代碼幾經修改,存在別的小問題還是難免的,也不能完全依賴它做事;定期查看一下日志還是很必要的。
由於Chrome隻支持online cookie,直接把代碼粘到一個本地文件運行是無效的,其它瀏覽器不存在這個問題。

發佈留言