How ImageMagick readimage from a relative path WampServer64 - imagick

I'm testing the php_imagick version 3.4.4.7.4 against a WampServer64 installation using
<?php
/* Create the Imagick object */
$im = new Imagick();
/* Read the image file */
try {
$im->readImage( "test.jpg" );
} catch( \ImagickException $e ) {
die( $e );
}
/* Thumbnail the image ( width 100, preserve dimensions ) */
$im->thumbnailImage( 100, null );
/* Write the thumbail to disk */
$im->writeImage( 'th_test.png' );
/* Free resources associated to the Imagick object */
$im->destroy();
It results in raised ImagickException No such file or directory. The file sits in the same folder as the php file.
When I replace 'test.jpg' by an absolute path the code works but the resulting file at writeImage ends up in the folder C:\wamp64\bin\apache\apache2.4.41
Is this normal behaviour? I don't see a remark in https://www.php.net/manual/en/imagick.readimage.php that paths should be absolute. Is this a quirk in WampServer64?

Related

Ignore `OutOfBoundsException` error when watermark grower of source image

In Yii2 and core yii\imagine\Image class, When use this command:
Image::watermark('image.jpg', 'watermark.jpg')->save('image.jpg');
If dimension of watermark, grower of source image, return this error:
Exception 'Imagine\Exception\OutOfBoundsException' with message 'Cannot paste image of the given size at the specified position, as it moves outside of the current image's box'
It's fine. But how can ignore this error, so new image will be create but the part of watermark that outside of the image box is hidden and removed.
There is no ignoring the Exceptions thats why they are called by that name, The Exception is thrown from the paste(ImageInterface $image, PointInterface $start); method
$size = $image->getSize();
if (!$this->getSize()->contains($size, $start)) {
throw new OutOfBoundsException('Cannot paste image of the given size at the specified position, as it moves outside of the current image\'s box');
}
that is called in the Image::watermark function. It is restricted and not allowed so you cannot Ignore it.
You can ignore/suppress notices or warnings but you can catch the exceptions and do something to fix it or present the error to the user
try{
\yii\imagine\Image::watermark ( 'img/image.png' , 'img/logo.jpg' );
} catch (\Imagine\Exception\OutOfBoundsException $ex) {
Yii::$app->session->setFlash('error',$ex->getMessage()) ;
}
Or if the exception occurs resize the watermark image smaller than the base image and call the Image::watermark again.
EDIT
You can do something like below what i was talking about suppose you have an actionWatermark() where you are creating the watermark image
public function actionWatermark() {
$image='image.jpg';
$watermark= 'watermark.jpg';
try {
//call watermark function
$this->watermark ($image,$watermark);
} catch ( \Imagine\Exception\OutOfBoundsException $ex ) {
$img = \yii\imagine\Image::getImagine ();
//get the base image dimensions
$size=$img->open ( $image )->getSize();
//resize the watermark image
$resized=\yii\imagine\Image::resize ( $watermark , $size->getWidth () , $size->getHeight (),TRUE);
//call again
$this->watermark ($image,$resized);
}
}
private function watermark($image,$watermark) {
\yii\imagine\Image::watermark ( $image , $watermark )->save ( 'image.jpg' );
}

'Media bulk upload' on site server using 'Dropzonejs module' in Drupal 8 gives "failed to open the output stream" error

