0
votes

I have a simple reactive form in angular 6 that it also has a file input to upload images.

The scenario is to submit the form, save the image and the text fields of the form and then update a photo gallery with the new image. For a photo gallery, I use the ng carousel.

This is the code in the front-end

<form [formGroup]="myForm" (ngSubmit)="submitForm($event.target)" >
  <input type="file" (change)='imageChange($event)' formControlName="imageInput" name = 'imageInput'> 
  <input type="text" formControlName="imageName" name='imageName'>
  <button type="submit" >Submit</button>  
</form>

save it like

  submitForm(form){
    let formData = new FormData(form);
    this.http.post('http://localhost:3000/cms/upload',formData,{reportProgress:true,observe:'events'}).subscribe(
      event=>{
        if(event.type === HttpEventType.Response){     
          eb = event.body;              
            this.addpic(eb.data);            
        }        
    }); 
}

eb.data contains data that came from the server, after successfully saving the form data, the id of the new image and its file name.

In addpic I try to add a new image in the carousel. Add all the new data to an array, so I can use the array later, to ngFor it and dynamically create the ng Carousel

  addpic(data){  
    this.images.push({
      'id': data.id,
      'name': data.name
     });
  }

use it like so

<ngb-carousel #carousel *ngIf="images" > 
  <ng-template ngbSlide *ngFor="let im of images; let i = index"  id="{{im.id}}">
    <img src='../assets/images{{im.newName}}' >
  </ng-template>
</ngb-carousel>

So this works fine, but the image is never rendered. I get no errors, I see all the data saved in my database, the image is transferred in the folder as it should, but no new image in the carousel, just a 404 error in the console. The images array is updated, but no image in the carousel. The URL is ok, all the other images with the same URL are rendered in the carousel. It's like the app had no time to see the whole update, so it cannot show the image.

I tried to grab the image file object from the form, save it in angular in a selectedFile: File; and use this in the carousel, but this has no path or anything similar. Grab it when it is set in the form

  imageChange(e){            
    this.selectedFile = e.target.files[0];
  }

and use it in addpic

  addpic(data){  
    this.images.push({
      'id': data.id,
      'name': this.selectedFile.path
     });
  }

I also tried to use the formData before the form submission, t get the image, but the result is the same, an object with no path.

I also tried to "read" the file using HTML5 FileReader, but this is an image and in the carousel, I need to provide a URL for the src, not just the image file.

I also used formidable in the node to parse the form and take the path of the image, return it back in the front-end along with the id and the file name and use that as an src. But this won't be used by the browser for security reasons I guess, because it is a URL in the temp files.

I also tried to get all the images from the server with a query, but the new image is still not available, giving a 404 error, even though the image is in the folder and the database is updated.

like this

  addpic(data){
    this.getImages(this.currentId); //get all images again   
     this.images.push({
      'id': this.images.id,
      'name': this.images.path
     }); 
  }

I have to refresh the page for the image to show. I don't know how to fix this. Any ideas? Is it a security issue that I cannot get the image right away, even though it is saved and I have to refresh? I would like to avoid performing an extra get, if it is possible, to keep client-server communication minimum.

I use angular6 and node 8.11. in windows 10, all locally in my laptop.

Thanks

1

1 Answers

1
votes

Might be issue related to updated variable refers to same reference. inside addPic(). add this line of code as last line.

this.images = this.images.slice();