1
0
mirror of https://github.com/django/django.git synced 2025-07-04 09:49:12 +00:00

unicode: Merged from trunk up to [5121].

git-svn-id: http://code.djangoproject.com/svn/django/branches/unicode@5126 bcc190cf-cafb-0310-a4f2-bffc1f526a37
This commit is contained in:
Malcolm Tredinnick 2007-04-28 16:49:21 +00:00
parent 080cebaf69
commit 63d95548a7
62 changed files with 871 additions and 350 deletions

View File

@ -42,6 +42,7 @@ people who have submitted patches, reported bugs, added translations, helped
answer newbie questions, and generally made Django that much better:
adurdin@gmail.com
alang@bright-green.com
Daniel Alves Barbosa de Oliveira Vaz <danielvaz@gmail.com>
Andreas
andy@jadedplanet.net
@ -150,6 +151,7 @@ answer newbie questions, and generally made Django that much better:
Manuzhai
Petar Marić <http://www.petarmaric.com/>
Nuno Mariz <nmariz@gmail.com>
marijn@metronomo.cl
mark@junklight.com
Yasushi Masuda <whosaysni@gmail.com>
mattycakes@gmail.com
@ -163,6 +165,7 @@ answer newbie questions, and generally made Django that much better:
Robin Munn <http://www.geekforgod.com/>
Robert Myers <myer0052@gmail.com>
Nebojša Dorđević
Gopal Narayanan <gopastro@gmail.com>
Fraser Nevett <mail@nevett.org>
Sam Newman <http://www.magpiebrain.com/>
Neal Norwitz <nnorwitz@google.com>
@ -185,9 +188,11 @@ answer newbie questions, and generally made Django that much better:
Brian Ray <http://brianray.chipy.org/>
remco@diji.biz
rhettg@gmail.com
Henrique Romano <onaiort@gmail.com>
Armin Ronacher
Oliver Rutherfurd <http://rutherfurd.net/>
Ivan Sagalaev (Maniac) <http://www.softwaremaniacs.org/>
Vinay Sajip <vinay_sajip@yahoo.co.uk>
David Schein
scott@staplefish.com
serbaut@gmail.com
@ -211,6 +216,7 @@ answer newbie questions, and generally made Django that much better:
torne-django@wolfpuppy.org.uk
Karen Tracey <graybark@bellsouth.net>
Makoto Tsuyuki <mtsuyuki@gmail.com>
tt@gurgle.no
Amit Upadhyay
Geert Vanderkelen
viestards.lists@gmail.com

View File

