Upload File (Data can't be blank)

221 views
Skip to first unread message

Heubel

unread,
Dec 23, 2009, 12:29:03 PM12/23/09
to StreamSend API Discuss
Does anybody could upload files using VB language? I'm using
WinHTTP.WinHTTPRequest.5.1 but it only shows error 442:
<errors><error>Data can't be blank</error></errors>. Some example
would be very nice.

Ian Lesperance

unread,
Dec 23, 2009, 1:01:45 PM12/23/09
to streamsend-...@googlegroups.com
Make sure you're sending a multipart form request and that the file contents are being stored in the "data" form variable.

Ian

Raymond Attipa

unread,
Dec 23, 2009, 2:15:06 PM12/23/09
to streamsend-...@googlegroups.com
Yes, someone PLEASE put a build for asp.net using vb.

Heubel

unread,
Dec 23, 2009, 5:50:04 PM12/23/09
to StreamSend API Discuss
Ian, thanks for your hints. I have tried but until now I could't. I'll
post my code, maybe you or somebody else could bring us some
enlightment?

This code is LotusScript but quite similar to VB.

'Declare Strings
Dim str_auth, str_boundary As String

'Declare long
Dim lng_resolveTimeout, lng_connectTimeout, lng_sendTimeout,
lng_receiveTimeout As Long

'Declare integer
Dim int_serverCredentials As Integer

'Declare variants
Dim var_submitObject As Variant

'Set values
int_serverCredentials = 0
lng_resolveTimeout = 120000 'miliseconds = 2 minutes
lng_connectTimeout = 1200000
lng_sendTimeout = 1200000
lng_receiveTimeout = 1200000

'Create HTTP object
Set var_submitObject = CreateObject("WinHTTP.WinHTTPRequest.5.1")
Call var_submitObject.SetTimeouts(lng_resolveTimeout,
lng_connectTimeout, lng_sendTimeout, lng_receiveTimeout)

'Standards for this post
%REM
Content-Type: multipart/form-data; boundary={boundary}
{boundary}
Content-Disposition: form-data; name="data"; filename="{filename}"
Content-Type: text/plain
{contents}
{boundary}--
%END REM

'Set post parameters
Call var_submitObject.open("POST", "https://app.streamsend.com/
uploads", False)
Call var_submitObject.setRequestHeader("Accept", "application/xml")
Call var_submitObject.setRequestHeader("Authorization", "Basic " &
str_auth)
Call var_submitObject.setRequestHeader("Content-Type", "multipart/form-
data; boundary=b1")
str_boundary = |--b1| & Chr(13) &_
|Content-Disposition: form-data; name="data";
filename="name.txt"| & Chr(13) &_
|Content-Type: text/plain| & Chr(13) &_
str_fileContent & |b1--|
'Send the HTTP request
Call var_submitObject.Send(str_boundary)
'Wait for the answer and set object as returned value for further
validation
Call var_submitObject.WaitForResponse
Set submitHTTP = var_submitObject
'Clear memory
Set var_submitObject = Nothing

Question: Shoud str_fileContent be the content of name.txt in full
string?

On Dec 23, 4:01 pm, Ian Lesperance <i...@streamsend.com> wrote:
> Make sure you're sending a multipart form request and that the file contents
> are being stored in the "data" form variable.
>
> Ian
>

Ian Lesperance

unread,
Jan 8, 2010, 1:00:26 PM1/8/10
to streamsend-...@googlegroups.com
Yes, it should be the full contents of the file.  But there are a few other problems that I think I see:

I believe the first part of str_boundary should be |b1|, not |--b1|.  This is just a literal string, right?  And b1 is your boundary string?  If that's true, then it should be on that line by itself, with nothing before or after it.

You need two empty lines between the multipart headers in the body and the content of the file.  So add another Chr(13) between the |Content-Type: text/plain| and str_fileContent.

The trailing boundary should be on a line by itself, so you'll need a Chr(13) between str_fileContent and |b1--|.  (The trailing "--" is correct for the final boundary.)

Ian

Heubel

unread,
Jan 14, 2010, 5:36:51 PM1/14/10
to StreamSend API Discuss
Hi Ian, thanks for your reply, once more we have worked on the code
but it is now showing us error 442 (data can't be blank), instead of
error 500. Could you please tell us where the mistake is? Surelly we
are missing something but we can't find it.

'Create HTTP object
Set var_submitObject = CreateObject("WinHTTP.WinHTTPRequest.5.1")
Call var_submitObject.SetTimeouts(lng_resolveTimeout,
lng_connectTimeout, lng_sendTimeout, lng_receiveTimeout)

'Set post parameters
Call var_submitObject.open(str_method, doc_profile.APIURL(0) &
str_URI, False)


Call var_submitObject.setRequestHeader("Authorization", "Basic " &
str_auth)
Call var_submitObject.setRequestHeader("Accept", "application/xml")

Call var_submitObject.setRequestHeader("Content-Type", "multipart/
form-data")

If str_contentType = "multipart/form-data" Then
str_content = "Content-Type: multipart/form-data; boundary=b1"
str_content = str_content & Chr(13) & Chr(13)
str_content = str_content & |b1|
str_content = str_content & Chr(13)
str_content = str_content & |Content-Disposition: form-data;
name="data"; filename="import.txt"|
str_content = str_content & Chr(13)
str_content = str_content & |Content-Type: text/plain|
str_content = str_content & Chr(13) & Chr(13)
str_content = str_content & |no...@none.com|
str_content = str_content & Chr(13)
str_content = str_content & |b1--|
End If

Call var_submitObject.Send(str_content)

On Jan 8, 4:00 pm, Ian Lesperance <i...@streamsend.com> wrote:
> Yes, it should be the full contents of the file.  But there are a few other
> problems that I think I see:
>
> I believe the first part of str_boundary should be |b1|, not |--b1|.  This
> is just a literal string, right?  And b1 is your boundary string?  If that's
> true, then it should be on that line by itself, with nothing before or after
> it.
>
> You need two empty lines between the multipart headers in the body and the
> content of the file.  So add another Chr(13) between the |Content-Type:
> text/plain| and str_fileContent.
>
> The trailing boundary should be on a line by itself, so you'll need a
> Chr(13) between str_fileContent and |b1--|.  (The trailing "--" is correct
> for the final boundary.)
>
> Ian
>

Ian Lesperance

unread,
Jan 14, 2010, 6:12:09 PM1/14/10
to streamsend-...@googlegroups.com
It looks like you're now duplicating the multipart Content-Type header in the body and only declaring the boundary that second time:

On Thu, Jan 14, 2010 at 2:36 PM, Heubel <heube...@gmail.com> wrote:
       Call var_submitObject.setRequestHeader("Content-Type", "multipart/
form-data")

       If str_contentType = "multipart/form-data" Then
               str_content = "Content-Type: multipart/form-data; boundary=b1"
               str_content = str_content & Chr(13) & Chr(13)
               str_content = str_content & |b1|


You should only specify that Content-Type once, and not in the body.  You also probably don't need those first two explicit newlines.  The library you're using will probably do that for you.

        Call var_submitObject.setRequestHeader("Content-Type", "multipart/
form-data; boundary=b1")

        str_content = |b1|
        ...

Ian

Heubel

unread,
Jan 15, 2010, 7:43:08 AM1/15/10
to StreamSend API Discuss
Hi Ian,

If doing like you told, we receive again error 500.

'Set post parameters
Call var_submitObject.open(str_method, doc_profile.APIURL(0) &
str_URI, False)
Call var_submitObject.setRequestHeader("Authorization", "Basic " &
str_auth)
Call var_submitObject.setRequestHeader("Accept", "application/xml")

Call var_submitObject.setRequestHeader("Content-Type", "multipart/form-
data; boundary=b1")
str_content = |b1|

str_content = str_content & Chr(13)

str_content = str_content & |Content-Disposition: form-data;
name="data"; filename="import.txt"|

str_content = str_content & Chr(13)

str_content = str_content & |Content-Type: text/plain|

str_content = str_content & Chr(13) & Chr(13)

str_content = str_content & |"no...@none.com"|


str_content = str_content & Chr(13)

str_content = str_content & |b1--|

Call var_submitObject.Send(str_content)

If we declare like this (as before) then we receive error 442 (data
can't be blank):

Call var_submitObject.open(str_method, doc_profile.APIURL(0) &
str_URI, False)
Call var_submitObject.setRequestHeader("Authorization", "Basic " &
str_auth)
Call var_submitObject.setRequestHeader("Accept", "application/xml")

Call var_submitObject.setRequestHeader("Content-Type", "multipart/form-
data")

str_content = "Content-Type: multipart/form-data; boundary=b1"
str_content = str_content & Chr(13) & Chr(13)

str_content = |b1|


str_content = str_content & Chr(13)

str_content = str_content & |Content-Disposition: form-data;
name="data"; filename="import.txt"|

str_content = str_content & Chr(13)

str_content = str_content & |Content-Type: text/plain|

str_content = str_content & Chr(13) & Chr(13)

str_content = str_content & |"no...@none.com"|


str_content = str_content & Chr(13)

str_content = str_content & |b1--|

Call var_submitObject.Send(str_content)

What can we do to fix it?

Kind regards.


On Jan 14, 9:12 pm, Ian Lesperance <i...@streamsend.com> wrote:
> It looks like you're now duplicating the multipart Content-Type header in
> the body and only declaring the boundary that second time:
>

Heubel

unread,
Jan 15, 2010, 7:48:18 AM1/15/10
to StreamSend API Discuss
Sorry there's a typo in one line, actually we have the code as:

str_content = str_content & |b1|

On Jan 15, 10:43 am, Heubel <heubelm...@gmail.com> wrote:
> Hi Ian,
>
> If doing like you told, we receive again error 500.
>
> 'Set post parameters
> Call var_submitObject.open(str_method, doc_profile.APIURL(0) &
> str_URI, False)
> Call var_submitObject.setRequestHeader("Authorization", "Basic " &
> str_auth)
> Call var_submitObject.setRequestHeader("Accept", "application/xml")
> Call var_submitObject.setRequestHeader("Content-Type", "multipart/form-
> data; boundary=b1")
> str_content = |b1|
> str_content = str_content & Chr(13)
> str_content = str_content & |Content-Disposition: form-data;
> name="data"; filename="import.txt"|
> str_content = str_content & Chr(13)
> str_content = str_content & |Content-Type: text/plain|
> str_content = str_content & Chr(13) & Chr(13)

> str_content = str_content & |"n...@none.com"|


> str_content = str_content & Chr(13)
> str_content = str_content & |b1--|
> Call var_submitObject.Send(str_content)
>
> If we declare like this (as before) then we receive error 442 (data
> can't be blank):
>
> Call var_submitObject.open(str_method, doc_profile.APIURL(0) &
> str_URI, False)
> Call var_submitObject.setRequestHeader("Authorization", "Basic " &
> str_auth)
> Call var_submitObject.setRequestHeader("Accept", "application/xml")
> Call var_submitObject.setRequestHeader("Content-Type", "multipart/form-
> data")
> str_content = "Content-Type: multipart/form-data; boundary=b1"
> str_content = str_content & Chr(13) & Chr(13)
> str_content = |b1|
> str_content = str_content & Chr(13)
> str_content = str_content & |Content-Disposition: form-data;
> name="data"; filename="import.txt"|
> str_content = str_content & Chr(13)
> str_content = str_content & |Content-Type: text/plain|
> str_content = str_content & Chr(13) & Chr(13)

> str_content = str_content & |"n...@none.com"|

Heubel

unread,
Jan 15, 2010, 8:43:58 PM1/15/10
to StreamSend API Discuss
Ian, as written in StreamSend API Documentation:

"As explained above, it is important that the Content-Type be
multipart/form-data. For simplicity, you may have been setting an
explicit Content-Type of application/xml on all of your other API
calls. If you were, you will need to override it (or remove it) for
this particular call. If you fail to do this, you will receive a +500+
response."

So, every value besides "multipart/form-data" will receive error 500.
But for WinHTTP library, you have to implement another condition for
the API because we have to pass the value as: "multipart/form-data;
boundary={boundary}" then the error 500 will not be presented and
things will surely start working.

On Jan 14, 9:12 pm, Ian Lesperance <i...@streamsend.com> wrote:
> It looks like you're now duplicating the multipart Content-Type header in
> the body and only declaring the boundary that second time:
>

Patrik Potocki

unread,
Feb 18, 2010, 10:20:38 AM2/18/10
to StreamSend API Discuss
Feels like no one can get the upload to work under .NET :S Need
working sample code!
Reply all
Reply to author
Forward
0 new messages