My website uses Drupal 8 and we are using Dropzonejs module for "media bulk upload" option. In my local environment, I'm able to bulk upload media without any problems. However, on server environment (having same configuration as local) when I try to bulk upload media, it throws "failed to open the output stream" error.
Any solutions/answers/suggestions are most welcome and much needed.
NOTE: Single item uploads work fine. Also during bulk upload, the error happens once the progress bar reaches 100%.
The defect screenshot is here
As of Drupal 8.6, we need a patch in the core for this functionality to work properly. For the fix, three files need to be changed as under:
drupal/core/includes/files.inc (Line 234)
/* #var \Drupal\Core\StreamWrapper\StreamWrapperInterface $wrapper */
if ($wrapper = \Drupal::service('stream_wrapper_manager')->getViaUri($uri)) {
return $wrapper->getExternalUrl();
}
return FALSE;
drupal/core/modules/locale/src/StreamWrapper/TranslationsStream.php (line 48 replace function)
public function getExternalUrl() {
return FALSE;
}
3.drupal/core/modules/locale/tests/src/Functional/LocaleImportFunctionalTest.php
(Add at line 365)
* Tests that imported PO files aren't break the UI provided by "views".
*
* #throws \Behat\Mink\Exception\ExpectationException
*
* #link https://www.drupal.org/project/drupal/issues/2449895
*/
public function testPoFileImportAndAccessibilityOfFilesOverviewViewsPage() {
$this->container
->get('module_installer')
->install(['system', 'user', 'file', 'views']);
// Create and log in a user that's able to upload/import translations
// and has an access to the overview of files in a system.
$this->drupalLogin($this->drupalCreateUser([
'access administration pages',
'access files overview',
'administer languages',
'translate interface',
]));
// Import a dummy PO file.
$this->importPoFile($this->getPoFile(), [
'langcode' => 'fr',
]);
// The problem this test cover is exposed in an exception that is thrown
// by the "\Drupal\locale\StreamWrapper\TranslationsStream" when "views"
// module provides a page of files overview. Refer to the issue to find
// more information.
$this->drupalGet('admin/content/files');
$this->assertSession()->statusCodeEquals(200);
}
(At line 373, overwrite the following function)
public function importPoFile($contents, array $options = []) {
$file_system = $this->container->get('file_system');
$file_path = $file_system->tempnam('temporary://', 'po_') . '.po';
file_put_contents($file_path, $contents);
$options['files[file]'] = $file_path;
$this->drupalPostForm('admin/config/regional/translate/import', $options,
t('Import'));
$file_system->unlink($file_path);
}

Storage Path not writeable in laravel with Intevention?

I'm getting a little confused here with this Storage VS Public paths in Laravel 5 > ... My understanding is one should use Storage:: instead of File:: for writing files to the Storage folder foresighting the use of cloud services like Amazon etc. So I am trying to put a jpg into a the storage/app folder using Intervention and this code:
public function apply(Request $request)
{
$user = Auth::user();
$path = '/users/'.$user->id;
if (!Storage::exists($path))
{
Storage::makeDirectory ($path, $mode = 0755, $recursive = false, $force = false);;
}
Image::make($request->file('image'))
->orientate()
->resize(600, null, function ($constraint) {
$constraint->aspectRatio();
})
->resizeCanvas(600, 600, 'center', false, 'ffffff')
->save($path.'/foo.jpg');
}
First of all I am not sure the !Storage::exists($path) will do anything as the API for storage tells it won't check for directories so how should I check if a Directory exists??
Second dd(is_writable($path)); return false, and indeed running that code results in
NotWritableException in Image.php line 143:
Can't write image data to path
error.
so how should this be done?
The "trick" that I used was manipulate the image directly in the temp path, and then save it in the storage folder using the Laravel storage method.
$tempFile = $request->file('image')->getRealPath();
Image::make($tempFile)
->resize(100, 100)
->save($tempFile); // Note that we are saving back to temporary path
// Now we can proceed and send the manipulated file to it's final destination
// in '/storage/app/public/uploads'
$path = $request->file('image')->storePublicly('public/uploads');

Dompdf converts fine on local but not on production server

