milesj / uploader

[Deprecated] A CakePHP plugin for file uploading and validating.
MIT License
193 stars 73 forks source link

can't save record if there is an input type file in the form #8

Closed MelodyNelson closed 14 years ago

MelodyNelson commented 14 years ago

follow-up on this issue : http://github.com/milesj/cake-uploader/issues/closed#issue/7 cake : 1.3 uploader version : 2010-08-22

I can't save any record if there is an input type file in the form if I delete the input file, records are saved correctly the issue is on any kind of record (HABTM or not)

gameiqinc commented 14 years ago

I think I'm experiencing the same problem. The input is saved correctly when an upload file is selected, but the form cannot be saved when no file is selected. It seems that an upload is always required. I thought setting optional to true would fix this, but it didn't.

gameiqinc commented 14 years ago

This is how I ended up working around my issue...

if(empty($this->data['Image']['filename']['name'])) { unset($this->data['Image']['filename']); }

This piece of code goes just before the save part in the controller. It's an ugly hack, but it works!

MelodyNelson commented 14 years ago

hi,

I've tried your hack but it didn't works for me

without the hack, some examples and results :

1) "simple record" without attachment -> doesn't work (record not saved)

Array ( [Category] => Array ( [id] => [parent_id] => [name] => test without file [description] => [disabled] => 0 [image] => Array ( [name] => [type] => [tmp_name] => [error] => 4 [size] => 0 )

    )

)

2) "simple record" with a file attached -> works fine (record saved + file uploaded)

Array ( [Category] => Array ( [id] => [parent_id] => [name] => test with file [description] => [disabled] => 0 [image] => Array ( [name] => button-complete-single.png [type] => image/png [tmp_name] => /private/var/tmp/php91BUEz [error] => 0 [size] => 1309 )

    )

)

3) "complex record" without attachments -> doesn't work (record not saved)

Array ( [Category] => Array ( [Category] => Array ( [0] => 17 [1] => 20 [2] => 23 )

    )

[Product] => Array
    (
        [id] => 
        [reference] => ref12345
        [name] => my product without attachement
        [description] => 
        [price] => 0.00
        [special_price] => 0.00
        [packaging] => 
        [available] => 
        [new] => 0
        [disabled] => 0
        [image] => Array
            (
                [name] => 
                [type] => 
                [tmp_name] => 
                [error] => 4
                [size] => 0
            )

        [file] => Array
            (
                [name] => 
                [type] => 
                [tmp_name] => 
                [error] => 4
                [size] => 0
            )

    )

)

4) "complex record" with 2 attachments -> doesn't work (record not saved, no file uploaded)

Array ( [Category] => Array ( [Category] => Array ( [0] => 17 [1] => 20 [2] => 23 )

    )

[Product] => Array
    (
        [id] => 
        [reference] => ref567
        [name] => my product with 2 attachments
        [description] => 
        [price] => 0.00
        [special_price] => 0.00
        [packaging] => 
        [available] => 
        [new] => 0
        [disabled] => 0
        [image] => Array
            (
                [name] => button-add-to-cart.png
                [type] => image/png
                [tmp_name] => /private/var/tmp/phptSEtRM
                [error] => 0
                [size] => 1729
            )

        [file] => Array
            (
                [name] => 2005-06.pdf
                [type] => application/pdf
                [tmp_name] => /private/var/tmp/phpUMmKiB
                [error] => 0
                [size] => 94950
            )

    )

)

in all these cases, my records are saved if I comment the lines for the files in the forms ex : // $form->input('image', array('label' => '', 'type' => 'file'))

milesj commented 14 years ago

If you are using the FileValidation behavior, the optional argument is no longer supported. You must use required.

http://github.com/milesj/cake-uploader/blob/master/models/behaviors/file_validation.php#L30

MelodyNelson commented 14 years ago

I'm not using the FileValidation behavior

milesj commented 14 years ago

Figured out the problem. If you aren't using the file validation behavior, the attachment behavior returns false in beforeSave(). I made it just skip that image in the loop if tmp_name is empty. Please re-open a new ticket if this persists.

gameiqinc commented 14 years ago

It still doesn't seem to work for me. This is how I have the behavior set up in my model...

