avoid forwarding to id page @ Haiku (brute force version :-)

  • /*
     * @title avoid forwarding to id page @ Haiku (brute force version :-)
     * @description はてなハイクで 2017-5-9 くらいから 不意に IDページに飛ばされちゃう件の無理やり対応(Haiku! するときに投稿内容の一部を数値参照に書き換えて投稿します)。
     * @include http://h.hatena.ne.jp/*
     * @license MIT http://opensource.org/licenses/MIT
     * @javascript_url
     */
    /*
        see http://h.hatena.ne.jp/target?word=%E3%81%AF%E3%81%A6%E3%81%AA%E3%83%8F%E3%82%A4%E3%82%AF&date=2017-05-19
    */
    (function() {
        var d_ = document;
        if (d_.location.href.indexOf("http://h.hatena.ne.jp/") == 0) {
    
    /*
        http://s.hatena.ne.jp/js/HatenaStar.js?201609121
        の Ten.XHR の部分をごっそりコピペして、一部だけ書き換えてる。
    */
    Ten.XHR = new Ten.Class({
        initialize: function(uri,opts,obj,callPropertyName) {
            Ten.EventDispatcher.implementEventDispatcher(this);
            this.method = 'GET';
    
            if (!uri) return;
    
            if (!Ten.XHR.isSafeUri(uri)) {
                throw "host differs : " + uri;
            }
    
            if (!opts) opts = {};
    
            if (opts.method) 
                this.method = opts.method;
    
            var self = this;
            this.addEventListener('complete', function() {
                if (!obj) return;
                if (typeof(obj) == 'function' && typeof(callPropertyName) == 'undefined') {
                    obj.call(obj, self.request);
                } else {
                    obj[callPropertyName].call(obj, self.request);
                }
            });
    
    
            /* ここから : 書き換え */
    
            if (/\/entry\.body$/.test(uri)) {
                /* IDページに飛ばされる地雷 */
                let mine_list = [
                    "ミ",
                    "о",
                    "卍",
                ];
                opts.data.body = opts.data.body.map(function(body) {
                    let txt = body;
                    mine_list.forEach(function(mine) {
                        var re = new RegExp(mine, "g");
                        var entity = Array.prototype.reduce.call(mine, function(prev, v) {
                            return prev + "&#" + v.codePointAt(0) + ";";
                        }, "");
                        txt = txt.replace(re, entity);
                    });
                    return txt;
                });
            }
    
            /* ここまで : 書き換え */
    
            this.load(uri, opts.data);
        },
        getXMLHttpRequest: function() {
            var xhr;
            var tryThese = [
                function () { return new XMLHttpRequest(); },
                function () { return new ActiveXObject('Msxml2.XMLHTTP'); },
                function () { return new ActiveXObject('Microsoft.XMLHTTP'); },
                function () { return new ActiveXObject('Msxml2.XMLHTTP.4.0'); }
            ];
            for (var i = 0; i < tryThese.length; i++) {
                var func = tryThese[i];
                try {
                    xhr = func;
                    return func();
                } catch (e) {
                    //alert(e);
                }
            }
            return xhr;
        },
        isSafeUri: function(uri) {
            if (uri.match(/^\w+:/) || uri.match(/^\/\//)) {
                if (uri.split('/')[2] == location.host) return true;
                else return false;
            } else if (uri.match(/^\/[^\/]/) || uri == '/') {
                return true;
            } else if (!uri || uri.length == 0) {
                return false;
            }
            return true;
        },
        makePostData: function(data) {
            var regexp = /%20/g;
            if (typeof data == 'string' || (data instanceof String)) {
                return encodeURIComponent(data).replace(regexp, '+');
            }
            var pairs = [];
            for (var k in data) {
                if (typeof data[k] == 'undefined') continue;
                var prefix = encodeURIComponent(k).replace(regexp, '+') + '=';
                var values = Array.prototype.concat(data[k]);
                for (var i = 0; i < values.length; i++) {
                    var pair = prefix + encodeURIComponent(values[i]).replace(regexp, '+');
                    pairs.push(pair);
                }
            }
            return pairs.join('&');
        }
    },{
        load: function(url, params) {
            var req = Ten.XHR.getXMLHttpRequest();
            this.request = req;
    
            var self = this;
            req.onreadystatechange = function() {
                self.stateChangeHandler.call(self, req);
            };
            params = params ? Ten.XHR.makePostData(params) : null;
    
            req.open(this.method, url, true);
            if (this.method == 'POST') 
                req.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');
            req.send(params);
        },
        stateChangeHandler: function(req) {
            this.dispatchEvent('state_change');
    
            if (req.readyState == 4) {
                this.dispatchEvent('ready', req.status.toString());
    
                if (req.status >= 200 && req.status < 300) {
                    this.dispatchEvent('complete', req);
                } else {
                    this.dispatchEvent('error', req);
                }
            }
        }
    });
    
        }
    
    
    
    })();
    
    
    
  • Permalink
    このページへの個別リンクです。
    RAW
    書かれたコードへの直接のリンクです。
    Packed
    文字列が圧縮された書かれたコードへのリンクです。
    Userscript
    Greasemonkey 等で利用する場合の .user.js へのリンクです。
    Loader
    @require やソースコードが長い場合に多段ロードする Loader コミのコードへのリンクです。
    Metadata
    コード中にコメントで @xxx と書かれたメタデータの JSON です。

History

  1. 2017/05/20 17:30:47 - 2017-05-20
  2. 2017/05/20 14:06:29 - 2017-05-20