diff options
author | Chocobozzz <me@florianbigard.com> | 2022-11-14 14:21:40 +0100 |
---|---|---|
committer | Chocobozzz <me@florianbigard.com> | 2022-11-14 14:21:40 +0100 |
commit | 2198bb5a1981177b04dd94b2b1b6a90c5d7a5c25 (patch) | |
tree | 668365a50351c573949e066c1be440683795e262 /client/src/app/shared/shared-video-miniature | |
parent | b1934b7e9cdece7c0c38e05b0f905dc2ccab9167 (diff) | |
download | PeerTube-2198bb5a1981177b04dd94b2b1b6a90c5d7a5c25.tar.gz PeerTube-2198bb5a1981177b04dd94b2b1b6a90c5d7a5c25.tar.zst PeerTube-2198bb5a1981177b04dd94b2b1b6a90c5d7a5c25.zip |
Prevent XSS with ng-select
When using ng-option
See https://github.com/ng-select/ng-select/issues/1363
Diffstat (limited to 'client/src/app/shared/shared-video-miniature')
-rw-r--r-- | client/src/app/shared/shared-video-miniature/video-filters-header.component.html | 1 | ||||
-rw-r--r-- | client/src/app/shared/shared-video-miniature/video-filters.model.ts | 26 |
2 files changed, 19 insertions, 8 deletions
diff --git a/client/src/app/shared/shared-video-miniature/video-filters-header.component.html b/client/src/app/shared/shared-video-miniature/video-filters-header.component.html index fe7a59bdb..9ddfd7dda 100644 --- a/client/src/app/shared/shared-video-miniature/video-filters-header.component.html +++ b/client/src/app/shared/shared-video-miniature/video-filters-header.component.html | |||
@@ -42,6 +42,7 @@ | |||
42 | formControlName="sort" | 42 | formControlName="sort" |
43 | [clearable]="false" | 43 | [clearable]="false" |
44 | [searchable]="false" | 44 | [searchable]="false" |
45 | [bindValue]="null" | ||
45 | > | 46 | > |
46 | <ng-option i18n value="-publishedAt">Sort by <strong>"Recently Added"</strong></ng-option> | 47 | <ng-option i18n value="-publishedAt">Sort by <strong>"Recently Added"</strong></ng-option> |
47 | <ng-option i18n value="-originallyPublishedAt">Sort by <strong>"Original Publication Date"</strong></ng-option> | 48 | <ng-option i18n value="-originallyPublishedAt">Sort by <strong>"Original Publication Date"</strong></ng-option> |
diff --git a/client/src/app/shared/shared-video-miniature/video-filters.model.ts b/client/src/app/shared/shared-video-miniature/video-filters.model.ts index 73a30ca08..4069ab4b5 100644 --- a/client/src/app/shared/shared-video-miniature/video-filters.model.ts +++ b/client/src/app/shared/shared-video-miniature/video-filters.model.ts | |||
@@ -1,7 +1,8 @@ | |||
1 | import { splitIntoArray, toBoolean } from '@app/helpers' | 1 | import { splitIntoArray, toBoolean } from '@app/helpers' |
2 | import { getAllPrivacies } from '@shared/core-utils' | 2 | import { getAllPrivacies } from '@shared/core-utils' |
3 | import { AttributesOnly } from '@shared/typescript-utils' | 3 | import { escapeHTML } from '@shared/core-utils/renderer' |
4 | import { BooleanBothQuery, NSFWPolicyType, VideoInclude, VideoPrivacy, VideoSortField } from '@shared/models' | 4 | import { BooleanBothQuery, NSFWPolicyType, VideoInclude, VideoPrivacy, VideoSortField } from '@shared/models' |
5 | import { AttributesOnly } from '@shared/typescript-utils' | ||
5 | 6 | ||
6 | type VideoFiltersKeys = { | 7 | type VideoFiltersKeys = { |
7 | [ id in keyof AttributesOnly<VideoFilters> ]: any | 8 | [ id in keyof AttributesOnly<VideoFilters> ]: any |
@@ -90,19 +91,28 @@ export class VideoFilters { | |||
90 | } | 91 | } |
91 | 92 | ||
92 | load (obj: Partial<AttributesOnly<VideoFilters>>) { | 93 | load (obj: Partial<AttributesOnly<VideoFilters>>) { |
93 | if (obj.sort !== undefined) this.sort = obj.sort | 94 | // FIXME: We may use <ng-option> that doesn't escape HTML so prefer to escape things |
95 | // https://github.com/ng-select/ng-select/issues/1363 | ||
96 | |||
97 | const escapeIfNeeded = (value: any) => { | ||
98 | if (typeof value === 'string') return escapeHTML(value) | ||
99 | |||
100 | return value | ||
101 | } | ||
102 | |||
103 | if (obj.sort !== undefined) this.sort = escapeIfNeeded(obj.sort) as VideoSortField | ||
94 | 104 | ||
95 | if (obj.nsfw !== undefined) this.nsfw = obj.nsfw | 105 | if (obj.nsfw !== undefined) this.nsfw = escapeIfNeeded(obj.nsfw) as BooleanBothQuery |
96 | 106 | ||
97 | if (obj.languageOneOf !== undefined) this.languageOneOf = splitIntoArray(obj.languageOneOf) | 107 | if (obj.languageOneOf !== undefined) this.languageOneOf = splitIntoArray(escapeIfNeeded(obj.languageOneOf)) |
98 | if (obj.categoryOneOf !== undefined) this.categoryOneOf = splitIntoArray(obj.categoryOneOf) | 108 | if (obj.categoryOneOf !== undefined) this.categoryOneOf = splitIntoArray(escapeIfNeeded(obj.categoryOneOf)) |
99 | 109 | ||
100 | if (obj.scope !== undefined) this.scope = obj.scope | 110 | if (obj.scope !== undefined) this.scope = escapeIfNeeded(obj.scope) as VideoFilterScope |
101 | if (obj.allVideos !== undefined) this.allVideos = toBoolean(obj.allVideos) | 111 | if (obj.allVideos !== undefined) this.allVideos = toBoolean(obj.allVideos) |
102 | 112 | ||
103 | if (obj.live !== undefined) this.live = obj.live | 113 | if (obj.live !== undefined) this.live = escapeIfNeeded(obj.live) as BooleanBothQuery |
104 | 114 | ||
105 | if (obj.search !== undefined) this.search = obj.search | 115 | if (obj.search !== undefined) this.search = escapeIfNeeded(obj.search) |
106 | 116 | ||
107 | this.buildActiveFilters() | 117 | this.buildActiveFilters() |
108 | } | 118 | } |