diff --git a/CHANGELOG.md b/CHANGELOG.md
index a44fb1630d6b4a790425247b9e64165f0337e2e4..3e467bc95e73019e46f3f6cc52d4e5cc74447bd3 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -6,6 +6,9 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).
 ### Changed
 - Removed the use of with_move parameters when fetching notifications
 
+### Fixed
+- Multiple issues with muted statuses/notifications
+
 ## [Unreleased patch]
 ### Add
 - Added private notifications option for push notifications
@@ -13,9 +16,15 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).
 
 ### Changed
 - Registration page no longer requires email if the server is configured not to require it
+- Change heart to thumbs up in reaction picker
+- Close the media modal on navigation events
+- Add colons to the emoji alt text, to make them copyable
 
 ### Fixed
 - Status ellipsis menu closes properly when selecting certain options
+- Cropped images look correct in Chrome
+- Newlines in the muted words settings work again
+- Clicking on non-latin hashtags won't open a new window
 
 ## [2.0.3] - 2020-05-02
 ### Fixed
diff --git a/README.md b/README.md
index 889f0837617b4a290f691143ac508f54870e8644..b66383ade7a4dc704cd47c1f7924aea63dafd91c 100644
--- a/README.md
+++ b/README.md
@@ -1,6 +1,6 @@
-# pleroma_fe
+# Pleroma-FE 
 
