]> git.immae.eu Git - github/Chocobozzz/PeerTube.git/blobdiff - client/src/app/shared/user-subscription/subscribe-button.component.ts
Fix OnInit for subscribe button
[github/Chocobozzz/PeerTube.git] / client / src / app / shared / user-subscription / subscribe-button.component.ts
index f0bee9d4779f605ba19d3d1e7538a95c87e325cb..947f34c852236e215304c68c089ab35315a0a536 100644 (file)
@@ -1,4 +1,4 @@
-import { Component, Input, OnInit } from '@angular/core'
+import { Component, Input, OnInit, OnChanges } from '@angular/core'
 import { Router } from '@angular/router'
 import { AuthService, Notifier } from '@app/core'
 import { UserSubscriptionService } from '@app/shared/user-subscription/user-subscription.service'
@@ -7,14 +7,14 @@ import { I18n } from '@ngx-translate/i18n-polyfill'
 import { VideoService } from '@app/shared/video/video.service'
 import { FeedFormat } from '../../../../../shared/models/feeds'
 import { Account } from '@app/shared/account/account.model'
-import { forkJoin } from 'rxjs'
+import { concat, forkJoin, merge } from 'rxjs'
 
 @Component({
   selector: 'my-subscribe-button',
   templateUrl: './subscribe-button.component.html',
   styleUrls: [ './subscribe-button.component.scss' ]
 })
