Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Simplify #6

Merged
merged 6 commits into from
Apr 3, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 3 additions & 6 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,14 +8,11 @@ matches the input source.
## Running linting
Run `make lint`.

## Rebuilding the auto-generated list of classifiers
Run `make build`.

## Adding a new classifier
To add a new classifier, edit `_internal/classifiers.py`, then rebuild the
compiled list of classifiers with `make build`.
To add a new classifier, add to the `classifiers` set in
`trove_classifiers/__init__.py`.

## Deprecating a classifier
To deprecate a classifier, move it from `classifiers` to
`deprecated_classifiers` in `_internal/classifiers.py`, and list any new
`deprecated_classifiers` in `trove_classifiers/__init__.py`, and list any new
classifiers that may replace it.
11 changes: 3 additions & 8 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -10,19 +10,14 @@ BINDIR = $(PWD)/.state/env/bin
# install various types of requirements
$(BINDIR)/python -m pip install -r requirements/dev.txt

build: .state/env/pyvenv.cfg
$(BINDIR)/python -m _internal.generator

test: .state/env/pyvenv.cfg
$(BINDIR)/pytest
$(eval TMPDIR := $(shell mktemp -d))
$(BINDIR)/python -m _internal.generator --output $(TMPDIR)/test.py
diff trove_classifiers/__init__.py $(TMPDIR)/test.py
$(BINDIR)/python -m tester

lint: .state/env/pyvenv.cfg
$(BINDIR)/black --check _internal tests
$(BINDIR)/black --check tests tester trove_classifiers

reformat: .state/env/pyvenv.cfg
$(BINDIR)/black _internal tests
$(BINDIR)/black tests tester trove_classifiers

.PHONY: build test lint reformat
Empty file removed _internal/__init__.py
Empty file.
1,046 changes: 0 additions & 1,046 deletions _internal/classifiers.py

This file was deleted.

2 changes: 0 additions & 2 deletions _internal/exceptions.py

This file was deleted.

30 changes: 0 additions & 30 deletions _internal/generator.py

This file was deleted.

77 changes: 0 additions & 77 deletions _internal/models.py

This file was deleted.

15 changes: 0 additions & 15 deletions _internal/templates/__init__.py.jinja2

This file was deleted.

2 changes: 1 addition & 1 deletion setup.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@

setup(
name='trove-classifiers',
version='1.0.0',
version='2020.04.01',
description="Cannonical source for classifiers on PyPI (pypi.org).",
long_description=long_description,
long_description_content_type="text/markdown",
Expand Down
53 changes: 53 additions & 0 deletions tester/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
class InvalidClassifier(Exception):
pass


def trove_tester(classifiers, deprecated_classifiers):
# Check the classifiers
for classifier in classifiers:
split = classifier.split(" :: ")

# Check if this is an invalid top-level classifier
if len(split) == 1:
raise InvalidClassifier(f"Top-level classifier {classifier!r} is invalid")

# Check if all parent classifiers are specified
for i in range(2, len(split)):
parent = " :: ".join(split[:i])
if parent not in classifiers:
raise InvalidClassifier(f"Classifier {parent!r} is missing")

# Check the sub-classifiers
for sub in split:

# Check for whitespace
if sub.strip().rstrip() != sub:
raise InvalidClassifier(
"Classifiers starting or ending with whitespace are invalid"
)

# Check for private classifiers
if sub.lower().startswith("private"):
raise InvalidClassifier(
"Classifiers starting with 'Private' are invalid"
)

# Check for stray colons
if ":" in sub:
raise InvalidClassifier("Classifiers containing ':' are invalid")

# Check the deprecated classifiers
for deprecated_classifier, deprecated_by in deprecated_classifiers.items():

# Check if the classifier is in both lists
if deprecated_classifier in classifiers:
raise InvalidClassifier(
f"Classifier {deprecated_classifier!r} in both valid and deprecated classifiers"
)

# Check if all deprecated_by classifiers exist
for new_classifier in deprecated_by:
if new_classifier not in classifiers:
raise InvalidClassifier(f"Classifier {new_classifier!r} does not exist")

print("All classifiers passed :)")
4 changes: 4 additions & 0 deletions tester/__main__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
from tester import trove_tester
from trove_classifiers import classifiers, deprecated_classifiers

trove_tester(classifiers, deprecated_classifiers)
78 changes: 0 additions & 78 deletions tests/test_classifiers.py

This file was deleted.

55 changes: 55 additions & 0 deletions tests/test_tester.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
import pytest

from tester import trove_tester, InvalidClassifier


@pytest.mark.parametrize(
"classifiers, deprecated_classifiers",
[
({"Foo :: Bar", "Foo :: Bar :: Baz",}, {}),
({"Foo :: Bar"}, {"Biz :: Baz": ["Foo :: Bar"]}),
],
)
def test_success(classifiers, deprecated_classifiers):
trove_tester(classifiers, deprecated_classifiers)


@pytest.mark.parametrize(
"classifiers, deprecated_classifiers, expected",
[
({"Foo", "Foo :: Bar"}, {}, "Top-level classifier 'Foo' is invalid",),
({"Foo :: Bar :: Baz"}, {}, "Classifier 'Foo :: Bar' is missing"),
(
{"Foo :: Bar",},
{"Biz :: Baz": ["Bing :: Bang"]},
"Classifier 'Bing :: Bang' does not exist",
),
(
{"Foo :: Bar",},
{"Foo :: Bar": []},
"Classifier 'Foo :: Bar' in both valid and deprecated classifiers",
),
({"Private :: Foo"}, {}, "Classifiers starting with 'Private' are invalid"),
({"private :: Foo"}, {}, "Classifiers starting with 'Private' are invalid"),
({"Foo :: Private"}, {}, "Classifiers starting with 'Private' are invalid"),
({"Foo :: private"}, {}, "Classifiers starting with 'Private' are invalid"),
(
{" Foo :: Bar"},
{},
"Classifiers starting or ending with whitespace are invalid",
),
(
{"Foo :: Bar "},
{},
"Classifiers starting or ending with whitespace are invalid",
),
({"Foo: :: Bar"}, {}, "Classifiers containing ':' are invalid",),
({"Foo :: B:ar"}, {}, "Classifiers containing ':' are invalid",),
({"Foo :: Bar: Baz"}, {}, "Classifiers containing ':' are invalid",),
],
)
def test_failure(classifiers, deprecated_classifiers, expected):
with pytest.raises(InvalidClassifier) as excinfo:
trove_tester(classifiers, deprecated_classifiers)

assert excinfo.value.args == (expected,)
5 changes: 1 addition & 4 deletions trove_classifiers/__init__.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,3 @@
# THIS FILE IS AUTOGENERATED
# Edit `_internal/classifiers.py` instead, and run `make build` to regenerate

classifiers = {
"Development Status :: 1 - Planning",
"Development Status :: 2 - Pre-Alpha",
Expand Down Expand Up @@ -703,6 +700,6 @@
}
di marked this conversation as resolved.
Show resolved Hide resolved

deprecated_classifiers = {
"Natural Language :: Ukranian": ['Natural Language :: Ukrainian'],
"Natural Language :: Ukranian": ["Natural Language :: Ukrainian"],
"Topic :: Communications :: Chat :: AOL Instant Messenger": [],
}