def validate_password(self, action, data): context = aq_inner(self.context) registration = getToolByName(context, 'portal_registration') membertool = getToolByName(context, 'portal_membership') errors = super(PasswordAccountPanel, self).validate(action, data) # check if password is correct current_password = data.get('current_password') if current_password: current_password = current_password.encode('ascii', 'ignore') if not membertool.testCurrentPassword(current_password): err_str = _(u"Incorrect value for current password") errors.append(WidgetInputError('current_password', u'label_current_password', err_str)) self.widgets['current_password'].error = err_str # check if passwords are same and valid according to plugin new_password = data.get('new_password') new_password_ctl = data.get('new_password_ctl') if new_password and new_password_ctl: failMessage = registration.testPasswordValidity(new_password, new_password_ctl) if failMessage: errors.append(WidgetInputError('new_password', u'label_new_password', failMessage)) errors.append(WidgetInputError('new_password_ctl', u'new_password_ctl', failMessage)) self.widgets['new_password'].error = failMessage self.widgets['new_password_ctl'].error = failMessage return errors
def getInputValue(self): """See zope.formlib.interfaces.IInputWidget.""" scope = self.request.form_ng.getOne(self.name) if scope == 'all': return None elif scope == 'project': if not self.request.form_ng.getOne(self.target_widget.name): self._error = WidgetInputError( self.name, self.label, LaunchpadValidationError('Please enter a project name')) raise self._error try: return self.target_widget.getInputValue() except ConversionError: entered_name = self.request.form_ng.getOne("%s.target" % self.name) self._error = WidgetInputError( self.name, self.label, LaunchpadValidationError( "There is no project named '%s' registered in" " Launchpad" % entered_name)) raise self._error elif self.required: raise UnexpectedFormData("No valid option was selected.") else: return None
def getInputValue(self): self._error = None action = self.action_widget.getInputValue() try: announcement_date = self.announcement_date_widget.getInputValue() except ConversionError: self._error = WidgetInputError( self.name, self.label, LaunchpadValidationError( _('Please provide a valid date and time.'))) raise self._error if action == 'immediately' and announcement_date is not None: self._error = WidgetInputError( self.name, self.label, LaunchpadValidationError( _('Please do not provide a date if you want to publish ' 'immediately.'))) raise self._error if action == 'specific' and announcement_date is None: self._error = WidgetInputError( self.name, self.label, LaunchpadValidationError( _('Please provide a publication date.'))) raise self._error if action == 'immediately': return datetime.now(pytz.utc) elif action == "sometime": return None elif action == "specific": return announcement_date else: raise AssertionError('Unknown action in AnnouncementDateWidget')
def getInputValue(self): """See zope.formlib.interfaces.IInputWidget.""" scope = self.request.form_ng.getOne(self.name) if scope == 'all': return None elif scope == 'project': if not self.request.form_ng.getOne(self.target_widget.name): self._error = WidgetInputError( self.name, self.label, LaunchpadValidationError('Please enter a project name')) raise self._error try: return self.target_widget.getInputValue() except ConversionError: entered_name = self.request.form_ng.getOne( "%s.target" % self.name) self._error = WidgetInputError( self.name, self.label, LaunchpadValidationError( "There is no project named '%s' registered in" " Launchpad" % entered_name)) raise self._error elif self.required: raise UnexpectedFormData("No valid option was selected.") else: return None
def _toFieldValue(self, form_value): """Convert the textual token to a field value. If the form value is _new_bugwatch_value, create a new bug watch, otherwise look up an existing one. """ if form_value == self._new_bugwatch_value: try: url = self.url_widget.getInputValue() bugtracker, remote_bug = getUtility( IBugWatchSet).extractBugTrackerAndBug(url) bugtask = self.context.context return bugtask.bug.addWatch(bugtracker, remote_bug, getUtility(ILaunchBag).user) except WidgetInputError as error: # Prefix the error with the widget name, since the error # will be display at the top of the page, and not right # next to the widget. raise WidgetInputError(self.context.__name__, self.label, 'Remote Bug: %s' % error.doc()) except (NoBugTrackerFound, UnrecognizedBugTrackerURL) as error: raise WidgetInputError(self.context.__name__, self.label, 'Invalid bug tracker URL.') else: return RadioWidget._toFieldValue(self, form_value)
def getInputValue(self): """See zope.formlib.interfaces.IInputWidget.""" self.setUpSubWidgets() form_value = self.request.form_ng.getOne(self.name) if form_value == 'product': try: return self.product_widget.getInputValue() except MissingInputError: self._error = WidgetInputError( self.name, self.label, LaunchpadValidationError('Please enter a project name')) raise self._error except ConversionError: entered_name = self.request.form_ng.getOne("%s.product" % self.name) self._error = WidgetInputError( self.name, self.label, LaunchpadValidationError( "There is no project named '%s' registered in" " Launchpad" % entered_name)) raise self._error elif form_value == 'package': try: distribution = self.distribution_widget.getInputValue() except ConversionError: entered_name = self.request.form_ng.getOne("%s.distribution" % self.name) self._error = WidgetInputError( self.name, self.label, LaunchpadValidationError( "There is no distribution named '%s' registered in" " Launchpad" % entered_name)) raise self._error if self.package_widget.hasInput(): try: package_name = self.package_widget.getInputValue() if package_name is None: return distribution if IDistributionSourcePackage.providedBy(package_name): dsp = package_name else: source_name = ( distribution.guessPublishedSourcePackageName( package_name.name)) dsp = distribution.getSourcePackage(source_name) except (ConversionError, NotFoundError): entered_name = self.request.form_ng.getOne('%s.package' % self.name) self._error = WidgetInputError( self.name, self.label, LaunchpadValidationError( "There is no package named '%s' published in %s." % (entered_name, distribution.displayname))) raise self._error return dsp else: return distribution else: raise UnexpectedFormData("No valid option was selected.")
def __init__(self, field_name, widget_title, errors): """Initialize Error `errors` is a ``ValidationError`` or a list of ValidationError objects """ if not isinstance(errors, list): errors = [errors] _WidgetInputError.__init__(self, field_name, widget_title, errors)
def getInputValue(self): self._error = None action = self.action_widget.getInputValue() form = self.request.form_ng if action == 'change' and not form.getOne(self.image_widget.name): self._error = WidgetInputError( self.name, self.label, LaunchpadValidationError( _('Please specify the image you want to use.'))) raise self._error if action == "keep": if self.style == self.ADD_STYLE: # It doesn't make any sense to return KEEP_SAME_IMAGE in this # case, since there's nothing to keep. return None elif self.style == self.EDIT_STYLE: return KEEP_SAME_IMAGE else: raise AssertionError( "Style must be one of EDIT_STYLE or ADD_STYLE, got %s" % self.style) elif action == "change": self._image = form.getOne(self.image_widget.name) try: self.context.validate(self._image) except ValidationError as v: self._error = WidgetInputError(self.name, self.label, v) raise self._error self._image.seek(0) content = self._image.read() filename = self._image.filename type, dummy = guess_content_type(name=filename, body=content) # This method may be called more than once in a single request. If # that's the case here we'll simply return the cached # LibraryFileAlias we already have. existing_alias = self._image_file_alias if existing_alias is not None: assert existing_alias.filename == filename, ( "The existing LibraryFileAlias' name doesn't match the " "given image's name.") assert existing_alias.content.filesize == len(content), ( "The existing LibraryFileAlias' size doesn't match " "the given image's size.") assert existing_alias.mimetype == type, ( "The existing LibraryFileAlias' type doesn't match " "the given image's type.") return existing_alias self._image_file_alias = getUtility(ILibraryFileAliasSet).create( name=filename, size=len(content), file=StringIO(content), contentType=type) return self._image_file_alias elif action == "delete": return None
def __init__(self, field_name, widget_title, errors): """Initialize Error `errors` is a ``ValidationError`` or a list of ValidationError objects """ if not isinstance(errors, list): errors = [errors] _WidgetInputError.__init__(self, field_name, widget_title, errors)
def validate(self, action, data): context = aq_inner(self.context) errors = super(UserDataPanel, self).validate(action, data) if not self.widgets['email'].error(): props = getToolByName(context, 'portal_properties') if props.site_properties.getProperty('use_email_as_login'): # Keeping your email the same (which happens when you # change something else on the personalize form) or # changing it back to your original user id, is fine. membership = getToolByName(context, 'portal_membership') if self.userid: member = membership.getMemberById(self.userid) else: member = membership.getAuthenticatedMember() email = data['email'] if email not in (member.getId(), member.getUserName()): # Our email has changed and is not the same as our # user id or login name, so we need to check if # this email is already in use by another user. pas = getToolByName(context, 'acl_users') # TODO: maybe search for lowercase as well. if (membership.getMemberById(email) or pas.searchUsers(login=email, exact_match=True)): err_str = _( 'message_email_in_use', default=( u"The email address you selected is " u"already in use or is not valid as login " u"name. Please choose another.")) errors.append( WidgetInputError('email', u'label_email', err_str)) self.widgets['email'].error = err_str return errors
def getInputValue(self): self._error = None field = self.context # form input is required, otherwise raise an error if not self.hasInput(): raise MissingInputError(self.name, self.label, None) # convert input to suitable value - may raise conversion error try: value = self._toFieldValue(self._getFormInput()) except ConversionError as error: # ConversionError is already a WidgetInputError self._error = error raise self._error # allow missing values only for non-required fields if value == field.missing_value and not field.required: return value # value must be valid per the field constraints try: field.validate(value) except ValidationError as v: self._error = WidgetInputError(self.context.__name__, self.label, v) raise self._error return value
def loadValueFromRequest(self): field = self.context missing_value = field.missing_value value = self.request.form.get(self.name) try: value = int(value) except (TypeError, ValueError): value = missing_value else: if value >= len(field.fields): value = missing_value else: self._field_index = value # value should be an int index of the active field active = field.fields[value].bind(self.context) if zc.form.interfaces.IOptionField.providedBy(active): return active.getValue() widget = component.getMultiAdapter((active, self.request), IInputWidget) widget.required = widget.context.required = self.required widget.setPrefix(self.name) try: return widget.getInputValue() except WidgetInputError as e: # recast with our name and title self._error = WidgetInputError(self.context.__name__, self.label, e.errors) return missing_value
def getInputValue(self): """Return converted and validated widget data. If there is no user input and the field is required, then a ``MissingInputError`` will be raised. If there is no user input and the field is not required, then the field default value will be returned. A ``WidgetInputError`` is raised in the case of one or more errors encountered, inputting, converting, or validating the data. """ if self.hasInput(): self.preserve_widgets = True sequence = self._type(self._generateSequence()) if sequence != self.context.missing_value: # catch and set field errors to ``_error`` attribute try: self.context.validate(sequence) except WidgetInputError as error: self._error = error raise self._error except ValidationError as error: self._error = WidgetInputError(self.context.__name__, self.label, error) raise self._error elif self.context.required: raise MissingInputError(self.context.__name__, self.context.title) return sequence raise MissingInputError(self.context.__name__, self.context.title)
def validate(self): """ This method used to be part of zope.formlib.interfaces.IInputWidget in Zope 3.0, but is no longer part of the interface in Zope 3.2 """ # If the user has chosen to assign this bug to somebody else, # ensure that they actually provided a valid input value for # the assignee field. option = self.request.form_ng.getOne(self.name + ".option") if option == self.assign_to: if not self.assignee_chooser_widget.hasInput(): raise WidgetInputError( self.name, self.label, ValidationError("Missing value for assignee")) if not self.assignee_chooser_widget.hasValidInput(): raise WidgetInputError(self.name, self.label, ValidationError("Assignee not found"))
def getInputValue(self): """See `IInputWidget`.""" self.setUpSubWidgets() track = self.track_widget.getInputValue() risks = self.risks_widget.getInputValue() branch = self.branch_widget.getInputValue() if track and self._separator in track: error_msg = "Track name cannot include '%s'." % self._separator raise WidgetInputError(self.name, self.label, LaunchpadValidationError(error_msg)) if branch and self._separator in branch: error_msg = "Branch name cannot include '%s'." % self._separator raise WidgetInputError(self.name, self.label, LaunchpadValidationError(error_msg)) channels = [ self.buildChannelName(track, risk, branch) for risk in risks ] return channels
def getInputValue(self): value = super(TextInputWidget, self).getInputValue() if value: try: value = scrubHTML(value) except IllegalHTML, err: self._error = WidgetInputError(self.context.__name__, self.label, err.args[0]) raise self._error
def getInputValue(self): """See `IInputWidget`.""" self.setUpSubWidgets() try: repository = self.repository_widget.getInputValue() except MissingInputError: if self.context.required: raise WidgetInputError( self.name, self.label, LaunchpadValidationError( "Please choose a Git repository.")) else: return None except ConversionError: entered_name = self.request.form_ng.getOne("%s.repository" % self.name) raise WidgetInputError( self.name, self.label, LaunchpadValidationError( "There is no Git repository named '%s' registered in " "Launchpad." % entered_name)) if self.path_widget.hasInput(): path = self.path_widget.getInputValue() else: path = None if not path: if self.context.required: raise WidgetInputError( self.name, self.label, LaunchpadValidationError( "Please enter a Git branch path.")) else: return if self.allow_external and not IGitRepository.providedBy(repository): ref = getUtility(IGitRefRemoteSet).new(repository, path) else: ref = repository.getRefByPath(path) if ref is None: raise WidgetInputError( self.name, self.label, LaunchpadValidationError( "The repository at %s does not contain a branch named " "'%s'." % (repository.display_name, path))) return ref
def set_invariant_error(self, errors, fields, msg): ''' Set an error with invariant validation to highlights the involved fields ''' for field in fields: label = self.widgets[field].label error = WidgetInputError(field, label, msg) errors.append(error) self.widgets[field].error = msg
def getInputValue(self): value = super(IDInputWidget, self).getInputValue() if value: context = getattr(self.context.context, 'context', self.context.context) if not context.checkIdAvailable(value): err_msg = _(u'Please choose another ID.') self._error = WidgetInputError(self.context.__name__, self.label, err_msg) raise self._error return value
def validate_registration(self, action, data): errors = super(CustomRegistrationForm, self).validate_registration( action, data, ) if not data.get('legal_conditions'): err_str = _(u'You need to accept our legal terms and conditions.') error = WidgetInputError( 'legal_conditions', _(u'I Accept Legal terms and conditions'), err_str, ) errors.append(error) self.widgets['legal_conditions'].error = err_str correct_captcha = self.context.restrictedTraverse('@@captcha').verify() if not correct_captcha: error = WidgetInputError('captcha', 'Captcha', _(u'Incorrect captcha')) errors.append(error) self.correct_captcha = correct_captcha return errors
def getInputValue(self): for name, queryview in self.queryviews: if name + '.apply' in self.request: token = self.request.form.get(name + '.selection') if token is not None: break else: token = self.request.get(self.name) field = self.context if token is None: if field.required: # TODO This code path is untested. raise MissingInputError( field.__name__, self.label, ) return field.missing_value try: value = self.terms.getValue(str(token)) except LookupError: # TODO This code path is untested. err = zope.schema.interfaces.ValidationError( "Invalid value id", token) raise WidgetInputError(field.__name__, self.label, err) # Remaining code copied from SimpleInputWidget # value must be valid per the field constraints try: field.validate(value) except ValidationError as err: # TODO This code path is untested. self._error = WidgetInputError(field.__name__, self.label, err) raise self._error return value
def getInputValue(self): value = self._input_value() # Remaining code copied from SimpleInputWidget # value must be valid per the field constraints field = self.context try: field.validate(value) except ValidationError, err: # TODO This code path is untested. self._error = WidgetInputError(field.__name__, self.label, err) raise self._error
def getInputValue(self): value = self._value() field = self.context # Remaining code copied from SimpleInputWidget # value must be valid per the field constraints try: field.validate(value) except ValidationError, err: self._error = WidgetInputError(field.__name__, self.label, err) raise self._error
def getInputValue(self): """Return the date, if it is in the allowed date range.""" value = super(DateTimeWidget, self).getInputValue() if value is None: return None # Establish if the value is within the date range. self._align_date_constraints_with_time_zone() if self.from_date is not None and value < self.from_date: limit = self.from_date.strftime(self.timeformat) self._error = WidgetInputError( self.name, self.label, LaunchpadValidationError( 'Please pick a date after %s' % limit)) raise self._error if self.to_date is not None and value > self.to_date: limit = self.to_date.strftime(self.timeformat) self._error = WidgetInputError( self.name, self.label, LaunchpadValidationError( 'Please pick a date before %s' % limit)) raise self._error return value
def getInputValue(self): """See zope.formlib.interfaces.IInputWidget.""" self.setUpSubWidgets() form_value = self.request.form_ng.getOne(self.name) if form_value == 'product': try: return self.product_widget.getInputValue() except MissingInputError: raise WidgetInputError( self.name, self.label, LaunchpadValidationError('Please enter a project name')) except ConversionError: entered_name = self.request.form_ng.getOne("%s.product" % self.name) raise WidgetInputError( self.name, self.label, LaunchpadValidationError( "There is no project named '%s' registered in" " Launchpad" % entered_name)) elif form_value == 'personal': return '+junk' else: raise UnexpectedFormData("No valid option was selected.")
def getInputValue(self): """See `IInputWidget`.""" self.setUpSubWidgets() form_value = self.request.form_ng.getOne(self.name) if form_value is None: return None elif form_value == "primary": return self.main_archive elif form_value == "ppa": try: ppa = self.ppa_widget.getInputValue() except MissingInputError: raise WidgetInputError( self.name, self.label, LaunchpadValidationError("Please choose a PPA.")) except ConversionError: entered_name = self.request.form_ng.getOne( "%s.ppa" % self.name) raise WidgetInputError( self.name, self.label, LaunchpadValidationError( "There is no PPA named '%s' registered in Launchpad." % entered_name)) return ppa
def getInputValue(self): """See `zope.formlib.interfaces.IInputWidget`.""" self.setUpSubWidgets() form_value = self.request.form_ng.getOne(self.name) if form_value == "repository_owner": return GitGranteeType.REPOSITORY_OWNER elif form_value == "person": try: return self.person_widget.getInputValue() except MissingInputError: raise WidgetInputError( self.name, self.label, LaunchpadValidationError( "Please enter a person or team name")) except ConversionError: entered_name = self.request.form_ng.getOne("%s.person" % self.name) raise WidgetInputError( self.name, self.label, LaunchpadValidationError( "There is no person or team named '%s' registered in " "Launchpad" % entered_name)) else: raise UnexpectedFormData("No valid option was selected.")
def convertTokensToValues(self, tokens): """Convert a list of tokens to a list of values. If an invalid token is encountered, WidgetInputError is raised. """ L = [] for token in tokens: try: term = self.vocabulary.getTermByToken(token) except LookupError: raise WidgetInputError( self.context.__name__, self.context.title, "token %r not found in vocabulary" % token) else: L.append(term.value) return L
def _generateSequence(self): """Extract the values of the subwidgets from the request. Returns a list of values. This can only be called if self.hasInput() returns true. """ if self.context.value_type is None: # Why would this ever happen? return [] # the marker field tells how many individual items were # included in the input; we check for exactly that many input # widgets try: count = int(self.request.form[self.name + ".count"]) except ValueError: # could not convert to int; the input was not generated # from the widget as implemented here raise WidgetInputError(self.context.__name__, self.context.title) # pre-populate sequence = [None] * count # now look through the request for interesting values # in reverse so that we can remove items as we go removing = self.name + ".remove" in self.request.form for i in reversed(list(range(count))): widget = self._getWidget(i) if widget.hasValidInput(): # catch and set sequence widget errors to ``_error`` attribute try: sequence[i] = widget.getInputValue() except WidgetInputError as error: self._error = error raise self._error remove_key = "%s.remove_%d" % (self.name, i) if remove_key in self.request.form and removing: del sequence[i] # add an entry to the list if the add button has been pressed if self.name + ".add" in self.request.form: # Should this be using self.context.value_type.missing_value # instead of None? sequence.append(None) return sequence
def validate(self, action, data): # Super's validate method does not actually check that all required # fields are present in the posted data. retval = super(EndpointMixin, self).validate(action, data) missing_required_params = [ parameter for parameter in self.required_endpoint_parameters if parameter['name'] not in data ] for missing_required_param in missing_required_params: retval.append( WidgetInputError( missing_required_param['name'], missing_required_param['value'].title, RequiredMissing(missing_required_param['name']))) return retval
def handle_edit_actions(self, action, data): # Filter out non-required fields that have no value so their # existing value is not overwritten. This protects us from # overwriting the bind password. data = dict([(key, value) for (key, value) in data.iteritems() if value is not None]) if applyChanges(self.context, self.form_fields, data, self.adapters): try: notify(ObjectModifiedEvent(self.storage)) except LDAPError: widget = self.widgets.get("bind_dn") widget.error = WidgetInputError("bind_dn", widget.label, LDAPBindFailure("value")) self.errors += (widget.error, ) self.status = _("There were errors") return self.request.response.redirect(self.nextURL())
def getInputValue(self): """ See zope.app.form.interfaces.IInputWidget """ self._error = None year = self.request.form.get(self.name + "Year") code = self.request.form.get(self.name + "Code") if not self.hasValidInput(): error = WidgetInputError(self.context.__name__, self.label, (year, code)) self._error = error raise error year = int(year.strip()) code = code.strip() return (year, code)
class ProjectScopeWidget(BrowserWidget, InputWidget): """Widget for selecting a scope. Either 'All projects' or only one.""" implements(IAlwaysSubmittedWidget, IInputWidget) default_option = "all" _error = None def __init__(self, field, vocabulary, request): super(ProjectScopeWidget, self).__init__(field, request) # We copy the title, description and vocabulary from the main # field since it determines the valid target types. # XXX flacoste 2007-02-21 bug=86861: We must # use field.vocabularyName instead of the vocabulary parameter # otherwise VocabularyPickerWidget will fail. target_field = Choice( __name__='target', title=field.title, description=field.description, vocabulary=field.vocabularyName, required=True) setUpWidget( self, target_field.__name__, target_field, IInputWidget, prefix=self.name) self.setUpOptions() def setUpOptions(self): """Set up options to be rendered.""" self.options = {} for option in ['all', 'project']: attributes = dict( type='radio', name=self.name, value=option, id='%s.option.%s' % (self.name, option)) if self.request.form_ng.getOne( self.name, self.default_option) == option: attributes['checked'] = 'checked' if option == 'project': attributes['onclick'] = ( "document.getElementById('field.scope.target').focus();") self.options[option] = renderElement('input', **attributes) self.target_widget.onKeyPress = ( "selectWidget('%s.option.project', event)" % self.name) def hasInput(self): """See zope.formlib.interfaces.IInputWidget.""" return self.name in self.request.form def hasValidInput(self): """See zope.formlib.interfaces.IInputWidget.""" try: self.getInputValue() return self.hasInput() except (InputErrors, UnexpectedFormData, LaunchpadValidationError): return False def getInputValue(self): """See zope.formlib.interfaces.IInputWidget.""" scope = self.request.form_ng.getOne(self.name) if scope == 'all': return None elif scope == 'project': if not self.request.form_ng.getOne(self.target_widget.name): self._error = WidgetInputError( self.name, self.label, LaunchpadValidationError('Please enter a project name')) raise self._error try: return self.target_widget.getInputValue() except ConversionError: entered_name = self.request.form_ng.getOne( "%s.target" % self.name) self._error = WidgetInputError( self.name, self.label, LaunchpadValidationError( "There is no project named '%s' registered in" " Launchpad" % entered_name)) raise self._error elif self.required: raise UnexpectedFormData("No valid option was selected.") else: return None def getScope(self): """Return the selected scope or None if it isn't selected.""" return self.request.form_ng.getOne(self.name) def setRenderedValue(self, value): """See IWidget.""" if value is None: self.default_option = 'all' self.target_widget.setRenderedValue(None) else: self.default_option = 'project' self.target_widget.setRenderedValue(value) self.setUpOptions() def __call__(self): """See zope.formlib.interfaces.IBrowserWidget.""" return "\n".join([ self.renderScopeOptions(), self.target_widget()]) def renderScopeOptions(self): """Render the HTML for the scope radio widgets.""" return dedent('''\ <label> %(all)s All projects </label> <label> %(project)s One project: </label> ''' % self.options) def error(self): """See zope.formlib.interfaces.IBrowserWidget""" if self._error: return self._error.doc() else: return u""