getenv获取不到自己export的环境变量_给Fast Word Query插件制作自己的网络词库

Anki添加单词有很多办法,可以导入他人的单词牌组,也可以自己去摘抄词典上的内容。当然,更高级一点的是通过浏览器插件遇到生词添加到Anki里。

那么有没有办法直接在Anki输入单词以后,可以将释义,发音等等内容自己添加进去呢?

答案就是:

​ 有!通过Fast Word Query 插件

9168224e38f006fcf083116481d9ba7c.png
这是一张卡片

除了单词和释义是原来有的,其他内容都是通过Fast Word Query插件自己生成

什么是Fast Word Query呢?麻烦请看一下这篇文章:

Innis:【Anki插件篇】(04)批量制卡:Fast Word Query​zhuanlan.zhihu.com
0ab5e519301baf2e72260c991e142453.png

我在这里是讲Fast Word Query 高级用法,自己制作网络词库


条件

想要自己制作网络词库,是有一定条件的:

  • python的基础
  • 爬虫的知识
  • 了解一点点网页结构(不美化界面,可以不太懂)

制作自己的词库其实不是特别难

如果你能获得你想捕获单词的网站API的话,可以很轻松的进行。

没有该网站的API的话,就要通过爬虫知识来获取内容进行封装【一般封装为字典类型(dict)】


简易的过程

这里用伪代码的表示(模板)

xx词库.py:

from ..base import *  #一定要有
import 引入自己需要的库
def 获取到单词的内容(word):
    ###对网站进行解析###
    ###对内容封装为dict(字典)###
    return word_dict

@register([u'词库的名称', u'词库的名称-英文'])#接口名称
class 接口函数名称(WebService):#接口函数名称
    def __init__(self):
        super(接口函数名称, self).__init__()#接口函数名称
    def _get_from_api(self):
        result=获取到单词的内容(self.word)#获取dict字典
        return self.cache_this(result)
    @export('单词释义')
    def 功能函数名称(self):
        ret=self._get_field('单词释义')#获取result[单词释义]内容
        return ret#返回单词释义

然后将该文件放入%APPDATA%Anki2addons211807206748servicedict文件夹里

好了,我们制作自己的词库已经完成了!

文章结束。


相信你看到这里还是一头雾水。

别急,现在才正式开始讲如何制作。

制作过程

首先,由于我的能力不足,才刚刚学编程不到半年,可能出现专有名词的出错。

Fast Word Query 插件添加自己词库,其实以前也有这种想法,网上却没有相关的文档的可以查看,只有在Github代码托管平台上源代码,没有帮助文档,只能参考他自带的词库。所以一直没弄成功(我自己的原因),要么直接导致插件崩溃了,要么就是输出不了如何东西。直到8月14日才成功。

  • 准备工作

首先,你需要有python

然后,你的python可能需要安装第三方库

cmd.exe下敲下:

pip install requests

pip install bs4

有了这些以后,你就可以编写代码

  • 提取信息及处理

这里,我以Weblio英日词典为例子。

f78c49a1714a39634dd7065dfdbe15c4.png

14b6ee231b8af976213af660808cb378.png

我们这里可以知道:

原来查询单词的地址是https://ejje.weblio.jp/content/{word}

如果我们需要取主な英訳/主な意味的内容的话,可以需要先看网页的源代码

aa7fd7ee915cbc14d58c1a8ed4044490.png

我们可以知道内容是在content-explanation ej/content-explanation je之下。

好了,如果我们现在就要编写代码的话,应该是这样的:

import requests
from bs4 import BeautifulSoup as bs4
def WeblioSearch_English(word):
    result={
        'mean':u'', 
    }
    try:
        url=u'https://ejje.weblio.jp/content/{word}'.format(word=word)
        get_requests=requests.get(url,timeout=5)#设置超时
        soup=bs4(get_requests.content,'html.parser')
    except:
        return result
    result['mean']=soup.find('td',
        attrs={'class':['content-explanation je','content-explanation ej']}).text #主要意思
    result.update()#对result 字典更新
    return result

