Testing forms
=============

Before we can begin, we need to setup a traversable folder.
Otherwise, Five won't get to to do its view lookup:

  >>> from Products.Five.tests.products.FiveTest.helpers import \
  ...     manage_addFiveTraversableFolder
  >>> manage_addFiveTraversableFolder(self.folder, 'ftf')


Add forms
---------

We can add objects to containers (object managers) through add forms.
An unprotected form can be accessed with anonymously:

  >>> print http(r"""
  ... GET /test_folder_1_/ftf/+/addfieldcontent.html HTTP/1.1
  ... """, handle_errors=False)
  HTTP/1.1 200 OK
  ...

For a protected one we need a manager account:

  >>> print http(r"""
  ... GET /test_folder_1_/ftf/+/protectedaddform.html HTTP/1.1
  ... Authorization: Basic manager:r00t
  ... """, handle_errors=False)
  HTTP/1.1 200 OK
  ...

otherwise we will fail to access it:

  >>> print http(r"""
  ... GET /test_folder_1_/ftf/+/protectedaddform.html HTTP/1.1
  ... Authorization: Basic viewer:secret
  ... """, handle_errors=False)
  Traceback (most recent call last):
  ...
  Unauthorized: ...

Now let's add a piece of our sample content object to test more things
on it:

  >>> print http(r"""
  ... POST /test_folder_1_/ftf/+/addfieldcontent.html HTTP/1.1
  ... Authorization: Basic manager:r00t
  ... Content-Type: multipart/form-data; boundary=---------------------------968064918930967154199105236
  ... Content-Length: 527
  ... 
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.title"
  ... 
  ... title
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.description"
  ... 
  ... 
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="UPDATE_SUBMIT"
  ... 
  ... Add
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="add_input_name"
  ... 
  ... edittest
  ... -----------------------------968064918930967154199105236--
  ... """, handle_errors=False)
  HTTP/1.1 302 Moved Temporarily
  ...
  Location: http://localhost/test_folder_1_/ftf/manage_main
  ...

Having added this piece of content, we can access it under its URL:

  >>> print http(r"""
  ... GET /test_folder_1_/ftf/edittest HTTP/1.1
  ... Authorization: Basic manager:r00t
  ... """, handle_errors=False)
  HTTP/1.1 200 OK
  ...

We can also verify that the title was set correctly, and the not
specified attribute is the default value:

  >>> edittest = self.folder.ftf.edittest
  >>> edittest.title
  u'title'
  >>> edittest.description #XXX shouldn't we get a u'' here???


Edit forms
----------

First, it's important to note that forms validate user input.
Therefore, if we specify invalid data, our object won't change:

  >>> print http(r"""
  ... POST /test_folder_1_/ftf/edittest/@@edit.html HTTP/1.1
  ... Authorization: Basic manager:r00t
  ... Content-Type: multipart/form-data; boundary=---------------------------968064918930967154199105236
  ... Content-Length: 418
  ... 
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.title"
  ... 
  ... 
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.description"
  ... 
  ... BarDescription
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="UPDATE_SUBMIT"
  ... 
  ... Change
  ... -----------------------------968064918930967154199105236--
  ... """, handle_errors=False)
  HTTP/1.1 200 OK
  ...
            There are <strong>1</strong> input errors.
  ...

We will see that nothing has changed:

  >>> edittest.title
  u'title'
  >>> edittest.description #XXX shouldn't we get a u'' here???

However, when we specify the correct fields:

  >>> print http(r"""
  ... POST /test_folder_1_/ftf/edittest/@@edit.html HTTP/1.1
  ... Authorization: Basic manager:r00t
  ... Content-Type: multipart/form-data; boundary=---------------------------968064918930967154199105236
  ... Content-Length: 426
  ... 
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.title"
  ... 
  ... FooTitle
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.description"
  ... 
  ... FooDescription
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="UPDATE_SUBMIT"
  ... 
  ... Change
  ... -----------------------------968064918930967154199105236--
  ... """, handle_errors=False)
  HTTP/1.1 200 OK
  ...

We will see that nothing has changed:

  >>> edittest.title
  u'FooTitle'
  >>> edittest.description
  u'FooDescription'


Unicode-safety of forms
-----------------------

