File Upload in update

I’ve seen the many file upload posts. I’m wondering if anybody has worked on the update action of the model?

What if there is a file that has been uploaded already and you want it to be replaced if a new one is uploaded?

Scenario:

I am working on a Podcast archive. I insert a new pcast with (or without) an audio file provided. Then I go into update some information in the record (model). How would I know if I am adding a new file, overwriting and old one, or what. I thought about having a hidden form field with the "old" file name, checking that, and doing what ever…What would be the best way to handle this?

Thanks, JK

I’m also starting to look into this for a classifieds application (for pictures). I’m thinking about limiting the number of pictures to 5 or so… if anyone has already done something like that or has any idea on the best practice, I’m all for some inputs too ;)

Benn

Hello,

I just found this :

http://smartcoderszone.com/2010/09/dynamic-jquery-multiple-image-upload-with-delete-and-limit-features/

which could be the kind of thing we’re looking for.

Anyone have any idea on how to adapt it to Yii?

Cheers

I have been looking at one of the demos (blog maybe?) that used a Private var to store some information in the afterFind() and use it in the before/afterSave() of the model.

Still looking thou :(

Ok Gang:

Lets try again. I’ve been searching, and reading, and searching to find information on uploading a file that would meet my need. And nothing seems to fit. Can any one help?

Requirements:

  • Create and update actions may or may not have a file uploaded.

  • When a file is uploaded, I need to rename the saved file as well as save that name in the ‘file_name’ column.

  • I also want to save the the size and mimeType into the ‘file_size’ and ‘file_type’ columns respectively.

  • If the $model->save() works, THEN move/save the file.

  • If, during update the file is being changed, I need to overwrite/delete the old file and save the new one with the old filename.

  • MVC seems to dictate that this should be down in the beforeSave()/afterSave() functions in the model, but all of the code examples use the controller.

I am just so confused :huh: that I don’t know where to look anymore.

Any help would be greatly appreciated. JK

Here is what I use for the create in my Controller. I am using MongoDB as the database which can store files in GridFS. I use only 1 field in my model called ‘image’. At the moment it simply gets set with the mime type of the file but I was thinking it may be more helpful to keep a count of the images associated with this record.

I hope this is some help. I am working on my update code now. Let me know if you want to see this.




	public function actionCreate()

	{

		$model=new Advert;


		// Uncomment the following line if AJAX validation is needed

		// $this->performAjaxValidation($model);


		if(isset($_POST['Advert']))

		{

			$model->attributes=$_POST['Advert'];


/* image handling */			

			$x=CUploadedFile::getInstance($model,'image');

			if (!$x==null)

			{

			    $model->image=$x->extensionName;  // maybe this should just be boolean or an image count

			}

			

			if($model->save())

			{

				

/* image handling */			

				if (!$x==null)

				{

				    // this line works & saves the file under the images directory

					$x->saveAs(Yii::app()->basePath . '/../images/advert/' . (string)$model->_id . '.' . $model->image);

				    // now lets try saving it in Mongo using GridFS

				    $img = new AdvertImage;

                                    $img->filename = Yii::app()->basePath . '/../images/advert/' . (string)$model->_id . '.' . $model->image;

                                    //$img->metadata = array('value1'=>1, 'value2'=>2);

                                    $img->metadata = array('advert'=>(string)$model->_id,

                                           'type'=>$x->extensionName,

                                           'mime'=>$x->type);

                                    $res = $img->save();

                                    if($res !== true)

                                    {

                                        echo 'error saving file';

                                        exit;

                                    }

                                   // now delete the file from the images directory as it is in GridFS now

                                   unlink($img->filename);

				}

				$this->redirect(array('view','id'=>$model->_id));

			}

		}


		$this->render('create',array(

			'model'=>$model,

		));

	}



On my apps I have

  • a field or a related table to the model that has the images or documents

  • when a model is saved i save a name of the image or document to its field or related table

  • when i update the model i check whether a new image or document has been submitted (ie. $model->photo = CUploadedFile::getInstance($model,‘photo’);) and check for its null value, if not null a new image or document has been submitted

  • if image or document has been submitted I try to save the new image or document to its specific folder (i create a unique name creator to avoid conflicts)

  • if save operation is successful, then i get object from related table or path from its field and check existence of old image or document

  • check for existence and delete if true

  • update the name of related table or field with the newly created filename and save

Here an example:




public function actionUpdate()

{

	$model=$this->loadModel(getParam('id'));

	

	if(isset($_POST['Product']))

	{

		$model->attributes=$_POST['Product'];

			

		$model->photo = CUploadedFile::getInstance($model,'photo');

	       // new submitted

	       if($model->photo){

		    // ...

		    // saving procedures here

		    // ....

                    // assuming saving procedure successfull

		    // delete old reference (this case a field)

                    if(file_exists($p . $model->picture))

			unlink($p . $model->picture);

		

		    // update with new name the field

		     $model->picture = $newImage;

		}

                // saving model

		if($model->save()){

		      // whatever you do here for positive saving

			Yii::app()->end();

		}

      }

     // render update form

}



Thanks dude! greetings from México :lol: