1
0
mirror of https://github.com/django/django.git synced 2025-07-04 01:39:20 +00:00

gis: Merged revisions 7643-7662,7667-7668,7672-7682,7686-7693,7695-7698,7700-7702,7704-7706,7710,7712-7729,7731-7732,7738-7758,7760-7766 via svnmerge from trunk.

git-svn-id: http://code.djangoproject.com/svn/django/branches/gis@7768 bcc190cf-cafb-0310-a4f2-bffc1f526a37
This commit is contained in:
Justin Bronn 2008-06-26 15:11:55 +00:00
parent 9fcc6c305a
commit aef8a8305d
130 changed files with 11148 additions and 2685 deletions

View File

@ -65,6 +65,7 @@ answer newbie questions, and generally made Django that much better:
Mikaël Barbero <mikael.barbero nospam at nospam free.fr>
Jiri Barton
Ned Batchelder <http://www.nedbatchelder.com/>
batiste@dosimple.ch
Shannon -jj Behrens <http://jjinux.blogspot.com/>
Esdras Beleza <linux@esdrasbeleza.com>
Chris Bennett <chrisrbennett@yahoo.com>
@ -228,6 +229,7 @@ answer newbie questions, and generally made Django that much better:
Nicola Larosa <nico@teknico.net>
Rune Rønde Laursen <runerl@skjoldhoej.dk>
Eugene Lazutkin <http://lazutkin.com/blog/>
lcordier@point45.com
Jeong-Min Lee <falsetru@gmail.com>
Jannis Leidel <jl@websushi.org>
Christopher Lenz <http://www.cmlenz.net/>
@ -374,6 +376,7 @@ answer newbie questions, and generally made Django that much better:
Wang Chun <wangchun@exoweb.net>
Filip Wasilewski <filip.wasilewski@gmail.com>
Dan Watson <http://theidioteque.net/>
Joel Watts <joel@joelwatts.com>
Chris Wesseling <Chris.Wesseling@cwi.nl>
James Wheare <django@sparemint.com>
charly.wilhelm@gmail.com

View File

@ -1,4 +1,4 @@
Copyright (c) 2005, the Lawrence Journal-World
Copyright (c) Django Software Foundation.
All rights reserved.
Redistribution and use in source and binary forms, with or without modification,

View File

@ -1,3 +1,5 @@
#!/usr/bin/env python
"""
gather_profile_stats.py /path/to/dir/of/profiles

View File

@ -52,6 +52,7 @@ LANGUAGES = (
('el', gettext_noop('Greek')),
('en', gettext_noop('English')),
('es', gettext_noop('Spanish')),
('et', gettext_noop('Estonian')),
('es-ar', gettext_noop('Argentinean Spanish')),
('eu', gettext_noop('Basque')),
('fa', gettext_noop('Persian')),
@ -70,6 +71,7 @@ LANGUAGES = (
('km', gettext_noop('Khmer')),
('kn', gettext_noop('Kannada')),
('lv', gettext_noop('Latvian')),
('lt', gettext_noop('Lithuanian')),
('mk', gettext_noop('Macedonian')),
('nl', gettext_noop('Dutch')),
('no', gettext_noop('Norwegian')),

View File

@ -5,8 +5,8 @@ msgid ""
msgstr ""
"Project-Id-Version: Django\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2008-05-26 10:35+0200\n"
"PO-Revision-Date: 2008-05-14 11:15+0200\n"
"POT-Creation-Date: 2008-06-20 12:36+0200\n"
"PO-Revision-Date: 2008-06-20 12:48+0200\n"
"Last-Translator: Django Catalan Group <django-cat@googlegroups.com>\n"
"Language-Team: Catalan <ca@li.org>\n"
"MIME-Version: 1.0\n"
@ -14,193 +14,201 @@ msgstr ""
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=2; plural=(n != 1);\n"
#: conf/global_settings.py:43
msgid "Arabic"
msgstr "Arabic"
#: conf/global_settings.py:44
msgid "Bengali"
msgstr "Bengalí"
msgid "Arabic"
msgstr "aràbic"
#: conf/global_settings.py:45
msgid "Bulgarian"
msgstr "Búlgar"
msgid "Bengali"
msgstr "bengalí"
#: conf/global_settings.py:46
msgid "Catalan"
msgstr "Català"
msgid "Bulgarian"
msgstr "búlgar"
#: conf/global_settings.py:47
msgid "Czech"
msgstr "Txec"
msgid "Catalan"
msgstr "català"
#: conf/global_settings.py:48
msgid "Welsh"
msgstr "Galès"
msgid "Czech"
msgstr "txec"
#: conf/global_settings.py:49
msgid "Danish"
msgstr "Danès"
msgid "Welsh"
msgstr "galès"
#: conf/global_settings.py:50
msgid "German"
msgstr "Alemany"
msgid "Danish"
msgstr "danès"
#: conf/global_settings.py:51
msgid "Greek"
msgstr "Grec"
msgid "German"
msgstr "alemany"
#: conf/global_settings.py:52
msgid "English"
msgstr "Anglès"
msgid "Greek"
msgstr "grec"
#: conf/global_settings.py:53
msgid "Spanish"
msgstr "Espanyol"
msgid "English"
msgstr "anglès"
#: conf/global_settings.py:54
msgid "Argentinean Spanish"
msgstr "Castellà Argentí"
msgid "Spanish"
msgstr "espanyol"
#: conf/global_settings.py:55
msgid "Basque"
msgstr "Euskera"
msgid "Estonian"
msgstr "estonià"
#: conf/global_settings.py:56
msgid "Persian"
msgstr "Persa"
msgid "Argentinean Spanish"
msgstr "castellà argentí"
#: conf/global_settings.py:57
msgid "Finnish"
msgstr "Finlandès"
msgid "Basque"
msgstr "euskera"
#: conf/global_settings.py:58
msgid "French"
msgstr "Francès"
msgid "Persian"
msgstr "persa"
#: conf/global_settings.py:59
msgid "Irish"
msgstr "Irlandès"
msgid "Finnish"
msgstr "finlandès"
#: conf/global_settings.py:60
msgid "Galician"
msgstr "Gallec"
msgid "French"
msgstr "francès"
#: conf/global_settings.py:61
msgid "Hungarian"
msgstr "Húngar"
msgid "Irish"
msgstr "irlandès"
#: conf/global_settings.py:62
msgid "Hebrew"
msgstr "Hebreu"
msgid "Galician"
msgstr "gallec"
#: conf/global_settings.py:63
msgid "Croatian"
msgstr "Croat"
msgid "Hungarian"
msgstr "húngar"
#: conf/global_settings.py:64
msgid "Icelandic"
msgstr "Islandès"
msgid "Hebrew"
msgstr "hebreu"
#: conf/global_settings.py:65
msgid "Italian"
msgstr "Italià"
msgid "Croatian"
msgstr "croat"
#: conf/global_settings.py:66
msgid "Japanese"
msgstr "Japonès"
msgid "Icelandic"
msgstr "islandès"
#: conf/global_settings.py:67
msgid "Georgian"
msgstr "Georgià"
msgid "Italian"
msgstr "italià"
#: conf/global_settings.py:68
msgid "Korean"
msgstr "Coreà"
msgid "Japanese"
msgstr "japonès"
#: conf/global_settings.py:69
msgid "Khmer"
msgstr "Khmer"
msgid "Georgian"
msgstr "georgià"
#: conf/global_settings.py:70
msgid "Kannada"
msgstr "Canès"
msgid "Korean"
msgstr "coreà"
#: conf/global_settings.py:71
msgid "Latvian"
msgstr "Letó"
msgid "khmer"
msgstr "khmer"
#: conf/global_settings.py:72
msgid "Macedonian"
msgstr "Macedoni"
msgid "Kannada"
msgstr "canès"
#: conf/global_settings.py:73
msgid "Dutch"
msgstr "Holandès"
msgid "Latvian"
msgstr "letó"
#: conf/global_settings.py:74
msgid "Norwegian"
msgstr "Norueg"
msgid "Lithuanian"
msgstr "lituà"
#: conf/global_settings.py:75
msgid "Polish"
msgstr "Polac"
msgid "Macedonian"
msgstr "macedoni"
#: conf/global_settings.py:76
msgid "Portugese"
msgstr "Portuguès"
msgid "Dutch"
msgstr "holandès"
#: conf/global_settings.py:77
msgid "Brazilian Portuguese"
msgstr "Portuguès de Brasil"
msgid "Norwegian"
msgstr "norueg"
#: conf/global_settings.py:78
msgid "Romanian"
msgstr "Rumanès"
msgid "Polish"
msgstr "polac"
#: conf/global_settings.py:79
msgid "Russian"
msgstr "s"
msgid "Portugese"
msgstr "portuguès"
#: conf/global_settings.py:80
msgid "Slovak"
msgstr "Eslovac"
msgid "Brazilian Portuguese"
msgstr "portuguès de brasil"
#: conf/global_settings.py:81
msgid "Slovenian"
msgstr "Esloveni"
msgid "Romanian"
msgstr "rumanès"
#: conf/global_settings.py:82
msgid "Serbian"
msgstr "Serbi"
msgid "Russian"
msgstr "rús"
#: conf/global_settings.py:83
msgid "Swedish"
msgstr "Suec"
msgid "Slovak"
msgstr "eslovac"
#: conf/global_settings.py:84
msgid "Tamil"
msgstr "Tàmil"
msgid "Slovenian"
msgstr "esloveni"
#: conf/global_settings.py:85
msgid "Telugu"
msgstr "Telugu"
msgid "Serbian"
msgstr "serbi"
#: conf/global_settings.py:86
msgid "Turkish"
msgstr "Turc"
msgid "Swedish"
msgstr "suec"
#: conf/global_settings.py:87
msgid "Ukrainian"
msgstr "Ucranià"
msgid "Tamil"
msgstr "tàmil"
#: conf/global_settings.py:88
msgid "Simplified Chinese"
msgstr "Xinès simplificat"
msgid "Telugu"
msgstr "telugu"
#: conf/global_settings.py:89
msgid "Turkish"
msgstr "turc"
#: conf/global_settings.py:90
msgid "Ukrainian"
msgstr "ucranià"
#: conf/global_settings.py:91
msgid "Simplified Chinese"
msgstr "xinès simplificat"
#: conf/global_settings.py:92
msgid "Traditional Chinese"
msgstr "Xinès tradicional"
msgstr "xinès tradicional"
#: contrib/admin/filterspecs.py:44
#, python-format
@ -1137,15 +1145,15 @@ msgstr "permisos"
msgid "group"
msgstr "grup"
#: contrib/auth/models.py:98 contrib/auth/models.py:141
#: contrib/auth/models.py:98 contrib/auth/models.py:148
msgid "groups"
msgstr "grups"
#: contrib/auth/models.py:131
#: contrib/auth/models.py:138
msgid "username"
msgstr "nom d'usuari"
#: contrib/auth/models.py:131
#: contrib/auth/models.py:138
msgid ""
"Required. 30 characters or fewer. Alphanumeric characters only (letters, "
"digits and underscores)."
@ -1153,23 +1161,23 @@ msgstr ""
"Obligatori. 30 o menys caràcters. Només caràcters alfanumèrics (lletres, "
"dígits i el guió baix)."
#: contrib/auth/models.py:132
#: contrib/auth/models.py:139
msgid "first name"
msgstr "nom propi"
#: contrib/auth/models.py:133
#: contrib/auth/models.py:140
msgid "last name"
msgstr "cognoms"
#: contrib/auth/models.py:134
#: contrib/auth/models.py:141
msgid "e-mail address"
msgstr "adreça de correu electrònic"
#: contrib/auth/models.py:135
#: contrib/auth/models.py:142
msgid "password"
msgstr "contrasenya"
#: contrib/auth/models.py:135
#: contrib/auth/models.py:142
msgid ""
"Use '[algo]$[salt]$[hexdigest]' or use the <a href=\"password/\">change "
"password form</a>."
@ -1177,19 +1185,19 @@ msgstr ""
"Utilitzeu '[algo]$[salt]$[hexdigest]' o el <a href=\"password/\">formulari "
"de canvi de contrasenya</a>."
#: contrib/auth/models.py:136
#: contrib/auth/models.py:143
msgid "staff status"
msgstr "membre del personal"
#: contrib/auth/models.py:136
#: contrib/auth/models.py:143
msgid "Designates whether the user can log into this admin site."
msgstr "Indica si l'usuari pot entrar en el lloc administratiu."
#: contrib/auth/models.py:137
#: contrib/auth/models.py:144
msgid "active"
msgstr "actiu"
#: contrib/auth/models.py:137
#: contrib/auth/models.py:144
msgid ""
"Designates whether this user should be treated as active. Unselect this "
"instead of deleting accounts."
@ -1197,11 +1205,11 @@ msgstr ""
"Designa si aquest usuari ha de ser tractat com a actiu. Deseleccioneu-ho "
"enlloc d'esborrar comptes d'usuari."
#: contrib/auth/models.py:138
#: contrib/auth/models.py:145
msgid "superuser status"
msgstr "estat de superusuari"
#: contrib/auth/models.py:138
#: contrib/auth/models.py:145
msgid ""
"Designates that this user has all permissions without explicitly assigning "
"them."
@ -1209,15 +1217,15 @@ msgstr ""
"Designa que aquest usuari té tots els permissos sense assignar-los "
"explícitament."
#: contrib/auth/models.py:139
#: contrib/auth/models.py:146
msgid "last login"
msgstr "últim inici de sessió"
#: contrib/auth/models.py:140
#: contrib/auth/models.py:147
msgid "date joined"
msgstr "data de creació"
#: contrib/auth/models.py:142
#: contrib/auth/models.py:149
msgid ""
"In addition to the permissions manually assigned, this user will also get "
"all permissions granted to each group he/she is in."
@ -1225,39 +1233,39 @@ msgstr ""
"Junt amb els permissos asignats manualment, aquest usuari tindrà, també, els "
"permissos dels grups dels que sigui membre."
#: contrib/auth/models.py:143
#: contrib/auth/models.py:150
msgid "user permissions"
msgstr "permissos de l'usuari"
#: contrib/auth/models.py:147
#: contrib/auth/models.py:154
msgid "user"
msgstr "usuari"
#: contrib/auth/models.py:148
#: contrib/auth/models.py:155
msgid "users"
msgstr "usuaris"
#: contrib/auth/models.py:154
#: contrib/auth/models.py:161
msgid "Personal info"
msgstr "Informació personal"
#: contrib/auth/models.py:155
#: contrib/auth/models.py:162
msgid "Permissions"
msgstr "permisos"
#: contrib/auth/models.py:156
#: contrib/auth/models.py:163
msgid "Important dates"
msgstr "Dates importants"
#: contrib/auth/models.py:157
#: contrib/auth/models.py:164
msgid "Groups"
msgstr "Grups"
#: contrib/auth/models.py:316
#: contrib/auth/models.py:323
msgid "message"
msgstr "missatge"
#: contrib/auth/views.py:47
#: contrib/auth/views.py:48
msgid "Logged out"
msgstr "Sessió finalitzada"
@ -3897,12 +3905,12 @@ msgstr ""
msgid "%(object)s with this %(type)s already exists for the given %(field)s."
msgstr "Ja existeix un %(object)s del tipus %(type)s amb aquest %(field)s."
#: db/models/fields/__init__.py:54
#: db/models/fields/__init__.py:51
#, python-format
msgid "%(optname)s with this %(fieldname)s already exists."
msgstr "Ja existeix %(optname)s amb aquest %(fieldname)s."
#: db/models/fields/__init__.py:179 db/models/fields/__init__.py:348
#: db/models/fields/__init__.py:176 db/models/fields/__init__.py:348
#: db/models/fields/__init__.py:780 db/models/fields/__init__.py:791
#: newforms/fields.py:46 oldforms/__init__.py:374
msgid "This field is required."
@ -3937,18 +3945,18 @@ msgstr "Aquest valor ha de ser None (Cap), True (Veritat) o False (Fals)"
msgid "Please enter a valid %s."
msgstr "Si us plau, introduïu un %s vàlid."
#: db/models/fields/related.py:721
#: db/models/fields/related.py:746
msgid "Separate multiple IDs with commas."
msgstr "Separi múltiples IDs amb comes."
#: db/models/fields/related.py:723
#: db/models/fields/related.py:748
msgid ""
"Hold down \"Control\", or \"Command\" on a Mac, to select more than one."
msgstr ""
"Premeu la tecla \"Control\" -o \"Command\" en un Mac- per seleccionar més "
"d'un valor."
#: db/models/fields/related.py:770
#: db/models/fields/related.py:795
#, python-format
msgid "Please enter valid %(self)s IDs. The value %(value)r is invalid."
msgid_plural ""
@ -4007,11 +4015,11 @@ msgstr "Assegureu-vos de que no hi ha més de %s decimals."
msgid "Ensure that there are no more than %s digits before the decimal point."
msgstr "Assegureu-vos de que no hi ha més de %s dígits decimals."
#: newforms/fields.py:263 newforms/fields.py:751
#: newforms/fields.py:263 newforms/fields.py:750
msgid "Enter a valid date."
msgstr "Introduïu una data vàlida."
#: newforms/fields.py:296 newforms/fields.py:752
#: newforms/fields.py:296 newforms/fields.py:751
msgid "Enter a valid time."
msgstr "Introduïu una hora vàlida."
@ -4035,25 +4043,25 @@ msgstr "Introduïu una URL vàlida."
msgid "This URL appears to be a broken link."
msgstr "Aquesta URL sembla ser un enllaç trencat."
#: newforms/fields.py:560 newforms/models.py:299
#: newforms/fields.py:559 newforms/models.py:305
msgid "Select a valid choice. That choice is not one of the available choices."
msgstr ""
"Escolli una opció vàlida; Aquesta opció no és una de les opcions disponibles."
#: newforms/fields.py:599
#: newforms/fields.py:598
#, python-format
msgid "Select a valid choice. %(value)s is not one of the available choices."
msgstr "Esculliu una opció vàlida. %(value)s no és una de les opcions vàlides."
#: newforms/fields.py:600 newforms/fields.py:662 newforms/models.py:371
#: newforms/fields.py:599 newforms/fields.py:661 newforms/models.py:372
msgid "Enter a list of values."
msgstr "Introduïu una llista de valors."
#: newforms/fields.py:780
#: newforms/fields.py:779
msgid "Enter a valid IPv4 address."
msgstr "Introduïu una adreça IPv4 vàlida."
#: newforms/models.py:372
#: newforms/models.py:373
#, python-format
msgid "Select a valid choice. %s is not one of the available choices."
msgstr "Escolliu una opció vàlida; %s' no és una de les opcions vàlides."
@ -4194,51 +4202,51 @@ msgstr "Dg"
#: utils/dates.py:18
msgid "January"
msgstr "Gener"
msgstr "gener"
#: utils/dates.py:18
msgid "February"
msgstr "Febrer"
msgstr "febrer"
#: utils/dates.py:18 utils/dates.py:31
msgid "March"
msgstr "Març"
msgstr "març"
#: utils/dates.py:18 utils/dates.py:31
msgid "April"
msgstr "Abril"
msgstr "abril"
#: utils/dates.py:18 utils/dates.py:31
msgid "May"
msgstr "Maig"
msgstr "maig"
#: utils/dates.py:18 utils/dates.py:31
msgid "June"
msgstr "Juny"
msgstr "juny"
#: utils/dates.py:19 utils/dates.py:31
msgid "July"
msgstr "Juliol"
msgstr "juliol"
#: utils/dates.py:19
msgid "August"
msgstr "Agost"
msgstr "agost"
#: utils/dates.py:19
msgid "September"
msgstr "Setembre"
msgstr "setembre"
#: utils/dates.py:19
msgid "October"
msgstr "Octubre"
msgstr "octubre"
#: utils/dates.py:19
msgid "November"
msgstr "Novembre"
msgstr "novembre"
#: utils/dates.py:20
msgid "December"
msgstr "Desembre"
msgstr "desembre"
#: utils/dates.py:23
msgid "jan"
@ -4290,31 +4298,31 @@ msgstr "des"
#: utils/dates.py:31
msgid "Jan."
msgstr "Gen."
msgstr "gen."
#: utils/dates.py:31
msgid "Feb."
msgstr "Feb."
msgstr "feb."
#: utils/dates.py:32
msgid "Aug."
msgstr "Ago."
msgstr "ago."
#: utils/dates.py:32
msgid "Sept."
msgstr "Set."
msgstr "set."
#: utils/dates.py:32
msgid "Oct."
msgstr "Oct."
msgstr "oct."
#: utils/dates.py:32
msgid "Nov."
msgstr "Nov."
msgstr "nov."
#: utils/dates.py:32
msgid "Dec."
msgstr "Des."
msgstr "des."
#: utils/text.py:127
msgid "or"

File diff suppressed because it is too large Load Diff

View File

@ -7,12 +7,13 @@ msgid ""
msgstr ""
"Project-Id-Version: Django\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2005-12-09 11:51+0100\n"
"PO-Revision-Date: 2005-12-04 13:21+0100\n"
"Last-Translator: Dirk Eschler <dirk.eschler@gmx.net>\n"
"POT-Creation-Date: 2008-06-23 20:52+0200\n"
"PO-Revision-Date: 2008-06-23 21:02+0100\n"
"Last-Translator: Jannis Leidel <jannis@leidel.info>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Language-Team: \n"
#: contrib/admin/media/js/SelectFilter2.js:33
#, perl-format
@ -38,82 +39,78 @@ msgstr "Ausgewählte %s"
#: contrib/admin/media/js/SelectFilter2.js:54
msgid "Select your choice(s) and click "
msgstr "Gewünschte Auswahl treffen und "
msgstr "Auswahl treffen und Klick auf"
#: contrib/admin/media/js/SelectFilter2.js:59
msgid "Clear all"
msgstr "Alles abwählen"
#: contrib/admin/media/js/dateparse.js:26
#: contrib/admin/media/js/calendar.js:24
msgid ""
"January February March April May June July August September October November "
"December"
msgstr ""
"Januar Februar März April Mai Juni Juli August September Oktober November "
"Dezember"
#: contrib/admin/media/js/dateparse.js:27
msgid "Sunday Monday Tuesday Wednesday Thursday Friday Saturday"
msgstr "Sonntag Montag Dienstag Mittwoch Donnerstag Freitag Samstag"
#: contrib/admin/media/js/dateparse.js:32
msgid "January February March April May June July August September October November December"
msgstr "Januar Februar März April Mai Juni Juli August September Oktober November Dezember"
#: contrib/admin/media/js/calendar.js:25
msgid "S M T W T F S"
msgstr "S M D M D F S"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:45
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:80
msgid "Now"
msgstr "Jetzt"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:48
msgid "Clock"
msgstr "Uhr"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:77
msgid "Choose a time"
msgstr "Uhrzeit"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:81
msgid "Midnight"
msgstr "Mitternacht"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:82
msgid "6 a.m."
msgstr "6 Uhr"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:83
msgid "Noon"
msgstr "Mittag"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:87
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:168
msgid "Cancel"
msgstr "Abbrechen"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:111
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:162
msgid "Today"
msgstr "Heute"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:114
msgid "Calendar"
msgstr "Kalender"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:160
msgid "Yesterday"
msgstr "Gestern"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:164
msgid "Tomorrow"
msgstr "Morgen"
#: contrib/admin/media/js/dateparse.js:33
msgid "Sunday Monday Tuesday Wednesday Thursday Friday Saturday"
msgstr "Sonntag Montag Dienstag Mittwoch Donnerstag Freitag Samstag"
#: contrib/admin/media/js/admin/CollapsedFieldsets.js:34
#: contrib/admin/media/js/admin/CollapsedFieldsets.js:72
msgid "Show"
msgstr "Anzeigen"
msgstr "Einblenden"
#: contrib/admin/media/js/admin/CollapsedFieldsets.js:63
msgid "Hide"
msgstr "Verbergen"
msgstr "Ausblenden"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:47
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:81
msgid "Now"
msgstr "Jetzt"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:51
msgid "Clock"
msgstr "Uhr"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:78
msgid "Choose a time"
msgstr "Uhrzeit"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:82
msgid "Midnight"
msgstr "Mitternacht"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:83
msgid "6 a.m."
msgstr "6 Uhr"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:84
msgid "Noon"
msgstr "Mittag"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:88
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:183
msgid "Cancel"
msgstr "Abbrechen"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:128
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:177
msgid "Today"
msgstr "Heute"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:132
msgid "Calendar"
msgstr "Kalender"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:175
msgid "Yesterday"
msgstr "Gestern"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:179
msgid "Tomorrow"
msgstr "Morgen"

View File

@ -6,7 +6,7 @@ msgstr ""
"Project-Id-Version: Django\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2008-06-13 16:14+0200\n"
"PO-Revision-Date: 2008-03-30 01:04+0100\n"
"PO-Revision-Date: 2008-06-18 22:45+0200\n"
"Last-Translator: Django Spanish Translation Team <django-cat@googlegroups.com>\n"
"Language-Team: Django Spanish Translation Team <django-cat@googlegroups.com>\n"
"MIME-Version: 1.0\n"
@ -16,191 +16,191 @@ msgstr ""
#: conf/global_settings.py:44
msgid "Arabic"
msgstr "Árabe"
msgstr "árabe"
#: conf/global_settings.py:45
msgid "Bengali"
msgstr "Bengalí"
msgstr "bengalí"
#: conf/global_settings.py:46
msgid "Bulgarian"
msgstr "Búlgaro"
msgstr "búlgaro"
#: conf/global_settings.py:47
msgid "Catalan"
msgstr "Catalán"
msgstr "catalán"
#: conf/global_settings.py:48
msgid "Czech"
msgstr "Checo"
msgstr "checo"
#: conf/global_settings.py:49
msgid "Welsh"
msgstr "Galés"
msgstr "galés"
#: conf/global_settings.py:50
msgid "Danish"
msgstr "Danés"
msgstr "danés"
#: conf/global_settings.py:51
msgid "German"
msgstr "Alemán"
msgstr "alemán"
#: conf/global_settings.py:52
msgid "Greek"
msgstr "Griego"
msgstr "griego"
#: conf/global_settings.py:53
msgid "English"
msgstr "Inglés"
msgstr "inglés"
#: conf/global_settings.py:54
msgid "Spanish"
msgstr "Español"
msgstr "español"
#: conf/global_settings.py:55
msgid "Argentinean Spanish"
msgstr "Español Argentino"
msgstr "español de Argentina"
#: conf/global_settings.py:56
msgid "Basque"
msgstr "Vasco"
msgstr "vasco"
#: conf/global_settings.py:57
msgid "Persian"
msgstr "Persa"
msgstr "persa"
#: conf/global_settings.py:58
msgid "Finnish"
msgstr "Finés"
msgstr "finés"
#: conf/global_settings.py:59
msgid "French"
msgstr "Francés"
msgstr "francés"
#: conf/global_settings.py:60
msgid "Irish"
msgstr "Irlandés"
msgstr "irlandés"
#: conf/global_settings.py:61
msgid "Galician"
msgstr "Gallego"
msgstr "gallego"
#: conf/global_settings.py:62
msgid "Hungarian"
msgstr "Húngaro"
msgstr "húngaro"
#: conf/global_settings.py:63
msgid "Hebrew"
msgstr "Hebreo"
msgstr "hebreo"
#: conf/global_settings.py:64
msgid "Croatian"
msgstr "Croata"
msgstr "croata"
#: conf/global_settings.py:65
msgid "Icelandic"
msgstr "Islandés"
msgstr "islandés"
#: conf/global_settings.py:66
msgid "Italian"
msgstr "Italiano"
msgstr "italiano"
#: conf/global_settings.py:67
msgid "Japanese"
msgstr "Japonés"
msgstr "japonés"
#: conf/global_settings.py:68
msgid "Georgian"
msgstr "Georgiano"
msgstr "georgiano"
#: conf/global_settings.py:69
msgid "Korean"
msgstr "Koreano"
msgstr "koreano"
#: conf/global_settings.py:70
msgid "Khmer"
msgstr "Khmer"
msgstr "khmer"
#: conf/global_settings.py:71
msgid "Kannada"
msgstr "Kannada"
msgstr "kannada"
#: conf/global_settings.py:72
msgid "Latvian"
msgstr "Latvio"
msgstr "letón"
#: conf/global_settings.py:73
msgid "Macedonian"
msgstr "Macedonio"
msgstr "macedonio"
#: conf/global_settings.py:74
msgid "Dutch"
msgstr "Holandés"
msgstr "holandés"
#: conf/global_settings.py:75
msgid "Norwegian"
msgstr "Noruego"
msgstr "noruego"
#: conf/global_settings.py:76
msgid "Polish"
msgstr "Polaco"
msgstr "polaco"
#: conf/global_settings.py:77
msgid "Portugese"
msgstr "Portugés"
msgstr "portugués"
#: conf/global_settings.py:78
msgid "Brazilian Portuguese"
msgstr "Portugés Brasileño"
msgstr "portugués de Brasil"
#: conf/global_settings.py:79
msgid "Romanian"
msgstr "Rumano"
msgstr "rumano"
#: conf/global_settings.py:80
msgid "Russian"
msgstr "Ruso"
msgstr "ruso"
#: conf/global_settings.py:81
msgid "Slovak"
msgstr "Eslovaco"
msgstr "eslovaco"
#: conf/global_settings.py:82
msgid "Slovenian"
msgstr "Esloveno"
msgstr "esloveno"
#: conf/global_settings.py:83
msgid "Serbian"
msgstr "Serbio"
msgstr "serbio"
#: conf/global_settings.py:84
msgid "Swedish"
msgstr "Sueco"
msgstr "sueco"
#: conf/global_settings.py:85
msgid "Tamil"
msgstr "Tamil"
msgstr "tamil"
#: conf/global_settings.py:86
msgid "Telugu"
msgstr "Telugu"
msgstr "telugu"
#: conf/global_settings.py:87
msgid "Turkish"
msgstr "Turco"
msgstr "turco"
#: conf/global_settings.py:88
msgid "Ukrainian"
msgstr "Ucraniano"
msgstr "ucraniano"
#: conf/global_settings.py:89
msgid "Simplified Chinese"
msgstr "Chino simplificado"
msgstr "chino simplificado"
#: conf/global_settings.py:90
msgid "Traditional Chinese"
msgstr "Chino tradicional"
msgstr "chino tradicional"
#: contrib/admin/filterspecs.py:44
#, python-format
@ -339,7 +339,7 @@ msgstr "Documentación"
#: contrib/admin/templates/admin/auth/user/change_password.html:14
#: contrib/admin/templates/admin/auth/user/change_password.html:45
msgid "Change password"
msgstr "Cambiar clave"
msgstr "Cambiar contraseña"
#: contrib/admin/templates/admin/base.html:30
#: contrib/comments/templates/comments/form.html:6
@ -356,8 +356,8 @@ msgstr "Administración de Django"
#: contrib/admin/templates/admin/change_form.html:14
#: contrib/admin/templates/admin/index.html:28
msgid "Añadir"
msgstr "Agregar"
msgid "Add"
msgstr "Añadir"
#: contrib/admin/templates/admin/change_form.html:20
#: contrib/admin/templates/admin/object_history.html:4
@ -802,14 +802,14 @@ msgstr "La contraseña se ha cambiado con éxito."
#: contrib/admin/views/auth.py:65
#, python-format
msgid "Change password: %s"
msgstr "Cambiar clave: %s"
msgstr "Cambiar contraseña: %s"
#: contrib/admin/views/decorators.py:17 contrib/auth/forms.py:60
msgid ""
"Please enter a correct username and password. Note that both fields are case-"
"sensitive."
msgstr ""
"Por favor, introduzca un nombre de usuario correcto y una contraseña. Note que "
"Por favor, introduzca un nombre de usuario y contraseña correctos. Note que "
"ambos campos son sensibles a mayúsculas/minúsculas."
#: contrib/admin/views/decorators.py:69
@ -867,7 +867,7 @@ msgstr "El modelo %(name)s no se ha encontrado en la aplicación %(label)r"
#: contrib/admin/views/doc.py:185
#, python-format
msgid "the related `%(label)s.%(type)s` object"
msgstr "el objeto relacionado`%(label)s.%(type)s` "
msgstr "el objeto relacionado `%(label)s.%(type)s`"
#: contrib/admin/views/doc.py:185 contrib/admin/views/doc.py:207
#: contrib/admin/views/doc.py:221 contrib/admin/views/doc.py:226
@ -1057,7 +1057,7 @@ msgstr "¿Está seguro?"
#: contrib/admin/views/main.py:549
#, python-format
msgid "Change history: %s"
msgstr "Modificar histórico: %s"
msgstr "Histórico de modificaciones: %s"
#: contrib/admin/views/main.py:583
#, python-format
@ -1067,7 +1067,7 @@ msgstr "Escoja %s"
#: contrib/admin/views/main.py:583
#, python-format
msgid "Select %s to change"
msgstr "Escoja %s para modificar"
msgstr "Escoja %s a modificar"
#: contrib/admin/views/main.py:765
msgid "Database error"
@ -1079,7 +1079,7 @@ msgstr "Las dos contraseñas no coinciden."
#: contrib/auth/forms.py:25
msgid "A user with that username already exists."
msgstr "Ya existe un usuario con este nombre."
msgstr "Ya existe un usuario con este nombre."
#: contrib/auth/forms.py:53
msgid ""
@ -1114,7 +1114,7 @@ msgstr ""
#: contrib/auth/forms.py:124
msgid "Your old password was entered incorrectly. Please enter it again."
msgstr ""
"Tu contraseña antigua es incorrecta. Por favor, vuelva a introducirla "
"Su contraseña antigua es incorrecta. Por favor, vuelva a introducirla "
"correctamente."
#: contrib/auth/models.py:73 contrib/auth/models.py:93
@ -1211,7 +1211,7 @@ msgstr ""
#: contrib/auth/models.py:146
msgid "last login"
msgstr "Último inicio de sesión"
msgstr "último inicio de sesión"
#: contrib/auth/models.py:147
msgid "date joined"
@ -1424,11 +1424,11 @@ msgstr "Marca de %r"
#: contrib/comments/models.py:300
msgid "deletion date"
msgstr "fecha de borrado"
msgstr "fecha de eliminación"
#: contrib/comments/models.py:303
msgid "moderator deletion"
msgstr "borrado del moderador"
msgstr "eliminación del moderador"
#: contrib/comments/models.py:304
msgid "moderator deletions"
@ -1441,7 +1441,7 @@ msgstr "Eliminación del moderador %r"
#: contrib/comments/templates/comments/form.html:8
msgid "Forgotten your password?"
msgstr "¿Has olvidado tu contraseña?"
msgstr "¿Ha olvidado su contraseña?"
#: contrib/comments/templates/comments/form.html:12
msgid "Ratings"
@ -1473,7 +1473,7 @@ msgstr "Previsualizar comentario"
#: contrib/comments/templates/comments/freeform.html:4
msgid "Your name:"
msgstr "Tu nombre:"
msgstr "Su nombre:"
#: contrib/comments/views/comments.py:28
msgid ""
@ -1528,8 +1528,7 @@ msgstr "No se proporcionó uno o más de los siguientes campos requeridos"
#: contrib/comments/views/comments.py:289
msgid "Somebody tampered with the comment form (security violation)"
msgstr ""
"Alguien realizó manipulaciones con el formulario de comentarios (violación de "
"seguridad)"
"Alguien manipuló el formulario de comentarios (violación de seguridad)"
#: contrib/comments/views/comments.py:208
#: contrib/comments/views/comments.py:295
@ -1555,7 +1554,7 @@ msgstr "ID de comentario no válido"
#: contrib/comments/views/karma.py:27
msgid "No voting for yourself"
msgstr "No puedes votarte a ti mismo"
msgstr "No puede votarse a sí mismo"
#: contrib/contenttypes/models.py:67
msgid "python model class name"
@ -1641,21 +1640,21 @@ msgstr "º"
msgid "%(value).1f million"
msgid_plural "%(value).1f million"
msgstr[0] "%(value).1f millón"
msgstr[1] "%(value).1f millión"
msgstr[1] "%(value).1f millón"
#: contrib/humanize/templatetags/humanize.py:54
#, python-format
msgid "%(value).1f billion"
msgid_plural "%(value).1f billion"
msgstr[0] "%(value).1f billón"
msgstr[1] "%(value).1f billón"
msgstr[0] "%(value).1f mil millones"
msgstr[1] "%(value).1f mil millones"
#: contrib/humanize/templatetags/humanize.py:57
#, python-format
msgid "%(value).1f trillion"
msgid_plural "%(value).1f trillion"
msgstr[0] "%(value).1f trillón"
msgstr[1] "%(value).1f trillón"
msgstr[0] "%(value).1f billón"
msgstr[1] "%(value).1f billón"
#: contrib/humanize/templatetags/humanize.py:73
msgid "one"
@ -1717,11 +1716,11 @@ msgstr "Este campo sólo acepta números."
#: contrib/localflavor/ar/forms.py:50
msgid "This field requires 7 or 8 digits."
msgstr "Este campo necesita 7 o 8 dígitos."
msgstr "Este campo necesita 7 u 8 dígitos."
#: contrib/localflavor/ar/forms.py:79
msgid "Enter a valid CUIT in XX-XXXXXXXX-X or XXXXXXXXXXXX format."
msgstr "Introduzca un CUIT válido en el formato XX-XXXXXXXX-X or XXXXXXXXXXXX."
msgstr "Introduzca un CUIT válido en el formato XX-XXXXXXXX-X o XXXXXXXXXXXX."
#: contrib/localflavor/ar/forms.py:80
msgid "Invalid CUIT."
@ -1753,15 +1752,15 @@ msgstr "Número CPF inválido."
#: contrib/localflavor/br/forms.py:95
msgid "This field requires at most 11 digits or 14 characters."
msgstr "Este campo necesita al menos 11 o 14 caracteres"
msgstr "Este campo necesita un máximo de 11 dígitos o 14 caracteres."
#: contrib/localflavor/br/forms.py:134
msgid "Invalid CNPJ number."
msgstr "Número CNPJ inválido"
msgstr "Número CNPJ inválido."
#: contrib/localflavor/br/forms.py:136
msgid "This field requires at least 14 digits"
msgstr "Este campo necesita 14 dígitos como máximo"
msgstr "Este campo necesita 14 dígitos como mínimo"
#: contrib/localflavor/ca/forms.py:17
msgid "Enter a postal code in the format XXX XXX."
@ -1770,7 +1769,7 @@ msgstr "Introduzca un código postal en el formato XXX XXX."
#: contrib/localflavor/ca/forms.py:88
msgid "Enter a valid Canadian Social Insurance number in XXX-XXX-XXX format."
msgstr ""
"Introduzca un Número del Seguro Social de Canada válido en el formato XXX-"
"Introduzca un Número del Seguro Social de Canadá válido en el formato XXX-"
"XXX-XXX."
#: contrib/localflavor/ch/ch_states.py:5
@ -1886,12 +1885,12 @@ msgid ""
"Enter a valid Swiss identity or passport card number in X1234567<0 or "
"1234567890 format."
msgstr ""
"Introduzca una identificación suiza válida o un número de pasaporte en el "
"formato X1234567<0 or 1234567890."
"Introduzca un número de identificación o pasaporte suizos válidos en el "
"formato X1234567<0 o 1234567890."
#: contrib/localflavor/cl/forms.py:29
msgid "Enter a valid Chilean RUT."
msgstr "Introduzca un RUT chileno válido"
msgstr "Introduzca un RUT chileno válido."
#: contrib/localflavor/cl/forms.py:30
msgid "Enter a valid Chilean RUT. The format is XX.XXX.XXX-X."
@ -2255,7 +2254,7 @@ msgid ""
"9XXXXXXXX."
msgstr ""
"Introduzca un número de teléfono válido en el formato 6XXXXXXXX, 8XXXXXXXX "
"or 9XXXXXXXX."
"o 9XXXXXXXX."
#: contrib/localflavor/es/forms.py:66
msgid "Please enter a valid NIF, NIE, or CIF."
@ -2723,7 +2722,7 @@ msgstr "El Número de Identificación Nacional es incorrecto."
msgid ""
"Enter a tax number field (NIP) in the format XXX-XXX-XX-XX or XX-XX-XXX-XXX."
msgstr ""
"Introduzca un número de impuesto (NIP) en el formato XXX-XXX-XX-XX or XX-XX-"
"Introduzca un número de impuesto (NIP) en el formato XXX-XXX-XX-XX o XX-XX-"
"XXX-XXX."
#: contrib/localflavor/pl/forms.py:73
@ -2733,7 +2732,7 @@ msgstr "El Número de Identificación Tributaria (NIP) es incorrecto."
#: contrib/localflavor/pl/forms.py:112
msgid "National Business Register Number (REGON) consists of 7 or 9 digits."
msgstr ""
"El Número Nacional de Registro de Negocios (REGON) consiste en 11 dígitos"
"El Número Nacional de Registro de Negocios (REGON) consiste en 7 o 9 dígitos."
#: contrib/localflavor/pl/forms.py:113
msgid "Wrong checksum for the National Business Register Number (REGON)."
@ -3161,7 +3160,7 @@ msgstr "Región de Zilina"
#: contrib/localflavor/uk/forms.py:21
msgid "Enter a valid postcode."
msgstr "Introduzca un código postal válido"
msgstr "Introduzca un código postal válido."
#: contrib/localflavor/uk/uk_regions.py:11
msgid "Bedfordshire"
@ -3454,11 +3453,11 @@ msgstr ""
#: contrib/localflavor/za/forms.py:20
msgid "Enter a valid South African ID number"
msgstr "Introduzca un ID Sur Africano válido"
msgstr "Introduzca un ID surafricano válido"
#: contrib/localflavor/za/forms.py:54
msgid "Enter a valid South African postal code"
msgstr "Introduzca un código postal Sur Africano válido"
msgstr "Introduzca un código postal surafricano válido"
#: contrib/localflavor/za/za_provinces.py:4
msgid "Eastern Cape"
@ -3642,7 +3641,7 @@ msgstr "Introduzca una fecha/hora válida en formato AAAA-MM-DD HH:MM."
#: core/validators.py:170 newforms/fields.py:403
msgid "Enter a valid e-mail address."
msgstr "Introduzca una dirección de correo electrónico válida"
msgstr "Introduzca una dirección de correo electrónico válida."
#: core/validators.py:182 core/validators.py:474 newforms/fields.py:433
#: oldforms/__init__.py:687
@ -3712,8 +3711,8 @@ msgstr "Introduzca una abreviatura válida de estado de los EEUU."
#, python-format
msgid "Watch your mouth! The word %s is not allowed here."
msgid_plural "Watch your mouth! The words %s are not allowed here."
msgstr[0] "¡Cuida tu vocabulario! Aquí no admitimos la palabra %s."
msgstr[1] "¡Cuida tu vocabulario! Aquí no admitimos las palabras %s."
msgstr[0] "¡Cuide su vocabulario! Aquí no admitimos la palabra %s."
msgstr[1] "¡Cuide su vocabulario! Aquí no admitimos las palabras %s."
#: core/validators.py:288
#, python-format
@ -3805,7 +3804,7 @@ msgstr[1] ""
#: core/validators.py:458
msgid "Please enter a valid floating point number."
msgstr "Por favor, introduzca un número decimal válido."
msgstr "Por favor, introduzca un número de coma flotante válido."
#: core/validators.py:467
#, python-format
@ -4005,7 +4004,7 @@ msgstr "Asegúrese de que no hay más de %s decimales."
#: newforms/fields.py:215
#, python-format
msgid "Ensure that there are no more than %s digits before the decimal point."
msgstr "Asegúrese de que no hay más de %s dígitos antes del punto decimal."
msgstr "Asegúrese de que no hay más de %s dígitos antes de la coma decimal."
#: newforms/fields.py:263 newforms/fields.py:751
msgid "Enter a valid date."
@ -4037,7 +4036,7 @@ msgstr "La URL parece ser un enlace roto."
#: newforms/fields.py:560 newforms/models.py:299
msgid "Select a valid choice. That choice is not one of the available choices."
msgstr "Escoja una opción válida. Esa opción no está entre las aceptadas."
msgstr "Escoja una opción válida. Esa opción no está entre las disponibles."
#: newforms/fields.py:599
#, python-format
@ -4076,7 +4075,7 @@ msgstr "Escoja una opción válida; '%(data)s' no está en %(choices)s."
#: oldforms/__init__.py:745
msgid "Enter a whole number between -32,768 and 32,767."
msgstr "Introduzca un número entero entre -32,768 y 32,767."
msgstr "Introduzca un número entero entre -32.768 y 32.767."
#: oldforms/__init__.py:755
msgid "Enter a positive number."
@ -4084,7 +4083,7 @@ msgstr "Introduzca un número positivo."
#: oldforms/__init__.py:765
msgid "Enter a whole number between 0 and 32,767."
msgstr "Introduzca un número entero entre 0 y 32,767."
msgstr "Introduzca un número entero entre 0 y 32.767."
#: template/defaultfilters.py:698
msgid "yes,no,maybe"
@ -4114,11 +4113,11 @@ msgstr "%.1f GB"
#: utils/dateformat.py:41
msgid "p.m."
msgstr "p.m"
msgstr "p.m."
#: utils/dateformat.py:42
msgid "a.m."
msgstr "a.m"
msgstr "a.m."
#: utils/dateformat.py:47
msgid "PM"
@ -4138,107 +4137,107 @@ msgstr "medio día"
#: utils/dates.py:6
msgid "Monday"
msgstr "Lunes"
msgstr "lunes"
#: utils/dates.py:6
msgid "Tuesday"
msgstr "Martes"
msgstr "martes"
#: utils/dates.py:6
msgid "Wednesday"
msgstr "Miércoles"
msgstr "miércoles"
#: utils/dates.py:6
msgid "Thursday"
msgstr "Jueves"
msgstr "jueves"
#: utils/dates.py:6
msgid "Friday"
msgstr "Viernes"
msgstr "viernes"
#: utils/dates.py:7
msgid "Saturday"
msgstr "Sábado"
msgstr "sábado"
#: utils/dates.py:7
msgid "Sunday"
msgstr "Domingo"
msgstr "domingo"
#: utils/dates.py:10
msgid "Mon"
msgstr "Lun"
msgstr "lun"
#: utils/dates.py:10
msgid "Tue"
msgstr "Mar"
msgstr "mar"
#: utils/dates.py:10
msgid "Wed"
msgstr "Mie"
msgstr "mié"
#: utils/dates.py:10
msgid "Thu"
msgstr "Jue"
msgstr "jue"
#: utils/dates.py:10
msgid "Fri"
msgstr "Vie"
msgstr "vie"
#: utils/dates.py:11
msgid "Sat"
msgstr "Sab"
msgstr "b"
#: utils/dates.py:11
msgid "Sun"
msgstr "Dom"
msgstr "dom"
#: utils/dates.py:18
msgid "January"
msgstr "Enero"
msgstr "enero"
#: utils/dates.py:18
msgid "February"
msgstr "Febrero"
msgstr "febrero"
#: utils/dates.py:18 utils/dates.py:31
msgid "March"
msgstr "Marzo"
msgstr "marzo"
#: utils/dates.py:18 utils/dates.py:31
msgid "April"
msgstr "Abril"
msgstr "abril"
#: utils/dates.py:18 utils/dates.py:31
msgid "May"
msgstr "Mayo"
msgstr "mayo"
#: utils/dates.py:18 utils/dates.py:31
msgid "June"
msgstr "Junio"
msgstr "junio"
#: utils/dates.py:19 utils/dates.py:31
msgid "July"
msgstr "Julio"
msgstr "julio"
#: utils/dates.py:19
msgid "August"
msgstr "Agosto"
msgstr "agosto"
#: utils/dates.py:19
msgid "September"
msgstr "Septiembre"
msgstr "septiembre"
#: utils/dates.py:19
msgid "October"
msgstr "Octubre"
msgstr "octubre"
#: utils/dates.py:19
msgid "November"
msgstr "Noviembre"
msgstr "noviembre"
#: utils/dates.py:20
msgid "December"
msgstr "Diciembre"
msgstr "diciembre"
#: utils/dates.py:23
msgid "jan"
@ -4290,31 +4289,31 @@ msgstr "dic"
#: utils/dates.py:31
msgid "Jan."
msgstr "Ene."
msgstr "ene."
#: utils/dates.py:31
msgid "Feb."
msgstr "Feb."
msgstr "feb."
#: utils/dates.py:32
msgid "Aug."
msgstr "Ago."
msgstr "ago."
#: utils/dates.py:32
msgid "Sept."
msgstr "Sept."
msgstr "sept."
#: utils/dates.py:32
msgid "Oct."
msgstr "Oct."
msgstr "oct."
#: utils/dates.py:32
msgid "Nov."
msgstr "Nov."
msgstr "nov."
#: utils/dates.py:32
msgid "Dec."
msgstr "Dic."
msgstr "dic."
#: utils/text.py:127
msgid "or"
@ -4393,7 +4392,7 @@ msgstr "j \\de F"
#: views/generic/create_update.py:43
#, python-format
msgid "The %(verbose_name)s was created successfully."
msgstr "El %(verbose_name)s se ha creado correctamente."
msgstr "El %(verbose_name)s se ha creado exitosamente."
#: views/generic/create_update.py:117
#, python-format

Binary file not shown.

File diff suppressed because it is too large Load Diff

Binary file not shown.

View File

@ -0,0 +1,115 @@
# Estonian translation for the Django Project.
# Copyright (C) 2008, Django Project
# This file is distributed under the same license as the django package.
msgid ""
msgstr ""
"Project-Id-Version: Django\n"
"Report-Msgid-Bugs-To: <removethis-eallik_at_gmail-com>\n"
"POT-Creation-Date: 2008-06-02 19:42+0300\n"
"PO-Revision-Date: 2008-06-17 12:29+0300\n"
"Last-Translator: Erik Allik <removethis-eallik_at_gmail-com>\n"
"Language-Team: Django-i18n <django-i18n@googlegroups.com>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
#: contrib/admin/media/js/SelectFilter2.js:33
#, perl-format
msgid "Available %s"
msgstr "Saadaval %s"
#: contrib/admin/media/js/SelectFilter2.js:41
msgid "Choose all"
msgstr "Vali kõik"
#: contrib/admin/media/js/SelectFilter2.js:46
msgid "Add"
msgstr "Lisa"
#: contrib/admin/media/js/SelectFilter2.js:48
msgid "Remove"
msgstr "Eemalda"
#: contrib/admin/media/js/SelectFilter2.js:53
#, perl-format
msgid "Chosen %s"
msgstr "Valitud %s"
#: contrib/admin/media/js/SelectFilter2.js:54
msgid "Select your choice(s) and click "
msgstr "Tee valik(ud) ja klõpsa"
#: contrib/admin/media/js/SelectFilter2.js:59
msgid "Clear all"
msgstr "Puhasta kõik"
#: contrib/admin/media/js/calendar.js:24
#: contrib/admin/media/js/dateparse.js:32
msgid ""
"January February March April May June July August September October November "
"December"
msgstr "Jaanuar Veebruar Märts Aprill Mai Juuni Juuli August September Oktoober November Detsember"
#: contrib/admin/media/js/calendar.js:25
msgid "S M T W T F S"
msgstr "P E T K N R L"
#: contrib/admin/media/js/dateparse.js:33
msgid "Sunday Monday Tuesday Wednesday Thursday Friday Saturday"
msgstr "Pühapäev Esmaspäev Teisipäev Kolmapäev Neljapäev Reede Laupäev"
#: contrib/admin/media/js/admin/CollapsedFieldsets.js:34
#: contrib/admin/media/js/admin/CollapsedFieldsets.js:72
msgid "Show"
msgstr "Näita"
#: contrib/admin/media/js/admin/CollapsedFieldsets.js:63
msgid "Hide"
msgstr "Varja"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:47
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:81
msgid "Now"
msgstr "Praegu"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:51
msgid "Clock"
msgstr "Kell"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:78
msgid "Choose a time"
msgstr "Vali aeg"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:82
msgid "Midnight"
msgstr "Kesköö"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:83
msgid "6 a.m."
msgstr "6 hommikul"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:84
msgid "Noon"
msgstr "Keskpäev"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:88
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:183
msgid "Cancel"
msgstr "Tühista"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:128
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:177
msgid "Today"
msgstr "Täna"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:132
msgid "Calendar"
msgstr "Kalender"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:175
msgid "Yesterday"
msgstr "Eile"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:179
msgid "Tomorrow"
msgstr "Homme"

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -6,7 +6,7 @@ msgstr ""
"Project-Id-Version: Django\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2007-08-13 11:13+1000\n"
"PO-Revision-Date: 2008-01-05 01:45+0100\n"
"PO-Revision-Date: 2008-06-17 23:45+0100\n"
"Last-Translator: Aljosa Mohorovic <aljosa.mohorovic@gmail.com>\n"
"Language-Team: Hrvatski jezik\n"
"MIME-Version: 1.0\n"

Binary file not shown.

File diff suppressed because it is too large Load Diff

Binary file not shown.

View File

@ -0,0 +1,116 @@
# Lithuanian translation of Django.
# Copyright (C) 2008 The Django Software Foundation
# This file is distributed under the same license as the Django package.
msgid ""
msgstr ""
"Project-Id-Version: Django\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2008-06-15 23:03+0300\n"
"PO-Revision-Date: 2008-06-18 22:37+0200\n"
"Last-Translator: Rapolas Kaselis <rapolas@gmail.com>\n"
"Language-Team: Django-i18n <django-i18n@googlegroups.com>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
#: contrib/admin/media/js/SelectFilter2.js:33
#, perl-format
msgid "Available %s"
msgstr "Galimas %s"
#: contrib/admin/media/js/SelectFilter2.js:41
msgid "Choose all"
msgstr "Pasirinkti visus"
#: contrib/admin/media/js/SelectFilter2.js:46
msgid "Add"
msgstr "Pridėti"
#: contrib/admin/media/js/SelectFilter2.js:48
msgid "Remove"
msgstr "Pašalinti"
#: contrib/admin/media/js/SelectFilter2.js:53
#, perl-format
msgid "Chosen %s"
msgstr "Pasirinktas %s"
#: contrib/admin/media/js/SelectFilter2.js:54
msgid "Select your choice(s) and click "
msgstr "Pasirink ir paspausk"
#: contrib/admin/media/js/SelectFilter2.js:59
msgid "Clear all"
msgstr "Išvalyti visus"
#: contrib/admin/media/js/dateparse.js:32
#: contrib/admin/media/js/calendar.js:24
msgid ""
"January February March April May June July August September October November "
"December"
msgstr "Sausis Vasaris Kovas Balandis Gegužė Birželis Liepa Rugpjūtis Rugsėjis "
"Spalis Lapkritis Gruodis"
#: contrib/admin/media/js/dateparse.js:33
msgid "Sunday Monday Tuesday Wednesday Thursday Friday Saturday"
msgstr "Sekmadienis Pirmadienis Antradienis Trečiadienis Ketvirtadienis Penktadienis Šeštadienis"
#: contrib/admin/media/js/calendar.js:25
msgid "S M T W T F S"
msgstr "S P A T K P Š"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:47
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:81
msgid "Now"
msgstr "Dabar"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:51
msgid "Clock"
msgstr "Laikrodis"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:78
msgid "Choose a time"
msgstr "Pasirink laiką"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:82
msgid "Midnight"
msgstr "Vidurnaktis"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:83
msgid "6 a.m."
msgstr "6 a.m."
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:84
msgid "Noon"
msgstr "Vidurdienis"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:88
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:183
msgid "Cancel"
msgstr "Atšaukti"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:128
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:177
msgid "Today"
msgstr "Šiandien"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:132
msgid "Calendar"
msgstr "Kalendorius"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:175
msgid "Yesterday"
msgstr "Vakar"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:179
msgid "Tomorrow"
msgstr "Rytoj"
#: contrib/admin/media/js/admin/CollapsedFieldsets.js:34
#: contrib/admin/media/js/admin/CollapsedFieldsets.js:72
msgid "Show"
msgstr "Parodyti"
#: contrib/admin/media/js/admin/CollapsedFieldsets.js:63
msgid "Hide"
msgstr "Slėpti"

View File

@ -5,9 +5,9 @@ msgid ""
msgstr ""
"Project-Id-Version: Django\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2008-04-14 18:02+0200\n"
"POT-Creation-Date: 2008-06-24 07:36+0200\n"
"PO-Revision-Date: 2008-02-25 15:53+0100\n"
"Last-Translator: Piotr Lewandowski <django@icomputing.pl>\n"
"Last-Translator: Jarek Zgoda <jarek.zgoda@gmail.com>\n"
"Language-Team: Polish <pl@li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
@ -16,191 +16,199 @@ msgstr ""
"Plural-Forms: nplurals=3; plural=(n==1 ? 0 : n%10>=2 && n%10<=4 && (n%"
"100<10 || n%100>=20) ? 1 : 2);\n"
#: conf/global_settings.py:39
#: conf/global_settings.py:44
msgid "Arabic"
msgstr "Arabski"
#: conf/global_settings.py:40
#: conf/global_settings.py:45
msgid "Bengali"
msgstr "Bengalski"
#: conf/global_settings.py:41
#: conf/global_settings.py:46
msgid "Bulgarian"
msgstr "Bułgarski"
#: conf/global_settings.py:42
#: conf/global_settings.py:47
msgid "Catalan"
msgstr "Kataloński"
#: conf/global_settings.py:43
#: conf/global_settings.py:48
msgid "Czech"
msgstr "Czeski"
#: conf/global_settings.py:44
#: conf/global_settings.py:49
msgid "Welsh"
msgstr "Walijski"
#: conf/global_settings.py:45
#: conf/global_settings.py:50
msgid "Danish"
msgstr "Duński"
#: conf/global_settings.py:46
#: conf/global_settings.py:51
msgid "German"
msgstr "Niemiecki"
#: conf/global_settings.py:47
#: conf/global_settings.py:52
msgid "Greek"
msgstr "Grecki"
#: conf/global_settings.py:48
#: conf/global_settings.py:53
msgid "English"
msgstr "Angielski"
#: conf/global_settings.py:49
#: conf/global_settings.py:54
msgid "Spanish"
msgstr "Hiszpański"
#: conf/global_settings.py:50
#: conf/global_settings.py:55
msgid "Estonian"
msgstr "Estoński"
#: conf/global_settings.py:56
msgid "Argentinean Spanish"
msgstr "Hiszpański argentyński"
#: conf/global_settings.py:51
#: conf/global_settings.py:57
msgid "Basque"
msgstr "Baskijski"
#: conf/global_settings.py:52
#: conf/global_settings.py:58
msgid "Persian"
msgstr "Perski"
#: conf/global_settings.py:53
#: conf/global_settings.py:59
msgid "Finnish"
msgstr "Fiński"
#: conf/global_settings.py:54
#: conf/global_settings.py:60
msgid "French"
msgstr "Francuski"
#: conf/global_settings.py:55
#: conf/global_settings.py:61
msgid "Irish"
msgstr "Irlandzki"
#: conf/global_settings.py:56
#: conf/global_settings.py:62
msgid "Galician"
msgstr "Galicyjski"
#: conf/global_settings.py:57
#: conf/global_settings.py:63
msgid "Hungarian"
msgstr "Węgierski"
#: conf/global_settings.py:58
#: conf/global_settings.py:64
msgid "Hebrew"
msgstr "Hebrajski"
#: conf/global_settings.py:59
#: conf/global_settings.py:65
msgid "Croatian"
msgstr "Chorwacki"
#: conf/global_settings.py:60
#: conf/global_settings.py:66
msgid "Icelandic"
msgstr "Islandzki"
#: conf/global_settings.py:61
#: conf/global_settings.py:67
msgid "Italian"
msgstr "Włoski"
#: conf/global_settings.py:62
#: conf/global_settings.py:68
msgid "Japanese"
msgstr "Japoński"
#: conf/global_settings.py:63
#: conf/global_settings.py:69
msgid "Georgian"
msgstr "Gruziński"
#: conf/global_settings.py:64
#: conf/global_settings.py:70
msgid "Korean"
msgstr "Koreański"
#: conf/global_settings.py:65
#: conf/global_settings.py:71
msgid "Khmer"
msgstr "Khmerski"
#: conf/global_settings.py:66
#: conf/global_settings.py:72
msgid "Kannada"
msgstr "Kannada"
#: conf/global_settings.py:67
#: conf/global_settings.py:73
msgid "Latvian"
msgstr "Łotewski"
#: conf/global_settings.py:68
#: conf/global_settings.py:74
msgid "Lithuanian"
msgstr "Litewski"
#: conf/global_settings.py:75
msgid "Macedonian"
msgstr "Macedoński"
#: conf/global_settings.py:69
#: conf/global_settings.py:76
msgid "Dutch"
msgstr "Holenderski"
#: conf/global_settings.py:70
#: conf/global_settings.py:77
msgid "Norwegian"
msgstr "Norweski"
#: conf/global_settings.py:71
#: conf/global_settings.py:78
msgid "Polish"
msgstr "Polski"
#: conf/global_settings.py:72
#: conf/global_settings.py:79
msgid "Portugese"
msgstr "Portugalski"
#: conf/global_settings.py:73
#: conf/global_settings.py:80
msgid "Brazilian Portuguese"
msgstr "Brazylijski portugalski"
#: conf/global_settings.py:74
#: conf/global_settings.py:81
msgid "Romanian"
msgstr "Rumuński"
#: conf/global_settings.py:75
#: conf/global_settings.py:82
msgid "Russian"
msgstr "Rosyjski"
#: conf/global_settings.py:76
#: conf/global_settings.py:83
msgid "Slovak"
msgstr "Słowacki"
#: conf/global_settings.py:77
#: conf/global_settings.py:84
msgid "Slovenian"
msgstr "Słoweński"
#: conf/global_settings.py:78
#: conf/global_settings.py:85
msgid "Serbian"
msgstr "Serbski"
#: conf/global_settings.py:79
#: conf/global_settings.py:86
msgid "Swedish"
msgstr "Szwedzki"
#: conf/global_settings.py:80
#: conf/global_settings.py:87
msgid "Tamil"
msgstr "Tamilski"
#: conf/global_settings.py:81
#: conf/global_settings.py:88
msgid "Telugu"
msgstr "Telugu"
#: conf/global_settings.py:82
#: conf/global_settings.py:89
msgid "Turkish"
msgstr "Turecki"
#: conf/global_settings.py:83
#: conf/global_settings.py:90
msgid "Ukrainian"
msgstr "Ukraiński"
#: conf/global_settings.py:84
#: conf/global_settings.py:91
msgid "Simplified Chinese"
msgstr "Uproszczony chiński"
#: conf/global_settings.py:85
#: conf/global_settings.py:92
msgid "Traditional Chinese"
msgstr "Chiński tradycyjny"
@ -417,7 +425,7 @@ msgstr ""
#: contrib/admin/templates/admin/delete_confirmation.html:25
msgid "Yes, I'm sure"
msgstr "Tak, usuń"
msgstr "Tak, na pewno"
#: contrib/admin/templates/admin/filter.html:2
#, python-format
@ -824,15 +832,15 @@ msgstr ""
"Twoja przeglądarka nie chce akceptować ciasteczek. Zmień jej ustawienia i "
"spróbuj ponownie."
#: contrib/admin/views/decorators.py:90
msgid "Usernames cannot contain the '@' character."
msgstr "Nazwy użytkowników nie mogą zawierać znaków '@'."
#: contrib/admin/views/decorators.py:92
#: contrib/admin/views/decorators.py:89
#, python-format
msgid "Your e-mail address is not your username. Try '%s' instead."
msgstr "Twój adres e-mail to nie jest twój login. Spróbuj '%s'."
#: contrib/admin/views/decorators.py:93
msgid "Usernames cannot contain the '@' character."
msgstr "Nazwy użytkowników nie mogą zawierać znaków '@'."
#: contrib/admin/views/doc.py:48 contrib/admin/views/doc.py:50
#: contrib/admin/views/doc.py:52
msgid "tag:"
@ -1063,7 +1071,7 @@ msgstr "Zaznacz %s"
msgid "Select %s to change"
msgstr "Zaznacz %s aby zmienić"
#: contrib/admin/views/main.py:784
#: contrib/admin/views/main.py:765
msgid "Database error"
msgstr "Błąd bazy danych"
@ -1128,15 +1136,15 @@ msgstr "uprawnienia"
msgid "group"
msgstr "grupa"
#: contrib/auth/models.py:98 contrib/auth/models.py:141
#: contrib/auth/models.py:98 contrib/auth/models.py:148
msgid "groups"
msgstr "grupy"
#: contrib/auth/models.py:131
#: contrib/auth/models.py:138
msgid "username"
msgstr "użytkownik"
#: contrib/auth/models.py:131
#: contrib/auth/models.py:138
msgid ""
"Required. 30 characters or fewer. Alphanumeric characters only (letters, "
"digits and underscores)."
@ -1144,23 +1152,23 @@ msgstr ""
"Wymagane. 30 znaków lub mniej. Tylko znaki alfanumeryczne (litery, cyfry i "
"podkreślenia)."
#: contrib/auth/models.py:132
#: contrib/auth/models.py:139
msgid "first name"
msgstr "Imię"
#: contrib/auth/models.py:133
#: contrib/auth/models.py:140
msgid "last name"
msgstr "Nazwisko"
#: contrib/auth/models.py:134
#: contrib/auth/models.py:141
msgid "e-mail address"
msgstr "adres e-mail"
#: contrib/auth/models.py:135
#: contrib/auth/models.py:142
msgid "password"
msgstr "hasło"
#: contrib/auth/models.py:135
#: contrib/auth/models.py:142
msgid ""
"Use '[algo]$[salt]$[hexdigest]' or use the <a href=\"password/\">change "
"password form</a>."
@ -1168,19 +1176,19 @@ msgstr ""
"Użyj '[algo]$[salt]$[hexdigest]' lub <a href=\"password/\">formularza zmiany "
"hasła</a>."
#: contrib/auth/models.py:136
#: contrib/auth/models.py:143
msgid "staff status"
msgstr "w zespole"
#: contrib/auth/models.py:136
#: contrib/auth/models.py:143
msgid "Designates whether the user can log into this admin site."
msgstr "Oznacza czy użytkownik może zalogować się do panelu admina."
#: contrib/auth/models.py:137
#: contrib/auth/models.py:144
msgid "active"
msgstr "aktywny"
#: contrib/auth/models.py:137
#: contrib/auth/models.py:144
msgid ""
"Designates whether this user should be treated as active. Unselect this "
"instead of deleting accounts."
@ -1188,11 +1196,11 @@ msgstr ""
"Oznacza czy użytkownika należy uważać za aktywnego. Odznacz tozamiast usuwać "
"konta."
#: contrib/auth/models.py:138
#: contrib/auth/models.py:145
msgid "superuser status"
msgstr "Główny Administrator"
#: contrib/auth/models.py:138
#: contrib/auth/models.py:145
msgid ""
"Designates that this user has all permissions without explicitly assigning "
"them."
@ -1200,15 +1208,15 @@ msgstr ""
"Oznacza, że ten użytkownik ma wszystkie uprawnienia bez jawnego "
"przypisywania ich."
#: contrib/auth/models.py:139
#: contrib/auth/models.py:146
msgid "last login"
msgstr "ostatnio zalogowany"
#: contrib/auth/models.py:140
#: contrib/auth/models.py:147
msgid "date joined"
msgstr "data przyłączenia"
#: contrib/auth/models.py:142
#: contrib/auth/models.py:149
msgid ""
"In addition to the permissions manually assigned, this user will also get "
"all permissions granted to each group he/she is in."
@ -1216,39 +1224,39 @@ msgstr ""
"Oprócz uprawnień przypisanych bezpośrednio użytkownikowi otrzyma on "
"uprawnienia grup, do których należy."
#: contrib/auth/models.py:143
#: contrib/auth/models.py:150
msgid "user permissions"
msgstr "uprawnienia użytkownika"
#: contrib/auth/models.py:147
#: contrib/auth/models.py:154
msgid "user"
msgstr "użytkownik"
#: contrib/auth/models.py:148
#: contrib/auth/models.py:155
msgid "users"
msgstr "użytkownicy"
#: contrib/auth/models.py:154
#: contrib/auth/models.py:161
msgid "Personal info"
msgstr "Dane osobowe"
#: contrib/auth/models.py:155
#: contrib/auth/models.py:162
msgid "Permissions"
msgstr "Uprawnienia"
#: contrib/auth/models.py:156
#: contrib/auth/models.py:163
msgid "Important dates"
msgstr "Ważne daty"
#: contrib/auth/models.py:157
#: contrib/auth/models.py:164
msgid "Groups"
msgstr "Grupy"
#: contrib/auth/models.py:316
#: contrib/auth/models.py:323
msgid "message"
msgstr "wiadomość"
#: contrib/auth/views.py:47
#: contrib/auth/views.py:48
msgid "Logged out"
msgstr "Wylogowany"
@ -3516,23 +3524,23 @@ msgstr "przekieruj"
msgid "redirects"
msgstr "przekierowania"
#: contrib/sessions/models.py:41
#: contrib/sessions/models.py:45
msgid "session key"
msgstr "klucz sesji"
#: contrib/sessions/models.py:42
#: contrib/sessions/models.py:47
msgid "session data"
msgstr "data sesji"
#: contrib/sessions/models.py:43
#: contrib/sessions/models.py:48
msgid "expire date"
msgstr "data wygaśnięcia sesji"
#: contrib/sessions/models.py:48
#: contrib/sessions/models.py:53
msgid "session"
msgstr "sesja"
#: contrib/sessions/models.py:49
#: contrib/sessions/models.py:54
msgid "sessions"
msgstr "sesje"
@ -3617,7 +3625,7 @@ msgstr "Rok nie może być wcześniejszy niż 1900."
msgid "Invalid date: %s"
msgstr "Niepoprawna data: %s"
#: core/validators.py:156 db/models/fields/__init__.py:527
#: core/validators.py:156 db/models/fields/__init__.py:548
msgid "Enter a valid date in YYYY-MM-DD format."
msgstr "Proszę wpisać poprawną datę w formacie RRRR-MM-DD."
@ -3625,7 +3633,7 @@ msgstr "Proszę wpisać poprawną datę w formacie RRRR-MM-DD."
msgid "Enter a valid time in HH:MM format."
msgstr "Proszę wpisać poprawną godzinę w formacie HH:MM."
#: core/validators.py:165 db/models/fields/__init__.py:604
#: core/validators.py:165 db/models/fields/__init__.py:625
msgid "Enter a valid date/time in YYYY-MM-DD HH:MM format."
msgstr "Wprowadź poprawną datę i godzinę w formacie RRRR-MM-DD GG:MM."
@ -3888,60 +3896,60 @@ msgstr ""
msgid "%(object)s with this %(type)s already exists for the given %(field)s."
msgstr "%(object)s z %(type)s już istnieje dla %(field)s."
#: db/models/fields/__init__.py:52
#: db/models/fields/__init__.py:51
#, python-format
msgid "%(optname)s with this %(fieldname)s already exists."
msgstr "Już istnieje %(optname)s z %(fieldname)s."
#: db/models/fields/__init__.py:161 db/models/fields/__init__.py:327
#: db/models/fields/__init__.py:759 db/models/fields/__init__.py:770
#: db/models/fields/__init__.py:176 db/models/fields/__init__.py:348
#: db/models/fields/__init__.py:780 db/models/fields/__init__.py:791
#: newforms/fields.py:46 oldforms/__init__.py:374
msgid "This field is required."
msgstr "To pole jest wymagane."
#: db/models/fields/__init__.py:427
#: db/models/fields/__init__.py:448
msgid "This value must be an integer."
msgstr "Ta wartość musi być liczbą całkowitą."
#: db/models/fields/__init__.py:466
#: db/models/fields/__init__.py:487
msgid "This value must be either True or False."
msgstr ""
"Ta wartość musi być wartością logiczną (True, False - prawda lub fałsz)."
#: db/models/fields/__init__.py:490
#: db/models/fields/__init__.py:511
msgid "This field cannot be null."
msgstr "To pole nie może być puste."
#: db/models/fields/__init__.py:668
#: db/models/fields/__init__.py:689
msgid "This value must be a decimal number."
msgstr "Ta wartość musi być liczbą dziesiętną."
#: db/models/fields/__init__.py:779
#: db/models/fields/__init__.py:800
msgid "Enter a valid filename."
msgstr "Wpisz poprawną nazwę pliku."
#: db/models/fields/__init__.py:960
#: db/models/fields/__init__.py:981
msgid "This value must be either None, True or False."
msgstr ""
"Ta wartość musi być jedną z None (nic), True (prawda) lub False (fałsz)."
#: db/models/fields/related.py:93
#: db/models/fields/related.py:94
#, python-format
msgid "Please enter a valid %s."
msgstr "Proszę wpisać poprawne %s."
#: db/models/fields/related.py:701
#: db/models/fields/related.py:746
msgid "Separate multiple IDs with commas."
msgstr "Oddziel identyfikatory przecinkami."
#: db/models/fields/related.py:703
#: db/models/fields/related.py:748
msgid ""
"Hold down \"Control\", or \"Command\" on a Mac, to select more than one."
msgstr ""
"Przytrzymaj wciśnięty klawisz \"Ctrl\" lub \"Command\" na Mac'u aby "
"zaznaczyć więcej niż jeden wybór."
#: db/models/fields/related.py:750
#: db/models/fields/related.py:795
#, python-format
msgid "Please enter valid %(self)s IDs. The value %(value)r is invalid."
msgid_plural ""
@ -4003,11 +4011,11 @@ msgstr "Upewnij się, że jest nie więcej niż %s miejsc po przecinku."
msgid "Ensure that there are no more than %s digits before the decimal point."
msgstr "Upewnij się, że jest nie więcej niż %s miejsc przed przecinkiem."
#: newforms/fields.py:263 newforms/fields.py:751
#: newforms/fields.py:263 newforms/fields.py:750
msgid "Enter a valid date."
msgstr "Wpisz poprawną datę."
#: newforms/fields.py:296 newforms/fields.py:752
#: newforms/fields.py:296 newforms/fields.py:751
msgid "Enter a valid time."
msgstr "Wpisz poprawną godzinę."
@ -4031,25 +4039,25 @@ msgstr "Wpisz poprawny URL."
msgid "This URL appears to be a broken link."
msgstr "Ten odnośnik jest nieprawidłowy."
#: newforms/fields.py:560 newforms/models.py:299
#: newforms/fields.py:559 newforms/models.py:305
msgid "Select a valid choice. That choice is not one of the available choices."
msgstr "Wybierz poprawną wartość. Podana nie jest jednym z dostępnych wyborów."
#: newforms/fields.py:599
#: newforms/fields.py:598
#, python-format
msgid "Select a valid choice. %(value)s is not one of the available choices."
msgstr ""
"Wybierz poprawną wartość. %(value)s nie jest jednym z dostępnych wyborów."
#: newforms/fields.py:600 newforms/fields.py:662 newforms/models.py:371
#: newforms/fields.py:599 newforms/fields.py:661 newforms/models.py:372
msgid "Enter a list of values."
msgstr "Podaj listę wartości."
#: newforms/fields.py:780
#: newforms/fields.py:779
msgid "Enter a valid IPv4 address."
msgstr "Wprowadź poprawny adres IPv4."
#: newforms/models.py:372
#: newforms/models.py:373
#, python-format
msgid "Select a valid choice. %s is not one of the available choices."
msgstr "Wybierz poprawną wartość. %s nie jest jednym z dostępnych wyborów."

View File

@ -1,17 +1,18 @@
from django import oldforms
from django.contrib.auth import REDIRECT_FIELD_NAME
from django.contrib.auth.decorators import login_required
from django.contrib.auth.forms import AuthenticationForm
from django.contrib.auth.forms import PasswordResetForm, PasswordChangeForm
from django import oldforms
from django.shortcuts import render_to_response
from django.template import RequestContext
from django.contrib.sites.models import Site, RequestSite
from django.http import HttpResponseRedirect
from django.contrib.auth.decorators import login_required
from django.contrib.auth import REDIRECT_FIELD_NAME
from django.shortcuts import render_to_response
from django.template import RequestContext
from django.utils.http import urlquote
from django.utils.translation import ugettext as _
def login(request, template_name='registration/login.html', redirect_field_name=REDIRECT_FIELD_NAME):
"Displays the login form and handles the login action."
manipulator = AuthenticationForm(request)
manipulator = AuthenticationForm()
redirect_to = request.REQUEST.get(redirect_field_name, '')
if request.POST:
errors = manipulator.get_validation_errors(request.POST)
@ -22,7 +23,8 @@ def login(request, template_name='registration/login.html', redirect_field_name=
redirect_to = settings.LOGIN_REDIRECT_URL
from django.contrib.auth import login
login(request, manipulator.get_user())
request.session.delete_test_cookie()
if request.session.test_cookie_worked():
request.session.delete_test_cookie()
return HttpResponseRedirect(redirect_to)
else:
errors = {}
@ -61,7 +63,7 @@ def redirect_to_login(next, login_url=None, redirect_field_name=REDIRECT_FIELD_N
if not login_url:
from django.conf import settings
login_url = settings.LOGIN_URL
return HttpResponseRedirect('%s?%s=%s' % (login_url, redirect_field_name, next))
return HttpResponseRedirect('%s?%s=%s' % (login_url, urlquote(redirect_field_name), urlquote(next)))
def password_reset(request, is_admin_site=False, template_name='registration/password_reset_form.html',
email_template_name='registration/password_reset_email.html'):
@ -74,7 +76,10 @@ def password_reset(request, is_admin_site=False, template_name='registration/pas
if is_admin_site:
form.save(domain_override=request.META['HTTP_HOST'])
else:
form.save(email_template_name=email_template_name)
if Site._meta.installed:
form.save(email_template_name=email_template_name)
else:
form.save(domain_override=RequestSite(request).domain, email_template_name=email_template_name)
return HttpResponseRedirect('%sdone/' % request.path)
return render_to_response(template_name, {'form': oldforms.FormWrapper(form, new_data, errors)},
context_instance=RequestContext(request))

View File

@ -26,7 +26,8 @@ class FlatPage(models.Model):
(None, {'fields': ('url', 'title', 'content', 'sites')}),
(_('Advanced options'), {'classes': 'collapse', 'fields': ('enable_comments', 'registration_required', 'template_name')}),
)
list_filter = ('sites',)
list_display = ('url', 'title')
list_filter = ('sites', 'enable_comments', 'registration_required')
search_fields = ('url', 'title')
def __unicode__(self):

View File

@ -23,12 +23,16 @@ class TestForm(forms.Form):
class PreviewTests(TestCase):
def setUp(self):
self._old_root_urlconf = settings.ROOT_URLCONF
settings.ROOT_URLCONF = 'django.contrib.formtools.test_urls'
# Create a FormPreview instance to share between tests
self.preview = preview.FormPreview(TestForm)
input_template = '<input type="hidden" name="%s" value="%s" />'
self.input = input_template % (self.preview.unused_name('stage'), "%d")
def tearDown(self):
settings.ROOT_URLCONF = self._old_root_urlconf
def test_unused_name(self):
"""
Verifies name mangling to get uniue field name.