words =['apple','リンゴ']
for word in words:
    ret=WeblioSearch_English(word)
    print(ret)

输出结果:

{'mean': 'リンゴ'}
{'mean': 'apple; Malus asiatica; Malus pumila'}
#这里type=dict

这里涉及爬虫和对网站的解析:

Dwzb:BeautifulSoup全面总结​zhuanlan.zhihu.com
f8efbbf53061b87d41e3bf10443c9620.png
  • 接口

好了,我们有了数据以后,要怎么样对接那插件呢?

我们先来看看插件自带百词斩词库的部分代码

#-*- coding:utf-8 -*-
import json
from ..base import *

@register([u'百词斩', u'Baicizhan'])
class Baicizhan(WebService):
    def __init__(self):
        super(Baicizhan, self).__init__()

    def _get_from_api(self):
        url = u"http://mall.baicizhan.com/ws/search?w={}".format(self.quote_word)
        result = {
            "img": u"",
            "mean_cn": u"",
            "tv": u"",
        }
        try:
            html = self.get_response(url, timeout=5)#urllib2.urlopen(url, timeout=5).read()
            result.update(json.loads(html))
        except:
            pass
        return self.cache_this(result)
    ...

看了一下

我们会发现他引入了from ..base import * 这应该是其中一个关键。

接下来是

@register([u'百词斩', u'Baicizhan'])
class Baicizhan(WebService):
    def __init__(self):
        super(Baicizhan, self).__init__()

    def _get_from_api(self):
        #...
        result = {
            "mean_cn": u"",
        }
        #...
        return self.cache_this(result)
    @export(u'中文释义')
    def fld_mean(self):
        return self._get_field('mean_cn')

from ..base import *:

​ 引入大量内置库,同时也包含WebService对象可作为词库基类

​ 所以我们的词库是从这里派生出来的。

@register([u'百词斩', u'Baicizhan']):

​ 词库的名称,一般是中文,英文。

cb52091f0c786498bb1710cf8fc9661b.png
@register

​ 注意:这里不要跟已有的词库一样,可能出错

class Baicizhan(WebService):
    def __init__(self):
        super(Baicizhan, self).__init__()

词库接口,需要注意的是

super(Baicizhan, self).__init__()super第一个参数需要是词库对象的名称

词库的名称不能跟已有词库一样,否则会重复加载一样的

def _get_from_api(self):
    #...
    return self.cache_this(result)

这个_get_from_api函数名称和参数不要动,是词库的接口

在这个函数里面敲人我们的代码,然后通过self.cache_this()返回

self.cache_this()

将我们输出的dict赋值给对象的self.cache[self.word]

@export(u'中文释义')
def fld_mean(self):
    return self._get_field('mean_cn')

5f6198f425b9812b7c1a08fe0512aa81.png
@export

注册该词库的功能之一

@export(u'中文释义'):该功能的名称

def fld_mean(self): 函数名称

self._get_field('mean_cn')获取我们之前在_get_from_apiresult['mean_cn']的内容。

​ 注意类型与原有保持一致。是string就是string,是list就是list

  • 对接

好了,这里就讲得差不多了,那么我们如何对接自己的词库呢?

我们需要引入from ..base import *class的内容写进去

Weblio_English-Text.py

import requests
from bs4 import BeautifulSoup as bs4
from ..base import * #对接

def WeblioSearch_English(word):
    result={
        'mean':u'', 
    }
    try:
        url=u'https://ejje.weblio.jp/content/{word}'.format(word=word)
        get_requests=requests.get(url,timeout=5)#设置超时
        soup=bs4(get_requests.content,'html.parser')
    except:
        return result
    result['mean']=soup.find('td',
        attrs={'class':['content-explanation je','content-explanation ej']}).text #主要意思
    result.update()
    return result
