PHP get data from DELETE request - php

I am using jquery plugin for multiple file upload. Everything is working fine, except delete the images. Firebug say that JS it is sending DELETE request to the function. How can I get data from delete request?
PHP delete code:
public function deleteImage() {
//Get the name in the url
$file = $this->uri->segment(3);
$r = $this->session->userdata('id_user');
$q=$this->caffe_model->caffe_get_one_user($r);
$cff_name= $q->name;
$cff_id = $q->id_caffe;
$w = $this->gallery_model->gallery_get_one_user($gll_id);
$gll_name = $w->name;
$success = unlink("./public/img/caffe/$cff_name/$gll_name/" . $file);
$success_th = unlink("./public/img/caffe/$cff_name/$gll_name/thumbnails/" . $file);
//info to see if it is doing what it is supposed to
$info = new stdClass();
$info->sucess = $success;
$info->path = $this->getPath_url_img_upload_folder() . $file;
$info->file = is_file($this->getPath_img_upload_folder() . $file);
if (IS_AJAX) {//I don't think it matters if this is set but good for error checking in the console/firebug
echo json_encode(array($info));
} else { //here you will need to decide what you want to show for a successful delete
var_dump($file);
}
}
and JS is using jQuery-File-Upload plugin: link

Generally, if the DELETE request sends data in the request body, you can read the data by using the following code:
$data = file_get_contents("php://input");
Depending on the encoding of the data (usually JSON or form-encoded), you use json_decode or parse_str to read the data into usable variables.
For a simple example, see this article, where the author uses form-encoded data to handle a PUT request. DELETE works similarly.
In your case however, it looks like the file name is read from the request URL (the call to $this->uri->segment(3);). When I look at your code, it seems that the variable $gll_id is not initailized and you don't check if the resulting object $w and the variable $gll_name are empty. Maybe this is causing the delete to fail. Turn on error logging with ini_set("log_errors",1); and have a look at your server error log. If the unlink fails, the error log should contain the path PHP tried to unlink - it's likely that the path is not correct.

Related

Having issues requesting videos for a channel when the channel ID comes from a text file (PHP)

I have an issue getting the youtube api to work when I set some of the parameters to variables that are extracted from a text file.
I have a list of channelids that grows that I need to use to know which channels I need videos from.
When I assign the variable directly in the code it works fine.
When i cycle through the text file and insert each channel id into the url one by one my file_get_contents returns nothing.
When I do a print_r to see if the request url is correct when pulling channelId from file the url is actually correct. If i copy that to the browser or even do a curl request from the command line it actually works.
For some reason, however, the file_get_contents seems to return nothing for the same url.
I thought originally that the issue was that I needed to set allow_url_fopen to On so that I could use something from a file in the url in php.
This unfortunately didn't fix the issue.
function that I want to pass variable into
function createList($API_key,$channelID,$maxResults) {
$request = "https://www.googleapis.com/youtube/v3/search?order=date&part=snippet&channelId=".$channelID."&key=".$API_key."&maxResults=".$maxResults;
$videoList = json_decode(file_get_contents($request));
//processes list
}
working:
createList ($API_key, 'UC1sELGmy5jp5fQUugmuYlXQ', $maxResults, $request);
not working:
function whitelist($API_key, $maxResults) {
$handle = fopen("channels.txt", "r");
if ($handle) {
while (($line = fgets($handle)) !== false) {
$channel = $line;
createList($API_key, $channel, $maxResults);
}
fclose($handle);
} else {
// error opening the file.
}
}
whitelist($API_key, $maxResults, $request);
Maybe there are some "hidden characters" like a carriage return or line feed at the beginning or end of the lines you get from your textfile.

Silverstripe Image Upload is changing name

