appy.shared: added support for country codes (iso-3166-1) - appy.gen: non-string variables are now allowed in i18n variable replacements; bugfix while browsing translation pages with the 'next' arrows in 'edit' mode.

This commit is contained in:
Gaetan Delannay 2011-04-26 20:49:33 +02:00
parent 4e848ce0a8
commit 9e7ddcc771
7 changed files with 298 additions and 14 deletions

View file

@ -1 +1 @@
0.6.5
0.6.6

View file

@ -8,7 +8,7 @@ from appy.gen.utils import sequenceTypes, GroupDescr, Keywords, FileWrapper, \
getClassName, SomeObjects
import appy.pod
from appy.pod.renderer import Renderer
from appy.shared.data import languages
from appy.shared.data import countries
from appy.shared.utils import Traceback, getOsTempFolder
# Default Appy permissions -----------------------------------------------------
@ -1066,7 +1066,7 @@ class String(Type):
# Maximum size is 34 chars
if (len(v) < 8) or (len(v) > 34): return False
# 2 first chars must be a valid country code
if not languages.exists(v[:2].lower()): return False
if not countries.exists(v[:2].upper()): return False
# 2 next chars are a control code whose value must be between 0 and 96.
try:
code = int(v[2:4])
@ -1095,7 +1095,7 @@ class String(Type):
for c in value[:4]:
if not letter.match(c): return False
# 2 next chars must be a valid country code
if not languages.exists(value[4:6].lower()): return False
if not countries.exists(value[4:6].upper()): return False
# Last chars represent some location within a country (a city, a
# province...). They can only be letters or figures.
for c in value[6:]:

View file

@ -1245,6 +1245,7 @@ class BaseMixin:
res = self.formatText(res, format)
# Perform variable replacements
for name, repl in mapping.iteritems():
if not isinstance(repl, basestring): repl = str(repl)
res = res.replace('${%s}' % name, repl)
return res

View file

@ -563,8 +563,6 @@
<td width="80%">
<b class="appyTitle" tal:content="contextObj/title_or_id"></b>
</td>
<td><metal:actions use-macro="here/document_actions/macros/document_actions"/>
</td>
</tr>
<tr tal:define="descrLabel python: contextObj.translate('%s_edit_descr' % contextObj.portal_type)"
tal:condition="descrLabel/strip" align="left">

View file

@ -22,9 +22,10 @@ class TranslationWrapper(AbstractWrapper):
else:
sourceMsg = getattr(sourceTranslation,fieldName)
# When editing the value, we don't want HTML code to be interpreted.
# This way, the translator sees the HTML tags and can reproduce them in
# the translation.
if self.request['URL'].endswith('/skyn/edit'):
# This way, the translator sees the HTML tags and can reproduce them
# in the translation.
url = self.request['URL']
if url.endswith('/skyn/edit') or url.endswith('/skyn/do'):
sourceMsg = sourceMsg.replace('<','&lt;').replace('>','&gt;')
sourceMsg = sourceMsg.replace('\n', '<br/>')
return '<div class="translationLabel"><acronym title="%s">' \

View file

