New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add support for multiple file input #281

Merged
merged 1 commit into from Jul 15, 2016

Conversation

5 participants
@davidism
Member

davidism commented Jun 22, 2016

Took a similar approach to SelectField and SelectMultipleField. The FileInput widget now takes a multiple argument, and there are two fields FileField and MultipleFileField.

FileField is no longer based on StringField, since it's only a coincidence that the data is a string. I updated the docs to clarify that extensions might change what data is passed to this field (see Flask-WTF for example).

If no data is passed to the field, its data is None rather than the empty string. There was no test for this before, so I figured it was ok to break this. None makes more sense for "no file was uploaded". The multiple field will have an empty list for no data.

FileInput always sets value to False so that it is not rendered. Browsers won't honor the value of a file input for security reasons anyway. FileField._value returns False as well, to be consistent if the widget it changed.

An alternate implementation could use one FileField with a multiple argument as well. I'm willing to implement that instead if it sounds better.

This patch contains #280 (call process_formdata if formdata is empty) since testing this ran into that issue. Merging this after that, or just closing that, should both work in git.

@davidism davidism merged commit 78ba1d6 into wtforms:master Jul 15, 2016

2 checks passed

continuous-integration/travis-ci/pr The Travis CI build passed
Details
coverage/coveralls Coverage increased (+0.003%) to 99.697%
Details

@davidism davidism deleted the davidism:multiple_file_field branch Jul 15, 2016

@nblomqvist

This comment has been minimized.

nblomqvist commented Jan 4, 2017

Would it be suitable to override the validation process of MultipleFileField such that validators do not need to be rewritten to also (and explicitly) handle multiple values?

@davidism

This comment has been minimized.

Member

davidism commented Jan 4, 2017

What validators need to be rewritten? You should be able to use DataRequired and Length, although I realize there's no test for it.

@nblomqvist

This comment has been minimized.

nblomqvist commented Jan 4, 2017

Sorry for being unclear. I was thinking of validators that people have written themselves, that are used for an input with a single value (e.g. a field holding a single FileStorage object), but that could just as well be applicable to multiple files. For example, I assume each validator in Flask-WTF will need to be rewritten to handle multiple files.

@davidism

This comment has been minimized.

Member

davidism commented Jan 4, 2017

Yes, that one's linked above and I'm assigned to it. 😉 I'm going to stick with rewriting that validator to work with either a single value or a list. I'm not sure what you have in mind for overriding validate that would allow the validator to work as-is. If you'd like to discuss it further, open a new issue or PR.

@nblomqvist

This comment has been minimized.

nblomqvist commented Jan 4, 2017

Got it, thanks. I'll open an issue in the near future with an example on what I was thinking.

@DuncanBetts

This comment has been minimized.

DuncanBetts commented Mar 6, 2017

I've been getting ImportError trying this:

from wtforms.fields import MultipleFileField

I can see that MultipleFileField is being imported from simple into field's init.py.

I've tried some other import statements (not expecting anything), to no avail.

I've looked in the source code for tagged release 2.1, and can see MultipleFileField in the right place.

Any idea what I'm doing wrong? I'm hoping to use this along with Flask-Uploads, closest example of this I've found is http://www.patricksoftwareblog.com/tag/flask-uploads/ (with a FileField).

Also, I've looked on Github Search, and can find no examples of anyone using this field type.

@davidism

This comment has been minimized.

Member

davidism commented Mar 6, 2017

This isn't released yet, not sure what code you're looking at.

@DuncanBetts

This comment has been minimized.

DuncanBetts commented Mar 6, 2017

I read about the field here:

WTForms Documentation

Thanks for clarifying.

@davidism

This comment has been minimized.

Member

davidism commented Mar 6, 2017

Those are the "latest" docs, i.e. the development docs. 2.1 is here: http://wtforms.readthedocs.io/en/2.1/fields.html. Unfortunately, I don't have maintainer access to the docs yet.

@Jigsaw-Jams

This comment has been minimized.

Jigsaw-Jams commented Mar 24, 2017

@davidism Do you have any idea when the latest version will be released?

Also for the time being I'm hunting for a workaround. I've been doing: form.files(class_="form-control", multiple="") but then I need to write filetype/extension validation in the view function.

