views:

1146

answers:

4

Dear all,

So far I have been trying to update the twitter profile bg image thr the twitter api with php... and without success

Many examples on the web, including this one:
http://stackoverflow.com/questions/1483163/updating-twitter-background-via-api
and this one
http://stackoverflow.com/questions/1485136/twitter-background-upload-with-api-and-multi-form-data
do not work at all, most ppl throw out answers without actually testing the code.

I found that directly submit the image to the twitter.com thr html form, it will work:

<form action="http://twitter.com/account/update_profile_background_image.xml" enctype="multipart/form-data" method="post">
    File: <input type="file" name="image" /><br/>
    <input type="submit" value="upload bg">
</form>

(although the browser will prompt you for the twitter account username and password)

However, if I want to go thr the same process with php, it fails

<?php
if( isset($_POST["submit"]) ) {

 $target_path = "";
 $target_path = $target_path . basename( $_FILES['myfile']['name']); 

 if(move_uploaded_file($_FILES['myfile']['tmp_name'], $target_path)) {
  // "The file ".  basename( $_FILES['myfile']['name']). " has been uploaded<br/>";
 } else{
  // "There was an error uploading the file, please try again!<br/>";
 }

    $ch = curl_init('http://twitter.com/account/update_profile_background_image.xml');
 curl_setopt($ch, CURLOPT_HTTPAUTH, CURLAUTH_ANY);
 curl_setopt($ch, CURLOPT_USERPWD, $_POST['name'] . ':' . $_POST['pass']);
 curl_setopt($ch, CURLOPT_HTTPHEADER, array('Expect:'));
 curl_setopt($ch, CURLOPT_TIMEOUT, 1);
 curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
 curl_setopt($ch, CURLOPT_POST, 1);
    curl_setopt($ch, CURLOPT_POSTFIELDS, array('image' => base64_encode(file_get_contents($target_path))));

    $rsp = curl_exec($ch);
 echo "<pre>" . str_replace("<", "&lt;", $rsp) . "</pre>";

}
?>
<form enctype="multipart/form-data" method="post">
<input type="hidden" name="submit" value="1"/>
name:<input type="text" name="name" value=""/><br/>
pass:<input type="password" name="pass" value=""/><br/>
File: <input type="file" name="myfile" /><br/>
<input type="submit" value="upload bg">
</form>

The strange thing of this code is that.. it successfully returns the twitter XML, WITHOUT having the profile background image updated. So at the end it still fails.

Many thanks for reading this. It will be great if you can help. Please kindly test your code first before throwing out answers, many many thanks.

A: 

Have you confirmed that the image you expect is present and being sent (i.e. echo out the base64 encoded data for verification)? Is it GIF/PNG/JPG and under the 800 kilobyte limit set by the API?

ceejayoz
of course. I tested using the same image file that is able to update inside twitter or the html form in my question, but the same image file failed for the php version
Unreality
And you've confirmed that the uploaded image is making it successfully to `$target_path`? If so, sounds like an issue with the Twitter API, and I'd suggest opening a ticket with them.
ceejayoz
hey but it works with the html form. pls read my question. It will be strange when it works with the html form but not in the php code.
Unreality
Please stop assuming I'm an idiot who hasn't read your question. The Twitter API is notoriously flaky, and often fails to work while the web interface works just fine. I've used similar code to yours to update background images, and that code works some days and not others, all dependent on how the API is feeling that day.
ceejayoz
Unreality
A: 

I think you're using the CURLOPT_POSTFIELDS method wrong. You need to put and @ sign in front of the full path to the file according to the documentation for curl PHP. You are not supposed to output the whole file contents.

The full data to post in a HTTP "POST" operation. To post a file, prepend a filename with @ and use the full path. This can either be passed as a urlencoded string like 'para1=val1&para2=val2&...' or as an array with the field name as key and field data as value. If value is an array, the Content-Type header will be set to multipart/form-data.

This is an example from the documentation.

<?php
/* http://localhost/upload.php:
print_r($_POST);
print_r($_FILES);
*/

$ch = curl_init();

$data = array('name' => 'Foo', 'file' => '@/home/user/test.png');

curl_setopt($ch, CURLOPT_URL, 'http://localhost/upload.php');
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, $data);

curl_exec($ch);
?>

I hope this helps.

Kristinn Örn Sigurðsson
unfortunately I have also tried the @ version before and it doesn't work at all. I have tried many ways to submit files to twitter, including using flash's URLLorder and flash's filereference's upload etc. Do you mind to make a real sample that really able to update the twitter background? Many many thanks.
Unreality
A: 

Right now no one can actualy update the profile background image nor the profile image. Twitter is working to fix that issue till then there is no fix.

streetparade
Not really. In fact you can update the bg image using the API thr plain html form as mentioned in my question. A plain html form like this http://code.dchammer.com/twitter/test3.php which directly submitted to Twitter. The problem lies in using the API thr php
Unreality
+4  A: 

This is what works for me (debug stuff left in):

$url      = 'http://twitter.com/account/update_profile_background_image.xml';
$uname    = 'myuname';
$pword    = 'mypword';
$img_path = '/path/to/myimage.jpg';
$userpwd  = $uname . ':' . $pword;
$img_post = array('image' => '@' . $img_path . ';type=image/jpeg',
                  'tile'  => 'true');

$opts = array(CURLOPT_URL => $url,
              CURLOPT_FOLLOWLOCATION => true,
              CURLOPT_RETURNTRANSFER => true,
              CURLOPT_HEADER => true,
              CURLOPT_POST => true,
              CURLOPT_POSTFIELDS => $img_post,
              CURLOPT_HTTPAUTH => CURLAUTH_ANY,
              CURLOPT_USERPWD => $userpwd,
              CURLOPT_HTTPHEADER => array('Expect:'),
              CURLINFO_HEADER_OUT => true);

$ch = curl_init();
curl_setopt_array($ch, $opts);
$response = curl_exec($ch);
$err      = curl_error($ch);
$info     = curl_getinfo($ch);
curl_close($ch);

echo '<pre>';
echo $err . '<br />';
echo '----------------' . '<br />';
print_r($info);
echo '----------------' . '<br />';
echo htmlspecialchars($response) . '<br />';
echo '</pre>';
GZipp
Many thanks for the full source!
Unreality