Codeigniter set_output function not working with image - codeigniter

I am trying to get the image as output, but it seems like set_output() function is not working properly with content type jpeg
My Code is given below...
$image = file_get_contents('assets/images/ThinkstockPhotos-145054512_small.jpg');
$this->output->set_content_type('jpeg')->set_output($image);
When I replace the image with a plain text file, in that case, it shows me the correct output
$file = file_get_contents('assets/images/test.txt');
$this->output->set_content_type('text')->set_output($file);
I have change content type from set_content_type('jpeg') to set_content_type('jpg') and set_content_type('gif') but stil it does not work and not show me on output.
What output I am getting now is shown in screenshot given below.

I was able to replicate the issue on my localhost setup only when I provided file_get_contents either a (1) bad path or (2) a non-existent image. I think you need to provide a full path to the image as with any directory/file related operation.
Try using FCPATH that is where you index.php lies and I assume your assets/ folder as well.
public function index() {
$file = FCPATH . 'assets/images/ThinkstockPhotos-145054512_small.jpg';
if (!is_file($file)) {
exit('File not found!');
}
$image = file_get_contents($file);
$this->output->set_content_type('jpeg')->set_output($image);
}
Note: if you get File not found! then assure that the file exists in /htdocs/assets/... where /htdocs/index.php is your main CI file

Related

Laravel putFileAs with External URL not working

Trying to save an external URL image, to my s3.
But when I use code below, it returns error.
$contents = file_get_contents($url);
$filename = Str::slug($findproduct->title)."-".uniqid().".".$extension;
Storage::disk('s3')->putFileAs('product', $contents, $filename, ['visibility' => 'public']);
Here's error:
fopen() expects parameter 1 to be a valid path, string given
fopen() is the first function called by putFileAs API Docs.
It attempts to open the File supplied as parameter 2 to putFileAs(), in your case this is $contents. (FWIW, newer versions of Laravel also accept a string as a file path here)
It expects this to be either a File or UploadedFile object.
file_get_contents() returns a string instead.
Try using this instead:
$contents = new File($url);

How to get file as a resource with Storage?

I am trying to lock a file with the flock function but I am not able to do it. I work with Laravel 8 and Storage Class.
The code is as follows:
$disk = Storage::disk('communication');
$file_name = 'received.json';
$file_exists = $disk->exists($file_name);
if($file_exists){
flock($disk->get($file_name), LOCK_EX);
...
}
The problem I'm having is that when I invoke the get() function on the file path, it returns the contents of the file (a string), which causes the following error:
flock() expects parameter 1 to be resource, string given
I need to know how to get file as a resource and not the content of the file.
Could someone help me and tell me how to do it?
Thank you very much in advance.
You can use Storage::readStream() method
if($file_exists){
$stream=Storage::disk('communication')->readStream($file_name);
flock($stream, LOCK_EX);
}
As per php doc
flock(resource $stream, int $operation, int &$would_block = null): bool
First param needed stream.flock() allows you to perform a simple
reader/writer model which can be used on virtually every platform
(including most Unix derivatives and even Windows).
Ref:https://www.php.net/manual/en/function.flock.php

Generate Excel file with PhpSpreadsheet in Codeigniter from a view

