Skip to content
This repository has been archived by the owner on Dec 22, 2023. It is now read-only.

Rename module #5

Open
wants to merge 10 commits into
base: master
Choose a base branch
from
Open
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
49 changes: 49 additions & 0 deletions .github/workflows/tests.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
name: Tests

on:
push:
branches:
- main
pull_request:

jobs:
tests:
name: Python ${{ matrix.python-version }}
runs-on: ubuntu-latest
strategy:
fail-fast: false
matrix:
python-version:
- "3.7"
- "3.8"
- "3.9"
- "3.10"

steps:
- uses: actions/checkout@v3
- name: Set up Python ${{ matrix.python-version }}
uses: actions/setup-python@v3
with:
python-version: ${{ matrix.python-version }}
- name: Install dependencies
run: |
python -m pip install --upgrade pip wheel setuptools tox
- name: Run tox targets for ${{ matrix.python-version }}
run: |
ENV_PREFIX=$(tr -C -d "0-9" <<< "${{ matrix.python-version }}")
TOXENV=$(tox --listenvs | grep "^py$ENV_PREFIX" | tr '\n' ',') python -m tox

# lint:
# name: Lint
# runs-on: ubuntu-latest
# steps:
# - uses: actions/checkout@v3
# - name: Set up Python
# uses: actions/setup-python@v3
# with:
# python-version: "3.10"
# - name: Install dependencies
# run: |
# python -m pip install --upgrade pip tox
# - name: Run lint
# run: tox -e style
11 changes: 11 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
# Byte-compiled / optimized / DLL files
__pycache__/
*.py[cod]
*$py.class
*~


db.sqlite3
.tox

django_timedeltafield.egg-info/
11 changes: 11 additions & 0 deletions manage.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
#!/usr/bin/env python
import os
import sys


if __name__ == "__main__":
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "test_app.settings")

from django.core.management import execute_from_command_line

execute_from_command_line(sys.argv)
8 changes: 4 additions & 4 deletions setup.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,17 +3,17 @@