I am uploading an image and while storing the image, I am setting the Filename like 'assets/Uploads/54f092af271b9.png' but after saving, the Filename fields loses some part. It becomes 'assets/54f092af271b9.png' losing the "Uploads/" directory altogether. Is it supposed to happen?
Here's the codes:
<?php
$img = new Image();
$baseName = pathinfo($file, PATHINFO_BASENAME);
$fileName = 'assets/Uploads/' . $baseName;
var_dump($fileName);
$img->Name = $baseName;
$img->Filename = $fileName;
$img->OwnerID = ($memberID = Member::currentUserID()) ? $memberID : 0;
$img->write();
var_dump($img->Filename); exit;
Output is:
assets/Uploads/54f092af271b9.png
assets/54f092af271b9.png'
Any ideas?
I was able to replicate the issue with the code you provided. After a bit of digging around, here is what I found.
It all starts in the onAfterWrite function in File class (which Image extends). Fired after you called write (obviously), this calls updateFilesystem where this line sets the Filename property with the result of the getRelativePath function call.
At the time of writing, getRelativePath looks like this:
public function getRelativePath() {
if($this->ParentID) {
// Don't use the cache, the parent has just been changed
$p = DataObject::get_by_id('Folder', $this->ParentID, false);
if($p && $p->exists()) return $p->getRelativePath() . $this->getField("Name");
else return ASSETS_DIR . "/" . $this->getField("Name");
} else if($this->getField("Name")) {
return ASSETS_DIR . "/" . $this->getField("Name");
} else {
return ASSETS_DIR;
}
}
Looking at that code, the issue you have comes from ParentID not being set on your record when you wrote it to the DB so the second condition is run instead returning the result of ASSETS_DIR . "/" . $this->getField("Name").
So that is the problem addressed, now for a solution. Silverstripe wants a parent folder, you've just got to give it one.
Fortunately there is a great little function on the Folder class called find_or_make which does what the name says, either finds the folder record in the filesystem and DB or it will generate it for you.
Note: In my own testing, while I had an "Uploads" folder, I did not have a corresponding DB record so this function wrote that for me an returned the result.
I then used the result to give the image I was writing to the DB a ParentID and it made the second var_dump return the same value as the first.
This is all you need to add to your code before calling write:
$parentFolder = Folder::find_or_make('Uploads');
$img->setParentID($parentFolder->ID);

Instagram API: Get All User Media API and Store to File

I know the way to get all user media in instagram api with pagination. And we must request again with pagination url provided to get next photos.
I just wonder if i can save all of json api response include with next photos in pagination to one flat file for caching. The purpose is i can call all photos value from one file only, e.g: cache.json.
Is there a way to realize that in PHP Code if possible? Like using file_get and file_put function. Any help is appreciated so much :)
Here's my code, but need a tweak to fix it. Im using this wrapper https://github.com/cosenary/Instagram-PHP-API
require 'instagram.class.php';
$cache = './cache.json';
$instagram = new Instagram($accessToken);
$instagram->setAccessToken($accessToken);
$response = $instagram->getUserMedia($userID,$settings['count']);
do {
if($response){
file_put_contents($cache,json_encode($response)); //Save as json
}
} while ($response = $instagram->pagination($response));
echo 'finish';
With this code i getting the last pagination only. It seems the code overwrite the cache.json file, not adding.
Maybe you can suggest me how to fix it become adding, not overwriting.
-- Edit --
My code now working but not perfect, maybe you can try and fix it.
<?php
include('conf.php');
require 'instagram.class.php';
$cache = './cache_coba.json';
$instagram = new Instagram($accessToken);
$instagram->setAccessToken($accessToken);
$response = $instagram->getUserMedia($userID,$settings['count']);
while ($response = $instagram->pagination($response)) {
if($response){
$opn = file_get_contents($cache);
$opn .= json_encode($response);
file_put_contents($cache, $opn);
}
}
echo 'finish';
?>

displaying blob images - symfony

