diff --git a/addons/survey/controllers/survey_session_manage.py b/addons/survey/controllers/survey_session_manage.py index ab40a893de8..4c4be7fdc7c 100644 --- a/addons/survey/controllers/survey_session_manage.py +++ b/addons/survey/controllers/survey_session_manage.py @@ -19,21 +19,18 @@ class UserInputSession(http.Controller): return request.env['survey.survey'].search([('access_token', '=', survey_token)]) def _fetch_from_session_code(self, session_code): - """ Matches a survey against a passed session_code. - We don't limit the session_state to be reachable (ready / in_progress) here because - in some cases, we want closed session as well (where session_state = False). - Instead, when necessary, the reachability is forced in routes calling this method to - avoid people using those routes to access other (private) surveys. - We limit to sessions opened within the last 7 days to avoid potential abuses. """ - if session_code: - matching_survey = request.env['survey.survey'].sudo().search([ - ('session_start_time', '>', fields.Datetime.now() - relativedelta(days=7)), - ('session_code', '=', session_code), - ], limit=1) - if matching_survey: - return matching_survey - - return False + """ Matches a survey against a passed session_code, and checks if it is valid. + If it is valid, returns the start url. Else, the error type.""" + if not session_code: + return None, {'error': 'survey_wrong'} + survey = request.env['survey.survey'].sudo().search([('session_code', '=', session_code)], limit=1) + if not survey or survey.certification: + return None, {'error': 'survey_wrong'} + if survey.session_state in ['ready', 'in_progress']: + return survey, None + if request.env.user.has_group("survey.group_survey_user"): + return None, {'error': 'survey_session_not_launched', 'survey_id': survey.id} + return None, {'error': 'survey_session_not_launched'} # ------------------------------------------------------------ # SURVEY SESSION MANAGEMENT @@ -176,28 +173,24 @@ class UserInputSession(http.Controller): @http.route('/s/', type='http', auth='public', website=True) def survey_start_short(self, session_code): """" Redirects to 'survey_start' route using a shortened link & token. - We match the session_code for open surveys. + Shows an error message if the survey is not valid. This route is used in survey sessions where we need short links for people to type. """ + survey, survey_error = self._fetch_from_session_code(session_code) - survey = self._fetch_from_session_code(session_code) - if survey and survey.session_state in ['ready', 'in_progress']: - return request.redirect("/survey/start/%s" % survey.access_token) - - return request.redirect("/s") + if survey_error: + return request.render('survey.survey_session_code', + dict(**survey_error, session_code=session_code)) + return request.redirect(survey.get_start_url()) @http.route('/survey/check_session_code/', type='json', auth='public', website=True) def survey_check_session_code(self, session_code): """ Checks if the given code is matching a survey session_code. If yes, redirect to /s/code route. - If not, return error. The user is invited to type again the code. """ - survey = self._fetch_from_session_code(session_code) - if survey: - if survey.session_state in ['ready', 'in_progress']: - return {"survey_url": "/survey/start/%s" % survey.access_token} - else: - return {"error": "survey_session_closed"} - - return {"error": "survey_wrong"} + If not, return error. The user is invited to type again the code.""" + survey, survey_error = self._fetch_from_session_code(session_code) + if survey_error: + return survey_error + return {'survey_url': survey.get_start_url()} def _prepare_manage_session_values(self, survey): is_first_question, is_last_question = False, False diff --git a/addons/survey/static/src/js/survey_quick_access.js b/addons/survey/static/src/js/survey_quick_access.js index bf41ab71643..abf509412c8 100644 --- a/addons/survey/static/src/js/survey_quick_access.js +++ b/addons/survey/static/src/js/survey_quick_access.js @@ -8,9 +8,10 @@ publicWidget.registry.SurveyQuickAccessWidget = publicWidget.Widget.extend({ events: { 'click button[type="submit"]': '_onSubmit', 'input #session_code': '_onSessionCodeInput', + 'click .o_survey_launch_session': '_onLaunchSessionClick', }, - //-------------------------------------------------------------------------- + //-------------------------------------------------------------------------- // Widget //-------------------------------------------------------------------------- @@ -23,9 +24,7 @@ publicWidget.registry.SurveyQuickAccessWidget = publicWidget.Widget.extend({ // Init event listener if (!self.readonly) { $(document).on('keypress', self._onKeyPress.bind(self)); - } - - self.$('input').focus(); + } }); }, @@ -36,8 +35,19 @@ publicWidget.registry.SurveyQuickAccessWidget = publicWidget.Widget.extend({ // Handlers // ------------------------------------------------------------------------- + _onLaunchSessionClick: async function () { + const sessionResult = await this._rpc({ + 'model': 'survey.survey', + 'method': 'action_start_session', + 'args': [[this.$('.o_survey_launch_session').data('surveyId')]], + }); + window.location = sessionResult.url; + }, + _onSessionCodeInput: function () { this.el.querySelectorAll('.o_survey_error > span').forEach((elem) => elem.classList.add('d-none')); + this.$('.o_survey_launch_session').addClass('d-none'); + this.$('button[type="submit"]').removeClass('d-none'); }, _onKeyPress: function (event) { @@ -54,10 +64,10 @@ publicWidget.registry.SurveyQuickAccessWidget = publicWidget.Widget.extend({ _submitCode: function () { var self = this; - this.$('.o_survey_error > span').addClass("d-none"); + this.$('.o_survey_error > span').addClass('d-none'); const sessionCodeInputVal = this.$('input#session_code').val().trim(); if (!sessionCodeInputVal) { - self.$('.o_survey_session_error_invalid_code').removeClass("d-none"); + self.$('.o_survey_session_error_invalid_code').removeClass('d-none'); return; } this._rpc({ @@ -66,10 +76,15 @@ publicWidget.registry.SurveyQuickAccessWidget = publicWidget.Widget.extend({ if (response.survey_url) { window.location = response.survey_url; } else { - if (response.error && response.error === 'survey_session_closed') { - self.$('.o_survey_session_error_closed').removeClass("d-none"); + if (response.error && response.error === 'survey_session_not_launched') { + self.$('.o_survey_session_error_not_launched').removeClass('d-none'); + if ("survey_id" in response) { + self.$('button[type="submit"]').addClass('d-none'); + self.$('.o_survey_launch_session').removeClass('d-none'); + self.$('.o_survey_launch_session').data('surveyId', response.survey_id); + } } else { - self.$('.o_survey_session_error_invalid_code').removeClass("d-none"); + self.$('.o_survey_session_error_invalid_code').removeClass('d-none'); } } }); diff --git a/addons/survey/static/src/js/survey_session_manage.js b/addons/survey/static/src/js/survey_session_manage.js index 6840dfca36b..4f0b43b48b4 100644 --- a/addons/survey/static/src/js/survey_session_manage.js +++ b/addons/survey/static/src/js/survey_session_manage.js @@ -51,6 +51,8 @@ publicWidget.registry.SurveySessionManage = publicWidget.Widget.extend(SurveyPre self.stopNextQuestion = false; // Background Management self.refreshBackground = self.$el.data('refreshBackground'); + // Copy link tooltip + self.$('.o_survey_session_copy').tooltip({delay: 0, title: 'Click to copy link', placement: 'right'}); var isRpcCall = self.$el.data('isRpcCall'); if (!isRpcCall) { diff --git a/addons/survey/static/src/scss/survey_templates_form.scss b/addons/survey/static/src/scss/survey_templates_form.scss index 8a4ad3153b0..8257fbb0342 100644 --- a/addons/survey/static/src/scss/survey_templates_form.scss +++ b/addons/survey/static/src/scss/survey_templates_form.scss @@ -367,11 +367,6 @@ _::-webkit-full-page-media, _:future, :root .o_survey_wrap { .o_survey_session_copy { cursor: pointer; - opacity: .75; - transition: opacity .3s ease; - &:hover { - opacity: 1; - } } } diff --git a/addons/survey/views/survey_templates_management.xml b/addons/survey/views/survey_templates_management.xml index 71a0ec00152..fb335e038e9 100644 --- a/addons/survey/views/survey_templates_management.xml +++ b/addons/survey/views/survey_templates_management.xml @@ -118,16 +118,20 @@
- +
-
- + +
diff --git a/addons/survey/views/survey_templates_user_input_session.xml b/addons/survey/views/survey_templates_user_input_session.xml index 726aa4b58fd..184a8626c3b 100644 --- a/addons/survey/views/survey_templates_user_input_session.xml +++ b/addons/survey/views/survey_templates_user_input_session.xml @@ -38,8 +38,7 @@