aboutsummaryrefslogtreecommitdiffhomepage
path: root/client/src
diff options
context:
space:
mode:
Diffstat (limited to 'client/src')
-rw-r--r--client/src/app/+admin/config/edit-custom-config/edit-custom-config.component.ts4
-rw-r--r--client/src/app/+admin/users/user-edit/user-edit.ts2
-rw-r--r--client/src/app/+admin/users/user-list/user-list.component.ts6
-rw-r--r--client/src/app/+my-account/my-account-video-channels/my-account-video-channel-update.component.ts6
-rw-r--r--client/src/app/+my-account/my-account-videos/my-account-videos.component.ts11
-rw-r--r--client/src/app/+my-account/my-account-videos/video-change-ownership/video-change-ownership.component.ts3
-rw-r--r--client/src/app/+my-account/shared/actor-avatar-info.component.ts4
-rw-r--r--client/src/app/core/auth/auth.service.ts2
-rw-r--r--client/src/app/core/server/server.service.ts4
-rw-r--r--client/src/app/menu/menu.component.ts2
-rw-r--r--client/src/app/search/advanced-search.model.ts4
-rw-r--r--client/src/app/shared/buttons/action-dropdown.component.ts6
-rw-r--r--client/src/app/shared/buttons/button.component.ts6
-rw-r--r--client/src/app/shared/buttons/edit-button.component.ts2
-rw-r--r--client/src/app/shared/guards/can-deactivate-guard.service.ts4
-rw-r--r--client/src/app/shared/misc/help.component.ts2
-rw-r--r--client/src/app/shared/rest/rest-extractor.service.ts4
-rw-r--r--client/src/app/shared/rest/rest.service.ts2
-rw-r--r--client/src/app/shared/shared.module.ts6
-rw-r--r--client/src/app/shared/users/user.model.ts1
-rw-r--r--client/src/app/shared/video/abstract-video-list.html2
-rw-r--r--client/src/app/shared/video/abstract-video-list.scss2
-rw-r--r--client/src/app/shared/video/abstract-video-list.ts11
-rw-r--r--client/src/app/shared/video/feed.component.html (renamed from client/src/app/shared/video/video-feed.component.html)0
-rw-r--r--client/src/app/shared/video/feed.component.scss (renamed from client/src/app/shared/video/video-feed.component.scss)0
-rw-r--r--client/src/app/shared/video/feed.component.ts11
-rw-r--r--client/src/app/shared/video/syndication.model.ts7
-rw-r--r--client/src/app/shared/video/video-edit.model.ts5
-rw-r--r--client/src/app/shared/video/video-feed.component.ts10
-rw-r--r--client/src/app/shared/video/video.service.ts4
-rw-r--r--client/src/app/videos/+video-edit/shared/video-caption-add-modal.component.ts5
-rw-r--r--client/src/app/videos/+video-edit/video-add-components/video-import-torrent.component.ts6
-rw-r--r--client/src/app/videos/+video-edit/video-add-components/video-send.ts6
-rw-r--r--client/src/app/videos/+video-edit/video-add-components/video-upload.component.ts6
-rw-r--r--client/src/app/videos/+video-watch/comment/linkifier.service.ts1
-rw-r--r--client/src/app/videos/+video-watch/comment/video-comment.component.ts2
-rw-r--r--client/src/app/videos/+video-watch/comment/video-comment.service.ts8
-rw-r--r--client/src/app/videos/+video-watch/comment/video-comments.component.html2
-rw-r--r--client/src/app/videos/+video-watch/comment/video-comments.component.scss2
-rw-r--r--client/src/app/videos/+video-watch/comment/video-comments.component.ts3
-rw-r--r--client/src/app/videos/+video-watch/video-watch.component.scss2
-rw-r--r--client/src/app/videos/+video-watch/video-watch.component.ts16
-rw-r--r--client/src/assets/player/peertube-chunk-store.ts12
-rw-r--r--client/src/assets/player/peertube-link-button.ts5
-rw-r--r--client/src/assets/player/peertube-load-progress-bar.ts5
-rw-r--r--client/src/assets/player/peertube-player.ts20
-rw-r--r--client/src/assets/player/peertube-videojs-plugin.ts20
-rw-r--r--client/src/assets/player/peertube-videojs-typings.ts5
-rw-r--r--client/src/assets/player/resolution-menu-button.ts6
-rw-r--r--client/src/assets/player/resolution-menu-item.ts6
-rw-r--r--client/src/assets/player/settings-menu-button.ts17
-rw-r--r--client/src/assets/player/settings-menu-item.ts8
-rw-r--r--client/src/assets/player/theater-button.ts6
-rw-r--r--client/src/assets/player/utils.ts2
-rw-r--r--client/src/assets/player/webtorrent-info-button.ts2
-rw-r--r--client/src/standalone/videos/embed.ts7
-rw-r--r--client/src/standalone/videos/test-embed.ts6
-rw-r--r--client/src/typings.d.ts6
58 files changed, 188 insertions, 137 deletions
diff --git a/client/src/app/+admin/config/edit-custom-config/edit-custom-config.component.ts b/client/src/app/+admin/config/edit-custom-config/edit-custom-config.component.ts
index 9a9298825..f48b6fc1a 100644
--- a/client/src/app/+admin/config/edit-custom-config/edit-custom-config.component.ts
+++ b/client/src/app/+admin/config/edit-custom-config/edit-custom-config.component.ts
@@ -62,7 +62,7 @@ export class EditCustomConfigComponent extends FormReactive implements OnInit {
62 } 62 }
63 63
64 ngOnInit () { 64 ngOnInit () {
65 const formGroupData: any = { 65 const formGroupData: { [key: string]: any } = {
66 instanceName: this.customConfigValidatorsService.INSTANCE_NAME, 66 instanceName: this.customConfigValidatorsService.INSTANCE_NAME,
67 instanceShortDescription: this.customConfigValidatorsService.INSTANCE_SHORT_DESCRIPTION, 67 instanceShortDescription: this.customConfigValidatorsService.INSTANCE_SHORT_DESCRIPTION,
68 instanceDescription: null, 68 instanceDescription: null,
@@ -202,7 +202,7 @@ export class EditCustomConfigComponent extends FormReactive implements OnInit {
202 } 202 }
203 203
204 private updateForm () { 204 private updateForm () {
205 const data: any = { 205 const data: { [key: string]: any } = {
206 instanceName: this.customConfig.instance.name, 206 instanceName: this.customConfig.instance.name,
207 instanceShortDescription: this.customConfig.instance.shortDescription, 207 instanceShortDescription: this.customConfig.instance.shortDescription,
208 instanceDescription: this.customConfig.instance.description, 208 instanceDescription: this.customConfig.instance.description,
diff --git a/client/src/app/+admin/users/user-edit/user-edit.ts b/client/src/app/+admin/users/user-edit/user-edit.ts
index a4d696e69..99ce5804b 100644
--- a/client/src/app/+admin/users/user-edit/user-edit.ts
+++ b/client/src/app/+admin/users/user-edit/user-edit.ts
@@ -7,7 +7,7 @@ export abstract class UserEdit extends FormReactive {
7 7
8 videoQuotaOptions: { value: string, label: string }[] = [] 8 videoQuotaOptions: { value: string, label: string }[] = []
9 videoQuotaDailyOptions: { value: string, label: string }[] = [] 9 videoQuotaDailyOptions: { value: string, label: string }[] = []
10 roles = Object.keys(USER_ROLE_LABELS).map((key: any) => ({ value: key.toString(), label: USER_ROLE_LABELS[key] })) 10 roles = Object.keys(USER_ROLE_LABELS).map(key => ({ value: key.toString(), label: USER_ROLE_LABELS[key] }))
11 11
12 protected abstract serverService: ServerService 12 protected abstract serverService: ServerService
13 protected abstract configService: ConfigService 13 protected abstract configService: ConfigService
diff --git a/client/src/app/+admin/users/user-list/user-list.component.ts b/client/src/app/+admin/users/user-list/user-list.component.ts
index 0d7f88d2b..3859af9ff 100644
--- a/client/src/app/+admin/users/user-list/user-list.component.ts
+++ b/client/src/app/+admin/users/user-list/user-list.component.ts
@@ -23,7 +23,7 @@ export class UserListComponent extends RestTable implements OnInit {
23 pagination: RestPagination = { count: this.rowsPerPage, start: 0 } 23 pagination: RestPagination = { count: this.rowsPerPage, start: 0 }
24 24
25 selectedUsers: User[] = [] 25 selectedUsers: User[] = []
26 bulkUserActions: DropdownAction<User>[] = [] 26 bulkUserActions: DropdownAction<User[]>[] = []
27 27
28 constructor ( 28 constructor (
29 private notificationsService: NotificationsService, 29 private notificationsService: NotificationsService,
@@ -45,12 +45,12 @@ export class UserListComponent extends RestTable implements OnInit {
45 { 45 {
46 label: this.i18n('Ban'), 46 label: this.i18n('Ban'),
47 handler: users => this.openBanUserModal(users), 47 handler: users => this.openBanUserModal(users),
48 isDisplayed: users => users.every((u: any) => u.blocked === false) 48 isDisplayed: users => users.every(u => u.blocked === false)
49 }, 49 },
50 { 50 {
51 label: this.i18n('Unban'), 51 label: this.i18n('Unban'),
52 handler: users => this.unbanUsers(users), 52 handler: users => this.unbanUsers(users),
53 isDisplayed: users => users.every((u: any) => u.blocked === true) 53 isDisplayed: users => users.every(u => u.blocked === true)
54 } 54 }
55 ] 55 ]
56 } 56 }
diff --git a/client/src/app/+my-account/my-account-video-channels/my-account-video-channel-update.component.ts b/client/src/app/+my-account/my-account-video-channels/my-account-video-channel-update.component.ts
index f2b8a4e26..5d43956f2 100644
--- a/client/src/app/+my-account/my-account-video-channels/my-account-video-channel-update.component.ts
+++ b/client/src/app/+my-account/my-account-video-channels/my-account-video-channel-update.component.ts
@@ -1,4 +1,4 @@
1import { Component, OnDestroy, OnInit, ViewChild } from '@angular/core' 1import { Component, OnDestroy, OnInit } from '@angular/core'
2import { ActivatedRoute, Router } from '@angular/router' 2import { ActivatedRoute, Router } from '@angular/router'
3import { NotificationsService } from 'angular2-notifications' 3import { NotificationsService } from 'angular2-notifications'
4import { MyAccountVideoChannelEdit } from './my-account-video-channel-edit' 4import { MyAccountVideoChannelEdit } from './my-account-video-channel-edit'
@@ -17,11 +17,9 @@ import { VideoChannelValidatorsService } from '@app/shared/forms/form-validators
17 styleUrls: [ './my-account-video-channel-edit.component.scss' ] 17 styleUrls: [ './my-account-video-channel-edit.component.scss' ]
18}) 18})
19export class MyAccountVideoChannelUpdateComponent extends MyAccountVideoChannelEdit implements OnInit, OnDestroy { 19export class MyAccountVideoChannelUpdateComponent extends MyAccountVideoChannelEdit implements OnInit, OnDestroy {
20 @ViewChild('avatarfileInput') avatarfileInput: any
21
22 error: string 20 error: string
23
24 videoChannelToUpdate: VideoChannel 21 videoChannelToUpdate: VideoChannel
22
25 private paramsSub: Subscription 23 private paramsSub: Subscription
26 24
27 constructor ( 25 constructor (
diff --git a/client/src/app/+my-account/my-account-videos/my-account-videos.component.ts b/client/src/app/+my-account/my-account-videos/my-account-videos.component.ts
index 52307f09e..2d88ac760 100644
--- a/client/src/app/+my-account/my-account-videos/my-account-videos.component.ts
+++ b/client/src/app/+my-account/my-account-videos/my-account-videos.component.ts
@@ -66,7 +66,7 @@ export class MyAccountVideosComponent extends AbstractVideoList implements OnIni
66 } 66 }
67 67
68 isInSelectionMode () { 68 isInSelectionMode () {
69 return Object.keys(this.checkedVideos).some((k: any) => this.checkedVideos[ k ] === true) 69 return Object.keys(this.checkedVideos).some(k => this.checkedVideos[ k ] === true)
70 } 70 }
71 71
72 getVideosObservable (page: number) { 72 getVideosObservable (page: number) {
@@ -81,7 +81,7 @@ export class MyAccountVideosComponent extends AbstractVideoList implements OnIni
81 81
82 async deleteSelectedVideos () { 82 async deleteSelectedVideos () {
83 const toDeleteVideosIds = Object.keys(this.checkedVideos) 83 const toDeleteVideosIds = Object.keys(this.checkedVideos)
84 .filter((k: any) => this.checkedVideos[ k ] === true) 84 .filter(k => this.checkedVideos[ k ] === true)
85 .map(k => parseInt(k, 10)) 85 .map(k => parseInt(k, 10))
86 86
87 const res = await this.confirmService.confirm( 87 const res = await this.confirmService.confirm(
@@ -168,10 +168,9 @@ export class MyAccountVideosComponent extends AbstractVideoList implements OnIni
168 } 168 }
169 169
170 private spliceVideosById (id: number) { 170 private spliceVideosById (id: number) {
171 let key: any 171 for (const key of Object.keys(this.loadedPages)) {
172 for (key of Object.keys(this.loadedPages)) { 172 const videos: Video[] = this.loadedPages[ key ]
173 const videos = this.loadedPages[ key ] 173 const index = videos.findIndex(v => v.id === id)
174 const index = videos.findIndex((v: any) => v.id === id)
175 174
176 if (index !== -1) { 175 if (index !== -1) {
177 videos.splice(index, 1) 176 videos.splice(index, 1)
diff --git a/client/src/app/+my-account/my-account-videos/video-change-ownership/video-change-ownership.component.ts b/client/src/app/+my-account/my-account-videos/video-change-ownership/video-change-ownership.component.ts
index eb3f9404f..9f94f3c13 100644
--- a/client/src/app/+my-account/my-account-videos/video-change-ownership/video-change-ownership.component.ts
+++ b/client/src/app/+my-account/my-account-videos/video-change-ownership/video-change-ownership.component.ts
@@ -49,8 +49,7 @@ export class VideoChangeOwnershipComponent extends FormReactive implements OnIni
49 .catch((_) => _) // Called when closing (cancel) the modal without validating, do nothing 49 .catch((_) => _) // Called when closing (cancel) the modal without validating, do nothing
50 } 50 }
51 51
52 // TODO: typing 52 search (event: { query: string }) {
53 search (event: any) {
54 const query = event.query 53 const query = event.query
55 this.userService.autocomplete(query) 54 this.userService.autocomplete(query)
56 .subscribe( 55 .subscribe(
diff --git a/client/src/app/+my-account/shared/actor-avatar-info.component.ts b/client/src/app/+my-account/shared/actor-avatar-info.component.ts
index b4505a7f2..54bacc212 100644
--- a/client/src/app/+my-account/shared/actor-avatar-info.component.ts
+++ b/client/src/app/+my-account/shared/actor-avatar-info.component.ts
@@ -1,4 +1,4 @@
1import { Component, EventEmitter, Input, Output, ViewChild } from '@angular/core' 1import { Component, ElementRef, EventEmitter, Input, Output, ViewChild } from '@angular/core'
2import { ServerService } from '../../core/server' 2import { ServerService } from '../../core/server'
3import { NotificationsService } from 'angular2-notifications' 3import { NotificationsService } from 'angular2-notifications'
4import { VideoChannel } from '@app/shared/video-channel/video-channel.model' 4import { VideoChannel } from '@app/shared/video-channel/video-channel.model'
@@ -10,7 +10,7 @@ import { Account } from '@app/shared/account/account.model'
10 styleUrls: [ './actor-avatar-info.component.scss' ] 10 styleUrls: [ './actor-avatar-info.component.scss' ]
11}) 11})
12export class ActorAvatarInfoComponent { 12export class ActorAvatarInfoComponent {
13 @ViewChild('avatarfileInput') avatarfileInput: any 13 @ViewChild('avatarfileInput') avatarfileInput: ElementRef<HTMLInputElement>
14 14
15 @Input() actor: VideoChannel | Account 15 @Input() actor: VideoChannel | Account
16 16
diff --git a/client/src/app/core/auth/auth.service.ts b/client/src/app/core/auth/auth.service.ts
index 5315c8b1d..443772c9e 100644
--- a/client/src/app/core/auth/auth.service.ts
+++ b/client/src/app/core/auth/auth.service.ts
@@ -221,7 +221,7 @@ export class AuthService {
221 } 221 }
222 222
223 refreshUserInformation () { 223 refreshUserInformation () {
224 const obj: any = { 224 const obj: UserLoginWithUsername = {
225 access_token: this.user.getAccessToken(), 225 access_token: this.user.getAccessToken(),
226 refresh_token: null, 226 refresh_token: null,
227 token_type: this.user.getTokenType(), 227 token_type: this.user.getTokenType(),
diff --git a/client/src/app/core/server/server.service.ts b/client/src/app/core/server/server.service.ts
index 1663a052c..da8bd26db 100644
--- a/client/src/app/core/server/server.service.ts
+++ b/client/src/app/core/server/server.service.ts
@@ -154,8 +154,8 @@ export class ServerService {
154 this.localeObservable 154 this.localeObservable
155 .pipe( 155 .pipe(
156 switchMap(translations => { 156 switchMap(translations => {
157 return this.http.get(ServerService.BASE_VIDEO_URL + attributeName) 157 return this.http.get<{ [id: string]: string }>(ServerService.BASE_VIDEO_URL + attributeName)
158 .pipe(map((data: any) => ({ data, translations }))) 158 .pipe(map(data => ({ data, translations })))
159 }) 159 })
160 ) 160 )
161 .subscribe(({ data, translations }) => { 161 .subscribe(({ data, translations }) => {
diff --git a/client/src/app/menu/menu.component.ts b/client/src/app/menu/menu.component.ts
index 348700c09..371beb4a5 100644
--- a/client/src/app/menu/menu.component.ts
+++ b/client/src/app/menu/menu.component.ts
@@ -18,7 +18,7 @@ export class MenuComponent implements OnInit {
18 userHasAdminAccess = false 18 userHasAdminAccess = false
19 helpVisible = false 19 helpVisible = false
20 20
21 private routesPerRight: any = { 21 private routesPerRight: { [ role in UserRight ]?: string } = {
22 [UserRight.MANAGE_USERS]: '/admin/users', 22 [UserRight.MANAGE_USERS]: '/admin/users',
23 [UserRight.MANAGE_SERVER_FOLLOW]: '/admin/friends', 23 [UserRight.MANAGE_SERVER_FOLLOW]: '/admin/friends',
24 [UserRight.MANAGE_VIDEO_ABUSES]: '/admin/moderation/video-abuses', 24 [UserRight.MANAGE_VIDEO_ABUSES]: '/admin/moderation/video-abuses',
diff --git a/client/src/app/search/advanced-search.model.ts b/client/src/app/search/advanced-search.model.ts
index 1d6c89282..033fa9bba 100644
--- a/client/src/app/search/advanced-search.model.ts
+++ b/client/src/app/search/advanced-search.model.ts
@@ -53,7 +53,7 @@ export class AdvancedSearch {
53 } 53 }
54 54
55 containsValues () { 55 containsValues () {
56 const obj: any = this.toUrlObject() 56 const obj = this.toUrlObject()
57 for (const k of Object.keys(obj)) { 57 for (const k of Object.keys(obj)) {
58 if (k === 'sort') continue // Exception 58 if (k === 'sort') continue // Exception
59 59
@@ -113,7 +113,7 @@ export class AdvancedSearch {
113 size () { 113 size () {
114 let acc = 0 114 let acc = 0
115 115
116 const obj: any = this.toUrlObject() 116 const obj = this.toUrlObject()
117 for (const k of Object.keys(obj)) { 117 for (const k of Object.keys(obj)) {
118 if (k === 'sort') continue // Exception 118 if (k === 'sort') continue // Exception
119 119
diff --git a/client/src/app/shared/buttons/action-dropdown.component.ts b/client/src/app/shared/buttons/action-dropdown.component.ts
index 9877f639d..d8026ef41 100644
--- a/client/src/app/shared/buttons/action-dropdown.component.ts
+++ b/client/src/app/shared/buttons/action-dropdown.component.ts
@@ -2,9 +2,9 @@ import { Component, Input } from '@angular/core'
2 2
3export type DropdownAction<T> = { 3export type DropdownAction<T> = {
4 label?: string 4 label?: string
5 handler?: (T: any) => any 5 handler?: (a: T) => any
6 linkBuilder?: (T: any) => (string | number)[] 6 linkBuilder?: (a: T) => (string | number)[]
7 isDisplayed?: (T: any) => boolean 7 isDisplayed?: (a: T) => boolean
8} 8}
9 9
10@Component({ 10@Component({
diff --git a/client/src/app/shared/buttons/button.component.ts b/client/src/app/shared/buttons/button.component.ts
index cccf98bc3..1a1162f09 100644
--- a/client/src/app/shared/buttons/button.component.ts
+++ b/client/src/app/shared/buttons/button.component.ts
@@ -8,9 +8,9 @@ import { Component, Input } from '@angular/core'
8 8
9export class ButtonComponent { 9export class ButtonComponent {
10 @Input() label = '' 10 @Input() label = ''
11 @Input() className: any = undefined 11 @Input() className: string = undefined
12 @Input() icon: any = undefined 12 @Input() icon: string = undefined
13 @Input() title: any = undefined 13 @Input() title: string = undefined
14 14
15 getTitle () { 15 getTitle () {
16 return this.title || this.label 16 return this.title || this.label
diff --git a/client/src/app/shared/buttons/edit-button.component.ts b/client/src/app/shared/buttons/edit-button.component.ts
index ea552663a..1fe4f7b30 100644
--- a/client/src/app/shared/buttons/edit-button.component.ts
+++ b/client/src/app/shared/buttons/edit-button.component.ts
@@ -8,5 +8,5 @@ import { Component, Input } from '@angular/core'
8 8
9export class EditButtonComponent { 9export class EditButtonComponent {
10 @Input() label: string 10 @Input() label: string
11 @Input() routerLink: any = [] 11 @Input() routerLink: string[] = []
12} 12}
diff --git a/client/src/app/shared/guards/can-deactivate-guard.service.ts b/client/src/app/shared/guards/can-deactivate-guard.service.ts
index e2a79e8c4..3a35fcfb3 100644
--- a/client/src/app/shared/guards/can-deactivate-guard.service.ts
+++ b/client/src/app/shared/guards/can-deactivate-guard.service.ts
@@ -4,8 +4,10 @@ import { Observable } from 'rxjs'
4import { ConfirmService } from '../../core/index' 4import { ConfirmService } from '../../core/index'
5import { I18n } from '@ngx-translate/i18n-polyfill' 5import { I18n } from '@ngx-translate/i18n-polyfill'
6 6
7export type CanComponentDeactivateResult = { text?: string, canDeactivate: Observable<boolean> | boolean }
8
7export interface CanComponentDeactivate { 9export interface CanComponentDeactivate {
8 canDeactivate: () => { text?: string, canDeactivate: Observable<boolean> | boolean } 10 canDeactivate: () => CanComponentDeactivateResult
9} 11}
10 12
11@Injectable() 13@Injectable()
diff --git a/client/src/app/shared/misc/help.component.ts b/client/src/app/shared/misc/help.component.ts
index ccce1ccfa..ba0452e77 100644
--- a/client/src/app/shared/misc/help.component.ts
+++ b/client/src/app/shared/misc/help.component.ts
@@ -60,7 +60,7 @@ export class HelpComponent implements OnInit, OnChanges {
60 } 60 }
61 61
62 private createMarkdownList (rules: string[]) { 62 private createMarkdownList (rules: string[]) {
63 const rulesToText: any = { 63 const rulesToText = {
64 'emphasis': this.i18n('Emphasis'), 64 'emphasis': this.i18n('Emphasis'),
65 'link': this.i18n('Links'), 65 'link': this.i18n('Links'),
66 'newline': this.i18n('New lines'), 66 'newline': this.i18n('New lines'),
diff --git a/client/src/app/shared/rest/rest-extractor.service.ts b/client/src/app/shared/rest/rest-extractor.service.ts
index 934f6c618..f149569ef 100644
--- a/client/src/app/shared/rest/rest-extractor.service.ts
+++ b/client/src/app/shared/rest/rest-extractor.service.ts
@@ -33,7 +33,7 @@ export class RestExtractor {
33 return this.applyToResultListData(result, this.convertDateToHuman, [ fieldsToConvert ]) 33 return this.applyToResultListData(result, this.convertDateToHuman, [ fieldsToConvert ])
34 } 34 }
35 35
36 convertDateToHuman (target: any, fieldsToConvert: string[]) { 36 convertDateToHuman (target: { [ id: string ]: string }, fieldsToConvert: string[]) {
37 fieldsToConvert.forEach(field => target[field] = dateToHuman(target[field])) 37 fieldsToConvert.forEach(field => target[field] = dateToHuman(target[field]))
38 38
39 return target 39 return target
@@ -83,7 +83,7 @@ export class RestExtractor {
83 errorMessage = err 83 errorMessage = err
84 } 84 }
85 85
86 const errorObj: any = { 86 const errorObj: { message: string, status: string, body: string } = {
87 message: errorMessage, 87 message: errorMessage,
88 status: undefined, 88 status: undefined,
89 body: undefined 89 body: undefined
diff --git a/client/src/app/shared/rest/rest.service.ts b/client/src/app/shared/rest/rest.service.ts
index 41824a18f..e6d4e6e5e 100644
--- a/client/src/app/shared/rest/rest.service.ts
+++ b/client/src/app/shared/rest/rest.service.ts
@@ -32,7 +32,7 @@ export class RestService {
32 return newParams 32 return newParams
33 } 33 }
34 34
35 addObjectParams (params: HttpParams, object: any) { 35 addObjectParams (params: HttpParams, object: { [ name: string ]: any }) {
36 for (const name of Object.keys(object)) { 36 for (const name of Object.keys(object)) {
37 const value = object[name] 37 const value = object[name]
38 if (!value) continue 38 if (!value) continue
diff --git a/client/src/app/shared/shared.module.ts b/client/src/app/shared/shared.module.ts
index 40e05fcc7..0ec2a9b15 100644
--- a/client/src/app/shared/shared.module.ts
+++ b/client/src/app/shared/shared.module.ts
@@ -25,7 +25,7 @@ import { VideoAbuseService } from './video-abuse'
25import { VideoBlacklistService } from './video-blacklist' 25import { VideoBlacklistService } from './video-blacklist'
26import { VideoOwnershipService } from './video-ownership' 26import { VideoOwnershipService } from './video-ownership'
27import { VideoMiniatureComponent } from './video/video-miniature.component' 27import { VideoMiniatureComponent } from './video/video-miniature.component'
28import { VideoFeedComponent } from './video/video-feed.component' 28import { FeedComponent } from './video/feed.component'
29import { VideoThumbnailComponent } from './video/video-thumbnail.component' 29import { VideoThumbnailComponent } from './video/video-thumbnail.component'
30import { VideoService } from './video/video.service' 30import { VideoService } from './video/video.service'
31import { AccountService } from '@app/shared/account/account.service' 31import { AccountService } from '@app/shared/account/account.service'
@@ -82,7 +82,7 @@ import { BlocklistService } from '@app/shared/blocklist'
82 LoaderComponent, 82 LoaderComponent,
83 VideoThumbnailComponent, 83 VideoThumbnailComponent,
84 VideoMiniatureComponent, 84 VideoMiniatureComponent,
85 VideoFeedComponent, 85 FeedComponent,
86 ButtonComponent, 86 ButtonComponent,
87 DeleteButtonComponent, 87 DeleteButtonComponent,
88 EditButtonComponent, 88 EditButtonComponent,
@@ -122,7 +122,7 @@ import { BlocklistService } from '@app/shared/blocklist'
122 LoaderComponent, 122 LoaderComponent,
123 VideoThumbnailComponent, 123 VideoThumbnailComponent,
124 VideoMiniatureComponent, 124 VideoMiniatureComponent,
125 VideoFeedComponent, 125 FeedComponent,
126 ButtonComponent, 126 ButtonComponent,
127 DeleteButtonComponent, 127 DeleteButtonComponent,
128 EditButtonComponent, 128 EditButtonComponent,
diff --git a/client/src/app/shared/users/user.model.ts b/client/src/app/shared/users/user.model.ts
index e6b612054..7c840ffa7 100644
--- a/client/src/app/shared/users/user.model.ts
+++ b/client/src/app/shared/users/user.model.ts
@@ -43,7 +43,6 @@ export class User implements UserServerModel {
43 43
44 blocked: boolean 44 blocked: boolean
45 blockedReason?: string 45 blockedReason?: string
46 [key: string]: any
47 46
48 constructor (hash: UserConstructorHash) { 47 constructor (hash: UserConstructorHash) {
49 this.id = hash.id 48 this.id = hash.id
diff --git a/client/src/app/shared/video/abstract-video-list.html b/client/src/app/shared/video/abstract-video-list.html
index 69a619b76..29492351b 100644
--- a/client/src/app/shared/video/abstract-video-list.html
+++ b/client/src/app/shared/video/abstract-video-list.html
@@ -3,7 +3,7 @@
3 <div *ngIf="titlePage" class="title-page title-page-single"> 3 <div *ngIf="titlePage" class="title-page title-page-single">
4 {{ titlePage }} 4 {{ titlePage }}
5 </div> 5 </div>
6 <my-video-feed [syndicationItems]="syndicationItems"></my-video-feed> 6 <my-feed [syndicationItems]="syndicationItems"></my-feed>
7 7
8 <div class="moderation-block" *ngIf="displayModerationBlock"> 8 <div class="moderation-block" *ngIf="displayModerationBlock">
9 <my-peertube-checkbox 9 <my-peertube-checkbox
diff --git a/client/src/app/shared/video/abstract-video-list.scss b/client/src/app/shared/video/abstract-video-list.scss
index 92998cb44..9fb3fd4d6 100644
--- a/client/src/app/shared/video/abstract-video-list.scss
+++ b/client/src/app/shared/video/abstract-video-list.scss
@@ -17,7 +17,7 @@
17 margin: 0 5px 0 0; 17 margin: 0 5px 0 0;
18 } 18 }
19 19
20 my-video-feed { 20 my-feed {
21 display: inline-block; 21 display: inline-block;
22 position: relative; 22 position: relative;
23 top: 1px; 23 top: 1px;
diff --git a/client/src/app/shared/video/abstract-video-list.ts b/client/src/app/shared/video/abstract-video-list.ts
index 87814d4ba..2d32dd6ad 100644
--- a/client/src/app/shared/video/abstract-video-list.ts
+++ b/client/src/app/shared/video/abstract-video-list.ts
@@ -12,6 +12,7 @@ import { Video } from './video.model'
12import { I18n } from '@ngx-translate/i18n-polyfill' 12import { I18n } from '@ngx-translate/i18n-polyfill'
13import { ScreenService } from '@app/shared/misc/screen.service' 13import { ScreenService } from '@app/shared/misc/screen.service'
14import { OwnerDisplayType } from '@app/shared/video/video-miniature.component' 14import { OwnerDisplayType } from '@app/shared/video/video-miniature.component'
15import { Syndication } from '@app/shared/video/syndication.model'
15 16
16export abstract class AbstractVideoList implements OnInit, OnDestroy { 17export abstract class AbstractVideoList implements OnInit, OnDestroy {
17 private static LINES_PER_PAGE = 4 18 private static LINES_PER_PAGE = 4
@@ -27,7 +28,7 @@ export abstract class AbstractVideoList implements OnInit, OnDestroy {
27 sort: VideoSortField = '-publishedAt' 28 sort: VideoSortField = '-publishedAt'
28 categoryOneOf?: number 29 categoryOneOf?: number
29 defaultSort: VideoSortField = '-publishedAt' 30 defaultSort: VideoSortField = '-publishedAt'
30 syndicationItems: any = [] 31 syndicationItems: Syndication[] = []
31 32
32 loadOnInit = true 33 loadOnInit = true
33 marginContent = true 34 marginContent = true
@@ -59,7 +60,7 @@ export abstract class AbstractVideoList implements OnInit, OnDestroy {
59 private resizeSubscription: Subscription 60 private resizeSubscription: Subscription
60 61
61 abstract getVideosObservable (page: number): Observable<{ videos: Video[], totalVideos: number}> 62 abstract getVideosObservable (page: number): Observable<{ videos: Video[], totalVideos: number}>
62 abstract generateSyndicationList (): any 63 abstract generateSyndicationList (): void
63 64
64 get user () { 65 get user () {
65 return this.authService.getUser() 66 return this.authService.getUser()
@@ -209,9 +210,11 @@ export abstract class AbstractVideoList implements OnInit, OnDestroy {
209 } 210 }
210 211
211 protected setNewRouteParams () { 212 protected setNewRouteParams () {
212 const paramsObject: any = this.buildRouteParams() 213 const paramsObject = this.buildRouteParams()
213 214
214 const queryParams = Object.keys(paramsObject).map(p => p + '=' + paramsObject[p]).join('&') 215 const queryParams = Object.keys(paramsObject)
216 .map(p => p + '=' + paramsObject[p])
217 .join('&')
215 this.location.replaceState(this.currentRoute, queryParams) 218 this.location.replaceState(this.currentRoute, queryParams)
216 } 219 }
217 220
diff --git a/client/src/app/shared/video/video-feed.component.html b/client/src/app/shared/video/feed.component.html
index 16116ba88..16116ba88 100644
--- a/client/src/app/shared/video/video-feed.component.html
+++ b/client/src/app/shared/video/feed.component.html
diff --git a/client/src/app/shared/video/video-feed.component.scss b/client/src/app/shared/video/feed.component.scss
index 385764be0..385764be0 100644
--- a/client/src/app/shared/video/video-feed.component.scss
+++ b/client/src/app/shared/video/feed.component.scss
diff --git a/client/src/app/shared/video/feed.component.ts b/client/src/app/shared/video/feed.component.ts
new file mode 100644
index 000000000..12507458f
--- /dev/null
+++ b/client/src/app/shared/video/feed.component.ts
@@ -0,0 +1,11 @@
1import { Component, Input } from '@angular/core'
2import { Syndication } from '@app/shared/video/syndication.model'
3
4@Component({
5 selector: 'my-feed',
6 styleUrls: [ './feed.component.scss' ],
7 templateUrl: './feed.component.html'
8})
9export class FeedComponent {
10 @Input() syndicationItems: Syndication[]
11}
diff --git a/client/src/app/shared/video/syndication.model.ts b/client/src/app/shared/video/syndication.model.ts
new file mode 100644
index 000000000..a52b5771b
--- /dev/null
+++ b/client/src/app/shared/video/syndication.model.ts
@@ -0,0 +1,7 @@
1import { FeedFormat } from '../../../../../shared/models/feeds/feed-format.enum'
2
3export interface Syndication {
4 format: FeedFormat,
5 label: string,
6 url: string
7} \ No newline at end of file
diff --git a/client/src/app/shared/video/video-edit.model.ts b/client/src/app/shared/video/video-edit.model.ts
index a62277e04..fc772a3cf 100644
--- a/client/src/app/shared/video/video-edit.model.ts
+++ b/client/src/app/shared/video/video-edit.model.ts
@@ -25,7 +25,6 @@ export class VideoEdit implements VideoUpdate {
25 uuid?: string 25 uuid?: string
26 id?: number 26 id?: number
27 scheduleUpdate?: VideoScheduleUpdate 27 scheduleUpdate?: VideoScheduleUpdate
28 [key: string]: any
29 28
30 constructor (video?: Video & { tags: string[], commentsEnabled: boolean, support: string, thumbnailUrl: string, previewUrl: string }) { 29 constructor (video?: Video & { tags: string[], commentsEnabled: boolean, support: string, thumbnailUrl: string, previewUrl: string }) {
31 if (video) { 30 if (video) {
@@ -50,14 +49,14 @@ export class VideoEdit implements VideoUpdate {
50 } 49 }
51 } 50 }
52 51
53 patch (values: any) { 52 patch (values: { [ id: string ]: string }) {
54 Object.keys(values).forEach((key) => { 53 Object.keys(values).forEach((key) => {
55 this[ key ] = values[ key ] 54 this[ key ] = values[ key ]
56 }) 55 })
57 56
58 // If schedule publication, the video is private and will be changed to public privacy 57 // If schedule publication, the video is private and will be changed to public privacy
59 if (parseInt(values['privacy'], 10) === VideoEdit.SPECIAL_SCHEDULED_PRIVACY) { 58 if (parseInt(values['privacy'], 10) === VideoEdit.SPECIAL_SCHEDULED_PRIVACY) {
60 const updateAt = (values['schedulePublicationAt'] as Date) 59 const updateAt = new Date(values['schedulePublicationAt'])
61 updateAt.setSeconds(0) 60 updateAt.setSeconds(0)
62 61
63 this.privacy = VideoPrivacy.PRIVATE 62 this.privacy = VideoPrivacy.PRIVATE
diff --git a/client/src/app/shared/video/video-feed.component.ts b/client/src/app/shared/video/video-feed.component.ts
deleted file mode 100644
index be6c80c3f..000000000
--- a/client/src/app/shared/video/video-feed.component.ts
+++ /dev/null
@@ -1,10 +0,0 @@
1import { Component, Input } from '@angular/core'
2
3@Component({
4 selector: 'my-video-feed',
5 styleUrls: [ './video-feed.component.scss' ],
6 templateUrl: './video-feed.component.html'
7})
8export class VideoFeedComponent {
9 @Input() syndicationItems: any
10}
diff --git a/client/src/app/shared/video/video.service.ts b/client/src/app/shared/video/video.service.ts
index 6283cf84d..65297d7a1 100644
--- a/client/src/app/shared/video/video.service.ts
+++ b/client/src/app/shared/video/video.service.ts
@@ -274,9 +274,9 @@ export class VideoService implements VideosProvider {
274 274
275 loadCompleteDescription (descriptionPath: string) { 275 loadCompleteDescription (descriptionPath: string) {
276 return this.authHttp 276 return this.authHttp
277 .get(environment.apiUrl + descriptionPath) 277 .get<{ description: string }>(environment.apiUrl + descriptionPath)
278 .pipe( 278 .pipe(
279 map((res: any) => res[ 'description' ]), 279 map(res => res.description),
280 catchError(err => this.restExtractor.handleError(err)) 280 catchError(err => this.restExtractor.handleError(err))
281 ) 281 )
282 } 282 }
diff --git a/client/src/app/videos/+video-edit/shared/video-caption-add-modal.component.ts b/client/src/app/videos/+video-edit/shared/video-caption-add-modal.component.ts
index a2c9237ad..796fbe531 100644
--- a/client/src/app/videos/+video-edit/shared/video-caption-add-modal.component.ts
+++ b/client/src/app/videos/+video-edit/shared/video-caption-add-modal.component.ts
@@ -5,6 +5,7 @@ import { VideoCaptionsValidatorsService } from '@app/shared/forms/form-validator
5import { ServerService } from '@app/core' 5import { ServerService } from '@app/core'
6import { VideoCaptionEdit } from '@app/shared/video-caption/video-caption-edit.model' 6import { VideoCaptionEdit } from '@app/shared/video-caption/video-caption-edit.model'
7import { NgbModal, NgbModalRef } from '@ng-bootstrap/ng-bootstrap' 7import { NgbModal, NgbModalRef } from '@ng-bootstrap/ng-bootstrap'
8import { VideoConstant } from '../../../../../../shared'
8 9
9@Component({ 10@Component({
10 selector: 'my-video-caption-add-modal', 11 selector: 'my-video-caption-add-modal',
@@ -19,7 +20,7 @@ export class VideoCaptionAddModalComponent extends FormReactive implements OnIni
19 20
20 @ViewChild('modal') modal: ElementRef 21 @ViewChild('modal') modal: ElementRef
21 22
22 videoCaptionLanguages: any = [] 23 videoCaptionLanguages: VideoConstant<string>[] = []
23 24
24 private openedModal: NgbModalRef 25 private openedModal: NgbModalRef
25 private closingModal = false 26 private closingModal = false
@@ -73,7 +74,7 @@ export class VideoCaptionAddModalComponent extends FormReactive implements OnIni
73 this.hide() 74 this.hide()
74 75
75 const languageId = this.form.value[ 'language' ] 76 const languageId = this.form.value[ 'language' ]
76 const languageObject = this.videoCaptionLanguages.find((l: any) => l.id === languageId) 77 const languageObject = this.videoCaptionLanguages.find(l => l.id === languageId)
77 78
78 this.captionAdded.emit({ 79 this.captionAdded.emit({
79 language: languageObject, 80 language: languageObject,
diff --git a/client/src/app/videos/+video-edit/video-add-components/video-import-torrent.component.ts b/client/src/app/videos/+video-edit/video-add-components/video-import-torrent.component.ts
index 9a50e2ab2..e13c06ce9 100644
--- a/client/src/app/videos/+video-edit/video-add-components/video-import-torrent.component.ts
+++ b/client/src/app/videos/+video-edit/video-add-components/video-import-torrent.component.ts
@@ -1,4 +1,4 @@
1import { Component, EventEmitter, OnInit, Output, ViewChild } from '@angular/core' 1import { Component, ElementRef, EventEmitter, OnInit, Output, ViewChild } from '@angular/core'
2import { Router } from '@angular/router' 2import { Router } from '@angular/router'
3import { NotificationsService } from 'angular2-notifications' 3import { NotificationsService } from 'angular2-notifications'
4import { VideoPrivacy, VideoUpdate } from '../../../../../../shared/models/videos' 4import { VideoPrivacy, VideoUpdate } from '../../../../../../shared/models/videos'
@@ -23,7 +23,7 @@ import { VideoImportService } from '@app/shared/video-import'
23}) 23})
24export class VideoImportTorrentComponent extends VideoSend implements OnInit, CanComponentDeactivate { 24export class VideoImportTorrentComponent extends VideoSend implements OnInit, CanComponentDeactivate {
25 @Output() firstStepDone = new EventEmitter<string>() 25 @Output() firstStepDone = new EventEmitter<string>()
26 @ViewChild('torrentfileInput') torrentfileInput: any 26 @ViewChild('torrentfileInput') torrentfileInput: ElementRef<HTMLInputElement>
27 27
28 videoFileName: string 28 videoFileName: string
29 magnetUri = '' 29 magnetUri = ''
@@ -64,7 +64,7 @@ export class VideoImportTorrentComponent extends VideoSend implements OnInit, Ca
64 } 64 }
65 65
66 fileChange () { 66 fileChange () {
67 const torrentfile = this.torrentfileInput.nativeElement.files[0] as File 67 const torrentfile = this.torrentfileInput.nativeElement.files[0]
68 if (!torrentfile) return 68 if (!torrentfile) return
69 69
70 this.importVideo(torrentfile) 70 this.importVideo(torrentfile)
diff --git a/client/src/app/videos/+video-edit/video-add-components/video-send.ts b/client/src/app/videos/+video-edit/video-add-components/video-send.ts
index cf9d47cbe..1bf22e1a9 100644
--- a/client/src/app/videos/+video-edit/video-add-components/video-send.ts
+++ b/client/src/app/videos/+video-edit/video-add-components/video-send.ts
@@ -3,7 +3,6 @@ import { LoadingBarService } from '@ngx-loading-bar/core'
3import { NotificationsService } from 'angular2-notifications' 3import { NotificationsService } from 'angular2-notifications'
4import { catchError, switchMap, tap } from 'rxjs/operators' 4import { catchError, switchMap, tap } from 'rxjs/operators'
5import { FormReactive } from '@app/shared' 5import { FormReactive } from '@app/shared'
6import { CanComponentDeactivate } from '@app/shared/guards/can-deactivate-guard.service'
7import { VideoConstant, VideoPrivacy } from '../../../../../../shared' 6import { VideoConstant, VideoPrivacy } from '../../../../../../shared'
8import { AuthService, ServerService } from '@app/core' 7import { AuthService, ServerService } from '@app/core'
9import { VideoService } from '@app/shared/video/video.service' 8import { VideoService } from '@app/shared/video/video.service'
@@ -11,8 +10,9 @@ import { VideoCaptionEdit } from '@app/shared/video-caption/video-caption-edit.m
11import { VideoCaptionService } from '@app/shared/video-caption' 10import { VideoCaptionService } from '@app/shared/video-caption'
12import { VideoEdit } from '@app/shared/video/video-edit.model' 11import { VideoEdit } from '@app/shared/video/video-edit.model'
13import { populateAsyncUserVideoChannels } from '@app/shared/misc/utils' 12import { populateAsyncUserVideoChannels } from '@app/shared/misc/utils'
13import { CanComponentDeactivateResult } from '@app/shared/guards/can-deactivate-guard.service'
14 14
15export abstract class VideoSend extends FormReactive implements OnInit, CanComponentDeactivate { 15export abstract class VideoSend extends FormReactive implements OnInit {
16 userVideoChannels: { id: number, label: string, support: string }[] = [] 16 userVideoChannels: { id: number, label: string, support: string }[] = []
17 videoPrivacies: VideoConstant<VideoPrivacy>[] = [] 17 videoPrivacies: VideoConstant<VideoPrivacy>[] = []
18 videoCaptions: VideoCaptionEdit[] = [] 18 videoCaptions: VideoCaptionEdit[] = []
@@ -30,7 +30,7 @@ export abstract class VideoSend extends FormReactive implements OnInit, CanCompo
30 protected videoService: VideoService 30 protected videoService: VideoService
31 protected videoCaptionService: VideoCaptionService 31 protected videoCaptionService: VideoCaptionService
32 32
33 abstract canDeactivate (): any 33 abstract canDeactivate (): CanComponentDeactivateResult
34 34
35 ngOnInit () { 35 ngOnInit () {
36 this.buildForm({}) 36 this.buildForm({})
diff --git a/client/src/app/videos/+video-edit/video-add-components/video-upload.component.ts b/client/src/app/videos/+video-edit/video-add-components/video-upload.component.ts
index fa6ee0c23..8e2d0deaf 100644
--- a/client/src/app/videos/+video-edit/video-add-components/video-upload.component.ts
+++ b/client/src/app/videos/+video-edit/video-add-components/video-upload.component.ts
@@ -1,5 +1,5 @@
1import { HttpEventType, HttpResponse } from '@angular/common/http' 1import { HttpEventType, HttpResponse } from '@angular/common/http'
2import { Component, EventEmitter, OnDestroy, OnInit, Output, ViewChild } from '@angular/core' 2import { Component, ElementRef, EventEmitter, OnDestroy, OnInit, Output, ViewChild } from '@angular/core'
3import { Router } from '@angular/router' 3import { Router } from '@angular/router'
4import { LoadingBarService } from '@ngx-loading-bar/core' 4import { LoadingBarService } from '@ngx-loading-bar/core'
5import { NotificationsService } from 'angular2-notifications' 5import { NotificationsService } from 'angular2-notifications'
@@ -25,7 +25,7 @@ import { VideoCaptionService } from '@app/shared/video-caption'
25}) 25})
26export class VideoUploadComponent extends VideoSend implements OnInit, OnDestroy, CanComponentDeactivate { 26export class VideoUploadComponent extends VideoSend implements OnInit, OnDestroy, CanComponentDeactivate {
27 @Output() firstStepDone = new EventEmitter<string>() 27 @Output() firstStepDone = new EventEmitter<string>()
28 @ViewChild('videofileInput') videofileInput: any 28 @ViewChild('videofileInput') videofileInput: ElementRef<HTMLInputElement>
29 29
30 // So that it can be accessed in the template 30 // So that it can be accessed in the template
31 readonly SPECIAL_SCHEDULED_PRIVACY = VideoEdit.SPECIAL_SCHEDULED_PRIVACY 31 readonly SPECIAL_SCHEDULED_PRIVACY = VideoEdit.SPECIAL_SCHEDULED_PRIVACY
@@ -110,7 +110,7 @@ export class VideoUploadComponent extends VideoSend implements OnInit, OnDestroy
110 } 110 }
111 111
112 uploadFirstStep () { 112 uploadFirstStep () {
113 const videofile = this.videofileInput.nativeElement.files[0] as File 113 const videofile = this.videofileInput.nativeElement.files[0]
114 if (!videofile) return 114 if (!videofile) return
115 115
116 // Cannot upload videos > 8GB for now 116 // Cannot upload videos > 8GB for now
diff --git a/client/src/app/videos/+video-watch/comment/linkifier.service.ts b/client/src/app/videos/+video-watch/comment/linkifier.service.ts
index 9ad419a69..4f4ec1e5d 100644
--- a/client/src/app/videos/+video-watch/comment/linkifier.service.ts
+++ b/client/src/app/videos/+video-watch/comment/linkifier.service.ts
@@ -1,5 +1,6 @@
1import { Injectable } from '@angular/core' 1import { Injectable } from '@angular/core'
2import { getAbsoluteAPIUrl } from '@app/shared/misc/utils' 2import { getAbsoluteAPIUrl } from '@app/shared/misc/utils'
3// FIXME: use @types/linkify when https://github.com/DefinitelyTyped/DefinitelyTyped/pull/29682/files is merged?
3const linkify = require('linkifyjs') 4const linkify = require('linkifyjs')
4const linkifyHtml = require('linkifyjs/html') 5const linkifyHtml = require('linkifyjs/html')
5 6
diff --git a/client/src/app/videos/+video-watch/comment/video-comment.component.ts b/client/src/app/videos/+video-watch/comment/video-comment.component.ts
index 982470786..00f0460a1 100644
--- a/client/src/app/videos/+video-watch/comment/video-comment.component.ts
+++ b/client/src/app/videos/+video-watch/comment/video-comment.component.ts
@@ -26,7 +26,7 @@ export class VideoCommentComponent implements OnInit, OnChanges {
26 @Output() resetReply = new EventEmitter() 26 @Output() resetReply = new EventEmitter()
27 27
28 sanitizedCommentHTML = '' 28 sanitizedCommentHTML = ''
29 newParentComments: any = [] 29 newParentComments: VideoComment[] = []
30 30
31 constructor ( 31 constructor (
32 private linkifierService: LinkifierService, 32 private linkifierService: LinkifierService,
diff --git a/client/src/app/videos/+video-watch/comment/video-comment.service.ts b/client/src/app/videos/+video-watch/comment/video-comment.service.ts
index 7d9c2d0ad..921447d5b 100644
--- a/client/src/app/videos/+video-watch/comment/video-comment.service.ts
+++ b/client/src/app/videos/+video-watch/comment/video-comment.service.ts
@@ -30,9 +30,9 @@ export class VideoCommentService {
30 const url = VideoCommentService.BASE_VIDEO_URL + videoId + '/comment-threads' 30 const url = VideoCommentService.BASE_VIDEO_URL + videoId + '/comment-threads'
31 const normalizedComment = lineFeedToHtml(comment, 'text') 31 const normalizedComment = lineFeedToHtml(comment, 'text')
32 32
33 return this.authHttp.post(url, normalizedComment) 33 return this.authHttp.post<{ comment: VideoCommentServerModel }>(url, normalizedComment)
34 .pipe( 34 .pipe(
35 map((data: any) => this.extractVideoComment(data['comment'])), 35 map(data => this.extractVideoComment(data.comment)),
36 catchError(err => this.restExtractor.handleError(err)) 36 catchError(err => this.restExtractor.handleError(err))
37 ) 37 )
38 } 38 }
@@ -41,9 +41,9 @@ export class VideoCommentService {
41 const url = VideoCommentService.BASE_VIDEO_URL + videoId + '/comments/' + inReplyToCommentId 41 const url = VideoCommentService.BASE_VIDEO_URL + videoId + '/comments/' + inReplyToCommentId
42 const normalizedComment = lineFeedToHtml(comment, 'text') 42 const normalizedComment = lineFeedToHtml(comment, 'text')
43 43
44 return this.authHttp.post(url, normalizedComment) 44 return this.authHttp.post<{ comment: VideoCommentServerModel }>(url, normalizedComment)
45 .pipe( 45 .pipe(
46 map((data: any) => this.extractVideoComment(data[ 'comment' ])), 46 map(data => this.extractVideoComment(data.comment)),
47 catchError(err => this.restExtractor.handleError(err)) 47 catchError(err => this.restExtractor.handleError(err))
48 ) 48 )
49 } 49 }
diff --git a/client/src/app/videos/+video-watch/comment/video-comments.component.html b/client/src/app/videos/+video-watch/comment/video-comments.component.html
index 42e129d65..44016d8ad 100644
--- a/client/src/app/videos/+video-watch/comment/video-comments.component.html
+++ b/client/src/app/videos/+video-watch/comment/video-comments.component.html
@@ -4,7 +4,7 @@
4 Comments 4 Comments
5 </div> 5 </div>
6 6
7 <my-video-feed [syndicationItems]="syndicationItems"></my-video-feed> 7 <my-feed [syndicationItems]="syndicationItems"></my-feed>
8 </div> 8 </div>
9 9
10 <ng-template [ngIf]="video.commentsEnabled === true"> 10 <ng-template [ngIf]="video.commentsEnabled === true">
diff --git a/client/src/app/videos/+video-watch/comment/video-comments.component.scss b/client/src/app/videos/+video-watch/comment/video-comments.component.scss
index dbb44c66c..575e331e4 100644
--- a/client/src/app/videos/+video-watch/comment/video-comments.component.scss
+++ b/client/src/app/videos/+video-watch/comment/video-comments.component.scss
@@ -23,7 +23,7 @@
23 margin-right: 0; 23 margin-right: 0;
24} 24}
25 25
26my-video-feed { 26my-feed {
27 display: inline-block; 27 display: inline-block;
28 margin-left: 5px; 28 margin-left: 5px;
29} 29}
diff --git a/client/src/app/videos/+video-watch/comment/video-comments.component.ts b/client/src/app/videos/+video-watch/comment/video-comments.component.ts
index 4c1bdf2dd..8850eccd8 100644
--- a/client/src/app/videos/+video-watch/comment/video-comments.component.ts
+++ b/client/src/app/videos/+video-watch/comment/video-comments.component.ts
@@ -12,6 +12,7 @@ import { VideoDetails } from '../../../shared/video/video-details.model'
12import { VideoComment } from './video-comment.model' 12import { VideoComment } from './video-comment.model'
13import { VideoCommentService } from './video-comment.service' 13import { VideoCommentService } from './video-comment.service'
14import { I18n } from '@ngx-translate/i18n-polyfill' 14import { I18n } from '@ngx-translate/i18n-polyfill'
15import { Syndication } from '@app/shared/video/syndication.model'
15 16
16@Component({ 17@Component({
17 selector: 'my-video-comments', 18 selector: 'my-video-comments',
@@ -35,7 +36,7 @@ export class VideoCommentsComponent implements OnInit, OnChanges, OnDestroy {
35 threadComments: { [ id: number ]: VideoCommentThreadTree } = {} 36 threadComments: { [ id: number ]: VideoCommentThreadTree } = {}
36 threadLoading: { [ id: number ]: boolean } = {} 37 threadLoading: { [ id: number ]: boolean } = {}
37 38
38 syndicationItems: any = [] 39 syndicationItems: Syndication[] = []
39 40
40 private sub: Subscription 41 private sub: Subscription
41 42
diff --git a/client/src/app/videos/+video-watch/video-watch.component.scss b/client/src/app/videos/+video-watch/video-watch.component.scss
index f31e4694a..2586a2204 100644
--- a/client/src/app/videos/+video-watch/video-watch.component.scss
+++ b/client/src/app/videos/+video-watch/video-watch.component.scss
@@ -162,7 +162,7 @@ $other-videos-width: 260px;
162 } 162 }
163 } 163 }
164 164
165 my-video-feed { 165 my-feed {
166 margin-left: 5px; 166 margin-left: 5px;
167 margin-top: 1px; 167 margin-top: 1px;
168 } 168 }
diff --git a/client/src/app/videos/+video-watch/video-watch.component.ts b/client/src/app/videos/+video-watch/video-watch.component.ts
index ed5e723c9..65b974037 100644
--- a/client/src/app/videos/+video-watch/video-watch.component.ts
+++ b/client/src/app/videos/+video-watch/video-watch.component.ts
@@ -7,7 +7,9 @@ import { VideoSupportComponent } from '@app/videos/+video-watch/modal/video-supp
7import { MetaService } from '@ngx-meta/core' 7import { MetaService } from '@ngx-meta/core'
8import { NotificationsService } from 'angular2-notifications' 8import { NotificationsService } from 'angular2-notifications'
9import { forkJoin, Subscription } from 'rxjs' 9import { forkJoin, Subscription } from 'rxjs'
10const videojs = require('video.js') 10// FIXME: something weird with our path definition in tsconfig and typings
11// @ts-ignore
12import videojs from 'video.js'
11import 'videojs-hotkeys' 13import 'videojs-hotkeys'
12import { Hotkey, HotkeysService } from 'angular2-hotkeys' 14import { Hotkey, HotkeysService } from 'angular2-hotkeys'
13import * as WebTorrent from 'webtorrent' 15import * as WebTorrent from 'webtorrent'
@@ -45,7 +47,7 @@ export class VideoWatchComponent implements OnInit, OnDestroy {
45 @ViewChild('videoBlacklistModal') videoBlacklistModal: VideoBlacklistComponent 47 @ViewChild('videoBlacklistModal') videoBlacklistModal: VideoBlacklistComponent
46 @ViewChild('subscribeButton') subscribeButton: SubscribeButtonComponent 48 @ViewChild('subscribeButton') subscribeButton: SubscribeButtonComponent
47 49
48 player: any 50 player: videojs.Player
49 playerElement: HTMLVideoElement 51 playerElement: HTMLVideoElement
50 userRating: UserVideoRateType = null 52 userRating: UserVideoRateType = null
51 video: VideoDetails = null 53 video: VideoDetails = null
@@ -435,7 +437,7 @@ export class VideoWatchComponent implements OnInit, OnDestroy {
435 this.zone.runOutsideAngular(async () => { 437 this.zone.runOutsideAngular(async () => {
436 videojs(this.playerElement, videojsOptions, function () { 438 videojs(this.playerElement, videojsOptions, function () {
437 self.player = this 439 self.player = this
438 this.on('customError', (data: any) => self.handleError(data.err)) 440 this.on('customError', ({ err }: { err: any }) => self.handleError(err))
439 441
440 addContextMenu(self.player, self.video.embedUrl) 442 addContextMenu(self.player, self.video.embedUrl)
441 }) 443 })
@@ -448,7 +450,7 @@ export class VideoWatchComponent implements OnInit, OnDestroy {
448 this.checkUserRating() 450 this.checkUserRating()
449 } 451 }
450 452
451 private setRating (nextRating: string) { 453 private setRating (nextRating: VideoRateType) {
452 let method 454 let method
453 switch (nextRating) { 455 switch (nextRating) {
454 case 'like': 456 case 'like':
@@ -466,11 +468,11 @@ export class VideoWatchComponent implements OnInit, OnDestroy {
466 .subscribe( 468 .subscribe(
467 () => { 469 () => {
468 // Update the video like attribute 470 // Update the video like attribute
469 this.updateVideoRating(this.userRating, nextRating as VideoRateType) 471 this.updateVideoRating(this.userRating, nextRating)
470 this.userRating = nextRating as UserVideoRateType 472 this.userRating = nextRating
471 }, 473 },
472 474
473 (err: any) => this.notificationsService.error(this.i18n('Error'), err.message) 475 (err: { message: string }) => this.notificationsService.error(this.i18n('Error'), err.message)
474 ) 476 )
475 } 477 }
476 478
diff --git a/client/src/assets/player/peertube-chunk-store.ts b/client/src/assets/player/peertube-chunk-store.ts
index ac3f9e654..54cc0ea64 100644
--- a/client/src/assets/player/peertube-chunk-store.ts
+++ b/client/src/assets/player/peertube-chunk-store.ts
@@ -76,7 +76,7 @@ export class PeertubeChunkStore extends EventEmitter {
76 this.runCleaner() 76 this.runCleaner()
77 } 77 }
78 78
79 put (index: number, buf: Buffer, cb: Function) { 79 put (index: number, buf: Buffer, cb: (err?: Error) => void) {
80 const isLastChunk = (index === this.lastChunkIndex) 80 const isLastChunk = (index === this.lastChunkIndex)
81 if (isLastChunk && buf.length !== this.lastChunkLength) { 81 if (isLastChunk && buf.length !== this.lastChunkLength) {
82 return this.nextTick(cb, new Error('Last chunk length must be ' + this.lastChunkLength)) 82 return this.nextTick(cb, new Error('Last chunk length must be ' + this.lastChunkLength))
@@ -113,7 +113,7 @@ export class PeertubeChunkStore extends EventEmitter {
113 }, PeertubeChunkStore.BUFFERING_PUT_MS) 113 }, PeertubeChunkStore.BUFFERING_PUT_MS)
114 } 114 }
115 115
116 get (index: number, opts: any, cb: any): any { 116 get (index: number, opts: any, cb: (err?: Error, buf?: Buffer) => void): void {
117 if (typeof opts === 'function') return this.get(index, null, opts) 117 if (typeof opts === 'function') return this.get(index, null, opts)
118 118
119 // IndexDB could be slow, use our memory index first 119 // IndexDB could be slow, use our memory index first
@@ -146,11 +146,11 @@ export class PeertubeChunkStore extends EventEmitter {
146 }) 146 })
147 } 147 }
148 148
149 close (db: any) { 149 close (cb: (err?: Error) => void) {
150 return this.destroy(db) 150 return this.destroy(cb)
151 } 151 }
152 152
153 async destroy (cb: any) { 153 async destroy (cb: (err?: Error) => void) {
154 try { 154 try {
155 if (this.pendingPut) { 155 if (this.pendingPut) {
156 clearTimeout(this.putBulkTimeout) 156 clearTimeout(this.putBulkTimeout)
@@ -225,7 +225,7 @@ export class PeertubeChunkStore extends EventEmitter {
225 } 225 }
226 } 226 }
227 227
228 private nextTick (cb: any, err: Error, val?: any) { 228 private nextTick <T> (cb: (err?: Error, val?: T) => void, err: Error, val?: T) {
229 process.nextTick(() => cb(err, val), undefined) 229 process.nextTick(() => cb(err, val), undefined)
230 } 230 }
231} 231}
diff --git a/client/src/assets/player/peertube-link-button.ts b/client/src/assets/player/peertube-link-button.ts
index b03952b47..de9a49de9 100644
--- a/client/src/assets/player/peertube-link-button.ts
+++ b/client/src/assets/player/peertube-link-button.ts
@@ -1,10 +1,13 @@
1import { VideoJSComponentInterface, videojsUntyped } from './peertube-videojs-typings' 1import { VideoJSComponentInterface, videojsUntyped } from './peertube-videojs-typings'
2import { buildVideoLink } from './utils' 2import { buildVideoLink } from './utils'
3// FIXME: something weird with our path definition in tsconfig and typings
4// @ts-ignore
5import { Player } from 'video.js'
3 6
4const Button: VideoJSComponentInterface = videojsUntyped.getComponent('Button') 7const Button: VideoJSComponentInterface = videojsUntyped.getComponent('Button')
5class PeerTubeLinkButton extends Button { 8class PeerTubeLinkButton extends Button {
6 9
7 constructor (player: any, options: any) { 10 constructor (player: Player, options: any) {
8 super(player, options) 11 super(player, options)
9 } 12 }
10 13
diff --git a/client/src/assets/player/peertube-load-progress-bar.ts b/client/src/assets/player/peertube-load-progress-bar.ts
index ee8a6cd81..af276d1b2 100644
--- a/client/src/assets/player/peertube-load-progress-bar.ts
+++ b/client/src/assets/player/peertube-load-progress-bar.ts
@@ -1,10 +1,13 @@
1import { VideoJSComponentInterface, videojsUntyped } from './peertube-videojs-typings' 1import { VideoJSComponentInterface, videojsUntyped } from './peertube-videojs-typings'
2// FIXME: something weird with our path definition in tsconfig and typings
3// @ts-ignore
4import { Player } from 'video.js'
2 5
3const Component: VideoJSComponentInterface = videojsUntyped.getComponent('Component') 6const Component: VideoJSComponentInterface = videojsUntyped.getComponent('Component')
4 7
5class PeerTubeLoadProgressBar extends Component { 8class PeerTubeLoadProgressBar extends Component {
6 9
7 constructor (player: any, options: any) { 10 constructor (player: Player, options: any) {
8 super(player, options) 11 super(player, options)
9 this.partEls_ = [] 12 this.partEls_ = []
10 this.on(player, 'progress', this.update) 13 this.on(player, 'progress', this.update)
diff --git a/client/src/assets/player/peertube-player.ts b/client/src/assets/player/peertube-player.ts
index ef9e7fcc0..db63071cb 100644
--- a/client/src/assets/player/peertube-player.ts
+++ b/client/src/assets/player/peertube-player.ts
@@ -14,6 +14,10 @@ import { UserWatching, VideoJSCaption, videojsUntyped } from './peertube-videojs
14import { buildVideoEmbed, buildVideoLink, copyToClipboard } from './utils' 14import { buildVideoEmbed, buildVideoLink, copyToClipboard } from './utils'
15import { getCompleteLocale, getShortLocale, is18nLocale, isDefaultLocale } from '../../../../shared/models/i18n/i18n' 15import { getCompleteLocale, getShortLocale, is18nLocale, isDefaultLocale } from '../../../../shared/models/i18n/i18n'
16 16
17// FIXME: something weird with our path definition in tsconfig and typings
18// @ts-ignore
19import { Player } from 'video.js'
20
17// Change 'Playback Rate' to 'Speed' (smaller for our settings menu) 21// Change 'Playback Rate' to 'Speed' (smaller for our settings menu)
18videojsUntyped.getComponent('PlaybackRateMenuButton').prototype.controlText_ = 'Speed' 22videojsUntyped.getComponent('PlaybackRateMenuButton').prototype.controlText_ = 'Speed'
19// Change Captions to Subtitles/CC 23// Change Captions to Subtitles/CC
@@ -75,12 +79,12 @@ function getVideojsOptions (options: {
75 enableVolumeScroll: false, 79 enableVolumeScroll: false,
76 enableModifiersForNumbers: false, 80 enableModifiersForNumbers: false,
77 81
78 fullscreenKey: function (event: any) { 82 fullscreenKey: function (event: KeyboardEvent) {
79 // fullscreen with the f key or Ctrl+Enter 83 // fullscreen with the f key or Ctrl+Enter
80 return event.key === 'f' || (event.ctrlKey && event.key === 'Enter') 84 return event.key === 'f' || (event.ctrlKey && event.key === 'Enter')
81 }, 85 },
82 86
83 seekStep: function (event: any) { 87 seekStep: function (event: KeyboardEvent) {
84 // mimic VLC seek behavior, and default to 5 (original value is 5). 88 // mimic VLC seek behavior, and default to 5 (original value is 5).
85 if (event.ctrlKey && event.altKey) { 89 if (event.ctrlKey && event.altKey) {
86 return 5 * 60 90 return 5 * 60
@@ -95,26 +99,26 @@ function getVideojsOptions (options: {
95 99
96 customKeys: { 100 customKeys: {
97 increasePlaybackRateKey: { 101 increasePlaybackRateKey: {
98 key: function (event: any) { 102 key: function (event: KeyboardEvent) {
99 return event.key === '>' 103 return event.key === '>'
100 }, 104 },
101 handler: function (player: any) { 105 handler: function (player: Player) {
102 player.playbackRate((player.playbackRate() + 0.1).toFixed(2)) 106 player.playbackRate((player.playbackRate() + 0.1).toFixed(2))
103 } 107 }
104 }, 108 },
105 decreasePlaybackRateKey: { 109 decreasePlaybackRateKey: {
106 key: function (event: any) { 110 key: function (event: KeyboardEvent) {
107 return event.key === '<' 111 return event.key === '<'
108 }, 112 },
109 handler: function (player: any) { 113 handler: function (player: Player) {
110 player.playbackRate((player.playbackRate() - 0.1).toFixed(2)) 114 player.playbackRate((player.playbackRate() - 0.1).toFixed(2))
111 } 115 }
112 }, 116 },
113 frameByFrame: { 117 frameByFrame: {
114 key: function (event: any) { 118 key: function (event: KeyboardEvent) {
115 return event.key === '.' 119 return event.key === '.'
116 }, 120 },
117 handler: function (player: any) { 121 handler: function (player: Player) {
118 player.pause() 122 player.pause()
119 // Calculate movement distance (assuming 30 fps) 123 // Calculate movement distance (assuming 30 fps)
120 const dist = 1 / 30 124 const dist = 1 / 30
diff --git a/client/src/assets/player/peertube-videojs-plugin.ts b/client/src/assets/player/peertube-videojs-plugin.ts
index 03def186e..40da5f1f7 100644
--- a/client/src/assets/player/peertube-videojs-plugin.ts
+++ b/client/src/assets/player/peertube-videojs-plugin.ts
@@ -1,11 +1,13 @@
1const videojs = require('video.js') 1// FIXME: something weird with our path definition in tsconfig and typings
2// @ts-ignore
3import * as videojs from 'video.js'
4
2import * as WebTorrent from 'webtorrent' 5import * as WebTorrent from 'webtorrent'
3import { VideoFile } from '../../../../shared/models/videos/video.model' 6import { VideoFile } from '../../../../shared/models/videos/video.model'
4import { renderVideo } from './video-renderer' 7import { renderVideo } from './video-renderer'
5import './settings-menu-button' 8import './settings-menu-button'
6import { PeertubePluginOptions, UserWatching, VideoJSCaption, VideoJSComponentInterface, videojsUntyped } from './peertube-videojs-typings' 9import { PeertubePluginOptions, UserWatching, VideoJSCaption, VideoJSComponentInterface, videojsUntyped } from './peertube-videojs-typings'
7import { isMobile, timeToInt, videoFileMaxByResolution, videoFileMinByResolution } from './utils' 10import { isMobile, timeToInt, videoFileMaxByResolution, videoFileMinByResolution } from './utils'
8const CacheChunkStore = require('cache-chunk-store')
9import { PeertubeChunkStore } from './peertube-chunk-store' 11import { PeertubeChunkStore } from './peertube-chunk-store'
10import { 12import {
11 getAverageBandwidthInStore, 13 getAverageBandwidthInStore,
@@ -17,6 +19,8 @@ import {
17 saveVolumeInStore 19 saveVolumeInStore
18} from './peertube-player-local-storage' 20} from './peertube-player-local-storage'
19 21
22const CacheChunkStore = require('cache-chunk-store')
23
20type PlayOptions = { 24type PlayOptions = {
21 forcePlay?: boolean, 25 forcePlay?: boolean,
22 seek?: number, 26 seek?: number,
@@ -61,7 +65,7 @@ class PeerTubePlugin extends Plugin {
61 65
62 private player: any 66 private player: any
63 private currentVideoFile: VideoFile 67 private currentVideoFile: VideoFile
64 private torrent: any 68 private torrent: WebTorrent.Torrent
65 private videoCaptions: VideoJSCaption[] 69 private videoCaptions: VideoJSCaption[]
66 70
67 private renderer: any 71 private renderer: any
@@ -83,7 +87,7 @@ class PeerTubePlugin extends Plugin {
83 87
84 private downloadSpeeds: number[] = [] 88 private downloadSpeeds: number[] = []
85 89
86 constructor (player: any, options: PeertubePluginOptions) { 90 constructor (player: videojs.Player, options: PeertubePluginOptions) {
87 super(player, options) 91 super(player, options)
88 92
89 // Disable auto play on iOS 93 // Disable auto play on iOS
@@ -273,7 +277,7 @@ class PeerTubePlugin extends Plugin {
273 277
274 const oldTorrent = this.torrent 278 const oldTorrent = this.torrent
275 const torrentOptions = { 279 const torrentOptions = {
276 store: (chunkLength: any, storeOpts: any) => new CacheChunkStore(new PeertubeChunkStore(chunkLength, storeOpts), { 280 store: (chunkLength: number, storeOpts: any) => new CacheChunkStore(new PeertubeChunkStore(chunkLength, storeOpts), {
277 max: 100 281 max: 100
278 }) 282 })
279 } 283 }
@@ -304,7 +308,7 @@ class PeerTubePlugin extends Plugin {
304 308
305 if (err) return this.fallbackToHttp(options, done) 309 if (err) return this.fallbackToHttp(options, done)
306 310
307 return this.tryToPlay((err: Error) => { 311 return this.tryToPlay(err => {
308 if (err) return done(err) 312 if (err) return done(err)
309 313
310 if (options.seek) this.seek(options.seek) 314 if (options.seek) this.seek(options.seek)
@@ -344,7 +348,7 @@ class PeerTubePlugin extends Plugin {
344 }) 348 })
345 } 349 }
346 350
347 private tryToPlay (done?: Function) { 351 private tryToPlay (done?: (err?: Error) => void) {
348 if (!done) done = function () { /* empty */ } 352 if (!done) done = function () { /* empty */ }
349 353
350 const playPromise = this.player.play() 354 const playPromise = this.player.play()
@@ -641,7 +645,7 @@ class PeerTubePlugin extends Plugin {
641 return this.videoFiles[Math.floor(this.videoFiles.length / 2)] 645 return this.videoFiles[Math.floor(this.videoFiles.length / 2)]
642 } 646 }
643 647
644 private stopTorrent (torrent: any) { 648 private stopTorrent (torrent: WebTorrent.Torrent) {
645 torrent.pause() 649 torrent.pause()
646 // Pause does not remove actual peers (in particular the webseed peer) 650 // Pause does not remove actual peers (in particular the webseed peer)
647 torrent.removePeer(torrent[ 'ws' ]) 651 torrent.removePeer(torrent[ 'ws' ])
diff --git a/client/src/assets/player/peertube-videojs-typings.ts b/client/src/assets/player/peertube-videojs-typings.ts
index 98a33077d..d127230fa 100644
--- a/client/src/assets/player/peertube-videojs-typings.ts
+++ b/client/src/assets/player/peertube-videojs-typings.ts
@@ -1,4 +1,7 @@
1const videojs = require('video.js') 1// FIXME: something weird with our path definition in tsconfig and typings
2// @ts-ignore
3import * as videojs from 'video.js'
4
2import { VideoFile } from '../../../../shared/models/videos/video.model' 5import { VideoFile } from '../../../../shared/models/videos/video.model'
3import { PeerTubePlugin } from './peertube-videojs-plugin' 6import { PeerTubePlugin } from './peertube-videojs-plugin'
4 7
diff --git a/client/src/assets/player/resolution-menu-button.ts b/client/src/assets/player/resolution-menu-button.ts
index 91818efc9..a3c1108ca 100644
--- a/client/src/assets/player/resolution-menu-button.ts
+++ b/client/src/assets/player/resolution-menu-button.ts
@@ -1,3 +1,7 @@
1// FIXME: something weird with our path definition in tsconfig and typings
2// @ts-ignore
3import { Player } from 'video.js'
4
1import { VideoJSComponentInterface, videojsUntyped } from './peertube-videojs-typings' 5import { VideoJSComponentInterface, videojsUntyped } from './peertube-videojs-typings'
2import { ResolutionMenuItem } from './resolution-menu-item' 6import { ResolutionMenuItem } from './resolution-menu-item'
3 7
@@ -6,7 +10,7 @@ const MenuButton: VideoJSComponentInterface = videojsUntyped.getComponent('MenuB
6class ResolutionMenuButton extends MenuButton { 10class ResolutionMenuButton extends MenuButton {
7 label: HTMLElement 11 label: HTMLElement
8 12
9 constructor (player: any, options: any) { 13 constructor (player: Player, options: any) {
10 super(player, options) 14 super(player, options)
11 this.player = player 15 this.player = player
12 16
diff --git a/client/src/assets/player/resolution-menu-item.ts b/client/src/assets/player/resolution-menu-item.ts
index afe490abb..b54fd91ef 100644
--- a/client/src/assets/player/resolution-menu-item.ts
+++ b/client/src/assets/player/resolution-menu-item.ts
@@ -1,9 +1,13 @@
1// FIXME: something weird with our path definition in tsconfig and typings
2// @ts-ignore
3import { Player } from 'video.js'
4
1import { VideoJSComponentInterface, videojsUntyped } from './peertube-videojs-typings' 5import { VideoJSComponentInterface, videojsUntyped } from './peertube-videojs-typings'
2 6
3const MenuItem: VideoJSComponentInterface = videojsUntyped.getComponent('MenuItem') 7const MenuItem: VideoJSComponentInterface = videojsUntyped.getComponent('MenuItem')
4class ResolutionMenuItem extends MenuItem { 8class ResolutionMenuItem extends MenuItem {
5 9
6 constructor (player: any, options: any) { 10 constructor (player: Player, options: any) {
7 const currentResolutionId = player.peertube().getCurrentResolutionId() 11 const currentResolutionId = player.peertube().getCurrentResolutionId()
8 options.selectable = true 12 options.selectable = true
9 options.selected = options.id === currentResolutionId 13 options.selected = options.id === currentResolutionId
diff --git a/client/src/assets/player/settings-menu-button.ts b/client/src/assets/player/settings-menu-button.ts
index f0ccb5862..aa7281727 100644
--- a/client/src/assets/player/settings-menu-button.ts
+++ b/client/src/assets/player/settings-menu-button.ts
@@ -1,7 +1,10 @@
1// Author: Yanko Shterev 1// Author: Yanko Shterev
2// Thanks https://github.com/yshterev/videojs-settings-menu 2// Thanks https://github.com/yshterev/videojs-settings-menu
3 3
4const videojs = require('video.js') 4// FIXME: something weird with our path definition in tsconfig and typings
5// @ts-ignore
6import * as videojs from 'video.js'
7
5import { SettingsMenuItem } from './settings-menu-item' 8import { SettingsMenuItem } from './settings-menu-item'
6import { VideoJSComponentInterface, videojsUntyped } from './peertube-videojs-typings' 9import { VideoJSComponentInterface, videojsUntyped } from './peertube-videojs-typings'
7import { toTitleCase } from './utils' 10import { toTitleCase } from './utils'
@@ -11,7 +14,7 @@ const Menu: VideoJSComponentInterface = videojsUntyped.getComponent('Menu')
11const Component: VideoJSComponentInterface = videojsUntyped.getComponent('Component') 14const Component: VideoJSComponentInterface = videojsUntyped.getComponent('Component')
12 15
13class SettingsButton extends Button { 16class SettingsButton extends Button {
14 constructor (player: any, options: any) { 17 constructor (player: videojs.Player, options: any) {
15 super(player, options) 18 super(player, options)
16 19
17 this.playerComponent = player 20 this.playerComponent = player
@@ -48,7 +51,7 @@ class SettingsButton extends Button {
48 } 51 }
49 } 52 }
50 53
51 onDisposeSettingsItem (name: string) { 54 onDisposeSettingsItem (event: any, name: string) {
52 if (name === undefined) { 55 if (name === undefined) {
53 let children = this.menu.children() 56 let children = this.menu.children()
54 57
@@ -74,7 +77,7 @@ class SettingsButton extends Button {
74 } 77 }
75 } 78 }
76 79
77 onAddSettingsItem (data: any) { 80 onAddSettingsItem (event: any, data: any) {
78 const [ entry, options ] = data 81 const [ entry, options ] = data
79 82
80 this.addMenuItem(entry, options) 83 this.addMenuItem(entry, options)
@@ -218,7 +221,7 @@ class SettingsButton extends Button {
218} 221}
219 222
220class SettingsPanel extends Component { 223class SettingsPanel extends Component {
221 constructor (player: any, options: any) { 224 constructor (player: videojs.Player, options: any) {
222 super(player, options) 225 super(player, options)
223 } 226 }
224 227
@@ -232,7 +235,7 @@ class SettingsPanel extends Component {
232} 235}
233 236
234class SettingsPanelChild extends Component { 237class SettingsPanelChild extends Component {
235 constructor (player: any, options: any) { 238 constructor (player: videojs.Player, options: any) {
236 super(player, options) 239 super(player, options)
237 } 240 }
238 241
@@ -246,7 +249,7 @@ class SettingsPanelChild extends Component {
246} 249}
247 250
248class SettingsDialog extends Component { 251class SettingsDialog extends Component {
249 constructor (player: any, options: any) { 252 constructor (player: videojs.Player, options: any) {
250 super(player, options) 253 super(player, options)
251 this.hide() 254 this.hide()
252 } 255 }
diff --git a/client/src/assets/player/settings-menu-item.ts b/client/src/assets/player/settings-menu-item.ts
index 2d752b62e..698f4627a 100644
--- a/client/src/assets/player/settings-menu-item.ts
+++ b/client/src/assets/player/settings-menu-item.ts
@@ -1,6 +1,10 @@
1// Author: Yanko Shterev 1// Author: Yanko Shterev
2// Thanks https://github.com/yshterev/videojs-settings-menu 2// Thanks https://github.com/yshterev/videojs-settings-menu
3 3
4// FIXME: something weird with our path definition in tsconfig and typings
5// @ts-ignore
6import * as videojs from 'video.js'
7
4import { toTitleCase } from './utils' 8import { toTitleCase } from './utils'
5import { VideoJSComponentInterface, videojsUntyped } from './peertube-videojs-typings' 9import { VideoJSComponentInterface, videojsUntyped } from './peertube-videojs-typings'
6 10
@@ -9,7 +13,7 @@ const component: VideoJSComponentInterface = videojsUntyped.getComponent('Compon
9 13
10class SettingsMenuItem extends MenuItem { 14class SettingsMenuItem extends MenuItem {
11 15
12 constructor (player: any, options: any, entry: string, menuButton: VideoJSComponentInterface) { 16 constructor (player: videojs.Player, options: any, entry: string, menuButton: VideoJSComponentInterface) {
13 super(player, options) 17 super(player, options)
14 18
15 this.settingsButton = menuButton 19 this.settingsButton = menuButton
@@ -229,7 +233,7 @@ class SettingsMenuItem extends MenuItem {
229 } 233 }
230 234
231 update (event?: any) { 235 update (event?: any) {
232 let target = null 236 let target: HTMLElement = null
233 let subMenu = this.subMenu.name() 237 let subMenu = this.subMenu.name()
234 238
235 if (event && event.type === 'tap') { 239 if (event && event.type === 'tap') {
diff --git a/client/src/assets/player/theater-button.ts b/client/src/assets/player/theater-button.ts
index b761f6030..4f8fede3d 100644
--- a/client/src/assets/player/theater-button.ts
+++ b/client/src/assets/player/theater-button.ts
@@ -1,3 +1,7 @@
1// FIXME: something weird with our path definition in tsconfig and typings
2// @ts-ignore
3import * as videojs from 'video.js'
4
1import { VideoJSComponentInterface, videojsUntyped } from './peertube-videojs-typings' 5import { VideoJSComponentInterface, videojsUntyped } from './peertube-videojs-typings'
2import { saveTheaterInStore, getStoredTheater } from './peertube-player-local-storage' 6import { saveTheaterInStore, getStoredTheater } from './peertube-player-local-storage'
3 7
@@ -6,7 +10,7 @@ class TheaterButton extends Button {
6 10
7 private static readonly THEATER_MODE_CLASS = 'vjs-theater-enabled' 11 private static readonly THEATER_MODE_CLASS = 'vjs-theater-enabled'
8 12
9 constructor (player: any, options: any) { 13 constructor (player: videojs.Player, options: any) {
10 super(player, options) 14 super(player, options)
11 15
12 const enabled = getStoredTheater() 16 const enabled = getStoredTheater()
diff --git a/client/src/assets/player/utils.ts b/client/src/assets/player/utils.ts
index 46081c0d2..c87287482 100644
--- a/client/src/assets/player/utils.ts
+++ b/client/src/assets/player/utils.ts
@@ -12,7 +12,7 @@ const dictionaryBytes: Array<{max: number, type: string}> = [
12 { max: 1073741824, type: 'MB' }, 12 { max: 1073741824, type: 'MB' },
13 { max: 1.0995116e12, type: 'GB' } 13 { max: 1.0995116e12, type: 'GB' }
14] 14]
15function bytes (value: any) { 15function bytes (value: number) {
16 const format = dictionaryBytes.find(d => value < d.max) || dictionaryBytes[dictionaryBytes.length - 1] 16 const format = dictionaryBytes.find(d => value < d.max) || dictionaryBytes[dictionaryBytes.length - 1]
17 const calc = Math.floor(value / (format.max / 1024)).toString() 17 const calc = Math.floor(value / (format.max / 1024)).toString()
18 18
diff --git a/client/src/assets/player/webtorrent-info-button.ts b/client/src/assets/player/webtorrent-info-button.ts
index 5b9d0a401..c3c1af951 100644
--- a/client/src/assets/player/webtorrent-info-button.ts
+++ b/client/src/assets/player/webtorrent-info-button.ts
@@ -65,7 +65,7 @@ class WebtorrentInfoButton extends Button {
65 subDivHttp.appendChild(subDivHttpText) 65 subDivHttp.appendChild(subDivHttpText)
66 div.appendChild(subDivHttp) 66 div.appendChild(subDivHttp)
67 67
68 this.player_.peertube().on('torrentInfo', (data: any) => { 68 this.player_.peertube().on('torrentInfo', (event: any, data: any) => {
69 // We are in HTTP fallback 69 // We are in HTTP fallback
70 if (!data) { 70 if (!data) {
71 subDivHttp.className = 'vjs-peertube-displayed' 71 subDivHttp.className = 'vjs-peertube-displayed'
diff --git a/client/src/standalone/videos/embed.ts b/client/src/standalone/videos/embed.ts
index e5a2d208a..7b269eeb9 100644
--- a/client/src/standalone/videos/embed.ts
+++ b/client/src/standalone/videos/embed.ts
@@ -17,7 +17,10 @@ import 'core-js/es6/set'
17// For google bot that uses Chrome 41 and does not understand fetch 17// For google bot that uses Chrome 41 and does not understand fetch
18import 'whatwg-fetch' 18import 'whatwg-fetch'
19 19
20const vjs = require('video.js') 20// FIXME: something weird with our path definition in tsconfig and typings
21// @ts-ignore
22import vjs from 'video.js'
23
21import * as Channel from 'jschannel' 24import * as Channel from 'jschannel'
22 25
23import { peertubeTranslate, ResultList, VideoDetails } from '../../../../shared' 26import { peertubeTranslate, ResultList, VideoDetails } from '../../../../shared'
@@ -304,7 +307,7 @@ class PeerTubeEmbed {
304 307
305 this.playerOptions = videojsOptions 308 this.playerOptions = videojsOptions
306 this.player = vjs(this.videoContainerId, videojsOptions, () => { 309 this.player = vjs(this.videoContainerId, videojsOptions, () => {
307 this.player.on('customError', (data: any) => this.handleError(data.err)) 310 this.player.on('customError', (event: any, data: any) => this.handleError(data.err))
308 311
309 window[ 'videojsPlayer' ] = this.player 312 window[ 'videojsPlayer' ] = this.player
310 313
diff --git a/client/src/standalone/videos/test-embed.ts b/client/src/standalone/videos/test-embed.ts
index b750c2ee6..30a298573 100644
--- a/client/src/standalone/videos/test-embed.ts
+++ b/client/src/standalone/videos/test-embed.ts
@@ -1,6 +1,6 @@
1import './test-embed.scss' 1import './test-embed.scss'
2import { PeerTubePlayer } from '../player/player' 2import { PeerTubePlayer } from '../player/player'
3import { PlayerEventType } from '../player/definitions' 3import { PeerTubeResolution, PlayerEventType } from '../player/definitions'
4 4
5window.addEventListener('load', async () => { 5window.addEventListener('load', async () => {
6 const urlParts = window.location.href.split('/') 6 const urlParts = window.location.href.split('/')
@@ -66,11 +66,11 @@ window.addEventListener('load', async () => {
66 updateRates() 66 updateRates()
67 }) 67 })
68 68
69 let updateResolutions = ((resolutions: any) => { 69 let updateResolutions = ((resolutions: PeerTubeResolution[]) => {
70 let resolutionListEl = document.querySelector('#resolution-list') 70 let resolutionListEl = document.querySelector('#resolution-list')
71 resolutionListEl.innerHTML = '' 71 resolutionListEl.innerHTML = ''
72 72
73 resolutions.forEach((resolution: any) => { 73 resolutions.forEach(resolution => {
74 if (resolution.active) { 74 if (resolution.active) {
75 let itemEl = document.createElement('strong') 75 let itemEl = document.createElement('strong')
76 itemEl.innerText = `${resolution.label} (active)` 76 itemEl.innerText = `${resolution.label} (active)`
diff --git a/client/src/typings.d.ts b/client/src/typings.d.ts
index 9615434ac..ef6c9f2f5 100644
--- a/client/src/typings.d.ts
+++ b/client/src/typings.d.ts
@@ -1,6 +1,6 @@
1/* SystemJS module definition */ 1/* SystemJS module definition */
2declare var module: NodeModule; 2declare var module: NodeModule
3
3interface NodeModule { 4interface NodeModule {
4 id: string; 5 id: string
5 [key: string]: any
6} 6}