I tried writing a validate_files() method in the form class, but it only had access to the first file. Same with FileAllowed from Flask-WTF (it only validates against the first file being uploaded).

Overall main goal is to have a single <input type="file" multiple> that gets validated when running validate_on_submit(), I want to remove all the logic involved in checking the file extension from the view function.

If anyone has any ideas they would be greatly appreciated!

@davidism

This comment has been minimized.

Member

davidism commented Mar 24, 2017

As a temporary fix, you can always pull this patch into your own code, the fields don't have to be in the WTForms package to work.

As to the next release, I still have not received maintainer access for the majority of the tools (PyPI, Read the Docs, and org access on GitHub). I maintain a lot of Flask-related projects and have limited time, but will start focusing on this more once I have full access so that things go smoothly.

All I can do for now is merge PRs. Any help in the form of triage of existing issues and creating pull requests, tests, and docs is very helpful towards getting a new release ready.

@r4jk3

This comment has been minimized.

r4jk3 commented Apr 20, 2018

Whats the status of this bug?
Any breakthrough?

It would be nice to see MultipleFileField in action.

ftm pushed a commit to ftm/wtforms that referenced this pull request May 10, 2018

davidism added a commit that referenced this pull request May 11, 2018

@abulte abulte referenced this pull request Jun 4, 2018

Merged

Update wtforms to 2.2 #1713

netbsd-srcmastr pushed a commit to NetBSD/pkgsrc that referenced this pull request Nov 12, 2018

py-wtforms: Update to 2.2.1.
Version 2.2.1
-------------

Released on June 7th, 2018

-   :class:`~fields.StringField` only sets ``data = ''`` when form data
    is empty and an initial value was not provided. This fixes an issue
    where the default value wasn't rendered with the initial form.
    (`#291`_, `#401`_)

.. _#291: wtforms/wtforms#291
.. _#401: wtforms/wtforms#401


Version 2.2
-----------

Released on June 2nd, 2018

-   Merged new and updated translations from the community.
-   Passing ``data_`` args to render a field converts all the
    underscores to hyphens when rendering the HTML attribute, not just
    the first one. ``data_foo_bar`` becomes ``data-foo-bar``. (`#248`_)
-   The :class:`~validators.UUID` validator uses the :class:`uuid.UUID`
    class instead of a regex. (`#251`_)
-   :class:`~fields.SelectField` copies the list of ``choices`` passed
    to it so modifying an instance's choices will not modify the global
    form definition. (`#286`_)
-   Fields call :meth:`~fields.Field.process_formdata` even if the raw
    data is empty. (`#280`_)
-   Added a :class:`~fields.MultipleFileField` to handle a multi-file
    input. :class:`~fields.FileField` continues to handle only one
    value. The underlying :class:`~widgets.FileInput` widget gained a
    ``multiple`` argument. (`#281`_)
-   :class:`~fields.SelectField` choices can contain HTML (MarkupSafe
    ``Markup`` object or equivalent API) and will be rendered properly.
    (`#302`_)
-   :class:`~fields.TimeField` and
    :class:`html5.TimeField <fields.html5.TimeField>` were added.
    (`#254`_)
-   Improved :class:`~validators.Email`. Note that it is still
    unreasonable to validate all emails with a regex and you should
    prefer validating by actually sending an email. (`#294`_)
-   Widgets render the ``required`` attribute when using a validator
    that provides the ``'required'`` flag, such as
    :class:`~validators.DataRequired`. (`#361`_)
-   Fix a compatibility issue with SQLAlchemy 2.1 that caused
    :class:`~ext.sqlalchemy.fields.QuerySelectField` to fail with
    ``ValueError: too many values to unpack``. (`#391`_)

.. _#248: wtforms/wtforms#248
.. _#251: wtforms/wtforms#251
.. _#254: wtforms/wtforms#254
.. _#280: wtforms/wtforms#280
.. _#281: wtforms/wtforms#281
.. _#286: wtforms/wtforms#286
.. _#294: wtforms/wtforms#294
.. _#302: wtforms/wtforms#302
.. _#361: wtforms/wtforms#361
.. _#391: wtforms/wtforms#391
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment