From 962e0d2e412306ac171c936bbb71c63e9bfe8389 Mon Sep 17 00:00:00 2001 From: Yax Date: Sat, 2 Jan 2021 12:36:42 +0100 Subject: [PATCH] object-oriented and DI --- config.ini | 4 +- run.py | 67 +++++++++++++++--------------- stacosys/core/database.py | 33 ++++++++++----- stacosys/core/rss.py | 83 ++++++++++++++++++++------------------ stacosys/core/templater.py | 6 +-- stacosys/model/comment.py | 18 ++++----- stacosys/model/site.py | 7 +--- 7 files changed, 114 insertions(+), 104 deletions(-) diff --git a/config.ini b/config.ini index 8d7b7e2..9a7cfab 100755 --- a/config.ini +++ b/config.ini @@ -2,9 +2,9 @@ ; Default configuration [main] lang = fr -db_url = sqlite:///db.sqlite +db_url = db.sqlite +db_backup_json_file = db.json newcomment_polling = 60 -db_file = db.json [site] name = "My blog" diff --git a/run.py b/run.py index 6fd1a19..5958b8b 100644 --- a/run.py +++ b/run.py @@ -4,12 +4,16 @@ import argparse import logging import os +import sys from flask import Flask from flask_apscheduler import APScheduler -from stacosys.conf import config - +import stacosys.conf.config as config +from stacosys.core import database +from stacosys.core import rss +#from stacosys.interface import api +#from stacosys.interface import form # configure logging def configure_logging(level): @@ -18,7 +22,7 @@ def configure_logging(level): ch = logging.StreamHandler() ch.setLevel(level) # create formatter - formatter = logging.Formatter('[%(asctime)s] %(name)s %(levelname)s %(message)s') + formatter = logging.Formatter("[%(asctime)s] %(name)s %(levelname)s %(message)s") # add formatter to ch ch.setFormatter(formatter) # add ch to logger @@ -29,21 +33,21 @@ class JobConfig(object): JOBS = [] - SCHEDULER_EXECUTORS = {'default': {'type': 'threadpool', 'max_workers': 4}} + SCHEDULER_EXECUTORS = {"default": {"type": "threadpool", "max_workers": 4}} def __init__(self, imap_polling_seconds, new_comment_polling_seconds): self.JOBS = [ { - 'id': 'fetch_mail', - 'func': 'stacosys.core.cron:fetch_mail_answers', - 'trigger': 'interval', - 'seconds': imap_polling_seconds, + "id": "fetch_mail", + "func": "stacosys.core.cron:fetch_mail_answers", + "trigger": "interval", + "seconds": imap_polling_seconds, }, { - 'id': 'submit_new_comment', - 'func': 'stacosys.core.cron:submit_new_comment', - 'trigger': 'interval', - 'seconds': new_comment_polling_seconds, + "id": "submit_new_comment", + "func": "stacosys.core.cron:submit_new_comment", + "trigger": "interval", + "seconds": new_comment_polling_seconds, }, ] @@ -51,56 +55,49 @@ class JobConfig(object): def stacosys_server(config_pathname): app = Flask(__name__) - config.initialize(config_pathname, app) + + conf = config.Config.load(config_pathname) # configure logging logger = logging.getLogger(__name__) configure_logging(logging.INFO) - logging.getLogger('werkzeug').level = logging.WARNING - logging.getLogger('apscheduler.executors').level = logging.WARNING + logging.getLogger("werkzeug").level = logging.WARNING + logging.getLogger("apscheduler.executors").level = logging.WARNING # initialize database - from stacosys.core import database + db = database.Database() + db.setup(conf.get(config.DB_URL)) - database.setup() - database.dump_db() - # cron email fetcher app.config.from_object( JobConfig( - config.get_int(config.IMAP_POLLING), config.get_int(config.COMMENT_POLLING) + conf.get_int(config.IMAP_POLLING), conf.get_int(config.COMMENT_POLLING) ) ) scheduler = APScheduler() scheduler.init_app(app) scheduler.start() - logger.info('Start Stacosys application') + logger.info("Start Stacosys application") # generate RSS for all sites - from stacosys.core import rss - - rss.generate_all() + rss_manager = rss.Rss(conf.get(config.LANG), conf.get(config.RSS_FILE), conf.get(config.RSS_PROTO)) + rss_manager.generate_all() # start Flask - from stacosys.interface import api - - logger.info('Load interface %s' % api) - - from stacosys.interface import form - - logger.info('Load interface %s' % form) + #logger.info("Load interface %s" % api) + #logger.info("Load interface %s" % form) app.run( - host=config.get(config.HTTP_HOST), - port=config.get(config.HTTP_PORT), + host=conf.get(config.HTTP_HOST), + port=conf.get(config.HTTP_PORT), debug=False, use_reloader=False, ) -if __name__ == '__main__': +if __name__ == "__main__": parser = argparse.ArgumentParser() - parser.add_argument('config', help='config path name') + parser.add_argument("config", help="config path name") args = parser.parse_args() stacosys_server(args.config) diff --git a/stacosys/core/database.py b/stacosys/core/database.py index dbce608..b70b1dd 100644 --- a/stacosys/core/database.py +++ b/stacosys/core/database.py @@ -2,23 +2,37 @@ # -*- coding: UTF-8 -*- import json -from playhouse.db_url import connect +from peewee import DatabaseProxy, Model +from playhouse.db_url import connect, SqliteDatabase from playhouse.shortcuts import model_to_dict from tinydb import TinyDB from stacosys.conf import config +db = SqliteDatabase(None) -def get_db(): - return connect(config.get(config.DB_URL)) +class BaseModel(Model): + class Meta: + database = db -def setup(): - from stacosys.model.site import Site - from stacosys.model.comment import Comment - get_db().create_tables([Site, Comment], safe=True) - if config.exists(config.DB_BACKUP_JSON_FILE): - _backup_db(config.DB_BACKUP_JSON_FILE, Comment) +class Database: + def get_db(self): + return db + + def setup(self, db_url): + + db.init(db_url) + db.connect() + + from stacosys.model.site import Site + from stacosys.model.comment import Comment + + db.create_tables([Site, Comment], safe=True) + + +# if config.exists(config.DB_BACKUP_JSON_FILE): +# _backup_db(config.DB_BACKUP_JSON_FILE, Comment) def _tojson_model(comment): @@ -35,3 +49,4 @@ def _backup_db(db_file, Comment): for comment in Comment.select(): cc = _tojson_model(comment) table.insert(cc) + diff --git a/stacosys/core/rss.py b/stacosys/core/rss.py index a6c3c5d..d333772 100644 --- a/stacosys/core/rss.py +++ b/stacosys/core/rss.py @@ -6,49 +6,54 @@ from datetime import datetime import markdown import PyRSS2Gen -from stacosys.conf import config +import stacosys.conf.config as config from stacosys.core.templater import get_template from stacosys.model.comment import Comment from stacosys.model.site import Site -def generate_all(): - - for site in Site.select(): - generate_site(site.token) - - -def generate_site(token): - - site = Site.select().where(Site.token == token).get() - rss_title = get_template('rss_title_message').render(site=site.name) - md = markdown.Markdown() - - items = [] - for row in ( - Comment.select() - .join(Site) - .where(Site.token == token, Comment.published) - .order_by(-Comment.published) - .limit(10) - ): - item_link = '%s://%s%s' % (config.get(config.RSS_PROTO), site.url, row.url) - items.append( - PyRSS2Gen.RSSItem( - title='%s - %s://%s%s' - % (config.get(config.RSS_PROTO), row.author_name, site.url, row.url), - link=item_link, - description=md.convert(row.content), - guid=PyRSS2Gen.Guid('%s/%d' % (item_link, row.id)), - pubDate=row.published, +class Rss: + def __init__(self, lang, rss_file, rss_proto): + self._lang = lang + self._rss_file = rss_file + self._rss_proto = rss_proto + + def generate_all(self): + + for site in Site.select(): + self._generate_site(site.token) + + def _generate_site(self, token): + + site = Site.select().where(Site.token == token).get() + rss_title = get_template(self._lang, "rss_title_message").render(site=site.name) + md = markdown.Markdown() + + items = [] + for row in ( + Comment.select() + .join(Site) + .where(Site.token == token, Comment.published) + .order_by(-Comment.published) + .limit(10) + ): + item_link = "%s://%s%s" % (self._rss_proto, site.url, row.url) + items.append( + PyRSS2Gen.RSSItem( + title="%s - %s://%s%s" + % (self._rss_proto, row.author_name, site.url, row.url), + link=item_link, + description=md.convert(row.content), + guid=PyRSS2Gen.Guid("%s/%d" % (item_link, row.id)), + pubDate=row.published, + ) ) - ) - rss = PyRSS2Gen.RSS2( - title=rss_title, - link='%s://%s' % (config.get(config.RSS_PROTO), site.url), - description='Commentaires du site "%s"' % site.name, - lastBuildDate=datetime.now(), - items=items, - ) - rss.write_xml(open(config.get(config.RSS_FILE), 'w'), encoding='utf-8') + rss = PyRSS2Gen.RSS2( + title=rss_title, + link="%s://%s" % (self._rss_proto, site.url), + description='Commentaires du site "%s"' % site.name, + lastBuildDate=datetime.now(), + items=items, + ) + rss.write_xml(open(self._rss_file, "w"), encoding="utf-8") diff --git a/stacosys/core/templater.py b/stacosys/core/templater.py index ca7b210..9f2d328 100644 --- a/stacosys/core/templater.py +++ b/stacosys/core/templater.py @@ -8,9 +8,9 @@ from jinja2 import Environment, FileSystemLoader from stacosys.conf import config current_path = os.path.dirname(__file__) -template_path = os.path.abspath(os.path.join(current_path, '../templates')) +template_path = os.path.abspath(os.path.join(current_path, "../templates")) env = Environment(loader=FileSystemLoader(template_path)) -def get_template(name): - return env.get_template(config.get(config.LANG) + '/' + name + '.tpl') +def get_template(lang, name): + return env.get_template(lang + "/" + name + ".tpl") diff --git a/stacosys/model/comment.py b/stacosys/model/comment.py index 1ebbfad..9493538 100644 --- a/stacosys/model/comment.py +++ b/stacosys/model/comment.py @@ -7,28 +7,24 @@ from peewee import TextField from peewee import DateTimeField from peewee import ForeignKeyField from stacosys.model.site import Site -from stacosys.core.database import get_db from datetime import datetime +from stacosys.core.database import BaseModel - -class Comment(Model): +class Comment(BaseModel): url = CharField() created = DateTimeField() notified = DateTimeField(null=True, default=None) published = DateTimeField(null=True, default=None) author_name = CharField() - author_site = CharField(default='') - author_gravatar = CharField(default='') + author_site = CharField(default="") + author_gravatar = CharField(default="") content = TextField() - site = ForeignKeyField(Site, related_name='site') - - class Meta: - database = get_db() + site = ForeignKeyField(Site, related_name="site") def notify_site_admin(self): - self.notified = datetime.now().strftime('%Y-%m-%d %H:%M:%S') + self.notified = datetime.now().strftime("%Y-%m-%d %H:%M:%S") self.save() def publish(self): - self.published = datetime.now().strftime('%Y-%m-%d %H:%M:%S') + self.published = datetime.now().strftime("%Y-%m-%d %H:%M:%S") self.save() diff --git a/stacosys/model/site.py b/stacosys/model/site.py index bbd6091..b2f4e9b 100644 --- a/stacosys/model/site.py +++ b/stacosys/model/site.py @@ -3,14 +3,11 @@ from peewee import Model from peewee import CharField -from stacosys.core.database import get_db +from stacosys.core.database import BaseModel -class Site(Model): +class Site(BaseModel): name = CharField(unique=True) url = CharField() token = CharField() admin_email = CharField() - - class Meta: - database = get_db()