View File

@ -149,7 +149,7 @@ class FormWizard(object):
data = [(bf.name, bf.data or '') for bf in form] + [settings.SECRET_KEY]
# Use HIGHEST_PROTOCOL because it's the most efficient. It requires
# Python 2.3, but Django requires 2.3 anyway, so that's OK.
pickled = pickle.dumps(data, protocol=pickle.HIGHEST_PROTOCOL)
pickled = pickle.dumps(data, pickle.HIGHEST_PROTOCOL)
return md5.new(pickled).hexdigest()
def determine_step(self, request, *args, **kwargs):

View File

@ -6,7 +6,7 @@ AR-specific Form helpers.
from django.newforms import ValidationError
from django.newforms.fields import RegexField, CharField, Select, EMPTY_VALUES
from django.utils.encoding import smart_unicode
from django.utils.translation import ugettext
from django.utils.translation import ugettext_lazy as _
class ARProvinceSelect(Select):
"""
@ -24,7 +24,7 @@ class ARPostalCodeField(RegexField):
See http://www.correoargentino.com.ar/consulta_cpa/home.php
"""
default_error_messages = {
'invalid': ugettext("Enter a postal code in the format NNNN or ANNNNAAA."),
'invalid': _("Enter a postal code in the format NNNN or ANNNNAAA."),
}
def __init__(self, *args, **kwargs):
@ -46,8 +46,8 @@ class ARDNIField(CharField):
A field that validates 'Documento Nacional de Identidad' (DNI) numbers.
"""
default_error_messages = {
'invalid': ugettext("This field requires only numbers."),
'max_digits': ugettext("This field requires 7 or 8 digits."),
'invalid': _("This field requires only numbers."),
'max_digits': _("This field requires 7 or 8 digits."),
}
def __init__(self, *args, **kwargs):
@ -76,8 +76,8 @@ class ARCUITField(RegexField):
CUIT is of the form XX-XXXXXXXX-V. The last digit is a check digit.
"""
default_error_messages = {
'invalid': ugettext('Enter a valid CUIT in XX-XXXXXXXX-X or XXXXXXXXXXXX format.'),
'checksum': ugettext("Invalid CUIT."),
'invalid': _('Enter a valid CUIT in XX-XXXXXXXX-X or XXXXXXXXXXXX format.'),
'checksum': _("Invalid CUIT."),
}
def __init__(self, *args, **kwargs):

