0
votes

I'm trying to upload a new image for a product with the prestashop webservice through a vb .net application, but I get the following error message:

"Unable to save this image".

The URL used to upload the image is this: http://localhost/prestashop/api/images/products/1 And the source code of the function that make the request is this:

Public Sub executeAddImage(ByVal resource As String, ByVal id As String, ByVal imageToAdd As Image)
    Dim response As String = Nothing

    Try
        Dim ms As New MemoryStream()
        imageToAdd.Save(ms, System.Drawing.Imaging.ImageFormat.Jpeg)
        Dim byteArray As Byte() = ms.ToArray()

        Dim requestUrl As String = Me.WebServiceURL & "/" & resource & "/" & id
        MsgBox(requestUrl)
        Dim webRequest As HttpWebRequest = DirectCast(System.Net.WebRequest.Create(requestUrl), HttpWebRequest)
        webRequest.Method = WebServicePrestashop.CRUDMethod.Create
        'webRequest.ContentType = "image/jpeg"
        webRequest.ContentType = "application/x-www-form-urlencoded"
        webRequest.Credentials = New NetworkCredential(Me.LoginName, WebServicePrestashop._password)
        webRequest.ContentLength = byteArray.Length
        MsgBox(byteArray.Length)
        ' Get the request stream
        Using dataStream As Stream = webRequest.GetRequestStream()
            dataStream.Write(byteArray, 0, byteArray.Length)
        End Using

        ' Get the response
        Using webResponse As HttpWebResponse = DirectCast(webRequest.GetResponse(), HttpWebResponse)
            If webResponse.StatusCode = HttpStatusCode.OK Then
                Using reader As New StreamReader(webResponse.GetResponseStream(), Encoding.UTF8)
                    Dim imageNew As Image = Image.FromStream(webResponse.GetResponseStream())
                End Using
            End If
        End Using

    Catch ex As WebException
        MsgBox(ex.Message.ToString())
        Dim reader As New StreamReader(ex.Response.GetResponseStream)
        MsgBox(reader.ReadToEnd)
    End Try
End Sub

I'm using the HTTP POST method, and the POST content is the bynary content of the new image.

How can I fix it?.

1

1 Answers

0
votes

Here the solution. I think the key is that I must write the body of the webrequest programatically adding to the stream of the webrequest the boundary (in binary array format), the Content-Type chain (in binary array format) and the content of the image to upload (in binary array format).

Public Sub executeAddImage(ByVal resource As String, ByVal id As String, ByVal imageToAdd As Byte())
    Dim response As String = Nothing


    Try
        Dim requestUrl As String = "urlShop" & "/api/" & resource & "/" & id
        MsgBox(requestUrl)
        Dim webRequest As HttpWebRequest = DirectCast(System.Net.WebRequest.Create(requestUrl), HttpWebRequest)
        webRequest.KeepAlive = True
        webRequest.Credentials = New NetworkCredential(Me.LoginName, WebServicePrestashop._password)
        webRequest.ContentLength = imageToAdd.Length
        webRequest.Method = "POST"
        webRequest.ContentType = "image/jpeg"


        Dim boundary As String = "----" & DateTime.Now.Ticks.ToString("x", CultureInfo.InvariantCulture)
        webRequest.ContentType = "multipart/form-data; boundary=" & boundary
        Dim beginPostData = "--" & boundary & vbCrLf & "Content-Disposition: form-data; name=""image""; filename=""torrente.jpg""" & _
            vbCrLf & "Content-Type: image/jpeg" & vbCrLf & vbCrLf
        Dim boundaryBytes = System.Text.Encoding.ASCII.GetBytes(vbCrLf & "--" & boundary & "--" & vbCrLf)
        Dim beginPostDataBytes = System.Text.Encoding.ASCII.GetBytes(beginPostData)


        webRequest.ContentLength = beginPostData.Length + imageToAdd.Length + boundaryBytes.Length


        ' Get the request stream
        Using dataStream As Stream = webRequest.GetRequestStream()
            dataStream.Write(beginPostDataBytes, 0, beginPostDataBytes.Length)
            dataStream.Write(imageToAdd, 0, imageToAdd.Length)
            dataStream.Write(boundaryBytes, 0, boundaryBytes.Length)
        End Using


        ' Get the response
        Using webResponse As HttpWebResponse = DirectCast(webRequest.GetResponse(), HttpWebResponse)
            If webResponse.StatusCode = HttpStatusCode.OK Then
                Using reader As New StreamReader(webResponse.GetResponseStream())
                    response = reader.ReadToEnd()
                    MsgBox(response)
                End Using
            End If
        End Using


    Catch ex As WebException
        MsgBox(ex.Message.ToString())
        Dim reader As New StreamReader(ex.Response.GetResponseStream)
        MsgBox(reader.ReadToEnd)
    End Try
End Sub