Add conversation mode script

Start to tackle #4.
This commit is contained in:
Lucas Verney 2016-10-07 04:29:33 +02:00
parent 741a021ef5
commit a5c9039fee
13 changed files with 137 additions and 8 deletions

View File

@ -51,6 +51,31 @@ Note: You can specify the host and port to listen on using the
`COZYWEBOOB_HOST` and `COZYWEBOOB_PORT` environment variables.
## Conversation script
There is another command-line script available if you would rather communicate
with it in a conversation manner, using `stdin` and `stdout` (typically to
integrate it with Node modules using
[Python-shell](https://github.com/extrabacon/python-shell)). To run it, use:
```bash
./stdin_conversation.py
```
Then, you can write on `stdin` and fetch the responses from `stdout`.
Available commands are:
* `GET /list` to list all available modules.
* `GET /fetch JSON_PARAMS` where `JSON_PARAMS` is an input JSON for module
parameters.
* `exit` to quit the script and end the conversation.
JSON responses are the same one as from the HTTP server script. It is
basically the same script without HTTP encapsulation.
_Note_: To simplify the script, note that it only supports single line
commands. Then, your `JSON_PARAMS` should be the same single `stdin` line as
the `GET /fetch` part.
## Notes concerning all the available scripts
Using `COZYWEBOOB_ENV=debug`, you can enable debug features for all of these

2
cozyweboob/__init__.py Normal file
View File

@ -0,0 +1,2 @@
from .cozyweboob import WeboobProxy, main_fetch, main
__all__ = ["WeboobProxy", "main_fetch", "main"]

View File

@ -27,7 +27,7 @@ import tools.weboob_tools as weboob_tools
# Dynamically load capabilities conversion modules
# Dynamic loading is required to be able to call them programatically.
CAPABILITIES_CONVERSION_MODULES = importlib.import_module("capabilities")
CAPABILITIES_CONVERSION_MODULES = importlib.import_module("cozyweboob.capabilities")
# Module specific logger
logger = logging.getLogger(__name__)

View File

@ -9,17 +9,17 @@ from bottle import post, request, response, route, run
from cozyweboob import main as cozyweboob
from cozyweboob import WeboobProxy
from tools.env import is_in_debug_mode
from tools.jsonwriter import pretty_json
from cozyweboob.tools.env import is_in_debug_mode
from cozyweboob.tools.jsonwriter import pretty_json
# Module specific logger
logger = logging.getLogger(__name__)
@post("/")
def index():
@post("/fetch")
def fetch_view():
"""
Main view, fetch from weboob modules.
Fetch from weboob modules.
"""
params = request.forms.get("params")
response.content_type = "application/json"
@ -36,9 +36,9 @@ def list_view():
return pretty_json(proxy.list_modules())
def main():
def init():
"""
Main function
Init function
"""
# Debug only: Set logging level and format
if is_in_debug_mode():
@ -52,6 +52,13 @@ def main():
proxy = WeboobProxy()
proxy.install_modules()
logger.info("Starting server.")
def main():
"""
Main function
"""
init()
# Get host to listen on
HOST = os.environ.get("COZYWEBOOB_HOST", "localhost")
PORT = os.environ.get("COZYWEBOOB_PORT", 8080)

95
stdin_conversation.py Executable file
View File

@ -0,0 +1,95 @@
#!/usr/bin/env python2
"""
Wrapper around weboob to be called from mode, in a conversation way, similar to
the
[Python-shell](https://github.com/Birch-san/python-shell/blob/9d8641dc1e55e808ba82d029f9920413ab63206f/test/python/conversation.py)
conversation example.
"""
import logging
import sys
from cozyweboob import main as cozyweboob
from cozyweboob import WeboobProxy
from cozyweboob.tools.env import is_in_debug_mode
from cozyweboob.tools.jsonwriter import pretty_json
# Module specific logger
logger = logging.getLogger(__name__)
def fetch_view(params):
"""
Fetch from weboob modules.
"""
return pretty_json(cozyweboob(params))
def list_view():
"""
List all available weboob modules and their configuration options.
"""
proxy = WeboobProxy()
return pretty_json(proxy.list_modules())
def process_query(query):
"""
Process input query on the command-line.
Args:
query: The query received on stdin.
Returns:
- A JSON response if a valid query is received.
- False if should exit.
- None if invalid query is received.
"""
query = query.strip()
if query == "GET /list":
# List modules view
logger.info("Calling /list view.")
return list_view()
elif query.startswith("GET /fetch"):
# Fetch modules view
logger.info("Calling /list view.")
params = query.split()[2]
return fetch_view(params)
elif query == "exit":
# Exit command
logger.info("Exiting.")
return False
else:
# Invalid query
logger.error("Invalid query, exiting: %s" % query)
return
def main():
"""
Main function
"""
# Debug only: Set logging level and format
if is_in_debug_mode():
logging.basicConfig(
format='%(levelname)s: %(message)s',
level=logging.INFO
)
# Ensure all modules are installed and up to date before starting the
# server
logger.info("Ensuring all modules are installed and up to date.")
proxy = WeboobProxy()
proxy.install_modules()
logger.info("Starting server.")
while True:
line = sys.stdin.readline()
if not line:
break
response = process_query(line)
if response:
print(response)
else:
break
sys.stdout.flush()
if __name__ == "__main__":
main()