View File

@ -5,7 +5,7 @@ Australian-specific Form helpers
from django.newforms import ValidationError
from django.newforms.fields import Field, RegexField, Select, EMPTY_VALUES
from django.newforms.util import smart_unicode
from django.utils.translation import ugettext
from django.utils.translation import ugettext_lazy as _
import re
PHONE_DIGITS_RE = re.compile(r'^(\d{10})$')
@ -13,7 +13,7 @@ PHONE_DIGITS_RE = re.compile(r'^(\d{10})$')
class AUPostCodeField(RegexField):
"""Australian post code field."""
default_error_messages = {
'invalid': ugettext('Enter a 4 digit post code.'),
'invalid': _('Enter a 4 digit post code.'),
}
def __init__(self, *args, **kwargs):

View File

@ -6,7 +6,7 @@ BR-specific Form helpers
from django.newforms import ValidationError
from django.newforms.fields import Field, RegexField, CharField, Select, EMPTY_VALUES
from django.utils.encoding import smart_unicode
from django.utils.translation import ugettext as _
from django.utils.translation import ugettext_lazy as _
import re
try:

View File

@ -5,7 +5,7 @@ Canada-specific Form helpers
from django.newforms import ValidationError
from django.newforms.fields import Field, RegexField, Select, EMPTY_VALUES
from django.newforms.util import smart_unicode
from django.utils.translation import gettext, ugettext
from django.utils.translation import ugettext_lazy as _
import re
phone_digits_re = re.compile(r'^(?:1-?)?(\d{3})[-\.]?(\d{3})[-\.]?(\d{4})$')
@ -14,7 +14,7 @@ sin_re = re.compile(r"^(\d{3})-(\d{3})-(\d{3})$")
class CAPostalCodeField(RegexField):
"""Canadian postal code field."""
default_error_messages = {
'invalid': gettext(u'Enter a postal code in the format XXX XXX.'),
'invalid': _(u'Enter a postal code in the format XXX XXX.'),
}
def __init__(self, *args, **kwargs):
@ -85,7 +85,7 @@ class CASocialInsuranceNumberField(Field):
See: http://en.wikipedia.org/wiki/Social_Insurance_Number
"""
default_error_messages = {
'invalid': ugettext('Enter a valid Canadian Social Insurance number in XXX-XXX-XXX format.'),
'invalid': _('Enter a valid Canadian Social Insurance number in XXX-XXX-XXX format.'),
}
def clean(self, value):

View File

@ -5,7 +5,7 @@ Swiss-specific Form helpers
from django.newforms import ValidationError
from django.newforms.fields import Field, RegexField, Select, EMPTY_VALUES
from django.utils.encoding import smart_unicode
from django.utils.translation import ugettext
from django.utils.translation import ugettext_lazy as _
import re
id_re = re.compile(r"^(?P<idnumber>\w{8})(?P<pos9>(\d{1}|<))(?P<checksum>\d{1})$")
@ -13,7 +13,7 @@ phone_digits_re = re.compile(r'^0([1-9]{1})\d{8}$')
class CHZipCodeField(RegexField):
default_error_messages = {
'invalid': ugettext('Enter a zip code in the format XXXX.'),
'invalid': _('Enter a zip code in the format XXXX.'),
}
def __init__(self, *args, **kwargs):
@ -61,7 +61,7 @@ class CHIdentityCardNumberField(Field):
Algorithm is documented at http://adi.kousz.ch/artikel/IDCHE.htm
"""
default_error_messages = {
'invalid': ugettext('Enter a valid Swiss identity or passport card number in X1234567<0 or 1234567890 format.'),
'invalid': _('Enter a valid Swiss identity or passport card number in X1234567<0 or 1234567890 format.'),
}
def has_valid_checksum(self, number):