@ -81,7 +81,7 @@ def make_messages():
src = pythonize_re.sub('\n#', src)
open(os.path.join(dirpath, '%s.py' % file), "wb").write(src)
thefile = '%s.py' % file
cmd = 'xgettext %s -d %s -L Perl --keyword=gettext_noop --keyword=gettext_lazy --keyword=ngettext_lazy --from-code UTF-8 -o - "%s"' % (
cmd = 'xgettext %s -d %s -L Perl --keyword=gettext_noop --keyword=gettext_lazy --keyword=ngettext_lazy:1,2 --from-code UTF-8 -o - "%s"' % (
os.path.exists(potfile) and '--omit-header' or '', domain, os.path.join(dirpath, thefile))
(stdin, stdout, stderr) = os.popen3(cmd, 'b')
msgs = stdout.read()
@ -103,7 +103,7 @@ def make_messages():
open(os.path.join(dirpath, '%s.py' % file), "wb").write(templatize(src))
thefile = '%s.py' % file
if verbose: sys.stdout.write('processing file %s in %s\n' % (file, dirpath))
cmd = 'xgettext %s -d %s -L Python --keyword=gettext_noop --keyword=gettext_lazy --keyword=ngettext_lazy --keyword=ugettext_noop --keyword=ugettext_lazy --keyword=ungettext_lazy:1,2 --from-code UTF-8 -o - "%s"' % (
cmd = 'xgettext %s -d %s -L Python --keyword=gettext_noop --keyword=gettext_lazy --keyword=ngettext_lazy:1,2 --keyword=ugettext_noop --keyword=ugettext_lazy --keyword=ungettext_lazy:1,2 --from-code UTF-8 -o - "%s"' % (
os.path.exists(potfile) and '--omit-header' or '', domain, os.path.join(dirpath, thefile))
(stdin, stdout, stderr) = os.popen3(cmd, 'b')
msgs = stdout.read()

View File

@ -22,7 +22,7 @@ def gather_stats(p):
else:
continue
print "Processing %s" % f
if profiles.has_key(path):
if path in profiles:
profiles[path].add(prof)
else:
profiles[path] = prof

View File

@ -10,7 +10,7 @@ msgstr ""
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2006-05-16 10:13+0200\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: panos laganakos <panos.laganakos@gmail.com>\n"
"Last-Translator: Orestis Markou <orestis@orestis.gr>\n"
"Language-Team: Greek\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=utf-8\n"
@ -164,9 +164,9 @@ msgid ""
"\n"
"%(text)s"
msgstr ""
"Αυτο το σχόλιο σημειώθηκε απο %(χρήστη)ες\n"
"Αυτο το σχόλιο σημειώθηκε απο %(user)s\n"
"\n"
"%(κείμενο)α"
"%(text)s"
#: contrib/comments/models.py:265
msgid "flag date"

View File

@ -1,4 +1,4 @@
# SOME DESCRIPTIVE TITLE.
# translation of django.po to
# Copyright (C) 2005 and beyond
# This file is distributed under the same license as the PACKAGE package.
# Espen Grindhaug <espen@grindhaug.org>, Nov 2005.
@ -6,74 +6,73 @@
#
msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Project-Id-Version: django\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2006-05-16 10:12+0200\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: Espen Grndhaug <espen@grindhaug.org>\n"
"Language-Team: Norwegian\n"
"PO-Revision-Date: 2007-04-27 06:48+0200\n"
"Last-Translator: \n"
"Language-Team: <en@li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=utf-8\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"X-Generator: KBabel 1.11.4\n"
#: contrib/comments/models.py:67 contrib/comments/models.py:166
#, fuzzy
msgid "object ID"
msgstr "Vis objekt ID"
msgstr "objekt ID"
#: contrib/comments/models.py:68
msgid "headline"
msgstr ""
msgstr "overskrift"
#: contrib/comments/models.py:69 contrib/comments/models.py:90
#: contrib/comments/models.py:167
#, fuzzy
msgid "comment"
msgstr "innhold"
msgstr "kommentar"
#: contrib/comments/models.py:70
msgid "rating #1"
msgstr ""
msgstr "rangering #1 "
#: contrib/comments/models.py:71
msgid "rating #2"
msgstr ""
msgstr "rangering #2"
#: contrib/comments/models.py:72
msgid "rating #3"
msgstr ""
msgstr "rangering #3"
#: contrib/comments/models.py:73
msgid "rating #4"
msgstr ""
msgstr "rangering #4"
#: contrib/comments/models.py:74
msgid "rating #5"
msgstr ""
msgstr "rangering #5"
#: contrib/comments/models.py:75
msgid "rating #6"
msgstr ""
msgstr "rangering #6"
#: contrib/comments/models.py:76
msgid "rating #7"
msgstr ""
msgstr "rangering #7"
#: contrib/comments/models.py:77
msgid "rating #8"
msgstr ""
msgstr "rangering #8"
#: contrib/comments/models.py:82
msgid "is valid rating"
msgstr ""
msgstr "er gyldig rangering"
#: contrib/comments/models.py:83 contrib/comments/models.py:169
msgid "date/time submitted"
msgstr ""
msgstr "dato/tid for innsendelse"
#: contrib/comments/models.py:84 contrib/comments/models.py:170
msgid "is public"
msgstr ""
msgstr "er tilgjengelig for alle"
#: contrib/comments/models.py:85 contrib/admin/views/doc.py:289
msgid "IP address"
@ -81,23 +80,21 @@ msgstr "IP adresse"
#: contrib/comments/models.py:86
msgid "is removed"
msgstr ""
msgstr "er fjernet"
#: contrib/comments/models.py:86
msgid ""
"Check this box if the comment is inappropriate. A \"This comment has been "
"removed\" message will be displayed instead."
msgstr ""
msgstr "Aktiver denne avkryssningsboksen hvis kommentaren er upasende. Beskjeden \"Denne kommentaren er blitt fjernet\" vil bli vist istedet."
#: contrib/comments/models.py:91
#, fuzzy
msgid "comments"
msgstr "innhold"
msgstr "kommentarer"
#: contrib/comments/models.py:131 contrib/comments/models.py:207
#, fuzzy
msgid "Content object"
msgstr "innholds type"
msgstr "innholdsobjekt"
#: contrib/comments/models.py:159
#, python-format
@ -108,101 +105,97 @@ msgid ""
"\n"
"http://%(domain)s%(url)s"
msgstr ""
"Sendt av %(user)s på %(date)s\n"
"\n"
"%(comment)s\n"
"\n"
"http://%(domain)s%(url)s"
#: contrib/comments/models.py:168
#, fuzzy
msgid "person's name"
msgstr "fornavn"
msgstr "personens navn"
#: contrib/comments/models.py:171
#, fuzzy
msgid "ip address"
msgstr "IP adresse"
#: contrib/comments/models.py:173
msgid "approved by staff"
msgstr ""
msgstr "godkjent av moderator"
#: contrib/comments/models.py:176
#, fuzzy
msgid "free comment"
msgstr "tillat kommentarer"
msgstr "åpen kommentar"
#: contrib/comments/models.py:177
#, fuzzy
msgid "free comments"
msgstr "tillat kommentarer"
msgstr "åpne kommentarer"
#: contrib/comments/models.py:233
msgid "score"
msgstr ""
msgstr "poeng"
#: contrib/comments/models.py:234
#, fuzzy
msgid "score date"
msgstr "utløpsdato"
msgstr "poeng dato"
#: contrib/comments/models.py:237
msgid "karma score"
msgstr ""
msgstr "karma poeng"
#: contrib/comments/models.py:238
msgid "karma scores"
msgstr ""
msgstr "karma poeng"
#: contrib/comments/models.py:242
#, python-format
msgid "%(score)d rating by %(user)s"
msgstr ""
msgstr "%(score)d rangering av %(user)s"
#: contrib/comments/models.py:258
#, fuzzy, python-format
#, python-format
msgid ""
"This comment was flagged by %(user)s:\n"
"\n"
"%(text)s"
msgstr ""
"Denne kommentaren er skrevet med lite omtanke:\n"
"Denne kommentaren er flagget av %(user)s:\n"
"\n"
"%(text)s"
#: contrib/comments/models.py:265
#, fuzzy
msgid "flag date"
msgstr "flatside"
msgstr "flagg dato"
#: contrib/comments/models.py:268
#, fuzzy
msgid "user flag"
msgstr "Bruker"
msgstr "brukerflag"
#: contrib/comments/models.py:269
#, fuzzy
msgid "user flags"
msgstr "Brukere"
msgstr "brukerflag"
#: contrib/comments/models.py:273
#, python-format
msgid "Flag by %r"
msgstr ""
msgstr "Flagg med %r"
#: contrib/comments/models.py:278
#, fuzzy
msgid "deletion date"
msgstr "sesjon data"
msgstr "fjernet dato"
#: contrib/comments/models.py:280
msgid "moderator deletion"
msgstr ""
msgstr "fjernet av moderator"
#: contrib/comments/models.py:281
msgid "moderator deletions"
msgstr ""
msgstr "fjernet av moderator"
#: contrib/comments/models.py:285
#, python-format
msgid "Moderator deletion by %r"
msgstr ""
msgstr "Fjernet av moderator med %r"
#: contrib/comments/views/karma.py:19
msgid "Anonymous users cannot vote"
@ -214,16 +207,14 @@ msgstr "Ikke gyldig kommentar ID"
#: contrib/comments/views/karma.py:25
msgid "No voting for yourself"
msgstr "Du kan ikke stemme selv"
msgstr "Du kan ikke stemme på deg selv"
#: contrib/comments/views/comments.py:28
#, fuzzy
msgid ""
"This rating is required because you've entered at least one other rating."
msgstr "Denne bla bla.."
msgid "This rating is required because you've entered at least one other rating."
msgstr "Denne rangeringen er påkrevd fordi du har rangert en eller flere ting fra før "
#: contrib/comments/views/comments.py:112
#, fuzzy, python-format
#, python-format
msgid ""
"This comment was posted by a user who has posted fewer than %(count)s "
"comment:\n"
@ -246,13 +237,13 @@ msgstr[1] ""
"%(text)s"
#: contrib/comments/views/comments.py:117
#, fuzzy, python-format
#, python-format
msgid ""
"This comment was posted by a sketchy user:\n"
"\n"
"%(text)s"
msgstr ""
"Denne kommentaren er skrevet med lite omtanke:\n"
"Denne kommentaren er skrevet av en upålitelig bruker:\n"
"\n"
"%(text)s"
@ -281,8 +272,7 @@ msgstr "Skjemaet hadde en ugyldig verdi - objekt IDen var ugyldig"
#: contrib/comments/views/comments.py:257
#: contrib/comments/views/comments.py:321
msgid "The comment form didn't provide either 'preview' or 'post'"
msgstr ""
"Kommentar skjemaet returnerte ikke et 'forhåndsvisning' eller 'post' objekt"
msgstr "Kommentar skjemaet returnerte ikke et 'forhåndsvisning' eller 'post' objekt"
#: contrib/comments/templates/comments/form.html:6
#: contrib/comments/templates/comments/form.html:8
@ -296,9 +286,8 @@ msgid "Password:"
msgstr "Passord:"
#: contrib/comments/templates/comments/form.html:6
#, fuzzy
msgid "Forgotten your password?"
msgstr "Endre passord"
msgstr "Har du glemt passordet ditt ?"
#: contrib/comments/templates/comments/form.html:8
#: contrib/admin/templates/admin/object_history.html:3
@ -323,38 +312,35 @@ msgstr "Log ut"
#: contrib/comments/templates/comments/form.html:12
msgid "Ratings"
msgstr ""
msgstr "Rangeringer"
#: contrib/comments/templates/comments/form.html:12
#: contrib/comments/templates/comments/form.html:23
msgid "Required"
msgstr ""
msgstr "Påkrevd"
#: contrib/comments/templates/comments/form.html:12
#: contrib/comments/templates/comments/form.html:23
msgid "Optional"
msgstr ""
msgstr "Valgfri"
#: contrib/comments/templates/comments/form.html:23
msgid "Post a photo"
msgstr ""
msgstr "Send et foto"
#: contrib/comments/templates/comments/form.html:27
#: contrib/comments/templates/comments/freeform.html:5
#, fuzzy
msgid "Comment:"
msgstr "tillat kommentarer"
msgstr "Kommentar:"
#: contrib/comments/templates/comments/form.html:32
#: contrib/comments/templates/comments/freeform.html:9
#, fuzzy
msgid "Preview comment"
msgstr "tillat kommentarer"
msgstr "Forhåndvis kommentar"
#: contrib/comments/templates/comments/freeform.html:4
#, fuzzy
msgid "Your name:"
msgstr "brukernavn"
msgstr "Ditt navn:"
#: contrib/admin/filterspecs.py:40
#, python-format
@ -416,7 +402,7 @@ msgstr "objekt repr"
#: contrib/admin/models.py:21
msgid "action flag"
msgstr "handlings flagg"
msgstr "handlingsflagg"
#: contrib/admin/models.py:22
msgid "change message"
@ -424,11 +410,11 @@ msgstr "endre melding"
#: contrib/admin/models.py:25
msgid "log entry"
msgstr "logg notis"
msgstr "logg post"
#: contrib/admin/models.py:26
msgid "log entries"
msgstr "logg innlegg"
msgstr "logg poster"
#: contrib/admin/templatetags/admin_list.py:228
msgid "All dates"
@ -440,8 +426,8 @@ msgid ""
"Please enter a correct username and password. Note that both fields are case-"
"sensitive."
msgstr ""
"Vær snill å angi korrekt brukernavn og passord. La merke til at små og "
"store bokstaver er betraktet ulik."
"Vennligst angi korrekt brukernavn og passord. Merk at små og "
"store bokstaver er betraktet ulikt."
#: contrib/admin/views/decorators.py:23
#: contrib/admin/templates/admin/login.html:25
@ -452,18 +438,15 @@ msgstr "Logg inn"
msgid ""
"Please log in again, because your session has expired. Don't worry: Your "
"submission has been saved."
msgstr ""
"Du må logge inn igjen, fordi sesjonen din har gått ut på dato, men ikke ikke "
"bekjymr deg informasjonen du sendte ble lagret."
msgstr "Du må logge inn igjen, fordi økten din har gått ut, men innlegget ditt ble lagret."
#: contrib/admin/views/decorators.py:68
msgid ""
"Looks like your browser isn't configured to accept cookies. Please enable "
"cookies, reload this page, and try again."
msgstr ""
"Det ser ut som om nettleseren din ikke vill ta i mot informasjonskapsler "
"('cookies'). Vennligst omkonfigurer nettleseren din, last siden på ny og "
"prøv igjen."
"Det ser ut som om nettleseren din ikke støtter informasjonskapsler "
"('cookies'). Vennligst konfigurer nettleseren din, og prøv igjen."
#: contrib/admin/views/decorators.py:82
msgid "Usernames cannot contain the '@' character."
@ -500,7 +483,7 @@ msgstr "Ny %s"
#: contrib/admin/views/main.py:336
#, python-format
msgid "Added %s."
msgstr "Lagt til %s"
msgstr "La til %s"
#: contrib/admin/views/main.py:336 contrib/admin/views/main.py:338
#: contrib/admin/views/main.py:340
@ -528,8 +511,7 @@ msgstr "%(name)s \"%(obj)s\" ble endret."
#: contrib/admin/views/main.py:354
#, python-format
msgid ""
"The %(name)s \"%(obj)s\" was added successfully. You may edit it again below."
msgid "The %(name)s \"%(obj)s\" was added successfully. You may edit it again below."
msgstr "%(name)s \"%(obj)s\" ble endret. Du kan endre det igjen under."
#: contrib/admin/views/main.py:392
@ -742,8 +724,8 @@ msgid ""
"There's been an error. It's been reported to the site administrators via e-"
"mail and should be fixed shortly. Thanks for your patience."
msgstr ""
"Det har vært en feil. Feilen er blitt rapportert til administrator via e-"
"mail, og vill bli fikset snart. Takk for din tålmodighet."
"Det har oppstått en feil. Feilen er blitt rapportert til administrator via e-"
"post, og vil bli fikset snart. Takk for din tålmodighet."
#: contrib/admin/templates/admin/404.html:4
#: contrib/admin/templates/admin/404.html:8
@ -909,7 +891,7 @@ msgstr "Tilbakestill mitt passord"
#: contrib/admin/templates/registration/logged_out.html:8
msgid "Thanks for spending some quality time with the Web site today."
msgstr "Takk for å bruke tid på internett siden i dag."
msgstr "Takk for at du valgte å bruke kvalitetstid på nettstedet idag."
#: contrib/admin/templates/registration/logged_out.html:10
msgid "Log in again"
@ -954,8 +936,7 @@ msgstr "Endre passord"
#: contrib/admin/templates/registration/password_reset_email.html:2
msgid "You're receiving this e-mail because you requested a password reset"
msgstr ""
"Du har mottatt denne e-posten fordi du ba om å tilbakestille passordet ditt"
msgstr "Du har mottatt denne e-posten fordi du ba om å tilbakestille passordet ditt"
#: contrib/admin/templates/registration/password_reset_email.html:3
#, python-format
@ -1002,6 +983,12 @@ msgid ""
"as \"internal\" (talk to your system administrator if you aren't sure if\n"
"your computer is \"internal\").</p>\n"
msgstr ""
"\n"
"<p class=\"help\">For å installere bokmerker, dra linken til verktøylinja\n"
"for bokmerker, eller høyreklikk og legg til i bokmerker. Nå kan du du velge\n"
"bokmerket fra hvilken som helst side på nettstedet. Noen av disse\n"
"bokmerkene krever at datamaskinen du bruker er markert som \"intern\"\n"
"(kontakt din systemadministrator hvis du er usikker på om maskinen din er \"intern\").</p>\n"
#: contrib/admin/templates/admin_doc/bookmarklets.html:19
msgid "Documentation for this page"
@ -1033,8 +1020,7 @@ msgstr "Endre dette objektet (åpnes i dette vinduet)"
#: contrib/admin/templates/admin_doc/bookmarklets.html:26
msgid "Jumps to the admin page for pages that represent a single object."
msgstr ""
"Hopp til administrasjonsiden for sidene som representerer et enkelt objekt."
msgstr "Hopp til administrasjonsiden for sidene som representerer et enkelt objekt."
#: contrib/admin/templates/admin_doc/bookmarklets.html:28
msgid "Edit this object (new window)"
@ -1069,7 +1055,7 @@ msgid ""
"This should be an absolute path, excluding the domain name. Example: '/"
"events/search/'."
msgstr ""
"Denne burde vær en fullstendig sti, uten domene navnet. Foreksempel: '/"
"Dette burde vært en fullstendig sti, uten domene navnet. Foreksempel: '/"
"nyheter/les/"
#: contrib/redirects/models.py:9
@ -1081,7 +1067,7 @@ msgid ""
"This can be either an absolute path (as above) or a full URL starting with "
"'http://'."
msgstr ""
"Denne kan enten være en fullstendig sti (som over), eller en hel "
"Dette kan enten være en fullstendig sti (som over), eller en hel "
"internettadresse som starter med 'http://'"
#: contrib/redirects/models.py:12
@ -1093,10 +1079,8 @@ msgid "redirects"
msgstr "omadresserelser"
#: contrib/flatpages/models.py:8
msgid ""
"Example: '/about/contact/'. Make sure to have leading and trailing slashes."
msgstr ""
"Eksempel: '/om/kontakt/'. Vær sikker på at du har en skråstrek forran og bak."
msgid "Example: '/about/contact/'. Make sure to have leading and trailing slashes."
msgstr "Eksempel: '/om/kontakt/'. Vær sikker på at du har en skråstrek forran og bak."
#: contrib/flatpages/models.py:9
msgid "title"
@ -1186,7 +1170,7 @@ msgstr "passord"
#: contrib/auth/models.py:59
msgid "Use '[algo]$[salt]$[hexdigest]'"
msgstr ""
msgstr "Bruk '[algo]$[salt]$[hexdigest]'"
#: contrib/auth/models.py:60
msgid "staff status"
@ -1256,7 +1240,7 @@ msgstr "Melding"
msgid ""
"Your Web browser doesn't appear to have cookies enabled. Cookies are "
"required for logging in."
msgstr ""
msgstr "Din nettleser ser ikkeut til å støtte informasjonskapsler (cookies). Informasjonskapsler er påkrevd for å logge inn."
#: contrib/contenttypes/models.py:25
msgid "python model class name"
@ -1698,8 +1682,7 @@ msgstr "Internettadressen %s peker ikke til et godkjent bilde."
#: core/validators.py:159
#, python-format
msgid "Phone numbers must be in XXX-XXX-XXXX format. \"%s\" is invalid."
msgstr ""
"Telefon nummeret må være i XXX-XXX-XXXX format. \"%s\" er ikke godkjent."
msgstr "Telefon nummeret må være i XXX-XXX-XXXX format. \"%s\" er ikke godkjent."
#: core/validators.py:167
#, python-format
@ -1784,30 +1767,26 @@ msgstr "Vennligst skriv inn et godkjent desimal tall."
#: core/validators.py:349
#, python-format
msgid "Please enter a valid decimal number with at most %s total digit."
msgid_plural ""
"Please enter a valid decimal number with at most %s total digits."
msgid_plural "Please enter a valid decimal number with at most %s total digits."
msgstr[0] "Skriv inn et desimal tall med maksimum %s total antall tall."
msgstr[1] "Skriv inn et desimal tall med maksimum %s total antall tall."
#: core/validators.py:352
#, python-format
msgid "Please enter a valid decimal number with at most %s decimal place."
msgid_plural ""
"Please enter a valid decimal number with at most %s decimal places."
msgid_plural "Please enter a valid decimal number with at most %s decimal places."
msgstr[0] "Skriv inn et desimal tall med maksimum %s tall bak komma. "
msgstr[1] "Skriv inn et desimal tall med maksimum %s tall bak komma. "
#: core/validators.py:362
#, python-format
msgid "Make sure your uploaded file is at least %s bytes big."
msgstr ""
"Vær sikker på at fila du prøver å laste opp er minimum %s bytes stor."
msgstr "Vær sikker på at fila du prøver å laste opp er minimum %s bytes stor."
#: core/validators.py:363
#, python-format
msgid "Make sure your uploaded file is at most %s bytes big."
msgstr ""
"Vær sikker på at fila du prøver å laste opp er maksimum %s bytes stor."
msgstr "Vær sikker på at fila du prøver å laste opp er maksimum %s bytes stor."
#: core/validators.py:376
msgid "The format for this field is wrong."
@ -1824,8 +1803,7 @@ msgstr "Klarte ikke å motta noe fra %s."
#: core/validators.py:429
#, python-format
msgid ""
"The URL %(url)s returned the invalid Content-Type header '%(contenttype)s'."
msgid "The URL %(url)s returned the invalid Content-Type header '%(contenttype)s'."
msgstr ""
"Internettadressen %(url)s returnerte en ikke godkjent Content-Type '%"
"(contenttype)s'."
@ -1926,16 +1904,13 @@ msgid "Separate multiple IDs with commas."
msgstr "Separer Id-ene med kommaer."
#: db/models/fields/related.py:581
msgid ""
"Hold down \"Control\", or \"Command\" on a Mac, to select more than one."
msgstr ""
"Hold nede \"Control\", eller \"Command\" på en Mac, for å velge mere enn en."
msgid "Hold down \"Control\", or \"Command\" on a Mac, to select more than one."
msgstr "Hold nede \"Control\", eller \"Command\" på en Mac, for å velge mere enn en."
#: db/models/fields/related.py:625
#, python-format
msgid "Please enter valid %(self)s IDs. The value %(value)r is invalid."
msgid_plural ""
"Please enter valid %(self)s IDs. The values %(value)r are invalid."
msgid_plural "Please enter valid %(self)s IDs. The values %(value)r are invalid."
msgstr[0] "Skriv inn gyldige %(self)s ID-er. Verdien %(value)r er ikke gyldig."
msgstr[1] "Skriv inn gyldige %(self)s ID-er. Verdiene %(value)r er ikke gyldige."

View File

@ -1,19 +1,20 @@
# SOME DESCRIPTIVE TITLE.
# translation of djangojs.po to
# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER
# This file is distributed under the same license as the PACKAGE package.
# Espen Grindhaug <espen.grindhaug@mail.com>, 2006.
#
msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Project-Id-Version: djangojs\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2005-12-09 11:51+0100\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: Espen Grindhaug <espen.grindhaug@gmail.com>\n"
"Language-Team: no\n"
"PO-Revision-Date: 2007-04-27 06:51+0200\n"
"Last-Translator: \n"
"Language-Team: <en@li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=utf-8\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"X-Generator: KBabel 1.11.4\n"
#: contrib/admin/media/js/SelectFilter2.js:33
#, perl-format
@ -21,7 +22,6 @@ msgid "Available %s"
msgstr "%s er tilgjengelige"
#: contrib/admin/media/js/SelectFilter2.js:41
#, fuzzy
msgid "Choose all"
msgstr "Velg alle"
@ -116,3 +116,4 @@ msgstr "I går"
#: contrib/admin/media/js/admin/DateTimeShortcuts.js:164
msgid "Tomorrow"
msgstr "I morgen"

View File

@ -11,9 +11,10 @@ def patterns(prefix, *args):
pattern_list = []
for t in args:
if isinstance(t, (list, tuple)):
pattern_list.append(url(prefix=prefix, *t))
else:
pattern_list.append(t)
t = url(prefix=prefix, *t)
elif isinstance(t, RegexURLPattern):
t.add_prefix(prefix)
pattern_list.append(t)
return pattern_list
def url(regex, view, kwargs=None, name=None, prefix=''):

View File

@ -74,7 +74,7 @@ class FieldWidgetNode(template.Node):
self.bound_field_var = bound_field_var
def get_nodelist(cls, klass):
if not cls.nodelists.has_key(klass):
if klass not in cls.nodelists:
try:
field_class_name = klass.__name__
template_name = "widget/%s.html" % class_name_to_underscored(field_class_name)

View File

@ -17,7 +17,7 @@ def user_add_stage(request):
if not errors:
new_user = manipulator.save(new_data)
msg = _('The %(name)s "%(obj)s" was added successfully.') % {'name': 'user', 'obj': new_user}
if request.POST.has_key("_addanother"):
if "_addanother" in request.POST:
request.user.message_set.create(message=msg)
return HttpResponseRedirect(request.path)
else:
@ -29,7 +29,7 @@ def user_add_stage(request):
return render_to_response('admin/auth/user/add_form.html', {
'title': _('Add user'),
'form': form,
'is_popup': request.REQUEST.has_key('_popup'),
'is_popup': '_popup' in request.REQUEST,
'add': True,
'change': False,
'has_delete_permission': False,
@ -63,7 +63,7 @@ def user_change_password(request, id):
return render_to_response('admin/auth/user/change_password.html', {
'title': _('Change password: %s') % escape(user.username),
'form': form,
'is_popup': request.REQUEST.has_key('_popup'),
'is_popup': '_popup' in request.REQUEST,
'add': True,
'change': False,
'has_delete_permission': False,

View File

@ -12,7 +12,7 @@ LOGIN_FORM_KEY = 'this_is_the_login_form'
def _display_login_form(request, error_message=''):
request.session.set_test_cookie()
if request.POST and request.POST.has_key('post_data'):
if request.POST and 'post_data' in request.POST:
# User has failed login BUT has previously saved post data.
post_data = request.POST['post_data']
elif request.POST:
@ -48,7 +48,7 @@ def staff_member_required(view_func):
def _checklogin(request, *args, **kwargs):
if request.user.is_authenticated() and request.user.is_staff:
# The user is valid. Continue to the admin page.
if request.POST.has_key('post_data'):
if 'post_data' in request.POST:
# User must have re-authenticated through a different window
# or tab.
request.POST = _decode_post_data(request.POST['post_data'])
@ -57,7 +57,7 @@ def staff_member_required(view_func):
assert hasattr(request, 'session'), "The Django admin requires session middleware to be installed. Edit your MIDDLEWARE_CLASSES setting to insert 'django.contrib.sessions.middleware.SessionMiddleware'."
# If this isn't already the login page, display it.
if not request.POST.has_key(LOGIN_FORM_KEY):
if LOGIN_FORM_KEY not in request.POST:
if request.POST:
message = _("Please log in again, because your session has expired. Don't worry: Your submission has been saved.")
else:
@ -90,9 +90,9 @@ def staff_member_required(view_func):
if user.is_active and user.is_staff:
login(request, user)
# TODO: set last_login with an event.
if request.POST.has_key('post_data'):
if 'post_data' in request.POST:
post_data = _decode_post_data(request.POST['post_data'])
if post_data and not post_data.has_key(LOGIN_FORM_KEY):
if post_data and LOGIN_FORM_KEY not in post_data:
# overwrite request.POST with the saved post_data, and continue
request.POST = post_data
request.user = user

View File

@ -257,17 +257,17 @@ def add_stage(request, app_label, model_name, show_delete=False, form_url='', po
msg = _('The %(name)s "%(obj)s" was added successfully.') % {'name': opts.verbose_name, 'obj': new_object}
# Here, we distinguish between different save types by checking for
# the presence of keys in request.POST.
if request.POST.has_key("_continue"):
if "_continue" in request.POST:
request.user.message_set.create(message=msg + ' ' + _("You may edit it again below."))
if request.POST.has_key("_popup"):
if "_popup" in request.POST:
post_url_continue += "?_popup=1"
return HttpResponseRedirect(post_url_continue % pk_value)
if request.POST.has_key("_popup"):
if "_popup" in request.POST:
if type(pk_value) is str: # Quote if string, so JavaScript doesn't think it's a variable.
pk_value = '"%s"' % pk_value.replace('"', '\\"')
return HttpResponse('<script type="text/javascript">opener.dismissAddAnotherPopup(window, %s, "%s");</script>' % \
(pk_value, str(new_object).replace('"', '\\"')))
elif request.POST.has_key("_addanother"):
elif "_addanother" in request.POST:
request.user.message_set.create(message=msg + ' ' + (_("You may add another %s below.") % opts.verbose_name))
return HttpResponseRedirect(request.path)
else:
@ -288,7 +288,7 @@ def add_stage(request, app_label, model_name, show_delete=False, form_url='', po
c = template.RequestContext(request, {
'title': _('Add %s') % opts.verbose_name,
'form': form,
'is_popup': request.REQUEST.has_key('_popup'),
'is_popup': '_popup' in request.REQUEST,
'show_delete': show_delete,
})
@ -308,7 +308,7 @@ def change_stage(request, app_label, model_name, object_id):
if not request.user.has_perm(app_label + '.' + opts.get_change_permission()):
raise PermissionDenied
if request.POST and request.POST.has_key("_saveasnew"):
if request.POST and "_saveasnew" in request.POST:
return add_stage(request, app_label, model_name, form_url='../../add/')
try:
@ -343,16 +343,16 @@ def change_stage(request, app_label, model_name, object_id):
LogEntry.objects.log_action(request.user.id, ContentType.objects.get_for_model(model).id, pk_value, str(new_object), CHANGE, change_message)
msg = _('The %(name)s "%(obj)s" was changed successfully.') % {'name': opts.verbose_name, 'obj': new_object}
if request.POST.has_key("_continue"):
if "_continue" in request.POST:
request.user.message_set.create(message=msg + ' ' + _("You may edit it again below."))
if request.REQUEST.has_key('_popup'):
if '_popup' in request.REQUEST:
return HttpResponseRedirect(request.path + "?_popup=1")
else:
return HttpResponseRedirect(request.path)
elif request.POST.has_key("_saveasnew"):
elif "_saveasnew" in request.POST:
request.user.message_set.create(message=_('The %(name)s "%(obj)s" was added successfully. You may edit it again below.') % {'name': opts.verbose_name, 'obj': new_object})
return HttpResponseRedirect("../%s/" % pk_value)
elif request.POST.has_key("_addanother"):
elif "_addanother" in request.POST:
request.user.message_set.create(message=msg + ' ' + (_("You may add another %s below.") % opts.verbose_name))
return HttpResponseRedirect("../add/")
else:
@ -392,7 +392,7 @@ def change_stage(request, app_label, model_name, object_id):
'form': form,
'object_id': object_id,
'original': manipulator.original_object,
'is_popup': request.REQUEST.has_key('_popup'),
'is_popup': '_popup' in request.REQUEST,
})
return render_change_form(model, manipulator, c, change=True)
change_stage = staff_member_required(never_cache(change_stage))
@ -558,12 +558,12 @@ class ChangeList(object):
self.page_num = int(request.GET.get(PAGE_VAR, 0))
except ValueError:
self.page_num = 0
self.show_all = request.GET.has_key(ALL_VAR)
self.is_popup = request.GET.has_key(IS_POPUP_VAR)
self.show_all = ALL_VAR in request.GET
self.is_popup = IS_POPUP_VAR in request.GET
self.params = dict(request.GET.items())
if self.params.has_key(PAGE_VAR):
if PAGE_VAR in self.params:
del self.params[PAGE_VAR]
if self.params.has_key(ERROR_FLAG):
if ERROR_FLAG in self.params:
del self.params[ERROR_FLAG]
self.order_field, self.order_type = self.get_ordering()
@ -594,7 +594,7 @@ class ChangeList(object):
if k.startswith(r):
del p[k]
for k, v in new_params.items():
if p.has_key(k) and v is None:
if k in p and v is None:
del p[k]
elif v is not None:
p[k] = v
@ -656,7 +656,7 @@ class ChangeList(object):
order_field, order_type = ordering[0][1:], 'desc'
else:
order_field, order_type = ordering[0], 'asc'
if params.has_key(ORDER_VAR):
if ORDER_VAR in params:
try:
field_name = lookup_opts.admin.list_display[int(params[ORDER_VAR])]
try:
@ -674,7 +674,7 @@ class ChangeList(object):
order_field = f.name
except (IndexError, ValueError):
pass # Invalid ordering specified. Just use the default.
if params.has_key(ORDER_TYPE_VAR) and params[ORDER_TYPE_VAR] in ('asc', 'desc'):
if ORDER_TYPE_VAR in params and params[ORDER_TYPE_VAR] in ('asc', 'desc'):
order_type = params[ORDER_TYPE_VAR]
return order_field, order_type
@ -682,7 +682,7 @@ class ChangeList(object):
qs = self.manager.get_query_set()
lookup_params = self.params.copy() # a dictionary of the query string
for i in (ALL_VAR, ORDER_VAR, ORDER_TYPE_VAR, SEARCH_VAR, IS_POPUP_VAR):
if lookup_params.has_key(i):
if i in lookup_params:
del lookup_params[i]
# Apply lookup parameters from the query string.

View File

@ -116,7 +116,7 @@ class CommentListNode(template.Node):
comment_list = get_list_function(**kwargs).order_by(self.ordering + 'submit_date').select_related()
if not self.free:
if context.has_key('user') and context['user'].is_authenticated():
if 'user' in context and context['user'].is_authenticated():
user_id = context['user'].id
context['user_can_moderate_comments'] = Comment.objects.user_is_moderator(context['user'])
else:

View File

@ -217,10 +217,10 @@ def post_comment(request):
errors = manipulator.get_validation_errors(new_data)
# If user gave correct username/password and wasn't already logged in, log them in
# so they don't have to enter a username/password again.
if manipulator.get_user() and not manipulator.get_user().is_authenticated() and new_data.has_key('password') and manipulator.get_user().check_password(new_data['password']):
if manipulator.get_user() and not manipulator.get_user().is_authenticated() and 'password' in new_data and manipulator.get_user().check_password(new_data['password']):
from django.contrib.auth import login
login(request, manipulator.get_user())
if errors or request.POST.has_key('preview'):
if errors or 'preview' in request.POST:
class CommentFormWrapper(oldforms.FormWrapper):
def __init__(self, manipulator, new_data, errors, rating_choices):
oldforms.FormWrapper.__init__(self, manipulator, new_data, errors)
@ -244,7 +244,7 @@ def post_comment(request):
'rating_range': rating_range,
'rating_choices': rating_choices,
}, context_instance=RequestContext(request))
elif request.POST.has_key('post'):
elif 'post' in request.POST:
# If the IP is banned, mail the admins, do NOT save the comment, and
# serve up the "Thanks for posting" page as if the comment WAS posted.
if request.META['REMOTE_ADDR'] in settings.BANNED_IPS:
@ -298,7 +298,7 @@ def post_free_comment(request):
new_data['is_public'] = IS_PUBLIC in option_list
manipulator = PublicFreeCommentManipulator()
errors = manipulator.get_validation_errors(new_data)
if errors or request.POST.has_key('preview'):
if errors or 'preview' in request.POST:
comment = errors and '' or manipulator.get_comment(new_data)
return render_to_response('comments/free_preview.html', {
'comment': comment,
@ -307,7 +307,7 @@ def post_free_comment(request):
'target': target,
'hash': security_hash,
}, context_instance=RequestContext(request))
elif request.POST.has_key('post'):
elif 'post' in request.POST:
# If the IP is banned, mail the admins, do NOT save the comment, and
# serve up the "Thanks for posting" page as if the comment WAS posted.
if request.META['REMOTE_ADDR'] in settings.BANNED_IPS:
@ -330,7 +330,7 @@ def comment_was_posted(request):
The object the comment was posted on
"""
obj = None
if request.GET.has_key('c'):
if 'c' in request.GET:
content_type_id, object_id = request.GET['c'].split(':')
try:
content_type = ContentType.objects.get(pk=content_type_id)

View File

@ -4,7 +4,7 @@ BR-specific Form helpers
"""
from django.newforms import ValidationError
from django.newforms.fields import Field, RegexField, Select, EMPTY_VALUES
from django.newforms.fields import Field, RegexField, CharField, Select, EMPTY_VALUES
from django.utils.encoding import smart_unicode
from django.utils.translation import gettext
import re
@ -15,7 +15,7 @@ class BRZipCodeField(RegexField):
def __init__(self, *args, **kwargs):
super(BRZipCodeField, self).__init__(r'^\d{5}-\d{3}$',
max_length=None, min_length=None,
error_message=gettext(u'Enter a zip code in the format XXXXX-XXX.'),
error_message=gettext('Enter a zip code in the format XXXXX-XXX.'),
*args, **kwargs)
class BRPhoneNumberField(Field):
@ -31,9 +31,89 @@ class BRPhoneNumberField(Field):
class BRStateSelect(Select):
"""
A Select widget that uses a list of brazilian states/territories
A Select widget that uses a list of Brazilian states/territories
as its choices.
"""
def __init__(self, attrs=None):
from br_states import STATE_CHOICES # relative import
super(BRStateSelect, self).__init__(attrs, choices=STATE_CHOICES)
def DV_maker(v):
if v >= 2:
return 11 - v
return 0
class BRCPFField(CharField):
"""
This field validate a CPF number or a CPF string. A CPF number is
compounded by XXX.XXX.XXX-VD. The two last digits are check digits.
More information:
http://en.wikipedia.org/wiki/Cadastro_de_Pessoas_F%C3%ADsicas
"""
def __init__(self, *args, **kwargs):
super(BRCPFField, self).__init__(max_length=14, min_length=11, *args, **kwargs)
def clean(self, value):
"""
Value can be either a string in the format XXX.XXX.XXX-XX or an
11-digit number.
"""
value = super(BRCPFField, self).clean(value)
if value in EMPTY_VALUES:
return u''
orig_value = value[:]
if not value.isdigit():
value = re.sub("[-\.]", "", value)
try:
int(value)
except ValueError:
raise ValidationError(gettext("This field requires only numbers."))
if len(value) != 11:
raise ValidationError(gettext("This field requires at most 11 digits or 14 characters."))
orig_dv = value[-2:]
new_1dv = sum([i * int(value[idx]) for idx, i in enumerate(range(10, 1, -1))])
new_1dv = DV_maker(new_1dv % 11)
value = value[:-2] + str(new_1dv) + value[-1]
new_2dv = sum([i * int(value[idx]) for idx, i in enumerate(range(11, 1, -1))])
new_2dv = DV_maker(new_2dv % 11)
value = value[:-1] + str(new_2dv)
if value[-2:] != orig_dv:
raise ValidationError(gettext("Invalid CPF number."))
return orig_value
class BRCNPJField(Field):
def clean(self, value):
"""
Value can be either a string in the format XX.XXX.XXX/XXXX-XX or a
group of 14 characters.
"""
value = super(BRCNPJField, self).clean(value)
if value in EMPTY_VALUES:
return u''
orig_value = value[:]
if not value.isdigit():
value = re.sub("[-/\.]", "", value)
try:
int(value)
except ValueError:
raise ValidationError("This field requires only numbers.")
if len(value) != 14:
raise ValidationError(
gettext("This field requires at least 14 digits"))
orig_dv = value[-2:]
new_1dv = sum([i * int(value[idx]) for idx, i in enumerate(range(5, 1, -1) + range(9, 1, -1))])
new_1dv = DV_maker(new_1dv % 11)
value = value[:-2] + str(new_1dv) + value[-1]
new_2dv = sum([i * int(value[idx]) for idx, i in enumerate(range(6, 1, -1) + range(9, 1, -1))])
new_2dv = DV_maker(new_2dv % 11)
value = value[:-1] + str(new_2dv)
if value[-2:] != orig_dv:
raise ValidationError(gettext("Invalid CNPJ number."))
return orig_value

View File

@ -0,0 +1,78 @@
"""
Chile specific form helpers.
"""
from django.newforms import ValidationError
from django.newforms.fields import RegexField, EMPTY_VALUES
from django.utils.translation import gettext
class CLRutField(RegexField):
"""
Chilean "Rol Unico Tributario" (RUT) field. This is the Chilean national
identification number.
Samples for testing are available from
https://palena.sii.cl/cvc/dte/ee_empresas_emisoras.html
"""
def __init__(self, *args, **kwargs):
if 'strict' in kwargs:
del kwargs['strict']
super(CLRutField, self).__init__(r'^(\d{1,2}\.)?\d{3}\.\d{3}-[\dkK]$',
error_message=gettext('Enter valid a Chilean RUT. The format is XX.XXX.XXX-X.'),
*args, **kwargs)
else:
# In non-strict mode, accept RUTs that validate but do not exist in
# the real world.
super(CLRutField, self).__init__(r'^[\d\.]{1,11}-?[\dkK]$', error_message=gettext(u'Enter valid a Chilean RUT'), *args, **kwargs)
def clean(self, value):
"""
Check and clean the Chilean RUT.
"""
super(CLRutField, self).clean(value)
if value in EMPTY_VALUES:
return u''
rut, verificador = self._canonify(value)
if self._algorithm(rut) == verificador:
return self._format(rut, verificador)
else:
raise ValidationError(u'The Chilean RUT is not valid.')
def _algorithm(self, rut):
"""
Takes RUT in pure canonical form, calculates the verifier digit.
"""
suma = 0
multi = 2
for r in rut[::-1]:
suma += int(r) * multi
multi += 1
if multi == 8:
multi = 2
return '0123456789K0'[11 - suma % 11]
def _canonify(self, rut):
"""
Turns the RUT into one normalized format. Returns a (rut, verifier)
tuple.
"""
rut = str(rut).replace(' ', '').replace('.', '').replace('-', '')
return rut[:-1], rut[-1]
def _format(self, code, verifier=None):
"""
Formats the RUT from canonical form to the common string representation.
If verifier=None, then the last digit in 'code' is the verifier.
"""
if verifier is None:
verifier = code[-1]
code = code[:-1]
while len(code) > 3 and '.' not in code[:3]:
pos = code.find('.')
if pos == -1:
new_dot = -3
else:
new_dot = pos - 3
code = code[:new_dot] + '.' + code[new_dot:]
return '%s-%s' % (code, verifier)

View File

@ -1,12 +1,12 @@
"""
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 gettext
class ISIdNumberField(RegexField):
"""
Icelandic identification number (kennitala). This is a number every citizen
@ -15,7 +15,6 @@ class ISIdNumberField(RegexField):
def __init__(self, *args, **kwargs):
error_msg = gettext(u'Enter a valid Icelandic identification number. The format is XXXXXX-XXXX.')
kwargs['min_length'],kwargs['max_length'] = 10,11
super(ISIdNumberField, self).__init__(r'^\d{6}(-| )?\d{4}$', error_message=error_msg, *args, **kwargs)
def clean(self, value):
@ -30,7 +29,6 @@ class ISIdNumberField(RegexField):
else:
raise ValidationError(gettext(u'The Icelandic identification number is not valid.'))
def _canonify(self, value):
"""
Returns the value as only digits.
@ -52,7 +50,6 @@ class ISIdNumberField(RegexField):
"""
return value[:6]+'-'+value[6:]
class ISPhoneNumberField(RegexField):
"""
Icelandic phone number. Seven digits with an optional hyphen or space after
@ -70,7 +67,6 @@ class ISPhoneNumberField(RegexField):
return value.replace('-', '').replace(' ', '')
class ISPostalCodeSelect(Select):
"""
A Select widget that uses a list of Icelandic postal codes as its choices.

View File

@ -16,7 +16,7 @@ def index(request, sitemaps):
def sitemap(request, sitemaps, section=None):
maps, urls = [], []
if section is not None:
if not sitemaps.has_key(section):
if section not in sitemaps:
raise Http404("No sitemap available for section: %r" % section)
maps.append(sitemaps[section])
else:

View File

@ -52,7 +52,7 @@ class CacheClass(BaseCache):
pass
def has_key(self, key):
return self._cache.has_key(key)
return key in self._cache
def _cull(self):
if self._cull_frequency == 0:

View File

@ -42,11 +42,11 @@ class ModPythonRequest(http.HttpRequest):
def is_secure(self):
# Note: modpython 3.2.10+ has req.is_https(), but we need to support previous versions
return self._req.subprocess_env.has_key('HTTPS') and self._req.subprocess_env['HTTPS'] == 'on'
return 'HTTPS' in self._req.subprocess_env and self._req.subprocess_env['HTTPS'] == 'on'
def _load_post_and_files(self):
"Populates self._post and self._files"
if self._req.headers_in.has_key('content-type') and self._req.headers_in['content-type'].startswith('multipart'):
if 'content-type' in self._req.headers_in and self._req.headers_in['content-type'].startswith('multipart'):
self._post, self._files = http.parse_file_upload(self._req.headers_in, self.raw_post_data)
else:
self._post, self._files = http.QueryDict(self.raw_post_data), datastructures.MultiValueDict()

View File

@ -103,7 +103,7 @@ class WSGIRequest(http.HttpRequest):
return '%s%s' % (self.path, self.environ.get('QUERY_STRING', '') and ('?' + self.environ.get('QUERY_STRING', '')) or '')
def is_secure(self):
return self.environ.has_key('HTTPS') and self.environ['HTTPS'] == 'on'
return 'HTTPS' in self.environ and self.environ['HTTPS'] == 'on'
def _load_post_and_files(self):
# Populates self._post and self._files

View File

@ -168,6 +168,8 @@ def _get_sql_model_create(model, known_models=set()):
for f in opts.fields:
if isinstance(f, (models.ForeignKey, models.OneToOneField)):
rel_field = f.rel.get_related_field()
while isinstance(rel_field, (models.ForeignKey, models.OneToOneField)):
rel_field = rel_field.rel.get_related_field()
data_type = get_rel_data_type(rel_field)
else:
rel_field = f
@ -314,7 +316,7 @@ def get_sql_delete(app):
# Drop the table now
output.append('%s %s;' % (style.SQL_KEYWORD('DROP TABLE'),
style.SQL_TABLE(backend.quote_name(model._meta.db_table))))
if backend.supports_constraints and references_to_delete.has_key(model):
if backend.supports_constraints and model in references_to_delete:
for rel_class, f in references_to_delete[model]:
table = rel_class._meta.db_table
col = f.column
@ -843,7 +845,7 @@ def inspectdb():
att_name += '_field'
comment_notes.append('Field renamed because it was a Python reserved word.')
if relations.has_key(i):
if i in relations:
rel_to = relations[i][1] == table_name and "'self'" or table2model(relations[i][1])
field_type = 'ForeignKey(%s' % rel_to
if att_name.endswith('_id'):
@ -1318,6 +1320,8 @@ def load_data(fixture_labels, verbosity=1):
from django.conf import settings
import sys
disable_termcolors()
# Keep a count of the installed objects and fixtures
count = [0,0]
models = set()
@ -1550,7 +1554,7 @@ def execute_from_command_line(action_mapping=DEFAULT_ACTION_MAPPING, argv=None):
action = args[0]
except IndexError:
parser.print_usage_and_exit()
if not action_mapping.has_key(action):
if action not in action_mapping:
print_error("Your action, %r, was invalid." % action, argv[0])
# Switch to English, because django-admin.py creates database content

View File

@ -208,15 +208,15 @@ def guess_scheme(environ):
else:
return 'http'
_hoppish = {
_hop_headers = {
'connection':1, 'keep-alive':1, 'proxy-authenticate':1,
'proxy-authorization':1, 'te':1, 'trailers':1, 'transfer-encoding':1,
'upgrade':1
}.has_key
}
def is_hop_by_hop(header_name):
"""Return true if 'header_name' is an HTTP/1.1 "Hop-by-Hop" header"""
return _hoppish(header_name.lower())
return header_name.lower() in _hop_headers
class ServerHandler(object):
"""Manage the invocation of a WSGI application"""
@ -334,7 +334,7 @@ class ServerHandler(object):
Subclasses can extend this to add other defaults.
"""
if not self.headers.has_key('Content-Length'):
if 'Content-Length' not in self.headers:
self.set_content_length()
def start_response(self, status, headers,exc_info=None):
@ -368,11 +368,11 @@ class ServerHandler(object):
if self.origin_server:
if self.client_is_modern():
self._write('HTTP/%s %s\r\n' % (self.http_version,self.status))
if not self.headers.has_key('Date'):
if 'Date' not in self.headers:
self._write(
'Date: %s\r\n' % time.asctime(time.gmtime(time.time()))
)
if self.server_software and not self.headers.has_key('Server'):
if self.server_software and 'Server' not in self.headers:
self._write('Server: %s\r\n' % self.server_software)
else:
self._write('Status: %s\r\n' % self.status)

View File

@ -102,6 +102,14 @@ class RegexURLPattern(object):
self.default_args = default_args or {}
self.name = name
def add_prefix(self, prefix):
"""
Adds the prefix string to a string-based callback.
"""
if not prefix or not hasattr(self, '_callback_str'):
return
self._callback_str = prefix + '.' + self._callback_str
def resolve(self, path):
match = self.regex.search(path)
if match:

View File

@ -284,7 +284,7 @@ class ValidateIfOtherFieldEquals(object):
self.always_test = True
def __call__(self, field_data, all_data):
if all_data.has_key(self.other_field) and all_data[self.other_field] == self.other_value:
if self.other_field in all_data and all_data[self.other_field] == self.other_value:
for v in self.validator_list:
v(field_data, all_data)
@ -322,7 +322,7 @@ class RequiredIfOtherFieldEquals(object):
self.always_test = True
def __call__(self, field_data, all_data):
if all_data.has_key(self.other_field) and all_data[self.other_field] == self.other_value and not field_data:
if self.other_field in all_data and all_data[self.other_field] == self.other_value and not field_data:
raise ValidationError(self.error_message)
class RequiredIfOtherFieldDoesNotEqual(object):
@ -335,7 +335,7 @@ class RequiredIfOtherFieldDoesNotEqual(object):
self.always_test = True
def __call__(self, field_data, all_data):
if all_data.has_key(self.other_field) and all_data[self.other_field] != self.other_value and not field_data:
if self.other_field in all_data and all_data[self.other_field] != self.other_value and not field_data:
raise ValidationError(self.error_message)
class IsLessThanOtherField(object):

View File

@ -53,7 +53,7 @@ class MysqlDebugWrapper:
raise Database.Warning, "%s: %s" % (w, self.cursor.fetchall())
def __getattr__(self, attr):
if self.__dict__.has_key(attr):
if attr in self.__dict__:
return self.__dict__[attr]
else:
return getattr(self.cursor, attr)

View File

@ -48,7 +48,7 @@ class UnicodeCursorWrapper(object):
return self.cursor.executemany(sql, new_param_list)
def __getattr__(self, attr):
if self.__dict__.has_key(attr):
if attr in self.__dict__:
return self.__dict__[attr]
else:
return getattr(self.cursor, attr)

View File

@ -33,7 +33,7 @@ class CursorDebugWrapper(object):
})
def __getattr__(self, attr):
if self.__dict__.has_key(attr):
if attr in self.__dict__:
return self.__dict__[attr]
else:
return getattr(self.cursor, attr)

View File

@ -341,11 +341,13 @@ class Field(object):
return self._choices
choices = property(_get_choices)
def formfield(self, **kwargs):
def formfield(self, form_class=forms.CharField, **kwargs):
"Returns a django.newforms.Field instance for this database Field."
defaults = {'required': not self.blank, 'label': capfirst(self.verbose_name), 'help_text': self.help_text}
if self.choices:
defaults['widget'] = forms.Select(choices=self.get_choices())
defaults.update(kwargs)
return forms.CharField(**defaults)
return form_class(**defaults)
def value_from_object(self, obj):
"Returns the value of this field in the given model instance."
@ -405,9 +407,9 @@ class BooleanField(Field):
return [oldforms.CheckboxField]
def formfield(self, **kwargs):
defaults = {'required': not self.blank, 'label': capfirst(self.verbose_name), 'help_text': self.help_text}
defaults = {'form_class': forms.BooleanField}
defaults.update(kwargs)
return forms.BooleanField(**defaults)
return super(BooleanField, self).formfield(**defaults)
class CharField(Field):
def get_manipulator_field_objs(self):
@ -424,9 +426,9 @@ class CharField(Field):
return str(value)
def formfield(self, **kwargs):
defaults = {'max_length': self.maxlength, 'required': not self.blank, 'label': capfirst(self.verbose_name), 'help_text': self.help_text}
defaults = {'max_length': self.maxlength}
defaults.update(kwargs)
return forms.CharField(**defaults)
return super(CharField, self).formfield(**defaults)
# TODO: Maybe move this into contrib, because it's specialized.
class CommaSeparatedIntegerField(CharField):
@ -502,9 +504,9 @@ class DateField(Field):
return {self.attname: (val is not None and val.strftime("%Y-%m-%d") or '')}
def formfield(self, **kwargs):
defaults = {'required': not self.blank, 'label': capfirst(self.verbose_name), 'help_text': self.help_text}
defaults = {'form_class': forms.DateField}
defaults.update(kwargs)
return forms.DateField(**defaults)
return super(DateField, self).formfield(**defaults)
class DateTimeField(DateField):
def to_python(self, value):
@ -567,9 +569,9 @@ class DateTimeField(DateField):
time_field: (val is not None and val.strftime("%H:%M:%S") or '')}
def formfield(self, **kwargs):
defaults = {'required': not self.blank, 'label': capfirst(self.verbose_name), 'help_text': self.help_text}
defaults = {'form_class': forms.DateTimeField}
defaults.update(kwargs)
return forms.DateTimeField(**defaults)
return super(DateTimeField, self).formfield(**defaults)
class EmailField(CharField):
def __init__(self, *args, **kwargs):
@ -586,9 +588,9 @@ class EmailField(CharField):
validators.isValidEmail(field_data, all_data)
def formfield(self, **kwargs):
defaults = {'required': not self.blank, 'label': capfirst(self.verbose_name), 'help_text': self.help_text}
defaults = {'form_class': forms.EmailField}
defaults.update(kwargs)
return forms.EmailField(**defaults)
return super(EmailField, self).formfield(**defaults)
class FileField(Field):
def __init__(self, verbose_name=None, name=None, upload_to='', **kwargs):
@ -723,9 +725,9 @@ class IntegerField(Field):
return [oldforms.IntegerField]
def formfield(self, **kwargs):
defaults = {'required': not self.blank, 'label': capfirst(self.verbose_name), 'help_text': self.help_text}
defaults = {'form_class': forms.IntegerField}
defaults.update(kwargs)
return forms.IntegerField(**defaults)
return super(IntegerField, self).formfield(**defaults)
class IPAddressField(Field):
def __init__(self, *args, **kwargs):
@ -762,9 +764,9 @@ class PhoneNumberField(IntegerField):
def formfield(self, **kwargs):
from django.contrib.localflavor.us.forms import USPhoneNumberField
defaults = {'required': not self.blank, 'label': capfirst(self.verbose_name), 'help_text': self.help_text}
defaults = {'form_class': USPhoneNumberField}
defaults.update(kwargs)
return USPhoneNumberField(**defaults)
return super(PhoneNumberField, self).formfield(**defaults)
class PositiveIntegerField(IntegerField):
def get_manipulator_field_objs(self):
@ -779,7 +781,7 @@ class SlugField(Field):
kwargs['maxlength'] = kwargs.get('maxlength', 50)
kwargs.setdefault('validator_list', []).append(validators.isSlug)
# Set db_index=True unless it's been set manually.
if not kwargs.has_key('db_index'):
if 'db_index' not in kwargs:
kwargs['db_index'] = True
Field.__init__(self, *args, **kwargs)
@ -795,9 +797,9 @@ class TextField(Field):
return [oldforms.LargeTextField]
def formfield(self, **kwargs):
defaults = {'required': not self.blank, 'widget': forms.Textarea, 'label': capfirst(self.verbose_name), 'help_text': self.help_text}
defaults = {'widget': forms.Textarea}
defaults.update(kwargs)
return forms.CharField(**defaults)
return super(TextField, self).formfield(**defaults)
class TimeField(Field):
empty_strings_allowed = False
@ -840,9 +842,9 @@ class TimeField(Field):
return {self.attname: (val is not None and val.strftime("%H:%M:%S") or '')}
def formfield(self, **kwargs):
defaults = {'required': not self.blank, 'label': capfirst(self.verbose_name), 'help_text': self.help_text}
defaults = {'form_class': forms.TimeField}
defaults.update(kwargs)
return forms.TimeField(**defaults)
return super(TimeField, self).formfield(**defaults)
class URLField(CharField):
def __init__(self, verbose_name=None, name=None, verify_exists=True, **kwargs):
@ -859,9 +861,9 @@ class URLField(CharField):
return "CharField"
def formfield(self, **kwargs):
defaults = {'required': not self.blank, 'verify_exists': self.verify_exists, 'label': capfirst(self.verbose_name), 'help_text': self.help_text}
defaults = {'form_class': forms.URLField, 'verify_exists': self.verify_exists}
defaults.update(kwargs)
return forms.URLField(**defaults)
return super(URLField, self).formfield(**defaults)
class USStateField(Field):
def get_manipulator_field_objs(self):

View File

@ -37,7 +37,7 @@ class GenericForeignKey(object):
def instance_pre_init(self, signal, sender, args, kwargs):
# Handle initalizing an object with the generic FK instaed of
# content-type/object-id fields.
if kwargs.has_key(self.name):
if self.name in kwargs:
value = kwargs.pop(self.name)
kwargs[self.ct_field] = self.get_content_type(value)
kwargs[self.fk_field] = value._get_pk_val()

View File

@ -474,7 +474,7 @@ class ForeignKey(RelatedField, Field):
to_field = to_field or to._meta.pk.name
kwargs['verbose_name'] = kwargs.get('verbose_name', '')
if kwargs.has_key('edit_inline_type'):
if 'edit_inline_type' in kwargs:
import warnings
warnings.warn("edit_inline_type is deprecated. Use edit_inline instead.")
kwargs['edit_inline'] = kwargs.pop('edit_inline_type')
@ -553,9 +553,9 @@ class ForeignKey(RelatedField, Field):
setattr(cls, related.get_accessor_name(), ForeignRelatedObjectsDescriptor(related))
def formfield(self, **kwargs):
defaults = {'queryset': self.rel.to._default_manager.all(), 'required': not self.blank, 'label': capfirst(self.verbose_name), 'help_text': self.help_text}
defaults = {'form_class': forms.ModelChoiceField, 'queryset': self.rel.to._default_manager.all()}
defaults.update(kwargs)
return forms.ModelChoiceField(**defaults)
return super(ForeignKey, self).formfield(**defaults)
class OneToOneField(RelatedField, IntegerField):
def __init__(self, to, to_field=None, **kwargs):
@ -567,7 +567,7 @@ class OneToOneField(RelatedField, IntegerField):
to_field = to_field or to._meta.pk.name
kwargs['verbose_name'] = kwargs.get('verbose_name', '')
if kwargs.has_key('edit_inline_type'):
if 'edit_inline_type' in kwargs:
import warnings
warnings.warn("edit_inline_type is deprecated. Use edit_inline instead.")
kwargs['edit_inline'] = kwargs.pop('edit_inline_type')
@ -619,9 +619,9 @@ class OneToOneField(RelatedField, IntegerField):
cls._meta.one_to_one_field = self
def formfield(self, **kwargs):
defaults = {'queryset': self.rel.to._default_manager.all(), 'required': not self.blank, 'label': capfirst(self.verbose_name), 'help_text': self.help_text}
defaults = {'form_class': forms.ModelChoiceField, 'queryset': self.rel.to._default_manager.all()}
defaults.update(kwargs)
return forms.ModelChoiceField(**defaults)
return super(OneToOneField, self).formfield(**defaults)
class ManyToManyField(RelatedField, Field):
def __init__(self, to, **kwargs):
@ -738,13 +738,13 @@ class ManyToManyField(RelatedField, Field):
return getattr(obj, self.attname).all()
def formfield(self, **kwargs):
defaults = {'form_class': forms.ModelMultipleChoiceField, 'queryset': self.rel.to._default_manager.all()}
defaults.update(kwargs)
# If initial is passed in, it's a list of related objects, but the
# MultipleChoiceField takes a list of IDs.
if kwargs.get('initial') is not None:
kwargs['initial'] = [i._get_pk_val() for i in kwargs['initial']]
defaults = {'queryset' : self.rel.to._default_manager.all(), 'required': not self.blank, 'label': capfirst(self.verbose_name), 'help_text': self.help_text}
defaults.update(kwargs)
return forms.ModelMultipleChoiceField(**defaults)
if defaults.get('initial') is not None:
defaults['initial'] = [i._get_pk_val() for i in defaults['initial']]
return super(ManyToManyField, self).formfield(**defaults)
class ManyToOneRel(object):
def __init__(self, to, field_name, num_in_admin=3, min_num_in_admin=None,

View File

@ -103,7 +103,7 @@ def register_models(app_label, *models):
# in the _app_models dictionary
model_name = model._meta.object_name.lower()
model_dict = _app_models.setdefault(app_label, {})
if model_dict.has_key(model_name):
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
# filename as a means to detect identity.

View File

@ -140,7 +140,7 @@ class Options(object):
def get_follow(self, override=None):
follow = {}
for f in self.fields + self.many_to_many + self.get_all_related_objects():
if override and override.has_key(f.name):
if override and f.name in override:
child_override = override[f.name]
else:
child_override = None
@ -182,7 +182,7 @@ class Options(object):
# TODO: follow
if not hasattr(self, '_field_types'):
self._field_types = {}
if not self._field_types.has_key(field_type):
if field_type not in self._field_types:
try:
# First check self.fields.
for f in self.fields:

View File

@ -46,12 +46,12 @@ def enter_transaction_management():
when no current block is running).
"""
thread_ident = thread.get_ident()
if state.has_key(thread_ident) and state[thread_ident]:
if thread_ident in state and state[thread_ident]:
state[thread_ident].append(state[thread_ident][-1])
else:
state[thread_ident] = []
state[thread_ident].append(settings.TRANSACTIONS_MANAGED)
if not dirty.has_key(thread_ident):
if thread_ident not in dirty:
dirty[thread_ident] = False
def leave_transaction_management():
@ -61,7 +61,7 @@ def leave_transaction_management():
those from outside. (Commits are on connection level.)
"""
thread_ident = thread.get_ident()
if state.has_key(thread_ident) and state[thread_ident]:
if thread_ident in state and state[thread_ident]:
del state[thread_ident][-1]
else:
raise TransactionManagementError("This code isn't under transaction management")
@ -84,7 +84,7 @@ def set_dirty():
changes waiting for commit.
"""
thread_ident = thread.get_ident()
if dirty.has_key(thread_ident):
if thread_ident in dirty:
dirty[thread_ident] = True
else:
raise TransactionManagementError("This code isn't under transaction management")
@ -96,7 +96,7 @@ def set_clean():
should happen.
"""
thread_ident = thread.get_ident()
if dirty.has_key(thread_ident):
if thread_ident in dirty:
dirty[thread_ident] = False
else:
raise TransactionManagementError("This code isn't under transaction management")
@ -106,7 +106,7 @@ def is_managed():
Checks whether the transaction manager is in manual or in auto state.
"""
thread_ident = thread.get_ident()
if state.has_key(thread_ident):
if thread_ident in state:
if state[thread_ident]:
return state[thread_ident][-1]
return settings.TRANSACTIONS_MANAGED

View File

@ -29,12 +29,12 @@ class HttpRequest(object):
def __getitem__(self, key):
for d in (self.POST, self.GET):
if d.has_key(key):
if key in d:
return d[key]
raise KeyError, "%s not found in either POST or GET" % key
def has_key(self, key):
return self.GET.has_key(key) or self.POST.has_key(key)
return key in self.GET or key in self.POST
def get_full_path(self):
return ''
@ -57,7 +57,7 @@ def parse_file_upload(header_dict, post_data):
# name_dict is something like {'name': 'file', 'filename': 'test.txt'} for file uploads
# or {'name': 'blah'} for POST fields
# We assume all uploaded files have a 'filename' set.
if name_dict.has_key('filename'):
if 'filename' in name_dict:
assert type([]) != type(submessage.get_payload()), "Nested MIME messages are not supported"
if not name_dict['filename'].strip():
continue
@ -66,7 +66,7 @@ def parse_file_upload(header_dict, post_data):
filename = name_dict['filename'][name_dict['filename'].rfind("\\")+1:]
FILES.appendlist(name_dict['name'], {
'filename': filename,
'content-type': (submessage.has_key('Content-Type') and submessage['Content-Type'] or None),
'content-type': 'Content-Type' in submessage and submessage['Content-Type'] or None,
'content': submessage.get_payload(),
})
else:

View File

@ -25,7 +25,7 @@ class CommonMiddleware(object):
"""
# Check for denied User-Agents
if request.META.has_key('HTTP_USER_AGENT'):
if 'HTTP_USER_AGENT' in request.META:
for user_agent_regex in settings.DISALLOWED_USER_AGENTS:
if user_agent_regex.search(request.META['HTTP_USER_AGENT']):
return http.HttpResponseForbidden('<h1>Forbidden</h1>')

View File

@ -457,7 +457,7 @@ class MultiValueField(Field):
for i, field in enumerate(self.fields):
try:
field_value = value[i]
except KeyError:
except IndexError:
field_value = None
if self.required and field_value in EMPTY_VALUES:
raise ValidationError(ugettext(u'This field is required.'))

View File

@ -122,7 +122,14 @@ class BaseForm(StrAndUnicode):
else:
if errors_on_separate_row and bf_errors:
output.append(error_row % bf_errors)
label = bf.label and bf.label_tag(escape(bf.label + ':')) or ''
if bf.label:
label = escape(bf.label)
# Only add a colon if the label does not end in punctuation.
if label[-1] not in ':?.!':
label += ':'
label = bf.label_tag(label) or ''
else:
label = ''
if field.help_text:
help_text = help_text_html % field.help_text
else:
@ -244,7 +251,7 @@ class BoundField(StrAndUnicode):
def as_widget(self, widget, attrs=None):
attrs = attrs or {}
auto_id = self.auto_id
if auto_id and not attrs.has_key('id') and not widget.attrs.has_key('id'):
if auto_id and 'id' not in attrs and 'id' not in widget.attrs:
attrs['id'] = auto_id
if not self.form.is_bound:
data = self.form.initial.get(self.name, self.field.initial)

View File

@ -230,7 +230,7 @@ class RadioInput(StrAndUnicode):
return self.value == self.choice_value
def tag(self):
if self.attrs.has_key('id'):
if 'id' in self.attrs:
self.attrs['id'] = '%s_%s' % (self.attrs['id'], self.index)
final_attrs = dict(self.attrs, type='radio', name=self.name, value=self.choice_value)
if self.is_checked():
@ -276,7 +276,7 @@ class RadioSelect(Select):
class CheckboxSelectMultiple(SelectMultiple):
def render(self, name, value, attrs=None, choices=()):
if value is None: value = []
has_id = attrs and attrs.has_key('id')
has_id = attrs and 'id' in attrs
final_attrs = self.build_attrs(attrs, name=name)
output = [u'<ul>']
str_values = set([smart_unicode(v) for v in value]) # Normalize to strings.
@ -347,7 +347,7 @@ class MultiWidget(Widget):
id_for_label = classmethod(id_for_label)
def value_from_datadict(self, data, name):
return [data.get(name + '_%s' % i) for i in range(len(self.widgets))]
return [widget.value_from_datadict(data, name + '_%s' % i) for i, widget in enumerate(self.widgets)]
def format_output(self, rendered_widgets):
return u''.join(rendered_widgets)

View File

@ -341,7 +341,7 @@ class FormField(object):
def convert_post_data(self, new_data):
name = self.get_member_name()
if new_data.has_key(self.field_name):
if self.field_name in new_data:
d = new_data.getlist(self.field_name)
try:
converted_data = [self.__class__.html2python(data) for data in d]

View File

@ -201,18 +201,27 @@ class Lexer(object):
def tokenize(self):
"Return a list of tokens from a given template_string"
# remove all empty strings, because the regex has a tendency to add them
bits = filter(None, tag_re.split(self.template_string))
return map(self.create_token, bits)
in_tag = False
result = []
for bit in tag_re.split(self.template_string):
if bit:
result.append(self.create_token(bit, in_tag))
in_tag = not in_tag
return result
def create_token(self,token_string):
"Convert the given token string into a new Token object and return it"
if token_string.startswith(VARIABLE_TAG_START):
token = Token(TOKEN_VAR, token_string[len(VARIABLE_TAG_START):-len(VARIABLE_TAG_END)].strip())
elif token_string.startswith(BLOCK_TAG_START):
token = Token(TOKEN_BLOCK, token_string[len(BLOCK_TAG_START):-len(BLOCK_TAG_END)].strip())
elif token_string.startswith(COMMENT_TAG_START):
token = Token(TOKEN_COMMENT, '')
def create_token(self, token_string, in_tag):
"""
Convert the given token string into a new Token object and return it.
If in_tag is True, we are processing something that matched a tag,
otherwise it should be treated as a literal string.
"""
if in_tag:
if token_string.startswith(VARIABLE_TAG_START):
token = Token(TOKEN_VAR, token_string[len(VARIABLE_TAG_START):-len(VARIABLE_TAG_END)].strip())
elif token_string.startswith(BLOCK_TAG_START):
token = Token(TOKEN_BLOCK, token_string[len(BLOCK_TAG_START):-len(BLOCK_TAG_END)].strip())
elif token_string.startswith(COMMENT_TAG_START):
token = Token(TOKEN_COMMENT, '')
else:
token = Token(TOKEN_TEXT, token_string)
return token
@ -223,22 +232,22 @@ class DebugLexer(Lexer):
def tokenize(self):
"Return a list of tokens from a given template_string"
token_tups, upto = [], 0
result, upto = [], 0
for match in tag_re.finditer(self.template_string):
start, end = match.span()
if start > upto:
token_tups.append( (self.template_string[upto:start], (upto, start)) )
result.append(self.create_token(self.template_string[upto:start], (upto, start), False))
upto = start
token_tups.append( (self.template_string[start:end], (start,end)) )
result.append(self.create_token(self.template_string[start:end], (start, end), True))
upto = end
last_bit = self.template_string[upto:]
if last_bit:
token_tups.append( (last_bit, (upto, upto + len(last_bit))) )
return [self.create_token(tok, (self.origin, loc)) for tok, loc in token_tups]
result.append(self.create_token(last_bit, (upto, upto + len(last_bit)), False))
return result
def create_token(self, token_string, source):
token = super(DebugLexer, self).create_token(token_string)
token.source = source
def create_token(self, token_string, source, in_tag):
token = super(DebugLexer, self).create_token(token_string, in_tag)
token.source = self.origin, source
return token
class Parser(object):
@ -346,7 +355,7 @@ class Parser(object):
return FilterExpression(token, self)
def find_filter(self, filter_name):
if self.filters.has_key(filter_name):
if filter_name in self.filters:
return self.filters[filter_name]
else:
raise TemplateSyntaxError, "Invalid filter: '%s'" % filter_name

View File

@ -35,7 +35,7 @@ class Context(object):
def __getitem__(self, key):
"Get a variable's value, starting at the current context and going upward"
for d in self.dicts:
if d.has_key(key):
if key in d:
return d[key]
raise KeyError(key)
@ -45,7 +45,7 @@ class Context(object):
def has_key(self, key):
for d in self.dicts:
if d.has_key(key):
if key in d:
return True
return False
@ -54,7 +54,7 @@ class Context(object):
def get(self, key, otherwise=None):
for d in self.dicts:
if d.has_key(key):
if key in d:
return d[key]
return otherwise

View File

@ -88,7 +88,7 @@ class ForNode(Node):
def render(self, context):
nodelist = NodeList()
if context.has_key('forloop'):
if 'forloop' in context:
parentloop = context['forloop']
else:
parentloop = {}
@ -134,7 +134,7 @@ class IfChangedNode(Node):
self._varlist = varlist
def render(self, context):
if context.has_key('forloop') and context['forloop']['first']:
if 'forloop' in context and context['forloop']['first']:
self._last_seen = None
try:
if self._varlist:
@ -433,7 +433,7 @@ def cycle(parser, token):
name = args[1]
if not hasattr(parser, '_namedCycleNodes'):
raise TemplateSyntaxError("No named cycles in template: '%s' is not defined" % name)
if not parser._namedCycleNodes.has_key(name):
if name not in parser._namedCycleNodes:
raise TemplateSyntaxError("Named cycle '%s' does not exist" % name)
return parser._namedCycleNodes[name]
@ -912,7 +912,7 @@ def templatetag(parser, token):
if len(bits) != 2:
raise TemplateSyntaxError, "'templatetag' statement takes one argument"
tag = bits[1]
if not TemplateTagNode.mapping.has_key(tag):
if tag not in TemplateTagNode.mapping:
raise TemplateSyntaxError, "Invalid templatetag argument: '%s'. Must be one of: %s" % \
(tag, TemplateTagNode.mapping.keys())
return TemplateTagNode(tag)

View File

@ -42,7 +42,7 @@ class MergeDict(object):
def has_key(self, key):
for dict in self.dicts:
if dict.has_key(key):
if key in dict:
return True
return False

View File

@ -42,7 +42,7 @@ def lazy(func, *resultclasses):
res = self.__func(*self.__args, **self.__kw)
return self.__dispatch[type(res)][funcname](res, *args, **kw)
if not self.__dispatch.has_key(klass):
if klass not in self.__dispatch:
self.__dispatch[klass] = {}
self.__dispatch[klass][funcname] = func
return __wrapper__

View File

@ -200,7 +200,7 @@ def deactivate():
will resolve against the default translation object, again.
"""
global _active
if _active.has_key(currentThread()):
if currentThread() in _active:
del _active[currentThread()]
def get_language():

View File

@ -97,7 +97,7 @@ def javascript_catalog(request, domain='djangojs', packages=None):
deliver your JavaScript source from Django templates.
"""
if request.GET:
if request.GET.has_key('language'):
if 'language' in request.GET:
if check_for_language(request.GET['language']):
activate(request.GET['language'])
if packages is None:
@ -136,7 +136,7 @@ def javascript_catalog(request, domain='djangojs', packages=None):
t.update(catalog._catalog)
src = [LibHead]
plural = None
if t.has_key(''):
if '' in t:
for l in t[''].split('\n'):
if l.startswith('Plural-Forms:'):
plural = l.split(':',1)[1].strip()
@ -155,7 +155,7 @@ def javascript_catalog(request, domain='djangojs', packages=None):
if type(k) in (str, unicode):
csrc.append("catalog['%s'] = '%s';\n" % (javascript_quote(k), javascript_quote(v)))
elif type(k) == tuple:
if not pdict.has_key(k[0]):
if k[0] not in pdict:
pdict[k[0]] = k[1]
else:
pdict[k[0]] = max(k[1], pdict[k[0]])

View File

@ -208,7 +208,8 @@ Hashtype is either ``sha1`` (default), ``md5`` or ``crypt`` -- the algorithm
used to perform a one-way hash of the password. Salt is a random string used
to salt the raw password to create the hash. Note that the ``crypt`` method is
only supported on platforms that have the standard Python ``crypt`` module
available.
available, and ``crypt`` support is only available in the Django development
version.
For example::

View File

@ -112,7 +112,7 @@ the previous record in the database::
b4 = Blog(id=3, name='Not Cheddar', tagline='Anything but cheese.')
b4.save() # Overrides the previous blog with ID=3!
See _`How Django knows to UPDATE vs. INSERT`, below, for the reason this
See `How Django knows to UPDATE vs. INSERT`_, below, for the reason this
happens.
Explicitly specifying auto-primary-key values is mostly useful for bulk-saving
@ -714,7 +714,7 @@ QuerySet methods that do not return QuerySets
The following ``QuerySet`` methods evaluate the ``QuerySet`` and return
something *other than* a ``QuerySet``.
These methods do not use a cache (see _`Caching and QuerySets` below). Rather,
These methods do not use a cache (see `Caching and QuerySets`_ below). Rather,
they query the database each time they're called.
``get(**kwargs)``

View File

@ -20,12 +20,21 @@ In two lines::
send_mail('Subject here', 'Here is the message.', 'from@example.com',
['to@example.com'], fail_silently=False)
Mail will be sent using the SMTP host and port specified in the `EMAIL_HOST`_
and `EMAIL_PORT`_ settings. The `EMAIL_HOST_USER`_ and `EMAIL_HOST_PASSWORD`_
settings, if set, will be used to authenticate to the SMTP server.
.. note::
The character set of email sent with ``django.core.mail`` will be set to
the value of your `DEFAULT_CHARSET setting`_.
.. _DEFAULT_CHARSET setting: ../settings/#DEFAULT_CHARSET
.. _DEFAULT_CHARSET setting: ../settings/#default-charset
.. _EMAIL_HOST: ../settings/#email-host
.. _EMAIL_PORT: ../settings/#email-port
.. _EMAIL_HOST_USER: ../settings/#email-host-user
.. _EMAIL_HOST_PASSWORD: ../settings/#email-host-password
send_mail()
===========

View File

@ -615,15 +615,19 @@ fails. If no message is passed in, a default message is used.
``other_value``, then the validators in ``validator_list`` are all run
against the current field.
``RequiredIfOtherFieldGiven``
Takes a field name of the current field is only required if the other
field has a value.
``RequiredIfOtherFieldsGiven``
Similar to ``RequiredIfOtherFieldGiven``, except that it takes a list of
field names and if any one of the supplied fields has a value provided,
the current field being validated is required.
``RequiredIfOtherFieldNotGiven``
Takes the name of the other field and this field is only required if the
other field has no value.
``RequiredIfOtherFieldsNotGiven``
Similar to ``RequiredIfOtherFieldNotGiven``, except that it takes a list
of field names and if any one of the supplied fields does not have a value
provided, the field being validated is required.
``RequiredIfOtherFieldEquals`` and ``RequiredIfOtherFieldDoesNotEqual``
Each of these validator classes takes a field name and a value (in that
order). If the given field does (or does not have, in the latter case) the

View File

@ -45,15 +45,15 @@ Get your database running
=========================
If you plan to use Django's database API functionality, you'll need to
make sure a database server is running. Django works with PostgreSQL_
(recommended), MySQL_ and SQLite_.
make sure a database server is running. Django works with PostgreSQL_,
MySQL_ and SQLite_.
Additionally, you'll need to make sure your Python database bindings are
installed.
* If you're using PostgreSQL, you'll need the psycopg_ package (version 2 is
recommended with ``postgresql_psycopg2`` backend, version 1.1 works also with the
``postgresql``` backend).
* If you're using PostgreSQL, you'll need the psycopg_ package. Django supports
both version 1 and 2. (When you configure Django's database layer, specify
either ``postgresql`` [for version 1] or ``postgresql_psycopg2`` [for version 2].)
If you're on Windows, check out the unofficial `compiled Windows version`_.

View File

@ -395,8 +395,10 @@ EMAIL_HOST_PASSWORD
Default: ``''`` (Empty string)
Username to use for the SMTP server defined in ``EMAIL_HOST``. If empty,
Django won't attempt authentication.
Password to use for the SMTP server defined in ``EMAIL_HOST``. This setting is
used in conjunction with ``EMAIL_HOST_USER`` when authenticating to the SMTP
server. If either of these settings is empty, Django won't attempt
authenticaion.
See also ``EMAIL_HOST_USER``.
@ -570,9 +572,23 @@ strings for translation, but the translation won't happen at runtime -- so
you'll have to remember to wrap the languages in the *real* ``gettext()`` in
any code that uses ``LANGUAGES`` at runtime.
LOGIN_REDIRECT_URL
------------------
**New in Django development version**
Default: ``'/accounts/profile/'``
The URL where requests are redirected after login when the
``contrib.auth.login`` view gets no ``next`` parameter.
This is used by the `@login_required`_ decorator, for example.
LOGIN_URL
---------
**New in Django development version**
Default: ``'/accounts/login/'``
The URL where requests are redirected for login, specially when using the
@ -581,6 +597,8 @@ The URL where requests are redirected for login, specially when using the
LOGOUT_URL
----------
**New in Django development version**
Default: ``'/accounts/logout/'``
LOGIN_URL counterpart.
@ -643,16 +661,6 @@ locales have different formats. For example, U.S. English would say
See `allowed date format strings`_. See also DATE_FORMAT, DATETIME_FORMAT,
TIME_FORMAT and YEAR_MONTH_FORMAT.
LOGIN_REDIRECT_URL
------------------
Default: ``'/accounts/profile/'``
The URL where requests are redirected after login when the
``contrib.auth.login`` view gets no ``next`` parameter.
This is used by the `@login_required`_ decorator, for example.
PREPEND_WWW
-----------

View File

@ -24,6 +24,12 @@ a commit=True parameter.
from django.db import models
ARTICLE_STATUS = (
(1, 'Draft'),
(2, 'Pending'),
(3, 'Live'),
)
class Category(models.Model):
name = models.CharField(maxlength=20)
url = models.CharField('The URL', maxlength=40)
@ -44,6 +50,7 @@ class Article(models.Model):
writer = models.ForeignKey(Writer)
article = models.TextField()
categories = models.ManyToManyField(Category, blank=True)
status = models.IntegerField(choices=ARTICLE_STATUS, blank=True, null=True)
def save(self):
import datetime
@ -147,8 +154,8 @@ Create a couple of Writers.
>>> w = Writer(name='Bob Woodward')
>>> w.save()
ManyToManyFields are represented by a MultipleChoiceField, and ForeignKeys are
represented by a ChoiceField.
ManyToManyFields are represented by a MultipleChoiceField, ForeignKeys and any
fields with the 'choices' attribute are represented by a ChoiceField.
>>> ArticleForm = form_for_model(Article)
>>> f = ArticleForm(auto_id=False)
>>> print f
@ -160,6 +167,12 @@ represented by a ChoiceField.
<option value="2">Bob Woodward</option>
</select></td></tr>
<tr><th>Article:</th><td><textarea rows="10" cols="40" name="article"></textarea></td></tr>
<tr><th>Status:</th><td><select name="status">
<option value="" selected="selected">---------</option>
<option value="1">Draft</option>
<option value="2">Pending</option>
<option value="3">Live</option>
</select></td></tr>
<tr><th>Categories:</th><td><select multiple="multiple" name="categories">
<option value="1">Entertainment</option>
<option value="2">It&#39;s a test</option>
@ -200,6 +213,12 @@ current values are inserted as 'initial' data in each Field.
<option value="2">Bob Woodward</option>
</select></li>
<li>Article: <textarea rows="10" cols="40" name="article">Hello.</textarea></li>
<li>Status: <select name="status">
<option value="" selected="selected">---------</option>
<option value="1">Draft</option>
<option value="2">Pending</option>
<option value="3">Live</option>
</select></li>
<li>Categories: <select multiple="multiple" name="categories">
<option value="1">Entertainment</option>
<option value="2">It&#39;s a test</option>
@ -232,6 +251,12 @@ Add some categories and test the many-to-many form output.
<option value="2">Bob Woodward</option>
</select></li>
<li>Article: <textarea rows="10" cols="40" name="article">Hello.</textarea></li>
<li>Status: <select name="status">
<option value="" selected="selected">---------</option>
<option value="1">Draft</option>
<option value="2">Pending</option>
<option value="3">Live</option>
</select></li>
<li>Categories: <select multiple="multiple" name="categories">
<option value="1" selected="selected">Entertainment</option>
<option value="2">It&#39;s a test</option>
@ -310,6 +335,12 @@ the data in the database when the form is instantiated.
<option value="2">Bob Woodward</option>
</select></li>
<li>Article: <textarea rows="10" cols="40" name="article"></textarea></li>
<li>Status: <select name="status">
<option value="" selected="selected">---------</option>
<option value="1">Draft</option>
<option value="2">Pending</option>
<option value="3">Live</option>
</select></li>
<li>Categories: <select multiple="multiple" name="categories">
<option value="1">Entertainment</option>
<option value="2">It&#39;s a test</option>
@ -329,6 +360,12 @@ the data in the database when the form is instantiated.
<option value="3">Carl Bernstein</option>
</select></li>
<li>Article: <textarea rows="10" cols="40" name="article"></textarea></li>
<li>Status: <select name="status">
<option value="" selected="selected">---------</option>
<option value="1">Draft</option>
<option value="2">Pending</option>
<option value="3">Live</option>
</select></li>
<li>Categories: <select multiple="multiple" name="categories">
<option value="1">Entertainment</option>
<option value="2">It&#39;s a test</option>

View File

@ -55,8 +55,10 @@ class Tester(unittest.TestCase):
for t in self.ts:
if hasattr(t, 'x'):
self.assert_(sd.has_key(safeRef(t.x)))
self.assert_(safeRef(t.x) in sd)
else:
self.assert_(sd.has_key(safeRef(t)))
self.assert_(safeRef(t) in sd)
def testRepresentation (self):
"""Test that the reference object's representation works

File diff suppressed because one or more lines are too long

View File

@ -5,6 +5,7 @@ from regressions import regression_tests
form_tests = r"""
>>> from django.newforms import *
>>> import datetime
>>> import time
>>> import re
###########
@ -2600,6 +2601,27 @@ underscores converted to spaces, and the initial letter capitalized.
<li>Password1: <input type="password" name="password1" /></li>
<li>Password (again): <input type="password" name="password2" /></li>
Labels for as_* methods will only end in a colon if they don't end in other
punctuation already.
>>> class Questions(Form):
... q1 = CharField(label='The first question')
... q2 = CharField(label='What is your name?')
... q3 = CharField(label='The answer to life is:')
... q4 = CharField(label='Answer this question!')
... q5 = CharField(label='The last question. Period.')
>>> print Questions(auto_id=False).as_p()
<p>The first question: <input type="text" name="q1" /></p>
<p>What is your name? <input type="text" name="q2" /></p>
<p>The answer to life is: <input type="text" name="q3" /></p>
<p>Answer this question! <input type="text" name="q4" /></p>
<p>The last question. Period. <input type="text" name="q5" /></p>
>>> print Questions().as_p()
<p><label for="id_q1">The first question:</label> <input type="text" name="q1" id="id_q1" /></p>
<p><label for="id_q2">What is your name?</label> <input type="text" name="q2" id="id_q2" /></p>
<p><label for="id_q3">The answer to life is:</label> <input type="text" name="q3" id="id_q3" /></p>
<p><label for="id_q4">Answer this question!</label> <input type="text" name="q4" id="id_q4" /></p>
<p><label for="id_q5">The last question. Period.</label> <input type="text" name="q5" id="id_q5" /></p>
A label can be a Unicode object or a bytestring with special characters.
>>> class UserRegistration(Form):
... username = CharField(max_length=10, label='ŠĐĆŽćžšđ')
@ -3297,6 +3319,94 @@ True
<option value="2016">2016</option>
</select>
# MultiWidget and MultiValueField #############################################
# MultiWidgets are widgets composed of other widgets. They are usually
# combined with MultiValueFields - a field that is composed of other fields.
# MulitWidgets can themselved be composed of other MultiWidgets.
# SplitDateTimeWidget is one example of a MultiWidget.
>>> class ComplexMultiWidget(MultiWidget):
... def __init__(self, attrs=None):
... widgets = (
... TextInput(),
... SelectMultiple(choices=(('J', 'John'), ('P', 'Paul'), ('G', 'George'), ('R', 'Ringo'))),
... SplitDateTimeWidget(),
... )
... super(ComplexMultiWidget, self).__init__(widgets, attrs)
...
... def decompress(self, value):
... if value:
... data = value.split(',')
... return [data[0], data[1], datetime.datetime(*time.strptime(data[2], "%Y-%m-%d %H:%M:%S")[0:6])]
... return [None, None, None]
... def format_output(self, rendered_widgets):
... return u'\n'.join(rendered_widgets)
>>> w = ComplexMultiWidget()
>>> print w.render('name', 'some text,JP,2007-04-25 06:24:00')
<input type="text" name="name_0" value="some text" />
<select multiple="multiple" name="name_1">
<option value="J" selected="selected">John</option>
<option value="P" selected="selected">Paul</option>
<option value="G">George</option>
<option value="R">Ringo</option>
</select>
<input type="text" name="name_2_0" value="2007-04-25" /><input type="text" name="name_2_1" value="06:24:00" />
>>> class ComplexField(MultiValueField):
... def __init__(self, required=True, widget=None, label=None, initial=None):
... fields = (
... CharField(),
... MultipleChoiceField(choices=(('J', 'John'), ('P', 'Paul'), ('G', 'George'), ('R', 'Ringo'))),
... SplitDateTimeField()
... )
... super(ComplexField, self).__init__(fields, required, widget, label, initial)
...
... def compress(self, data_list):
... if data_list:
... return '%s,%s,%s' % (data_list[0],''.join(data_list[1]),data_list[2])
... return None
>>> f = ComplexField(widget=w)
>>> f.clean(['some text', ['J','P'], ['2007-04-25','6:24:00']])
u'some text,JP,2007-04-25 06:24:00'
>>> f.clean(['some text',['X'], ['2007-04-25','6:24:00']])
Traceback (most recent call last):
...
ValidationError: [u'Select a valid choice. X is not one of the available choices.']
# If insufficient data is provided, None is substituted
>>> f.clean(['some text',['JP']])
Traceback (most recent call last):
...
ValidationError: [u'This field is required.']
>>> class ComplexFieldForm(Form):
... field1 = ComplexField(widget=w)
>>> f = ComplexFieldForm()
>>> print f
<tr><th><label for="id_field1_0">Field1:</label></th><td><input type="text" name="field1_0" id="id_field1_0" />
<select multiple="multiple" name="field1_1" id="id_field1_1">
<option value="J">John</option>
<option value="P">Paul</option>
<option value="G">George</option>
<option value="R">Ringo</option>
</select>
<input type="text" name="field1_2_0" id="id_field1_2_0" /><input type="text" name="field1_2_1" id="id_field1_2_1" /></td></tr>
>>> f = ComplexFieldForm({'field1_0':'some text','field1_1':['J','P'], 'field1_2_0':'2007-04-25', 'field1_2_1':'06:24:00'})
>>> print f
<tr><th><label for="id_field1_0">Field1:</label></th><td><input type="text" name="field1_0" value="some text" id="id_field1_0" />
<select multiple="multiple" name="field1_1" id="id_field1_1">
<option value="J" selected="selected">John</option>
<option value="P" selected="selected">Paul</option>
<option value="G">George</option>
<option value="R">Ringo</option>
</select>
<input type="text" name="field1_2_0" value="2007-04-25" id="id_field1_2_0" /><input type="text" name="field1_2_1" value="06:24:00" id="id_field1_2_1" /></td></tr>
>>> f.clean_data
{'field1': u'some text,JP,2007-04-25 06:24:00'}
#################################
# Tests of underlying functions #
#################################

View File

@ -34,6 +34,9 @@ AttributeError: This QueryDict instance is immutable
>>> q.has_key('foo')
False
>>> 'foo' in q
False
>>> q.items()
[]
@ -124,6 +127,9 @@ MultiValueDictKeyError: "Key 'foo' not found in <MultiValueDict: {}>"
>>> q.has_key('foo')
True
>>> 'foo' in q
True
>>> q.items()
[('foo', 'another'), ('name', 'john')]
@ -218,9 +224,15 @@ AttributeError: This QueryDict instance is immutable
>>> q.has_key('foo')
True
>>> 'foo' in q
True
>>> q.has_key('bar')
False
>>> 'bar' in q
False
>>> q.items()
[('foo', 'bar')]
@ -303,9 +315,15 @@ AttributeError: This QueryDict instance is immutable
>>> q.has_key('vote')
True
>>> 'vote' in q
True
>>> q.has_key('foo')
False
>>> 'foo' in q
False
>>> q.items()
[('vote', 'no')]

View File

@ -133,6 +133,18 @@ class Templates(unittest.TestCase):
# Fail silently when accessing a non-simple method
'basic-syntax20': ("{{ var.method2 }}", {"var": SomeClass()}, ("","INVALID")),
# Don't get confused when parsing something that is almost, but not
# quite, a template tag.
'basic-syntax21': ("a {{ moo %} b", {}, "a {{ moo %} b"),
'basic-syntax22': ("{{ moo #}", {}, "{{ moo #}"),
# Will try to treat "moo #} {{ cow" as the variable. Not ideal, but
# costly to work around, so this triggers an error.
'basic-syntax23': ("{{ moo #} {{ cow }}", {"cow": "cow"}, template.TemplateSyntaxError),
# Embedded newlines make it not-a-tag.
'basic-syntax24': ("{{ moo\n }}", {}, "{{ moo\n }}"),
# List-index syntax allows a template to access a certain item of a subscriptable object.
'list-index01': ("{{ var.1 }}", {"var": ["first item", "second item"]}, "second item"),
@ -157,60 +169,61 @@ class Templates(unittest.TestCase):
'list-index07': ("{{ var.1 }}", {"var": {'1': "hello", 1: "world"}}, "hello"),
# Basic filter usage
'basic-syntax21': ("{{ var|upper }}", {"var": "Django is the greatest!"}, "DJANGO IS THE GREATEST!"),
'filter-syntax01': ("{{ var|upper }}", {"var": "Django is the greatest!"}, "DJANGO IS THE GREATEST!"),
# Chained filters
'basic-syntax22': ("{{ var|upper|lower }}", {"var": "Django is the greatest!"}, "django is the greatest!"),
'filter-syntax02': ("{{ var|upper|lower }}", {"var": "Django is the greatest!"}, "django is the greatest!"),
# Raise TemplateSyntaxError for space between a variable and filter pipe
'basic-syntax23': ("{{ var |upper }}", {}, template.TemplateSyntaxError),
'filter-syntax03': ("{{ var |upper }}", {}, template.TemplateSyntaxError),
# Raise TemplateSyntaxError for space after a filter pipe
'basic-syntax24': ("{{ var| upper }}", {}, template.TemplateSyntaxError),
'filter-syntax04': ("{{ var| upper }}", {}, template.TemplateSyntaxError),
# Raise TemplateSyntaxError for a nonexistent filter
'basic-syntax25': ("{{ var|does_not_exist }}", {}, template.TemplateSyntaxError),
'filter-syntax05': ("{{ var|does_not_exist }}", {}, template.TemplateSyntaxError),
# Raise TemplateSyntaxError when trying to access a filter containing an illegal character
'basic-syntax26': ("{{ var|fil(ter) }}", {}, template.TemplateSyntaxError),
'filter-syntax06': ("{{ var|fil(ter) }}", {}, template.TemplateSyntaxError),
# Raise TemplateSyntaxError for invalid block tags
'basic-syntax27': ("{% nothing_to_see_here %}", {}, template.TemplateSyntaxError),
'filter-syntax07': ("{% nothing_to_see_here %}", {}, template.TemplateSyntaxError),
# Raise TemplateSyntaxError for empty block tags
'basic-syntax28': ("{% %}", {}, template.TemplateSyntaxError),
'filter-syntax08': ("{% %}", {}, template.TemplateSyntaxError),
# Chained filters, with an argument to the first one
'basic-syntax29': ('{{ var|removetags:"b i"|upper|lower }}', {"var": "<b><i>Yes</i></b>"}, "yes"),
'filter-syntax09': ('{{ var|removetags:"b i"|upper|lower }}', {"var": "<b><i>Yes</i></b>"}, "yes"),
# Escaped string as argument
'basic-syntax30': (r'{{ var|default_if_none:" endquote\" hah" }}', {"var": None}, ' endquote" hah'),
'filter-syntax10': (r'{{ var|default_if_none:" endquote\" hah" }}', {"var": None}, ' endquote" hah'),
# Variable as argument
'basic-syntax31': (r'{{ var|default_if_none:var2 }}', {"var": None, "var2": "happy"}, 'happy'),
'filter-syntax11': (r'{{ var|default_if_none:var2 }}', {"var": None, "var2": "happy"}, 'happy'),
# Default argument testing
'basic-syntax32': (r'{{ var|yesno:"yup,nup,mup" }} {{ var|yesno }}', {"var": True}, 'yup yes'),
'filter-syntax12': (r'{{ var|yesno:"yup,nup,mup" }} {{ var|yesno }}', {"var": True}, 'yup yes'),
# Fail silently for methods that raise an exception with a "silent_variable_failure" attribute
'basic-syntax33': (r'1{{ var.method3 }}2', {"var": SomeClass()}, ("12", "1INVALID2")),
# Fail silently for methods that raise an exception with a
# "silent_variable_failure" attribute
'filter-syntax13': (r'1{{ var.method3 }}2', {"var": SomeClass()}, ("12", "1INVALID2")),
# In methods that raise an exception without a "silent_variable_attribute" set to True,
# the exception propagates
'basic-syntax34': (r'1{{ var.method4 }}2', {"var": SomeClass()}, SomeOtherException),
# In methods that raise an exception without a
# "silent_variable_attribute" set to True, the exception propagates
'filter-syntax14': (r'1{{ var.method4 }}2', {"var": SomeClass()}, SomeOtherException),
# Escaped backslash in argument
'basic-syntax35': (r'{{ var|default_if_none:"foo\bar" }}', {"var": None}, r'foo\bar'),
'filter-syntax15': (r'{{ var|default_if_none:"foo\bar" }}', {"var": None}, r'foo\bar'),
# Escaped backslash using known escape char
'basic-syntax35': (r'{{ var|default_if_none:"foo\now" }}', {"var": None}, r'foo\now'),
'filter-syntax16': (r'{{ var|default_if_none:"foo\now" }}', {"var": None}, r'foo\now'),
# Empty strings can be passed as arguments to filters
'basic-syntax36': (r'{{ var|join:"" }}', {'var': ['a', 'b', 'c']}, 'abc'),
'filter-syntax17': (r'{{ var|join:"" }}', {'var': ['a', 'b', 'c']}, 'abc'),
# Make sure that any unicode strings are converted to bytestrings
# in the final output.
'basic-syntax37': (r'{{ var }}', {'var': UnicodeInStrClass()}, '\xc5\xa0\xc4\x90\xc4\x86\xc5\xbd\xc4\x87\xc5\xbe\xc5\xa1\xc4\x91'),
'filter-syntax18': (r'{{ var }}', {'var': UnicodeInStrClass()}, '\xc5\xa0\xc4\x90\xc4\x86\xc5\xbd\xc4\x87\xc5\xbe\xc5\xa1\xc4\x91'),
### COMMENT SYNTAX ########################################################
'comment-syntax01': ("{# this is hidden #}hello", {}, "hello"),