Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP

Loading…

Fixed #19988 -- Updated is_safe filter check for integer variables. #896

Closed
wants to merge 9 commits into from

7 participants

@matiasb

No description provided.

Alex Gaynor and others added some commits
Alex Gaynor Fixed a line that was overindented. 1aca9d9
@charettes charettes Merge pull request #993 from almostabc/template-include-docs-update
Removed a trailing space in the template builtins docs.
d7fa802
@aaugustin aaugustin Removed LocaleMiddleware from settings template.
It was added in 3f1c7b7.

Single language sites should always be translated in LANGUAGE_CODE,
regardless of the browser's Accept-Language. Having LocaleMiddleware
enabled can result in having some parts, like the admin, translated
in an unexpected language, typically if someone browses a non-English
website on a system set up in English. Since most websites won't be
translated in multiple languages — especially at the time they're
created — it's better not to enable LocaleMiddleware by default.

Thanks Ramiro for the feedback.
2322906
@claudep claudep Added release note about percent literals in cursor.execute
Thanks Aymeric Augustin for noticing the omission and Tim Graham
for the text review.
Fixes #9055 (again).
975c5af
@ptone ptone Fixed #20114 -- support custom project login_url in tests
Thanks to Matias Bordese for the patch
a49e7dd
@charettes charettes Fixed #20207 -- Handle ManyToManyField with a unicode name correctly. 216580e
@andrewjesaitis andrewjesaitis Explicitly removes dismissClock
Uses the removeEvent function in core.js to remove the function from
the document click event.
Refs #4045.
4509a1b
@andrewjesaitis andrewjesaitis Explicitly removes dismissCalendar
Uses the removeEvent function in core.js to remove the dismissCalendar
function from the document click event.
Fixes #4045.
5ab66de
@matiasb matiasb Fixed #19988 -- Updated is_safe filter check for integer variables. fe91a49
@timgraham timgraham closed this
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Commits on Apr 4, 2013
  1. Fixed a line that was overindented.

    Alex Gaynor authored
Commits on Apr 5, 2013
  1. @charettes

    Merge pull request #993 from almostabc/template-include-docs-update

    charettes authored
    Removed a trailing space in the template builtins docs.
  2. @aaugustin

    Removed LocaleMiddleware from settings template.

    aaugustin authored
    It was added in 3f1c7b7.
    
    Single language sites should always be translated in LANGUAGE_CODE,
    regardless of the browser's Accept-Language. Having LocaleMiddleware
    enabled can result in having some parts, like the admin, translated
    in an unexpected language, typically if someone browses a non-English
    website on a system set up in English. Since most websites won't be
    translated in multiple languages — especially at the time they're
    created — it's better not to enable LocaleMiddleware by default.
    
    Thanks Ramiro for the feedback.
  3. @claudep

    Added release note about percent literals in cursor.execute

    claudep authored
    Thanks Aymeric Augustin for noticing the omission and Tim Graham
    for the text review.
    Fixes #9055 (again).
  4. @ptone

    Fixed #20114 -- support custom project login_url in tests

    ptone authored
    Thanks to Matias Bordese for the patch
  5. @charettes
Commits on Apr 6, 2013
  1. @andrewjesaitis @claudep

    Explicitly removes dismissClock

    andrewjesaitis authored claudep committed
    Uses the removeEvent function in core.js to remove the function from
    the document click event.
    Refs #4045.
  2. @andrewjesaitis @claudep

    Explicitly removes dismissCalendar

    andrewjesaitis authored claudep committed
    Uses the removeEvent function in core.js to remove the dismissCalendar
    function from the document click event.
    Fixes #4045.
Commits on Apr 7, 2013
  1. @matiasb