View File

@ -4,7 +4,7 @@ Chile specific form helpers.
from django.newforms import ValidationError
from django.newforms.fields import RegexField, Select, EMPTY_VALUES
from django.utils.translation import ugettext
from django.utils.translation import ugettext_lazy as _
from django.utils.encoding import smart_unicode
@ -26,9 +26,9 @@ class CLRutField(RegexField):
https://palena.sii.cl/cvc/dte/ee_empresas_emisoras.html
"""
default_error_messages = {
'invalid': ugettext('Enter a valid Chilean RUT.'),
'strict': ugettext('Enter a valid Chilean RUT. The format is XX.XXX.XXX-X.'),
'checksum': ugettext('The Chilean RUT is not valid.'),
'invalid': _('Enter a valid Chilean RUT.'),
'strict': _('Enter a valid Chilean RUT. The format is XX.XXX.XXX-X.'),
'checksum': _('The Chilean RUT is not valid.'),
}
def __init__(self, *args, **kwargs):

View File

@ -4,14 +4,14 @@ DE-specific Form helpers
from django.newforms import ValidationError
from django.newforms.fields import Field, RegexField, Select, EMPTY_VALUES
from django.utils.translation import ugettext
from django.utils.translation import ugettext_lazy as _
import re
id_re = re.compile(r"^(?P<residence>\d{10})(?P<origin>\w{1,3})[-\ ]?(?P<birthday>\d{7})[-\ ]?(?P<validity>\d{7})[-\ ]?(?P<checksum>\d{1})$")
class DEZipCodeField(RegexField):
default_error_messages = {
'invalid': ugettext('Enter a zip code in the format XXXXX.'),
'invalid': _('Enter a zip code in the format XXXXX.'),
}
def __init__(self, *args, **kwargs):
super(DEZipCodeField, self).__init__(r'^\d{5}$',
@ -38,7 +38,7 @@ class DEIdentityCardNumberField(Field):
Algorithm is documented at http://de.wikipedia.org/wiki/Personalausweis
"""
default_error_messages = {
'invalid': ugettext('Enter a valid German identity card number in XXXXXXXXXXX-XXXXXXX-XXXXXXX-X format.'),
'invalid': _('Enter a valid German identity card number in XXXXXXXXXXX-XXXXXXX-XXXXXXX-X format.'),
}
def has_valid_checksum(self, number):

View File

@ -5,7 +5,7 @@ Spanish-specific Form helpers
from django.newforms import ValidationError
from django.newforms.fields import RegexField, Select, EMPTY_VALUES
from django.utils.translation import ugettext as _
from django.utils.translation import ugettext_lazy as _
import re
class ESPostalCodeField(RegexField):

View File

