diff --git a/package-lock.json b/package-lock.json
index ae8c27a2b00569114e537719e3a120124ff84acb..039a56eb74f70bd05ba34720ae27ad8fe2405585 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -4458,6 +4458,11 @@
       "resolved": "https://registry.npmjs.org/cssesc/-/cssesc-3.0.0.tgz",
       "integrity": "sha512-/Tb/JcjK111nNScGob5MNtsntNM1aCNUDipB/TkwZFhyDrrE47SOx/18wF2bbjgc3ZzCSKW1T5nt5EbFoAz/Vg=="
     },
+    "cssfilter": {
+      "version": "0.0.10",
+      "resolved": "https://registry.npmjs.org/cssfilter/-/cssfilter-0.0.10.tgz",
+      "integrity": "sha1-xtJnJjKi5cg+AT5oZKQs6N79IK4="
+    },
     "cssnano": {
       "version": "4.1.10",
       "resolved": "https://registry.npmjs.org/cssnano/-/cssnano-4.1.10.tgz",
@@ -14977,6 +14982,15 @@
         "@babel/runtime-corejs3": "^7.8.3"
       }
     },
+    "xss": {
+      "version": "1.0.8",
+      "resolved": "https://registry.npmjs.org/xss/-/xss-1.0.8.tgz",
+      "integrity": "sha512-3MgPdaXV8rfQ/pNn16Eio6VXYPTkqwa0vc7GkiymmY/DqR1SE/7VPAAVZz1GJsJFrllMYO3RHfEaiUGjab6TNw==",
+      "requires": {
+        "commander": "^2.20.3",
+        "cssfilter": "0.0.10"
+      }
+    },
     "xtend": {
       "version": "4.0.2",
       "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz",
diff --git a/package.json b/package.json
index fe1ec7035b92d15b03b5b46660db6d8b40fcbd27..ce86b5863423cefb4b5ce769bed4bff74a06846e 100644
--- a/package.json
+++ b/package.json
@@ -21,7 +21,8 @@
     "react-scripts": "3.4.3",
     "showdown": "^1.9.1",
     "unfetch": "^4.2.0",
-    "wait-queue": "^1.1.4"
+    "wait-queue": "^1.1.4",
+    "xss": "^1.0.8"
   },
   "scripts": {
     "start": "react-scripts start",
@@ -58,7 +59,7 @@
               "^@?\\w"
             ],
             [
-              "^(api|actions|config|hooks|components|containers|pages|utils|stores|keycloak|ws)(/.*|$)"
+              "^(api|actions|config|hooks|components|containers|pages|utils|stores|keycloak|markdown|ws)(/.*|$)"
             ],
             [
               "^(test-utils)(/.*|$)"
diff --git a/src/components/annoucements/Announcement.jsx b/src/components/annoucements/Announcement.jsx
index 95973cc4ff7fb264ec4c30e33181986fac5b8328..0852cad74098905a0bd68f0217500038ddc181ec 100644
--- a/src/components/annoucements/Announcement.jsx
+++ b/src/components/annoucements/Announcement.jsx
@@ -95,7 +95,11 @@ const Announcement = ({
           )}
         </div>
         {canRunActions && (
-          <DropdownMenu right triggerIconClass="ico--dots-three-horizontal">
+          <DropdownMenu
+            right
+            className="pl-4"
+            triggerIconClass="ico--dots-three-horizontal"
+          >
             {showEdit && (
               <DropdownMenuItem
                 onClick={onEdit}
diff --git a/src/components/mde/MarkdownEditor.jsx b/src/components/mde/MarkdownEditor.jsx
index 88a74fe4d50d38f0dbcea58e67d6e9bd5bc99de9..f2ff08973950087196d358d40fcd1f9a46d2dfda 100644
--- a/src/components/mde/MarkdownEditor.jsx
+++ b/src/components/mde/MarkdownEditor.jsx
@@ -1,18 +1,12 @@
 import React, { useState } from "react";
 import ReactMde from "react-mde";
 import classNames from "classnames";
-import Showdown from "showdown";
+
+import { markdownConverter } from "markdown";
 
 import "react-mde/lib/styles/css/react-mde-toolbar.css";
 import "./MarkdownEditor.css";
 
-const converter = new Showdown.Converter({
-  tables: true,
-  simplifiedAutoLink: true,
-  strikethrough: true,
-  tasklists: true,
-});
-
 const MarkdownEditor = ({
   value,
   onChange,
@@ -47,7 +41,7 @@ const MarkdownEditor = ({
         selectedTab={selectedTab}
         onTabChange={setSelectedTab}
         generateMarkdownPreview={(markdown) =>
-          Promise.resolve(converter.makeHtml(markdown))
+          Promise.resolve(markdownConverter.makeHtml(markdown))
         }
         classes={classes}
         l18n={l18n}
diff --git a/src/components/posts/Post.jsx b/src/components/posts/Post.jsx
index 72ed9925703251ea0ab18032730d8a93f37db9a6..3a57d1e219f75140f2b2e9d0084dd7d13f6663ca 100644
--- a/src/components/posts/Post.jsx
+++ b/src/components/posts/Post.jsx
@@ -135,6 +135,10 @@ const Post = ({
   const showHideAction = !archived;
   const showArchiveAction = !archived;
 
+  const htmlContent = {
+    __html: content,
+  };
+
   return (
     <div className={wrapperClassName} ref={ref}>
       <img
@@ -164,7 +168,7 @@ const Post = ({
                 {labels}
               </div>
             </div>
-            <div className="flex items-center space-x-4">
+            <div className="flex items-center">
               <Thumbs
                 likes={ranking.likes}
                 dislikes={ranking.dislikes}
@@ -174,7 +178,7 @@ const Post = ({
                 myVote={ranking.myVote}
               />
               {canRunActions && (
-                <DropdownMenu right>
+                <DropdownMenu right className="pl-4">
                   {showAnnounceAction && (
                     <DropdownMenuItem
                       onClick={onAnnounceProcedureProposal}
@@ -239,9 +243,10 @@ const Post = ({
         <div className="flex lg:hidden flex-row flex-wrap my-2 space-x-2">
           {labels}
         </div>
-        <p className="text-sm lg:text-base text-black leading-normal">
-          {content}
-        </p>
+        <div
+          className="text-sm lg:text-base text-black leading-normal content-block"
+          dangerouslySetInnerHTML={htmlContent}
+        ></div>
       </div>
     </div>
   );
diff --git a/src/components/posts/PostList.jsx b/src/components/posts/PostList.jsx
index c8143ece2ba6ffa9a911990b0ab0289ee7f93482..da1ad33890b159d90d45442aff4f3f49b12df94a 100644
--- a/src/components/posts/PostList.jsx
+++ b/src/components/posts/PostList.jsx
@@ -56,7 +56,7 @@ const PostList = ({
             author={item.author}
             type={item.type}
             state={item.state}
-            content={item.content}
+            content={item.contentHtml}
             ranking={item.ranking}
             historyLog={item.historyLog}
             modified={item.modified}
diff --git a/src/markdown.js b/src/markdown.js
new file mode 100644
index 0000000000000000000000000000000000000000..559427cef5a0542cd2e59a33f18b1465acf1adf4
--- /dev/null
+++ b/src/markdown.js
@@ -0,0 +1,21 @@
+import Showdown from "showdown";
+import xss from "xss";
+
+const xssFilter = (converter) => [
+  {
+    type: "output",
+    filter: (text) => xss(text),
+  },
+];
+
+export const markdownConverter = new Showdown.Converter({
+  tables: true,
+  simplifiedAutoLink: true,
+  strikethrough: true,
+  tasklists: true,
+  omitExtraWLInCodeBlocks: true,
+  noHeaderId: true,
+  headerLevelStart: 2,
+  openLinksInNewWindow: true,
+  extensions: [xssFilter],
+});
diff --git a/src/pages/Home.jsx b/src/pages/Home.jsx
index c3740ac3cdc37bd46c21f50741539426063a7203..6e15e30fed9379ffb05dd879e6e94d6db1c3c92f 100644
--- a/src/pages/Home.jsx
+++ b/src/pages/Home.jsx
@@ -151,7 +151,7 @@ const Home = () => {
             <h1 className="head-alt-md lg:head-alt-lg mb-0">
               Bod č. {programEntry.number}: {programEntry.title}
             </h1>
-            <DropdownMenu right triggerSize="lg">
+            <DropdownMenu right triggerSize="lg" className="pl-4">
               <DropdownMenuItem
                 onClick={() => setShowProgramEditModal(true)}
                 icon="ico--edit-pencil"
diff --git a/src/utils.js b/src/utils.js
index 83fb40083240e42090dc552b3dd27bc12d4063f3..a35571edb8d2ee1e42907d0f81dff022295c8ea4 100644
--- a/src/utils.js
+++ b/src/utils.js
@@ -3,6 +3,8 @@ import pick from "lodash/pick";
 import property from "lodash/property";
 import values from "lodash/values";
 
+import { markdownConverter } from "markdown";
+
 /**
  * Filter & sort collection of posts.
  * @param {CF2021.PostStoreFilters} filters
@@ -120,6 +122,7 @@ export const announcementTypeMappingRev = {
 export const parseRawPost = (rawPost) => {
   const post = {
     ...pick(rawPost, ["id", "content", "author"]),
+    contentHtml: markdownConverter.makeHtml(rawPost.content),
     datetime: new Date(rawPost.datetime),
     historyLog: rawPost.history_log,
     ranking: {
diff --git a/src/ws/handlers/posts.js b/src/ws/handlers/posts.js
index 3c07ed0677243efddaa841762afffaf82d9c8fcd..1eb6dc7d898aecef4d676a5560a056b093ff0793 100644
--- a/src/ws/handlers/posts.js
+++ b/src/ws/handlers/posts.js
@@ -1,5 +1,6 @@
 import has from "lodash/has";
 
+import { markdownConverter } from "markdown";
 import { PostStore } from "stores";
 import { parseRawPost, postsStateMapping, updateWindowPosts } from "utils";
 
@@ -24,6 +25,9 @@ export const handlePostChanged = (payload) => {
     if (state.items[payload.id]) {
       if (has(payload, "content")) {
         state.items[payload.id].content = payload.content;
+        state.items[payload.id].contentHtml = markdownConverter.makeHtml(
+          payload.content
+        );
         state.items[payload.id].modified = true;
       }
 
diff --git a/typings/cf2021.d.ts b/typings/cf2021.d.ts
index 7c0d20197581b1952f9069d73ce8999558d62e59..fbed0e076d90270ed75dfc7abd2134f954a2252f 100644
--- a/typings/cf2021.d.ts
+++ b/typings/cf2021.d.ts
@@ -80,6 +80,7 @@ declare namespace CF2021 {
     };
     type: PostType;
     content: string;
+    contentHtml: string;
     ranking: {
       score: number;
       likes: number;