I have blob data in my database and they are images that I want to display as a basic gallery.
I have a method that I have written to display the images, but I'm getting an error, saying that it is a string, rather than blob data being returned:
public function getFilenamePath()
{
$file_src = false;
if (null !== $fp = $this->getFilename())
{
$file = stream_get_contents($fp);
$file_src = '/uploads/gallery/'.$this->getId().'.jpg';
}
return $file_src;
}
where getFilename() is my blob column.
action:
public function executeSingle(sfWebRequest $request)
{
$application_id = $this->getRequestParameter('id');
$c = new Criteria();
$c->addJoin(GalleryPeer::APPLICATION_ID, ApplicationPeer::ID);
$c->addJoin(GalleryImagePeer::GALLERY_ID, GalleryPeer::ID);
$c->add(GalleryPeer::APPLICATION_ID, $application_id);
$this->galleries = GalleryImagePeer::doSelect ( $c );
}
template:
foreach($galleries as $gallery)
{
$path = $gallery->getFilenamePath();
if($path)
{
echo '<img src="'.$path.'" />';
}
}
The error I get is that stream_get_contents seems to be returning a string.
Is there anyway, I can get the blob data, or rather than use a model method, use an action to return all the images attached to the application?
Thanks
If you store images in the database, you have (basically) two options to show them on the client:
First solution: Get file content and encode it with base64 encoding. You can find a working example here:
http://www.php.net/manual/en/function.base64-encode.php#99842
This method is not the best as if you do it like that, the client won't be able to cache these images, that means more traffic, more processing time, more database connection, slower page loading etc.
Second solution: You create an image loading action in Symfony. The routing is like:
mapimage:
url: /myimage/:image_id.png
param: { module: myimagemodul, action: myimageaction }
You have to create a controller action myimageaction and there you can get the image ID like
$request->getParameter('image_id');
And get the blob data from the database and return it as binary with specific http headers. You can find working examples with simple Googleing, one example:
$this->image = ImagePeer::retrieveByPk ($request->getParameter('image_id'));
$response = $this->getResponse();
$response->clearHttpHeaders();
$response->setContentType ($this->image->getMimeType());
$response->setHttpHeader ('Content-Disposition', 'inline;filename='.$filename);
$content = $this->image->getData();
$response->setContent (stream_get_contents ($content));
$this->setLayout (false);
return sfView::NONE;
So in the template you can do like:
<img src='<?= url_for ('route_to_action_above', array ('image_id' => $image->getId()) ?>'/>
I have found this one at
http://forum.symfony-project.org/viewtopic.php?f=22&t=31207#p109705
This code doesn't make any sense.
Why do you feed binary(read string) data from ->getFilename() to stream_get_contents() which operates ONLY on resource data type? Of course it will complain.
Outputing blob to a browser is as simple as:
$this->getResponse->setContentType('image/jpeg');
echo $data->getFilename(); // assuming filename column is your blob column
try switching your getFilenamePath function to this.
public function getFilenamePath() {
$file_src = '/uploads/gallery/'.$this->getId().'.jpg';
if (file_exists($file_src ) {
return $file_src;
} else {
return false;
}
}
$profile_picture = base64_encode(stream_get_contents($image->getContent()));
echo '<img src="data:image/jpeg;base64,'.$profile_picture.'" />';

Zend Framework: image upload

I want to upload an image with Zend Framework version 1.9.6. The uploading itself works fine, but I want a couple of other things as well ... and I'm completely stuck.
Error messages for failing to upload an image won't show up.
If a user doesn't enter all the required fields but has uploaded an image then I want to display the uploaded image in my form. Either as an image or as a link to the image. Just some form of feedback to the user.
I want to use Zend_ Validate_ File_ IsImage. But it doesn't seem to do anything.
And lastly; is there some automatic renaming functionality?
All ideas and suggestions are very welcome. I've been struggling for two days now.
These are simplified code snippets:
myform.ini
method = "post"
elements.title.type = "text"
elements.title.options.label = "Title"
elements.title.options.attribs.size = 40
elements.title.options.required = true
elements.image.type = "file"
elements.image.options.label = "Image"
elements.image.options.validators.isimage.validator = "IsImage"
elements.submit.type = "submit"
elements.submit.options.label = "Save"
TestController
<?php
class Admin_TestController extends Zend_Controller_Action
{
public function testAction ()
{
$config = new Zend_Config_Ini(MY_SECRET_PATH . 'myform.ini');
$f = new Zend_Form($config);
if ($this->_request->isPost())
{
$data = $this->_request->getPost();
$imageElement = $f->getElement('image');
$imageElement->receive();
//$imageElement->getValue();
if ($f->isValid($data))
{
//save data
$this->_redirect('/admin');
}
else
{
$f->populate($data);
}
}
$this->view->form = $f;
}
}
?>
My view just echo's the 'form' variable.
First, put this at the start of your script:
error_reporting(E_ALL);//this should show all php errors
I think the error messages are missing from the form because you re-populate the form before you display it. I think that wipes out any error messages. To fix that, remove this part:
else
{
$f->populate($data);
}
To show the uploaded image in the form, just add a div to your view template, like this:
<div style="float:right"><?=$this->image?></div>
If the image uploaded ok, then populate $view->image with an img tag.
As for automatic re-naming, no, it's not built in, but it's very easy. I'll show you how below.
Here's how I handle my image uploads:
$form = new Zend_Form();
$form->setEnctype(Zend_Form::ENCTYPE_MULTIPART);
$image = new Zend_Form_Element_File('image');
$image->setLabel('Upload an image:')
->setDestination($config->paths->upload)
->setRequired(true)
->setMaxFileSize(10240000) // limits the filesize on the client side
->setDescription('Click Browse and click on the image file you would like to upload');
$image->addValidator('Count', false, 1); // ensure only 1 file
$image->addValidator('Size', false, 10240000); // limit to 10 meg
$image->addValidator('Extension', false, 'jpg,jpeg,png,gif');// only JPEG, PNG, and GIFs
$form->addElement($image);
$this->view->form = $form;
if($this->getRequest()->isPost())
{
if(!$form->isValid($this->getRequest()->getParams()))
{
return $this->render('add');
}
if(!$form->image->receive())
{
$this->view->message = '<div class="popup-warning">Errors Receiving File.</div>';
return $this->render('add');
}
if($form->image->isUploaded())
{
$values = $form->getValues();
$source = $form->image->getFileName();
//to re-name the image, all you need to do is save it with a new name, instead of the name they uploaded it with. Normally, I use the primary key of the database row where I'm storing the name of the image. For example, if it's an image of Person 1, I call it 1.jpg. The important thing is that you make sure the image name will be unique in whatever directory you save it to.
$new_image_name = 'someNameYouInvent';
//save image to database and filesystem here
$image_saved = move_uploaded_file($source, '/www/yoursite/images/'.$new_image_name);
if($image_saved)
{
$this->view->image = '<img src="/images/'.$new_image_name.'" />';
$form->reset();//only do this if it saved ok and you want to re-display the fresh empty form
}
}
}
First, have a look at the Quick Start tutorial. Note how it has an ErrorController.php that will display error messages for you. Also note how the application.ini has these lines to cause PHP to emit error messages, but make sure you're in the "development" environment to see them (which is set in public/.htaccess).
phpSettings.display_startup_errors = 1
phpSettings.display_errors = 1
Second, ZF has a renaming filter for file uploads:
$upload_elt = new Zend_Form_Element_File('upload');
$upload_elt
->setRequired(true)
->setLabel('Select the file to upload:')
->setDestination($uploadDir)
->addValidator('Count', false, 1) // ensure only 1 file
->addValidator('Size', false, 2097152) // limit to 2MB
->addValidator('Extension', false, 'doc,txt')
->addValidator('MimeType', false,
array('application/msword',
'text/plain'))
->addFilter('Rename', implode('_',
array($this->_user_id,
$this->_upload_category,
date('YmdHis'))))
->addValidator('NotExists', false, $uploadDir)
;
Some of the interesting things above:
mark the upload as required (which your .ini doesn't seem to do)
put all the uploads in a special directory
limit file size and acceptable mime types
rename upload to myuser_category_timestamp
don't overwrite an existing file (unlikely, given our timestamp scheme, but let's make sure anyway)
So, the above goes in your form. In the controller/action that receives the upload, you could do this:
$original_filename = $form->upload->getFileName(null, false);
if ($form->upload->receive()) {
$model->saveUpload(
$this->_identity, $form->upload->getFileName(null, false),
$original_filename
);
}
Note how we capture the $original_filename (if you need it) before doing receive(). After we receive(), we do getFileName() to get the thing that the rename filter picked as the new filename.
Finally, in the model->saveUpload method you could store whatever stuff to your database.
Make sure your view also outputs any error messages that you generate in the controller: loading errors, field validation, file validation. Renaming would be your job, as would other post processing such as by image-magick convert.
When following lo_fye's listing I experienced problems with custom decorators.
I do not have the default File Decorator set and got the following exception:
Warning: Exception caught by form: No file decorator found... unable to render file element Stack Trace:
The Answer to this is that one of your decrators must implement the empty interface Zend_Form_Decorator_Marker_File_Interface
Also sometimes it happens to bug when using an ajax request. Try it without an ajax request and don't forget the multipart form.

Categories