diff --git a/CHANGES.md b/CHANGES.md new file mode 100644 index 0000000..2fd3f54 --- /dev/null +++ b/CHANGES.md @@ -0,0 +1,4 @@ +0.0.1 - first version +---------------------- + + - setting up the project diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md new file mode 100644 index 0000000..7e27de1 --- /dev/null +++ b/CONTRIBUTING.md @@ -0,0 +1,117 @@ +Contributing +============ + +Contributions are welcome, and they are greatly appreciated! Every little bit +helps, and credit will always be given. + +You can contribute in many ways: + +Types of Contributions +---------------------- + +### Report Bugs + +Report bugs at https://git.cpi.imtek.uni-freiburg.de/CPI/honeypot.git/issues. + +If you are reporting a bug, please include: + +* Your operating system name and version. +* Any details about your local setup that might be helpful in troubleshooting. +* Detailed steps to reproduce the bug. + +### Fix Bugs + +Look through the GitHub issues for bugs. Anything tagged with "bug" and "help +wanted" is open to whoever wants to implement it. + +### Implement Features + +Look through the GitHub issues for features. Anything tagged with "enhancement" +and "help wanted" is open to whoever wants to implement it. + +### Write Documentation + +Honeypot could always use more documentation, whether as part of the +official Honeypot docs, in docstrings, or even on the web in blog posts, +articles, and such. + +### Submit Feedback + +The best way to send feedback is to file an issue at https://git.cpi.imtek.uni-freiburg.de/CPI/honeypot.git/issues. + +If you are proposing a feature: + +* Explain in detail how it would work. +* Keep the scope as narrow as possible, to make it easier to implement. +* Remember that this is a volunteer-driven project, and that contributions + are welcome :) + +Get Started! +------------ + +Ready to contribute? Here's how to set up `honeypot` for local development. + +1. Fork the `honeypot` repo on GitHub. +2. Clone your fork locally:: + + `$ git clone git@github.com:your_name_here/honeypot.git` + +3. Install your local copy into a virtualenv. + + `$ cd honeypot/` + `$ make devenv` + +4. Create a branch for local development:: + + `$ git checkout -b name-of-your-bugfix-or-feature` + + Now you can make your changes locally. + +5. When you're done making changes, check that your changes passes the linters and the + tests, including testing other Python versions with tox:: + + ``` + $ make lint + $ make coverage + $ make tox + ``` + +6. Commit your changes and push your branch to GitHub:: + + ``` + $ git add . + $ git commit -m "Your detailed description of your changes." + $ git push origin name-of-your-bugfix-or-feature + ``` + +7. Submit a pull request through the GitHub website. + +Pull Request Guidelines +----------------------- + +Before you submit a pull request, check that it meets these guidelines: + +1. The pull request should include tests. +2. If the pull request adds functionality, the docs should be updated. Put + your new functionality into a function with a docstring, and add the + feature to the list in README.md and CHANGES.md + +Tips +---- + +To run a quick set of tests without coverage report + + $ make test + +Deploying +--------- + +A reminder for the maintainers on how to deploy. +Bump the version in `honeypot/__init__.py` and +make sure all your changes are committed (including an entry in CHANGES.md). + + $ git tag + $ git push + $ git push --tags + $ flit publish + diff --git a/LICENSE b/LICENSE index 08e174a..a3dfb3e 100644 --- a/LICENSE +++ b/LICENSE @@ -1,13 +1,10 @@ -BEERWARE +/* +* ---------------------------------------------------------------------------- +* "THE BEER-WARE LICENSE" (Revision 42): +* frey@imtek.de wrote this file. As long as you retain this notice you +* can do whatever you want with this stuff. If we meet some day, and you think +* this stuff is worth it, you can buy me a beer in return. Holger Frey +* ---------------------------------------------------------------------------- +*/ -The beerware license is very open, close to public domain, but insists on -honoring the original author by just not claiming that the code is yours. -Instead assume that someone writing Open Source Software in the domain you’re -obviously interested in would be a nice match for having a beer with. - -So, just keep the name and contact details intact and if you ever meet the -author in person, just have an appropriate brand of sparkling beverage choice -together. The conversation will be worth the time for both of you. - -(Kudos to https://erdgeist.org/beerware.html) diff --git a/MANIFEST.in b/MANIFEST.in deleted file mode 100644 index 44585e3..0000000 --- a/MANIFEST.in +++ /dev/null @@ -1,2 +0,0 @@ -include *.txt *.ini *.cfg *.rst -recursive-include honeypot *.ico *.png *.css *.gif *.jpg *.pt *.txt *.mak *.mako *.js *.html *.xml *.jinja2 diff --git a/Makefile b/Makefile new file mode 100644 index 0000000..ea45988 --- /dev/null +++ b/Makefile @@ -0,0 +1,90 @@ +.PHONY: clean clean-test clean-pyc clean-build docs help +.DEFAULT_GOAL := help + +define BROWSER_PYSCRIPT +import os, webbrowser, sys + +try: + from urllib import pathname2url +except: + from urllib.request import pathname2url + +webbrowser.open("file://" + pathname2url(os.path.abspath(sys.argv[1]))) +endef +export BROWSER_PYSCRIPT + +define PRINT_HELP_PYSCRIPT +import re, sys + +for line in sys.stdin: + match = re.match(r'^([a-zA-Z_-]+):.*?## (.*)$$', line) + if match: + target, help = match.groups() + print("%-20s %s" % (target, help)) +endef +export PRINT_HELP_PYSCRIPT + +BROWSER := python -c "$$BROWSER_PYSCRIPT" + +help: + @python -c "$$PRINT_HELP_PYSCRIPT" < $(MAKEFILE_LIST) + +clean: clean-build clean-pyc clean-test ## remove all build, test, coverage and Python artifacts + +clean-build: ## remove build artifacts + rm -fr build/ + rm -fr dist/ + rm -fr .eggs/ + find . -name '*.egg-info' -exec rm -fr {} + + find . -name '*.egg' -exec rm -f {} + + +clean-pyc: ## remove Python file artifacts + find . -name '*.pyc' -exec rm -f {} + + find . -name '*.pyo' -exec rm -f {} + + find . -name '*~' -exec rm -f {} + + find . -name '__pycache__' -exec rm -fr {} + + +clean-test: ## remove test and coverage artifacts + rm -fr .pytest_cache/ + rm -fr .tox/ + rm -f .coverage + rm -fr htmlcov/ + +lint: ## reformat with black and check style with flake8 + isort honeypot + isort tests + black honeypot tests + flake8 honeypot tests + +test: lint ## run tests quickly with the default Python + pytest tests -x --disable-warnings -m "not fun" + +testall: lint ## run tests quickly with the default Python + pytest tests + +coverage: lint ## full test suite, check code coverage and open coverage report + pytest tests --cov=honeypot -m "fun" + coverage html + $(BROWSER) htmlcov/index.html + +tox: ## run fully isolated tests with tox + tox + +install: ## install updated project.toml with flint + flit install --pth-file + +devenv: ## setup development environment + python3 -m venv --prompt honeypot .venv + .venv/bin/pip3 install --upgrade pip + .venv/bin/pip3 install flit + .venv/bin/flit install --pth-file + +repo: devenv ## complete project setup with development environment and git repo + git init . + git branch -m master + git add . + git commit -m "import of project template" + git remote add origin https://git.cpi.imtek.uni-freiburg.de/CPI/honeypot.git + git push -u origin main --no-verify + + .venv/bin/pre-commit install --install-hooks diff --git a/Pipfile b/Pipfile deleted file mode 100644 index ea1b6fd..0000000 --- a/Pipfile +++ /dev/null @@ -1,12 +0,0 @@ -[[source]] -url = "https://pypi.org/simple" -verify_ssl = true -name = "pypi" - -[packages] -"e1839a8" = {path = ".", editable = true} - -[dev-packages] - -[requires] -python_version = "3.6" diff --git a/Pipfile.lock b/Pipfile.lock deleted file mode 100644 index 12c1151..0000000 --- a/Pipfile.lock +++ /dev/null @@ -1,116 +0,0 @@ -{ - "_meta": { - "hash": { - "sha256": "a166821031f60007a08b6fec9ba3caa9dc601786a8eb3ed72bbd9342668d2b3d" - }, - "pipfile-spec": 6, - "requires": { - "python_version": "3.6" - }, - "sources": [ - { - "name": "pypi", - "url": "https://pypi.org/simple", - "verify_ssl": true - } - ] - }, - "default": { - "e1839a8": { - "editable": true, - "path": "." - }, - "hupper": { - "hashes": [ - "sha256:20387760e4d32bd4813c2cabc8e51d92b2c22c546102a0af182c33c152cd7ede", - "sha256:6b8133e9c5cc0a8ec422a29ef3b38aea2c49a809a0af73f419a78a7015b32615" - ], - "version": "==1.3" - }, - "pastedeploy": { - "hashes": [ - "sha256:39973e73f391335fac8bc8a8a95f7d34a9f42e2775600ce2dc518d93b37ef943", - "sha256:d5858f89a255e6294e63ed46b73613c56e3b9a2d82a42f1df4d06c8421a9e3cb" - ], - "version": "==1.5.2" - }, - "plaster": { - "hashes": [ - "sha256:215c921a438b5349931fd7df9a5a11a3572947f20f4bc6dd622ac08f1c3ba249", - "sha256:8351c7c7efdf33084c1de88dd0f422cbe7342534537b553c49b857b12d98c8c3" - ], - "version": "==1.0" - }, - "plaster-pastedeploy": { - "hashes": [ - "sha256:25cc239d767c5fab0afa44b1ed3c1a33a3d7ec6302ff2e599aec674b77ff6667", - "sha256:70a3185b2a3336996a26e9987968cf35e84cf13390b7e8a0a9a91eb8f6f85ba9" - ], - "version": "==0.5" - }, - "pyramid": { - "hashes": [ - "sha256:600f12e0d11211a55c2da970120af33214f77607ed45caba6af6c891afeaa771", - "sha256:cf89a48cb899291639686bf3d4a883b39e496151fa4871fb83cc1a3200d5b925" - ], - "version": "==1.9.2" - }, - "repoze.lru": { - "hashes": [ - "sha256:0429a75e19380e4ed50c0694e26ac8819b4ea7851ee1fc7583c8572db80aff77", - "sha256:f77bf0e1096ea445beadd35f3479c5cff2aa1efe604a133e67150bc8630a62ea" - ], - "version": "==0.7" - }, - "translationstring": { - "hashes": [ - "sha256:4ee44cfa58c52ade8910ea0ebc3d2d84bdcad9fa0422405b1801ec9b9a65b72d", - "sha256:e26c7bf383413234ed442e0980a2ebe192b95e3745288a8fd2805156d27515b4" - ], - "version": "==1.3" - }, - "venusian": { - "hashes": [ - "sha256:757162c5f907e18571b6ab41b7673e5bf18cc8715abf8164292eaef4f1610668", - "sha256:9902e492c71a89a241a18b2f9950bea7e41d025cc8f3af1ea8d8201346f8577d" - ], - "version": "==1.1.0" - }, - "waitress": { - "hashes": [ - "sha256:40b0f297a7f3af61fbfbdc67e59090c70dc150a1601c39ecc9f5f1d283fb931b", - "sha256:d33cd3d62426c0f1b3cd84ee3d65779c7003aae3fc060dee60524d10a57f05a9" - ], - "version": "==1.1.0" - }, - "webob": { - "hashes": [ - "sha256:1771899117c8851153f6f91e8b8a86236972aa8a1b6bd69ad0a36a9879ea2cd7", - "sha256:54f35073d2fdcddd7a98c2a1dedeede49739150737164a787220f30283139ba6" - ], - "version": "==1.8.1" - }, - "zope.deprecation": { - "hashes": [ - "sha256:7d52e134bbaaa0d72e1e2bc90f0587f1adc116c4bdf15912afaf2f1e8856b224", - "sha256:c83cfef3085d10dcb07de5a59a2d95713865befa46e0e88784c5648610fba789" - ], - "version": "==4.3.0" - }, - "zope.interface": { - "hashes": [ - "sha256:21506674d30c009271fe68a242d330c83b1b9d76d62d03d87e1e9528c61beea6", - "sha256:3d184aff0756c44fff7de69eb4cd5b5311b6f452d4de28cb08343b3f21993763", - "sha256:467d364b24cb398f76ad5e90398d71b9325eb4232be9e8a50d6a3b3c7a1c8789", - "sha256:57c38470d9f57e37afb460c399eb254e7193ac7fb8042bd09bdc001981a9c74c", - "sha256:9ada83f4384bbb12dedc152bcdd46a3ac9f5f7720d43ac3ce3e8e8b91d733c10", - "sha256:a1daf9c5120f3cc6f2b5fef8e1d2a3fb7bbbb20ed4bfdc25bc8364bc62dcf54b", - "sha256:e6b77ae84f2b8502d99a7855fa33334a1eb6159de45626905cb3e454c023f339", - "sha256:e881ef610ff48aece2f4ee2af03d2db1a146dc7c705561bd6089b2356f61641f", - "sha256:f41037260deaacb875db250021fe883bf536bf6414a4fd25b25059b02e31b120" - ], - "version": "==4.5.0" - } - }, - "develop": {} -} diff --git a/README.md b/README.md index 13d09d2..272f543 100644 --- a/README.md +++ b/README.md @@ -1,3 +1,18 @@ -# honeypot +Honeypot +======== -Simple repository for the `/HonigTopf` (HoneyPot) link, that alerts the admins if someone tries to scrape a moin moin wiki. \ No newline at end of file +A honeypot for wiki scrapers. + +Simple repository for the `/HonigTopf` (HoneyPot) link, that alerts the admins if someone tries to scrape a moin moin wiki. + +## Development + +To install the development version of Honeypot: + + git clone https://git.cpi.imtek.uni-freiburg.de/CPI/honeypot.git + + # create a virtual environment and install all required dev dependencies + cd honeypot + make devenv + +To run the tests, use `make tests` or `make coverage` for a complete report. diff --git a/honeypot/__init__.py b/honeypot/__init__.py index 53e9644..62d6907 100644 --- a/honeypot/__init__.py +++ b/honeypot/__init__.py @@ -1,3 +1,10 @@ +""" Honeypot + +A honeypot for wiki scrapers +""" + +__version__ = "0.0.1" + import os import pickle import re diff --git a/pyproject.toml b/pyproject.toml new file mode 100644 index 0000000..4149d03 --- /dev/null +++ b/pyproject.toml @@ -0,0 +1,85 @@ + + +[build-system] +requires = ["flit"] +build-backend = "flit.buildapi" + +[tool.flit.metadata] +module = "honeypot" +dist-name = "honeypot" +author = "Holger Frey" +author-email = "frey@imtek.de" +home-page = "https://git.cpi.imtek.uni-freiburg.de/CPI/honeypot.git" +description-file = "README.md" +license = "Beerware" + +# see https://pypi.org/classifiers/ +classifiers = [ + "Development Status :: 2 - Pre-Alpha", + "Framework :: Pyramid", + "Topic :: Internet :: WWW/HTTP", + "Topic :: Internet :: WWW/HTTP :: WSGI :: Application", + "Programming Language :: Python :: 3.7", + "Programming Language :: Python :: 3.8", + "Programming Language :: Python :: 3.9", + "Programming Language :: Python :: 3 :: Only", + "License :: Freely Distributable", +] + +requires = [ + "chardet", + "plaster_pastedeploy", + "pyramid", + "pyramid_mailer", + "waitress", +] +requires-python = ">=3.7" + +[tool.flit.metadata.requires-extra] +test = [ + "pytest >=4.0.0", + "pytest-cov", + "pytest-mock", + "pytest-randomly", + "tox", +] +dev = [ + "black", + "flake8", + "flake8-comprehensions", + "flake8-bandit", + "isort >= 5.0.0", + "keyring", + "pre-commit", +] + +[tool.black] +line-length = 79 +py37 = true +include = "\.pyi?$" +exclude = """ +/( + \.git + | \.tox + | \.venv + | build + | dist +)/ +""" + +[tool.isort] +line_length=79 +multi_line_output=3 +length_sort="True" +include_trailing_comma="True" + +[tool.pytest.ini_options] +markers = [ + 'fun: marks tests as functional (deselect with "-m \"not fun\"")', +] +addopts = [ + "--strict-markers", +] + +[project.entry-points."paste.app_factory"] +main = "honeypot:main" diff --git a/requirements.txt b/requirements.txt deleted file mode 100644 index edab75d..0000000 --- a/requirements.txt +++ /dev/null @@ -1,5 +0,0 @@ -chardet==3.0.4 -plaster-pastedeploy==0.7 -pyramid==1.10.4 -pyramid-mailer==0.15.1 -waitress==1.4.4 \ No newline at end of file diff --git a/setup.py b/setup.py deleted file mode 100644 index 506ee6f..0000000 --- a/setup.py +++ /dev/null @@ -1,41 +0,0 @@ -import os - -from setuptools import setup, find_packages - -here = os.path.abspath(os.path.dirname(__file__)) -with open(os.path.join(here, 'README.md')) as f: - README = f.read() - -requires = [ - 'chardet', - 'plaster_pastedeploy', - 'pyramid', - 'pyramid_mailer', - 'waitress', -] - -setup( - name='honeypot', - version='0.0.1', - description='HoneyPot', - long_description=README, - classifiers=[ - 'Programming Language :: Python', - 'Framework :: Pyramid', - 'Topic :: Internet :: WWW/HTTP', - 'Topic :: Internet :: WWW/HTTP :: WSGI :: Application', - ], - author='Holger Frey', - author_email='frey@imtek.de', - url='https://git.cpi.imtek.uni-freiburg.de/holgi/honeypot', - keywords='web pyramid pylons', - packages=find_packages(), - include_package_data=True, - zip_safe=False, - install_requires=requires, - entry_points={ - 'paste.app_factory': [ - 'main = honeypot:main', - ], - }, -) diff --git a/tests/test_honeypot.py b/tests/test_honeypot.py new file mode 100644 index 0000000..ab75af1 --- /dev/null +++ b/tests/test_honeypot.py @@ -0,0 +1,41 @@ +""" Stub file for testing the project + +There are three predefined ways to run tests: + +make test: + runs only unit tests, that are not marked with "fun" (for functional test) + in a random order. If a test failed before, only the failed tests will be + run. This is intended to be the default testing method while developing. + +make testall: + runs unit tests and functional tests in random order. Will give a complete + overview of the test suite. + +make coverage: + runs only tests marked with "fun" (for functional tests) and generates a + coverage report for the test run. The idea is to check the test coverage + only on functinal tests to see if a) everything is as much covered as + possible and b) to find dead code that is not called in end-to-end tests. + +all three test strategies will run "make lint" before to catch easily made +mistakes. +""" + +import pytest + + +def test_example_unittest(): + """ example unittest + + will be run by 'make test' and 'make testall' but not 'make coverage' + """ + assert True + + +@pytest.mark.fun +def test_example_functional_test(): + """ example unittest + + will be by 'make coverage' and 'make testall' but not 'make test' + """ + assert True diff --git a/tox.ini b/tox.ini new file mode 100644 index 0000000..71bd72f --- /dev/null +++ b/tox.ini @@ -0,0 +1,14 @@ +[tox] +envlist = py37 +isolated_build = True + +[testenv] +deps = + pytest + pytest-cov + pytest-mock + setuptools>=41.2.0 + pip>=20.0.2 + +changedir = {toxinidir}/tests +commands = pytest --cov=honeypot