setup(
name = "django-timedeltafield",
version = open(os.path.join(os.path.dirname(__file__), 'timedelta', 'VERSION')).read().strip(),
version = open(os.path.join(os.path.dirname(__file__), 'timedelta_field', 'VERSION')).read().strip(),
description = "TimedeltaField for django models",
long_description = open("README").read(),
url = "http://hg.schinckel.net/django-timedelta-field/",
author = "Matthew Schinckel",
author_email = "[email protected]",
packages = [
"timedelta",
"timedelta.templatetags",
"timedelta_field",
"timedelta_field.templatetags",
],
package_data = {'timedelta': ['VERSION']},
package_data = {'timedelta_field': ['VERSION']},
classifiers = [
'Programming Language :: Python',
'License :: OSI Approved :: BSD License',
Expand Down
48 changes: 48 additions & 0 deletions test_app/migrations/0001_initial.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
# Generated by Django 4.1 on 2022-09-02 20:04

import datetime
from django.db import migrations, models
import timedelta_field.fields


class Migration(migrations.Migration):

initial = True

dependencies = []

operations = [
migrations.CreateModel(
name="MinMaxTestModel",
fields=[
(
"id",
models.AutoField(
auto_created=True,
primary_key=True,
serialize=False,
verbose_name="ID",
),
),
(
"min",
timedelta_field.fields.TimedeltaField(
min_value=datetime.timedelta(days=1)
),
),
(
"max",
timedelta_field.fields.TimedeltaField(
max_value=datetime.timedelta(days=1)
),
),
(
"minmax",
timedelta_field.fields.TimedeltaField(
max_value=datetime.timedelta(days=7),
min_value=datetime.timedelta(days=1),
),
),
],
),
]
10 changes: 10 additions & 0 deletions test_app/models.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@

from django.db import models
from timedelta_field.fields import TimedeltaField
import datetime


class MinMaxTestModel(models.Model):
min = TimedeltaField(min_value=datetime.timedelta(1))
max = TimedeltaField(max_value=datetime.timedelta(1))
minmax = TimedeltaField(min_value=datetime.timedelta(1), max_value=datetime.timedelta(7))
108 changes: 108 additions & 0 deletions test_app/settings.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,108 @@
"""
Django settings for test_project project.

For more information on this file, see
https://docs.djangoproject.com/en/1.7/topics/settings/

For the full list of settings and their values, see
https://docs.djangoproject.com/en/1.7/ref/settings/
"""

# Build paths inside the project like this: os.path.join(BASE_DIR, ...)
import os
from typing import List


BASE_DIR = os.path.dirname(os.path.dirname(__file__))


# Quick-start development settings - unsuitable for production
# See https://docs.djangoproject.com/en/1.7/howto/deployment/checklist/

# SECURITY WARNING: keep the secret key used in production secret!
SECRET_KEY = "f8fkupu8pa%%u$wgk6c!os39el41v7i7^u*8xf#g5p@+c&)b#^"

# SECURITY WARNING: don't run with debug turned on in production!
DEBUG = True

TEMPLATES = [
{
"BACKEND": "django.template.backends.django.DjangoTemplates",
"APP_DIRS": True,
"OPTIONS": {
"debug": True,
"context_processors": [
"django.contrib.auth.context_processors.auth",
"django.template.context_processors.debug",
"django.template.context_processors.i18n",
"django.template.context_processors.media",
"django.template.context_processors.static",
"django.template.context_processors.tz",
"django.template.context_processors.request",
"django.contrib.messages.context_processors.messages",
],
},
},
]

ALLOWED_HOSTS: List[str] = []


# Application definition

INSTALLED_APPS = (
"django.contrib.admin",
"django.contrib.auth",
"django.contrib.contenttypes",
"django.contrib.sessions",
"django.contrib.messages",
"django.contrib.staticfiles",
"timedelta_field",
"test_app",
)

MIDDLEWARE = (
"django.contrib.sessions.middleware.SessionMiddleware",
"django.middleware.common.CommonMiddleware",
"django.middleware.csrf.CsrfViewMiddleware",
"django.contrib.auth.middleware.AuthenticationMiddleware",
"django.contrib.messages.middleware.MessageMiddleware",
"django.middleware.clickjacking.XFrameOptionsMiddleware",
)
MIDDLEWARE_CLASSES = MIDDLEWARE

# ROOT_URLCONF = "test_project.urls"

# WSGI_APPLICATION = "test_project.wsgi.application"

DEFAULT_AUTO_FIELD = "django.db.models.BigAutoField"


# Database
# https://docs.djangoproject.com/en/1.7/ref/settings/#databases

DATABASES = {
"default": {
"ENGINE": "django.db.backends.sqlite3",
"NAME": os.path.join(BASE_DIR, "db.sqlite3"),
}
}

# Internationalization
# https://docs.djangoproject.com/en/1.7/topics/i18n/

LANGUAGE_CODE = "en-us"

TIME_ZONE = "UTC"

USE_I18N = True

USE_L10N = True

USE_TZ = True


# Static files (CSS, JavaScript, Images)
# https://docs.djangoproject.com/en/1.7/howto/static-files/

STATIC_URL = "/static/"
2 changes: 1 addition & 1 deletion tests.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ def main(db_engine='sqlite3'):
You can play with a django model without a complete django app installation.
http://www.djangosnippets.org/snippets/1044/
"""
os.environ["DJANGO_SETTINGS_MODULE"] = "django.conf.global_settings"
os.environ["DJANGO_SETTINGS_MODULE"] = "test_app.settings"
from django.conf import global_settings

global_settings.INSTALLED_APPS = (
Expand Down
File renamed without changes.
File renamed without changes.
28 changes: 25 additions & 3 deletions timedelta/fields.py → timedelta_field/fields.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
from django.db import models
from django.core.exceptions import ValidationError
from django.utils import six

from collections import defaultdict
import datetime
Expand All @@ -10,7 +9,7 @@

# TODO: Figure out why django admin thinks fields of this type have changed every time an object is saved.

class TimedeltaField(six.with_metaclass(models.SubfieldBase, models.Field)):
class TimedeltaField(models.Field):
"""
Store a datetime.timedelta as an INTERVAL in postgres, or a
CHAR(20) in other database backends.
Expand Down Expand Up @@ -39,7 +38,7 @@ def to_python(self, value):
def get_prep_value(self, value):
if self.null and value == "":
return None
if (value is None) or isinstance(value, six.string_types):
if (value is None) or isinstance(value, str):
return value
return str(value).replace(',', '')

Expand Down Expand Up @@ -87,3 +86,26 @@ def deconstruct(self):
if self._max_value is not None:
kwargs['max_value'] = self._max_value
return name, path, args, kwargs

def contribute_to_class(self, cls, name):
super(TimedeltaField, self).contribute_to_class(cls, name)
setattr(cls, name, CastOnAssignDescriptor(self))


class CastOnAssignDescriptor(object):
"""
A property descriptor which ensures that `field.to_python()` is called on _every_ assignment to the field.
This used to be provided by the `django.db.models.subclassing.Creator` class, which in turn
was used by the deprecated-in-Django-1.10 `SubfieldBase` class, hence the reimplementation here.
"""

def __init__(self, field):
self.field = field

def __get__(self, obj, type=None):
if obj is None:
return self
return obj.__dict__[self.field.name]

def __set__(self, obj, value):
obj.__dict__[self.field.name] = self.field.to_python(value)
Loading