Skip to content

Commit

Permalink
Convert zconfig to a console entry point and test it.
Browse files Browse the repository at this point in the history
Port to Python 3.

Document it.
  • Loading branch information
jamadden authored and freddrake committed Feb 22, 2017
1 parent e3801a5 commit 36b9bd7
Show file tree
Hide file tree
Showing 9 changed files with 201 additions and 111 deletions.
7 changes: 7 additions & 0 deletions .readthedocs.yml
@@ -0,0 +1,7 @@
formats:
- none

python:
pip_install: true
extra_requirements:
- docs
8 changes: 5 additions & 3 deletions ZConfig/tests/support.py
Expand Up @@ -24,11 +24,13 @@
from ZConfig._compat import NStringIO as StringIO
from ZConfig._compat import pathname2url

d = os.path.abspath(os.path.join(os.path.dirname(__file__), "input"))
CONFIG_BASE = "file://%s/" % pathname2url(d)
INPUT_DIR = os.path.abspath(os.path.join(os.path.dirname(__file__), "input"))
CONFIG_BASE = "file://%s/" % pathname2url(INPUT_DIR)

def input_file(fname):
return os.path.abspath(os.path.join(INPUT_DIR, fname))

class TestHelper:
class TestHelper(object):
"""Utility methods which can be used with the schema support."""

# Not derived from unittest.TestCase; some test runners seem to
Expand Down
79 changes: 79 additions & 0 deletions ZConfig/tests/test_validator.py
@@ -0,0 +1,79 @@
##############################################################################
#
# Copyright (c) 2017 Zope Foundation and Contributors.
# All Rights Reserved.
#
# This software is subject to the provisions of the Zope Public License,
# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
# FOR A PARTICULAR PURPOSE.
#
##############################################################################
from __future__ import absolute_import

import contextlib
import sys
import unittest

from ZConfig import validator

from .support import input_file

def run_validator(*args):
return validator.main(args)

def with_stdin_from_input_file(fname):
input_fname = input_file(fname)
@contextlib.contextmanager
def stdin_replaced():
old_stdin = sys.stdin
sys.stdin = open(input_fname)
try:
yield
finally:
sys.stdin = old_stdin

def make_wrapper(f):
def f2(self):
with stdin_replaced():
f(self)
return f2

return make_wrapper



class TestValidator(unittest.TestCase):

def test_no_schema(self):
self.assertRaises(SystemExit,
run_validator)

def test_schema_only(self):
res = run_validator("--schema", input_file('simple.xml'))
self.assertEqual(res, 0)

@with_stdin_from_input_file('simple.conf')
def test_schema_only_redirect(self):
res = run_validator("--schema", input_file('simple.xml'))
self.assertEqual(res, 0)

def test_good_config(self):
res = run_validator("--schema", input_file('simple.xml'),
input_file('simple.conf'),
input_file('simple.conf'))
self.assertEqual(res, 0)

def test_bad_config(self):
res = run_validator("--schema", input_file("simple.xml"),
input_file("outer.conf"))
self.assertEqual(res, 1)


def test_suite():
return unittest.makeSuite(TestValidator)

if __name__ == "__main__":
unittest.main(defaultTest="test_suite")
75 changes: 75 additions & 0 deletions ZConfig/validator.py
@@ -0,0 +1,75 @@
##############################################################################
#
# Copyright (c) 2003 Zope Corporation and Contributors.
# All Rights Reserved.
#
# This software is subject to the provisions of the Zope Public License,
# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
# FOR A PARTICULAR PURPOSE.
#
##############################################################################

"""Script to check validity of a configuration file.
"""

from __future__ import print_function
import argparse
import sys


import ZConfig


def main(args=None):
optparser = argparse.ArgumentParser(
description="Script to check validity of a configuration file",
epilog="""
Each file named on the command line is checked for syntactical errors
and schema conformance. The schema must be specified. If no files
are specified and standard input is not a TTY, standard in is treated
as a configuration file. Specifying a schema and no configuration
files causes the schema to be checked.""",
)

optparser.add_argument(
"-s", "--schema", dest="schema",
required=True,
help="use the schema in FILE (can be a URL)",
metavar="FILE"
)

optparser.add_argument(
"file",
nargs='*',
help="Optional configuration file to check",
type=argparse.FileType('r'),
)

options = optparser.parse_args(args=args)

schema = ZConfig.loadSchema(options.schema)

if not options.file:
if sys.stdin.isatty():
# just checking the schema
return 0

# stdin is a pipe
options.file = [sys.stdin]

errors = False
for f in options.file:
try:
ZConfig.loadConfigFile(schema, f)
except ZConfig.ConfigurationError as e:
print(str(e), file=sys.stderr)
errors = True

return int(errors)


if __name__ == "__main__":
sys.exit(main())
3 changes: 2 additions & 1 deletion doc/conf.py
Expand Up @@ -32,7 +32,8 @@
# ones.
extensions = [
'sphinx.ext.autodoc',
'sphinx.ext.intersphinx'
'sphinx.ext.intersphinx',
'sphinxcontrib.programoutput',
]

# Add any paths that contain templates here, relative to this directory.
Expand Down
1 change: 1 addition & 0 deletions doc/index.rst
Expand Up @@ -32,6 +32,7 @@ Development of ZConfig is hosted on `GitHub <https://github.com/zopefoundation/Z
using-zconfig
developing-with-zconfig
zconfig
tools

.. toctree::
:maxdepth: 1
Expand Down
16 changes: 16 additions & 0 deletions doc/tools.rst
@@ -0,0 +1,16 @@
=================
ZConfig Tooling
=================

ZConfig ships with some tools that can be helpful to anyone
either writing configurations or writing programs that read
configurations.

Schema and Configuration Validation
===================================

When ZConfig is installed, it installs a program called ``zconfig``
that can validate both schemas and configurations written against
those schemas:

.. program-output:: zconfig --help
101 changes: 0 additions & 101 deletions scripts/zconfig

This file was deleted.

22 changes: 16 additions & 6 deletions setup.py
@@ -1,3 +1,9 @@
try:
from setuptools import setup
except ImportError:
from distutils.core import setup


with open("README.rst") as f:
README = f.read()
with open("CHANGES.rst") as f:
Expand Down Expand Up @@ -45,7 +51,12 @@ def alltests():
"ZConfig.tests.library.thing",
"ZConfig.tests.library.widget",
],
scripts=["scripts/zconfig", "scripts/zconfig_schema2html"],
scripts=["scripts/zconfig_schema2html"],
entry_points={
'console_scripts': [
'zconfig = ZConfig.validator:main',
],
},
include_package_data=True,
zip_safe=False,
classifiers=[
Expand All @@ -72,12 +83,11 @@ def alltests():
tests_require=tests_require,
extras_require={
'test': tests_require,
'docs': [
'nti.sphinxcontrib-programoutput',
]
},
)
)

try:
from setuptools import setup
except ImportError:
from distutils.core import setup

setup(**options)

0 comments on commit 36b9bd7

Please sign in to comment.