Специальный виджет выбора, возвращающий ошибки формы при отправке («нет данных») - PullRequest
1 голос
/ 13 декабря 2011

Мне нужна помощь для корректной работы виджета в приложении web2py.Кстати, после исправления я думаю, что это может быть полезно для других пользователей ...

Я создал виджет SELECT, чтобы отображать регионы и их субрегионы («отдел»), чтобы пользователь мог иметьвыбор.Например: регион А делится на департамент 11 и департамент 12 и так далее.Пользователь может выбрать либо регион, либо определенный департамент (субрегион).

Виджет работает правильно, за исключением того, что при отправке форма возвращает ошибки: form.errors: "r_name: no data".Ниже приведен рабочий пример, показывающий проблему.

Может ли кто-нибудь помочь мне правильно настроить этот виджет, не возвращая ошибок, пожалуйста.Поскольку я не понимаю, в чём дело ... Я был бы очень признателен за вашу помощь.Заранее большое спасибо.Извините за форматирование, но я впервые публикую здесь ...;)

Доминик

в модели:

     db.define_table('region',
Field('r_name', 'string', length=250, required=True)
)  
db.define_table('departement',
Field('d_name', 'string', length=250, required=True),
Field('d_code', 'string', length=3, required=True),
Field('d_region', db.region)
)
db.define_table('region',
Field('r_name', 'string', length=250, required=True)
)  
db.define_table('departement',
Field('d_name', 'string', length=250, required=True),
Field('d_code', 'string', length=3, required=True),
Field('d_region', db.region)
)

def region_widget(f,v,_class= "options"):
"""
Widget  that shows regions and departements in a SELECT.
Can be used with SQLFORM and SQLFORM.factory
Usage:
db.region.r_name.widget = region_dptt_select_widget
"""
region_dptt = db(db.region.id==db.departement.d_region)\
                .select(db.region.r_name, db.region.id, db.departement.d_name, db.departement.d_code, db.departement.id, \
                orderby=db.region.r_name, cache=(cache.ram,6))

   def prepare_select(rows):
    """
    Creates a list of tuples to be used in the SELECT helper:
    ['Region A', OPTGROUP('SubRegion 1','SubRegion 2', 'SubRegion 3'),
    'Region B', OPTGROUP('SubRegion 4','SubRegion 5', 'SubRegion 6')]
    """
    l_r=[]
    for row in rows:
        r = row.region.r_name
        if row.region.r_name not in l_r:
            l_r.append(row.region.r_name)
    interm_list=[]
    for reg in l_r:
       l_sr=[]
       for row in rows:
            if reg == row.region.r_name:
                reg_id = row.region.id
                dep = row.departement.d_code + ' ' + row.departement.d_name
                dep_id = row.departement.id
                l_sr.append(OPTION(dep,_value=row.departement.d_code)) 
       option_reg = OPTION(reg, _value= 'R'+str(reg_id))
       interm_list.append((option_reg,l_sr))
    res=[]
    for reg, l_sr in interm_list:
        res.append(reg)
        res.append(OPTGROUP(*l_sr))
    return res
return SELECT(*prepare_select(region_dptt),
              **dict(_name='region_to_search', _value=v, _id='region_to_search', _type = 'string', _class="options"))

в контроллере:

  def test():
db.region.r_name.widget = region_widget
fields=['r_name']
labels = {'r_name':T('')}
form= SQLFORM(db.region, fields = fields, labels = labels)
a=None
if form.accepts(request.vars, session, formname='test_form', dbio=False):
    a = form.vars
elif form.errors:
    a = form.errors
return dict(form=form, a = a)

def insertions():# TO RUN one time to fill regions and departments in the db
db.region.insert(r_name="Region A")
db.region.insert(r_name="Region B")
db.departement.insert(d_name="SubRegion 1", d_code="11", d_region=1)
db.departement.insert(d_name="SubRegion 2", d_code="12",  d_region=1)
db.departement.insert(d_name="SubRegion 3", d_code="21",  d_region=2)
db.departement.insert(d_name="SubRegion 4", d_code="22",  d_region=2)
db.departement.insert(d_name="SubRegion 5", d_code="25",  d_region=2)
db.departement.insert(d_name="SubRegion 6", d_code="26",  d_region=2) 

1 Ответ

1 голос
/ 13 декабря 2011

Ваш виджет устанавливает _name='region_to_search', но SQLFORM ожидает, что имя поля ввода формы (и, следовательно, связанная переменная в request.vars) будет таким же, как имя поля в таблице базы данных, используемой для генерации формы (котораяэто 'r_name').Итак, попробуйте изменить код вашего виджета на _name='r_name'.

...