<?php var $actsAs = array( 'Uploader.Attachment' => array( 'avatar' => array( 'uploadDir' => '/img/avatars/', // Where to upload to, relative to app webroot 'dbColumn' => 'avatar', // The database column name to save the path to 'maxNameLength'=> 100, // Max file name length 'overwrite' => true, // Overwrite file with same name if it exists 'name' => '', // The name to give the file (should be done right before a save) 'transforms' => array( 'resize' => array('width'=> 64, 'height'=> 64, 'dbColumn'=> 'avatar') // Removes original image and uses this one instead ), 'extension' => array( // Valid file extensions for the upload 'value' => array('gif', 'jpg', 'png', 'jpeg'), 'error' => 'Mimetype incorrect', ), 'filesize' => array( // Maximum file size allowed 'value' => '100K', 'error' => 'The avatar is too big. Please upload a file less than 100kb in size' ), 'required' => false, 'expand' => true ) ) ); ?>

This is the error I get...

Warning (512): SQL Error: 1054: Unknown column 'Array' in 'field list' [CORE\cake\libs\model\datasources\dbo_source.php, line 681]

I'm going to investigate this further to give you more info before I open a new ticket.

milesj commented 14 years ago

You are doing it incorrectly. You must use the FileValidation and Attachment behaviors separately. Take a look at my example here:

http://github.com/milesj/cake-uploader/blob/master/tests/upload.php

gameiqinc commented 14 years ago

Sorry if I'm obtuse or something. I changed my code according to your example to...

<?php var $actsAs = array( 'Uploader.FileValidation' => array( 'avatar' => array( 'filesize' => array( 'value' => '100K', 'error' => 'The avatar is too big. Please upload a file less than 100K in size' ), 'extension' => array( 'value' => array('gif', 'jpg', 'jpeg', 'png'), 'error' => 'Only png, gif, jpg and jpeg images are allowed!' ), 'required' => false, ) ), 'Uploader.Attachment' => array( 'avatar' => array( 'uploadDir' => '/img/avatars/', 'dbColumn' => 'avatar', 'maxNameLength'=> 100, 'overwrite' => false, 'name' => '', 'transforms' => array( 'resize' => array( 'width'=> 64, 'height'=> 64, 'dbColumn'=> 'avatar', 'expand'=> true ) ), ) ) ); ?>

...but I still get the same error message.

milesj commented 14 years ago

Can I see your controller code? It looks to be happening outside the behaviors.

gameiqinc commented 14 years ago

Yes, it's very simple...

<?php class ProfilesController extends AppController {

var $name = 'Profiles';
var $components = array('Uploader.Uploader');

function edit() {
    $user_id = $this->Auth->user("id");
    if (!$user_id && empty($this->data)) {
        $this->Session->setFlash(__('Invalid profile', true), 'flash_error');
        $this->redirect($this->referer());
    }
    if (!empty($this->data)) {
        if ($this->Profile->save($this->data)) {
            $this->Session->setFlash(__('The profile has been saved', true), 'flash_notice');
            $this->redirect(array('controller' => 'users'));
        } else {
            $this->Session->setFlash(__('The profile could not be saved. Please, try again.', true), 'flash_error');
        }
    } else {
        $this->data = $this->Profile->find('first', array('conditions' => array('Profile.user_id' => $user_id)));
    }
}

} ?>

Also in app_controller.php I have...

<?php var $components = array('Auth', 'Session', 'Security', 'Simplepie', 'Permission'); ?>

But, I doubt any of those components would interfere...

milesj commented 14 years ago

In your Profile model, can you add this code and show me the output:

function beforeSave($query) {
    debug($query);
    debug($this->data);

    return false;
}
gameiqinc commented 14 years ago

This is what I get...

<?php

app\models\profile.php (line 82)

Array ( [validate] => 1 [fieldList] => Array ( )

[callbacks] => 1

)

app\models\profile.php (line 83)

Array ( [_Token] => Array ( [key] => 06147e60ef4808f1d501f505dd9cf2a4e42a7b74 [fields] => a3679f5b98d80b5ca3653b21f11b8bf3ff7123fd%3An%3A1%3A%7Bv%3A0%3Bf%3A10%3A%22Cebsvyr.vq%22%3B%7D )

[Profile] => Array
    (
        [id] => 1
        [gender] => M
        [description] => Lorem ipsum dolor sit amet...
        [billing_first_name] => 
        [billing_last_name] => 
        [billing_address_1] => 
        [billing_address_2] => 
        [billing_city] => 
        [billing_state] => 
        [blilling_zip] => 
        [billing_country] => 
        [shipping_same] => 0
        [shipping_first_name] => 
        [shipping_last_name] => 
        [shipping_address_1] => 
        [shipping_address_2] => 
        [shipping_city] => 
        [shipping_state] => 
        [shipping_zip] => 
        [shipping_country] => 
        [avatar] => Array
            (
                [name] => 
                [type] => 
                [tmp_name] => 
                [error] => 4
                [size] => 0
            )

        [modified] => 2010-09-28 09:19:14
    )

) ?>

milesj commented 14 years ago

I was able to use your same exact settings with no problem. There must be something else going on :/

If I were you, I would go through the attachment line by line and try placing debug()s to see if everything is working correctly.

gameiqinc commented 14 years ago

So I verified that I get the same error if I use the attachment or the component. Also, the validate structure of my model has this entry:

                [required] => Array
                    (
                        [rule] => Array
                            (
                                [0] => required
                                [1] => 
                            )

                        [message] => This file is required
                        [allowEmpty] => 1
                    )

Does that look correct?