@ -5,11 +5,11 @@ FI-specific Form helpers
import re
from django.newforms import ValidationError
from django.newforms.fields import Field, RegexField, Select, EMPTY_VALUES
from django.utils.translation import ugettext
from django.utils.translation import ugettext_lazy as _
class FIZipCodeField(RegexField):
default_error_messages = {
'invalid': ugettext('Enter a zip code in the format XXXXX.'),
'invalid': _('Enter a zip code in the format XXXXX.'),
}
def __init__(self, *args, **kwargs):
super(FIZipCodeField, self).__init__(r'^\d{5}$',
@ -25,7 +25,7 @@ class FIMunicipalitySelect(Select):
class FISocialSecurityNumber(Field):
default_error_messages = {
'invalid': ugettext('Enter a valid Finnish social security number.'),
'invalid': _('Enter a valid Finnish social security number.'),
}
def clean(self, value):

View File

@ -5,14 +5,14 @@ FR-specific Form helpers
from django.newforms import ValidationError
from django.newforms.fields import Field, RegexField, Select, EMPTY_VALUES
from django.utils.encoding import smart_unicode
from django.utils.translation import ugettext
from django.utils.translation import ugettext_lazy as _
import re
phone_digits_re = re.compile(r'^0\d(\s|\.)?(\d{2}(\s|\.)?){3}\d{2}$')
class FRZipCodeField(RegexField):
default_error_messages = {
'invalid': ugettext('Enter a zip code in the format XXXXX.'),
'invalid': _('Enter a zip code in the format XXXXX.'),
}
def __init__(self, *args, **kwargs):

View File

@ -5,7 +5,7 @@ Iceland specific form helpers.
from django.newforms import ValidationError
from django.newforms.fields import RegexField, EMPTY_VALUES
from django.newforms.widgets import Select
from django.utils.translation import ugettext
from django.utils.translation import ugettext_lazy as _
from django.utils.encoding import smart_unicode
class ISIdNumberField(RegexField):
@ -14,8 +14,8 @@ class ISIdNumberField(RegexField):
of Iceland has.
"""
default_error_messages = {
'invalid': ugettext('Enter a valid Icelandic identification number. The format is XXXXXX-XXXX.'),
'checksum': ugettext(u'The Icelandic identification number is not valid.'),
'invalid': _('Enter a valid Icelandic identification number. The format is XXXXXX-XXXX.'),
'checksum': _(u'The Icelandic identification number is not valid.'),
}
def __init__(self, *args, **kwargs):

View File

@ -4,14 +4,14 @@ IT-specific Form helpers
from django.newforms import ValidationError
from django.newforms.fields import Field, RegexField, Select, EMPTY_VALUES
from django.utils.translation import ugettext
from django.utils.translation import ugettext_lazy as _
from django.utils.encoding import smart_unicode
from django.contrib.localflavor.it.util import ssn_check_digit, vat_number_check_digit
import re
class ITZipCodeField(RegexField):
default_error_messages = {
'invalid': ugettext('Enter a valid zip code.'),
'invalid': _('Enter a valid zip code.'),
}
def __init__(self, *args, **kwargs):
super(ITZipCodeField, self).__init__(r'^\d{5}$',
@ -27,7 +27,7 @@ class ITRegionSelect(Select):
class ITProvinceSelect(Select):
"""
A Select widget that uses a list of IT regions as its choices.
A Select widget that uses a list of IT provinces as its choices.
"""
def __init__(self, attrs=None):
from it_province import PROVINCE_CHOICES
@ -40,7 +40,7 @@ class ITSocialSecurityNumberField(RegexField):
'Informazioni sulla codificazione delle persone fisiche'.
"""
default_error_messages = {
'invalid': ugettext(u'Enter a valid Social Security number.'),
'invalid': _(u'Enter a valid Social Security number.'),
}
def __init__(self, *args, **kwargs):
@ -65,7 +65,7 @@ class ITVatNumberField(Field):
A form field that validates Italian VAT numbers (partita IVA).
"""
default_error_messages = {
'invalid': ugettext(u'Enter a valid VAT number.'),
'invalid': _(u'Enter a valid VAT number.'),
}
def clean(self, value):

View File

@ -4,7 +4,7 @@ JP-specific Form helpers
from django.core import validators
from django.newforms import ValidationError
from django.utils.translation import ugettext
from django.utils.translation import ugettext_lazy as _
from django.newforms.fields import RegexField, Select
class JPPostalCodeField(RegexField):
@ -14,7 +14,7 @@ class JPPostalCodeField(RegexField):
Accepts 7 digits, with or without a hyphen.
"""
default_error_messages = {
'invalid': ugettext('Enter a postal code in the format XXXXXXX or XXX-XXXX.'),
'invalid': _('Enter a postal code in the format XXXXXXX or XXX-XXXX.'),
}
def __init__(self, *args, **kwargs):

View File

@ -6,7 +6,7 @@ import re
from django.newforms import ValidationError
from django.newforms.fields import Field, Select, EMPTY_VALUES
from django.utils.translation import ugettext as _
from django.utils.translation import ugettext_lazy as _
from django.utils.encoding import smart_unicode
pc_re = re.compile('^\d{4}[A-Z]{2}$')

View File

@ -5,11 +5,11 @@ Norwegian-specific Form helpers
import re, datetime
from django.newforms import ValidationError
from django.newforms.fields import Field, RegexField, Select, EMPTY_VALUES
from django.utils.translation import ugettext
from django.utils.translation import ugettext_lazy as _
class NOZipCodeField(RegexField):
default_error_messages = {
'invalid': ugettext('Enter a zip code in the format XXXX.'),
'invalid': _('Enter a zip code in the format XXXX.'),
}
def __init__(self, *args, **kwargs):
@ -30,7 +30,7 @@ class NOSocialSecurityNumber(Field):
Algorithm is documented at http://no.wikipedia.org/wiki/Personnummer
"""
default_error_messages = {
'invalid': ugettext(u'Enter a valid Norwegian social security number.'),
'invalid': _(u'Enter a valid Norwegian social security number.'),
}
def clean(self, value):

View File

@ -5,7 +5,7 @@ PE-specific Form helpers.
from django.newforms import ValidationError
from django.newforms.fields import RegexField, CharField, Select, EMPTY_VALUES
from django.utils.translation import ugettext
from django.utils.translation import ugettext_lazy as _
class PEDepartmentSelect(Select):
"""
@ -20,8 +20,8 @@ class PEDNIField(CharField):
A field that validates `Documento Nacional de IdentidadŽ (DNI) numbers.
"""
default_error_messages = {
'invalid': ugettext("This field requires only numbers."),
'max_digits': ugettext("This field requires 8 digits."),
'invalid': _("This field requires only numbers."),
'max_digits': _("This field requires 8 digits."),
}
def __init__(self, *args, **kwargs):
@ -48,8 +48,8 @@ class PERUCField(RegexField):
the form XXXXXXXXXXX.
"""
default_error_messages = {
'invalid': ugettext("This field requires only numbers."),
'max_digits': ugettext("This field requires 11 digits."),
'invalid': _("This field requires only numbers."),
'max_digits': _("This field requires 11 digits."),
}
def __init__(self, *args, **kwargs):

View File

@ -6,7 +6,7 @@ import re
from django.newforms import ValidationError
from django.newforms.fields import Select, RegexField
from django.utils.translation import ugettext as _
from django.utils.translation import ugettext_lazy as _
class PLVoivodeshipSelect(Select):
"""

View File

@ -3,7 +3,7 @@ Slovak-specific form helpers
"""
from django.newforms.fields import Select, RegexField
from django.utils.translation import ugettext
from django.utils.translation import ugettext_lazy as _
class SKRegionSelect(Select):
"""
@ -27,7 +27,7 @@ class SKPostalCodeField(RegexField):
Valid form is XXXXX or XXX XX, where X represents integer.
"""
default_error_messages = {
'invalid': ugettext(u'Enter a postal code in the format XXXXX or XXX XX.'),
'invalid': _(u'Enter a postal code in the format XXXXX or XXX XX.'),
}
def __init__(self, *args, **kwargs):

View File

@ -6,7 +6,7 @@ import re
from django.newforms.fields import CharField, Select
from django.newforms import ValidationError
from django.utils.translation import ugettext
from django.utils.translation import ugettext_lazy as _
class UKPostcodeField(CharField):
"""
@ -18,7 +18,7 @@ class UKPostcodeField(CharField):
The value is uppercased and a space added in the correct place, if required.
"""
default_error_messages = {
'invalid': ugettext(u'Enter a valid postcode.'),
'invalid': _(u'Enter a valid postcode.'),
}
outcode_pattern = '[A-PR-UWYZ]([0-9]{1,2}|([A-HIK-Y][0-9](|[0-9]|[ABEHMNPRVWXY]))|[0-9][A-HJKSTUW])'
incode_pattern = '[0-9][ABD-HJLNP-UW-Z]{2}'

View File

@ -5,7 +5,7 @@ Sources:
Welsh regions: http://en.wikipedia.org/wiki/Preserved_counties_of_Wales
Scottish regions: http://en.wikipedia.org/wiki/Regions_and_districts_of_Scotland
"""
from django.utils.translation import ugettext as _
from django.utils.translation import ugettext_lazy as _
ENGLAND_REGION_CHOICES = (
("Bedfordshire", _("Bedfordshire")),

View File

@ -5,7 +5,7 @@ USA-specific Form helpers
from django.newforms import ValidationError
from django.newforms.fields import Field, RegexField, Select, EMPTY_VALUES
from django.utils.encoding import smart_unicode
from django.utils.translation import ugettext
from django.utils.translation import ugettext_lazy as _
import re
phone_digits_re = re.compile(r'^(?:1-?)?(\d{3})[-\.]?(\d{3})[-\.]?(\d{4})$')
@ -13,7 +13,7 @@ ssn_re = re.compile(r"^(?P<area>\d{3})[-\ ]?(?P<group>\d{2})[-\ ]?(?P<serial>\d{
class USZipCodeField(RegexField):
default_error_messages = {
'invalid': ugettext('Enter a zip code in the format XXXXX or XXXXX-XXXX.'),
'invalid': _('Enter a zip code in the format XXXXX or XXXXX-XXXX.'),
}
def __init__(self, *args, **kwargs):
@ -51,7 +51,7 @@ class USSocialSecurityNumberField(Field):
1962 promotional number).
"""
default_error_messages = {
'invalid': ugettext('Enter a valid U.S. Social Security number in XXX-XX-XXXX format.'),
'invalid': _('Enter a valid U.S. Social Security number in XXX-XX-XXXX format.'),
}
def clean(self, value):

View File

@ -17,6 +17,7 @@ class Redirect(models.Model):
ordering = ('old_path',)
class Admin:
list_display = ('old_path', 'new_path')
list_filter = ('site',)
search_fields = ('old_path', 'new_path')

View File

@ -5,14 +5,15 @@ import random
import sys
import time
from datetime import datetime, timedelta
from django.conf import settings
from django.core.exceptions import SuspiciousOperation
try:
import cPickle as pickle
except ImportError:
import pickle
from django.conf import settings
from django.core.exceptions import SuspiciousOperation
class SessionBase(object):
"""
Base class for all Session classes.
@ -87,6 +88,25 @@ class SessionBase(object):
except:
return {}
def update(self, dict_):
self._session.update(dict_)
self.modified = True
def has_key(self, key):
return self._session.has_key(key)
def values(self):
return self._session.values()
def iterkeys(self):
return self._session.iterkeys()
def itervalues(self):
return self._session.itervalues()
def iteritems(self):
return self._session.iteritems()
def _get_new_session_key(self):
"Returns session key that isn't being used."
# The random module is seeded when this Apache child is created.
@ -150,8 +170,8 @@ class SessionBase(object):
def set_expiry(self, value):
"""
Sets a custom expiration for the session. ``value`` can be an integer, a
Python ``datetime`` or ``timedelta`` object or ``None``.
Sets a custom expiration for the session. ``value`` can be an integer,
a Python ``datetime`` or ``timedelta`` object or ``None``.
If ``value`` is an integer, the session will expire after that many
seconds of inactivity. If set to ``0`` then the session will expire on

View File

@ -2,6 +2,7 @@ from django.conf import settings
from django.contrib.sessions.backends.base import SessionBase
from django.core.cache import cache
class SessionStore(SessionBase):
"""
A cache-based session store.
@ -23,4 +24,4 @@ class SessionStore(SessionBase):
return False
def delete(self, session_key):
self._cache.delete(session_key)
self._cache.delete(session_key)

View File

@ -1,12 +1,14 @@
import datetime
from django.conf import settings
from django.contrib.sessions.models import Session
from django.contrib.sessions.backends.base import SessionBase
from django.core.exceptions import SuspiciousOperation
import datetime
class SessionStore(SessionBase):
"""
Implements database session store
Implements database session store.
"""
def __init__(self, session_key=None):
super(SessionStore, self).__init__(session_key)

View File

@ -1,9 +1,11 @@
import os
import tempfile
from django.conf import settings
from django.contrib.sessions.backends.base import SessionBase
from django.core.exceptions import SuspiciousOperation, ImproperlyConfigured
class SessionStore(SessionBase):
"""
Implements a file based session store.
@ -15,10 +17,10 @@ class SessionStore(SessionBase):
# Make sure the storage path is valid.
if not os.path.isdir(self.storage_path):
raise ImproperlyConfigured("The session storage path %r doesn't exist. "\
"Please set your SESSION_FILE_PATH setting "\
"to an existing directory in which Django "\
"can store session data." % self.storage_path)
raise ImproperlyConfigured(
"The session storage path %r doesn't exist. Please set your"
" SESSION_FILE_PATH setting to an existing directory in which"
" Django can store session data." % self.storage_path)
self.file_prefix = settings.SESSION_COOKIE_NAME
super(SessionStore, self).__init__(session_key)
@ -31,9 +33,11 @@ class SessionStore(SessionBase):
session_key = self.session_key
# Make sure we're not vulnerable to directory traversal. Session keys
# should always be md5s, so they should never contain directory components.
# should always be md5s, so they should never contain directory
# components.
if os.path.sep in session_key:
raise SuspiciousOperation("Invalid characters (directory components) in session key")
raise SuspiciousOperation(
"Invalid characters (directory components) in session key")
return os.path.join(self.storage_path, self.file_prefix + session_key)

View File

@ -7,6 +7,7 @@ from django.utils.http import cookie_date
TEST_COOKIE_NAME = 'testcookie'
TEST_COOKIE_VALUE = 'worked'
class SessionMiddleware(object):
def process_request(self, request):
@ -40,5 +41,4 @@ class SessionMiddleware(object):
expires=expires, domain=settings.SESSION_COOKIE_DOMAIN,
path=settings.SESSION_COOKIE_PATH,
secure=settings.SESSION_COOKIE_SECURE or None)
return response

View File

@ -6,9 +6,12 @@ from django.db import models
from django.utils.translation import ugettext_lazy as _
from django.conf import settings
class SessionManager(models.Manager):
def encode(self, session_dict):
"Returns the given session dictionary pickled and encoded as a string."
"""
Returns the given session dictionary pickled and encoded as a string.
"""
pickled = pickle.dumps(session_dict)
pickled_md5 = md5.new(pickled + settings.SECRET_KEY).hexdigest()
return base64.encodestring(pickled + pickled_md5)
@ -21,6 +24,7 @@ class SessionManager(models.Manager):
s.delete() # Clear sessions with no data.
return s
class Session(models.Model):
"""
Django provides full support for anonymous sessions. The session
@ -38,7 +42,8 @@ class Session(models.Model):
the sessions documentation that is shipped with Django (also available
on the Django website).
"""
session_key = models.CharField(_('session key'), max_length=40, primary_key=True)
session_key = models.CharField(_('session key'), max_length=40,
primary_key=True)
session_data = models.TextField(_('session data'))
expire_date = models.DateTimeField(_('expire date'))
objects = SessionManager()

View File

@ -89,6 +89,66 @@ False
>>> s.pop('some key', 'does not exist')
'does not exist'
>>> s.get('update key', None)
# test .update()
>>> s.modified = s.accessed = False # Reset to pretend this wasn't accessed previously
>>> s.update({'update key':1})
>>> s.accessed, s.modified
(True, True)
>>> s.get('update key', None)
1
# test .has_key()
>>> s.modified = s.accessed = False # Reset to pretend this wasn't accessed previously
>>> s.has_key('update key')
True
>>> s.accessed, s.modified
(True, False)
# test .values()
>>> s = SessionBase()
>>> s.values()
[]
>>> s.accessed
True
>>> s['x'] = 1
>>> s.values()
[1]
# test .iterkeys()
>>> s.accessed = False
>>> i = s.iterkeys()
>>> hasattr(i,'__iter__')
True
>>> s.accessed
True
>>> list(i)
['x']
# test .itervalues()
>>> s.accessed = False
>>> i = s.itervalues()
>>> hasattr(i,'__iter__')
True
>>> s.accessed
True
>>> list(i)
[1]
# test .iteritems()
>>> s.accessed = False
>>> i = s.iteritems()
>>> hasattr(i,'__iter__')
True
>>> s.accessed
True
>>> list(i)
[('x', 1)]
#########################
# Custom session expiry #
#########################

View File

@ -13,5 +13,6 @@ def create_default_site(app, created_models, verbosity):
print "Creating example.com Site object"
s = Site(domain="example.com", name="example.com")
s.save()
Site.objects.clear_cache()
dispatcher.connect(create_default_site, sender=site_app, signal=signals.post_syncdb)

View File

@ -44,6 +44,15 @@ class Site(models.Model):
def __unicode__(self):
return self.domain
def delete(self):
pk = self.pk
super(Site, self).delete()
try:
del(SITE_CACHE[pk])
except KeyError:
pass
class RequestSite(object):
"""
A class that shares the primary interface of Site (i.e., it has

View File

@ -0,0 +1,13 @@
"""
>>> # Make sure that get_current() does not return a deleted Site object.
>>> from django.contrib.sites.models import Site
>>> s = Site.objects.get_current()
>>> isinstance(s, Site)
True
>>> s.delete()
>>> Site.objects.get_current()
Traceback (most recent call last):
...
DoesNotExist: Site matching query does not exist.
"""

View File

@ -111,7 +111,10 @@ class Command(BaseCommand):
models.add(obj.object.__class__)
obj.save()
label_found = True
except Exception, e:
except (SystemExit, KeyboardInterrupt):
raise
except Exception:
import traceback
fixture.close()
transaction.rollback()
transaction.leave_transaction_management()
@ -121,7 +124,7 @@ class Command(BaseCommand):
else:
sys.stderr.write(
self.style.ERROR("Problem installing fixture '%s': %s\n" %
(full_path, str(e))))
(full_path, traceback.format_exc())))
return
fixture.close()
except:

View File

@ -7,4 +7,4 @@ class Command(AppCommand):
def handle_app(self, app, **options):
from django.core.management.sql import sql_create
return '\n'.join(sql_create(app, self.style))
return u'\n'.join(sql_create(app, self.style)).encode('utf-8')

View File

@ -7,4 +7,4 @@ class Command(AppCommand):
def handle_app(self, app, **options):
from django.core.management.sql import sql_all
return '\n'.join(sql_all(app, self.style))
return u'\n'.join(sql_all(app, self.style)).encode('utf-8')

View File

@ -7,4 +7,4 @@ class Command(AppCommand):
def handle_app(self, app, **options):
from django.core.management.sql import sql_delete
return '\n'.join(sql_delete(app, self.style))
return u'\n'.join(sql_delete(app, self.style)).encode('utf-8')

View File

@ -7,4 +7,4 @@ class Command(AppCommand):
def handle_app(self, app, **options):
from django.core.management.sql import sql_custom
return '\n'.join(sql_custom(app, self.style))
return u'\n'.join(sql_custom(app, self.style)).encode('utf-8')

View File

@ -7,4 +7,4 @@ class Command(NoArgsCommand):
def handle_noargs(self, **options):
from django.core.management.sql import sql_flush
return '\n'.join(sql_flush(self.style, only_django=True))
return u'\n'.join(sql_flush(self.style, only_django=True)).encode('utf-8')

View File

@ -7,4 +7,4 @@ class Command(AppCommand):
def handle_app(self, app, **options):
from django.core.management.sql import sql_indexes
return '\n'.join(sql_indexes(app, self.style))
return u'\n'.join(sql_indexes(app, self.style)).encode('utf-8')

View File

@ -7,4 +7,4 @@ class Command(AppCommand):
def handle_app(self, app, **options):
from django.core.management.sql import sql_reset
return '\n'.join(sql_reset(app, self.style))
return u'\n'.join(sql_reset(app, self.style)).encode('utf-8')

View File

@ -6,4 +6,4 @@ class Command(AppCommand):
def handle_app(self, app, **options):
from django.db import connection, models
return '\n'.join(connection.ops.sequence_reset_sql(self.style, models.get_models(app)))
return u'\n'.join(connection.ops.sequence_reset_sql(self.style, models.get_models(app))).encode('utf-8')

View File

@ -3,8 +3,7 @@ import os
from django.core.management.base import copy_helper, CommandError, LabelCommand
class Command(LabelCommand):
help = ("Creates a Django app directory structure for the given app name"
" in the current directory.")
help = "Creates a Django app directory structure for the given app name in the current directory."
args = "[appname]"
label = 'application name'
@ -16,6 +15,7 @@ class Command(LabelCommand):
def handle_label(self, app_name, directory=None, **options):
if directory is None:
directory = os.getcwd()
# Determine the project_name by using the basename of directory,
# which should be the full path of the project directory (or the
# current directory if no directory was passed).
@ -23,6 +23,15 @@ class Command(LabelCommand):
if app_name == project_name:
raise CommandError("You cannot create an app with the same name"
" (%r) as your project." % app_name)
# Check that the app_name cannot be imported.
try:
__import__(app_name)
except ImportError:
pass
else:
raise CommandError("%r conflicts with the name of an existing Python module and cannot be used as an app name. Please try another name." % app_name)
copy_helper(self.style, 'app', app_name, directory, project_name)
class ProjectCommand(Command):

View File

@ -3,8 +3,6 @@ import os
import re
from random import choice
INVALID_PROJECT_NAMES = ('django', 'site', 'test')
class Command(LabelCommand):
help = "Creates a Django project directory structure for the given project name in the current directory."
args = "[projectname]"
@ -20,13 +18,13 @@ class Command(LabelCommand):
# the parent directory.
directory = os.getcwd()
# Check that the project_name cannot be imported.
try:
proj_name = __import__(project_name)
if proj_name:
raise CommandError("%r conflicts with the name of an existing Python module and cannot be used as a project name. Please try another name." % project_name)
__import__(project_name)
except ImportError:
if project_name in INVALID_PROJECT_NAMES:
raise CommandError("%r contains an invalid project name. Please try another name." % project_name)
pass
else:
raise CommandError("%r conflicts with the name of an existing Python module and cannot be used as a project name. Please try another name." % project_name)
copy_helper(self.style, 'project', project_name, directory)

View File

@ -25,6 +25,7 @@ class Command(NoArgsCommand):
verbosity = int(options.get('verbosity', 1))
interactive = options.get('interactive')
show_traceback = options.get('traceback', False)
self.style = no_style()
@ -119,12 +120,17 @@ class Command(NoArgsCommand):
for sql in custom_sql:
cursor.execute(sql)
except Exception, e:
sys.stderr.write("Failed to install custom SQL for %s.%s model: %s" % \
sys.stderr.write("Failed to install custom SQL for %s.%s model: %s\n" % \
(app_name, model._meta.object_name, e))
if show_traceback:
import traceback
traceback.print_exc()
transaction.rollback_unless_managed()
else:
transaction.commit_unless_managed()
else:
if verbosity >= 2:
print "No custom SQL for %s.%s model" % (app_name, model._meta.object_name)
# Install SQL indicies for all newly created models
for app in models.get_apps():
app_name = app.__name__.split('.')[-2]

View File

@ -17,7 +17,7 @@ import urllib
from django.utils.http import http_date
__version__ = "0.1"
__all__ = ['WSGIServer','WSGIRequestHandler','demo_app']
__all__ = ['WSGIServer','WSGIRequestHandler']
server_version = "WSGIServer/" + __version__
sys_version = "Python/" + sys.version.split()[0]

View File

@ -86,7 +86,7 @@ def reverse_helper(regex, *args, **kwargs):
"""
# TODO: Handle nested parenthesis in the following regex.
result = re.sub(r'\(([^)]+)\)', MatchChecker(args, kwargs), regex.pattern)
return result.replace('^', '').replace('$', '')
return result.replace('^', '').replace('$', '').replace('\\', '')
class MatchChecker(object):
"Class used in reverse RegexURLPattern lookup."

View File

@ -45,13 +45,16 @@ class BaseDatabaseFeatures(object):
autoindexes_primary_keys = True
inline_fk_references = True
needs_datetime_string_cast = True
needs_upper_for_iops = False
supports_constraints = True
supports_tablespaces = False
uses_case_insensitive_names = False
uses_custom_query_class = False
empty_fetchmany_value = []
update_can_self_select = True
supports_usecs = True
time_field_needs_date = False
interprets_empty_strings_as_nulls = False
date_field_supports_time_value = True
class BaseDatabaseOperations(object):
"""
@ -266,3 +269,8 @@ class BaseDatabaseOperations(object):
tablespaces.
"""
return None
def prep_for_like_query(self, x):
"""Prepares a value for use in a LIKE query."""
from django.utils.encoding import smart_unicode
return smart_unicode(x).replace("\\", "\\\\").replace("%", "\%").replace("_", "\_")

View File

@ -64,6 +64,7 @@ class DatabaseFeatures(BaseDatabaseFeatures):
inline_fk_references = False
empty_fetchmany_value = ()
update_can_self_select = False
supports_usecs = False
class DatabaseOperations(BaseDatabaseOperations):
def date_extract_sql(self, lookup_type, field_name):

View File

@ -68,6 +68,7 @@ class DatabaseFeatures(BaseDatabaseFeatures):
inline_fk_references = False
empty_fetchmany_value = ()
update_can_self_select = False
supports_usecs = False
class DatabaseOperations(BaseDatabaseOperations):
def date_extract_sql(self, lookup_type, field_name):

View File

@ -27,10 +27,12 @@ class DatabaseFeatures(BaseDatabaseFeatures):
allows_unique_and_pk = False # Suppress UNIQUE/PK for Oracle (ORA-02259)
empty_fetchmany_value = ()
needs_datetime_string_cast = False
needs_upper_for_iops = True
supports_tablespaces = True
uses_case_insensitive_names = True
uses_custom_query_class = True
time_field_needs_date = True
interprets_empty_strings_as_nulls = True
date_field_supports_time_value = False
class DatabaseOperations(BaseDatabaseOperations):
def autoinc_sql(self, table, column):

View File

@ -5,9 +5,13 @@ from django.core import management
# types, as strings. Column-type strings can contain format strings; they'll
# be interpolated against the values of Field.__dict__ before being output.
# If a column type is set to None, it won't be included in the output.
#
# Any format strings starting with "qn_" are quoted before being used in the
# output (the "qn_" prefix is stripped before the lookup is performed.
DATA_TYPES = {
'AutoField': 'NUMBER(11)',
'BooleanField': 'NUMBER(1) CHECK (%(column)s IN (0,1))',
'BooleanField': 'NUMBER(1) CHECK (%(qn_column)s IN (0,1))',
'CharField': 'NVARCHAR2(%(max_length)s)',
'CommaSeparatedIntegerField': 'VARCHAR2(%(max_length)s)',
'DateField': 'DATE',
@ -19,11 +23,11 @@ DATA_TYPES = {
'ImageField': 'NVARCHAR2(%(max_length)s)',
'IntegerField': 'NUMBER(11)',
'IPAddressField': 'VARCHAR2(15)',
'NullBooleanField': 'NUMBER(1) CHECK ((%(column)s IN (0,1)) OR (%(column)s IS NULL))',
'NullBooleanField': 'NUMBER(1) CHECK ((%(qn_column)s IN (0,1)) OR (%(column)s IS NULL))',
'OneToOneField': 'NUMBER(11)',
'PhoneNumberField': 'VARCHAR2(20)',
'PositiveIntegerField': 'NUMBER(11) CHECK (%(column)s >= 0)',
'PositiveSmallIntegerField': 'NUMBER(11) CHECK (%(column)s >= 0)',
'PositiveIntegerField': 'NUMBER(11) CHECK (%(qn_column)s >= 0)',
'PositiveSmallIntegerField': 'NUMBER(11) CHECK (%(qn_column)s >= 0)',
'SlugField': 'NVARCHAR2(50)',
'SmallIntegerField': 'NUMBER(11)',
'TextField': 'NCLOB',

View File

@ -10,7 +10,7 @@ from django.core import validators
from django.core.exceptions import ObjectDoesNotExist, MultipleObjectsReturned, FieldError
from django.db.models.fields import AutoField, ImageField, FieldDoesNotExist
from django.db.models.fields.related import OneToOneRel, ManyToOneRel, OneToOneField
from django.db.models.query import delete_objects, Q
from django.db.models.query import delete_objects, Q, CollectedObjects
from django.db.models.options import Options, AdminOptions
from django.db import connection, transaction
from django.db.models import signals
@ -368,17 +368,16 @@ class Model(object):
error_dict[f.name] = errors
return error_dict
def _collect_sub_objects(self, seen_objs):
def _collect_sub_objects(self, seen_objs, parent=None, nullable=False):
"""
Recursively populates seen_objs with all objects related to this object.
When done, seen_objs will be in the format:
{model_class: {pk_val: obj, pk_val: obj, ...},
model_class: {pk_val: obj, pk_val: obj, ...}, ...}
When done, seen_objs.items() will be in the format:
[(model_class, {pk_val: obj, pk_val: obj, ...}),
(model_class, {pk_val: obj, pk_val: obj, ...}),...]
"""
pk_val = self._get_pk_val()
if pk_val in seen_objs.setdefault(self.__class__, {}):
if seen_objs.add(self.__class__, pk_val, self, parent, nullable):
return
seen_objs.setdefault(self.__class__, {})[pk_val] = self
for related in self._meta.get_all_related_objects():
rel_opts_name = related.get_accessor_name()
@ -388,16 +387,16 @@ class Model(object):
except ObjectDoesNotExist:
pass
else:
sub_obj._collect_sub_objects(seen_objs)
sub_obj._collect_sub_objects(seen_objs, self.__class__, related.field.null)
else:
for sub_obj in getattr(self, rel_opts_name).all():
sub_obj._collect_sub_objects(seen_objs)
sub_obj._collect_sub_objects(seen_objs, self.__class__, related.field.null)
def delete(self):
assert self._get_pk_val() is not None, "%s object can't be deleted because its %s attribute is set to None." % (self._meta.object_name, self._meta.pk.attname)
# Find all the objects than need to be deleted
seen_objs = SortedDict()
seen_objs = CollectedObjects()
self._collect_sub_objects(seen_objs)
# Actually delete the objects

View File

@ -7,7 +7,7 @@ try:
except ImportError:
from django.utils import _decimal as decimal # for Python 2.3
from django.db import get_creation_module
from django.db import connection, get_creation_module
from django.db.models import signals
from django.db.models.query_utils import QueryWrapper
from django.dispatch import dispatcher
@ -16,6 +16,7 @@ from django.core import validators
from django import oldforms
from django import newforms as forms
from django.core.exceptions import ObjectDoesNotExist
from django.utils.datastructures import DictWrapper
from django.utils.functional import curry
from django.utils.itercompat import tee
from django.utils.text import capfirst
@ -33,9 +34,6 @@ HORIZONTAL, VERTICAL = 1, 2
BLANK_CHOICE_DASH = [("", "---------")]
BLANK_CHOICE_NONE = [("", "None")]
# prepares a value for use in a LIKE query
prep_for_like_query = lambda x: smart_unicode(x).replace("\\", "\\\\").replace("%", "\%").replace("_", "\_")
# returns the <ul> class for a given radio_admin value
get_ul_class = lambda x: 'radiolist%s' % ((x == HORIZONTAL) and ' inline' or '')
@ -97,7 +95,7 @@ class Field(object):
self.blank, self.null = blank, null
# Oracle treats the empty string ('') as null, so coerce the null
# option whenever '' is a possible value.
if self.empty_strings_allowed and settings.DATABASE_ENGINE == 'oracle':
if self.empty_strings_allowed and connection.features.interprets_empty_strings_as_nulls:
self.null = True
self.core, self.rel, self.default = core, rel, default
self.editable = editable
@ -164,8 +162,9 @@ class Field(object):
# mapped to one of the built-in Django field types. In this case, you
# can implement db_type() instead of get_internal_type() to specify
# exactly which wacky database column type you want to use.
data = DictWrapper(self.__dict__, connection.ops.quote_name, "qn_")
try:
return get_creation_module().DATA_TYPES[self.get_internal_type()] % self.__dict__
return get_creation_module().DATA_TYPES[self.get_internal_type()] % data
except KeyError:
return None
@ -235,13 +234,13 @@ class Field(object):
elif lookup_type in ('range', 'in'):
return value
elif lookup_type in ('contains', 'icontains'):
return ["%%%s%%" % prep_for_like_query(value)]
return ["%%%s%%" % connection.ops.prep_for_like_query(value)]
elif lookup_type == 'iexact':
return [prep_for_like_query(value)]
return [connection.ops.prep_for_like_query(value)]
elif lookup_type in ('startswith', 'istartswith'):
return ["%s%%" % prep_for_like_query(value)]
return ["%s%%" % connection.ops.prep_for_like_query(value)]
elif lookup_type in ('endswith', 'iendswith'):
return ["%%%s" % prep_for_like_query(value)]
return ["%%%s" % connection.ops.prep_for_like_query(value)]
elif lookup_type == 'isnull':
return []
elif lookup_type == 'year':
@ -252,9 +251,12 @@ class Field(object):
if settings.DATABASE_ENGINE == 'sqlite3':
first = '%s-01-01'
second = '%s-12-31 23:59:59.999999'
elif settings.DATABASE_ENGINE == 'oracle' and self.get_internal_type() == 'DateField':
elif not connection.features.date_field_supports_time_value and self.get_internal_type() == 'DateField':
first = '%s-01-01'
second = '%s-12-31'
elif not connection.features.supports_usecs:
first = '%s-01-01 00:00:00'
second = '%s-12-31 23:59:59.99'
else:
first = '%s-01-01 00:00:00'
second = '%s-12-31 23:59:59.999999'
@ -271,7 +273,7 @@ class Field(object):
if callable(self.default):
return self.default()
return force_unicode(self.default, strings_only=True)
if not self.empty_strings_allowed or (self.null and settings.DATABASE_ENGINE != 'oracle'):
if not self.empty_strings_allowed or (self.null and not connection.features.interprets_empty_strings_as_nulls):
return None
return ""
@ -633,7 +635,7 @@ class DateTimeField(DateField):
if value is not None:
# MySQL will throw a warning if microseconds are given, because it
# doesn't support microseconds.
if settings.DATABASE_ENGINE == 'mysql' and hasattr(value, 'microsecond'):
if not connection.features.supports_usecs and hasattr(value, 'microsecond'):
value = value.replace(microsecond=0)
value = smart_unicode(value)
return Field.get_db_prep_save(self, value)
@ -867,7 +869,7 @@ class FilePathField(Field):
self.path, self.match, self.recursive = path, match, recursive
kwargs['max_length'] = kwargs.get('max_length', 100)
Field.__init__(self, verbose_name, name, **kwargs)
def formfield(self, **kwargs):
defaults = {
'path': self.path,
@ -1075,7 +1077,7 @@ class TimeField(Field):
return "TimeField"
def get_db_prep_lookup(self, lookup_type, value):
if settings.DATABASE_ENGINE == 'oracle':
if connection.features.time_field_needs_date:
# Oracle requires a date in order to parse.
def prep(value):
if isinstance(value, datetime.time):
@ -1102,9 +1104,9 @@ class TimeField(Field):
if value is not None:
# MySQL will throw a warning if microseconds are given, because it
# doesn't support microseconds.
if settings.DATABASE_ENGINE == 'mysql' and hasattr(value, 'microsecond'):
if not connection.features.supports_usecs and hasattr(value, 'microsecond'):
value = value.replace(microsecond=0)
if settings.DATABASE_ENGINE == 'oracle':
if connection.features.time_field_needs_date:
# cx_Oracle expects a datetime.datetime to persist into TIMESTAMP field.
if isinstance(value, datetime.time):
value = datetime.datetime(1900, 1, 1, value.hour, value.minute,

View File

@ -103,13 +103,15 @@ class RelatedField(object):
if hasattr(sup, 'contribute_to_class'):
sup.contribute_to_class(cls, name)
if not cls._meta.abstract and self.rel.related_name:
self.rel.related_name = self.rel.related_name % {'class': cls.__name__.lower()}
other = self.rel.to
if isinstance(other, basestring):
add_lazy_relation(cls, self, other)
else:
self.do_related_class(other, cls)
if not cls._meta.abstract and self.rel.related_name:
self.rel.related_name = self.rel.related_name % {'class': cls.__name__.lower()}
def set_attributes_from_rel(self):
self.name = self.name or (self.rel.to._meta.object_name.lower() + '_' + self.rel.to._meta.pk.name)
@ -119,7 +121,8 @@ class RelatedField(object):
def do_related_class(self, other, cls):
self.set_attributes_from_rel()
related = RelatedObject(other, cls, self)
self.contribute_to_related_class(other, related)
if not cls._meta.abstract:
self.contribute_to_related_class(other, related)
def get_db_prep_lookup(self, lookup_type, value):
# If we are doing a lookup on a Related Field, we must be

View File

@ -2,6 +2,8 @@
from django.conf import settings
from django.core.exceptions import ImproperlyConfigured
from django.utils.datastructures import SortedDict
import sys
import os
import threading
@ -18,10 +20,10 @@ class AppCache(object):
# http://aspn.activestate.com/ASPN/Cookbook/Python/Recipe/66531.
__shared_state = dict(
# Keys of app_store are the model modules for each application.
app_store = {},
app_store = SortedDict(),
# Mapping of app_labels to a dictionary of model names to model code.
app_models = {},
app_models = SortedDict(),
# Mapping of app_labels to errors raised when trying to import the app.
app_errors = {},
@ -133,7 +135,7 @@ class AppCache(object):
"""
self._populate()
if app_mod:
return self.app_models.get(app_mod.__name__.split('.')[-2], {}).values()
return self.app_models.get(app_mod.__name__.split('.')[-2], SortedDict()).values()
else:
model_list = []
for app_entry in self.app_models.itervalues():
@ -149,7 +151,7 @@ class AppCache(object):
"""
if seed_cache:
self._populate()
return self.app_models.get(app_label, {}).get(model_name.lower())
return self.app_models.get(app_label, SortedDict()).get(model_name.lower())
def register_models(self, app_label, *models):
"""
@ -157,9 +159,9 @@ class AppCache(object):
"""
for model in models:
# Store as 'name: model' pair in a dictionary
# in the _app_models dictionary
# in the app_models dictionary
model_name = model._meta.object_name.lower()
model_dict = self.app_models.setdefault(app_label, {})
model_dict = self.app_models.setdefault(app_label, SortedDict())
if model_name in model_dict:
# The same model may be imported via different paths (e.g.
# appname.models and project.appname.models). We use the source

View File

@ -274,14 +274,17 @@ class Options(object):
"""
Initialises the field name -> field object mapping.
"""
cache = dict([(f.name, (f, m, True, False)) for f, m in
self.get_fields_with_model()])
for f, model in self.get_m2m_with_model():
cache[f.name] = (f, model, True, True)
cache = {}
# We intentionally handle related m2m objects first so that symmetrical
# m2m accessor names can be overridden, if necessary.
for f, model in self.get_all_related_m2m_objects_with_model():
cache[f.field.related_query_name()] = (f, model, False, True)
for f, model in self.get_all_related_objects_with_model():
cache[f.field.related_query_name()] = (f, model, False, False)
for f, model in self.get_m2m_with_model():
cache[f.name] = (f, model, True, True)
for f, model in self.get_fields_with_model():
cache[f.name] = (f, model, True, False)
if self.order_with_respect_to:
cache['_order'] = OrderWrt(), None, True, False
if app_cache_ready():

View File

@ -16,6 +16,92 @@ ITER_CHUNK_SIZE = CHUNK_SIZE
# Pull into this namespace for backwards compatibility
EmptyResultSet = sql.EmptyResultSet
class CyclicDependency(Exception):
pass
class CollectedObjects(object):
"""
A container that stores keys and lists of values along with
remembering the parent objects for all the keys.
This is used for the database object deletion routines so that we
can calculate the 'leaf' objects which should be deleted first.
"""
def __init__(self):
self.data = {}
self.children = {}
def add(self, model, pk, obj, parent_model, nullable=False):
"""
Adds an item.
model is the class of the object being added,
pk is the primary key, obj is the object itself,
parent_model is the model of the parent object
that this object was reached through, nullable should
be True if this relation is nullable.
If the item already existed in the structure,
returns true, otherwise false.
"""
d = self.data.setdefault(model, SortedDict())
retval = pk in d
d[pk] = obj
# Nullable relationships can be ignored -- they
# are nulled out before deleting, and therefore
# do not affect the order in which objects have
# to be deleted.
if parent_model is not None and not nullable:
self.children.setdefault(parent_model, []).append(model)
return retval
def __contains__(self, key):
return self.data.__contains__(key)
def __getitem__(self, key):
return self.data[key]
def __nonzero__(self):
return bool(self.data)
def iteritems(self):
for k in self.ordered_keys():
yield k, self[k]
def items(self):
return list(self.iteritems())
def keys(self):
return self.ordered_keys()
def ordered_keys(self):
"""
Returns the models in the order that they should be
dealth with i.e. models with no dependencies first.
"""
dealt_with = SortedDict()
# Start with items that have no children
models = self.data.keys()
while len(dealt_with) < len(models):
found = False
for model in models:
children = self.children.setdefault(model, [])
if len([c for c in children if c not in dealt_with]) == 0:
dealt_with[model] = None
found = True
if not found:
raise CyclicDependency("There is a cyclic dependency of items to be processed.")
return dealt_with.keys()
def unordered_keys(self):
"""
Fallback for the case where is a cyclic dependency but we
don't care.
"""
return self.data.keys()
class QuerySet(object):
"Represents a lazy database lookup for a set of objects"
def __init__(self, model=None, query=None):
@ -132,6 +218,8 @@ class QuerySet(object):
def __and__(self, other):
self._merge_sanity_check(other)
if isinstance(other, EmptyQuerySet):
return other._clone()
combined = self._clone()
combined.query.combine(other.query, sql.AND)
return combined
@ -139,6 +227,8 @@ class QuerySet(object):
def __or__(self, other):
self._merge_sanity_check(other)
combined = self._clone()
if isinstance(other, EmptyQuerySet):
return combined
combined.query.combine(other.query, sql.OR)
return combined
@ -275,7 +365,7 @@ class QuerySet(object):
while 1:
# Collect all the objects to be deleted in this chunk, and all the
# objects that are related to the objects that are to be deleted.
seen_objs = SortedDict()
seen_objs = CollectedObjects()
for object in del_query[:CHUNK_SIZE]:
object._collect_sub_objects(seen_objs)
@ -402,7 +492,9 @@ class QuerySet(object):
and usually it will be more natural to use other methods.
"""
if isinstance(filter_obj, Q) or hasattr(filter_obj, 'add_to_query'):
return self._filter_or_exclude(None, filter_obj)
clone = self._clone()
clone.query.add_q(filter_obj)
return clone
else:
return self._filter_or_exclude(None, **filter_obj)
@ -497,11 +589,11 @@ class QuerySet(object):
def _merge_sanity_check(self, other):
"""
Checks that we are merging two comparable queryset classes.
Checks that we are merging two comparable queryset classes. By default
this does nothing, but see the ValuesQuerySet for an example of where
it's useful.
"""
if self.__class__ is not other.__class__:
raise TypeError("Cannot merge querysets of different types ('%s' and '%s'."
% (self.__class__.__name__, other.__class__.__name__))
pass
class ValuesQuerySet(QuerySet):
def __init__(self, *args, **kwargs):
@ -513,7 +605,7 @@ class ValuesQuerySet(QuerySet):
# names of the model fields to select.
def iterator(self):
if (not self.extra_names and
if (not self.extra_names and
len(self.field_names) != len(self.model._meta.fields)):
self.query.trim_extra_select(self.extra_names)
names = self.query.extra_select.keys() + self.field_names
@ -602,9 +694,9 @@ class DateQuerySet(QuerySet):
"""
self.query = self.query.clone(klass=sql.DateQuery, setup=True)
self.query.select = []
self.query.add_date_select(self._field.column, self._kind, self._order)
self.query.add_date_select(self._field, self._kind, self._order)
if self._field.null:
self.query.add_filter(('%s__isnull' % self._field.name, True))
self.query.add_filter(('%s__isnull' % self._field.name, False))
def _clone(self, klass=None, setup=False, **kwargs):
c = super(DateQuerySet, self)._clone(klass, False, **kwargs)
@ -619,6 +711,12 @@ class EmptyQuerySet(QuerySet):
super(EmptyQuerySet, self).__init__(model, query)
self._result_cache = []
def __and__(self, other):
return self._clone()
def __or__(self, other):
return other._clone()
def count(self):
return 0
@ -682,19 +780,27 @@ def delete_objects(seen_objs):
Iterate through a list of seen classes, and remove any instances that are
referred to.
"""
ordered_classes = seen_objs.keys()
ordered_classes.reverse()
try:
ordered_classes = seen_objs.keys()
except CyclicDependency:
# if there is a cyclic dependency, we cannot in general delete
# the objects. However, if an appropriate transaction is set
# up, or if the database is lax enough, it will succeed.
# So for now, we go ahead and try anway.
ordered_classes = seen_objs.unordered_keys()
obj_pairs = {}
for cls in ordered_classes:
seen_objs[cls] = seen_objs[cls].items()
seen_objs[cls].sort()
items = seen_objs[cls].items()
items.sort()
obj_pairs[cls] = items
# Pre notify all instances to be deleted
for pk_val, instance in seen_objs[cls]:
for pk_val, instance in items:
dispatcher.send(signal=signals.pre_delete, sender=cls,
instance=instance)
pk_list = [pk for pk,instance in seen_objs[cls]]
pk_list = [pk for pk,instance in items]
del_query = sql.DeleteQuery(cls, connection)
del_query.delete_batch_related(pk_list)
@ -705,15 +811,17 @@ def delete_objects(seen_objs):
# Now delete the actual data
for cls in ordered_classes:
seen_objs[cls].reverse()
pk_list = [pk for pk,instance in seen_objs[cls]]
items = obj_pairs[cls]
items.reverse()
pk_list = [pk for pk,instance in items]
del_query = sql.DeleteQuery(cls, connection)
del_query.delete_batch(pk_list)
# Last cleanup; set NULLs where there once was a reference to the
# object, NULL the primary key of the found objects, and perform
# post-notification.
for pk_val, instance in seen_objs[cls]:
for pk_val, instance in items:
for field in cls._meta.fields:
if field.rel and field.null and field.rel.to in seen_objs:
setattr(instance, field.attname, None)

View File

@ -610,6 +610,10 @@ class Query(object):
alias = joins[-1]
col = target.column
# Must use left outer joins for nullable fields.
for join in joins:
self.promote_alias(join)
# If we get to this point and the field is a relation to another model,
# append the default ordering for that model.
if field.rel and len(joins) > 1 and opts.ordering:
@ -631,8 +635,10 @@ class Query(object):
# We have to do the same "final join" optimisation as in
# add_filter, since the final column might not otherwise be part of
# the select set (so we can't order on it).
join = self.alias_map[alias]
if col == join[RHS_JOIN_COL]:
while 1:
join = self.alias_map[alias]
if col != join[RHS_JOIN_COL]:
break
self.unref_alias(alias)
alias = join[LHS_ALIAS]
col = join[LHS_JOIN_COL]
@ -679,12 +685,16 @@ class Query(object):
for the join to contain NULL values on the left. If 'unconditional' is
False, the join is only promoted if it is nullable, otherwise it is
always promoted.
Returns True if the join was promoted.
"""
if ((unconditional or self.alias_map[alias][NULLABLE]) and
self.alias_map[alias] != self.LOUTER):
data = list(self.alias_map[alias])
data[JOIN_TYPE] = self.LOUTER
self.alias_map[alias] = tuple(data)
return True
return False
def change_aliases(self, change_map):
"""
@ -826,6 +836,10 @@ class Query(object):
if not always_create:
for alias in self.join_map.get(t_ident, ()):
if alias not in exclusions:
if lhs_table and not self.alias_refcount[self.alias_map[alias][LHS_ALIAS]]:
# The LHS of this join tuple is no longer part of the
# query, so skip this possibility.
continue
self.ref_alias(alias)
if promote:
self.promote_alias(alias)
@ -985,20 +999,22 @@ class Query(object):
col = target.column
alias = join_list[-1]
if final > 1:
while final > 1:
# An optimization: if the final join is against the same column as
# we are comparing against, we can go back one step in the join
# chain and compare against the lhs of the join instead. The result
# (potentially) involves one less table join.
# chain and compare against the lhs of the join instead (and then
# repeat the optimization). The result, potentially, involves less
# table joins.
join = self.alias_map[alias]
if col == join[RHS_JOIN_COL]:
self.unref_alias(alias)
alias = join[LHS_ALIAS]
col = join[LHS_JOIN_COL]
join_list = join_list[:-1]
final -= 1
if final == penultimate:
penultimate = last.pop()
if col != join[RHS_JOIN_COL]:
break
self.unref_alias(alias)
alias = join[LHS_ALIAS]
col = join[LHS_JOIN_COL]
join_list = join_list[:-1]
final -= 1
if final == penultimate:
penultimate = last.pop()
if (lookup_type == 'isnull' and value is True and not negate and
final > 1):
@ -1033,17 +1049,27 @@ class Query(object):
self.promote_alias(table)
self.where.add((alias, col, field, lookup_type, value), connector)
if negate:
for alias in join_list:
self.promote_alias(alias)
if final > 1 and lookup_type != 'isnull':
for alias in join_list:
if self.alias_map[alias] == self.LOUTER:
j_col = self.alias_map[alias][RHS_JOIN_COL]
entry = Node([(alias, j_col, None, 'isnull', True)])
entry.negate()
self.where.add(entry, AND)
break
if lookup_type != 'isnull':
if final > 1:
for alias in join_list:
if self.alias_map[alias][JOIN_TYPE] == self.LOUTER:
j_col = self.alias_map[alias][RHS_JOIN_COL]
entry = Node([(alias, j_col, None, 'isnull', True)])
entry.negate()
self.where.add(entry, AND)
break
elif not (lookup_type == 'in' and not value):
# Leaky abstraction artifact: We have to specifically
# exclude the "foo__in=[]" case from this handling, because
# it's short-circuited in the Where class.
entry = Node([(alias, col, field, 'isnull', True)])
entry.negate()
self.where.add(entry, AND)
if can_reuse is not None:
can_reuse.update(join_list)
@ -1294,10 +1320,12 @@ class Query(object):
final_alias = join[LHS_ALIAS]
col = join[LHS_JOIN_COL]
joins = joins[:-1]
promote = False
for join in joins[1:]:
# Only nullable aliases are promoted, so we don't end up
# doing unnecessary left outer joins here.
self.promote_alias(join)
if self.promote_alias(join, promote):
promote = True
self.select.append((final_alias, col))
self.select_fields.append(field)
except MultiJoin:

View File

@ -357,12 +357,14 @@ class DateQuery(Query):
date = typecast_timestamp(str(date))
yield date
def add_date_select(self, column, lookup_type, order='ASC'):
def add_date_select(self, field, lookup_type, order='ASC'):
"""
Converts the query into a date extraction query.
"""
alias = self.join((None, self.model._meta.db_table, None, None))
select = Date((alias, column), lookup_type,
result = self.setup_joins([field.name], self.get_meta(),
self.get_initial_alias(), False)
alias = result[3][-1]
select = Date((alias, field.column), lookup_type,
self.connection.ops.date_trunc_sql)
self.select = [select]
self.select_fields = [None]

View File

@ -108,7 +108,7 @@ class CommonMiddleware(object):
if response.has_header('ETag'):
etag = response['ETag']
else:
etag = md5.new(response.content).hexdigest()
etag = '"%s"' % md5.new(response.content).hexdigest()
if response.status_code >= 200 and response.status_code < 300 and request.META.get('HTTP_IF_NONE_MATCH') == etag:
cookies = response.cookies
response = http.HttpResponseNotModified()

View File

@ -514,7 +514,6 @@ class URLField(RegexField):
return value
if self.verify_exists:
import urllib2
from django.conf import settings
headers = {
"Accept": "text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,image/png,*/*;q=0.5",
"Accept-Language": "en-us,en;q=0.5",

View File

@ -285,11 +285,17 @@ class ModelChoiceIterator(object):
def __iter__(self):
if self.field.empty_label is not None:
yield (u"", self.field.empty_label)
for obj in self.queryset:
yield (obj.pk, self.field.label_from_instance(obj))
# Clear the QuerySet cache if required.
if not self.field.cache_choices:
self.queryset._result_cache = None
if self.field.cache_choices:
if self.field.choice_cache is None:
self.field.choice_cache = [
(obj.pk, self.field.label_from_instance(obj))
for obj in self.queryset.all()
]
for choice in self.field.choice_cache:
yield choice
else:
for obj in self.queryset.all():
yield (obj.pk, self.field.label_from_instance(obj))
class ModelChoiceField(ChoiceField):
"""A ChoiceField whose choices are a model QuerySet."""
@ -311,6 +317,7 @@ class ModelChoiceField(ChoiceField):
Field.__init__(self, required, widget, label, initial, help_text,
*args, **kwargs)
self.queryset = queryset
self.choice_cache = None
def _get_queryset(self):
return self._queryset
@ -346,13 +353,7 @@ class ModelChoiceField(ChoiceField):
# the queryset.
return ModelChoiceIterator(self)
def _set_choices(self, value):
# This method is copied from ChoiceField._set_choices(). It's necessary
# because property() doesn't allow a subclass to overwrite only
# _get_choices without implementing _set_choices.
self._choices = self.widget.choices = list(value)
choices = property(_get_choices, _set_choices)
choices = property(_get_choices, ChoiceField._set_choices)
def clean(self, value):
Field.clean(self, value)

View File

@ -281,8 +281,12 @@ class RadioInput(StrAndUnicode):
self.index = index
def __unicode__(self):
return mark_safe(u'<label>%s %s</label>' % (self.tag(),
conditional_escape(force_unicode(self.choice_label))))
if 'id' in self.attrs:
label_for = ' for="%s_%s"' % (self.attrs['id'], self.index)
else:
label_for = ''
choice_label = conditional_escape(force_unicode(self.choice_label))
return mark_safe(u'<label%s>%s %s</label>' % (label_for, self.tag(), choice_label))
def is_checked(self):
return self.value == self.choice_value
@ -364,11 +368,15 @@ class CheckboxSelectMultiple(SelectMultiple):
# so that the checkboxes don't all have the same ID attribute.
if has_id:
final_attrs = dict(final_attrs, id='%s_%s' % (attrs['id'], i))
label_for = u' for="%s"' % final_attrs['id']
else:
label_for = ''
cb = CheckboxInput(final_attrs, check_test=lambda value: value in str_values)
option_value = force_unicode(option_value)
rendered_cb = cb.render(name, option_value)
output.append(u'<li><label>%s %s</label></li>' % (rendered_cb,
conditional_escape(force_unicode(option_label))))
option_label = conditional_escape(force_unicode(option_label))
output.append(u'<li><label%s>%s %s</label></li>' % (label_for, rendered_cb, option_label))
output.append(u'</ul>')
return mark_safe(u'\n'.join(output))

View File

@ -39,12 +39,11 @@ class CommentNode(Node):
class CycleNode(Node):
def __init__(self, cyclevars, variable_name=None):
self.cycle_iter = itertools_cycle(cyclevars)
self.cycle_iter = itertools_cycle([Variable(v) for v in cyclevars])
self.variable_name = variable_name
def render(self, context):
value = self.cycle_iter.next()
value = Variable(value).resolve(context)
value = self.cycle_iter.next().resolve(context)
if self.variable_name:
context[self.variable_name] = value
return value
@ -162,10 +161,12 @@ class IfChangedNode(Node):
self.nodelist = nodelist
self._last_seen = None
self._varlist = map(Variable, varlist)
self._id = str(id(self))
def render(self, context):
if 'forloop' in context and context['forloop']['first']:
if 'forloop' in context and self._id not in context['forloop']:
self._last_seen = None
context['forloop'][self._id] = 1
try:
if self._varlist:
# Consider multiple parameters. This automatically behaves
@ -452,17 +453,17 @@ def cycle(parser, token):
<tr class="{% cycle rowcolors %}">...</tr>
<tr class="{% cycle rowcolors %}">...</tr>
You can use any number of values, seperated by spaces. Commas can also
You can use any number of values, separated by spaces. Commas can also
be used to separate values; if a comma is used, the cycle values are
interpreted as literal strings.
"""
# Note: This returns the exact same node on each {% cycle name %} call;
# that is, the node object returned from {% cycle a b c as name %} and the
# one returned from {% cycle name %} are the exact same object. This
# one returned from {% cycle name %} are the exact same object. This
# shouldn't cause problems (heh), but if it does, now you know.
#
# Ugly hack warning: this stuffs the named template dict into parser so
# Ugly hack warning: This stuffs the named template dict into parser so
# that names are only unique within each template (as opposed to using
# a global variable, which would make cycle names have to be unique across
# *all* templates.
@ -481,8 +482,7 @@ def cycle(parser, token):
# {% cycle foo %} case.
name = args[1]
if not hasattr(parser, '_namedCycleNodes'):
raise TemplateSyntaxError("No named cycles in template."
" '%s' is not defined" % name)
raise TemplateSyntaxError("No named cycles in template. '%s' is not defined" % name)
if not name in parser._namedCycleNodes:
raise TemplateSyntaxError("Named cycle '%s' does not exist" % name)
return parser._namedCycleNodes[name]
@ -682,8 +682,10 @@ ifnotequal = register.tag(ifnotequal)
def do_if(parser, token):
"""
The ``{% if %}`` tag evaluates a variable, and if that variable is "true"
(i.e. exists, is not empty, and is not a false boolean value) the contents
of the block are output::
(i.e., exists, is not empty, and is not a false boolean value), the
contents of the block are output:
::
{% if athlete_list %}
Number of athletes: {{ athlete_list|count }}

View File

@ -69,10 +69,6 @@ class ExtendsNode(Node):
def render(self, context):
compiled_parent = self.get_parent(context)
pos = 0
while isinstance(compiled_parent.nodelist[pos], TextNode):
pos += 1
parent_is_child = isinstance(compiled_parent.nodelist[pos], ExtendsNode)
parent_blocks = dict([(n.name, n) for n in compiled_parent.nodelist.get_nodes_by_type(BlockNode)])
for block_node in self.nodelist.get_nodes_by_type(BlockNode):
# Check for a BlockNode with this node's name, and replace it if found.
@ -83,8 +79,16 @@ class ExtendsNode(Node):
# parent block might be defined in the parent's *parent*, so we
# add this BlockNode to the parent's ExtendsNode nodelist, so
# it'll be checked when the parent node's render() is called.
if parent_is_child:
compiled_parent.nodelist[pos].nodelist.append(block_node)
# Find out if the parent template has a parent itself
for node in compiled_parent.nodelist:
if not isinstance(node, TextNode):
# If the first non-text node is an extends, handle it.
if isinstance(node, ExtendsNode):
node.nodelist.append(block_node)
# Extends must be the first non-text node, so once you find
# the first non-text node you can stop looking.
break
else:
# Keep any existing parents and add a new one. Used by BlockNode.
parent_block.parent = block_node.parent

View File

@ -1,4 +1,4 @@
from django.template import Library, Node, TemplateSyntaxError
from django.template import Library, Node, TemplateSyntaxError, Variable, VariableDoesNotExist
from django.template import resolve_variable
from django.core.cache import cache
from django.utils.encoding import force_unicode
@ -6,20 +6,27 @@ from django.utils.encoding import force_unicode
register = Library()
class CacheNode(Node):
def __init__(self, nodelist, expire_time, fragment_name, vary_on):
def __init__(self, nodelist, expire_time_var, fragment_name, vary_on):
self.nodelist = nodelist
self.expire_time = expire_time
self.expire_time_var = Variable(expire_time_var)
self.fragment_name = fragment_name
self.vary_on = vary_on
def render(self, context):
try:
expire_time = self.expire_time_var.resolve(context)
except VariableDoesNotExist:
raise TemplateSyntaxError('"cache" tag got an unknkown variable: %r' % self.expire_time_var.var)
try:
expire_time = int(expire_time)
except (ValueError, TypeError):
raise TemplateSyntaxError('"cache" tag got a non-integer timeout value: %r' % expire_time)
# Build a unicode key for this fragment and all vary-on's.
cache_key = u':'.join([self.fragment_name] + \
[force_unicode(resolve_variable(var, context)) for var in self.vary_on])
cache_key = u':'.join([self.fragment_name] + [force_unicode(resolve_variable(var, context)) for var in self.vary_on])
value = cache.get(cache_key)
if value is None:
value = self.nodelist.render(context)
cache.set(cache_key, value, self.expire_time)
cache.set(cache_key, value, expire_time)
return value
def do_cache(parser, token):
@ -48,10 +55,6 @@ def do_cache(parser, token):
tokens = token.contents.split()
if len(tokens) < 3:
raise TemplateSyntaxError(u"'%r' tag requires at least 2 arguments." % tokens[0])
try:
expire_time = int(tokens[1])
except ValueError:
raise TemplateSyntaxError(u"First argument to '%r' must be an integer (got '%s')." % (tokens[0], tokens[1]))
return CacheNode(nodelist, expire_time, tokens[2], tokens[3:])
return CacheNode(nodelist, tokens[1], tokens[2], tokens[3:])
register.tag('cache', do_cache)

View File

@ -104,7 +104,7 @@ def patch_response_headers(response, cache_timeout=None):
if cache_timeout < 0:
cache_timeout = 0 # Can't have max-age negative
if not response.has_header('ETag'):
response['ETag'] = md5.new(response.content).hexdigest()
response['ETag'] = '"%s"' % md5.new(response.content).hexdigest()
if not response.has_header('Last-Modified'):
response['Last-Modified'] = http_date()
if not response.has_header('Expires'):

View File

@ -343,3 +343,34 @@ class FileDict(dict):
d = dict(self, content='<omitted>')
return dict.__repr__(d)
return dict.__repr__(self)
class DictWrapper(dict):
"""
Wraps accesses to a dictionary so that certain values (those starting with
the specified prefix) are passed through a function before being returned.
The prefix is removed before looking up the real value.
Used by the SQL construction code to ensure that values are correctly
quoted before being used.
"""
def __init__(self, data, func, prefix):
super(DictWrapper, self).__init__(data)
self.func = func
self.prefix = prefix
def __getitem__(self, key):
"""
Retrieves the real value after stripping the prefix string (if
present). If the prefix is present, pass the value through self.func
before returning, otherwise return the raw value.
"""
if key.startswith(self.prefix):
use_func = True
key = key[len(self.prefix):]
else:
use_func = False
value = super(DictWrapper, self).__getitem__(key)
if use_func:
return self.func(value)
return value

Some files were not shown because too many files have changed in this diff Show More