Migrate config system to YamlSettings
This commit is contained in:
parent
a994d37a9e
commit
dcba91c0c1
1
.gitignore
vendored
1
.gitignore
vendored
|
@ -1,5 +1,6 @@
|
|||
# Don't check in site specific settings.
|
||||
settings.ini
|
||||
settings.yml
|
||||
|
||||
# Compiled Python
|
||||
*.pyc
|
||||
|
|
195
defaults.ini
195
defaults.ini
|
@ -1,195 +0,0 @@
|
|||
# Default configuration settings for Rophako - DO NOT EDIT THIS FILE!
|
||||
#
|
||||
# To configure your site, create a new file named "settings.ini" and override
|
||||
# settings defined in this file. Your settings.ini is masked on top of the
|
||||
# settings in defaults.ini.
|
||||
#
|
||||
# String values can substitute the following special variables:
|
||||
# %(_basedir): The absolute path to the root of this git repository, such that
|
||||
# ./rophako/app.py exists.
|
||||
# %(_year): inserts the current year (for the RSS feed copyright setting)
|
||||
#
|
||||
# You can also define custom global variables in the [DEFAULT] section.
|
||||
# Variables in this section are injected into ALL other sections, so it's
|
||||
# recommended to prefix these with an underscore to avoid any conflicting names.
|
||||
#
|
||||
# See the Python documentation for ConfigParser if you have any questions
|
||||
# on the syntax of this file.
|
||||
|
||||
# Constants that may be useful in this file.
|
||||
[DEFAULT]
|
||||
_admin_email = root@localhost
|
||||
_date_format = %A, %B %d %Y @ %I:%M:%S %p
|
||||
# "Weekday, Month dd yyyy @ hh:mm:ss AM"
|
||||
|
||||
#------------------------------------------------------------------------------#
|
||||
# General Website Settings #
|
||||
#------------------------------------------------------------------------------#
|
||||
[site]
|
||||
|
||||
# Debug mode for development only!
|
||||
debug = false
|
||||
|
||||
# Unique name of your site, e.g. "kirsle.net"
|
||||
site_name = example.com
|
||||
|
||||
# Path to your site's HTML root. Whenever Rophako tries to render a
|
||||
# template, it will check in your site's root for the template first before
|
||||
# defaulting to the default fallback pages in the rophako/www folder. All
|
||||
# of the core Rophako pages, e.g. for account, blog, photo albums and so on,
|
||||
# have templates in the default site. You can override those templates by
|
||||
# creating files with the same paths in your site's HTML folder.
|
||||
site_root = %(_basedir)s/site/www
|
||||
|
||||
# E-mail address for site notifications (e.g. new comments and exceptions)
|
||||
notify_address = %(_admin_email)s
|
||||
|
||||
# Where to save temp files for photo uploads etc.
|
||||
tempdir = /tmp
|
||||
|
||||
#------------------------------------------------------------------------------#
|
||||
# Database settings #
|
||||
#------------------------------------------------------------------------------#
|
||||
[db]
|
||||
|
||||
# Rophako uses a flat file JSON database system, and a Redis server sits
|
||||
# between Rophako and the filesystem. The db_root is the path on the
|
||||
# filesystem to store documents in (can be relative, default "./db")
|
||||
db_root = db
|
||||
|
||||
redis_host = localhost
|
||||
redis_port = 6379
|
||||
redis_db = 0
|
||||
redis_prefix = rophako:
|
||||
|
||||
#------------------------------------------------------------------------------#
|
||||
# Security Settings #
|
||||
#------------------------------------------------------------------------------#
|
||||
[security]
|
||||
|
||||
# Set this value to true to force SSL/TLS use on your web app. Turning
|
||||
# this on will do the following:
|
||||
# - Send HTTP Strict-Transport-Security header
|
||||
# - Use secure session cookies
|
||||
force_ssl = false
|
||||
|
||||
# Secret key used for session cookie signing. Make this long and hard to
|
||||
# guess.
|
||||
#
|
||||
# Tips for creating a strong secret key:
|
||||
# $ python
|
||||
# >>> import os
|
||||
# >>> os.urandom(24)
|
||||
# '\xfd{H\xe5<\x95\xf9\xe3\x96.5\xd1\x01O<!\xd5\xa2\xa0\x9fR"\xa1\xa8'
|
||||
#
|
||||
# Then take that whole quoted string and paste it right in as the secret
|
||||
# key! Do NOT use that one. It was just an example! Make your own.
|
||||
secret_key = for the love of Arceus, change this key!
|
||||
|
||||
# Password strength: number of iterations for bcrypt password.
|
||||
bcrypt_iterations = 12
|
||||
|
||||
#------------------------------------------------------------------------------#
|
||||
# Mail Settings #
|
||||
#------------------------------------------------------------------------------#
|
||||
[mail]
|
||||
|
||||
# method = smtp or sendmail (not yet implemented)
|
||||
method = smtp
|
||||
server = localhost
|
||||
port = 25
|
||||
sender = Rophako CMS <no-reply@rophako.kirsle.net>
|
||||
|
||||
#------------------------------------------------------------------------------#
|
||||
# Plugin Configurations #
|
||||
#------------------------------------------------------------------------------#
|
||||
|
||||
###
|
||||
# Emoticons
|
||||
###
|
||||
# Emoticon theme used for blog posts and comments. Should exist at the URL
|
||||
# "/static/smileys" from your document root, and have a file named
|
||||
# "emoticons.json" inside. If you add a custom theme to your private site
|
||||
# folder, then also change EMOTICON_ROOT_PRIVATE to look there instead.
|
||||
[emoticons]
|
||||
theme = tango
|
||||
root_private = %(_basedir)s/rophako/www/static/smileys
|
||||
|
||||
###
|
||||
# Blog
|
||||
###
|
||||
[blog]
|
||||
default_category = Uncategorized
|
||||
default_privacy = public
|
||||
time_format = %(_date_format)s
|
||||
allow_comments = true
|
||||
entries_per_page = 5
|
||||
|
||||
# RSS feed settings.
|
||||
title = Rophako CMS Blog
|
||||
link = http://rophako.kirsle.net/
|
||||
language = en
|
||||
description = The web blog of the Rophako CMS.
|
||||
copyright = Copyright %(_year)s
|
||||
webmaster = %(_admin_email)s
|
||||
image_title = Rophako CMS Blog
|
||||
image_url = //www.kirsle.net/static/avatars/default.png
|
||||
image_width = 100
|
||||
image_height = 100
|
||||
image_description = Rophako CMS
|
||||
entries_per_feed = 5
|
||||
|
||||
###
|
||||
# Photo
|
||||
###
|
||||
[photo]
|
||||
# The path to where uploaded photos will be stored.
|
||||
# The PRIVATE path is from the perspective of the server file system.
|
||||
# The PUBLIC path is from the perspective of the web browser via HTTP.
|
||||
root_private = %(_basedir)s/site/www/static/photos
|
||||
root_public = /static/photos
|
||||
default_album = My Photos
|
||||
time_format = %(_date_format)s
|
||||
# Max widths for photo sizes
|
||||
width_large = 800
|
||||
width_thumb = 256
|
||||
width_avatar = 96
|
||||
|
||||
###
|
||||
# Comment
|
||||
###
|
||||
[comment]
|
||||
time_format = %(_date_format)s
|
||||
# We use Gravatar for comments if the user provides an e-mail address.
|
||||
# Specify the URL to a fallback image to use in case they don't have
|
||||
# a gravatar.
|
||||
default_avatar =
|
||||
|
||||
###
|
||||
# Wiki
|
||||
###
|
||||
[wiki]
|
||||
default_page = Main Page
|
||||
time_format = %(_date_format)s
|
||||
|
||||
#------------------------------------------------------------------------------#
|
||||
# List of Enabled Plugins #
|
||||
#------------------------------------------------------------------------------#
|
||||
[plugins]
|
||||
|
||||
# Which plugins to enable? List each plugin by module name. The plugins
|
||||
# will be assumed to be blueprints that can be attached to the main app
|
||||
# object. If you instead want to load an arbitrary Python module (i.e. to
|
||||
# define custom routes at the app layer, not in a blueprint) list those
|
||||
# under the "custom" section (remove the empty array [] and list them
|
||||
# like shown in the plugins section).
|
||||
blueprints =
|
||||
rophako.modules.blog
|
||||
rophako.modules.wiki
|
||||
rophako.modules.photo
|
||||
rophako.modules.comment
|
||||
rophako.modules.emoticons
|
||||
rophako.modules.contact
|
||||
# rophako.modules.tracking
|
||||
|
||||
custom =
|
161
defaults.yml
Normal file
161
defaults.yml
Normal file
|
@ -0,0 +1,161 @@
|
|||
# Default configuration settings for Rophako -- DO NOT EDIT THIS FILE!
|
||||
#
|
||||
# To configure your site, create a new file named "settings.yml" and override
|
||||
# settings defined in this file. Your settings.yml is masked on top of the
|
||||
# settings in defaults.yml.
|
||||
|
||||
rophako:
|
||||
###
|
||||
# General Website Settings
|
||||
###
|
||||
site:
|
||||
debug: false
|
||||
|
||||
# Unique name of your site, e.g. "kirsle.net"
|
||||
site_name: example.com
|
||||
|
||||
# Path to your site's HTML root. Whenever Rophako tries to render a
|
||||
# template, it will check in your site's root for the template first
|
||||
# before defaulting to the fallback pages in the rophako/www folder.
|
||||
# All of the core Rophako pages, e.g. for account, blog, photo albums
|
||||
# and so on, have templates in the default site. You can override those
|
||||
# templates by creating files with the same paths in your site's root.
|
||||
site_root: "{basedir}/site/www"
|
||||
|
||||
# E-mail address for site notifications (e.g. new comments and errors)
|
||||
notify_address: &ADMIN_EMAIL root@localhost
|
||||
|
||||
# Default date/time format (not used by the Rophako app but referenced
|
||||
# by other spots in this config file, for easy overriding).
|
||||
_date_format: &DATE_FORMAT '%A, %B %d %Y @ %I:%M:%S %p'
|
||||
|
||||
# Where to save temp files for photo uploads etc.
|
||||
tempdir: /tmp
|
||||
|
||||
###
|
||||
# Database settings
|
||||
###
|
||||
db:
|
||||
# Rophako uses a flat file JSON database system, and a Redis server sits
|
||||
# between Rophako and the filesystem. The db_root is the path on the
|
||||
# filesystem to store documents in (can be relative, default "./db")
|
||||
db_root: db
|
||||
|
||||
# Redis connection settings
|
||||
redis_host: localhost
|
||||
redis_port: 6379
|
||||
redis_db: 0
|
||||
redis_prefix: "rophako:"
|
||||
|
||||
###
|
||||
# Security Settings
|
||||
###
|
||||
security:
|
||||
# Set this value to true to force SSL/TLS on your web app. Turning this on
|
||||
# will do the following:
|
||||
# - Send HTTP Strict-Transport-Security header
|
||||
# - Use secure session cookies (SSL-only)
|
||||
force_ssl: true
|
||||
|
||||
# Secret key used for session cookie signing. Make this long and hard to
|
||||
# guess.
|
||||
#
|
||||
# Tips for creating a strong secret key:
|
||||
# $ python
|
||||
# >>> import os
|
||||
# >>> os.urandom(24)
|
||||
# '\xfd{H\xe5<\x95\xf9\xe3\x96.5\xd1\x01O<!\xd5\xa2\xa0\x9fR"\xa1\xa8'
|
||||
#
|
||||
# Then take that whole quoted string and paste it right in as the secret
|
||||
# key. Do NOT use that one, it was just an example. Make your own!
|
||||
secret_key: 'for the love of Arceus, change this key!'
|
||||
|
||||
# Password strength: number of iterations for bcrypt password.
|
||||
bcrypt_iterations: 12
|
||||
|
||||
###
|
||||
# Mail Settings
|
||||
###
|
||||
mail:
|
||||
method: smtp # or sendmail (not implemented yet)
|
||||
server: localhost
|
||||
port: 25
|
||||
sender: Rophako CMS <no-reply@rophako.kirsle.net>
|
||||
|
||||
###
|
||||
# Plugin Configurations
|
||||
###
|
||||
emoticons:
|
||||
# Emoticon theme used for blog posts and comments. Should exist at the URL
|
||||
# "/static/smileys" from your document root, and have a file named
|
||||
# "emoticons.json" inside. If you add a custom theme to your private site
|
||||
# folder, then also change the root_private to look there instead.
|
||||
theme: tango
|
||||
root_private: "{basedir}/rophako/www/static/smileys"
|
||||
|
||||
blog:
|
||||
default_category: Uncategorized
|
||||
default_privacy: public
|
||||
time_format: *DATE_FORMAT
|
||||
allow_comments: true
|
||||
entries_per_page: 5
|
||||
|
||||
# RSS feed settings
|
||||
title: Rophako CMS Blog
|
||||
link: http://rophako.kirsle.net/
|
||||
language: en
|
||||
description: The web blog of the Rophako CMS.
|
||||
copyright: "Copyright {year}"
|
||||
webmaster: *ADMIN_EMAIL
|
||||
image_title: Rophako CMS Blog
|
||||
image_url: https://www.kirsle.net/static/avatars/default.png
|
||||
image_width: 100
|
||||
image_height: 100
|
||||
image_description: Rophako CMS
|
||||
entries_per_feed: 5
|
||||
|
||||
photo:
|
||||
# The path to where the uploaded photos will be stored.
|
||||
# The PRIVATE path is from the perspective of the server file system.
|
||||
# The PUBLIC path is from the perspective of the web browser via HTTP.
|
||||
root_private: "{basedir}/site/www/static/photos"
|
||||
root_public: /static/photos
|
||||
default_album: My Photos
|
||||
time_format: *DATE_FORMAT
|
||||
|
||||
# Max widths for photo sizes
|
||||
width_large: 800
|
||||
width_thumb: 256
|
||||
width_avatar: 96
|
||||
|
||||
comment:
|
||||
time_format: *DATE_FORMAT
|
||||
# We use Gravatar for comments if the user provides an e-mail address.
|
||||
# Specify the URL to a fallback image to use in case they don't have
|
||||
# a gravatar.
|
||||
default_avatar:
|
||||
|
||||
wiki:
|
||||
default_page: Main Page
|
||||
time_format: *DATE_FORMAT
|
||||
|
||||
###
|
||||
# List of Enabled Plugins
|
||||
###
|
||||
|
||||
# Which plugins to enable? List each plugin by module name. The plugins
|
||||
# will be assumed to be blueprints that can be attached to the main app
|
||||
# object. If you instead want to load an arbitrary Python module (i.e. to
|
||||
# define custom routes at the app layer, not in a blueprint) list those
|
||||
# under the "custom" section.
|
||||
blueprints:
|
||||
- rophako.modules.blog
|
||||
- rophako.modules.wiki
|
||||
- rophako.modules.photo
|
||||
- rophako.modules.comment
|
||||
- rophako.modules.emoticons
|
||||
- rophako.modules.contact
|
||||
|
||||
# If adding custom scripts, remove the empty array and define a list like
|
||||
# in the above blueprints example.
|
||||
custom: []
|
|
@ -8,3 +8,4 @@ Markdown
|
|||
Pygments
|
||||
attrdict
|
||||
gunicorn
|
||||
yamlsettings
|
||||
|
|
|
@ -5,58 +5,49 @@ import os
|
|||
import datetime
|
||||
from attrdict import AttrDict
|
||||
from ConfigParser import ConfigParser
|
||||
from yamlsettings import YamlSettings
|
||||
|
||||
from rophako.plugin import load_plugin
|
||||
|
||||
# Get the base directory of the git root.
|
||||
basedir = os.path.abspath(os.path.join(os.path.dirname(__file__), os.path.pardir))
|
||||
|
||||
# https://github.com/bcj/AttrDict/issues/20
|
||||
if not hasattr(AttrDict, "copy"):
|
||||
setattr(AttrDict, "copy", lambda self: self._mapping.copy())
|
||||
|
||||
class ConfigHandler(object):
|
||||
settings = None
|
||||
|
||||
def load_settings(self):
|
||||
"""Load the settings files and make them available in the global config."""
|
||||
self.settings = ConfigParser(dict_type=AttrDict)
|
||||
"""Load the settings and make them available in the global config."""
|
||||
settings_file = os.environ.get("ROPHAKO_SETTINGS", "settings.yml")
|
||||
project_settings = YamlSettings("defaults.yml", settings_file,
|
||||
default_section="rophako")
|
||||
self.settings = project_settings.get_settings()
|
||||
|
||||
# Set dynamic default variables.
|
||||
self.settings.set("DEFAULT", "_basedir", basedir)
|
||||
self.settings.set("DEFAULT", "_year", str(datetime.datetime.now().strftime("%Y")))
|
||||
|
||||
# Read the defaults and then apply the custom settings on top.
|
||||
settings_file = os.environ.get("ROPHAKO_SETTINGS", "settings.ini")
|
||||
self.settings.read(["defaults.ini", settings_file])
|
||||
# Extrapolate {basedir} in certain keys.
|
||||
# TODO: find a better way...
|
||||
self.site.site_root = self.site.site_root.format(basedir=basedir)
|
||||
self.emoticons.root_private = self.emoticons.root_private.format(
|
||||
basedir=basedir
|
||||
)
|
||||
self.photo.root_private = self.photo.root_private.format(basedir=basedir)
|
||||
|
||||
def print_settings(self):
|
||||
"""Pretty-print the contents of the configuration as JSON."""
|
||||
for section in self.settings.sections():
|
||||
print "[{}]".format(section)
|
||||
for opt in self.settings.options(section):
|
||||
print "{} = {}".format(opt, repr(self.settings.get(section, opt)))
|
||||
print ""
|
||||
"""Pretty-print the contents of the configuration."""
|
||||
print self.settings
|
||||
|
||||
def load_plugins(self):
|
||||
"""Load all the plugins specified by the config file."""
|
||||
for plugin in self.plugins.blueprints.split("\n"):
|
||||
for plugin in self.blueprints:
|
||||
plugin = plugin.strip()
|
||||
if not plugin:
|
||||
continue
|
||||
if not plugin: continue
|
||||
load_plugin(plugin)
|
||||
for custom in self.plugins.custom.split("\n"):
|
||||
for custom in self.custom:
|
||||
custom = custom.strip()
|
||||
if not custom:
|
||||
continue
|
||||
if not custom: continue
|
||||
load_plugin(custom, as_blueprint=False)
|
||||
|
||||
def __getattr__(self, section):
|
||||
"""Attribute access for the config object.
|
||||
|
||||
You can access config settings via Config.<section>.<name>, for example
|
||||
Config.site.notify_email and Config.blog.posts_per_page. All results are
|
||||
returned as strings per ConfigParser, so cast them if you need to."""
|
||||
return AttrDict(dict(self.settings.items(section)))
|
||||
"""Attribute accessor for the config object. Acts as a simple pass-thru
|
||||
to YamlSettings."""
|
||||
return getattr(self.settings, section)
|
||||
|
||||
Config = ConfigHandler()
|
||||
|
|
Loading…
Reference in New Issue
Block a user