I'm using Laravel 4 with dompdf package: https://github.com/barryvdh/laravel-dompdf
When I generate a report and it converts it to PDF on my local, everything is fine and displays well, but when I do the same exact thing on my production server, it displays random letters where there is either dynamic or static content.
Screenshot of local vs production:
http://s28.postimg.org/u5zk3pc19/report_diff.png
Here is the code that creates the PDF:
/**
* Create PDF
*
*/
public function createPdf( $reportData )
{
if( $this->validate() )
{
// Get Final Data Information
$btu_hp = static::getBtuHp( $reportData['booth_cfm'], $reportData['cure_temp_hp'], $reportData['outside_temp'] );
$btu_current = static::getBtuCurrent( $reportData['booth_cfm'], $reportData['bake_temp_current'], $reportData['outside_temp'] );
$reportData['energy_percentage_per_unit'] = static::getEnergyPercentagePerUnit( $btu_hp, $btu_current );
$reportData['energy_dollar_per_unit'] = static::getEnergyDollarPerUnit( $reportData['cost_per_therm'], $reportData['bake_time_current'], $reportData['cure_time_hp'], $btu_current, $btu_hp );
$reportData['time_savings_per_unit'] = static::getTimeSavingsPerUnit( $reportData['bake_time_current'], $reportData['cure_time_hp'] );
$reportData['time_savings_per_year'] = static::getTimeSavingsPerYear( $reportData['time_savings_per_unit'][0], $reportData['units_per_day'], $reportData['production_days'] );
$reportData['labor_dollar_per_year'] = static::getLaborDollarPerYear( $reportData['labor_rate'], $reportData['time_savings_per_year'][0] );
$reportData['energy_dollar_per_year'] = static::getEnergyDollarPerYear( $reportData['energy_dollar_per_unit'][0], $reportData['units_per_day'], $reportData['production_days'] );
$view = View::make('pages.report.hp-report.print', array('report' => $reportData));
if( ! $this->saveAsPdf($view, $this->generateFileName()) )
{
return false;
}
return true;
}
return false;
}
/**
* Save report as PDF
* #param html HTML of PDF
* #param fileName Name of File
*
*/
public function saveAsPdf( $html, $fileName = null )
{
if(is_null($fileName))
$fileName = $this->generateFileName();
$htmlPath = $this->reportDirectory.'/'.$fileName.'.html';
$pdfPath = $this->reportDirectory.'/'.$fileName.'.pdf';
file_put_contents( $htmlPath, $html );
// set recent PDF to name of PDF
$this->recentReportFile = $fileName . '.pdf';
return PDF::loadFile($htmlPath)->save($pdfPath);
}
/**
* Get most recent uploaded PDF
*
*/
public function getRecentPdf()
{
return $this->recentReportFile;
}
/**
* Generate file name for PDF
*
*/
public function generateFileName()
{
return Auth::user()->id . '_hp_' . str_random(10) . '_' . time();
}
Everything writes fine and it uses the right template and has the styling... Only the static content and dynamic content (values written out with PHP variables) display badly, although you can see some of the static content like Energy Savings and such prints fine.
Is there a reason this could be all jumbled up on the live server, but not local?
Here is the HTML for the view that is being grabbed (the HTML the php variables are injected into): http://pastebin.com/5bMR6G2s
And here is my config file for dompdf:
http://pastebin.com/Ld6MQckG
There are two possible causes for this:
Missing font(s) on the production server. Make sure you have the correct fonts installed on the production site.
Character encoding issues. I'm not sure which site (dev/live) the issue is on, but it may be that one is outputting UTF-8 and the other is not. You could try to sort this out by detecting the encoding on the input file on both dev and live by using mb_detect_encoding and see if they're different. If they are, then use mb_convert_encoding before converting to PDF.

download remote image in codeigniter

I want to download a remotely hosted image using codeiogniter . and a validation feature also has to be added so that only images are downloaded..
is it possible to use the built in functions offered by CI ??
thanks .
To get a remote image, you can just use file_get_contents, assuming allow_url_fopen is set to on in php.ini.
$image=file_get_contents('http://othersite.com/image.jpg');
Once you have that, you can validate the file extension, or try and resize the image to check that it really is an image.
This solution is not from CI but PHP, think it can be usefull anyway.
May be checking the image size is enough to be sure it's an image, like
$imagedata = getimagesize('http://othersite.com/image.jpg');
or use exif_imagetype
if ( ! function_exists( 'exif_imagetype' ) ) {
function exif_imagetype ( $filename ) {
if ( ( list($width, $height, $type, $attr) = getimagesize( $filename ) ) !== false ) {
return $type;
}
return false;
}
}
if( exif_imagetype('http://othersite.com/image.jpg') )
{
//is an image
}

Resources