Closed SergeR closed 11 years ago
It looks like it fails because AttachedFile::$foreignModel
is empty when delete is called. You need to set it to the value of what it was when the file was saved.
AttachedFile::$foreignModel
preperty holds the name of currenly linked model. It's just for set a 'model' field of AttachedFile
'magically' when saving. This value stored in the separate fied ('model'). I think I need to set the 'uploadDir' properly before deleting.
Yeah. The AttachmentBehavior
calls protected methos _deleteFile()
, and
$basepath = $attachment['uploadDir'] : $attachment['tempDir'];
//file to delete
$file = new File($basepath . basename($path));
So the change of uploadDir
before deleting may help.
Place a debug($options)
in beforeUpload()
to see if the uploadDir is correct?
Initially 'uploadDir' points to document_root/files/.
In the beforeUpload
method I change it to the other value (document_root/files/Exposition/). The filename in database stored as /files/Exposition/image.jpg
. After uploading file is placed in the appropriate directory. Upload process works fine, without any problems.
When I try to call a delete()
method, row in the db table is deleted but file remains in the directory. I can't (or I don't know how to) set uploadDir
before delete.
A test for my model.
Fixture:
<?php
/**
* AttachedFileFixture
*
*/
class AttachedFileFixture extends CakeTestFixture {
/**
* Fields
*
* @var array
*/
public $fields = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'primary'),
'model' => array('type' => 'string', 'null' => false, 'default' => null, 'length' => 100, 'key' => 'index', 'collate' => 'utf8_general_ci', 'charset' => 'utf8'),
'foreign_id' => array('type' => 'integer', 'null' => false, 'default' => null),
'image' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_general_ci', 'charset' => 'utf8'),
'indexes' => array(
'PRIMARY' => array('column' => 'id', 'unique' => 1),
'model' => array('column' => array('model', 'foreign_id'), 'unique' => 0)
),
'tableParameters' => array('charset' => 'utf8', 'collate' => 'utf8_general_ci', 'engine' => 'InnoDB')
);
/**
* Records
*
* @var array
*/
public $records = array(
array(
'id' => 1,
'model' => 'Exposition',
'foreign_id' => 1,
'image' => '/files/Exposition/test'
),
);
}
Test
<?php
App::uses('AttachedFile', 'Model');
App::uses('File', 'Utility');
App::uses('Folder', 'Utility');
define('UPLOAD_DIR', TMP . DS . 'files' . DS);
/**
* AttachedFile Test Case
*
*/
class AttachedFileTest extends CakeTestCase {
public $fixtures = array(
'app.attached_file',
);
public function setUp() {
parent::setUp();
$this->AttachedFile = ClassRegistry::init('AttachedFile');
}
public function tearDown() {
unset($this->AttachedFile);
parent::tearDown();
}
public function testDelete()
{
//Create directories
$folder = new Folder(UPLOAD_DIR . 'Exposition', TRUE, 0777);
// Create a file as in the fixture's image field
$file = new File(UPLOAD_DIR . 'Exposition' .DS . 'test', TRUE);
$file->write('Foo and Bar');
$file->close();
$delResult = $this->AttachedFile->delete(1);
$this->assertTrue($delResult, 'Model delete method fail');
// Is record deleted?
$findRes = $this->AttachedFile->findById(1);
$this->assertEmpty($findRes, 'Record not deleted');
$this->assertFalse($file->exists(), 'File not deleted!');
}
}
Like I mentioned before, you need to set $foreignModel
before you delete.
$this->AttachedFile->foreignModel = 'Exposition';
$delResult = $this->AttachedFile->delete(1);
Bump.
:) Sorry. You're right, it works.
I'm not sure if that is an issue. I try to generate dynamic paths, it works, but files aren't deleted after delete() method call.
The attached_files table:
Example of model, that has many images.:
The model AttachedFile with Uploader behavior:
When I call the delete() method of Exposition model to delete the record (that has no children):
the rows in the AttachedFile model are deleted, but the files in the /files/Exposition directory aren't