l0o0 / translators_CN

Zotero translator中文网页抓取翻译器🎉This is Zotero translators for Chinese Sites(beta), not the official Zotero repo
GNU Affero General Public License v3.0
4.11k stars 525 forks source link

add (ChinaXiv.js) 新增中国科学院科技论文预发布平台 (#184) #224

Closed jiaojiaodubai closed 1 year ago

jiaojiaodubai commented 1 year ago

184 已完成。

有一点需要补充的就是,ChinaXiv导出的bib文件编码是GBK(虽然它注释写Encoding=UTF-8),Connector默认以UTF-8来解码返回的内容,于是就出现了乱码。UTF-8解码之后,原来的信息已经被污染,没有办法还原。我尝试过向服务器请求Bytes,但没有对应的响应。两周前我已经发邮件给ChinaXiv的运营方反馈这个问题,他们至今没有回应。 现在的暂时是用页面抓取的内容来填字段,如果这个问题能解决的话,extra里面就不会有乱码了。

yfdyh000 commented 1 year ago

184 已完成。 有一点需要补充的就是,ChinaXiv导出的bib文件编码是GBK(虽然它注释写Encoding=UTF-8),Connector默认以UTF-8来解码返回的内容,于是就出现了乱码。UTF-8解码之后,原来的信息已经被污染,没有办法还原。我尝试过向服务器请求Bytes,但没有对应的响应。两周前我已经发邮件给ChinaXiv的运营方反馈这个问题,他们至今没有回应。 现在的暂时是用页面抓取的内容来填字段,如果这个问题能解决的话,extra里面就不会有乱码了。

function isGBK(arrayBuffer) {
  const dataView = new DataView(arrayBuffer);
  const length = dataView.byteLength;

  let hasASCII = false;
  let hasGBK = false;

  for (let i = 0; i < length; i++) {
    const byte = dataView.getUint8(i);

    // 检查是否为ASCII字符
    if (byte <= 0x7F) {
      hasASCII = true;
    }

    // 检查是否为GBK字符
    if ((byte >= 0x81 && byte <= 0xFE) && ((byte >= 0x40 && byte <= 0x7E) || (byte >= 0x80 && byte <= 0xFE))) {
      if (i + 1 >= length) {
        return false;
      }
      const nextByte = dataView.getUint8(i + 1);
      if (!(nextByte >= 0x40 && nextByte <= 0xFE && nextByte !== 0x7F && nextByte !== 0xFF)) {
        return false;
      }
      hasGBK = true;
      i++;
    }
  }

  return hasASCII && hasGBK;
}

function GBKtoUTF8(gbkArrayBuffer) {
  const gbkUint8Array = new Uint8Array(gbkArrayBuffer);
  const gbkDecoder = new TextDecoder('gbk');
  const gbkString = gbkDecoder.decode(gbkUint8Array);
  return gbkString
}

        let bibResp = await request(bibUrl, {responseType: 'arraybuffer'});
        Z.debug(isGBK(bibResp.body));
        Z.debug(GBKtoUTF8(bibResp.body));

经测可解码。检测部分出自AI,我不保证可靠性。 request的首个参数不是请求方法,不知为何与文档不同。 没有研究错误处理等问题。

jiaojiaodubai commented 12 months ago

request的请求参数是可选的,里面的每一个属性也是可选的,这不矛盾。 我之前尝试过这样获取,但那时无法得到ArrayBuffer,刚才一试居然可以了,我会在下一次commit中修复这个问题。