@register([u'Weblio-英日', u'Weblio-us'])#词库名称
class Weblio_English(WebService):#接口名称
    def __init__(self):
        super(Weblio_English, self).__init__()#接口名称保持一致
    def _get_from_api(self):
        result=WeblioSearch_English(self.word)#获取dict
        return self.cache_this(result)

    @export('意思')#功能名称
    def mean_(self):#功能函数
        return self._get_field('mean')

到这里,我们的词库已经写完了。

我们需要将自己的词库放到插件里面去。

那么放在哪里呢?

我们需要将该文件Weblio_English-Text.py放入%APPDATA%Anki2addons211807206748servicedict文件夹里

你也可以通过find_dict.py找到这个文件夹

find_dict.py:

from aqt.winpaths import get_appdata
import os
ret=os.path.join(get_appdata(), "Anki2","addons21",'1807206748','service','dict')
#获取Anki的Fast Words Query插件dict位置
print(ret)
  • 展示

05e45f2d66f5c7919957c42b3416312d.png
@register

60a00530225683c31d13f2506d732e07.png

0cd725059f8d85bf0c897672291d8ef0.png

总结

通过给Fast Words Query添加词库,学到很多知识。

我以前有计划要学爬虫,但一直没有付出行动。

通过这次机会学习了requests,BeautifulSoup和一些网页结构知识。

  • 如果插件崩溃了,在Anki里找不到,可能是你代码出现严重错误
  • 如果没有输出不了内容,可能是result返回正常,但是在@export(string)下面的功能函数里面有写错的地方
  • 没有设置超时,网络延迟情况下会导致Anki卡死
  • 每一次测试都需要重开Anki

扩展

由于是扩展内容,就不做详细解释

导入媒体文件

可以找共同点

  • 音频
@export('单词发音')
def word_audio(self):
    tts_url=self._get_field('tts')#取tts_url 地址
    audio_name = get_hex_name(self.unique.lower(), url, 'mp3')#文件名称
    if os.path.exists(audio_name) or self.download(tts_url, audio_name, 5):
        #判断是否存在 或者 是否写入成功
        with open(audio_name, 'rb') as f:
            if f.read().strip() == '{"error":"Document not found"}':
                res = ''
            else:
                res = self.get_anki_label(audio_name, 'audio') #返回符合Anki音频的代码
        if not res:
            os.remove(audio_name)
    return res
  • 图片
@export('图片')
def word_img(self):
    url = self._get_field('img')#取img_url 地址
    if url and self.bcz_download_img:
        filename = url[url.rindex('/') + 1:]
        if os.path.exists(filename) or self.download(url, filename):
            return self.get_anki_label(filename, 'img')
    return ''
  • 视频
@export(u'单词tv')
def word_tv(self):
    video = self._get_field('tv')
    if video:
        return self.get_anki_label(video, 'video')
    return ''

使用CSS文件

Moji-fast.py:

e326f2d8416e61d015ddd33a6ccf078f.png
@with_styles(cssfile="_moji.css", need_wrap_css=False,
    wrap_class='mojidict-helper-card-container')
def _css(self, val):
    return val
@export('单词释义[简]')
def mean_simple(self):
    words=self._get_field('words')
    ret='''<div class="mojidict-helper-card"><div class="word-detail-container">'''
    for word in words:
        if word['spell']==self.word or word['pron']==self.word:
            word_Part_of_speech='['+''.join(re.findall(r'[(.*?)]',
                word['excerpt']))+']<br>'#词性
            word_val=re.sub(r"[(.*?)]", "",word['excerpt']).split()#分割
            word_text=''
            for text in word_val:
                word_text+=text+'<br>'
            word_text.rstrip('<br>')#去除末尾换行符
            word_text= word_Part_of_speech+word_text #词性+释义
            w='''<div class="word-detail"><span class="detail-title">{pron}</span>
            <p>{excerpt}</p></div>'''.format(pron=word['pron'],excerpt=word_text)
            ret+=w
    ret=ret+'</div></div>'
    return self._css(ret)

Github​github.com

提供

  • 日语词库服务
  • 文章涉及的代码
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值