From a6909d0cc0960163d00d5065fb4df50fbf1e0882 Mon Sep 17 00:00:00 2001 From: "pap (openerp)" Date: Wed, 20 Jan 2010 18:14:10 +0530 Subject: [PATCH 01/59] [IMP:moved _check_dates function from module project_long_term to module project] bzr revid: pap@tinyerp.co.in-20100120124410-gl06rvx06c4vo1xw --- addons/project/project.py | 17 ++++++++++------- addons/project_long_term/project.py | 11 ----------- 2 files changed, 10 insertions(+), 18 deletions(-) diff --git a/addons/project/project.py b/addons/project/project.py index 89cf75e454c..0865c24857b 100644 --- a/addons/project/project.py +++ b/addons/project/project.py @@ -324,13 +324,13 @@ class task(osv.osv): default['work_ids'] = [] return super(task, self).copy_data(cr, uid, id, default, context) - def _check_date(self,cr,uid,ids): - for res in self.browse(cr,uid,ids): - if res.date_start and res.date_end: - if res.date_start > res.date_end: - return False - return True - + def _check_dates(self, cr, uid, ids): + task = self.read(cr, uid, ids[0],['date_start','date_end']) + if task['date_start'] and task['date_end']: + if task['date_start'] > task['date_end']: + return False + return True + _columns = { 'active': fields.boolean('Active', help="If the active field is set to true, it will allow you to hide the task without removing it."), 'name': fields.char('Task summary', size=128, required=True), @@ -380,6 +380,9 @@ class task(osv.osv): } _order = "sequence, priority, date_deadline, id" + _constraints = [ + (_check_dates, 'Error! task start-date must be lower then task end-date.', ['date_start', 'date_end']) + ] # # Override view according to the company definition # diff --git a/addons/project_long_term/project.py b/addons/project_long_term/project.py index c5734263ea5..3f16b33ea31 100644 --- a/addons/project_long_term/project.py +++ b/addons/project_long_term/project.py @@ -125,17 +125,6 @@ class task(osv.osv): _columns = { 'phase_id': fields.many2one('project.phase', 'Project Phase') } - def _check_dates(self, cr, uid, ids): - leave = self.read(cr, uid, ids[0],['date_start','date_end']) - if leave['date_start'] and leave['date_end']: - if leave['date_start'] > leave['date_end']: - return False - return True - - _constraints = [ - (_check_dates, 'Error! task start-date must be lower then task end-date.', ['date_start', 'date_end']) - ] - task() # vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4: From 4dcbc1429d44df4378eadbba80d2c3d395ccda7c Mon Sep 17 00:00:00 2001 From: "sbh (Open ERP)" Date: Wed, 27 Jan 2010 16:25:59 +0530 Subject: [PATCH 02/59] [IMP] document_change: Modfify the action of Coverage Analysis bzr revid: sbh@tinyerp.com-20100127105559-ahwz675u6wo93soq --- addons/document_change/document_change_view.xml | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/addons/document_change/document_change_view.xml b/addons/document_change/document_change_view.xml index 29004fd42b7..8be74cdcd9a 100644 --- a/addons/document_change/document_change_view.xml +++ b/addons/document_change/document_change_view.xml @@ -733,8 +733,10 @@ ir.actions.act_window document.change.report form - graph + graph,tree + + board.document.change.form board.board From 936f5e53f333a7436f345dc3199a71746ee0580b Mon Sep 17 00:00:00 2001 From: "sbh (Open ERP)" Date: Wed, 27 Jan 2010 16:52:59 +0530 Subject: [PATCH 03/59] [Fix] document_change: remove date column for document_change report bzr revid: sbh@tinyerp.com-20100127112259-ysf5iny64ymodoon --- addons/document_change/document_change_report.py | 1 - 1 file changed, 1 deletion(-) diff --git a/addons/document_change/document_change_report.py b/addons/document_change/document_change_report.py index 20c5a5993ba..e6a766ba695 100644 --- a/addons/document_change/document_change_report.py +++ b/addons/document_change/document_change_report.py @@ -52,7 +52,6 @@ class document_change_report(osv.osv): 'level': fields.integer('Level', readonly=True), 'amount_required': fields.function(_amount_all, method=True, string='Required', multi='sums', type='integer'), - 'date': fields.date('Date', readonly=True), 'amount_exist': fields.function(_amount_all, method=True, string='Existing', multi='sums', type='integer'), 'amount_percent': fields.function(_amount_all, method=True, From cb5b75b569d8542772fb03f9442335bc77df86d4 Mon Sep 17 00:00:00 2001 From: "rpa (Open ERP)" Date: Wed, 27 Jan 2010 18:49:41 +0530 Subject: [PATCH 04/59] [FIX]: base_calendar, caldav: Fixed problem of wrong attribute value in attendee and put proper email and cn value while importing ics file with attendee data bzr revid: rpa@openerp.co.in-20100127131941-gubmtane9u92wi1s --- addons/base_calendar/base_calendar.py | 34 +++++++++++++++++---------- addons/caldav/caldav.py | 9 +++++++ addons/caldav/caldav_view.xml | 4 ++++ 3 files changed, 35 insertions(+), 12 deletions(-) diff --git a/addons/base_calendar/base_calendar.py b/addons/base_calendar/base_calendar.py index 9260d9c0730..168da55eaf7 100644 --- a/addons/base_calendar/base_calendar.py +++ b/addons/base_calendar/base_calendar.py @@ -27,6 +27,7 @@ from tools.translate import _ import base64 import pooler import re +import tools import vobject # O-1 Optional and can come only once @@ -84,7 +85,7 @@ def get_attribute_mapping(cr, uid, calname, context={}): if not res.get('uid', None): res['uid'] = {} res['uid']['field'] = 'id' - res[attr]['type'] = "integer" + res['uid']['type'] = "integer" return res def map_data(cr, uid, obj): @@ -170,12 +171,15 @@ class CalDAV(object): self.__attribute__[name][type] = None return True - def parse_ics(self, cr, uid, child): + def parse_ics(self, cr, uid, child, cal_children=None, context=None): att_data = [] for cal_data in child.getChildren(): if cal_data.name.lower() == 'attendee': + ctx = context.copy() + if cal_children: + ctx.update({'model': cal_children[cal_data.name.lower()]}) attendee = self.pool.get('basic.calendar.attendee') - att_data.append(attendee.import_cal(cr, uid, cal_data)) + att_data.append(attendee.import_cal(cr, uid, cal_data, context=ctx)) self.ical_set(cal_data.name.lower(), att_data, 'value') continue if cal_data.name.lower() == 'valarm': @@ -230,7 +234,7 @@ class CalDAV(object): data[map_field][0], vevent, context=context) elif data[map_field]: if map_type in ("char", "text"): - vevent.add(field).value = str(data[map_field].encode('utf8')) + vevent.add(field).value = tools.ustr(data[map_field]) elif map_type in ('datetime', 'date') and data[map_field]: if field in ('exdate'): vevent.add(field).value = [parser.parse(data[map_field])] @@ -239,12 +243,12 @@ class CalDAV(object): elif map_type == "timedelta": vevent.add(field).value = timedelta(hours=data[map_field]) elif map_type == "many2one": - vevent.add(field).value = (data.get(map_field)[1]).encode('utf8') + vevent.add(field).value = tools.ustr(data.get(map_field)[1]) elif map_type in ("float", "integer"): vevent.add(field).value = str(data.get(map_field)) elif map_type == "selection": if not self.ical_get(field, 'mapping'): - vevent.add(field).value = (data[map_field].encode('utf8')).upper() + vevent.add(field).value = (tools.ustr(data[map_field])).upper() else: for key1, val1 in self.ical_get(field, 'mapping').items(): if val1 == data[map_field]: @@ -291,7 +295,7 @@ class CalDAV(object): res = [] for child in parsedCal.getChildren(): if child.name.lower() in ('vevent', 'vtodo'): - vals = self.parse_ics(cr, uid, child) + vals = self.parse_ics(cr, uid, child, context=context) else: vals = {} continue @@ -359,7 +363,7 @@ class Calendar(CalDAV, osv.osv): if child.name.lower() in cal_children: context.update({'model': cal_children[child.name.lower()]}) self.__attribute__ = get_attribute_mapping(cr, uid, child.name.lower(), context=context) - val = self.parse_ics(cr, uid, child) + val = self.parse_ics(cr, uid, child, cal_children=cal_children, context=context) obj = self.pool.get(cal_children[child.name.lower()]) if hasattr(obj, 'check_import'): obj.check_import(cr, uid, [val], context=context) @@ -638,7 +642,10 @@ class Attendee(CalDAV, osv.osv_memory): 'language': None, # Use: 0-1 Specify the language for text values in a property or property parameter. } - def import_cal(self, cr, uid, ical_data): + def import_cal(self, cr, uid, ical_data, context=None): + ctx = context.copy() + ctx.update({'model': context.get('model', None)}) + self.__attribute__ = get_attribute_mapping(cr, uid, self._calname, ctx) for para in ical_data.params: if para.lower() == 'cn': self.ical_set(para.lower(), ical_data.params[para][0]+':'+ \ @@ -652,7 +659,9 @@ class Attendee(CalDAV, osv.osv_memory): def export_cal(self, cr, uid, model, attendee_ids, vevent, context={}): attendee_object = self.pool.get(model) - self.__attribute__ = get_attribute_mapping(cr, uid, self._calname, context) + ctx = context.copy() + ctx.update({'model': model}) + self.__attribute__ = get_attribute_mapping(cr, uid, self._calname, ctx) for attendee in attendee_object.read(cr, uid, attendee_ids, []): attendee_add = vevent.add('attendee') cn_val = '' @@ -662,9 +671,10 @@ class Attendee(CalDAV, osv.osv_memory): attendee_add.params[a_key] = [str(attendee[a_val['field']])] elif a_val['type'] == 'boolean': attendee_add.params[a_key] = [str(attendee[a_val['field']])] - if a_val['field'] == 'cn': + if a_val['field'] == 'cn' and attendee[a_val['field']]: cn_val = [str(attendee[a_val['field']])] - attendee_add.params['CN'] = cn_val + if cn_val: + attendee_add.params['CN'] = cn_val return vevent Attendee() diff --git a/addons/caldav/caldav.py b/addons/caldav/caldav.py index 450b3a2bdd9..2d988456da2 100644 --- a/addons/caldav/caldav.py +++ b/addons/caldav/caldav.py @@ -215,6 +215,15 @@ request was delegated to"), def do_decline(self, cr, uid, ids, context=None, *args): self.write(cr, uid, ids, {'state': 'declined'}, context) + def create(self, cr, uid, vals, context={}): + if not vals.get("email") and vals.get("cn"): + cnval = vals.get("cn").split(':') + email = filter(lambda x:x.__contains__('@'), cnval) + vals['email'] = email[0] + vals['cn'] = vals.get("cn") + res = super(calendar_attendee, self).create(cr, uid, vals, context) + return res + calendar_attendee() class res_alarm(osv.osv): diff --git a/addons/caldav/caldav_view.xml b/addons/caldav/caldav_view.xml index 06050f03b5a..559c45485cc 100644 --- a/addons/caldav/caldav_view.xml +++ b/addons/caldav/caldav_view.xml @@ -260,5 +260,9 @@ new + + From f88791536c8f191348fa7d541a24dd0bf1618d76 Mon Sep 17 00:00:00 2001 From: apa-tiny Date: Wed, 27 Jan 2010 19:25:23 +0530 Subject: [PATCH 05/59] [IMP] Survey:-Improvement in view and code. ref-YSA bzr revid: apa@tinyerp.com-20100127135523-kra22c2hy0w97o67 --- .../survey/report/survey_analysis_report.py | 6 +- .../survey/report/survey_browse_response.py | 416 ++++--- addons/survey/report/survey_form.py | 6 +- addons/survey/survey.py | 134 +- addons/survey/survey_report.xml | 1 - addons/survey/survey_view.xml | 1075 +++++++++-------- addons/survey/survey_wizard.xml | 3 + addons/survey/wizard/__init__.py | 1 + 8 files changed, 872 insertions(+), 770 deletions(-) diff --git a/addons/survey/report/survey_analysis_report.py b/addons/survey/report/survey_analysis_report.py index b7b2dad634f..ffb01093501 100755 --- a/addons/survey/report/survey_analysis_report.py +++ b/addons/survey/report/survey_analysis_report.py @@ -100,10 +100,6 @@ class survey_analysis(report_rml): """ surv_obj = pooler.get_pool(cr.dbname).get('survey') for survey in surv_obj.browse(cr, uid, ids): - if survey.question_prefix: - prefix = survey.question_prefix + " : " - else: - prefix = '' rml += """ @@ -139,7 +135,7 @@ class survey_analysis(report_rml): for que in page.question_ids: rml +=""" - """ + to_xml(tools.ustr(prefix)) + to_xml(tools.ustr(que.question)) + """ + Que : """ + to_xml(tools.ustr(que.question)) + """ """ cols_widhts = [] diff --git a/addons/survey/report/survey_browse_response.py b/addons/survey/report/survey_browse_response.py index 93b9ec011f6..3b60d3fbdf7 100644 --- a/addons/survey/report/survey_browse_response.py +++ b/addons/survey/report/survey_browse_response.py @@ -131,224 +131,222 @@ class survey_browse_response(report_rml): """ surv_resp_obj = pooler.get_pool(cr.dbname).get('survey.response') + if datas.has_key('form') and datas['form'].has_key('response_ids'): + response_id = datas['form']['response_ids'][0][2] + elif context.has_key('response_id'): + response_id = [int(context['response_id'])] + else: + response_id = surv_resp_obj.search(cr, uid, [('survey_id','in',ids)]) surv_resp_line_obj = pooler.get_pool(cr.dbname).get('survey.response.line') surv_obj = pooler.get_pool(cr.dbname).get('survey') - for id in ids: - for survey in surv_obj.browse(cr, uid, [id]): - if context.has_key('response_id'): - s_id = [int(context['response_id'])] - else: - s_id = surv_resp_obj.search(cr,uid, [('survey_id','=',[survey.id])]) - for response in surv_resp_obj.browse(cr,uid,s_id): #surv_resp_obj.search(cr,uid, [('survey_id','=',ids[0])]) - if survey.question_prefix: - prefix = survey.question_prefix + " : " - else: - prefix = '' - rml += """ - - - Survey Title - - - Response Create Date - - - Respose By - - - - - - - """ + to_xml(tools.ustr(survey.title)) + """ - - - """ + to_xml(time.strftime('%d-%m-%Y %I:%M:%S %p', time.strptime(response.date_create.split('.')[0], '%Y-%m-%d %H:%M:%S'))) + """ - - - """ + to_xml(response.user_id.name) + """ - - - """ - for page in survey.page_ids: + for response in surv_resp_obj.browse(cr,uid, response_id): + for survey in surv_obj.browse(cr, uid, [response.survey_id.id]): + rml += """ + + + Survey Title + + + Response Create Date + + + Respose By + + + + + + + """ + to_xml(tools.ustr(survey.title)) + """ + + + """ + to_xml(time.strftime('%d-%m-%Y %I:%M:%S %p', time.strptime(response.date_create.split('.')[0], '%Y-%m-%d %H:%M:%S'))) + """ + + + """ + to_xml(response.user_id.name) + """ + + + """ + for page in survey.page_ids: + rml += """ + + + Page :- """ + to_xml(tools.ustr(page.title)) + """ + + """ + for que in page.question_ids: rml += """ - - - Page :- """ + to_xml(tools.ustr(page.title)) + """ - - """ - for que in page.question_ids: - rml += """ - - - """ + to_xml(tools.ustr(prefix)) + to_xml(to_xml(que.question)) + """ - - """ - answer = surv_resp_line_obj.browse(cr,uid, surv_resp_line_obj.search(cr, uid, [('question_id','=',que.id),('response_id','=',response.id)])) - if que.type in ['descriptive_text']: - rml +=""" - """ + to_xml(tools.ustr(que.descriptive_text)) + """ - """ - elif que.type in ['table']: - if len(answer) and answer[0].state == "done": - col_heading = pooler.get_pool(cr.dbname).get('survey.tbl.column.heading') - cols_widhts = [] - for col in range(0, len(que.column_heading_ids)): - cols_widhts.append(float(500 / (len(que.column_heading_ids)))) - colWidths = ",".join(map(tools.ustr, cols_widhts)) - matrix_ans = [] - rml +="""""" - for col in que.column_heading_ids: - if col.title not in matrix_ans: - matrix_ans.append(col.title) - rml +=""" """ + to_xml(tools.ustr(col.title)) +"""""" + + + Que : """ + to_xml(to_xml(que.question)) + """ + + """ + answer = surv_resp_line_obj.browse(cr,uid, surv_resp_line_obj.search(cr, uid, [('question_id','=',que.id),('response_id','=',response.id)])) + if que.type in ['descriptive_text']: + rml +=""" + """ + to_xml(tools.ustr(que.descriptive_text)) + """ + """ + elif que.type in ['table']: + if len(answer) and answer[0].state == "done": + col_heading = pooler.get_pool(cr.dbname).get('survey.tbl.column.heading') + cols_widhts = [] + for col in range(0, len(que.column_heading_ids)): + cols_widhts.append(float(500 / (len(que.column_heading_ids)))) + colWidths = ",".join(map(tools.ustr, cols_widhts)) + matrix_ans = [] + rml +="""""" + for col in que.column_heading_ids: + if col.title not in matrix_ans: + matrix_ans.append(col.title) + rml +=""" """ + to_xml(tools.ustr(col.title)) +"""""" + rml += """""" + for row in range(0, que.no_of_rows): + rml +="""""" + table_data = col_heading.browse(cr, uid, col_heading.search(cr, uid, [('response_table_id', '=', answer[0].id),('name','=',row)])) + for column in matrix_ans: + value = """ """ + for col in table_data: + if column == col.column_id.title: + value = col.value + rml += """ """ + to_xml(tools.ustr(value)) +"""""" rml += """""" - for row in range(0, que.no_of_rows): - rml +="""""" - table_data = col_heading.browse(cr, uid, col_heading.search(cr, uid, [('response_table_id', '=', answer[0].id),('name','=',row)])) - for column in matrix_ans: - value = """ """ - for col in table_data: - if column == col.column_id.title: - value = col.value - rml += """ """ + to_xml(tools.ustr(value)) +"""""" - rml += """""" - else: + else: + rml +=""" + No Response + """ + elif que.type in ['multiple_choice_only_one_ans','multiple_choice_multiple_ans']: + if len(answer) and answer[0].state == "done": + for ans in answer[0].response_answer_ids: rml +=""" - No Response - """ - elif que.type in ['multiple_choice_only_one_ans','multiple_choice_multiple_ans']: - if len(answer) and answer[0].state == "done": - for ans in answer[0].response_answer_ids: - rml +=""" - """ + to_xml(tools.ustr(ans.answer_id.answer)) + """ - """ - if que.comment_field_type: - if answer[0].comment: - rml+=""" - """ + to_xml(tools.ustr(answer[0].comment)) + """""" - else: - rml +=""" - No Response - """ - elif que.type in ['multiple_textboxes','date','date_and_time','numerical_textboxes']: - if len(answer) and answer[0].state == "done": - for ans in answer[0].response_answer_ids: - rml +=""" - """ + to_xml(tools.ustr(ans.answer_id.answer)) + """ - """ + to_xml(tools.ustr(ans.answer)) + """ - """ - else: - rml +=""" - No Response - """ - elif que.type in ['single_textbox']: - if len(answer) and answer[0].state == "done": - rml +=""" - """ + to_xml(tools.ustr(answer[0].single_text)) + """ + """ + to_xml(tools.ustr(ans.answer_id.answer)) + """ """ - else: - rml +=""" - No Response - """ - elif que.type in ['comment']: - if len(answer) and answer[0].state == "done": - rml +=""" - """ + to_xml(tools.ustr(answer[0].comment)) + """ - """ - else: - rml +=""" - No Response - """ - elif que.type in ['matrix_of_choices_only_one_ans','matrix_of_choices_only_multi_ans','rating_scale','matrix_of_drop_down_menus']: - if len(answer) and answer[0].state == "done": - if que.comment_column: - pass - cols_widhts = [] - cols_widhts.append(200) - len_col_heading = len(que.column_heading_ids) - for col in range(0, len_col_heading): - cols_widhts.append(float(300 / len_col_heading)) - tmp=0.0 - sum = 0.0 - i = 0 - if que.comment_column: - for col in cols_widhts: - if i==0: - cols_widhts[i] = cols_widhts[i]/2.0 - tmp = cols_widhts[i] - sum += col - i+=1 - cols_widhts.append(round(tmp,2)) - colWidths = ",".join(map(tools.ustr, cols_widhts)) - matrix_ans = ['',] - for col in que.column_heading_ids: - if col.title not in matrix_ans: - matrix_ans.append(col.title) - len_matrix = len(matrix_ans) - if que.comment_column: - matrix_ans.append(que.column_name) - rml+="""""" - for mat_col in matrix_ans: - rml+="""""" + to_xml(tools.ustr(mat_col)) + """""" - rml +="""""" - rml+="""""" - i=0 - for ans in que.answer_choice_ids: - if i%2!=0: - style='ans_tbl_white' - else: - style='ans_tbl_gainsboro' - i+=1 - rml+=""" - """ + to_xml(tools.ustr(ans.answer)) + """""" - comment_value = "" - for mat_col in range(1, len_matrix): - value = """""" - for res_ans in answer[0].response_answer_ids: - if res_ans.answer_id.id == ans.id and res_ans.answer == matrix_ans[mat_col]: - comment_value = to_xml(tools.ustr(res_ans.comment_field)) - if que.type in ['matrix_of_drop_down_menus']: - value = """""" + to_xml(tools.ustr(res_ans.value_choice)) + """""" - elif que.type in ['matrix_of_choices_only_one_ans','rating_scale']: - value = """ - - - - """ - elif que.type in ['matrix_of_choices_only_multi_ans']: - value = """ - - - - - """ - break - else: - if que.type in ['matrix_of_drop_down_menus']: - value = """""" - elif que.type in ['matrix_of_choices_only_one_ans','rating_scale']: - value = """ - - """ - elif que.type in ['matrix_of_choices_only_multi_ans']: - value = """ - - """ - rml+= """""" + value + """""" - if que.comment_column: - if comment_value=='False': - comment_value = '' - rml+= """"""+ to_xml(tools.ustr(comment_value)) + """""" - rml+=""" """ - if que.comment_field_type: + if que.comment_field_type: + if answer[0].comment: rml+=""" """ + to_xml(tools.ustr(answer[0].comment)) + """""" - else: - rml +=""" - No Response + else: + rml +=""" + No Response + """ + elif que.type in ['multiple_textboxes','date','date_and_time','numerical_textboxes']: + if len(answer) and answer[0].state == "done": + for ans in answer[0].response_answer_ids: + rml +=""" + """ + to_xml(tools.ustr(ans.answer_id.answer)) + """ + """ + to_xml(tools.ustr(ans.answer)) + """ + """ + else: + rml +=""" + No Response + """ + elif que.type in ['single_textbox']: + if len(answer) and answer[0].state == "done": + rml +=""" + """ + to_xml(tools.ustr(answer[0].single_text)) + """ """ - rml += """""" + else: + rml +=""" + No Response + """ + elif que.type in ['comment']: + if len(answer) and answer[0].state == "done": + rml +=""" + """ + to_xml(tools.ustr(answer[0].comment)) + """ + """ + else: + rml +=""" + No Response + """ + elif que.type in ['matrix_of_choices_only_one_ans','matrix_of_choices_only_multi_ans','rating_scale','matrix_of_drop_down_menus']: + if len(answer) and answer[0].state == "done": + if que.comment_column: + pass + cols_widhts = [] + cols_widhts.append(200) + len_col_heading = len(que.column_heading_ids) + for col in range(0, len_col_heading): + cols_widhts.append(float(300 / len_col_heading)) + tmp=0.0 + sum = 0.0 + i = 0 + if que.comment_column: + for col in cols_widhts: + if i==0: + cols_widhts[i] = cols_widhts[i]/2.0 + tmp = cols_widhts[i] + sum += col + i+=1 + cols_widhts.append(round(tmp,2)) + colWidths = ",".join(map(tools.ustr, cols_widhts)) + matrix_ans = ['',] + for col in que.column_heading_ids: + if col.title not in matrix_ans: + matrix_ans.append(col.title) + len_matrix = len(matrix_ans) + if que.comment_column: + matrix_ans.append(que.column_name) + rml+="""""" + for mat_col in matrix_ans: + rml+="""""" + to_xml(tools.ustr(mat_col)) + """""" + rml +="""""" + rml+="""""" + i=0 + for ans in que.answer_choice_ids: + if i%2!=0: + style='ans_tbl_white' + else: + style='ans_tbl_gainsboro' + i+=1 + rml+=""" + """ + to_xml(tools.ustr(ans.answer)) + """""" + comment_value = "" + for mat_col in range(1, len_matrix): + value = """""" + for res_ans in answer[0].response_answer_ids: + if res_ans.answer_id.id == ans.id and res_ans.answer == matrix_ans[mat_col]: + comment_value = to_xml(tools.ustr(res_ans.comment_field)) + if que.type in ['matrix_of_drop_down_menus']: + value = """""" + to_xml(tools.ustr(res_ans.value_choice)) + """""" + elif que.type in ['matrix_of_choices_only_one_ans','rating_scale']: + value = """ + + + + """ + elif que.type in ['matrix_of_choices_only_multi_ans']: + value = """ + + + + + """ + break + else: + if que.type in ['matrix_of_drop_down_menus']: + value = """""" + elif que.type in ['matrix_of_choices_only_one_ans','rating_scale']: + value = """ + + """ + elif que.type in ['matrix_of_choices_only_multi_ans']: + value = """ + + """ + rml+= """""" + value + """""" + if que.comment_column: + if comment_value=='False': + comment_value = '' + rml+= """"""+ to_xml(tools.ustr(comment_value)) + """""" + rml+=""" """ + if que.comment_field_type: + rml+=""" + """ + to_xml(tools.ustr(answer[0].comment)) + """""" + else: + rml +=""" + No Response + """ + + rml += """""" rml += """""" report_type = datas.get('report_type', 'pdf') create_doc = self.generators[report_type] diff --git a/addons/survey/report/survey_form.py b/addons/survey/report/survey_form.py index 9994a47e3e5..8b9c71baa64 100644 --- a/addons/survey/report/survey_form.py +++ b/addons/survey/report/survey_form.py @@ -135,10 +135,6 @@ class survey_form(report_rml): """ surv_obj = pooler.get_pool(cr.dbname).get('survey') for survey in surv_obj.browse(cr,uid,ids): - if survey.question_prefix: - prefix = survey.question_prefix + " : " - else: - prefix = '' if datas.has_key('form') and datas['form']['survey_title']: rml += """ @@ -156,7 +152,7 @@ class survey_form(report_rml): rml +=""" - """ + to_xml(tools.ustr(prefix)) + to_xml(tools.ustr(que.question)) + """ + Que : """ + to_xml(tools.ustr(que.question)) + """ """ if que.type in ['descriptive_text']: diff --git a/addons/survey/survey.py b/addons/survey/survey.py index ffe21807603..55636163579 100644 --- a/addons/survey/survey.py +++ b/addons/survey/survey.py @@ -32,10 +32,25 @@ import tools from mx.DateTime import * import netsvc +class survey_type(osv.osv): + _name = 'survey.type' + _description = 'Survey Type' + _columns = { + 'name' : fields.char("Name", size=128, required=1), + 'code' : fields.char("Code", size=64), + } +survey_type() + class survey(osv.osv): _name = 'survey' _description = 'Survey' _rec_name = 'title' + + def default_get(self, cr, uid, fields, context={}): + data = super(survey, self).default_get(cr, uid, fields, context) + data['responsible_id'] = uid + return data + _columns = { 'title' : fields.char('Survey Title', size=128, required=1), 'page_ids' : fields.one2many('survey.page', 'survey_id', 'Page'), @@ -51,14 +66,15 @@ class survey(osv.osv): 'note' : fields.text('Description', size=128), 'history' : fields.one2many('survey.history', 'survey_id', 'History Lines', readonly=True), 'users': fields.many2many('res.users', 'survey_users_rel', 'sid', 'uid', 'Users'), - 'question_prefix' : fields.char('Question Prefix', size=128), 'send_response' : fields.boolean('E-mail Notification on Response'), + 'type' : fields.many2one('survey.type', 'Type') } _defaults = { 'state' : lambda * a: "draft", 'tot_start_survey' : lambda * a: 0, 'tot_comp_survey' : lambda * a: 0, 'send_response' : lambda * a: 1, + 'response_user' : lambda * a:1, } def survey_draft(self, cr, uid, ids, arg): @@ -154,14 +170,14 @@ class survey_question(osv.osv): for id in ids1: val[id] = 0 return val - + _columns = { 'page_id' : fields.many2one('survey.page', 'Survey Page', ondelete='cascade', required=1), 'question' : fields.char('Question', size=128, required=1), 'answer_choice_ids' : fields.one2many('survey.answer', 'question_id', 'Answer'), 'response_ids' : fields.one2many('survey.response.line', 'question_id', 'Response', readonly=1), - 'is_require_answer' : fields.boolean('Required Answer'), - 'required_type' : fields.selection([('',''), ('all','All'), ('at least','At Least'), ('at most','At Most'), ('exactly','Exactly'), ('a range','A Range')], 'Respondent must answer'), + 'is_require_answer' : fields.boolean('Require Answer to Question (optional)'), + 'required_type' : fields.selection([('all','All'), ('at least','At Least'), ('at most','At Most'), ('exactly','Exactly'), ('a range','A Range')], 'Respondent must answer'), 'req_ans' : fields.integer('#Required Answer'), 'maximum_req_ans' : fields.integer('Maximum Required Answer'), 'minimum_req_ans' : fields.integer('Minimum Required Answer'), @@ -183,8 +199,9 @@ class survey_question(osv.osv): ('date_and_time','Date and Time'),('descriptive_text','Descriptive Text'), ('table','Table'), ], 'Question Type', required=1,), + 'is_comment_require' : fields.boolean('Add Comment Field (optional)'), 'comment_label' : fields.char('Field Label', size = 255), - 'comment_field_type' : fields.selection([('',''),('char', 'Single Line Of Text'), ('text', 'Paragraph of Text')], 'Comment Field Type'), + 'comment_field_type' : fields.selection([('char', 'Single Line Of Text'), ('text', 'Paragraph of Text')], 'Comment Field Type'), 'comment_valid_type' : fields.selection([('do_not_validate', '''Don't Validate Comment Text.'''), ('must_be_specific_length', 'Must Be Specific Length'), ('must_be_whole_number', 'Must Be A Whole Number'), @@ -201,6 +218,7 @@ class survey_question(osv.osv): 'comment_valid_err_msg' : fields.text('Error message'), 'make_comment_field' : fields.boolean('Make Comment Field an Answer Choice'), 'make_comment_field_err_msg' : fields.text('Error message'), + 'is_validation_require' : fields.boolean('Validate Text (optional)'), 'validation_type' : fields.selection([('do_not_validate', '''Don't Validate Comment Text.'''),\ ('must_be_specific_length', 'Must Be Specific Length'),\ ('must_be_whole_number', 'Must Be A Whole Number'),\ @@ -228,8 +246,10 @@ class survey_question(osv.osv): 'sequence' : lambda * a: 1, 'type' : lambda * a: 'multiple_choice_multiple_ans', 'req_error_msg' : lambda * a: 'This question requires an answer.', - 'required_type' : lambda * a: '', - 'comment_label' : lambda * a: 'Other', + 'required_type' : lambda * a: 'at least', + 'req_ans' : lambda * a: 1, + 'comment_field_type' : lambda * a: 'char', + 'comment_label' : lambda * a: 'Other (please specify)', 'comment_valid_type' : lambda * a: 'do_not_validate', 'comment_valid_err_msg' : lambda * a : 'The comment you entered is in an invalid format.', 'validation_type' : lambda * a: 'do_not_validate', @@ -280,34 +300,35 @@ class survey_question(osv.osv): req_type = vals['required_type'] else: req_type = question['required_type'] - if req_type in ['at least', 'at most', 'exactly']: - if vals.has_key('req_ans'): - if not vals['req_ans'] or vals['req_ans'] > ans_len: - raise osv.except_osv(_('Error !'),_("#Required Answer you entered is greater than the number of answer. Please use a number that is smaller than %d.") % (ans_len + 1)) - else: - if not question['req_ans'] or question['req_ans'] > ans_len: - raise osv.except_osv(_('Error !'),_("#Required Answer you entered is greater than the number of answer. Please use a number that is smaller than %d.") % (ans_len + 1)) - if req_type == 'a range': - minimum_ans = 0 - maximum_ans = 0 - if vals.has_key('minimum_req_ans'): - minimum_ans = vals['minimum_req_ans'] - if not vals['minimum_req_ans'] or vals['minimum_req_ans'] > ans_len: - raise osv.except_osv(_('Error !'),_("Minimum Required Answer you entered is greater than the number of answer. Please use a number that is smaller than %d.") % (ans_len + 1)) - else: - minimum_ans = question['minimum_req_ans'] - if not question['minimum_req_ans'] or question['minimum_req_ans'] > ans_len: - raise osv.except_osv(_('Error !'),_("Minimum Required Answer you entered is greater than the number of answer. Please use a number that is smaller than %d.") % (ans_len + 1)) - if vals.has_key('maximum_req_ans'): - maximum_ans = vals['maximum_req_ans'] - if not vals['maximum_req_ans'] or vals['maximum_req_ans'] > ans_len: - raise osv.except_osv(_('Error !'),_("Maximum Required Answer you entered for your maximum is greater than the number of answer. Please use a number that is smaller than %d.") % (ans_len + 1)) - else: - maximum_ans = question['maximum_req_ans'] - if not question['maximum_req_ans'] or question['maximum_req_ans'] > ans_len: - raise osv.except_osv(_('Error !'),_("Maximum Required Answer you entered for your maximum is greater than the number of answer. Please use a number that is smaller than %d.") % (ans_len + 1)) - if maximum_ans <= minimum_ans: - raise osv.except_osv(_('Error !'),_("Maximum Required Answer is greater than Minimum Required Answer")) + if que_type in ['multiple_choice_multiple_ans','matrix_of_choices_only_one_ans', 'matrix_of_choices_only_multi_ans', 'matrix_of_drop_down_menus', 'rating_scale','multiple_textboxes','numerical_textboxes','date','date_and_time']: + if req_type in ['at least', 'at most', 'exactly']: + if vals.has_key('req_ans'): + if not vals['req_ans'] or vals['req_ans'] > ans_len: + raise osv.except_osv(_('Error !'),_("#Required Answer you entered is greater than the number of answer. Please use a number that is smaller than %d.") % (ans_len + 1)) + else: + if not question['req_ans'] or question['req_ans'] > ans_len: + raise osv.except_osv(_('Error !'),_("#Required Answer you entered is greater than the number of answer. Please use a number that is smaller than %d.") % (ans_len + 1)) + if req_type == 'a range': + minimum_ans = 0 + maximum_ans = 0 + if vals.has_key('minimum_req_ans'): + minimum_ans = vals['minimum_req_ans'] + if not vals['minimum_req_ans'] or vals['minimum_req_ans'] > ans_len: + raise osv.except_osv(_('Error !'),_("Minimum Required Answer you entered is greater than the number of answer. Please use a number that is smaller than %d.") % (ans_len + 1)) + else: + minimum_ans = question['minimum_req_ans'] + if not question['minimum_req_ans'] or question['minimum_req_ans'] > ans_len: + raise osv.except_osv(_('Error !'),_("Minimum Required Answer you entered is greater than the number of answer. Please use a number that is smaller than %d.") % (ans_len + 1)) + if vals.has_key('maximum_req_ans'): + maximum_ans = vals['maximum_req_ans'] + if not vals['maximum_req_ans'] or vals['maximum_req_ans'] > ans_len: + raise osv.except_osv(_('Error !'),_("Maximum Required Answer you entered for your maximum is greater than the number of answer. Please use a number that is smaller than %d.") % (ans_len + 1)) + else: + maximum_ans = question['maximum_req_ans'] + if not question['maximum_req_ans'] or question['maximum_req_ans'] > ans_len: + raise osv.except_osv(_('Error !'),_("Maximum Required Answer you entered for your maximum is greater than the number of answer. Please use a number that is smaller than %d.") % (ans_len + 1)) + if maximum_ans <= minimum_ans: + raise osv.except_osv(_('Error !'),_("Maximum Required Answer is greater than Minimum Required Answer")) if question['type'] == 'matrix_of_drop_down_menus' and vals.has_key('column_heading_ids'): for col in vals['column_heading_ids']: if col[2].has_key('menu_choice') and not col[2]['menu_choice']: @@ -325,18 +346,19 @@ class survey_question(osv.osv): if vals.has_key('column_heading_ids') and not len(vals['column_heading_ids']): if vals.has_key('type') and vals['type'] in ['matrix_of_choices_only_one_ans', 'matrix_of_choices_only_multi_ans', 'matrix_of_drop_down_menus', 'rating_scale']: raise osv.except_osv(_('Error !'),_("You must enter one or more column heading.")) - if vals.has_key('required_type') and vals['required_type'] in ['at least', 'at most', 'exactly']: - if vals['req_ans'] > len(vals['answer_choice_ids']) or not vals['req_ans']: - raise osv.except_osv(_('Error !'),_("#Required Answer you entered is greater than the number of answer. Please use a number that is smaller than %d.") % (len(vals['answer_choice_ids'])+1)) - if vals.has_key('required_type') and vals['required_type'] == 'a range': - minimum_ans = vals['minimum_req_ans'] - maximum_ans = vals['maximum_req_ans'] - if vals['minimum_req_ans'] > len(vals['answer_choice_ids']) or not vals['minimum_req_ans']: - raise osv.except_osv(_('Error !'),_("Minimum Required Answer you entered is greater than the number of answer. Please use a number that is smaller than %d.") % (len(vals['answer_choice_ids'])+1)) - if vals['maximum_req_ans'] > len(vals['answer_choice_ids']) or not vals['maximum_req_ans']: - raise osv.except_osv(_('Error !'),_("Maximum Required Answer you entered for your maximum is greater than the number of answer. Please use a number that is smaller than %d.") % (len(vals['answer_choice_ids'])+1)) - if maximum_ans <= minimum_ans: - raise osv.except_osv(_('Error !'),_("Maximum Required Answer is greater than Minimum Required Answer")) + if vals['type'] in ['multiple_choice_multiple_ans','matrix_of_choices_only_one_ans', 'matrix_of_choices_only_multi_ans', 'matrix_of_drop_down_menus', 'rating_scale','multiple_textboxes','numerical_textboxes','date','date_and_time']: + if vals.has_key('is_require_answer') and vals.has_key('required_type') and vals['required_type'] in ['at least', 'at most', 'exactly']: + if vals['req_ans'] > len(vals['answer_choice_ids']) or not vals['req_ans']: + raise osv.except_osv(_('Error !'),_("#Required Answer you entered is greater than the number of answer. Please use a number that is smaller than %d.") % (len(vals['answer_choice_ids'])+1)) + if vals.has_key('is_require_answer') and vals.has_key('required_type') and vals['required_type'] == 'a range': + minimum_ans = vals['minimum_req_ans'] + maximum_ans = vals['maximum_req_ans'] + if vals['minimum_req_ans'] > len(vals['answer_choice_ids']) or not vals['minimum_req_ans']: + raise osv.except_osv(_('Error !'),_("Minimum Required Answer you entered is greater than the number of answer. Please use a number that is smaller than %d.") % (len(vals['answer_choice_ids'])+1)) + if vals['maximum_req_ans'] > len(vals['answer_choice_ids']) or not vals['maximum_req_ans']: + raise osv.except_osv(_('Error !'),_("Maximum Required Answer you entered for your maximum is greater than the number of answer. Please use a number that is smaller than %d.") % (len(vals['answer_choice_ids'])+1)) + if maximum_ans <= minimum_ans: + raise osv.except_osv(_('Error !'),_("Maximum Required Answer is greater than Minimum Required Answer")) if vals['type'] == 'matrix_of_drop_down_menus': for col in vals['column_heading_ids']: if not col[2]['menu_choice']: @@ -524,6 +546,12 @@ survey_response_answer() class survey_name_wiz(osv.osv_memory): _name = 'survey.name.wiz' + def default_get(self, cr, uid, fields, context={}): + data = super(survey_name_wiz, self).default_get(cr, uid, fields, context) + if context.has_key('survey_id'): + data['survey_id'] = context['survey_id'] + return data + def _get_survey(self, cr, uid, context=None): surv_obj = self.pool.get("survey") result = [] @@ -651,7 +679,7 @@ class survey_question_wiz(osv.osv_memory): que_rec = que_obj.read(cr, uid, que) descriptive_text = "" separator_string = tools.ustr(qu_no) + "." + tools.ustr(que_rec['question']) - if not context.has_key('active') and (que_rec['is_require_answer'] or que_rec['required_type'] != ''): + if not context.has_key('active') and que_rec['is_require_answer']: star='*' else: star='' @@ -755,7 +783,7 @@ class survey_question_wiz(osv.osv_memory): for col in que_col_head.read(cr, uid, que_rec['column_heading_ids']): etree.SubElement(xml_group, 'field', {'name': tools.ustr(que) + "_table_" + tools.ustr(col['id']) +"_"+ tools.ustr(row), 'nolabel':"1"}) fields[tools.ustr(que) + "_table_" + tools.ustr(col['id']) +"_"+ tools.ustr(row)] = {'type':'char','size':255,'views':{}} - if que_rec['type'] in ['multiple_choice_only_one_ans', 'multiple_choice_multiple_ans', 'matrix_of_choices_only_one_ans', 'matrix_of_choices_only_multi_ans', 'matrix_of_drop_down_menus', 'rating_scale']: + if que_rec['type'] in ['multiple_choice_only_one_ans', 'multiple_choice_multiple_ans', 'matrix_of_choices_only_one_ans', 'matrix_of_choices_only_multi_ans', 'matrix_of_drop_down_menus', 'rating_scale'] and que_rec['is_comment_require']: if que_rec['type'] in ['multiple_choice_only_one_ans', 'multiple_choice_multiple_ans'] and que_rec['comment_field_type'] in ['char','text'] and que_rec['make_comment_field']: etree.SubElement(xml_group, 'field', {'name': tools.ustr(que) + "_otherfield", 'colspan':"4"}) fields[tools.ustr(que) + "_otherfield"] = {'type':'boolean', 'string':que_rec['comment_label'], 'views':{}} @@ -944,14 +972,14 @@ class survey_question_wiz(osv.osv_memory): else: error = False if que_rec['comment_valid_type'] == 'must_be_specific_length': - if (not val1 and que_rec['validation_minimum_no']) or len(val1) < que_rec['validation_maximum_no'] or len(val1) > que_rec['comment_maximum_no']: + if (not val1 and que_rec['comment_minimum_no']) or len(val1) < que_rec['comment_minimum_no'] or len(val1) > que_rec['comment_maximum_no']: error = True elif que_rec['comment_valid_type'] in ['must_be_whole_number', 'must_be_decimal_number', 'must_be_date']: error = False try: if que_rec['comment_valid_type'] == 'must_be_whole_number': value = int(val1) - if value < que_rec['validation_minimum_no'] or value > que_rec['validation_maximum_no']: + if value < que_rec['comment_minimum_no'] or value > que_rec['comment_maximum_no']: error = True elif que_rec['comment_valid_type'] == 'must_be_decimal_number': value = float(val1) @@ -1057,7 +1085,7 @@ class survey_question_wiz(osv.osv_memory): sur_name_read['store_ans'].pop(res) surv_name_wiz.write(cr, uid, [context['sur_name_id']], {'response' :0}) raise osv.except_osv(_('Error re !'), _("'" + que_rec['question'] + "' " + tools.ustr(que_rec['numeric_required_sum_err_msg']))) - if que_rec['type'] in ['multiple_choice_multiple_ans','matrix_of_choices_only_one_ans','matrix_of_choices_only_multi_ans','matrix_of_drop_down_menus','rating_scale','multiple_textboxes','numerical_textboxes','date','date_and_time'] and que_rec['required_type']: + if que_rec['type'] in ['multiple_choice_multiple_ans','matrix_of_choices_only_one_ans','matrix_of_choices_only_multi_ans','matrix_of_drop_down_menus','rating_scale','multiple_textboxes','numerical_textboxes','date','date_and_time'] and que_rec['is_require_answer']: if matrix_list: if (que_rec['required_type'] == 'all' and len(list(set(matrix_list))) < len(que_rec['answer_choice_ids'])) or \ (que_rec['required_type'] == 'at least' and len(list(set(matrix_list))) < que_rec['req_ans']) or \ @@ -1228,7 +1256,7 @@ class survey_question_wiz(osv.osv_memory): raise osv.except_osv(_('Error re !'), _("'" + que_rec['question'] + "' " + tools.ustr(que_rec['numeric_required_sum_err_msg']))) if not select_count: resp_obj.write(cr, uid, update, {'state': 'skip'}) - if que_rec['type'] in ['multiple_choice_multiple_ans','matrix_of_choices_only_one_ans','matrix_of_choices_only_multi_ans','matrix_of_drop_down_menus','rating_scale','multiple_textboxes','numerical_textboxes','date','date_and_time'] and que_rec['required_type']: + if que_rec['type'] in ['multiple_choice_multiple_ans','matrix_of_choices_only_one_ans','matrix_of_choices_only_multi_ans','matrix_of_drop_down_menus','rating_scale','multiple_textboxes','numerical_textboxes','date','date_and_time'] and que_rec['is_require_answer']: if matrix_list: if (que_rec['required_type'] == 'all' and len(list(set(matrix_list))) < len(que_rec['answer_choice_ids'])) or \ (que_rec['required_type'] == 'at least' and len(list(set(matrix_list))) < que_rec['req_ans']) or \ diff --git a/addons/survey/survey_report.xml b/addons/survey/survey_report.xml index e7a483018e8..52f2d47ed24 100644 --- a/addons/survey/survey_report.xml +++ b/addons/survey/survey_report.xml @@ -18,6 +18,5 @@ name="survey.browse.response" rml="" string="Browse Response"/> - diff --git a/addons/survey/survey_view.xml b/addons/survey/survey_view.xml index 40d8b695136..18f035e2d3e 100644 --- a/addons/survey/survey_view.xml +++ b/addons/survey/survey_view.xml @@ -2,19 +2,17 @@ - - - - - - + + + + + + + @@ -24,8 +22,16 @@ form
- - + + + +