-export class SubscribeButtonComponent implements OnInit {
+export class SubscribeButtonComponent implements OnInit, OnChanges {
   /**
    * SubscribeButtonComponent can be used with a single VideoChannel passed as [VideoChannel],
    * or with an account and a full list of that account's videoChannels. The latter is intended
@@ -26,7 +26,7 @@ export class SubscribeButtonComponent implements OnInit {
   @Input() displayFollowers = false
   @Input() size: 'small' | 'normal' = 'normal'
 
-  subscribed: Map<string, boolean>
+  subscribed = new Map<string, boolean>()
 
   constructor (
     private authService: AuthService,
@@ -35,18 +35,16 @@ export class SubscribeButtonComponent implements OnInit {
     private userSubscriptionService: UserSubscriptionService,
     private i18n: I18n,
     private videoService: VideoService
-  ) {
-    this.subscribed = new Map<string, boolean>()
-  }
+  ) { }
 
   get handle () {
     return this.account
       ? this.account.nameWithHost
-      : this.videoChannels[0].name + '@' + this.videoChannels[0].host
+      : this.videoChannel.name + '@' + this.videoChannel.host
   }
 
   get channelHandle () {
-    return this.getChannelHandler(this.videoChannels[0])
+    return this.getChannelHandler(this.videoChannel)
   }
 
   get uri () {
@@ -67,20 +65,28 @@ export class SubscribeButtonComponent implements OnInit {
     return rssFeed.url
   }
 
-  ngOnInit () {
-    if (this.isUserLoggedIn()) {
+  get videoChannel () {
+    return this.videoChannels[0]
+  }
 
-      forkJoin(this.videoChannels.map(videoChannel => {
-        const handle = this.getChannelHandler(videoChannel)
-        this.subscribed.set(handle, false)
-        this.userSubscriptionService.doesSubscriptionExist(handle)
-          .subscribe(
-            res => this.subscribed.set(handle, res[handle]),
+  get isAllChannelsSubscribed () {
+    return this.subscribeStatus(true).length === this.videoChannels.length
+  }
 
-            err => this.notifier.error(err.message)
-          )
-      }))
-    }
+  get isAtLeastOneChannelSubscribed () {
+    return this.subscribeStatus(true).length > 0
+  }
+
+  get isBigButton () {
+    return this.isUserLoggedIn() && this.videoChannels.length > 1 && this.isAtLeastOneChannelSubscribed
+  }
+
+  ngOnInit () {
+    this.loadSubscribedStatus()
+  }
+
+  ngOnChanges () {
+    this.ngOnInit()
   }
 
   subscribe () {
@@ -92,31 +98,24 @@ export class SubscribeButtonComponent implements OnInit {
   }
 
   localSubscribe () {
-    const observableBatch: any = []
+    const subscribedStatus = this.subscribeStatus(false)
 
-    this.videoChannels
-      .filter(videoChannel => this.subscribeStatus(false).includes(this.getChannelHandler(videoChannel)))
-      .forEach(videoChannel => observableBatch.push(
-        this.userSubscriptionService.addSubscription(this.getChannelHandler(videoChannel))
-      ))
+    const observableBatch = this.videoChannels
+      .map(videoChannel => this.getChannelHandler(videoChannel))
+      .filter(handle => subscribedStatus.includes(handle))
+      .map(handle => this.userSubscriptionService.addSubscription(handle))
 
     forkJoin(observableBatch)
       .subscribe(
         () => {
-          [...this.subscribed.keys()].forEach((key) => {
-            this.subscribed.set(key, true)
-          })
-
           this.notifier.success(
             this.account
               ? this.i18n(
-                  'Subscribed to all current channels of {{nameWithHost}}. ' +
-                  'You will be notified of all their new videos.',
+                  'Subscribed to all current channels of {{nameWithHost}}. You will be notified of all their new videos.',
                   { nameWithHost: this.account.displayName }
                 )
               : this.i18n(
-                  'Subscribed to {{nameWithHost}}. ' +
-                  'You will be notified of all their new videos.',
+                  'Subscribed to {{nameWithHost}}. You will be notified of all their new videos.',
                   { nameWithHost: this.videoChannels[0].displayName }
                 )
             ,
@@ -135,55 +134,65 @@ export class SubscribeButtonComponent implements OnInit {
   }
 
   localUnsubscribe () {
-    const observableBatch: any = []
+    const subscribeStatus = this.subscribeStatus(true)
 
-    this.videoChannels
-      .filter(videoChannel => this.subscribeStatus(true).includes(this.getChannelHandler(videoChannel)))
-      .forEach(videoChannel => observableBatch.push(
-        this.userSubscriptionService.deleteSubscription(this.getChannelHandler(videoChannel))
-      ))
+    const observableBatch = this.videoChannels
+                                .map(videoChannel => this.getChannelHandler(videoChannel))
+                                .filter(handle => subscribeStatus.includes(handle))
+                                .map(handle => this.userSubscriptionService.deleteSubscription(handle))
 
-    forkJoin(observableBatch)
-        .subscribe(
-          () => {
-            [...this.subscribed.keys()].forEach((key) => {
-              this.subscribed.set(key, false)
-            })
-
-            this.notifier.success(
-              this.account
-                ? this.i18n('Unsubscribed from all channels of {{nameWithHost}}', { nameWithHost: this.account.nameWithHost })
-                : this.i18n('Unsubscribed from {{nameWithHost}}', { nameWithHost: this.videoChannels[0].nameWithHost })
-              ,
-              this.i18n('Unsubscribed')
-            )
-          },
+    concat(...observableBatch)
+      .subscribe({
+        complete: () => {
+          this.notifier.success(
+            this.account
+              ? this.i18n('Unsubscribed from all channels of {{nameWithHost}}', { nameWithHost: this.account.nameWithHost })
+              : this.i18n('Unsubscribed from {{nameWithHost}}', { nameWithHost: this.videoChannels[ 0 ].nameWithHost })
+            ,
+            this.i18n('Unsubscribed')
+          )
+        },
 
-          err => this.notifier.error(err.message)
-        )
+        error: err => this.notifier.error(err.message)
+      })
   }
 
   isUserLoggedIn () {
     return this.authService.isLoggedIn()
   }
 
-  isAllChannelsSubscribed () {
-    return !Array.from(this.subscribed.values()).includes(false)
-  }
-
   gotoLogin () {
     this.router.navigate([ '/login' ])
   }
 
+  subscribeStatus (subscribed: boolean) {
+    const accumulator: string[] = []
+    for (const [key, value] of this.subscribed.entries()) {
+      if (value === subscribed) accumulator.push(key)
+    }
+
+    return accumulator
+  }
+
   private getChannelHandler (videoChannel: VideoChannel) {
     return videoChannel.name + '@' + videoChannel.host
   }
 
-  private subscribeStatus (subscribed: boolean) {
-    const accumulator = []
-    for (const [key, value] of this.subscribed.entries()) {
-      if (value === subscribed) accumulator.push(key)
+  private loadSubscribedStatus () {
+    if (!this.isUserLoggedIn()) return
+
+    for (const videoChannel of this.videoChannels) {
+      const handle = this.getChannelHandler(videoChannel)
+      this.subscribed.set(handle, false)
+
+      merge(
+        this.userSubscriptionService.listenToSubscriptionCacheChange(handle),
+        this.userSubscriptionService.doesSubscriptionExist(handle)
+      ).subscribe(
+        res => this.subscribed.set(handle, res),
+
+        err => this.notifier.error(err.message)
+      )
     }
-    return accumulator
   }
 }