@ -0,0 +1,249 @@
AFGHANISTAN;AF
ÅLAND ISLANDS;AX
ALBANIA;AL
ALGERIA;DZ
AMERICAN SAMOA;AS
ANDORRA;AD
ANGOLA;AO
ANGUILLA;AI
ANTARCTICA;AQ
ANTIGUA AND BARBUDA;AG
ARGENTINA;AR
ARMENIA;AM
ARUBA;AW
AUSTRALIA;AU
AUSTRIA;AT
AZERBAIJAN;AZ
BAHAMAS;BS
BAHRAIN;BH
BANGLADESH;BD
BARBADOS;BB
BELARUS;BY
BELGIUM;BE
BELIZE;BZ
BENIN;BJ
BERMUDA;BM
BHUTAN;BT
BOLIVIA, PLURINATIONAL STATE OF;BO
BONAIRE, SAINT EUSTATIUS AND SABA;BQ
BOSNIA AND HERZEGOVINA;BA
BOTSWANA;BW
BOUVET ISLAND;BV
BRAZIL;BR
BRITISH INDIAN OCEAN TERRITORY;IO
BRUNEI DARUSSALAM;BN
BULGARIA;BG
BURKINA FASO;BF
BURUNDI;BI
CAMBODIA;KH
CAMEROON;CM
CANADA;CA
CAPE VERDE;CV
CAYMAN ISLANDS;KY
CENTRAL AFRICAN REPUBLIC;CF
CHAD;TD
CHILE;CL
CHINA;CN
CHRISTMAS ISLAND;CX
COCOS (KEELING) ISLANDS;CC
COLOMBIA;CO
COMOROS;KM
CONGO;CG
CONGO, THE DEMOCRATIC REPUBLIC OF THE;CD
COOK ISLANDS;CK
COSTA RICA;CR
CÔTE D'IVOIRE;CI
CROATIA;HR
CUBA;CU
CURAÇAO;CW
CYPRUS;CY
CZECH REPUBLIC;CZ
DENMARK;DK
DJIBOUTI;DJ
DOMINICA;DM
DOMINICAN REPUBLIC;DO
ECUADOR;EC
EGYPT;EG
EL SALVADOR;SV
EQUATORIAL GUINEA;GQ
ERITREA;ER
ESTONIA;EE
ETHIOPIA;ET
FALKLAND ISLANDS (MALVINAS);FK
FAROE ISLANDS;FO
FIJI;FJ
FINLAND;FI
FRANCE;FR
FRENCH GUIANA;GF
FRENCH POLYNESIA;PF
FRENCH SOUTHERN TERRITORIES;TF
GABON;GA
GAMBIA;GM
GEORGIA;GE
GERMANY;DE
GHANA;GH
GIBRALTAR;GI
GREECE;GR
GREENLAND;GL
GRENADA;GD
GUADELOUPE;GP
GUAM;GU
GUATEMALA;GT
GUERNSEY;GG
GUINEA;GN
GUINEA-BISSAU;GW
GUYANA;GY
HAITI;HT
HEARD ISLAND AND MCDONALD ISLANDS;HM
HOLY SEE (VATICAN CITY STATE);VA
HONDURAS;HN
HONG KONG;HK
HUNGARY;HU
ICELAND;IS
INDIA;IN
INDONESIA;ID
IRAN, ISLAMIC REPUBLIC OF;IR
IRAQ;IQ
IRELAND;IE
ISLE OF MAN;IM
ISRAEL;IL
ITALY;IT
JAMAICA;JM
JAPAN;JP
JERSEY;JE
JORDAN;JO
KAZAKHSTAN;KZ
KENYA;KE
KIRIBATI;KI
KOREA, DEMOCRATIC PEOPLE'S REPUBLIC OF;KP
KOREA, REPUBLIC OF;KR
KUWAIT;KW
KYRGYZSTAN;KG
LAO PEOPLE'S DEMOCRATIC REPUBLIC;LA
LATVIA;LV
LEBANON;LB
LESOTHO;LS
LIBERIA;LR
LIBYAN ARAB JAMAHIRIYA;LY
LIECHTENSTEIN;LI
LITHUANIA;LT
LUXEMBOURG;LU
MACAO;MO
MACEDONIA, THE FORMER YUGOSLAV REPUBLIC OF;MK
MADAGASCAR;MG
MALAWI;MW
MALAYSIA;MY
MALDIVES;MV
MALI;ML
MALTA;MT
MARSHALL ISLANDS;MH
MARTINIQUE;MQ
MAURITANIA;MR
MAURITIUS;MU
MAYOTTE;YT
MEXICO;MX
MICRONESIA, FEDERATED STATES OF;FM
MOLDOVA, REPUBLIC OF;MD
MONACO;MC
MONGOLIA;MN
MONTENEGRO;ME
MONTSERRAT;MS
MOROCCO;MA
MOZAMBIQUE;MZ
MYANMAR;MM
NAMIBIA;NA
NAURU;NR
NEPAL;NP
NETHERLANDS;NL
NEW CALEDONIA;NC
NEW ZEALAND;NZ
NICARAGUA;NI
NIGER;NE
NIGERIA;NG
NIUE;NU
NORFOLK ISLAND;NF
NORTHERN MARIANA ISLANDS;MP
NORWAY;NO
OMAN;OM
PAKISTAN;PK
PALAU;PW
PALESTINIAN TERRITORY, OCCUPIED;PS
PANAMA;PA
PAPUA NEW GUINEA;PG
PARAGUAY;PY
PERU;PE
PHILIPPINES;PH
PITCAIRN;PN
POLAND;PL
PORTUGAL;PT
PUERTO RICO;PR
QATAR;QA
RÉUNION;RE
ROMANIA;RO
RUSSIAN FEDERATION;RU
RWANDA;RW
SAINT BARTHÉLEMY;BL
SAINT HELENA, ASCENSION AND TRISTAN DA CUNHA;SH
SAINT KITTS AND NEVIS;KN
SAINT LUCIA;LC
SAINT MARTIN (FRENCH PART);MF
SAINT PIERRE AND MIQUELON;PM
SAINT VINCENT AND THE GRENADINES;VC
SAMOA;WS
SAN MARINO;SM
SAO TOME AND PRINCIPE;ST
SAUDI ARABIA;SA
SENEGAL;SN
SERBIA;RS
SEYCHELLES;SC
SIERRA LEONE;SL
SINGAPORE;SG
SINT MAARTEN (DUTCH PART);SX
SLOVAKIA;SK
SLOVENIA;SI
SOLOMON ISLANDS;SB
SOMALIA;SO
SOUTH AFRICA;ZA
SOUTH GEORGIA AND THE SOUTH SANDWICH ISLANDS;GS
SPAIN;ES
SRI LANKA;LK
SUDAN;SD
SURINAME;SR
SVALBARD AND JAN MAYEN;SJ
SWAZILAND;SZ
SWEDEN;SE
SWITZERLAND;CH
SYRIAN ARAB REPUBLIC;SY
TAIWAN, PROVINCE OF CHINA;TW
TAJIKISTAN;TJ
TANZANIA, UNITED REPUBLIC OF;TZ
THAILAND;TH
TIMOR-LESTE;TL
TOGO;TG
TOKELAU;TK
TONGA;TO
TRINIDAD AND TOBAGO;TT
TUNISIA;TN
TURKEY;TR
TURKMENISTAN;TM
TURKS AND CAICOS ISLANDS;TC
TUVALU;TV
UGANDA;UG
UKRAINE;UA
UNITED ARAB EMIRATES;AE
UNITED KINGDOM;GB
UNITED STATES;US
UNITED STATES MINOR OUTLYING ISLANDS;UM
URUGUAY;UY
UZBEKISTAN;UZ
VANUATU;VU
VENEZUELA, BOLIVARIAN REPUBLIC OF;VE
VIET NAM;VN
VIRGIN ISLANDS, BRITISH;VG
VIRGIN ISLANDS, U.S.;VI
WALLIS AND FUTUNA;WF
WESTERN SAHARA;EH
YEMEN;YE
ZAMBIA;ZM
ZIMBABWE;ZW