Even though ZPublisher does not support unicode, automatically
generated forms do.  In the following we will enter the following two
chinese sequences (How do you do? and I'm doing good) in forms
(they're encoded in UTF-8 here):

  >>> ni_hao = '\xe4\xbd\xa0\xe5\xa5\xbd'
  >>> wo_hen_hao = '\346\210\221\345\276\210\345\245\275'

First, it's imaginable that we make a mistake and enter one of the
phrases in the integer field:

  >>> print http(r"""
  ... POST /test_folder_1_/ftf/+/addfieldcontent.html HTTP/1.1
  ... Authorization: Basic manager:r00t
  ... Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
  ... Content-Type: multipart/form-data; boundary=---------------------------968064918930967154199105236
  ... Content-Length: 418
  ... 
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.title"
  ... 
  ... ChineseTitle
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.description"
  ... 
  ... ChineseDescription
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.somenumber"
  ... 
  ... %s
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="UPDATE_SUBMIT"
  ... 
  ... Add
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="add_input_name"
  ... 
  ... unicodetest
  ... -----------------------------968064918930967154199105236--
  ... """ % ni_hao, handle_errors=False)
  HTTP/1.1 200 OK
  ...
            There are <strong>1</strong> input errors.
  ...

When we enter the unicode data in the right fields (the text fields),
the form will submit correctly and create the object:

  >>> print http(r"""
  ... POST /test_folder_1_/ftf/+/addfieldcontent.html HTTP/1.1
  ... Authorization: Basic manager:r00t
  ... Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
  ... Content-Type: multipart/form-data; boundary=---------------------------968064918930967154199105236
  ... Content-Length: 418
  ... 
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.title"
  ... 
  ... %s
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.description"
  ... 
  ... %s
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.somenumber"
  ... 
  ... 0
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="UPDATE_SUBMIT"
  ... 
  ... Add
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="add_input_name"
  ... 
  ... unicodetest
  ... -----------------------------968064918930967154199105236--
  ... """ % (ni_hao, wo_hen_hao), handle_errors=False)
  HTTP/1.1 302 Moved Temporarily
  ...
  Location: http://localhost/test_folder_1_/ftf/manage_main
  ...

We can test the object has the correct values, as unicode strings, of
course:

  >>> unicodetest = self.folder.ftf.unicodetest
  >>> unicodetest.title == ni_hao.decode('utf-8')
  True
  >>> unicodetest.description == wo_hen_hao.decode('utf-8')
  True
  >>> unicodetest.somenumber
  0

Of course, the same should apply to edit forms.  First, we happen to
again make the mistake of entering unicode data in the integer field:

  >>> print http(r"""
  ... POST /test_folder_1_/ftf/unicodetest/@@edit.html HTTP/1.1
  ... Authorization: Basic manager:r00t
  ... Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
  ... Content-Type: multipart/form-data; boundary=---------------------------968064918930967154199105236
  ... Content-Length: 418
  ... 
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.title"
  ... 
  ... ChineseTitle
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.description"
  ... 
  ... ChineseDescription
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.somenumber"
  ... 
  ... %s
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="UPDATE_SUBMIT"
  ... 
  ... Change
  ... -----------------------------968064918930967154199105236--
  ... """ % ni_hao, handle_errors=False)
  HTTP/1.1 200 OK
  ...
            There are <strong>1</strong> input errors.
  ...

We see that the object hasn't changed:

  >>> unicodetest.title == ni_hao.decode('utf-8')
  True
  >>> unicodetest.description == wo_hen_hao.decode('utf-8')
  True
  >>> unicodetest.somenumber
  0

Now we provide some valid form data:

  >>> print http(r"""
  ... POST /test_folder_1_/ftf/unicodetest/@@edit.html HTTP/1.1
  ... Authorization: Basic manager:r00t
  ... Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
  ... Content-Type: multipart/form-data; boundary=---------------------------968064918930967154199105236
  ... Content-Length: 418
  ... 
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.title"
  ... 
  ... %s
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.description"
  ... 
  ... %s
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.somenumber"
  ... 
  ... 1
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="UPDATE_SUBMIT"
  ... 
  ... Change
  ... -----------------------------968064918930967154199105236--
  ... """ % (wo_hen_hao, ni_hao), handle_errors=False)
  HTTP/1.1 200 OK
  ...

We see that the object's data has changed:

  >>> unicodetest.title == wo_hen_hao.decode('utf-8')
  True
  >>> unicodetest.description == ni_hao.decode('utf-8')
  True
  >>> unicodetest.somenumber
  1

Let's also not forget about List widgets.  Let's see if we can add an
element to the list:

  >>> print http(r"""
  ... POST /test_folder_1_/ftf/unicodetest/@@edit.html HTTP/1.1
  ... Authorization: Basic manager:r00t
  ... Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
  ... Content-Type: multipart/form-data; boundary=---------------------------968064918930967154199105236
  ... Content-Length: 418
  ... 
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.title"
  ... 
  ... %s
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.description"
  ... 
  ... %s
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.somenumber"
  ... 
  ... 1
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.somelist.add"
  ... 
  ... Add
  ... -----------------------------968064918930967154199105236--
  ... """ % (wo_hen_hao, ni_hao), handle_errors=False)
  HTTP/1.1 200 OK
  ...
  ...<input class="textType" id="field.somelist.0." name="field.somelist.0." size="20" type="text" value=""  />...
  ...

Now, let's enter some more Chinese:

  >>> de_guo = '\345\276\267\345\233\275'
  
  >>> print http(r"""
  ... POST /test_folder_1_/ftf/unicodetest/@@edit.html HTTP/1.1
  ... Authorization: Basic manager:r00t
  ... Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
  ... Content-Type: multipart/form-data; boundary=---------------------------968064918930967154199105236
  ... Content-Length: 418
  ... 
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.title"
  ... 
  ... %s
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.description"
  ... 
  ... %s
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.somenumber"
  ... 
  ... 1
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="field.somelist.0."
  ... 
  ... %s
  ... -----------------------------968064918930967154199105236
  ... Content-Disposition: form-data; name="UPDATE_SUBMIT"
  ... 
  ... Change
  ... -----------------------------968064918930967154199105236--
  ... """ % (wo_hen_hao, ni_hao, de_guo), handle_errors=False)
  HTTP/1.1 200 OK
  ...

The object's data will have changed accordingly:

  >>> unicodetest.somelist == [de_guo.decode('utf-8')]
  True

Object widget:
--------------

A little more complex is the ``ObjectWidget``.  Here we simply test
that the edit form works:

  >>> from Products.Five.tests.products.FiveTest.schemacontent import \
  ...     manage_addComplexSchemaContent
  >>> n = manage_addComplexSchemaContent(self.folder.ftf, 'objecttest')

  >>> print http(r"""
  ... GET /test_folder_1_/ftf/objecttest/@@edit.html HTTP/1.1
  ... """, handle_errors=False)
  HTTP/1.1 200 OK
  ...
