2016-08-09 6 views
1

私はかなりシンプルな設定だと思っていました。プロファイル入力コンポーネントにユーザープロファイルを作成しています。その後、フォームが送信され、ユーザーが作成された後、profile-img-uploadコンポーネントにユーザーを送信して写真を追加します。私が理解しておくことは、作成したプロファイルをプロファイルサービスに保存し、img-uploadコンポーネントでそのプロファイルを呼び出すことで意味をなさないことです。しかし、何かが欠けているのは、img-uploadコンポーネントconsole.log(this.profile)のプロファイルは常にnullです。Angular2サブスクリプションが常にヌルになる

サブスクリプションとオブザーバビリティに関する非常にコアなものを誤解しているような気がします。私がしたいのは、最初のコンポーネントにProfileオブジェクトを作成し、作成したProfileを2番目のコンポーネントに渡して、写真をアップロードしてそれをプロファイルに割り当てることだけです。

私はここで何が欠けているのか理解してもらえますか?

プロファイルinput.component

import... 

@Component({ 
    moduleId: module.id, 
    selector: 'my-profile-input', 
    templateUrl: 'profile-input.template.html', 
    directives: [REACTIVE_FORM_DIRECTIVES] 
}) 

export class ProfileInputComponent implements OnInit { 
@Output() profile: Profile; 
profile: Profile = null; 

constructor(private formBuilder:FormBuilder, 
      private profileSrevice: ProfileService, 
      private errorService: ErrorService, 
      private router: Router, 
      private route: ActivatedRoute) {} 

onSubmit() { 
const profile: Profile = new Profile(
      this.profileForm.value.first_name, 
      this.profileForm.value.last_name 
); 

this.profileSrevice.addProfile(profile) 
      .subscribe(
       data => { 
        console.log('what comes back from addProfile is: ' + JSON.stringify(data)); 
        this.profileSrevice.profiles.push(data); 

        // The line below will superceded the one above. 
        this.profileSrevice.pushData(data); 
       }, 
       error => this.errorService.handleError(error) 
      ); 
     this.router.navigate(['profile-img-upload', {myProfile: this.profile}]); 
} 

profile.service.ts

import... 

@Injectable() 
export class ProfileService { 
    pushedData = new EventEmitter<Profile>(); 

    pushData(value: Profile) { 
    this.pushedData.emit(value); 
    console.log('value in service is '); 
    console.log(value); 
    } 
} 

プロファイルIMG-upload.component.ts

import... 

@Component({ 
moduleId: module.id, 
selector: 'my-profile-img-upload', 
templateUrl: 'profile-img-upload.template.html', 
directives: [ ROUTER_DIRECTIVES, FILE_UPLOAD_DIRECTIVES, NgClass, NgStyle, CORE_DIRECTIVES, FORM_DIRECTIVES ], 
providers: [AWSUploadService, UploadFileService] 
}) 

export class ProfileImgUploadComponent implements OnInit { 
    @Input() myProfile: Profile; 
    profile: Profile; 

    constructor(private uploadFileService: UploadFileService, 
      private route: ActivatedRoute, 
      private profileService: ProfileService, 
      private errorService: ErrorService) { 
    this.filesToUpload = [];} 

    ngOnInit() { 
    this.profileService.pushedData.subscribe(
     (value: Profile) => this.profile 
    ); 

    console.log("this.profile in img upload is"); 
    console.log(this.profile); 
    } 
} 

答えて

0

から到着したときにこのコールバックは、私が持っていた問題は、観測を使用する方法の誤解によるものであったといいます。私は別のページにリダイレクトしていました(新しいコンポーネントで新しいテンプレートをリロードしています)、プロファイルデータから画像をアップロードしたい領域に移動しました。これは欠陥のあるコンセプトでした。

  1. ときを決定するために、いくつかのngIf文を追加し、アップロードするために第二の成分とテンプレートを削除し、プロファイル作成コンポーネントにそのコードのすべてを組み込む:私はそれを固定方法は、次の操作を行うことでしたユーザーがさまざまなタスク(プロファイル情報の入力とプロファイルオブジェクトの作成、写真の追加、ビデオの追加など)を実行することに基づいて、プロファイル作成ページのさまざまな領域を表示します。私は別のに使用する1つのアクションの結果を参照することができ、そして物事が達成されたとして、私は、アプリケーションの状態と何を制御するための変数を設定することができるように、私は同じページに常にだったこれらの事を行うことにより

ユーザーに表示されていました。

テンプレートのための最終的なコードは以下の通りです:

<script src="profile-input.component.ts"></script> 
<section class="col-md-8 col-md-offset-2"> 
    <form [hidden]="formSubmitted" [formGroup]="profileForm" (ngSubmit)="onSubmit()"> 

    <div class="row"> 
     <div class="col-xs-12"> 
     <div class="form-group"> 
      <label for="first_name">First Name</label> 
      <input 
      type="text" 
      id="first_name" 
      class="form-control" 
      formControlName="first_name"> 
     </div> 
     </div> 
    </div> 
    <div class="row"> 
     <div class="col-xs-12"> 
     <div class="form-group"> 
      <label for="last_name">Last name</label> 
      <input 
      type="text" 
      id="last_name" 
      class="form-control" 
      formControlName="last_name"> 
     </div> 
     </div> 
    </div> 


    <div class="row"> 
     <label>UserType</label> 
     <input type="checkbox" id="producer" class="form-control" formControlName="producer" >Producer<br> 
     <input type="checkbox" id="client" class="form-control" formControlName="client" >Client<br> 
     <input type="checkbox" id="creative" class="form-control" formControlName="creative" >Creative<br> 
    </div> 


    <button type="submit" class="btn btn-primary" [disabled]="!profileForm.valid" >{{ !profile ? 'Add Profile' : 'Save Profile' }}</button> 
    <button type="button" class="btn btn-danger" (click)="onCancel()" *ngIf="profile">Cancel</button> 
    </form> 
</section> 

<!-- image upload START--> 
<section [hidden]="!imgUploadVisible" class="col-md-8 col-md-offset-2"> 
    <h2 *ngIf="createdProfile">Welcome {{createdProfile.first_name}}!</h2> 
    <p>Now lets get a look at you.</p> 
    <hr> 
    <h2>Profile Image Upload</h2> 
    <input type="file" (change)="imgFileChangeEvent($event)" placeholder="Upload file..." /> 
    <br> 
    <button type="button" (click)="uploadImg()">Upload Image</button> 
    <hr> 

    <div *ngIf="uploadFile" > 
    Uploaded File Path: {{ uploadFile }} 
    </div> 
    <div class="row"> 
    <div class="col-xs-12"> 
     <div class="img" *ngIf="uploadFile"> 
     <img [src]="uploadFile" width="200px" alt=""> 
     </div> 
    </div> 
    </div> 
    <br> 
    <button [hidden]="!uploadFile" type="button" (click)="sendToS3()">Send TO S3</button> 
    <hr> 
    <div *ngIf="s3LocString"> 
    S3 Location: {{s3LocString}} 
    <br> 
    <img [src]="s3LocString" width="200px" alt=""> 
    </div> 

    <button type="button" (click)="imgUploadComplete()">Next</button> 

</section> 
<!-- image upload END--> 


<!-- Video upload START--> 

<section [hidden]="!vidUploadVisible" class="col-md-8 col-md-offset-2"> 
    <h2>Upload Profile Video</h2> 
    <p>Now show us what you can do.</p> 
    <hr> 
    <h2>Demo Video Upload</h2> 
    <input type="file" (change)="vidFileChangeEvent($event)" placeholder="Upload file..." /> 
    <br> 
    <button type="button" (click)="uploadVid()">Upload Video</button> 
    <hr> 

    <div *ngIf="vidUploadFile" > 
    Uploaded File Path: {{ vidUploadFile }} 
    </div> 
    <div class="row"> 
    <div class="col-xs-12"> 
     <div class="vid" *ngIf="vidUploadFile"> 
     <video autoplay controls [src]="vidUploadFile"></video> 

     </div> 
    </div> 
    </div> 


</section> 

プロファイル入力コンポーネントの重要な部分は以下の通りです:これは他の誰かがより良いこれらの概念を理解するのに役立ちます

uploadImg() { 
    console.log('this.createdProfile before upload'); 
    console.log(this.createdProfile); 
    this.uploadFileService.makeFileRequest("http://localhost:3000/upload", this.createdProfile.profileId, this.imgFilesToUpload, 'profileImg') 
     .subscribe(
     (result) => { 
      console.log('result in prof input action removed is'); 
      console.log(result); 
      this.imageUploaded = true; 
      this.formSubmitted = true; 
      this.uploadFile = result.obj.path; 
      this.uploadObject = result.obj 
     }, 
     (error) => { 
      console.log('We are in error'); 
      console.error(error); 
     }); 
    } 

    uploadVid() { 
    console.log('this.createdProfile before upload'); 
    console.log(this.createdProfile); 
    this.uploadFileService.makeFileRequest("http://localhost:3000/upload", this.createdProfile.profileId, this.vidFilesToUpload, 'profileVideo') 
     .subscribe(
     (result) => { 
      console.log('result in prof input action removed is'); 
      console.log(result); 
      this.vidUploaded = true; 
      this.vidUploadFile = result.obj.path; 
      this.vidUploadObject = result.obj 
     }, 
     (error) => { 
      console.log('We are in error'); 
      console.error(error); 
     }); 
    } 

    sendToS3() { 
    console.log('uploading to S3'); 
    console.log(this.uploadObject); 

    this.uploadFileService.sendToS3(this.uploadObject, this.createdProfile.profileId, this.uploadObject._id) 
     .subscribe(
     data => { 
      console.log(data); 
      this.s3Location = data; 
      this.s3LocString = data.Location; 
     }, 
     error => { 
      console.log(error); 
     } 
    ); 
    } 

希望。

0

サブスクリプションから返されたデータを参照するコードをサブスクリプションコールバックに移動する必要があります。データが観測

ngOnInit() { 
    this.profileService.pushedData.subscribe(
     (value: Profile) => { 
      this.profile = value; 
      console.log("this.profile in img upload is"); 
      console.log(this.profile); 
     }); 
    } 
} 
+0

これを試してみましたが、実際にログが「img uploadのthis.profile」というログをコンソールに表示することはありません。 – JasonPerr

+0

コンソールに最後に出力される値は**サービスの**値ですプロファイルオブジェクト(profile.service pushDataメソッドから取得) – JasonPerr

+0

実行時に実際に何が起こっているのかをいくつかのコードスニペットから得るのは難しいです。コールバックが呼び出された後にのみデータが利用可能であることに注意する必要があります。 –

関連する問題