-> A single column frontend for both Pleroma and GS servers.
+> A single column frontend designed for Pleroma.
 
 ![screenshot](https://i.imgur.com/DJVqSJ0.png)
 
@@ -11,7 +11,6 @@ To translate Pleroma-FE, add your language to [src/i18n/messages.js](https://git
 # FOR ADMINS
 
 You don't need to build Pleroma-FE yourself. Those using the Pleroma backend will be able to use it out of the box.
-For the GNU social backend, check out https://git.pleroma.social/pleroma/pleroma-fe/wikis/dual-boot-with-qvitter to see how to run Pleroma-FE and Qvitter at the same time.
 
 ## Build Setup
 
diff --git a/docs/USER_GUIDE.md b/docs/USER_GUIDE.md
index 076bfb1c3b09e104a8df4c27c8306b4bf609d587..f417f33d7579a0b334a121793e9a2cfe04a760cd 100644
--- a/docs/USER_GUIDE.md
+++ b/docs/USER_GUIDE.md
@@ -33,7 +33,7 @@ will become
 Note that you can only use emoji defined on your instance, you cannot "copy" someone else's emoji, and will have to ask your administrator to copy emoji from other instance to yours.  
 Lastly, there's two convenience options for emoji: an emoji picker (smiley face to the right of "submit" button) and autocomplete suggestions - when you start typing :shortcode: it will automatically try to suggest you emoj and complete the shortcode for you if you select one. **Note** that if emoji doesn't show up in suggestions nor in emoji picker it means there's no such emoji on your instance, if shortcode doesn't match any defined emoji it will appear as text.
 * **Attachments** are fairly simple - you can attach any file to a post as long as the file is within maximum size limits. If you're uploading explicit material you can mark all of your attachments as sensitive (or add `#nsfw` tag) - it will hide the images and videos behind a warning so that it won't be displayed instantly.
-* **Subject line** also known as **CW** (Content Warning) could be used as a header to the post and/or to warn others about contents of the post having something that might upset somebody or something among those lines. Several applications allow to hide post content leaving only subject line visible. As a side-effect using subject line will also mark your images as sensitive (see above).
+* **Subject line** also known as **CW** (Content Warning) could be used as a header to the post and/or to warn others about contents of the post having something that might upset somebody or something among those lines. Several applications allow to hide post content leaving only subject line visible. Using a subject line will not mark your images as sensitive, you will have to do that explicitly (see above).
 * **Visiblity scope** controls who will be able to see your posts. There are four scopes available:
 
 1. `Public`: This is the default, and some fediverse software like GNU Social only supports this. This means that your post is accessible by anyone and will be shown in the public timelines.
diff --git a/src/boot/after_store.js b/src/boot/after_store.js
index abdba305a289ae519e1bb60f983eacc86bffe97a..0db035475f7f8ce7ba9f59492da471cd2b7e3413 100644
--- a/src/boot/after_store.js
+++ b/src/boot/after_store.js
@@ -110,6 +110,7 @@ const setSettings = async ({ apiConfig, staticConfig, store }) => {
   copyInstanceOption('alwaysShowSubjectInput')
   copyInstanceOption('showFeaturesPanel')
   copyInstanceOption('hideSitename')
+  copyInstanceOption('sidebarRight')
 
   return store.dispatch('setTheme', config['theme'])
 }
diff --git a/src/components/media_modal/media_modal.js b/src/components/media_modal/media_modal.js
index abb18c7de70107a7788be0d38785b471e6eae038..24764e800f576fb00b3211cdbd9e047464aad85c 100644
--- a/src/components/media_modal/media_modal.js
+++ b/src/components/media_modal/media_modal.js
@@ -84,10 +84,12 @@ const MediaModal = {
     }
   },
   mounted () {
+    window.addEventListener('popstate', this.hide)
     document.addEventListener('keyup', this.handleKeyupEvent)
     document.addEventListener('keydown', this.handleKeydownEvent)
   },
   destroyed () {
+    window.removeEventListener('popstate', this.hide)
     document.removeEventListener('keyup', this.handleKeyupEvent)
     document.removeEventListener('keydown', this.handleKeydownEvent)
   }
diff --git a/src/components/notification/notification.js b/src/components/notification/notification.js
index 1cf4c9bc7b43248bfca027ded68939b6766e6ff0..5aa40e988d2052da279fcf4c2adfc021820c2587 100644
--- a/src/components/notification/notification.js
+++ b/src/components/notification/notification.js
@@ -1,3 +1,4 @@
+import StatusContent from '../status_content/status_content.vue'
 import Status from '../status/status.vue'
 import UserAvatar from '../user_avatar/user_avatar.vue'
 import UserCard from '../user_card/user_card.vue'
@@ -16,10 +17,11 @@ const Notification = {
   },
   props: [ 'notification' ],
   components: {
-    Status,
+    StatusContent,
     UserAvatar,
     UserCard,
-    Timeago
+    Timeago,
+    Status
   },
   methods: {
     toggleUserExpanded () {
diff --git a/src/components/notification/notification.vue b/src/components/notification/notification.vue
index 0e46a2a722349a61582278227a3a88dd240ac00a..044ac871548113eb0e57b3ea7284fd9f267a201d 100644
--- a/src/components/notification/notification.vue
+++ b/src/components/notification/notification.vue
@@ -157,11 +157,9 @@
           </router-link>
         </div>
         <template v-else>
-          <status
+          <status-content
             class="faint"
-            :compact="true"
-            :statusoid="notification.action"
-            :no-heading="true"
+            :status="notification.action"
           />
         </template>
       </div>
diff --git a/src/components/notifications/notifications.scss b/src/components/notifications/notifications.scss
index 9efcfcf86ebca995f4ff8c9a4a7b603d74e751b3..b675af5a0087d398a878fa5347a96bef749a560e 100644
--- a/src/components/notifications/notifications.scss
+++ b/src/components/notifications/notifications.scss
@@ -36,6 +36,8 @@
   border-bottom: 1px solid;
   border-color: $fallback--border;
   border-color: var(--border, $fallback--border);
+  word-wrap: break-word;
+  word-break: break-word;
 
   &:hover .animated.avatar {
     canvas {
@@ -46,10 +48,6 @@
     }
   }
 
-  .muted {
-    padding: .25em .6em;
-  }
-
   .non-mention {
     display: flex;
     flex: 1;
diff --git a/src/components/react_button/react_button.js b/src/components/react_button/react_button.js
index abc3bf07d990abb40821b0536ed4ee0874631203..f0931446f2c1d47e003161de960684fd4451833c 100644
--- a/src/components/react_button/react_button.js
+++ b/src/components/react_button/react_button.js
@@ -24,7 +24,7 @@ const ReactButton = {
   },
   computed: {
     commonEmojis () {
-      return ['❤️', '😠', '👀', '😂', '🔥']
+      return ['👍', '😠', '👀', '😂', '🔥']
     },
     emojis () {
       if (this.filterWord !== '') {
diff --git a/src/components/settings_modal/tabs/filtering_tab.js b/src/components/settings_modal/tabs/filtering_tab.js
index ec3306670571d9fd8ab90d9ea02e6fd4f0bce5a7..dd7ecaf7f98f61e2d5d77163b60c623389776f95 100644
--- a/src/components/settings_modal/tabs/filtering_tab.js
+++ b/src/components/settings_modal/tabs/filtering_tab.js
@@ -1,13 +1,31 @@
+import { filter, trim } from 'lodash'
 import Checkbox from 'src/components/checkbox/checkbox.vue'
 
 import SharedComputedObject from './helpers/shared_computed_object.js'
 
 const FilteringTab = {
+  data () {
+    return {
+      muteWordsStringLocal: this.$store.getters.mergedConfig.muteWords.join('\n')
+    }
+  },
   components: {
     Checkbox
   },
   computed: {
-    ...SharedComputedObject()
+    ...SharedComputedObject(),
+    muteWordsString: {
+      get () {
+        return this.muteWordsStringLocal
+      },
+      set (value) {
+        this.muteWordsStringLocal = value
+        this.$store.dispatch('setOption', {
+          name: 'muteWords',
+          value: filter(value.split('\n'), (word) => trim(word).length > 0)
+        })
+      }
+    }
   },
   // Updating nested properties
   watch: {
diff --git a/src/components/settings_modal/tabs/helpers/shared_computed_object.js b/src/components/settings_modal/tabs/helpers/shared_computed_object.js
index b6a18e9cd4ae5622220da41b0ee212693d10b74a..86703697d260397379cb495b29cc127e34287959 100644
--- a/src/components/settings_modal/tabs/helpers/shared_computed_object.js
+++ b/src/components/settings_modal/tabs/helpers/shared_computed_object.js
@@ -1,4 +1,3 @@
-import { filter, trim } from 'lodash'
 import {
   instanceDefaultProperties,
   multiChoiceProperties,
@@ -38,15 +37,6 @@ const SharedComputedObject = () => ({
     }])
     .reduce((acc, [key, value]) => ({ ...acc, [key]: value }), {}),
   // Special cases (need to transform values or perform actions first)
-  muteWordsString: {
-    get () { return this.$store.getters.mergedConfig.muteWords.join('\n') },
-    set (value) {
-      this.$store.dispatch('setOption', {
-        name: 'muteWords',
-        value: filter(value.split('\n'), (word) => trim(word).length > 0)
-      })
-    }
-  },
   useStreamingApi: {
     get () { return this.$store.getters.mergedConfig.useStreamingApi },
     set (value) {
diff --git a/src/components/status/status.js b/src/components/status/status.js
index 9cd9d61c6d1062be06cd57ccd607d8afd26fe18a..733825212606819f88dca87ec3e9ecff691051a0 100644
--- a/src/components/status/status.js
+++ b/src/components/status/status.js
@@ -12,7 +12,8 @@ import StatusPopover from '../status_popover/status_popover.vue'
 import EmojiReactions from '../emoji_reactions/emoji_reactions.vue'
 import generateProfileLink from 'src/services/user_profile_link_generator/user_profile_link_generator'
 import { highlightClass, highlightStyle } from '../../services/user_highlighter/user_highlighter.js'
-import { filter, unescape, uniqBy } from 'lodash'
+import { muteWordHits } from '../../services/status_parser/status_parser.js'
+import { unescape, uniqBy } from 'lodash'
 import { mapGetters, mapState } from 'vuex'
 
 const Status = {
@@ -44,6 +45,12 @@ const Status = {
     muteWords () {
       return this.mergedConfig.muteWords
     },
+    showReasonMutedThread () {
+      return (
+        this.status.thread_muted ||
+          (this.status.reblog && this.status.reblog.thread_muted)
+      ) && !this.inConversation
+    },
     repeaterClass () {
       const user = this.statusoid.user
       return highlightClass(user)
@@ -93,20 +100,42 @@ const Status = {
       return !!this.currentUser
     },
     muteWordHits () {
-      const statusText = this.status.text.toLowerCase()
-      const statusSummary = this.status.summary.toLowerCase()
-      const hits = filter(this.muteWords, (muteWord) => {
-        return statusText.includes(muteWord.toLowerCase()) || statusSummary.includes(muteWord.toLowerCase())
-      })
-
-      return hits
+      return muteWordHits(this.status, this.muteWords)
     },
     muted () {
-      const relationship = this.$store.getters.relationship(this.status.user.id)
-      return !this.unmuted && (
-        (!(this.inProfile && this.status.user.id === this.profileUserId) && relationship.muting) ||
-        (!this.inConversation && this.status.thread_muted) ||
-        this.muteWordHits.length > 0)
+      const { status } = this
+      const { reblog } = status
+      const relationship = this.$store.getters.relationship(status.user.id)
+      const relationshipReblog = reblog && this.$store.getters.relationship(reblog.user.id)
+      const reasonsToMute = (
+        // Post is muted according to BE
+        status.muted ||
+        // Reprööt of a muted post according to BE
+        (reblog && reblog.muted) ||
+        // Muted user
+        relationship.muting ||
+        // Muted user of a reprööt
+        (relationshipReblog && relationshipReblog.muting) ||
+        // Thread is muted
+        status.thread_muted ||
+        // Wordfiltered
+        this.muteWordHits.length > 0
+      )
+      const excusesNotToMute = (
+        (
+          this.inProfile && (
+            // Don't mute user's posts on user timeline (except reblogs)
+            (!reblog && status.user.id === this.profileUserId) ||
+            // Same as above but also allow self-reblogs
+            (reblog && reblog.user.id === this.profileUserId)
+          )
+        ) ||
+        // Don't mute statuses in muted conversation when said conversation is opened
+        (this.inConversation && status.thread_muted)
+        // No excuses if post has muted words
+      ) && !this.muteWordHits.length > 0
+
+      return !this.unmuted && !excusesNotToMute && reasonsToMute
     },
     hideFilteredStatuses () {
       return this.mergedConfig.hideFilteredStatuses
diff --git a/src/components/status/status.vue b/src/components/status/status.vue
index e4c7545bbb7098e4f1bc773b68520ec71b20fdb7..336f912a7064ad3a60b161f48d46cc97b9073c47 100644
--- a/src/components/status/status.vue
+++ b/src/components/status/status.vue
@@ -17,12 +17,33 @@
     </div>
     <template v-if="muted && !isPreview">
       <div class="media status container muted">
-        <small>
+        <small class="username">
+          <i
+            v-if="muted && retweet"
+            class="button-icon icon-retweet"
+          />
           <router-link :to="userProfileLink">
             {{ status.user.screen_name }}
           </router-link>
         </small>
-        <small class="muteWords">{{ muteWordHits.join(', ') }}</small>
+        <small
+          v-if="showReasonMutedThread"
+          class="mute-thread"
+        >
+          {{ $t('status.thread_muted') }}
+        </small>
+        <small
+          v-if="showReasonMutedThread && muteWordHits.length > 0"
+          class="mute-thread"
+        >
+          {{ $t('status.thread_muted_and_words') }}
+        </small>
+        <small
+          class="mute-words"
+          :title="muteWordHits.join(', ')"
+        >
+          {{ muteWordHits.join(', ') }}
+        </small>
         <a
           href="#"
           class="unmute"
@@ -637,19 +658,48 @@ $status-margin: 0.75em;
 }
 
 .muted {
-  padding: 0.25em 0.5em;
-  button {
-    margin-left: auto;
+  padding: .25em .6em;
+  height: 1.2em;
+  line-height: 1.2em;
+  text-overflow: ellipsis;
+  overflow: hidden;
+  display: flex;
+  flex-wrap: nowrap;
+
+  .username, .mute-thread, .mute-words {
+    word-wrap: normal;
+    word-break: normal;
+    white-space: nowrap;
   }
 
-  .muteWords {
-    margin-left: 10px;
+  .username, .mute-words {
+    text-overflow: ellipsis;
+    overflow: hidden;
+  }
+
+  .username {
+    flex: 0 1 auto;
+    margin-right: .2em;
+  }
+
+  .mute-thread {
+    flex: 0 0 auto;
   }
-}
 
-a.unmute {
-  display: block;
-  margin-left: auto;
+  .mute-words {
+    flex: 1 0 5em;
+    margin-left: .2em;
+    &::before {
+      content: ' '
+    }
+  }
+
+  .unmute {
+    flex: 0 0 auto;
+    margin-left: auto;
+    display: block;
+    margin-left: auto;
+  }
 }
 
 .reply-body {
diff --git a/src/components/status_content/status_content.js b/src/components/status_content/status_content.js
index ccc01b6f96c998e88fbd76ce5942ba21af9aaf5a..c0a71e8f77f1ca57d3a1f05aabc065e651cf06e4 100644
--- a/src/components/status_content/status_content.js
+++ b/src/components/status_content/status_content.js
@@ -176,8 +176,8 @@ const StatusContent = {
           }
         }
         if (target.rel.match(/(?:^|\s)tag(?:$|\s)/) || target.className.match(/hashtag/)) {
-          // Extract tag name from link url
-          const tag = extractTagFromUrl(target.href)
+          // Extract tag name from dataset or link url
+          const tag = target.dataset.tag || extractTagFromUrl(target.href)
           if (tag) {
             const link = this.generateTagLink(tag)
             this.$router.push(link)
diff --git a/src/components/still-image/still-image.vue b/src/components/still-image/still-image.vue
index 4137bd5960cf887a3105cda7d27eb7f2a302233d..08af26f6c381509dd12ba07a7d6d82383d50586a 100644
--- a/src/components/still-image/still-image.vue
+++ b/src/components/still-image/still-image.vue
@@ -23,12 +23,21 @@
 
 <style lang="scss">
 @import '../../_variables.scss';
+.contain-fit {
+  .still-image {
+    img {
+      height: 100%;
+    }
+  }
+}
+
 .still-image {
   position: relative;
   line-height: 0;
   overflow: hidden;
   width: 100%;
   height: 100%;
+  display: flex;
 
   &:hover canvas {
     display: none;
@@ -36,8 +45,8 @@
 
   img {
     width: 100%;
-    height: 100%;
     object-fit: contain;
+    align-self: center;
   }
 
   &.animated {
diff --git a/src/i18n/en.json b/src/i18n/en.json
index 062af2c7ca20316a0b034a20aebe489a350f72da..fddead69e2125e65432c0c978639ed7a182ca7f9 100644
--- a/src/i18n/en.json
+++ b/src/i18n/en.json
@@ -627,7 +627,9 @@
     "mute_conversation": "Mute conversation",
     "unmute_conversation": "Unmute conversation",
     "status_unavailable": "Status unavailable",
-    "copy_link": "Copy link to status"
+    "copy_link": "Copy link to status",
+    "thread_muted": "Thread muted",
+    "thread_muted_and_words": ", has words:"
   },
   "user_card": {
     "approve": "Approve",
diff --git a/src/modules/statuses.js b/src/modules/statuses.js
index cd8c1dba66986d74cfe0406e524e584ccba90b0c..9a2e0df1e9646427995bd2573dfa024465fdcde3 100644
--- a/src/modules/statuses.js
+++ b/src/modules/statuses.js
@@ -15,7 +15,7 @@ import {
 import { set } from 'vue'
 import { isStatusNotification } from '../services/notification_utils/notification_utils.js'
 import apiService from '../services/api/api.service.js'
-// import parse from '../services/status_parser/status_parser.js'
+import { muteWordHits } from '../services/status_parser/status_parser.js'
 
 const emptyTl = (userId = 0) => ({
   statuses: [],
@@ -381,7 +381,18 @@ const addNewNotifications = (state, { dispatch, notifications, older, visibleNot
           notifObj.image = status.attachments[0].url
         }
 
-        if (!notification.seen && !state.notifications.desktopNotificationSilence && visibleNotificationTypes.includes(notification.type)) {
+        const reasonsToMuteNotif = (
+          notification.seen ||
+            state.notifications.desktopNotificationSilence ||
+            !visibleNotificationTypes.includes(notification.type) ||
+            (
+              notification.type === 'mention' && status && (
+                status.muted ||
+                  muteWordHits(status, rootGetters.mergedConfig.muteWords).length === 0
+              )
+            )
+        )
+        if (!reasonsToMuteNotif) {
           let desktopNotification = new window.Notification(title, notifObj)
           // Chrome is known for not closing notifications automatically
           // according to MDN, anyway.
diff --git a/src/services/api/api.service.js b/src/services/api/api.service.js
index 7f82d2fa07199aa7098e07c81a3e59f481de1f61..9c7530a27597e59a01243d0f6c00fbc6a2f572a5 100644
--- a/src/services/api/api.service.js
+++ b/src/services/api/api.service.js
@@ -538,9 +538,11 @@ const fetchTimeline = ({
   if (timeline === 'public' || timeline === 'publicAndExternal') {
     params.push(['only_media', false])
   }
+  if (timeline !== 'favorites') {
+    params.push(['with_muted', withMuted])
+  }
 
   params.push(['limit', 20])
-  params.push(['with_muted', withMuted])
 
   const queryString = map(params, (param) => `${param[0]}=${param[1]}`).join('&')
   url += `?${queryString}`
diff --git a/src/services/entity_normalizer/entity_normalizer.service.js b/src/services/entity_normalizer/entity_normalizer.service.js
index 6dac7c1570c5f0992f4f2bb7106714253a45cd70..c7ed65a4d42300bba9be1e4f3781a137f4c75b53 100644
--- a/src/services/entity_normalizer/entity_normalizer.service.js
+++ b/src/services/entity_normalizer/entity_normalizer.service.js
@@ -210,7 +210,7 @@ export const addEmojis = (string, emojis) => {
     const regexSafeShortCode = emoji.shortcode.replace(matchOperatorsRegex, '\\$&')
     return acc.replace(
       new RegExp(`:${regexSafeShortCode}:`, 'g'),
-      `<img src='${emoji.url}' alt='${emoji.shortcode}' title='${emoji.shortcode}' class='emoji' />`
+      `<img src='${emoji.url}' alt=':${emoji.shortcode}:' title=':${emoji.shortcode}:' class='emoji' />`
     )
   }, string)
 }
diff --git a/src/services/status_parser/status_parser.js b/src/services/status_parser/status_parser.js
index 900cd56ebdf025ce72359a24034833a039b9ade0..3d517e3c1e374f1245f8b310225cee3d1b9c6429 100644
--- a/src/services/status_parser/status_parser.js
+++ b/src/services/status_parser/status_parser.js
@@ -1,3 +1,4 @@
+import { filter } from 'lodash'
 import sanitize from 'sanitize-html'
 
 export const removeAttachmentLinks = (html) => {
@@ -12,4 +13,14 @@ export const parse = (html) => {
   return removeAttachmentLinks(html)
 }
 
+export const muteWordHits = (status, muteWords) => {
+  const statusText = status.text.toLowerCase()
+  const statusSummary = status.summary.toLowerCase()
+  const hits = filter(muteWords, (muteWord) => {
+    return statusText.includes(muteWord.toLowerCase()) || statusSummary.includes(muteWord.toLowerCase())
+  })
+
+  return hits
+}
+
 export default parse
diff --git a/test/unit/specs/services/entity_normalizer/entity_normalizer.spec.js b/test/unit/specs/services/entity_normalizer/entity_normalizer.spec.js
index cfb380bafcf9d54728ead47b919cd0103c00ae9a..166fce2b7a37f934521ac4720dbaaffebd6e4692 100644
--- a/test/unit/specs/services/entity_normalizer/entity_normalizer.spec.js
+++ b/test/unit/specs/services/entity_normalizer/entity_normalizer.spec.js
@@ -338,9 +338,9 @@ describe('API Entities normalizer', () => {
 
   describe('MastoAPI emoji adder', () => {
     const emojis = makeMockEmojiMasto()
-    const imageHtml = '<img src="https://example.com/image.png" alt="image" title="image" class="emoji" />'
+    const imageHtml = '<img src="https://example.com/image.png" alt=":image:" title=":image:" class="emoji" />'
       .replace(/"/g, '\'')
-    const thinkHtml = '<img src="https://example.com/think.png" alt="thinking" title="thinking" class="emoji" />'
+    const thinkHtml = '<img src="https://example.com/think.png" alt=":thinking:" title=":thinking:" class="emoji" />'
       .replace(/"/g, '\'')
 
     it('correctly replaces shortcodes in supplied string', () => {
@@ -366,8 +366,8 @@ describe('API Entities normalizer', () => {
         shortcode: '[a-z] {|}*'
       }])
       const result = addEmojis('This post has :c++: emoji and :[a-z] {|}*: emoji', emojis)
-      expect(result).to.include('title=\'c++\'')
-      expect(result).to.include('title=\'[a-z] {|}*\'')
+      expect(result).to.include('title=\':c++:\'')
+      expect(result).to.include('title=\':[a-z] {|}*:\'')
     })
   })
 })