diff --git a/app/Resources/views/layout.html.twig b/app/Resources/views/layout.html.twig
index cb070f9f..6992b8a0 100755
--- a/app/Resources/views/layout.html.twig
+++ b/app/Resources/views/layout.html.twig
@@ -53,6 +53,7 @@
+
@@ -99,7 +100,6 @@
gtag('config', 'UA-131671930-1');
{% endif %}
-
diff --git a/src/AppBundle/Controller/BuilderController.php b/src/AppBundle/Controller/BuilderController.php
index 134da914..f8c07854 100755
--- a/src/AppBundle/Controller/BuilderController.php
+++ b/src/AppBundle/Controller/BuilderController.php
@@ -12,6 +12,7 @@
use AppBundle\Service\CardsData;
use AppBundle\Service\DeckManager;
use AppBundle\Service\Judge;
+use AppBundle\Service\TextProcessor;
use Doctrine\ORM\EntityManagerInterface;
use Psr\Log\LoggerInterface;
use Sensio\Bundle\FrameworkExtraBundle\Configuration\IsGranted;
@@ -630,11 +631,12 @@ public function octgnExportAction(Deck $deck)
* @param Request $request
* @param EntityManagerInterface $entityManager
* @param DeckManager $deckManager
+ * @param TextProcessor $textProcessor
* @return \Symfony\Component\HttpFoundation\RedirectResponse|Response
*
* @IsGranted("IS_AUTHENTICATED_REMEMBERED")
*/
- public function saveAction(Request $request, EntityManagerInterface $entityManager, DeckManager $deckManager)
+ public function saveAction(Request $request, EntityManagerInterface $entityManager, DeckManager $deckManager, TextProcessor $textProcessor)
{
/** @var User $user */
$user = $this->getUser();
@@ -674,7 +676,7 @@ public function saveAction(Request $request, EntityManagerInterface $entityManag
}
$name = filter_var($request->get('name'), FILTER_SANITIZE_STRING, FILTER_FLAG_NO_ENCODE_QUOTES);
$decklist_id = intval(filter_var($request->get('decklist_id'), FILTER_SANITIZE_NUMBER_INT));
- $description = filter_var(trim(($request->get('description'))), FILTER_SANITIZE_SPECIAL_CHARS);
+ $description = $textProcessor->purify(trim($request->get('description')));
$tags = explode(',', filter_var($request->get('tags'), FILTER_SANITIZE_STRING, FILTER_FLAG_NO_ENCODE_QUOTES));
$mwl_code = $request->get('format_casual') ? null : $request->get('mwl_code');
diff --git a/web/js/deck.v2.js b/web/js/deck.v2.js
index 1f217f31..b5aea833 100755
--- a/web/js/deck.v2.js
+++ b/web/js/deck.v2.js
@@ -462,7 +462,8 @@ $(function() {
var converter = new Markdown.Converter();
$('#description').on('keyup', function() {
$('#description-preview').html(
- converter.makeHtml(escapeHtml($('#description').val())));
+ DOMPurify.sanitize(converter.makeHtml($('#description').val()))
+ );
});
$('#description').textcomplete([{
diff --git a/web/js/decklist.v2.js b/web/js/decklist.v2.js
index 8b2c3e98..26f0d73d 100755
--- a/web/js/decklist.v2.js
+++ b/web/js/decklist.v2.js
@@ -110,7 +110,7 @@ function setup_comment_form() {
$('#comment-form-text').on(
'keyup',
function () {
- $('#comment-form-preview').html(converter.makeHtml(escapeHtml($('#comment-form-text').val())));
+ $('#comment-form-preview').html(DOMPurify.sanitize(converter.makeHtml($('#comment-form-text').val())));
}
);
@@ -385,10 +385,12 @@ function edit_form() {
var converter = new Markdown.Converter();
$('#publish-decklist-description-preview').html(
- converter.makeHtml(escapeHtml($('#publish-decklist-description').val())));
+ DOMPurify.sanitize(converter.makeHtml($('#publish-decklist-description').val()))
+ );
$('#publish-decklist-description').on('keyup', function() {
$('#publish-decklist-description-preview').html(
- converter.makeHtml(escapeHtml($('#publish-decklist-description').val())));
+ DOMPurify.sanitize(converter.makeHtml($('#publish-decklist-description').val()))
+ );
});
$('#publish-decklist-description').textcomplete([{
diff --git a/web/js/deckview.v2.js b/web/js/deckview.v2.js
index 5fbb4f3e..c5614355 100755
--- a/web/js/deckview.v2.js
+++ b/web/js/deckview.v2.js
@@ -57,7 +57,13 @@ $(function() {
});
var converter = new Markdown.Converter();
- $('#description').html(converter.makeHtml(SelectedDeck.description ? SelectedDeck.description : 'No description.'));
+ $('#description').html(
+ DOMPurify.sanitize(
+ converter.makeHtml(
+ SelectedDeck.description ? SelectedDeck.description : 'No description.'
+ )
+ )
+ );
$('.btn-actions').on({
click: do_action_deck
diff --git a/web/js/publish_deck_form.v2.js b/web/js/publish_deck_form.v2.js
index 43c5e6f3..b5cba9dd 100644
--- a/web/js/publish_deck_form.v2.js
+++ b/web/js/publish_deck_form.v2.js
@@ -1,10 +1,13 @@
function initialize_publish_deck_form_typeahead() {
var converter = new Markdown.Converter();
$('#publish-decklist-description-preview').html(
- converter.makeHtml($('#publish-decklist-description').val()));
+ DOMPurify.sanitize(converter.makeHtml($('#publish-decklist-description').val()))
+ );
+
$('#publish-decklist-description').on('keyup', function() {
$('#publish-decklist-description-preview').html(
- converter.makeHtml($('#publish-decklist-description').val()));
+ DOMPurify.sanitize(converter.makeHtml($('#publish-decklist-description').val()))
+ );
});
$('#publish-decklist-description').textcomplete([{
diff --git a/web/js/sanitize.js b/web/js/sanitize.js
deleted file mode 100644
index 5c4bcd13..00000000
--- a/web/js/sanitize.js
+++ /dev/null
@@ -1,11 +0,0 @@
-function escapeHtml(text) {
- let map = {
- '&': '&',
- '<': '<',
- '>': '>',
- '"': '"',
- "'": '''
- };
-
- return text.replace(/[&<>"']/g, function(m) { return map[m]; });
-}
diff --git a/web/js/zoom.js b/web/js/zoom.js
index 38c86f18..1ba96404 100755
--- a/web/js/zoom.js
+++ b/web/js/zoom.js
@@ -41,7 +41,7 @@ function add_ruling(event) {
$('#add-ruling-form-text').on(
'keyup',
function () {
- $('#add-ruling-form-preview').html(converter.makeHtml($('#add-ruling-form-text').val()));
+ $('#add-ruling-form-preview').html(DOMPurify.sanitize(converter.makeHtml($('#add-ruling-form-text').val())));
}
);
@@ -105,7 +105,7 @@ function edit_ruling(event) {
$('#edit-ruling-form-text').on(
'keyup',
function () {
- $('#edit-ruling-form-preview').html(converter.makeHtml($('#edit-ruling-form-text').val()));
+ $('#edit-ruling-form-preview').html(DOMPurify.sanitize(converter.makeHtml($('#edit-ruling-form-text').val())));
}
);
@@ -175,7 +175,7 @@ function write_comment(event) {
$('.comment-form-text').on(
'keyup',
function () {
- $('.comment-form-preview').html(converter.makeHtml($('.comment-form-text').val()));
+ $('.comment-form-preview').html(DOMPurify.sanitize(converter.makeHtml($('.comment-form-text').val())));
}
);
@@ -318,7 +318,7 @@ function write_review_open(event) {
$('.review-form-text').on(
'keyup',
function () {
- $('.review-form-preview').html(converter.makeHtml(escapeHtml($('.review-form-text').val())));
+ $('.review-form-preview').html(DOMPurify.sanitize(converter.makeHtml($('.review-form-text').val())));
}
);