From 4e87c73a0136decb30fc7f2befdea127364dfe89 Mon Sep 17 00:00:00 2001 From: Lance Edgar Date: Thu, 14 Jun 2012 14:39:55 -0500 Subject: [PATCH 01/19] update changes file --- CHANGES.txt | 14 +++++++++++++- 1 file changed, 13 insertions(+), 1 deletion(-) diff --git a/CHANGES.txt b/CHANGES.txt index fbe7946..11224dc 100644 --- a/CHANGES.txt +++ b/CHANGES.txt @@ -2,4 +2,16 @@ 0.1a1 ----- -- Initial version +- Initial version + +0.1a2 +----- + +- Add ``win32.send_data_to_printer()`` function. + +- Various tweaks to Pyramid code. + +0.1a3 +----- + +- Various tweaks to Pyramid code. From fb0240005cb435ebb32a950ca6a1cfddabca4c89 Mon Sep 17 00:00:00 2001 From: Lance Edgar Date: Thu, 14 Jun 2012 14:41:16 -0500 Subject: [PATCH 03/19] bump version --- edbob/_version.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/edbob/_version.py b/edbob/_version.py index ce39c68..c093203 100644 --- a/edbob/_version.py +++ b/edbob/_version.py @@ -1 +1 @@ -__version__ = '0.1a3' +__version__ = '0.1a4' From 135f0531ec1b641bd4880e8ec9a9fc1cd4fc4903 Mon Sep 17 00:00:00 2001 From: Lance Edgar Date: Sat, 16 Jun 2012 21:24:37 -0500 Subject: [PATCH 04/19] fix alembic version comment --- setup.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/setup.py b/setup.py index a18574d..75dff85 100644 --- a/setup.py +++ b/setup.py @@ -121,7 +121,7 @@ setup( # # package # low high - 'alembic', # 0.2.1 + 'alembic', # 0.3.4 'py-bcrypt', # 0.2 'SQLAlchemy', # 0.7.6 'Tempita', # 0.5.1 From 2e447db219ce45b53b2d749eb3617ac28bd9cf14 Mon Sep 17 00:00:00 2001 From: Lance Edgar Date: Tue, 19 Jun 2012 19:43:07 -0500 Subject: [PATCH 05/19] fixed sleep() call in filemone service --- edbob/filemon_server.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/edbob/filemon_server.py b/edbob/filemon_server.py index 881c7b1..8071a51 100644 --- a/edbob/filemon_server.py +++ b/edbob/filemon_server.py @@ -109,7 +109,7 @@ class FileMonitorService(win32serviceutil.ServiceFramework): while not file_is_free(path): # TODO: Add configurable timeout so long-open files can't hijack # our prcessing. - time.sleep(0.25) + win32api.SleepEx(250, True) for action in self.monitored[key].actions: if isinstance(action, tuple): func = action[0] From 8c3239edf1f9fa8c984d03a0236586b53a9e4965 Mon Sep 17 00:00:00 2001 From: Lance Edgar Date: Tue, 19 Jun 2012 19:46:39 -0500 Subject: [PATCH 07/19] bump version --- edbob/_version.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/edbob/_version.py b/edbob/_version.py index c093203..27dc911 100644 --- a/edbob/_version.py +++ b/edbob/_version.py @@ -1 +1 @@ -__version__ = '0.1a4' +__version__ = '0.1a5' From 5710acb6f5c17e5b4767bf4b6d560161ff1b7090 Mon Sep 17 00:00:00 2001 From: Lance Edgar Date: Sat, 23 Jun 2012 16:59:46 -0500 Subject: [PATCH 08/19] add csv module --- edbob/csv.py | 71 ++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 71 insertions(+) create mode 100644 edbob/csv.py diff --git a/edbob/csv.py b/edbob/csv.py new file mode 100644 index 0000000..77518c9 --- /dev/null +++ b/edbob/csv.py @@ -0,0 +1,71 @@ +#!/usr/bin/env python +# -*- coding: utf-8 -*- +################################################################################ +# +# edbob -- Pythonic Software Framework +# Copyright © 2010-2012 Lance Edgar +# +# This file is part of edbob. +# +# edbob is free software: you can redistribute it and/or modify it under the +# terms of the GNU Affero General Public License as published by the Free +# Software Foundation, either version 3 of the License, or (at your option) +# any later version. +# +# edbob 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 Affero General Public License for +# more details. +# +# You should have received a copy of the GNU Affero General Public License +# along with edbob. If not, see . +# +################################################################################ + +""" +``edbob.csv`` -- CSV File Utilities +""" + +from __future__ import absolute_import + +import codecs +import csv + + +class UTF8Recoder(object): + """ + Iterator that reads an encoded stream and reencodes the input to UTF-8. + + .. note:: + This class was stolen from the Python 2.7 documentation. + """ + + def __init__(self, fileobj, encoding): + self.reader = codecs.getreader(encoding)(fileobj) + + def __iter__(self): + return self + + def next(self): + return self.reader.next().encode('utf_8') + + +class UnicodeReader(object): + """ + A CSV reader which will iterate over lines in a CSV file, which is encoded + in the given encoding. + + .. note:: + This class was stolen from the Python 2.7 documentation. + """ + + def __init__(self, fileobj, dialect=csv.excel, encoding='utf_8', **kwargs): + fileobj = UTF8Recoder(fileobj, encoding) + self.reader = csv.reader(fileobj, dialect=dialect, **kwargs) + + def __iter__(self): + return self + + def next(self): + row = self.reader.next() + return [unicode(x, 'utf_8') for x in row] From b939bc42aa9868878413d48025cf5c458b522f12 Mon Sep 17 00:00:00 2001 From: Lance Edgar Date: Sun, 8 Jul 2012 11:43:37 -0500 Subject: [PATCH 09/19] convert initialization module to unix format --- edbob/initialization.py | 196 ++++++++++++++++++++-------------------- 1 file changed, 98 insertions(+), 98 deletions(-) diff --git a/edbob/initialization.py b/edbob/initialization.py index e27c7fb..e4c8ede 100644 --- a/edbob/initialization.py +++ b/edbob/initialization.py @@ -1,98 +1,98 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- -################################################################################ -# -# edbob -- Pythonic Software Framework -# Copyright © 2010-2012 Lance Edgar -# -# This file is part of edbob. -# -# edbob is free software: you can redistribute it and/or modify it under the -# terms of the GNU Affero General Public License as published by the Free -# Software Foundation, either version 3 of the License, or (at your option) -# any later version. -# -# edbob 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 Affero General Public License for -# more details. -# -# You should have received a copy of the GNU Affero General Public License -# along with edbob. If not, see . -# -################################################################################ - -""" -``edbob.initialization`` -- Initialization Framework -""" - -import os -import logging - -import edbob -from edbob.configuration import ( - AppConfigParser, - default_system_paths, - default_user_paths, - ) - - -__all__ = ['init'] - -log = logging.getLogger(__name__) - - -def init(appname='edbob', *args, **kwargs): - """ - Initializes the edbob framework, typically by first reading some config - file(s) to determine which interfaces to engage. This must normally be - called prior to doing anything really useful, as it is responsible for - extending the live API in-place. - - The meaning of ``args`` is as follows: - - If ``args`` is empty, the ``EDBOB_CONFIG`` environment variable is first - consulted. If it is nonempty, then its value is split according to - ``os.pathsep`` and the resulting sequence is passed to - ``edbob.config.read()``. - - If both ``args`` and ``EDBOB_CONFIG`` are empty, the "standard" locations - are assumed, and the results of calling both - :func:`edbob.configuration.default_system_paths()` and - :func:`edbob.configuration.default_user_paths()` are passed on to - ``edbob.config.read()``. - - Any other values in ``args`` will be passed directly to - ``edbob.config.read()`` and so will be interpreted there. Basically they - are assumed to be either strings, or sequences of strings, which represent - paths to various config files, each being read in the order in which it - appears within ``args``. (Configuration is thereby cascaded such that the - file read last will override those before it.) - """ - - config = AppConfigParser(appname) - - if args: - config_paths = list(args) - elif os.environ.get('EDBOB_CONFIG'): - config_paths = os.environ['EDBOB_CONFIG'].split(os.pathsep) - else: - config_paths = default_system_paths(appname) + default_user_paths(appname) - - shell = bool(kwargs.get('shell')) - for paths in config_paths: - config.read(paths, recurse=not shell) - config.configure_logging() - - default_modules = 'edbob.time' - modules = config.get('edbob', 'init', default=default_modules) - if modules: - for name in modules.split(','): - name = name.strip() - module = __import__(name, globals(), locals(), fromlist=['init']) - getattr(module, 'init')(config) - # config.inited.append(name) - - # config.inited.append('edbob') - edbob.graft(edbob, locals(), 'config') - edbob.inited = True +#!/usr/bin/env python +# -*- coding: utf-8 -*- +################################################################################ +# +# edbob -- Pythonic Software Framework +# Copyright © 2010-2012 Lance Edgar +# +# This file is part of edbob. +# +# edbob is free software: you can redistribute it and/or modify it under the +# terms of the GNU Affero General Public License as published by the Free +# Software Foundation, either version 3 of the License, or (at your option) +# any later version. +# +# edbob 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 Affero General Public License for +# more details. +# +# You should have received a copy of the GNU Affero General Public License +# along with edbob. If not, see . +# +################################################################################ + +""" +``edbob.initialization`` -- Initialization Framework +""" + +import os +import logging + +import edbob +from edbob.configuration import ( + AppConfigParser, + default_system_paths, + default_user_paths, + ) + + +__all__ = ['init'] + +log = logging.getLogger(__name__) + + +def init(appname='edbob', *args, **kwargs): + """ + Initializes the edbob framework, typically by first reading some config + file(s) to determine which interfaces to engage. This must normally be + called prior to doing anything really useful, as it is responsible for + extending the live API in-place. + + The meaning of ``args`` is as follows: + + If ``args`` is empty, the ``EDBOB_CONFIG`` environment variable is first + consulted. If it is nonempty, then its value is split according to + ``os.pathsep`` and the resulting sequence is passed to + ``edbob.config.read()``. + + If both ``args`` and ``EDBOB_CONFIG`` are empty, the "standard" locations + are assumed, and the results of calling both + :func:`edbob.configuration.default_system_paths()` and + :func:`edbob.configuration.default_user_paths()` are passed on to + ``edbob.config.read()``. + + Any other values in ``args`` will be passed directly to + ``edbob.config.read()`` and so will be interpreted there. Basically they + are assumed to be either strings, or sequences of strings, which represent + paths to various config files, each being read in the order in which it + appears within ``args``. (Configuration is thereby cascaded such that the + file read last will override those before it.) + """ + + config = AppConfigParser(appname) + + if args: + config_paths = list(args) + elif os.environ.get('EDBOB_CONFIG'): + config_paths = os.environ['EDBOB_CONFIG'].split(os.pathsep) + else: + config_paths = default_system_paths(appname) + default_user_paths(appname) + + shell = bool(kwargs.get('shell')) + for paths in config_paths: + config.read(paths, recurse=not shell) + config.configure_logging() + + default_modules = 'edbob.time' + modules = config.get('edbob', 'init', default=default_modules) + if modules: + for name in modules.split(','): + name = name.strip() + module = __import__(name, globals(), locals(), fromlist=['init']) + getattr(module, 'init')(config) + # config.inited.append(name) + + # config.inited.append('edbob') + edbob.graft(edbob, locals(), 'config') + edbob.inited = True From c371a2d9974cd219c7d87e871d88c6e1616049b1 Mon Sep 17 00:00:00 2001 From: Lance Edgar Date: Sun, 8 Jul 2012 12:07:40 -0500 Subject: [PATCH 10/19] convert db module to unix format --- edbob/db/__init__.py | 368 +++++++++++++++++++++---------------------- edbob/db/alembic.ini | 92 +++++------ 2 files changed, 230 insertions(+), 230 deletions(-) diff --git a/edbob/db/__init__.py b/edbob/db/__init__.py index 18d6888..0fd3018 100644 --- a/edbob/db/__init__.py +++ b/edbob/db/__init__.py @@ -1,184 +1,184 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- -################################################################################ -# -# edbob -- Pythonic Software Framework -# Copyright © 2010-2012 Lance Edgar -# -# This file is part of edbob. -# -# edbob is free software: you can redistribute it and/or modify it under the -# terms of the GNU Affero General Public License as published by the Free -# Software Foundation, either version 3 of the License, or (at your option) -# any later version. -# -# edbob 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 Affero General Public License for -# more details. -# -# You should have received a copy of the GNU Affero General Public License -# along with edbob. If not, see . -# -################################################################################ - -""" -``edbob.db`` -- Database Framework -""" - -from __future__ import absolute_import - -from sqlalchemy import engine_from_config, MetaData -from sqlalchemy.orm import sessionmaker -from sqlalchemy.ext.declarative import declarative_base - -import edbob - - -# __all__ = ['engines', 'engine', 'Session', 'metadata', -# 'get_setting', 'save_setting'] - -__all__ = ['engines', 'engine', 'Session', 'get_setting', 'save_setting'] - -inited = False -engines = None -engine = None -Session = sessionmaker() -Base = declarative_base() -# metadata = None - - -def init(config): - """ - Initializes the database connection(s); called by :func:`edbob.init()` if - config includes something like:: - - .. highlight:: ini - - [edbob] - init = ['edbob.db'] - - [edbob.db] - sqlalchemy.urls = { - 'default': 'postgresql://user:pass@localhost/edbob, - } - - This function reads connection info from ``config`` and builds a dictionary - or :class:`sqlalchemy.Engine` instances accordingly. It also extends the - root ``edbob`` namespace with the ORM classes (:class:`edbob.Person`, - :class:`edbob.User`, etc.), as well as a few other things - (e.g. :attr:`edbob.engine`, :attr:`edbob.Session`, :attr:`edbob.metadata`). - """ - - import edbob.db - # from edbob.db import classes - from edbob.db import model - from edbob.db import enum - # from edbob.db.model import get_metadata - # from edbob.db.mappers import make_mappers - from edbob.db.extensions import extend_framework - - # global inited, engines, engine, metadata - global inited, engines, engine - - keys = config.get('edbob.db', 'sqlalchemy.keys') - if keys: - keys = keys.split() - else: - keys = ['default'] - - engines = {} - cfg = config.get_dict('edbob.db') - for key in keys: - try: - engines[key] = engine_from_config(cfg, 'sqlalchemy.%s.' % key) - except KeyError: - if key == 'default': - try: - engines[key] = engine_from_config(cfg) - except KeyError: - pass - - engine = engines.get('default') - if engine: - Base.metadata.bind = engine - - # metadata = get_metadata(bind=engine) - # make_mappers(metadata) - extend_framework() - - edbob.graft(edbob, edbob.db) - # edbob.graft(edbob, classes) - edbob.graft(edbob, model) - edbob.graft(edbob, enum) - inited = True - - -def get_setting(name, session=None): - """ - Returns a setting from the database. - """ - - _session = session - if not session: - session = Session() - setting = session.query(edbob.Setting).get(name) - if setting: - setting = setting.value - if not _session: - session.close() - return setting - - -def save_setting(name, value, session=None): - """ - Saves a setting to the database. - """ - - _session = session - if not session: - session = Session() - setting = session.query(edbob.Setting).get(name) - if not setting: - setting = edbob.Setting(name=name) - session.add(setting) - setting.value = value - if not _session: - session.commit() - session.close() - - -def get_core_metadata(): - """ - Returns a :class:`sqlalchemy.MetaData` instance containing only those - :class:`sqlalchemy.Table`s which are part of the core ``edbob`` schema. - """ - - from edbob.db import model - - meta = MetaData() - for name in model.__all__: - if name != 'Base': - obj = getattr(model, name) - if isinstance(obj, type) and issubclass(obj, model.Base): - obj.__table__.tometadata(meta) - return meta - - -def needs_session(func): - """ - Decorator which adds helpful session handling. - """ - - def wrapped(*args, **kwargs): - session = kwargs.pop('session', None) - _orig_session = session - if not session: - session = Session() - res = func(session, *args, **kwargs) - if not _orig_session: - session.commit() - session.close() - return res - - return wrapped +#!/usr/bin/env python +# -*- coding: utf-8 -*- +################################################################################ +# +# edbob -- Pythonic Software Framework +# Copyright © 2010-2012 Lance Edgar +# +# This file is part of edbob. +# +# edbob is free software: you can redistribute it and/or modify it under the +# terms of the GNU Affero General Public License as published by the Free +# Software Foundation, either version 3 of the License, or (at your option) +# any later version. +# +# edbob 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 Affero General Public License for +# more details. +# +# You should have received a copy of the GNU Affero General Public License +# along with edbob. If not, see . +# +################################################################################ + +""" +``edbob.db`` -- Database Framework +""" + +from __future__ import absolute_import + +from sqlalchemy import engine_from_config, MetaData +from sqlalchemy.orm import sessionmaker +from sqlalchemy.ext.declarative import declarative_base + +import edbob + + +# __all__ = ['engines', 'engine', 'Session', 'metadata', +# 'get_setting', 'save_setting'] + +__all__ = ['engines', 'engine', 'Session', 'get_setting', 'save_setting'] + +inited = False +engines = None +engine = None +Session = sessionmaker() +Base = declarative_base() +# metadata = None + + +def init(config): + """ + Initializes the database connection(s); called by :func:`edbob.init()` if + config includes something like:: + + .. highlight:: ini + + [edbob] + init = ['edbob.db'] + + [edbob.db] + sqlalchemy.urls = { + 'default': 'postgresql://user:pass@localhost/edbob, + } + + This function reads connection info from ``config`` and builds a dictionary + or :class:`sqlalchemy.Engine` instances accordingly. It also extends the + root ``edbob`` namespace with the ORM classes (:class:`edbob.Person`, + :class:`edbob.User`, etc.), as well as a few other things + (e.g. :attr:`edbob.engine`, :attr:`edbob.Session`, :attr:`edbob.metadata`). + """ + + import edbob.db + # from edbob.db import classes + from edbob.db import model + from edbob.db import enum + # from edbob.db.model import get_metadata + # from edbob.db.mappers import make_mappers + from edbob.db.extensions import extend_framework + + # global inited, engines, engine, metadata + global inited, engines, engine + + keys = config.get('edbob.db', 'sqlalchemy.keys') + if keys: + keys = keys.split() + else: + keys = ['default'] + + engines = {} + cfg = config.get_dict('edbob.db') + for key in keys: + try: + engines[key] = engine_from_config(cfg, 'sqlalchemy.%s.' % key) + except KeyError: + if key == 'default': + try: + engines[key] = engine_from_config(cfg) + except KeyError: + pass + + engine = engines.get('default') + if engine: + Base.metadata.bind = engine + + # metadata = get_metadata(bind=engine) + # make_mappers(metadata) + extend_framework() + + edbob.graft(edbob, edbob.db) + # edbob.graft(edbob, classes) + edbob.graft(edbob, model) + edbob.graft(edbob, enum) + inited = True + + +def get_setting(name, session=None): + """ + Returns a setting from the database. + """ + + _session = session + if not session: + session = Session() + setting = session.query(edbob.Setting).get(name) + if setting: + setting = setting.value + if not _session: + session.close() + return setting + + +def save_setting(name, value, session=None): + """ + Saves a setting to the database. + """ + + _session = session + if not session: + session = Session() + setting = session.query(edbob.Setting).get(name) + if not setting: + setting = edbob.Setting(name=name) + session.add(setting) + setting.value = value + if not _session: + session.commit() + session.close() + + +def get_core_metadata(): + """ + Returns a :class:`sqlalchemy.MetaData` instance containing only those + :class:`sqlalchemy.Table`s which are part of the core ``edbob`` schema. + """ + + from edbob.db import model + + meta = MetaData() + for name in model.__all__: + if name != 'Base': + obj = getattr(model, name) + if isinstance(obj, type) and issubclass(obj, model.Base): + obj.__table__.tometadata(meta) + return meta + + +def needs_session(func): + """ + Decorator which adds helpful session handling. + """ + + def wrapped(*args, **kwargs): + session = kwargs.pop('session', None) + _orig_session = session + if not session: + session = Session() + res = func(session, *args, **kwargs) + if not _orig_session: + session.commit() + session.close() + return res + + return wrapped diff --git a/edbob/db/alembic.ini b/edbob/db/alembic.ini index 891ae32..0bebfc7 100644 --- a/edbob/db/alembic.ini +++ b/edbob/db/alembic.ini @@ -1,46 +1,46 @@ -# A generic, single database configuration. - -[alembic] -# path to migration scripts -script_location = schema - -# template used to generate migration files -# file_template = %%(rev)s_%%(slug)s - -sqlalchemy.url = driver://user:pass@localhost/dbname - - -# Logging configuration -[loggers] -keys = root,sqlalchemy,alembic - -[handlers] -keys = console - -[formatters] -keys = generic - -[logger_root] -level = WARN -handlers = console -qualname = - -[logger_sqlalchemy] -level = WARN -handlers = -qualname = sqlalchemy.engine - -[logger_alembic] -level = INFO -handlers = -qualname = alembic - -[handler_console] -class = StreamHandler -args = (sys.stderr,) -level = NOTSET -formatter = generic - -[formatter_generic] -format = %(levelname)-5.5s [%(name)s] %(message)s -datefmt = %H:%M:%S +# A generic, single database configuration. + +[alembic] +# path to migration scripts +script_location = schema + +# template used to generate migration files +# file_template = %%(rev)s_%%(slug)s + +sqlalchemy.url = driver://user:pass@localhost/dbname + + +# Logging configuration +[loggers] +keys = root,sqlalchemy,alembic + +[handlers] +keys = console + +[formatters] +keys = generic + +[logger_root] +level = WARN +handlers = console +qualname = + +[logger_sqlalchemy] +level = WARN +handlers = +qualname = sqlalchemy.engine + +[logger_alembic] +level = INFO +handlers = +qualname = alembic + +[handler_console] +class = StreamHandler +args = (sys.stderr,) +level = NOTSET +formatter = generic + +[formatter_generic] +format = %(levelname)-5.5s [%(name)s] %(message)s +datefmt = %H:%M:%S From bb7d234778887353487ac4096877161394f983da Mon Sep 17 00:00:00 2001 From: Lance Edgar Date: Sun, 8 Jul 2012 13:43:28 -0500 Subject: [PATCH 11/19] tweaked logging config --- edbob/configuration.py | 21 ++++++++++--------- edbob/core.py | 4 +++- .../edbob/+package+/pyramid/__init__.py_tmpl | 1 - edbob/scaffolds/edbob/development.ini_tmpl | 11 +--------- edbob/scaffolds/edbob/production.ini_tmpl | 20 ++++++------------ edbob/time.py | 2 +- 6 files changed, 22 insertions(+), 37 deletions(-) diff --git a/edbob/configuration.py b/edbob/configuration.py index e65b31e..d13613c 100644 --- a/edbob/configuration.py +++ b/edbob/configuration.py @@ -70,15 +70,17 @@ class AppConfigParser(ConfigParser.SafeConfigParser): file, and passes that to ``logging.config.fileConfig()``. """ - if self.getboolean(self.appname, 'basic_logging', default=False): - edbob.basic_logging(self.appname) - path = edbob.temp_path(suffix='.conf') - self.save(path) - try: - logging.config.fileConfig(path) - except ConfigParser.NoSectionError: - pass - os.remove(path) + if self.getboolean('edbob', 'basic_logging', default=False): + edbob.basic_logging() + if self.getboolean('edbob', 'configure_logging', default=False): + path = edbob.temp_path(suffix='.conf') + self.save(path) + try: + logging.config.fileConfig(path, disable_existing_loggers=False) + except ConfigParser.NoSectionError: + pass + os.remove(path) + log.debug("Configured logging") def get(self, section, option, raw=False, vars=None, default=None): """ @@ -243,7 +245,6 @@ class AppConfigParser(ConfigParser.SafeConfigParser): config.has_option('edbob', 'include_config')): include = config.get('edbob', 'include_config') if include: - log.debug("Including config: %s" % include) for p in eval(include): self.read_path(os.path.abspath(p)) ConfigParser.SafeConfigParser.read(self, path) diff --git a/edbob/core.py b/edbob/core.py index f100cf8..04a00ea 100644 --- a/edbob/core.py +++ b/edbob/core.py @@ -71,7 +71,9 @@ def basic_logging(): handler = logging.StreamHandler() handler.setFormatter(logging.Formatter( '%(levelname)-5.5s [%(name)s][%(threadName)s] %(message)s')) - logging.getLogger().addHandler(handler) + root = logging.getLogger() + root.addHandler(handler) + root.setLevel(logging.INFO) def get_uuid(): diff --git a/edbob/scaffolds/edbob/+package+/pyramid/__init__.py_tmpl b/edbob/scaffolds/edbob/+package+/pyramid/__init__.py_tmpl index 134e5ab..202366b 100644 --- a/edbob/scaffolds/edbob/+package+/pyramid/__init__.py_tmpl +++ b/edbob/scaffolds/edbob/+package+/pyramid/__init__.py_tmpl @@ -51,7 +51,6 @@ def main(global_config, **settings): # Configure edbob. Note that this is done last, primarily to allow logging # to leverage edbob's config inheritance. - edbob.basic_logging() edbob.init('{{package}}', os.path.abspath(settings['edbob.config'])) return config.make_wsgi_app() diff --git a/edbob/scaffolds/edbob/development.ini_tmpl b/edbob/scaffolds/edbob/development.ini_tmpl index ffec311..300d5d4 100644 --- a/edbob/scaffolds/edbob/development.ini_tmpl +++ b/edbob/scaffolds/edbob/development.ini_tmpl @@ -27,10 +27,7 @@ whatever = you like use = egg:{{package}} pyramid.reload_templates = true -pyramid.debug_authorization = false -pyramid.debug_notfound = false -pyramid.debug_routematch = false -pyramid.debug_templates = true +pyramid.debug_all = true pyramid.default_locale_name = en pyramid.includes = pyramid_debugtoolbar @@ -51,9 +48,6 @@ port = 6543 [edbob] include_config = ['%(here)s/production.ini'] -[edbob.db] -sqlalchemy.url = sqlite:///{{package}}.sqlite - #################### # logging @@ -62,8 +56,5 @@ sqlalchemy.url = sqlite:///{{package}}.sqlite [logger_root] level = INFO -[logger_edbob] -level = INFO - [logger_{{package_logger}}] level = DEBUG diff --git a/edbob/scaffolds/edbob/production.ini_tmpl b/edbob/scaffolds/edbob/production.ini_tmpl index c42110b..c5bfdbd 100644 --- a/edbob/scaffolds/edbob/production.ini_tmpl +++ b/edbob/scaffolds/edbob/production.ini_tmpl @@ -21,10 +21,7 @@ whatever = you like use = egg:{{package}} pyramid.reload_templates = false -pyramid.debug_authorization = false -pyramid.debug_notfound = false -pyramid.debug_routematch = false -pyramid.debug_templates = false +pyramid.debug_all = false pyramid.default_locale_name = en # Hack so edbob can find this file from within WSGI app. @@ -56,6 +53,8 @@ sqlalchemy.url = postgresql://user:pass@localhost/{{package}} [edbob] init = edbob.time, edbob.db +basic_logging = True +configure_logging = True # shell.python = ipython [edbob.db] @@ -82,7 +81,7 @@ timezone = US/Central #################### [loggers] -keys = root, edbob, {{package_logger}} +keys = root, {{package_logger}} [handlers] keys = file, console, email @@ -95,15 +94,10 @@ keys = generic, console handlers = file, console level = WARNING -[logger_edbob] -qualname = edbob -handlers = -# level = INFO - [logger_{{package_logger}}] qualname = {{package}} handlers = -level = WARNING +# level = NOTSET [handler_file] class = FileHandler @@ -114,12 +108,10 @@ formatter = generic class = StreamHandler args = (sys.stderr,) formatter = console -# level = NOTSET [handler_email] class = handlers.SMTPHandler -args = ('mail.example.com', '{{package}}@example.com', ['support@example.com'], '[{{project}} error]', - ('user', 'pass')) +args = ('mail.example.com', '{{package}}@example.com', ['support@example.com'], '[{{project}} error]', ('user', 'pass')) level = ERROR formatter = generic diff --git a/edbob/time.py b/edbob/time.py index c9b7d04..1f0d63a 100644 --- a/edbob/time.py +++ b/edbob/time.py @@ -47,7 +47,7 @@ def init(config): tz = config.get('edbob.time', 'timezone') if tz: set_timezone(tz) - log.debug("Timezone set to '%s'" % tz) + log.info("Timezone set to '%s'" % tz) else: log.warning("No timezone configured; falling back to US/Central") set_timezone('US/Central') From e3fb13785921af5f9d41f5d2fbfa9981784f3de2 Mon Sep 17 00:00:00 2001 From: Lance Edgar Date: Mon, 9 Jul 2012 02:02:48 -0500 Subject: [PATCH 12/19] update changes.txt --- CHANGES.txt | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/CHANGES.txt b/CHANGES.txt index 11224dc..7665bef 100644 --- a/CHANGES.txt +++ b/CHANGES.txt @@ -15,3 +15,15 @@ ----- - Various tweaks to Pyramid code. + +0.1a4 +----- + +- Fixed call to sleep() in filemon service. + +0.1a5 +----- + +- Added :mod:`edbob.csv` module. + +- Tweaked logging configuration and initialization semantics. From 2360a35afe3cac62995ffad09f8f9fd984a26526 Mon Sep 17 00:00:00 2001 From: Lance Edgar Date: Mon, 9 Jul 2012 02:04:26 -0500 Subject: [PATCH 14/19] bump version --- edbob/_version.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/edbob/_version.py b/edbob/_version.py index 27dc911..9f4ebbe 100644 --- a/edbob/_version.py +++ b/edbob/_version.py @@ -1 +1 @@ -__version__ = '0.1a5' +__version__ = '0.1a6' From 1a9cc374390809857d4b2b6ea3c740a61d5de67e Mon Sep 17 00:00:00 2001 From: Lance Edgar Date: Mon, 9 Jul 2012 03:30:33 -0500 Subject: [PATCH 15/19] updated (fixed) manifest --- MANIFEST.in | 18 +++++++++++++++++- 1 file changed, 17 insertions(+), 1 deletion(-) diff --git a/MANIFEST.in b/MANIFEST.in index 7dc6232..a4c1d15 100644 --- a/MANIFEST.in +++ b/MANIFEST.in @@ -1,2 +1,18 @@ -include *.txt +include COPYING.txt README.txt CHANGES.txt include ez_setup.py + +include edbob/pyramid/static/favicon.ico +include edbob/pyramid/static/robots.txt +include edbob/pyramid/static/css/*.css +include edbob/pyramid/static/js/*.js + +include edbob/scaffolds/edbob/CHANGES.txt +include edbob/scaffolds/edbob/+package+/pyramid/static/favicon.ico +include edbob/scaffolds/edbob/+package+/pyramid/static/robots.txt + +recursive-include edbob/pyramid/static/img *.jpg *.png +recursive-include edbob/pyramid/templates *.mako + +recursive-include edbob/scaffolds/edbob *.py +recursive-include edbob/scaffolds/edbob *_tmpl +recursive-include edbob/scaffolds/edbob/+package+/pyramid/templates *.mako From 9a5251e8cdb606f19ee1b31d171440ddb04478f2 Mon Sep 17 00:00:00 2001 From: Lance Edgar Date: Mon, 9 Jul 2012 03:31:09 -0500 Subject: [PATCH 16/19] update changes file --- CHANGES.txt | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/CHANGES.txt b/CHANGES.txt index 7665bef..fb7b9c3 100644 --- a/CHANGES.txt +++ b/CHANGES.txt @@ -27,3 +27,8 @@ - Added :mod:`edbob.csv` module. - Tweaked logging configuration and initialization semantics. + +0.1a6 +----- + +- Fixed MANIFEST.in file. From 811eb1566cee5549fbf451abbdf6cd8949a60e67 Mon Sep 17 00:00:00 2001 From: Lance Edgar Date: Mon, 9 Jul 2012 03:32:11 -0500 Subject: [PATCH 18/19] bump version --- edbob/_version.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/edbob/_version.py b/edbob/_version.py index 9f4ebbe..fdb6c79 100644 --- a/edbob/_version.py +++ b/edbob/_version.py @@ -1 +1 @@ -__version__ = '0.1a6' +__version__ = '0.1a7' From 53e40c9d7f912a1842d2a144ed96c93b9cf50b75 Mon Sep 17 00:00:00 2001 From: Lance Edgar Date: Mon, 9 Jul 2012 03:35:59 -0500 Subject: [PATCH 19/19] fixed version order in changes file --- CHANGES.txt | 42 +++++++++++++++++++++--------------------- 1 file changed, 21 insertions(+), 21 deletions(-) diff --git a/CHANGES.txt b/CHANGES.txt index fb7b9c3..f09870a 100644 --- a/CHANGES.txt +++ b/CHANGES.txt @@ -1,25 +1,8 @@ -0.1a1 +0.1a6 ----- -- Initial version - -0.1a2 ------ - -- Add ``win32.send_data_to_printer()`` function. - -- Various tweaks to Pyramid code. - -0.1a3 ------ - -- Various tweaks to Pyramid code. - -0.1a4 ------ - -- Fixed call to sleep() in filemon service. +- Fixed MANIFEST.in file. 0.1a5 ----- @@ -28,7 +11,24 @@ - Tweaked logging configuration and initialization semantics. -0.1a6 +0.1a4 ----- -- Fixed MANIFEST.in file. +- Fixed call to sleep() in filemon service. + +0.1a3 +----- + +- Various tweaks to Pyramid code. + +0.1a2 +----- + +- Add ``win32.send_data_to_printer()`` function. + +- Various tweaks to Pyramid code. + +0.1a1 +----- + +- Initial version