Snippets
Created by
Colin Cheng
last modified
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 | // ==UserScript==
// @id rate@segmentfault
// @name segmentfault's user's question accepted rate
// @version 1.1
// @namespace http://www.segmentfault.com/
// @author zbinlin
// @description 显示用户的结贴率
// @updateURL https://bitbucket.org/zbinlin/segmentfault-rate/raw/tip/rate@segmentfault.meta.js
// @include http://www.segmentfault.com/q/*
// @include http://segmentfault.com/q/*
// @include https://www.segmentfault.com/q/*
// @include https://segmentfault.com/q/*
// @run-at document-end
// @grant GM_xmlhttpRequest
// ==/UserScript==
"use strict";
var ajax = "function" === typeof GM_xmlhttpRequest ? GM_xmlhttpRequest : function GM_xmlhttpRequest(obj) {
var xhr = new XMLHttpRequest();
xhr.open(obj.method, obj.url, true);
xhr.onload = (obj.onload || noop).bind(xhr);
xhr.onerror = (obj.onerror || noop).bind(xhr);
xhr.send(null);
function noop() {}
};
let authorURL = (document.querySelector(".post-topheader .author > a") || {}).href;
let headers = new Headers();
let req = new Request(authorURL, {
method: "GET",
headers,
mode: "same-origin"
});
let global = (() => this)();
let btn = document.createElement("a");
btn.textContent = "»查看结贴率«";
btn.style.cursor = "pointer";
btn.style.marginLeft = "1rem";
btn.addEventListener("click", function _(e) {
btn.textContent = "查询中...";
getAcceptedRate().then(questions => {
questions = JSON.parse(questions);
let rate = questions.filter(item => item).length / questions.length;
let span = document.createElement("span");
span.style.marginLeft = "1rem";
span.style.color = "green";
span.textContent = `[提问数:${questions.length} | 结贴率:${(rate * 100).toFixed(2)}%]`;
btn.removeEventListener("click", _);
btn.parentNode.replaceChild(span, btn);
btn = undefined;
}, err => {
btn.textContent = "查询失败";
});
});
let author = document.querySelector(".post-topheader .author");
author.appendChild(btn);
author = undefined;
function getAcceptedRate() {
return fetch(req).then(res => res.text()).then(text => {
let uid = (text.match(/data-id="(\d+)"[^>]*>\s*加关注/i) || [])[1];
if (!uid) return Promise.reject("Can't find uid");
return uid;
}).then(uid => {
let gen = getQuestions(`//api.segmentfault.com/user/${uid}/questions`);
return co(gen);
});
};
function coFetch(uri) {
return new Promise((resolve, reject) => {
ajax({
method: "GET",
url: uri,
headers: {
"Accept": "application/json,text/html;q=0.8,*/*;q=0.5",
"Accept-Encoding": "gzip,deflate",
"Connection": "key-alive",
"User-Agent": "gm-httpengine v2.1.1"
},
onload: function (res) {
let text = res.responseText;
resolve({
json: function () {
try {
return JSON.parse(text);
} catch (ex) {}
}
});
},
onerror: reject
});
});
}
function* getQuestions(url) {
let page = 1;
let questions = [];
while (1) {
let uri = url + "?page=" + page;
let rst = yield coFetch(uri).then(res => res.json());
let data = rst.data;
if (data && Array.isArray(data.rows)) {
questions.push(...data.rows.map(d => d.isAccepted));
}
if (data && data.page) {
page = data.page.next;
}
if (!page) return JSON.stringify(questions);
}
}
function co(gen) {
return new Promise((resolve, reject) => {
function next(val) {
let ret = gen.next(val);
if (ret.done) {
resolve(ret.value);
} else {
ret.value.then(rst => {
next(rst);
}).catch(err => {
});
}
}
next();
});
}
|
Comments (0)
You can clone a snippet to your computer for local editing. Learn more.