mirror of
				https://github.com/django/django.git
				synced 2025-10-31 09:41:08 +00:00 
			
		
		
		
	Fixed #24866 -- Added Now() database function
This commit is contained in:
		| @@ -1,7 +1,7 @@ | |||||||
| """ | """ | ||||||
| Classes that represent database functions. | Classes that represent database functions. | ||||||
| """ | """ | ||||||
| from django.db.models import IntegerField | from django.db.models import DateTimeField, IntegerField | ||||||
| from django.db.models.expressions import Func, Value | from django.db.models.expressions import Func, Value | ||||||
|  |  | ||||||
|  |  | ||||||
| @@ -103,6 +103,22 @@ class Lower(Func): | |||||||
|         super(Lower, self).__init__(expression, **extra) |         super(Lower, self).__init__(expression, **extra) | ||||||
|  |  | ||||||
|  |  | ||||||
|  | class Now(Func): | ||||||
|  |     template = 'CURRENT_TIMESTAMP' | ||||||
|  |  | ||||||
|  |     def __init__(self, output_field=None, **extra): | ||||||
|  |         if output_field is None: | ||||||
|  |             output_field = DateTimeField() | ||||||
|  |         super(Now, self).__init__(output_field=output_field, **extra) | ||||||
|  |  | ||||||
|  |     def as_postgresql(self, compiler, connection): | ||||||
|  |         # Postgres' CURRENT_TIMESTAMP means "the time at the start of the | ||||||
|  |         # transaction". We use STATEMENT_TIMESTAMP to be cross-compatible with | ||||||
|  |         # other databases. | ||||||
|  |         self.template = 'STATEMENT_TIMESTAMP()' | ||||||
|  |         return self.as_sql(compiler, connection) | ||||||
|  |  | ||||||
|  |  | ||||||
| class Substr(Func): | class Substr(Func): | ||||||
|     function = 'SUBSTRING' |     function = 'SUBSTRING' | ||||||
|  |  | ||||||
|   | |||||||
| @@ -117,6 +117,21 @@ Usage example:: | |||||||
|     >>> print(author.name_lower) |     >>> print(author.name_lower) | ||||||
|     margaret smith |     margaret smith | ||||||
|  |  | ||||||
|  | Now | ||||||
|  | --- | ||||||
|  |  | ||||||
|  | .. class:: Now() | ||||||
|  |  | ||||||
|  | .. versionadded:: 1.9 | ||||||
|  |  | ||||||
|  | Returns the database server's current date and time when the query is executed. | ||||||
|  |  | ||||||
|  | Usage example:: | ||||||
|  |  | ||||||
|  |     >>> from django.db.models.functions import Now | ||||||
|  |     >>> Article.objects.filter(published__lte=Now()) | ||||||
|  |     [<Article: How to Django>] | ||||||
|  |  | ||||||
| Substr | Substr | ||||||
| ------ | ------ | ||||||
|  |  | ||||||
|   | |||||||
| @@ -240,6 +240,9 @@ Models | |||||||
| * Added the :lookup:`date` lookup to :class:`~django.db.models.DateTimeField` | * Added the :lookup:`date` lookup to :class:`~django.db.models.DateTimeField` | ||||||
|   to allow querying the field by only the date portion. |   to allow querying the field by only the date portion. | ||||||
|  |  | ||||||
|  | * Added the :class:`~django.db.models.functions.Now` database function, which | ||||||
|  |   returns the current date and time. | ||||||
|  |  | ||||||
| CSRF | CSRF | ||||||
| ^^^^ | ^^^^ | ||||||
|  |  | ||||||
|   | |||||||
| @@ -1,8 +1,10 @@ | |||||||
| from __future__ import unicode_literals | from __future__ import unicode_literals | ||||||
|  |  | ||||||
|  | from datetime import datetime, timedelta | ||||||
|  |  | ||||||
| from django.db.models import CharField, TextField, Value as V | from django.db.models import CharField, TextField, Value as V | ||||||
| from django.db.models.functions import ( | from django.db.models.functions import ( | ||||||
|     Coalesce, Concat, Length, Lower, Substr, Upper, |     Coalesce, Concat, Length, Lower, Now, Substr, Upper, | ||||||
| ) | ) | ||||||
| from django.test import TestCase | from django.test import TestCase | ||||||
| from django.utils import six, timezone | from django.utils import six, timezone | ||||||
| @@ -311,3 +313,40 @@ class FunctionTests(TestCase): | |||||||
|             ], |             ], | ||||||
|             lambda a: a.name |             lambda a: a.name | ||||||
|         ) |         ) | ||||||
|  |  | ||||||
|  |     def test_now(self): | ||||||
|  |         ar1 = Article.objects.create( | ||||||
|  |             title='How to Django', | ||||||
|  |             text=lorem_ipsum, | ||||||
|  |             written=timezone.now(), | ||||||
|  |         ) | ||||||
|  |         ar2 = Article.objects.create( | ||||||
|  |             title='How to Time Travel', | ||||||
|  |             text=lorem_ipsum, | ||||||
|  |             written=timezone.now(), | ||||||
|  |         ) | ||||||
|  |  | ||||||
|  |         num_updated = Article.objects.filter(id=ar1.id, published=None).update(published=Now()) | ||||||
|  |         self.assertEqual(num_updated, 1) | ||||||
|  |  | ||||||
|  |         num_updated = Article.objects.filter(id=ar1.id, published=None).update(published=Now()) | ||||||
|  |         self.assertEqual(num_updated, 0) | ||||||
|  |  | ||||||
|  |         ar1.refresh_from_db() | ||||||
|  |         self.assertIsInstance(ar1.published, datetime) | ||||||
|  |  | ||||||
|  |         ar2.published = Now() + timedelta(days=2) | ||||||
|  |         ar2.save() | ||||||
|  |         ar2.refresh_from_db() | ||||||
|  |         self.assertIsInstance(ar2.published, datetime) | ||||||
|  |  | ||||||
|  |         self.assertQuerysetEqual( | ||||||
|  |             Article.objects.filter(published__lte=Now()), | ||||||
|  |             ['How to Django'], | ||||||
|  |             lambda a: a.title | ||||||
|  |         ) | ||||||
|  |         self.assertQuerysetEqual( | ||||||
|  |             Article.objects.filter(published__gt=Now()), | ||||||
|  |             ['How to Time Travel'], | ||||||
|  |             lambda a: a.title | ||||||
|  |         ) | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user