diff -Nru django-measurement-3.1.1/debian/changelog django-measurement-3.2.3/debian/changelog --- django-measurement-3.1.1/debian/changelog 2019-04-14 02:04:35.000000000 +0000 +++ django-measurement-3.2.3/debian/changelog 2021-02-02 22:26:44.000000000 +0000 @@ -1,3 +1,38 @@ +django-measurement (3.2.3-1) unstable; urgency=medium + + [ Ondřej Nový ] + * Bump Standards-Version to 4.4.1. + * d/control: Fix wrong Vcs-*. + * d/watch: Use https protocol. + * d/control: Update Maintainer field with new Debian Python Team + contact address. + * d/control: Update Vcs-* fields with new Debian Python Team Salsa + layout. + + [ Debian Janitor ] + * Trim trailing whitespace. + * Bump debhelper from old 11 to 12. + * Set field Upstream-Name in debian/copyright. + * Set upstream metadata fields: Bug-Database, Bug-Submit, Repository, + Repository-Browse. + * Update standards version to 4.5.0, no changes needed. + + [ Antonio Terceiro ] + * debian/watch: pull from github + * New upstream version 3.2.3 + * debian/rules: set SETUPTOOLS_SCM_PRETEND_VERSION. + The upstream build system is now using use_scm_version=True. Add + python3-setuptools-scm as a build dependency. + * Add new build dependencies: + - python3-pytest-runner + - python3-pytest-cov + - python3-sphinx + * debian/watch: bump to version 4 + * Bump Standards-Version to 4.5.1 + * debian/rules: don't include .coverage in binary package + + -- Antonio Terceiro Tue, 02 Feb 2021 19:26:44 -0300 + django-measurement (3.1.1-1) unstable; urgency=low * Initial release diff -Nru django-measurement-3.1.1/debian/control django-measurement-3.2.3/debian/control --- django-measurement-3.1.1/debian/control 2019-04-14 02:04:35.000000000 +0000 +++ django-measurement-3.2.3/debian/control 2021-02-02 22:26:44.000000000 +0000 @@ -1,21 +1,25 @@ Source: django-measurement -Maintainer: Debian Python Modules Team +Maintainer: Debian Python Team Uploaders: Antonio Terceiro Section: python Priority: optional -Build-Depends: debhelper-compat (= 11), +Build-Depends: debhelper-compat (= 12), dh-python, python3-all (>= 2.6.6-3), python3-django-appconf, python3-measurement, python3-pbr, python3-pytest, + python3-pytest-cov, python3-pytest-django, - python3-setuptools (>= 0.6b3) -Standards-Version: 4.3.0 + python3-pytest-runner, + python3-setuptools (>= 0.6b3), + python3-setuptools-scm, + python3-sphinx, +Standards-Version: 4.5.1 Homepage: https://github.com/coddingtonbear/django-measurement -Vcs-Git: https://salsa.debian.org/python-team/modules/python-django-measurement.git -Vcs-Browser: https://salsa.debian.org/python-team/modules/python-measurement-mptt +Vcs-Git: https://salsa.debian.org/python-team/packages/python-django-measurement.git +Vcs-Browser: https://salsa.debian.org/python-team/packages/python-django-measurement Package: python3-django-measurement Architecture: all diff -Nru django-measurement-3.1.1/debian/copyright django-measurement-3.2.3/debian/copyright --- django-measurement-3.1.1/debian/copyright 2019-04-14 02:04:35.000000000 +0000 +++ django-measurement-3.2.3/debian/copyright 2021-02-02 22:26:44.000000000 +0000 @@ -1,4 +1,5 @@ Format: https://www.debian.org/doc/packaging-manuals/copyright-format/1.0/ +Upstream-Name: django-measurement Files: * Copyright: 2014, Adam Coddington diff -Nru django-measurement-3.1.1/debian/rules django-measurement-3.2.3/debian/rules --- django-measurement-3.1.1/debian/rules 2019-04-14 02:04:35.000000000 +0000 +++ django-measurement-3.2.3/debian/rules 2021-02-02 22:26:44.000000000 +0000 @@ -1,9 +1,14 @@ #!/usr/bin/make -f -# This file was automatically generated by stdeb 0.8.5 at -# Sat, 13 Apr 2019 23:04:35 -0300 +include /usr/share/dpkg/pkg-info.mk + export PYBUILD_NAME=django-measurement export DJANGO_SETTINGS_MODULE=tests.settings +export SETUPTOOLS_SCM_PRETEND_VERSION = $(DEB_VERSION_UPSTREAM) + %: dh $@ --with python3 --buildsystem=pybuild +override_dh_auto_install: + dh_auto_install + find $(CURDIR)/debian/ -name .coverage -delete diff -Nru django-measurement-3.1.1/debian/upstream/metadata django-measurement-3.2.3/debian/upstream/metadata --- django-measurement-3.1.1/debian/upstream/metadata 1970-01-01 00:00:00.000000000 +0000 +++ django-measurement-3.2.3/debian/upstream/metadata 2021-02-02 22:26:44.000000000 +0000 @@ -0,0 +1,5 @@ +--- +Bug-Database: https://github.com/coddingtonbear/django-measurement/issues +Bug-Submit: https://github.com/coddingtonbear/django-measurement/issues/new +Repository: https://github.com/coddingtonbear/django-measurement.git +Repository-Browse: https://github.com/coddingtonbear/django-measurement diff -Nru django-measurement-3.1.1/debian/watch django-measurement-3.2.3/debian/watch --- django-measurement-3.1.1/debian/watch 2019-04-14 02:04:35.000000000 +0000 +++ django-measurement-3.2.3/debian/watch 2021-02-02 22:26:44.000000000 +0000 @@ -1,4 +1,4 @@ -# please also check http://pypi.debian.net/django-measurement/watch -version=3 +# please also check https://pypi.debian.net/django-measurement/watch +version=4 opts=uversionmangle=s/(rc|a|b|c)/~$1/ \ -https://pypi.debian.net/django-measurement/django-measurement-(.+)\.(?:zip|tgz|tbz|txz|(?:tar\.(?:gz|bz2|xz))) +https://github.com/coddingtonbear/django-measurement/tags .*/([\d\.]+)\.tar\.gz diff -Nru django-measurement-3.1.1/django_measurement/conf.py django-measurement-3.2.3/django_measurement/conf.py --- django-measurement-3.1.1/django_measurement/conf.py 2018-10-05 08:20:13.000000000 +0000 +++ django-measurement-3.2.3/django_measurement/conf.py 2020-04-22 10:37:43.000000000 +0000 @@ -2,16 +2,16 @@ from appconf import AppConf from django.conf import settings -__all__ = ('settings',) +__all__ = ("settings",) class DjangoMeasurementConf(AppConf): """Settings for django-measurement.""" - BIDIMENSIONAL_SEPARATOR = '/' + BIDIMENSIONAL_SEPARATOR = "/" """ For measurement classes subclassing a BidimensionalMeasure, this . """ class Meta: - prefix = 'measurement' + prefix = "measurement" diff -Nru django-measurement-3.1.1/django_measurement/forms.py django-measurement-3.2.3/django_measurement/forms.py --- django-measurement-3.1.1/django_measurement/forms.py 2018-10-05 08:20:13.000000000 +0000 +++ django-measurement-3.2.3/django_measurement/forms.py 2020-04-22 10:37:43.000000000 +0000 @@ -9,8 +9,15 @@ class MeasurementWidget(forms.MultiWidget): - def __init__(self, attrs=None, float_widget=None, - unit_choices_widget=None, unit_choices=None, *args, **kwargs): + def __init__( + self, + attrs=None, + float_widget=None, + unit_choices_widget=None, + unit_choices=None, + *args, + **kwargs + ): self.unit_choices = unit_choices @@ -18,20 +25,14 @@ float_widget = forms.TextInput(attrs=attrs) if not unit_choices_widget: - unit_choices_widget = forms.Select( - attrs=attrs, - choices=unit_choices - ) + unit_choices_widget = forms.Select(attrs=attrs, choices=unit_choices) widgets = (float_widget, unit_choices_widget) super(MeasurementWidget, self).__init__(widgets, attrs) def decompress(self, value): if value: - choice_units = set([ - u - for u, n in self.unit_choices - ]) + choice_units = set([u for u, n in self.unit_choices]) unit = value.STANDARD_UNIT if unit not in choice_units: @@ -44,42 +45,56 @@ class MeasurementField(forms.MultiValueField): - def __init__(self, measurement, max_value=None, min_value=None, - unit_choices=None, validators=None, - bidimensional_separator=settings.MEASUREMENT_BIDIMENSIONAL_SEPARATOR, - *args, **kwargs): + def __init__( + self, + measurement, + max_value=None, + min_value=None, + unit_choices=None, + validators=None, + bidimensional_separator=settings.MEASUREMENT_BIDIMENSIONAL_SEPARATOR, + *args, + **kwargs + ): if not issubclass(measurement, (MeasureBase, BidimensionalMeasure)): - raise ValueError( - "%s must be a subclass of MeasureBase" % measurement - ) + raise ValueError("%s must be a subclass of MeasureBase" % measurement) self.measurement_class = measurement if not unit_choices: if issubclass(measurement, BidimensionalMeasure): - assert isinstance(bidimensional_separator, str), \ - "Supplied bidimensional_separator for %s must be of string/unicode type;" \ - " Instead got type %s" % (measurement, str(type(bidimensional_separator)),) - unit_choices = tuple(( + assert isinstance(bidimensional_separator, str), ( + "Supplied bidimensional_separator for %s must be of string/unicode type;" + " Instead got type %s" + % (measurement, str(type(bidimensional_separator)),) + ) + unit_choices = tuple( ( - '{0}__{1}'.format(primary, reference), - '{0}{1}{2}'.format( - getattr(measurement.PRIMARY_DIMENSION, 'LABELS', {}).get( - primary, primary), - bidimensional_separator, - getattr(measurement.REFERENCE_DIMENSION, 'LABELS', {}).get( - reference, reference)), + ( + "{0}__{1}".format(primary, reference), + "{0}{1}{2}".format( + getattr( + measurement.PRIMARY_DIMENSION, "LABELS", {} + ).get(primary, primary), + bidimensional_separator, + getattr( + measurement.REFERENCE_DIMENSION, "LABELS", {} + ).get(reference, reference), + ), + ) + for primary, reference in product( + measurement.PRIMARY_DIMENSION.get_units(), + measurement.REFERENCE_DIMENSION.get_units(), + ) ) - for primary, reference in product( - measurement.PRIMARY_DIMENSION.get_units(), - measurement.REFERENCE_DIMENSION.get_units(), - ) - )) + ) else: - unit_choices = tuple(( - (u, getattr(measurement, 'LABELS', {}).get(u, u)) - for u in measurement.get_units() - )) + unit_choices = tuple( + ( + (u, getattr(measurement, "LABELS", {}).get(u, u)) + for u in measurement.get_units() + ) + ) if validators is None: validators = [] @@ -99,16 +114,17 @@ float_field = forms.FloatField(*args, **kwargs) choice_field = forms.ChoiceField(choices=unit_choices) defaults = { - 'widget': MeasurementWidget( + "widget": MeasurementWidget( float_widget=float_field.widget, unit_choices_widget=choice_field.widget, - unit_choices=unit_choices + unit_choices=unit_choices, ), } defaults.update(kwargs) fields = (float_field, choice_field) - super(MeasurementField, self).__init__(fields, validators=validators, - *args, **defaults) + super(MeasurementField, self).__init__( + fields, validators=validators, *args, **defaults + ) def compress(self, data_list): if not data_list: @@ -118,8 +134,4 @@ if value in self.empty_values: return None - return utils.get_measurement( - self.measurement_class, - value, - unit - ) + return utils.get_measurement(self.measurement_class, value, unit) diff -Nru django-measurement-3.1.1/django_measurement/models.py django-measurement-3.2.3/django_measurement/models.py --- django-measurement-3.1.1/django_measurement/models.py 2018-10-05 08:20:13.000000000 +0000 +++ django-measurement-3.2.3/django_measurement/models.py 2020-04-22 10:37:43.000000000 +0000 @@ -9,7 +9,7 @@ from . import forms from .utils import get_measurement -logger = logging.getLogger('django_measurement') +logger = logging.getLogger("django_measurement") class MeasurementField(FloatField): @@ -20,44 +20,51 @@ MeasureBase, ) default_error_messages = { - 'invalid_type': _( - "'%(value)s' (%(type_given)s) value" - " must be of type %(type_wanted)s." + "invalid_type": _( + "'%(value)s' (%(type_given)s) value" " must be of type %(type_wanted)s." ), } - def __init__(self, verbose_name=None, name=None, measurement=None, - measurement_class=None, unit_choices=None, *args, **kwargs): + def __init__( + self, + verbose_name=None, + name=None, + measurement=None, + measurement_class=None, + unit_choices=None, + *args, + **kwargs + ): if not measurement and measurement_class is not None: warnings.warn( - "\"measurement_class\" will be removed in version 4.0", - DeprecationWarning + '"measurement_class" will be removed in version 4.0', DeprecationWarning ) measurement = getattr(measures, measurement_class) if not measurement: - raise TypeError('MeasurementField() takes a measurement' - ' keyword argument. None given.') + raise TypeError( + "MeasurementField() takes a measurement" + " keyword argument. None given." + ) if not issubclass(measurement, self.MEASURE_BASES): raise TypeError( - 'MeasurementField() takes a measurement keyword argument.' - ' It has to be a valid MeasureBase subclass.' + "MeasurementField() takes a measurement keyword argument." + " It has to be a valid MeasureBase subclass." ) self.measurement = measurement self.widget_args = { - 'measurement': measurement, - 'unit_choices': unit_choices, + "measurement": measurement, + "unit_choices": unit_choices, } - super(MeasurementField, self).__init__(verbose_name, name, - *args, **kwargs) + super(MeasurementField, self).__init__(verbose_name, name, *args, **kwargs) def deconstruct(self): name, path, args, kwargs = super(MeasurementField, self).deconstruct() - kwargs['measurement'] = self.measurement + kwargs["measurement"] = self.measurement return name, path, args, kwargs def get_prep_value(self, value): @@ -75,7 +82,7 @@ return super(MeasurementField, self).get_prep_value(value) def get_default_unit(self): - unit_choices = self.widget_args['unit_choices'] + unit_choices = self.widget_args["unit_choices"] if unit_choices: return unit_choices[0][0] return self.measurement.STANDARD_UNIT @@ -90,32 +97,50 @@ original_unit=self.get_default_unit(), ) + def value_to_string(self, obj): + value = self.value_from_object(obj) + if not isinstance(value, self.MEASURE_BASES): + return value + return "%s:%s" % (value.value, value.unit) + + def deserialize_value_from_string(self, s: str): + parts = s.split(":", 1) + if len(parts) != 2: + return None + value, unit = float(parts[0]), parts[1] + measure = get_measurement(self.measurement, value=value, unit=unit) + return measure + def to_python(self, value): + if value is None: return value elif isinstance(value, self.MEASURE_BASES): return value + elif isinstance(value, str): + parsed = self.deserialize_value_from_string(value) + if parsed is not None: + return parsed value = super(MeasurementField, self).to_python(value) return_unit = self.get_default_unit() - msg = "You assigned a %s instead of %s to %s.%s.%s, unit was guessed to be \"%s\"." % ( - type(value).__name__, - str(self.measurement.__name__), - self.model.__module__, - self.model.__name__, - self.name, - return_unit, + msg = ( + 'You assigned a %s instead of %s to %s.%s.%s, unit was guessed to be "%s".' + % ( + type(value).__name__, + str(self.measurement.__name__), + self.model.__module__, + self.model.__name__, + self.name, + return_unit, + ) ) logger.warning(msg) - return get_measurement( - measure=self.measurement, - value=value, - unit=return_unit, - ) + return get_measurement(measure=self.measurement, value=value, unit=return_unit,) def formfield(self, **kwargs): - defaults = {'form_class': forms.MeasurementField} + defaults = {"form_class": forms.MeasurementField} defaults.update(kwargs) defaults.update(self.widget_args) return super(MeasurementField, self).formfield(**defaults) diff -Nru django-measurement-3.1.1/django_measurement/utils.py django-measurement-3.2.3/django_measurement/utils.py --- django-measurement-3.1.1/django_measurement/utils.py 2018-10-05 08:20:13.000000000 +0000 +++ django-measurement-3.2.3/django_measurement/utils.py 2020-04-22 10:37:43.000000000 +0000 @@ -4,9 +4,7 @@ def get_measurement(measure, value, unit=None, original_unit=None): unit = unit or measure.STANDARD_UNIT - m = measure( - **{unit: value} - ) + m = measure(**{unit: value}) if original_unit: m.unit = original_unit if isinstance(m, BidimensionalMeasure): diff -Nru django-measurement-3.1.1/django_measurement.egg-info/dependency_links.txt django-measurement-3.2.3/django_measurement.egg-info/dependency_links.txt --- django-measurement-3.1.1/django_measurement.egg-info/dependency_links.txt 2018-10-05 08:21:42.000000000 +0000 +++ django-measurement-3.2.3/django_measurement.egg-info/dependency_links.txt 1970-01-01 00:00:00.000000000 +0000 @@ -1 +0,0 @@ - diff -Nru django-measurement-3.1.1/django_measurement.egg-info/not-zip-safe django-measurement-3.2.3/django_measurement.egg-info/not-zip-safe --- django-measurement-3.1.1/django_measurement.egg-info/not-zip-safe 2018-10-05 08:21:42.000000000 +0000 +++ django-measurement-3.2.3/django_measurement.egg-info/not-zip-safe 1970-01-01 00:00:00.000000000 +0000 @@ -1 +0,0 @@ - diff -Nru django-measurement-3.1.1/django_measurement.egg-info/pbr.json django-measurement-3.2.3/django_measurement.egg-info/pbr.json --- django-measurement-3.1.1/django_measurement.egg-info/pbr.json 2018-10-05 08:21:42.000000000 +0000 +++ django-measurement-3.2.3/django_measurement.egg-info/pbr.json 1970-01-01 00:00:00.000000000 +0000 @@ -1 +0,0 @@ -{"git_version": "a91945e", "is_release": false} \ No newline at end of file diff -Nru django-measurement-3.1.1/django_measurement.egg-info/PKG-INFO django-measurement-3.2.3/django_measurement.egg-info/PKG-INFO --- django-measurement-3.1.1/django_measurement.egg-info/PKG-INFO 2018-10-05 08:21:42.000000000 +0000 +++ django-measurement-3.2.3/django_measurement.egg-info/PKG-INFO 1970-01-01 00:00:00.000000000 +0000 @@ -1,86 +0,0 @@ -Metadata-Version: 1.1 -Name: django-measurement -Version: 3.1.1 -Summary: Convenient fields and classes for handling measurements -Home-page: https://github.com/coddingtonbear/django-measurement -Author: Adam Coddington -Author-email: me@adamcoddington.net -License: MIT -Description: |version| |ci| |coverage| |license| - - Django Measurement - ================== - - Easily use, manipulate, and store unit-aware measurement objects using Python - and Django. - - `django.contrib.gis.measure `_ - has these wonderful 'Distance' objects that can be used not only for storing a - unit-aware distance measurement, but also for converting between different - units and adding/subtracting these objects from one another. - - This module provides for a django model field and admin interface for storing - any measurements provided by `python-measurement`_. - - Example use with a model: - - .. code-block:: python - - from django_measurement.models import MeasurementField - from measurement.measures import Volume - from django.db import models - - class BeerConsumptionLogEntry(models.Model): - name = models.CharField(max_length=255) - volume = MeasurementField(measurement=Volume) - - def __unicode__(self): - return u"%s of %s" % (self.name, self.volume) - - entry = BeerConsumptionLogEntry() - entry.name = 'Bear Republic Racer 5' - entry.volume = Volume(us_pint=1) - entry.save() - - These stored measurement objects can be used in all of the usual ways supported - by `python-measurement`_ - too: - - .. code-block:: python - - >>> from measurement.measures import Weight - >>> weight_1 = Weight(lb=125) - >>> weight_2 = Weight(kg=40) - >>> added_together = weight_1 + weight_2 - >>> added_together - Weight(lb=213.184976807) - >>> added_together.kg # Maybe I actually need this value in kg? - 96.699 - - - Documentation for django-measurement is available via `Read the Docs`_. - - Please post issues on GitHub_. - - .. _Read the Docs: https://django-measurement.readthedocs.io/ - .. _GitHub: https://github.com/coddingtonbear/django-measurement/issues - .. _python-measurement: https://github.com/coddingtonbear/python-measurement - - .. |version| image:: https://img.shields.io/pypi/v/django-measurement.svg - :target: https://pypi.python.org/pypi/django-measurement - .. |ci| image:: https://api.travis-ci.org/coddingtonbear/django-measurement.svg?branch=master - :target: https://travis-ci.org/coddingtonbear/django-measurement - .. |coverage| image:: https://codecov.io/gh/coddingtonbear/django-measurement/branch/master/graph/badge.svg - :target: https://codecov.io/gh/coddingtonbear/django-measurement - .. |license| image:: https://img.shields.io/badge/license-MIT-blue.svg - :target: LICENSE - - -Platform: UNKNOWN -Classifier: Development Status :: 5 - Production/Stable -Classifier: Framework :: Django -Classifier: Intended Audience :: Developers -Classifier: License :: OSI Approved :: MIT License -Classifier: Operating System :: OS Independent -Classifier: Environment :: Web Environment -Classifier: Programming Language :: Python -Classifier: Programming Language :: Python :: 3 -Classifier: Framework :: Django diff -Nru django-measurement-3.1.1/django_measurement.egg-info/requires.txt django-measurement-3.2.3/django_measurement.egg-info/requires.txt --- django-measurement-3.1.1/django_measurement.egg-info/requires.txt 2018-10-05 08:21:42.000000000 +0000 +++ django-measurement-3.2.3/django_measurement.egg-info/requires.txt 1970-01-01 00:00:00.000000000 +0000 @@ -1,3 +0,0 @@ -django -django-appconf>=1.0.2 -measurement>=1.6 diff -Nru django-measurement-3.1.1/django_measurement.egg-info/SOURCES.txt django-measurement-3.2.3/django_measurement.egg-info/SOURCES.txt --- django-measurement-3.1.1/django_measurement.egg-info/SOURCES.txt 2018-10-05 08:21:43.000000000 +0000 +++ django-measurement-3.2.3/django_measurement.egg-info/SOURCES.txt 1970-01-01 00:00:00.000000000 +0000 @@ -1,34 +0,0 @@ -.travis.yml -LICENSE -README.rst -requirements-dev.txt -requirements.txt -setup.cfg -setup.py -tox.ini -django_measurement/__init__.py -django_measurement/conf.py -django_measurement/forms.py -django_measurement/models.py -django_measurement/utils.py -django_measurement.egg-info/PKG-INFO -django_measurement.egg-info/SOURCES.txt -django_measurement.egg-info/dependency_links.txt -django_measurement.egg-info/not-zip-safe -django_measurement.egg-info/pbr.json -django_measurement.egg-info/requires.txt -django_measurement.egg-info/top_level.txt -docs/conf.py -docs/index.rst -docs/topics/forms.rst -docs/topics/installation.rst -docs/topics/measures.rst -docs/topics/settings.rst -docs/topics/storing.rst -docs/topics/use.rst -tests/__init__.py -tests/custom_measure_base.py -tests/forms.py -tests/models.py -tests/settings.py -tests/test_fields.py \ No newline at end of file diff -Nru django-measurement-3.1.1/django_measurement.egg-info/top_level.txt django-measurement-3.2.3/django_measurement.egg-info/top_level.txt --- django-measurement-3.1.1/django_measurement.egg-info/top_level.txt 2018-10-05 08:21:42.000000000 +0000 +++ django-measurement-3.2.3/django_measurement.egg-info/top_level.txt 1970-01-01 00:00:00.000000000 +0000 @@ -1 +0,0 @@ -django_measurement diff -Nru django-measurement-3.1.1/docs/conf.py django-measurement-3.2.3/docs/conf.py --- django-measurement-3.1.1/docs/conf.py 2018-10-05 08:20:13.000000000 +0000 +++ django-measurement-3.2.3/docs/conf.py 2020-04-22 10:37:43.000000000 +0000 @@ -1 +1 @@ -master_doc = 'index' +master_doc = "index" diff -Nru django-measurement-3.1.1/.github/workflows/ci.yml django-measurement-3.2.3/.github/workflows/ci.yml --- django-measurement-3.1.1/.github/workflows/ci.yml 1970-01-01 00:00:00.000000000 +0000 +++ django-measurement-3.2.3/.github/workflows/ci.yml 2020-04-22 10:37:43.000000000 +0000 @@ -0,0 +1,85 @@ +name: CI +on: pull_request + +jobs: + + isort: + runs-on: ubuntu-latest + steps: + - uses: actions/setup-python@v1 + - uses: actions/checkout@v2 + - run: python -m pip install isort + - run: isort --check-only --diff --recursive . + + flake8: + runs-on: ubuntu-latest + steps: + - uses: actions/setup-python@v1 + - uses: actions/checkout@v2 + - run: python -m pip install flake8 + - run: flake8 . + + pydocstyle: + runs-on: ubuntu-latest + steps: + - uses: actions/setup-python@v1 + - uses: actions/checkout@v2 + - run: python -m pip install pydocstyle + - run: pydocstyle . + + black: + runs-on: ubuntu-latest + steps: + - uses: actions/setup-python@v1 + - uses: actions/checkout@v2 + - run: python -m pip install black + - run: black --check --diff . + + docs: + runs-on: ubuntu-latest + steps: + - uses: actions/setup-python@v1 + - run: sudo apt-get install -y graphviz + - uses: actions/checkout@v2 + - run: git fetch --prune --unshallow + - run: python setup.py develop + - run: python setup.py build_sphinx -W + + dist: + runs-on: ubuntu-latest + steps: + - uses: actions/setup-python@v1 + - run: python -m pip install --upgrade pip setuptools wheel twine readme-renderer + - uses: actions/checkout@v2 + - run: python setup.py sdist bdist_wheel + - run: python -m twine check dist/* + + pytest: + needs: + - isort + - pydocstyle + - flake8 + - black + strategy: + matrix: + os: + - ubuntu-latest + python-version: + - 3.7 + - 3.8 + django-version: + - "2.2" + - "3.0" + runs-on: ${{ matrix.os }} + steps: + - name: Set up Python ${{ matrix.python-version }} + uses: actions/setup-python@v1 + with: + python-version: ${{ matrix.python-version }} + - uses: actions/checkout@v2 + - run: python -m pip install --upgrade setuptools wheel codecov + - run: python -m pip install Django~=${{ matrix.django-version }} + - run: python setup.py test + - run: codecov + env: + CODECOV_TOKEN: ${{ secrets.CODECOV_TOKEN }} diff -Nru django-measurement-3.1.1/.github/workflows/release.yml django-measurement-3.2.3/.github/workflows/release.yml --- django-measurement-3.1.1/.github/workflows/release.yml 1970-01-01 00:00:00.000000000 +0000 +++ django-measurement-3.2.3/.github/workflows/release.yml 2020-04-22 10:37:43.000000000 +0000 @@ -0,0 +1,20 @@ +name: Release + +on: [release] + +jobs: + + PyPi: + runs-on: ubuntu-latest + steps: + - uses: actions/setup-python@v1 + - uses: actions/checkout@v2 + - name: Install dependencies + run: python -m pip install --upgrade pip setuptools wheel twine + - name: Build dist packages + run: python setup.py sdist bdist_wheel + - name: Upload packages + run: python -m twine upload dist/* + env: + TWINE_USERNAME: ${{ secrets.TWINE_USERNAME }} + TWINE_PASSWORD: ${{ secrets.TWINE_PASSWORD }} diff -Nru django-measurement-3.1.1/.gitignore django-measurement-3.2.3/.gitignore --- django-measurement-3.1.1/.gitignore 1970-01-01 00:00:00.000000000 +0000 +++ django-measurement-3.2.3/.gitignore 2020-04-22 10:37:43.000000000 +0000 @@ -0,0 +1,101 @@ +# Byte-compiled / optimized / DLL files +__pycache__/ +*.py[cod] +*$py.class + +# C extensions +*.so + +# Distribution / packaging +.Python +env/ +build/ +develop-eggs/ +dist/ +downloads/ +eggs/ +.eggs/ +lib/ +lib64/ +parts/ +sdist/ +var/ +wheels/ +*.egg-info/ +.installed.cfg +*.egg + +# PyInstaller +# Usually these files are written by a python script from a template +# before PyInstaller builds the exe, so as to inject date/other infos into it. +*.manifest +*.spec + +# Installer logs +pip-log.txt +pip-delete-this-directory.txt + +# Unit test / coverage reports +htmlcov/ +.tox/ +.coverage +.coverage.* +.cache +nosetests.xml +coverage.xml +*.cover +.hypothesis/ + +# Translations +*.mo +*.pot + +# Django stuff: +*.log +local_settings.py + +# Flask stuff: +instance/ +.webassets-cache + +# Scrapy stuff: +.scrapy + +# Sphinx documentation +docs/_build/ + +# PyBuilder +target/ + +# Jupyter Notebook +.ipynb_checkpoints + +# pyenv +.python-version + +# celery beat schedule file +celerybeat-schedule + +# SageMath parsed files +*.sage.py + +# dotenv +.env + +# virtualenv +.venv +venv/ +ENV/ + +# Spyder project settings +.spyderproject +.spyproject + +# Rope project settings +.ropeproject + +# mkdocs documentation +/site + +# mypy +.mypy_cache/ \ No newline at end of file diff -Nru django-measurement-3.1.1/MANIFEST.in django-measurement-3.2.3/MANIFEST.in --- django-measurement-3.1.1/MANIFEST.in 1970-01-01 00:00:00.000000000 +0000 +++ django-measurement-3.2.3/MANIFEST.in 2020-04-22 10:37:43.000000000 +0000 @@ -0,0 +1,3 @@ +exclude .* +prune tests +prune docs diff -Nru django-measurement-3.1.1/PKG-INFO django-measurement-3.2.3/PKG-INFO --- django-measurement-3.1.1/PKG-INFO 2018-10-05 08:21:43.000000000 +0000 +++ django-measurement-3.2.3/PKG-INFO 1970-01-01 00:00:00.000000000 +0000 @@ -1,86 +0,0 @@ -Metadata-Version: 1.1 -Name: django-measurement -Version: 3.1.1 -Summary: Convenient fields and classes for handling measurements -Home-page: https://github.com/coddingtonbear/django-measurement -Author: Adam Coddington -Author-email: me@adamcoddington.net -License: MIT -Description: |version| |ci| |coverage| |license| - - Django Measurement - ================== - - Easily use, manipulate, and store unit-aware measurement objects using Python - and Django. - - `django.contrib.gis.measure `_ - has these wonderful 'Distance' objects that can be used not only for storing a - unit-aware distance measurement, but also for converting between different - units and adding/subtracting these objects from one another. - - This module provides for a django model field and admin interface for storing - any measurements provided by `python-measurement`_. - - Example use with a model: - - .. code-block:: python - - from django_measurement.models import MeasurementField - from measurement.measures import Volume - from django.db import models - - class BeerConsumptionLogEntry(models.Model): - name = models.CharField(max_length=255) - volume = MeasurementField(measurement=Volume) - - def __unicode__(self): - return u"%s of %s" % (self.name, self.volume) - - entry = BeerConsumptionLogEntry() - entry.name = 'Bear Republic Racer 5' - entry.volume = Volume(us_pint=1) - entry.save() - - These stored measurement objects can be used in all of the usual ways supported - by `python-measurement`_ - too: - - .. code-block:: python - - >>> from measurement.measures import Weight - >>> weight_1 = Weight(lb=125) - >>> weight_2 = Weight(kg=40) - >>> added_together = weight_1 + weight_2 - >>> added_together - Weight(lb=213.184976807) - >>> added_together.kg # Maybe I actually need this value in kg? - 96.699 - - - Documentation for django-measurement is available via `Read the Docs`_. - - Please post issues on GitHub_. - - .. _Read the Docs: https://django-measurement.readthedocs.io/ - .. _GitHub: https://github.com/coddingtonbear/django-measurement/issues - .. _python-measurement: https://github.com/coddingtonbear/python-measurement - - .. |version| image:: https://img.shields.io/pypi/v/django-measurement.svg - :target: https://pypi.python.org/pypi/django-measurement - .. |ci| image:: https://api.travis-ci.org/coddingtonbear/django-measurement.svg?branch=master - :target: https://travis-ci.org/coddingtonbear/django-measurement - .. |coverage| image:: https://codecov.io/gh/coddingtonbear/django-measurement/branch/master/graph/badge.svg - :target: https://codecov.io/gh/coddingtonbear/django-measurement - .. |license| image:: https://img.shields.io/badge/license-MIT-blue.svg - :target: LICENSE - - -Platform: UNKNOWN -Classifier: Development Status :: 5 - Production/Stable -Classifier: Framework :: Django -Classifier: Intended Audience :: Developers -Classifier: License :: OSI Approved :: MIT License -Classifier: Operating System :: OS Independent -Classifier: Environment :: Web Environment -Classifier: Programming Language :: Python -Classifier: Programming Language :: Python :: 3 -Classifier: Framework :: Django diff -Nru django-measurement-3.1.1/README.rst django-measurement-3.2.3/README.rst --- django-measurement-3.1.1/README.rst 2018-10-05 08:20:13.000000000 +0000 +++ django-measurement-3.2.3/README.rst 2020-04-22 10:37:43.000000000 +0000 @@ -26,11 +26,11 @@ name = models.CharField(max_length=255) volume = MeasurementField(measurement=Volume) - def __unicode__(self): - return u"%s of %s" % (self.name, self.volume) + def __str__(self): + return f"{self.name} of {self.volume}" entry = BeerConsumptionLogEntry() - entry.name = 'Bear Republic Racer 5' + entry.name = "Bear Republic Racer 5" entry.volume = Volume(us_pint=1) entry.save() @@ -40,12 +40,12 @@ .. code-block:: python - >>> from measurement.measures import Weight - >>> weight_1 = Weight(lb=125) - >>> weight_2 = Weight(kg=40) + >>> from measurement.measures import Mass + >>> weight_1 = Mass(lb=125) + >>> weight_2 = Mass(kg=40) >>> added_together = weight_1 + weight_2 >>> added_together - Weight(lb=213.184976807) + Mass(lb=213.18497680735112) >>> added_together.kg # Maybe I actually need this value in kg? 96.699 diff -Nru django-measurement-3.1.1/requirements-dev.txt django-measurement-3.2.3/requirements-dev.txt --- django-measurement-3.1.1/requirements-dev.txt 2018-10-05 08:20:13.000000000 +0000 +++ django-measurement-3.2.3/requirements-dev.txt 1970-01-01 00:00:00.000000000 +0000 @@ -1,8 +0,0 @@ --e . -coverage -flake8 -isort -pydocstyle -pep8-naming -pytest -pytest-django diff -Nru django-measurement-3.1.1/requirements.txt django-measurement-3.2.3/requirements.txt --- django-measurement-3.1.1/requirements.txt 2018-10-05 08:20:13.000000000 +0000 +++ django-measurement-3.2.3/requirements.txt 1970-01-01 00:00:00.000000000 +0000 @@ -1,3 +0,0 @@ -django -django-appconf>=1.0.2 -measurement>=1.6 diff -Nru django-measurement-3.1.1/setup.cfg django-measurement-3.2.3/setup.cfg --- django-measurement-3.1.1/setup.cfg 2018-10-05 08:21:43.000000000 +0000 +++ django-measurement-3.2.3/setup.cfg 2020-04-22 10:37:43.000000000 +0000 @@ -1,61 +1,98 @@ [metadata] name = django-measurement author = Adam Coddington -author-email = me@adamcoddington.net -summary = Convenient fields and classes for handling measurements -description-file = README.rst -description-content-type = text/x-rst; charset=UTF-8 -home-page = https://github.com/coddingtonbear/django-measurement +author_email = me@adamcoddington.net +description = Convenient fields and classes for handling measurements +long_description = file: README.rst +long_description_content_type = text/x-rst +url = https://github.com/coddingtonbear/django-measurement license = MIT -classifier = - Development Status :: 5 - Production/Stable - Framework :: Django - Intended Audience :: Developers - License :: OSI Approved :: MIT License - Operating System :: OS Independent - Environment :: Web Environment - Programming Language :: Python - Programming Language :: Python :: 3 - Framework :: Django - -[files] -packages = - django_measurement - -[pbr] -skip_authors = true -skip_changelog = true +license_file = LICENSE +classifier = + Development Status :: 5 - Production/Stable + Intended Audience :: Developers + License :: OSI Approved :: MIT License + Operating System :: OS Independent + Programming Language :: Python + Programming Language :: Python :: 3 + Programming Language :: Python :: 3 :: Only + Programming Language :: Python :: 3.7 + Programming Language :: Python :: 3.8 + Environment :: Web Environment + Framework :: Django + Framework :: Django :: 2.2 + Framework :: Django :: 3.0 + + Topic :: Utilities + Topic :: Scientific/Engineering + Topic :: Scientific/Engineering :: Astronomy + Topic :: Scientific/Engineering :: Atmospheric Science + Topic :: Scientific/Engineering :: Chemistry + Topic :: Scientific/Engineering :: GIS + Topic :: Scientific/Engineering :: Mathematics + Topic :: Scientific/Engineering :: Physics + Topic :: Software Development :: Localization + +keywords = + measurement + django + +[options] +packages = find: +install_requires = + django>=2.2 + django-appconf>=1.0.2 + measurement>=1.6,<4.0 +setup_requires = + setuptools_scm + sphinx + pytest-runner +tests_require = + pytest + pytest-cov + pytest-django + +[options.packages.find] +exclude = + tests + +[bdist_wheel] +universal = 1 [build_sphinx] source-dir = docs build-dir = docs/_build -warning-is-error = 1 + +[aliases] +test = pytest [tool:pytest] -norecursedirs = env docs .tox .eggs -django_settings_module = tests.settings -addopts = --tb=short -rxs +norecursedirs=env docs .tox .eggs +DJANGO_SETTINGS_MODULE=tests.settings +addopts = + --doctest-glob='*.rst' + --doctest-modules + --cov=django_measurement + +[coverage:report] +show_missing = True [flake8] -max-line-length = 99 -max-complexity = 10 -statistics = true -show-source = true -exclude = */migrations/*,docs/*,env/*,.tox/*,.eggs/* +max-line-length=88 +select = C,E,F,W,B,B950 +ignore = E203, E501, W503 +exclude = venv,.tox,.eggs [pydocstyle] -add_ignore = D1 +add-ignore = D1 [isort] atomic = true -multi_line_output = 5 -line_length = 79 +line_length = 88 +multi_line_output=3 +include_trailing_comma=True +force_grid_wrap=0 +use_parentheses=True +known_first_party = django_measurement, tests +default_section=THIRDPARTY combine_as_imports = true -skip = wsgi.py,docs,env,.tox,.eggs -known_first_party = django_measurement,tests -known_third_party = django - -[egg_info] -tag_build = -tag_date = 0 - diff -Nru django-measurement-3.1.1/setup.py django-measurement-3.2.3/setup.py --- django-measurement-3.1.1/setup.py 2018-10-05 08:20:13.000000000 +0000 +++ django-measurement-3.2.3/setup.py 2020-04-22 10:37:43.000000000 +0000 @@ -1,7 +1,4 @@ #!/usr/bin/env python from setuptools import setup -setup( - setup_requires=['pbr'], - pbr=True, -) +setup(name="django-measurement", use_scm_version=True) diff -Nru django-measurement-3.1.1/tests/custom_measure_base.py django-measurement-3.2.3/tests/custom_measure_base.py --- django-measurement-3.1.1/tests/custom_measure_base.py 2018-10-05 08:20:13.000000000 +0000 +++ django-measurement-3.2.3/tests/custom_measure_base.py 2020-04-22 10:37:43.000000000 +0000 @@ -2,33 +2,29 @@ from sympy import S, Symbol __all__ = ( - 'Temperature', - 'Time', - 'DegreePerTime', + "Temperature", + "Time", + "DegreePerTime", ) class Temperature(MeasureBase): - SU = Symbol('kelvin') - STANDARD_UNIT = 'k' - UNITS = { - 'c': SU - S(273.15), - 'f': (SU - S(273.15)) * S('9/5') + 32, - 'k': 1.0 - } + SU = Symbol("kelvin") + STANDARD_UNIT = "k" + UNITS = {"c": SU - S(273.15), "f": (SU - S(273.15)) * S("9/5") + 32, "k": 1.0} LABELS = { - 'c': u'°C', - 'f': u'°F', - 'k': u'°K', + "c": u"°C", + "f": u"°F", + "k": u"°K", } class Time(MeasureBase): UNITS = { - 's': 3600.0, - 'h': 1.0, + "s": 3600.0, + "h": 1.0, } - SI_UNITS = ['s'] + SI_UNITS = ["s"] class DegreePerTime(BidimensionalMeasure): diff -Nru django-measurement-3.1.1/tests/models.py django-measurement-3.2.3/tests/models.py --- django-measurement-3.1.1/tests/models.py 2018-10-05 08:20:13.000000000 +0000 +++ django-measurement-3.2.3/tests/models.py 2020-04-22 10:37:43.000000000 +0000 @@ -11,80 +11,82 @@ measurement=measures.Distance, validators=[ MinValueValidator(measures.Distance(mi=1.0)), - MaxValueValidator(measures.Distance(mi=3.0)) + MaxValueValidator(measures.Distance(mi=3.0)), ], - blank=True, null=True, + blank=True, + null=True, ) measurement_distance_km = MeasurementField( measurement=measures.Distance, - unit_choices=(('km', 'km'),), + unit_choices=(("km", "km"),), validators=[ MinValueValidator(measures.Distance(km=1.0)), - MaxValueValidator(measures.Distance(km=3.0)) + MaxValueValidator(measures.Distance(km=3.0)), ], - blank=True, null=True, + blank=True, + null=True, ) measurement_weight = MeasurementField( measurement=measures.Weight, validators=[ MinValueValidator(measures.Weight(kg=1.0)), - MaxValueValidator(measures.Weight(kg=3.0)) + MaxValueValidator(measures.Weight(kg=3.0)), ], - blank=True, null=True, + blank=True, + null=True, ) measurement_speed = MeasurementField( measurement=measures.Speed, validators=[ MinValueValidator(measures.Speed(mph=1.0)), - MaxValueValidator(measures.Speed(mph=3.0)) + MaxValueValidator(measures.Speed(mph=3.0)), ], - blank=True, null=True, + blank=True, + null=True, ) measurement_temperature = MeasurementField( measurement=measures.Temperature, validators=[ MinValueValidator(measures.Temperature(1.0)), - MaxValueValidator(measures.Temperature(3.0)) + MaxValueValidator(measures.Temperature(3.0)), ], - blank=True, null=True, + blank=True, + null=True, ) measurement_temperature2 = MeasurementField( - measurement_class='Temperature', + measurement_class="Temperature", validators=[ MinValueValidator(measures.Temperature(1.0)), - MaxValueValidator(measures.Temperature(3.0)) + MaxValueValidator(measures.Temperature(3.0)), ], - blank=True, null=True, + blank=True, + null=True, ) measurement_speed_mph = MeasurementField( measurement=measures.Speed, - unit_choices=(('mi__hr', 'mph'),), + unit_choices=(("mi__hr", "mph"),), validators=[ MinValueValidator(measures.Speed(mph=1.0)), - MaxValueValidator(measures.Speed(mph=3.0)) + MaxValueValidator(measures.Speed(mph=3.0)), ], - blank=True, null=True, + blank=True, + null=True, ) measurement_custom_degree_per_time = MeasurementField( - measurement=DegreePerTime, - blank=True, null=True, + measurement=DegreePerTime, blank=True, null=True, ) measurement_custom_temperature = MeasurementField( - measurement=Temperature, - blank=True, null=True, + measurement=Temperature, blank=True, null=True, ) - measurement_custom_time = MeasurementField( - measurement=Time, - blank=True, null=True, - ) + measurement_custom_time = MeasurementField(measurement=Time, blank=True, null=True,) def __str__(self): return self.measurement diff -Nru django-measurement-3.1.1/tests/settings.py django-measurement-3.2.3/tests/settings.py --- django-measurement-3.1.1/tests/settings.py 2018-10-05 08:20:13.000000000 +0000 +++ django-measurement-3.2.3/tests/settings.py 2020-04-22 10:37:43.000000000 +0000 @@ -1,20 +1,15 @@ -DATABASES = { - 'default': { - 'ENGINE': 'django.db.backends.sqlite3', - 'NAME': ':memory:', - } -} +DATABASES = {"default": {"ENGINE": "django.db.backends.sqlite3", "NAME": ":memory:"}} INSTALLED_APPS = ( - 'django.contrib.auth', - 'django.contrib.contenttypes', - 'django_measurement', - 'tests' + "django.contrib.auth", + "django.contrib.contenttypes", + "django_measurement", + "tests", ) SITE_ID = 1 -ROOT_URLCONF = 'core.urls' +ROOT_URLCONF = "core.urls" -SECRET_KEY = 'foobar' +SECRET_KEY = "foobar" USE_L10N = True diff -Nru django-measurement-3.1.1/tests/test_fields.py django-measurement-3.2.3/tests/test_fields.py --- django-measurement-3.1.1/tests/test_fields.py 2018-10-05 08:20:13.000000000 +0000 +++ django-measurement-3.2.3/tests/test_fields.py 2020-04-22 10:37:43.000000000 +0000 @@ -1,5 +1,5 @@ -# -*- coding: utf-8 -*- import pytest +from django.core import serializers from django.core.exceptions import ValidationError from django.utils import module_loading from measurement import measures @@ -8,7 +8,10 @@ from django_measurement.forms import MeasurementField from tests.custom_measure_base import DegreePerTime, Temperature, Time from tests.forms import ( - BiDimensionalLabelTestForm, LabelTestForm, MeasurementTestForm, SITestForm + BiDimensionalLabelTestForm, + LabelTestForm, + MeasurementTestForm, + SITestForm, ) from tests.models import MeasurementTestModel @@ -72,9 +75,7 @@ def test_storage_and_retrieval_of_bidimensional_measurement(self): original_value = measures.Speed(mph=65) - MeasurementTestModel.objects.create( - measurement_speed=original_value, - ) + MeasurementTestModel.objects.create(measurement_speed=original_value,) retrieved = MeasurementTestModel.objects.get() @@ -87,9 +88,7 @@ def test_storage_and_retrieval_of_bidimensional_measurement_choice(self): original_value = measures.Speed(mph=65) - MeasurementTestModel.objects.create( - measurement_speed_mph=original_value, - ) + MeasurementTestModel.objects.create(measurement_speed_mph=original_value,) retrieved = MeasurementTestModel.objects.get() @@ -102,9 +101,7 @@ def test_storage_and_retrieval_of_measurement(self): original_value = measures.Weight(lb=124) - MeasurementTestModel.objects.create( - measurement_weight=original_value, - ) + MeasurementTestModel.objects.create(measurement_weight=original_value,) retrieved = MeasurementTestModel.objects.get() new_value = retrieved.measurement_weight @@ -116,9 +113,7 @@ def test_storage_and_retrieval_of_measurement_choice(self): original_value = measures.Distance(km=100) - MeasurementTestModel.objects.create( - measurement_distance_km=original_value, - ) + MeasurementTestModel.objects.create(measurement_distance_km=original_value,) retrieved = MeasurementTestModel.objects.get() new_value = retrieved.measurement_distance_km @@ -128,17 +123,20 @@ assert new_value.unit == original_value.unit -@pytest.mark.parametrize('fieldname, measure_cls', [ - ('measurement_weight', measures.Weight), - ('measurement_distance', measures.Distance), - ('measurement_distance_km', measures.Distance), - ('measurement_speed', measures.Speed), - ('measurement_temperature', measures.Temperature), - ('measurement_speed_mph', measures.Speed), - ('measurement_custom_degree_per_time', DegreePerTime), - ('measurement_custom_temperature', Temperature), - ('measurement_custom_time', Time), -]) +@pytest.mark.parametrize( + "fieldname, measure_cls", + [ + ("measurement_weight", measures.Weight), + ("measurement_distance", measures.Distance), + ("measurement_distance_km", measures.Distance), + ("measurement_speed", measures.Speed), + ("measurement_temperature", measures.Temperature), + ("measurement_speed_mph", measures.Speed), + ("measurement_custom_degree_per_time", DegreePerTime), + ("measurement_custom_temperature", Temperature), + ("measurement_custom_time", Time), + ], +) class TestDeconstruct: def test_deconstruct(self, fieldname, measure_cls): field = MeasurementTestModel._meta.get_field(fieldname) @@ -146,63 +144,76 @@ name, path, args, kwargs = field.deconstruct() assert name == fieldname - assert path == 'django_measurement.models.MeasurementField' + assert path == "django_measurement.models.MeasurementField" assert args == [] - assert kwargs['blank'] == field.blank - assert kwargs['null'] == field.null - if 'measurement_class' in kwargs: - assert kwargs['measurement_class'] == measure_cls.__name__ - assert kwargs['measurement_class'] == field.measurement_class - else: - assert 'measurement' in kwargs + assert kwargs["blank"] == field.blank + assert kwargs["null"] == field.null + assert kwargs["measurement"] == field.measurement new_cls = module_loading.import_string(path) new_field = new_cls(name=name, *args, **kwargs) assert type(field) == type(new_field) - assert field.deconstruct() == ( - name, path, args, kwargs - ) + assert field.deconstruct() == (name, path, args, kwargs) + + +@pytest.mark.parametrize( + "fieldname, measure, expected_serialized_value", + [ + ("measurement_weight", measures.Weight(kg=4.0), "4.0:kg"), + ("measurement_speed", measures.Speed(mi__hr=2.0), "2.0:mi__hr"), + ], +) +class TestSerialization: + def test_deconstruct(self, fieldname, measure, expected_serialized_value): + instance = MeasurementTestModel(pk=0) + setattr(instance, fieldname, measure) + serialized_object = serializers.serialize("python", [instance])[0] + serialized_value = serialized_object["fields"][fieldname] + + assert isinstance(serialized_value, str) + assert serialized_value == expected_serialized_value + + deserialized_obj = next(serializers.deserialize("python", [serialized_object])) + deserialized_value = getattr(deserialized_obj.object, fieldname) + + assert deserialized_value == measure class TestMeasurementFormField: def test_max_value(self): - valid_form = MeasurementTestForm({ - 'measurement_distance_0': 2.0, - 'measurement_distance_1': 'mi', - }) - invalid_form = MeasurementTestForm({ - 'measurement_distance_0': 4.0, - 'measurement_distance_1': 'mi', - }) + valid_form = MeasurementTestForm( + {"measurement_distance_0": 2.0, "measurement_distance_1": "mi"} + ) + invalid_form = MeasurementTestForm( + {"measurement_distance_0": 4.0, "measurement_distance_1": "mi"} + ) assert valid_form.is_valid() assert not invalid_form.is_valid() field = MeasurementField(measures.Distance, max_value=measures.Distance(mi=1)) - field.clean([0.5, 'mi']) + field.clean([0.5, "mi"]) with pytest.raises(ValidationError) as e: - field.clean([2.0, 'mi']) - assert 'Ensure this value is less than or equal to 1.0 mi.' in str(e) + field.clean([2.0, "mi"]) + assert "Ensure this value is less than or equal to 1.0 mi." in str(e) with pytest.raises(ValueError) as e: MeasurementField(measures.Distance, max_value=1.0) assert bytes(e) == '"max_value" must be a measure, got float' def test_form_storage(self): - form = MeasurementTestForm({ - 'measurement_distance_0': 2.0, - 'measurement_distance_1': 'mi', - }) + form = MeasurementTestForm( + {"measurement_distance_0": 2.0, "measurement_distance_1": "mi"} + ) assert form.is_valid() obj = form.save() assert obj.measurement_distance == measures.Distance(mi=2) def test_form_bidir(self): - form = MeasurementTestForm({ - 'measurement_speed_0': 2.0, - 'measurement_speed_1': 'mi__hr', - }) + form = MeasurementTestForm( + {"measurement_speed_0": 2.0, "measurement_speed_1": "mi__hr"} + ) assert form.is_valid() obj = form.save() @@ -210,10 +221,10 @@ def test_min_value(self): field = MeasurementField(measures.Distance, min_value=measures.Distance(mi=1.0)) - field.clean([2.0, 'mi']) + field.clean([2.0, "mi"]) with pytest.raises(ValidationError) as e: - field.clean([0.5, 'mi']) - assert 'Ensure this value is greater than or equal to 1.0 mi.' in str(e) + field.clean([0.5, "mi"]) + assert "Ensure this value is greater than or equal to 1.0 mi." in str(e) with pytest.raises(ValueError) as e: MeasurementField(measures.Distance, min_value=1.0) @@ -221,8 +232,7 @@ def test_float_casting(self, caplog): m = MeasurementTestModel( - measurement_distance=float(2000), - measurement_distance_km=2, + measurement_distance=float(2000), measurement_distance_km=2, ) m.full_clean() @@ -230,32 +240,34 @@ assert m.measurement_distance.unit == Distance.STANDARD_UNIT assert m.measurement_distance_km.value == 2 - assert m.measurement_distance_km.unit == 'km' + assert m.measurement_distance_km.unit == "km" assert m.measurement_distance_km == Distance(km=2) m.measurement_distance_km = Distance(km=1) m.full_clean() assert m.measurement_distance_km.value == 1 - assert m.measurement_distance_km.unit == 'km' + assert m.measurement_distance_km.unit == "km" assert m.measurement_distance_km == Distance(km=1) record = caplog.records[0] - assert record.levelname == 'WARNING' - assert record.message == ('You assigned a float instead of Distance to' - ' tests.models.MeasurementTestModel.measurement_distance,' - ' unit was guessed to be "m".') + assert record.levelname == "WARNING" + assert record.message == ( + "You assigned a float instead of Distance to" + " tests.models.MeasurementTestModel.measurement_distance," + ' unit was guessed to be "m".' + ) def test_unicode_labels(self): form = LabelTestForm() - assert ('c', u'°C') in form.fields['simple'].fields[1].choices - assert ('f', u'°F') in form.fields['simple'].fields[1].choices - assert ('k', u'°K') in form.fields['simple'].fields[1].choices + assert ("c", u"°C") in form.fields["simple"].fields[1].choices + assert ("f", u"°F") in form.fields["simple"].fields[1].choices + assert ("k", u"°K") in form.fields["simple"].fields[1].choices si_form = SITestForm() - assert ('ms', 'ms') in si_form.fields['simple'].fields[1].choices - assert ('Ps', 'Ps') in si_form.fields['simple'].fields[1].choices + assert ("ms", "ms") in si_form.fields["simple"].fields[1].choices + assert ("Ps", "Ps") in si_form.fields["simple"].fields[1].choices bi_dim_form = BiDimensionalLabelTestForm() - assert ('c__ms', u'°C/ms') in bi_dim_form.fields['simple'].fields[1].choices - assert ('c__Ps', u'°C/Ps') in bi_dim_form.fields['simple'].fields[1].choices + assert ("c__ms", u"°C/ms") in bi_dim_form.fields["simple"].fields[1].choices + assert ("c__Ps", u"°C/Ps") in bi_dim_form.fields["simple"].fields[1].choices diff -Nru django-measurement-3.1.1/tox.ini django-measurement-3.2.3/tox.ini --- django-measurement-3.1.1/tox.ini 2018-10-05 08:20:13.000000000 +0000 +++ django-measurement-3.2.3/tox.ini 1970-01-01 00:00:00.000000000 +0000 @@ -1,26 +0,0 @@ -[tox] -envlist = py{36}-dj{111,20,master},qa,docs -[testenv] -deps= - -rrequirements-dev.txt - dj111: https://github.com/django/django/archive/stable/1.11.x.tar.gz#egg=django - dj20: https://github.com/django/django/archive/stable/2.0.x.tar.gz#egg=django - djmaster: https://github.com/django/django/archive/master.tar.gz#egg=django -commands= - coverage run --source=django_measurement -m 'pytest' \ - --basetemp={envtmpdir} \ - --ignore=.tox \ - {posargs} - -[testenv:qa] -changedir={toxinidir} -deps= - -rrequirements-dev.txt -commands= - isort --check-only --recursive --diff {posargs} - flake8 --jobs=2 {posargs} - pydocstyle --verbose --explain --source --count {posargs} - -[testenv:docs] -deps=sphinx -commands=python setup.py build_sphinx diff -Nru django-measurement-3.1.1/.travis.yml django-measurement-3.2.3/.travis.yml --- django-measurement-3.1.1/.travis.yml 2018-10-05 08:20:13.000000000 +0000 +++ django-measurement-3.2.3/.travis.yml 1970-01-01 00:00:00.000000000 +0000 @@ -1,38 +0,0 @@ -language: python -sudo: false -cache: pip -python: 3.6 -env: - matrix: - - DJANGO=111 - - DJANGO=20 - - DJANGO=master - - TOXENV=qa - - TOXENV=docs -matrix: - fast_finish: true - allow_failures: - - env: DJANGO=master -install: -- pip install --upgrade pip tox -- pip install -U codecov -before_script: -- | - if [[ -z $TOXENV ]]; then - export TOXENV=py$(echo $TRAVIS_PYTHON_VERSION | sed -e 's/\.//g')-dj$DJANGO - fi -- echo $TOXENV -script: -- tox -e $TOXENV -after_success: -- codecov -deploy: - provider: pypi - user: codingjoe - password: - secure: a5tlCZBkW+ZaTq0ZAJX5nrucGbzV3TCPxY5wWBTrcFDynGVhSEkN/xG3obxi9dNxRP3Y/iTDZp+CUJraUxHehbsFZ7vtRWXWOnhWeJrlVrc0/KPmMWpHOAbTZ/UIZZfn8q362HAb8c6BcrAWOK00Bpt3DBIzzGXvsg2sdcrpW4k= - on: - tags: true - distributions: sdist bdist_wheel - repo: coddingtonbear/django-measurement - branch: master