This page is out of date. Refresh to see the latest.
View
1  django/conf/project_template/project_name/settings.py
@@ -40,7 +40,6 @@
MIDDLEWARE_CLASSES = (
'django.contrib.sessions.middleware.SessionMiddleware',
- 'django.middleware.locale.LocaleMiddleware',
'django.middleware.common.CommonMiddleware',
'django.middleware.csrf.CsrfViewMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
View
12 django/contrib/admin/static/admin/js/admin/DateTimeShortcuts.js
@@ -6,6 +6,8 @@ var DateTimeShortcuts = {
calendars: [],
calendarInputs: [],
clockInputs: [],
+ dismissClockFunc: [],
+ dismissCalendarFunc: [],
calendarDivName1: 'calendarbox', // name of calendar <div> that gets toggled
calendarDivName2: 'calendarin', // name of <div> that contains calendar
calendarLinkName: 'calendarlink',// name of the link that is used to toggle
@@ -39,6 +41,7 @@ var DateTimeShortcuts = {
addClock: function(inp) {
var num = DateTimeShortcuts.clockInputs.length;
DateTimeShortcuts.clockInputs[num] = inp;
+ DateTimeShortcuts.dismissClockFunc[num] = function() { DateTimeShortcuts.dismissClock(num); return true; };
// Shortcut links (clock icon and "Now" link)
var shortcuts_span = document.createElement('span');
@@ -118,11 +121,11 @@ var DateTimeShortcuts = {
// Show the clock box
clock_box.style.display = 'block';
- addEvent(window.document, 'click', function() { DateTimeShortcuts.dismissClock(num); return true; });
+ addEvent(document, 'click', DateTimeShortcuts.dismissClockFunc[num]);
},
dismissClock: function(num) {
document.getElementById(DateTimeShortcuts.clockDivName + num).style.display = 'none';
- window.document.onclick = null;
+ removeEvent(document, 'click', DateTimeShortcuts.dismissClockFunc[num]);
},
handleClockQuicklink: function(num, val) {
DateTimeShortcuts.clockInputs[num].value = val;
@@ -134,6 +137,7 @@ var DateTimeShortcuts = {
var num = DateTimeShortcuts.calendars.length;
DateTimeShortcuts.calendarInputs[num] = inp;
+ DateTimeShortcuts.dismissCalendarFunc[num] = function() { DateTimeShortcuts.dismissCalendar(num); return true; };
// Shortcut links (calendar icon and "Today" link)
var shortcuts_span = document.createElement('span');
@@ -241,11 +245,11 @@ var DateTimeShortcuts = {
cal_box.style.top = Math.max(0, findPosY(cal_link) - 75) + 'px';
cal_box.style.display = 'block';
- addEvent(window.document, 'click', function() { DateTimeShortcuts.dismissCalendar(num); return true; });
+ addEvent(document, 'click', DateTimeShortcuts.dismissCalendarFunc[num]);
},
dismissCalendar: function(num) {
document.getElementById(DateTimeShortcuts.calendarDivName1+num).style.display = 'none';
- window.document.onclick = null;
+ removeEvent(document, 'click', DateTimeShortcuts.dismissCalendarFunc[num]);
},
drawPrev: function(num) {
DateTimeShortcuts.calendars[num].drawPreviousMonth();
View
5 django/contrib/auth/tests/test_decorators.py
@@ -1,3 +1,4 @@
+from django.conf import settings
from django.contrib.auth.decorators import login_required
from django.contrib.auth.tests.test_views import AuthViewsTestCase
from django.contrib.auth.tests.utils import skipIfCustomUser
@@ -27,11 +28,13 @@ def normal_view(request):
pass
login_required(normal_view)
- def testLoginRequired(self, view_url='/login_required/', login_url='/login/'):
+ def testLoginRequired(self, view_url='/login_required/', login_url=None):
"""
Check that login_required works on a simple view wrapped in a
login_required decorator.
"""
+ if login_url is None:
+ login_url = settings.LOGIN_URL
response = self.client.get(view_url)
self.assertEqual(response.status_code, 302)
self.assertTrue(login_url in response.url)
View
36 django/contrib/humanize/tests.py
@@ -38,11 +38,14 @@ def now(self, tz=None):
class HumanizeTests(TestCase):
- def humanize_tester(self, test_list, result_list, method):
+ def humanize_tester(self, test_list, result_list, method, filter_is_safe=False):
for test_content, result in zip(test_list, result_list):
t = Template('{%% load humanize %%}{{ test_content|%s }}' % method)
rendered = t.render(Context(locals())).strip()
- self.assertEqual(rendered, escape(result),
+ expected = result
+ if not filter_is_safe:
+ expected = escape(result)
+ self.assertEqual(rendered, expected,
msg="%s test failed, produced '%s', should've produced '%s'" % (method, rendered, result))
def test_ordinal(self):
@@ -51,10 +54,21 @@ def test_ordinal(self):
'something else', None)
result_list = ('1st', '2nd', '3rd', '4th', '11th',
'12th', '13th', '101st', '102nd', '103rd',
- '111th', 'something else', None)
+ '111th', 'something else', 'None')
with translation.override('en'):
- self.humanize_tester(test_list, result_list, 'ordinal')
+ self.humanize_tester(test_list, result_list, 'ordinal', filter_is_safe=True)
+
+ def test_intvar_ordinal_is_safe(self):
+ # related to bug #19988
+ with translation.override('fr'):
+ test_list = (1, 2, 3, 4, 11, 12, 13, 101, 102, 103, 111, None)
+ result_list = ('1<sup>er</sup>', '2<sup>e</sup>',
+ '3<sup>e</sup>', '4<sup>e</sup>', '11<sup>e</sup>',
+ '12<sup>e</sup>', '13<sup>e</sup>',
+ '101<sup>er</sup>', '102<sup>e</sup>',
+ '103<sup>e</sup>', '111<sup>e</sup>', 'None')
+ self.humanize_tester(test_list, result_list, 'ordinal', filter_is_safe=True)
def test_intcomma(self):
test_list = (100, 1000, 10123, 10311, 1000000, 1234567.25,
@@ -62,10 +76,10 @@ def test_intcomma(self):
None)
result_list = ('100', '1,000', '10,123', '10,311', '1,000,000', '1,234,567.25',
'100', '1,000', '10,123', '10,311', '1,000,000', '1,234,567.1234567', '1,234,567.1234567',
- None)
+ 'None')
with translation.override('en'):
- self.humanize_tester(test_list, result_list, 'intcomma')
+ self.humanize_tester(test_list, result_list, 'intcomma', filter_is_safe=True)
def test_l10n_intcomma(self):
test_list = (100, 1000, 10123, 10311, 1000000, 1234567.25,
@@ -73,17 +87,17 @@ def test_l10n_intcomma(self):
None)
result_list = ('100', '1,000', '10,123', '10,311', '1,000,000', '1,234,567.25',
'100', '1,000', '10,123', '10,311', '1,000,000', '1,234,567.1234567', '1,234,567.1234567',
- None)
+ 'None')
with self.settings(USE_L10N=True, USE_THOUSAND_SEPARATOR=False):
with translation.override('en'):
- self.humanize_tester(test_list, result_list, 'intcomma')
+ self.humanize_tester(test_list, result_list, 'intcomma', filter_is_safe=True)
def test_intcomma_without_number_grouping(self):
# Regression for #17414
with translation.override('ja'):
with self.settings(USE_L10N=True):
- self.humanize_tester([100], ['100'], 'intcomma')
+ self.humanize_tester([100], ['100'], 'intcomma', filter_is_safe=True)
def test_intword(self):
test_list = ('100', '1000000', '1200000', '1290000',
@@ -101,10 +115,10 @@ def test_i18n_intcomma(self):
test_list = (100, 1000, 10123, 10311, 1000000, 1234567.25,
'100', '1000', '10123', '10311', '1000000', None)
result_list = ('100', '1.000', '10.123', '10.311', '1.000.000', '1.234.567,25',
- '100', '1.000', '10.123', '10.311', '1.000.000', None)
+ '100', '1.000', '10.123', '10.311', '1.000.000', 'None')
with self.settings(USE_L10N=True, USE_THOUSAND_SEPARATOR=True):
with translation.override('de'):
- self.humanize_tester(test_list, result_list, 'intcomma')
+ self.humanize_tester(test_list, result_list, 'intcomma', filter_is_safe=True)
def test_i18n_intword(self):
test_list = ('100', '1000000', '1200000', '1290000',
View
2  django/db/models/base.py
@@ -163,7 +163,7 @@ def __new__(cls, name, bases, attrs):
else:
base = parent
if base is None:
- raise TypeError("Proxy model '%s' has no non-abstract model base class." % name)
+ raise TypeError("Proxy model '%s' has no non-abstract model base class." % name)
if (new_class._meta.local_fields or
new_class._meta.local_many_to_many):
raise FieldError("Proxy model '%s' contains model fields." % name)
View
2  django/db/models/fields/related.py
@@ -1327,7 +1327,7 @@ def set_managed(field, model, cls):
'verbose_name_plural': '%(from)s-%(to)s relationships' % {'from': from_, 'to': to},
})
# Construct and return the new class.
- return type(name, (models.Model,), {
+ return type(str(name), (models.Model,), {
'Meta': meta,
'__module__': klass.__module__,
from_: models.ForeignKey(klass, related_name='%s+' % name, db_tablespace=field.db_tablespace, db_constraint=field.rel.db_constraint),
View
7 django/template/base.py
@@ -611,7 +611,12 @@ def resolve(self, context, ignore_failures=False):
new_obj = func(obj, autoescape=context.autoescape, *arg_vals)
else:
new_obj = func(obj, *arg_vals)
- if getattr(func, 'is_safe', False) and isinstance(obj, SafeData):
+ # integer_types should be considered safe;
+ # if 'obj' is a string type, we should check it for SafeData
+ if getattr(func, 'is_safe', False) and (
+ isinstance(obj, six.integer_types) or
+ (isinstance(obj, six.string_types) and
+ isinstance(obj, SafeData))):
obj = mark_safe(new_obj)
elif isinstance(obj, EscapeData):
obj = mark_for_escaping(new_obj)
View
18 docs/releases/1.6.txt
@@ -392,6 +392,24 @@ If you do not apply this change, the behaviour is unchanged: on MySQL, IPv6
addresses are silently truncated; on Oracle, an exception is generated. No
database change is needed for SQLite or PostgreSQL databases.
+Percent literals in ``cursor.execute`` queries
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+When you are running raw SQL queries through the
+:ref:`cursor.execute <executing-custom-sql>` method, the rule about doubling
+percent literals (``%``) inside the query has been unified. Past behavior
+depended on the database backend. Now, across all backends, you only need to
+double literal percent characters if you are also providing replacement
+parameters. For example::
+
+ # No parameters, no percent doubling
+ cursor.execute("SELECT foo FROM bar WHERE baz = '30%'")
+
+ # Parameters passed, non-placeholders have to be doubled
+ cursor.execute("SELECT foo FROM bar WHERE baz = '30%%' and id = %s", [self.id])
+
+``SQLite`` users need to check and update such queries.
+
Miscellaneous
~~~~~~~~~~~~~
View
5 tests/many_to_many/models.py
@@ -6,6 +6,7 @@
In this example, an ``Article`` can be published in multiple ``Publication``
objects, and a ``Publication`` has multiple ``Article`` objects.
"""
+from __future__ import unicode_literals
from django.db import models
from django.utils.encoding import python_2_unicode_compatible
@@ -24,7 +25,9 @@ class Meta:
@python_2_unicode_compatible
class Article(models.Model):
headline = models.CharField(max_length=100)
- publications = models.ManyToManyField(Publication)
+ # Assign a unicode string as name to make sure the intermediary model is
+ # correctly created. Refs #20207
+ publications = models.ManyToManyField(Publication, name='publications')
def __str__(self):
return self.headline
Something went wrong with that request. Please try again.