Work on remote API
This commit is contained in:
parent
820348f7c2
commit
6e7938a93c
@ -29,14 +29,14 @@ class AjaxRequest:
|
||||
|
||||
|
||||
class AjaxClient:
|
||||
def __init__(self, sock, callback):
|
||||
def __init__(self, sock, handler):
|
||||
self.sock = sock
|
||||
self.callback = callback
|
||||
self.readBuff = ''
|
||||
self.handler = handler
|
||||
self.readBuff = ''
|
||||
self.writeBuff = ''
|
||||
|
||||
|
||||
def advance(self, recvSize=1):
|
||||
def advance(self, recvSize=1024):
|
||||
if self.sock is None:
|
||||
return False
|
||||
|
||||
@ -53,12 +53,12 @@ class AjaxClient:
|
||||
req, length = self.parseRequest(self.readBuff)
|
||||
if req is not None:
|
||||
self.readBuff = self.readBuff[length:]
|
||||
self.readBuff += self.callback(req)
|
||||
self.writeBuff += self.handler(req)
|
||||
|
||||
if wlist and self.readBuff:
|
||||
length = self.sock.send(self.readBuff)
|
||||
self.readBuff = self.readBuff[length:]
|
||||
if not self.readBuff:
|
||||
if wlist and self.writeBuff:
|
||||
length = self.sock.send(self.writeBuff)
|
||||
self.writeBuff = self.writeBuff[length:]
|
||||
if not self.writeBuff:
|
||||
self.close()
|
||||
return False
|
||||
|
||||
@ -71,7 +71,7 @@ class AjaxClient:
|
||||
self.sock = None
|
||||
|
||||
self.readBuff = ''
|
||||
self.readBuff = ''
|
||||
self.writeBuff = ''
|
||||
|
||||
|
||||
def parseRequest(self, data):
|
||||
@ -96,8 +96,8 @@ class AjaxClient:
|
||||
|
||||
|
||||
class AjaxServer:
|
||||
def __init__(self, callback):
|
||||
self.callback = callback
|
||||
def __init__(self, handler):
|
||||
self.handler = handler
|
||||
self.clients = []
|
||||
self.sock = None
|
||||
|
||||
@ -116,7 +116,7 @@ class AjaxServer:
|
||||
clientSock = self.sock.accept()[0]
|
||||
if clientSock is not None:
|
||||
clientSock.setblocking(False)
|
||||
self.clients.append(AjaxClient(clientSock, self.callbackWrapper))
|
||||
self.clients.append(AjaxClient(clientSock, self.handlerWrapper))
|
||||
|
||||
|
||||
def advanceClients(self):
|
||||
@ -133,8 +133,8 @@ class AjaxServer:
|
||||
self.sock.listen(backlog)
|
||||
|
||||
|
||||
def callbackWrapper(self, req):
|
||||
body = json.dumps(self.callback(json.loads(req.body)))
|
||||
def handlerWrapper(self, req):
|
||||
body = json.dumps(self.handler(json.loads(req.body)))
|
||||
resp = ''
|
||||
|
||||
headers = {
|
||||
|
@ -21,7 +21,7 @@ import aqt
|
||||
|
||||
|
||||
class Anki:
|
||||
def addNote(self, deckName, modelName, fields, tags=list()):
|
||||
def addNote(self, deckName, modelName, fields, tags=[]):
|
||||
note = self.createNote(deckName, modelName, fields, tags)
|
||||
if note is not None:
|
||||
collection = self.collection()
|
||||
@ -35,7 +35,7 @@ class Anki:
|
||||
return bool(self.createNote(deckName, modelName, fields))
|
||||
|
||||
|
||||
def createNote(self, deckName, modelName, fields, tags=list()):
|
||||
def createNote(self, deckName, modelName, fields, tags=[]):
|
||||
model = self.models().byName(modelName)
|
||||
if model is None:
|
||||
return None
|
||||
|
@ -31,14 +31,14 @@ class MainWindowReader(QtGui.QMainWindow, gen.reader_ui.Ui_MainWindowReader):
|
||||
class State:
|
||||
def __init__(self):
|
||||
self.filename = unicode()
|
||||
self.kanjiDefs = list()
|
||||
self.kanjiDefs = []
|
||||
self.scanPosition = 0
|
||||
self.searchPosition = 0
|
||||
self.searchText = unicode()
|
||||
self.vocabDefs = list()
|
||||
self.vocabDefs = []
|
||||
|
||||
|
||||
def __init__(self, parent, preferences, language, filename=None, anki=None, closed=None):
|
||||
def __init__(self, parent, preferences, language, filename=None, anki=None, remoteApi=None, closed=None):
|
||||
QtGui.QMainWindow.__init__(self, parent)
|
||||
self.setupUi(self)
|
||||
|
||||
@ -46,8 +46,9 @@ class MainWindowReader(QtGui.QMainWindow, gen.reader_ui.Ui_MainWindowReader):
|
||||
self.textContent.mousePressEvent = self.onContentMousePress
|
||||
self.dockAnki.setEnabled(anki is not None)
|
||||
|
||||
self.facts = list()
|
||||
self.facts = []
|
||||
self.anki = anki
|
||||
self.remoteApi = remoteApi
|
||||
self.closed = closed
|
||||
self.language = language
|
||||
self.preferences = preferences
|
||||
@ -103,6 +104,9 @@ class MainWindowReader(QtGui.QMainWindow, gen.reader_ui.Ui_MainWindowReader):
|
||||
if self.preferences['windowSize'] is not None:
|
||||
self.resize(QtCore.QSize(*self.preferences['windowSize']))
|
||||
|
||||
if self.remoteApi is not None:
|
||||
self.remoteApi.enable(self.preferences['enableRemoteApi'])
|
||||
|
||||
self.comboTags.addItems(self.preferences['tags'])
|
||||
self.applyPreferencesContent()
|
||||
|
||||
@ -587,8 +591,8 @@ class MainWindowReader(QtGui.QMainWindow, gen.reader_ui.Ui_MainWindowReader):
|
||||
|
||||
|
||||
def importWordList(self, words):
|
||||
self.state.vocabDefs = list()
|
||||
self.state.kanjiDefs = list()
|
||||
self.state.vocabDefs = []
|
||||
self.state.kanjiDefs = []
|
||||
|
||||
for word in words:
|
||||
if self.dockVocab.isVisible():
|
||||
|
80
yomi_base/remote_api.py
Normal file
80
yomi_base/remote_api.py
Normal file
@ -0,0 +1,80 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
# Copyright (C) 2016 Alex Yatskov <alex@foosoft.net>
|
||||
# Author: Alex Yatskov <alex@foosoft.net>
|
||||
#
|
||||
# This program is free software: you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation, either version 3 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
|
||||
from PyQt4 import QtCore
|
||||
from ajax import AjaxServer
|
||||
import constants
|
||||
|
||||
|
||||
class RemoteApi:
|
||||
def __init__(self, anki, enabled, interval=50):
|
||||
self.server = None
|
||||
self.enable(enabled)
|
||||
self.timer = QtCore.QTimer()
|
||||
self.timer.timeout.connect(self.advance)
|
||||
self.timer.start(interval)
|
||||
|
||||
self.handlers = {
|
||||
'addNote': self.apiAddNote,
|
||||
'apiCanAddNote': self.apiCanAddNote,
|
||||
'getVersion': self.apiGetVersion,
|
||||
}
|
||||
|
||||
|
||||
def enable(self, enabled=True):
|
||||
if self.server is None and enabled:
|
||||
self.server = AjaxServer(self.handler)
|
||||
self.server.listen()
|
||||
elif self.server is not None and not enabled:
|
||||
self.server.close()
|
||||
self.server = None
|
||||
|
||||
|
||||
def advance(self):
|
||||
if self.server is not None:
|
||||
self.server.advance()
|
||||
|
||||
|
||||
def handler(self, request):
|
||||
self.handlers.get(request.get('action'), self.apiInvalidRequest)(request.get('data'))
|
||||
|
||||
|
||||
def apiAddNote(self, data):
|
||||
deckName = data.get('deckName', unicode())
|
||||
modelName = data.get('modelName', unicode())
|
||||
fields = data.get('fields', {})
|
||||
tags = data.get('tags', [])
|
||||
|
||||
return self.anki.addNote(deckName, modelName, fields, tags)
|
||||
|
||||
|
||||
def apiCanAddNote(self, data):
|
||||
deckName = data.get('deckName', unicode())
|
||||
modelName = data.get('modelName', unicode())
|
||||
fields = data.get('fields', {})
|
||||
|
||||
return self.anki.canAddNote(deckName, modelName, fields)
|
||||
|
||||
|
||||
def apiGetVersion(self, data):
|
||||
return {'version': constants.c['appVersion']}
|
||||
|
||||
|
||||
def apiInvalidRequest(self, data):
|
||||
return {}
|
@ -17,10 +17,11 @@
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
|
||||
from PyQt4 import QtGui, QtCore
|
||||
from PyQt4 import QtGui
|
||||
from yomi_base import japanese
|
||||
from yomi_base.preference_data import Preferences
|
||||
from yomi_base.reader import MainWindowReader
|
||||
from yomi_base.remote_api import RemoteApi
|
||||
import sys
|
||||
|
||||
|
||||
@ -39,6 +40,7 @@ class YomichanPlugin(Yomichan):
|
||||
self.window = None
|
||||
self.anki = anki_bridge.Anki()
|
||||
self.parent = self.anki.window()
|
||||
self.remoteApi = RemoteApi(self.anki, self.preferences['enableRemoteApi'])
|
||||
|
||||
separator = QtGui.QAction(self.parent)
|
||||
separator.setSeparator(True)
|
||||
@ -62,6 +64,7 @@ class YomichanPlugin(Yomichan):
|
||||
self.language,
|
||||
None,
|
||||
self.anki,
|
||||
self.remoteApi,
|
||||
self.onWindowClose
|
||||
)
|
||||
self.window.show()
|
||||
|
Loading…
Reference in New Issue
Block a user