View file

@ -162,9 +162,10 @@ nativeNames = {
}
# ------------------------------------------------------------------------------
class Languages:
'''This class gives access to the language codes as standardized by
ISO-639. The file has been downloaded in July 2009 from
'''This class gives access to the language codes and names as standardized
by ISO-639. The file has been downloaded in July 2009 from
http://www.loc.gov/standards/iso639-2/ascii_8bits.html (UTF-8 version)'''
def __init__(self):
self.fileName = os.path.dirname(__file__) + '/LanguageCodesIso639.2.txt'
self.languageCodes = []
@ -194,7 +195,7 @@ class Languages:
f.close()
def exists(self, code):
'''Is p_code a valid 2-digits language/country code?'''
'''Is p_code a valid 2-digits language code?'''
return code in self.languageCodes
def get(self, code):
@ -214,7 +215,39 @@ class Languages:
res += 'Language: ' + languageCode + ' - ' + self.languageNames[i]
res += '\n'
return res
languages = Languages() # As this is international, I instantiate it.
# We instantiate here Languages because it is used by the appy.gen languages
# management.
languages = Languages()
# Country codes ISO 3166-1. ----------------------------------------------------
class Countries:
'''This class gives access to the country codes and names as standardized by
ISO 3166-1. The file has been downloaded in March 2011 from
http://www.iso.org/iso/country_codes/iso_3166_code_lists.htm
(first line has been removed).'''
def __init__(self):
self.fileName = os.path.dirname(__file__) + '/CountryCodesIso3166.1.txt'
self.countryCodes = []
# Names of countries in English
self.countryNames = []
self.parseFile()
def parseFile(self):
f = file(self.fileName)
for line in f:
if line.strip():
name, code = line.split(';')
self.countryCodes.append(code.strip())
self.countryNames.append(name.strip())
f.close()
def exists(self, code):
'''Is p_code a valid 2-digits country code?'''
return code in self.countryCodes
# We instantiate here Countries because it is used by appy.gen for some field
# validations.
countries = Countries()
# ------------------------------------------------------------------------------
class BelgianCities:
@ -224,18 +257,20 @@ class BelgianCities:
https://www.post.be/site/fr/sse/advertising/addressed/biblio.html,
converted to CSV (field separator being ";" field content is surrrounded
by double quotes).'''
def __init__(self):
self.fileName = os.path.dirname(__file__) + '/BelgianCommunes.txt'
self.data = {}
self.parseFile()
def parseFile(self):
f = file(self.fileName)
for line in f:
if line.strip():
lineElems = line.split(';')
self.data[int(lineElems[0].strip('"'))]= lineElems[1].strip('"')
def exists(self, postalCode):
'''Is postalCode a valid Belgian postal code?'''
return self.data.has_key(postalCode)
# As this is not international, Appy user will instantiate it if needed.
# ------------------------------------------------------------------------------