I am trying to generate an Excel file with CodeIgniter and the PhpSpreadsheet library from a view. The reports that I need to make are not a list but much more complex and I can generate them more quickly with a view and sending parameters. This is my code:
$data = $this->model->bringdata();
$view = $this->load->view("data_view", $ data);
$spreadsheet = new Spreadsheet();
$writer = new \PhpOffice\PhpSpreadsheet\Writer\Html($spreadsheet);
$writer-> save($view);
And the following error is shown
Severity: Warning
Message: fopen (): Filename can not be empty
Filename: Writer / Html.php
Line Number: 160
In the PhpSpreadsheet documentation it shows that an html page must be explicitly sent:
$writer->save("05featuredemo.htm");
Is there any way to do what I need?
Thanks for the help
It's a simple solution, you need to pass true to the third argument of load->view in order for it to return a string rather than sending it to the browser.
$view = $this->load->view("data_view", $ data, true);
Added after comment
I made the mistake of not looking into how the Html writer works.
The HTML writer writes a spreadsheet as an html file. It does not create a spreadsheet. As I understand it (and I might be mistaken) you can use \PhpOffice\PhpSpreadsheet\Reader\Html to read an html file into a spreadsheet.
In your case I think you will have to save the string returned from $this->load->view() to a temporary file. CodeIgniter's file_helper might be useful here.
You then read the temporary file to create a spreadsheet. After that you can use $writer to save the spreadsheet somewhere as any of the file types the PhpSpreadsheet supports.
$view = $this->load->view("data_view", $data, true);
$this->load->helper("file");
$fileName = "temp_file_name.html";
$path = "full/path/to/some_writable_folder/";
$path_file = $path . $fileName;
if (write_file($path_file, $view))
{
//create spreadsheet the temp html
$reader = new \PhpOffice\PhpSpreadsheet\Reader\Html();
$spreadsheet = $reader->load($path_file);
//write out to html file
$writer = new \PhpOffice\PhpSpreadsheet\Writer\Html($spreadsheet);
$writer->save($path."05featuredemo.htm");
//delete the temporary file
unlink($path_file);
}
else
{
//handle the failure to write the temp file
}
I haven't tested this and I'm not sure you really want to save to an html file, but I think the above is close to the answer.
Second addition
If you want to save .xlsx files you need an Xlsx writer. Use the following instead of what's shown above.
//write out to excel file
$writer = new \PhpOffice\PhpSpreadsheet\Writer\Xlsx($spreadsheet);
$writer->save($ path. "doc.xlsx");
I confess that I have never used, or considered using the html reader so I'm not sure you'll get what you want. I honestly think that creating an html table so you can import it into excel is probably doing it the hard way.

Laravel move uploaded file

It is working good for full path like this
$file=$request->file('file');
$file->move('C:\xampp\htdocs\modo\images',$file->getClientOriginalName());
But i cant understand why it doesnt for root folder path :
$file->move('\modo\images',$file->getClientOriginalName());
You need to use base_path() method. This method returns the fully qualified path to the project root:
So in your case try the below code:
$file = $request->file('file');
$file->move(base_path('\modo\images'), $file->getClientOriginalName());
and if you want to return the public directory then use:
$path = public_path();
For more info read Laravel helper functions
You need to do it this way:
$file->move(base_path('\modo\images'),$file->getClientOriginalName());

Accessing temporary file from upload in django view

Just as the title says, I want to know how to access the data from the temporary file stored by Django, when a file is uploaded, inside a view.
I want to read the data uploaded values so I can make a progress bar. My methodology is to perform a jquery getJSON request:
function update_progress_info() {
$progress.show();
$.getJSON(progress_url, function(data, status){
if (data) {
var progress = parseInt(data.uploaded) / parseInt(data.length);
var width = $progress.find('.progress-container').width()
var progress_width = width * progress;
$progress.find('.progress-bar').width(progress_width);
$progress.find('.progress-info').text('uploading ' + parseInt(progress*100) + '%');
}
window.setTimeout(update_progress_info, freq);
});
};
where progress_url is the view I have that handles the uploaded file data:
# views.py (I don't know what to do here):
def upload_progress(request):
for line in UploadedFile.temporary_file_path
response = (line)
return response
Django handles uploaded files with UploadHandler defined in settings.py with this name FILE_UPLOAD_HANDLERS that defaults to this tuple:
FILE_UPLOAD_HANDLERS =
("django.core.files.uploadhandler.MemoryFileUploadHandler",
"django.core.files.uploadhandler.TemporaryFileUploadHandler",)
The behavior with file uploads is that if the file is less than 2.5 mg then it will be kept on memory, hence, they will not be written in disk as temporary files.
If the file weights more, it will be written in chunks in the FILE_UPLOAD_TEMP_DIR in the settings.py. That's the file you'll have to query to know how many bytes have been uploaded.
You can access the uploaded/uploading files through your request variables in views like this: file = requests.FILES['file'] . There, file variable will have the type UploadedFile which contains a method temporary_file_path with the address of the file in the disk being uploaded. (Note: only files larger than 2.5 mg will have this methods) so there you may get the size of the file being uploaded.
Another way to do this is create your own UploadHandler like a ProgressBarUploadHandler and add it to your file upload handlers. This is the way the docs recommend it. Here are some snippets and tutorials for doing it.
If you need any more info the doc is really well documented.
I hope you find this helpful. Good luck.

Resources