do the impossible, fix the unfixable
This commit is contained in:
		
							parent
							
								
									636dbdaba8
								
							
						
					
					
						commit
						c21b1cf898
					
				
					 8 changed files with 118 additions and 41 deletions
				
			
		| 
						 | 
				
			
			@ -5,6 +5,7 @@ import { convertHtmlToTree } from 'src/services/html_converter/html_tree_convert
 | 
			
		|||
import { convertHtmlToLines } from 'src/services/html_converter/html_line_converter.service.js'
 | 
			
		||||
import StillImage from 'src/components/still-image/still-image.vue'
 | 
			
		||||
import MentionLink from 'src/components/mention_link/mention_link.vue'
 | 
			
		||||
import MentionsLine from 'src/components/mentions_line/mentions_line.vue'
 | 
			
		||||
 | 
			
		||||
import './rich_content.scss'
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -51,6 +52,11 @@ export default Vue.component('RichContent', {
 | 
			
		|||
      required: false,
 | 
			
		||||
      type: Boolean,
 | 
			
		||||
      default: false
 | 
			
		||||
    },
 | 
			
		||||
    hideMentions: {
 | 
			
		||||
      required: false,
 | 
			
		||||
      type: Boolean,
 | 
			
		||||
      default: false
 | 
			
		||||
    }
 | 
			
		||||
  },
 | 
			
		||||
  // NEVER EVER TOUCH DATA INSIDE RENDER
 | 
			
		||||
| 
						 | 
				
			
			@ -64,6 +70,7 @@ export default Vue.component('RichContent', {
 | 
			
		|||
    // unique index for vue "tag" property
 | 
			
		||||
    let mentionIndex = 0
 | 
			
		||||
    let tagsIndex = 0
 | 
			
		||||
    let firstMentionReplaced = false
 | 
			
		||||
 | 
			
		||||
    const renderImage = (tag) => {
 | 
			
		||||
      return <StillImage
 | 
			
		||||
| 
						 | 
				
			
			@ -90,7 +97,12 @@ export default Vue.component('RichContent', {
 | 
			
		|||
      writtenMentions.push(linkData)
 | 
			
		||||
      if (!encounteredText) {
 | 
			
		||||
        firstMentions.push(linkData)
 | 
			
		||||
        return ''
 | 
			
		||||
        if (!firstMentionReplaced && !this.hideMentions) {
 | 
			
		||||
          firstMentionReplaced = true
 | 
			
		||||
          return <MentionsLine mentions={ firstMentions } />
 | 
			
		||||
        } else {
 | 
			
		||||
          return ''
 | 
			
		||||
        }
 | 
			
		||||
      } else {
 | 
			
		||||
        return <MentionLink
 | 
			
		||||
          url={attrs.href}
 | 
			
		||||
| 
						 | 
				
			
			@ -143,7 +155,7 @@ export default Vue.component('RichContent', {
 | 
			
		|||
              if (firstMentions.length > 1 && lastMentions.length > 1) {
 | 
			
		||||
                break
 | 
			
		||||
              } else {
 | 
			
		||||
                return ''
 | 
			
		||||
                return !this.hideMentions ? <MentionsLine mentions={lastMentions} /> : ''
 | 
			
		||||
              }
 | 
			
		||||
            } else {
 | 
			
		||||
              break
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,6 +1,5 @@
 | 
			
		|||
import fileType from 'src/services/file_type/file_type.service'
 | 
			
		||||
import RichContent from 'src/components/rich_content/rich_content.jsx'
 | 
			
		||||
import MentionsLine from 'src/components/mentions_line/mentions_line.vue'
 | 
			
		||||
import { mapGetters } from 'vuex'
 | 
			
		||||
import { library } from '@fortawesome/fontawesome-svg-core'
 | 
			
		||||
import { set } from 'vue'
 | 
			
		||||
| 
						 | 
				
			
			@ -36,9 +35,6 @@ const StatusContent = {
 | 
			
		|||
      showingLongSubject: false,
 | 
			
		||||
      // not as computed because it sets the initial state which will be changed later
 | 
			
		||||
      expandingSubject: !this.$store.getters.mergedConfig.collapseMessageWithSubject,
 | 
			
		||||
      headTailLinks: null,
 | 
			
		||||
      firstMentions: [],
 | 
			
		||||
      lastMentions: []
 | 
			
		||||
    }
 | 
			
		||||
  },
 | 
			
		||||
  computed: {
 | 
			
		||||
| 
						 | 
				
			
			@ -81,8 +77,7 @@ const StatusContent = {
 | 
			
		|||
    ...mapGetters(['mergedConfig'])
 | 
			
		||||
  },
 | 
			
		||||
  components: {
 | 
			
		||||
    RichContent,
 | 
			
		||||
    MentionsLine
 | 
			
		||||
    RichContent
 | 
			
		||||
  },
 | 
			
		||||
  mounted () {
 | 
			
		||||
    this.status.attentions && this.status.attentions.forEach(attn => {
 | 
			
		||||
| 
						 | 
				
			
			@ -98,11 +93,6 @@ const StatusContent = {
 | 
			
		|||
        this.expandingSubject = !this.expandingSubject
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    setHeadTailLinks (headTailLinks) {
 | 
			
		||||
      set(this, 'headTailLinks', headTailLinks)
 | 
			
		||||
      set(this, 'firstMentions', headTailLinks.firstMentions)
 | 
			
		||||
      set(this, 'lastMentions', headTailLinks.lastMentions)
 | 
			
		||||
    },
 | 
			
		||||
    generateTagLink (tag) {
 | 
			
		||||
      return `/tag/${tag}`
 | 
			
		||||
    }
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -62,7 +62,7 @@
 | 
			
		|||
      overflow-y: hidden;
 | 
			
		||||
      z-index: 1;
 | 
			
		||||
 | 
			
		||||
      .rich-content-wrapper {
 | 
			
		||||
      .media-body {
 | 
			
		||||
        min-height: 0;
 | 
			
		||||
        mask:
 | 
			
		||||
          linear-gradient(to top, white, transparent) bottom/100% 70px no-repeat,
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -38,28 +38,17 @@
 | 
			
		|||
        >
 | 
			
		||||
          {{ $t("general.show_more") }}
 | 
			
		||||
        </button>
 | 
			
		||||
        <span
 | 
			
		||||
        <RichContent
 | 
			
		||||
          v-if="!hideSubjectStatus && !(singleLine && status.summary_raw_html)"
 | 
			
		||||
          class="rich-content-wrapper"
 | 
			
		||||
        >
 | 
			
		||||
          <MentionsLine
 | 
			
		||||
            v-if="!hideMentions && firstMentions && firstMentions.length > 0"
 | 
			
		||||
            :mentions="firstMentions"
 | 
			
		||||
          />
 | 
			
		||||
          <RichContent
 | 
			
		||||
            :class="{ '-single-line': singleLine }"
 | 
			
		||||
            class="text media-body"
 | 
			
		||||
            :html="status.raw_html"
 | 
			
		||||
            :emoji="status.emojis"
 | 
			
		||||
            :handle-links="true"
 | 
			
		||||
            :greentext="mergedConfig.greentext"
 | 
			
		||||
            @parseReady="setHeadTailLinks"
 | 
			
		||||
          />
 | 
			
		||||
          <MentionsLine
 | 
			
		||||
            v-if="!hideMentions && lastMentions.length > 1 && firstMentions.length <= 1"
 | 
			
		||||
            :mentions="lastMentions"
 | 
			
		||||
          />
 | 
			
		||||
        </span>
 | 
			
		||||
          :class="{ '-single-line': singleLine }"
 | 
			
		||||
          class="text media-body"
 | 
			
		||||
          :html="status.raw_html"
 | 
			
		||||
          :emoji="status.emojis"
 | 
			
		||||
          :handle-links="true"
 | 
			
		||||
          :hide-mentions="hideMentions"
 | 
			
		||||
          :greentext="mergedConfig.greentext"
 | 
			
		||||
          @parseReady="$emit('parseReady', $event)"
 | 
			
		||||
        />
 | 
			
		||||
 | 
			
		||||
        <button
 | 
			
		||||
          v-if="hideSubjectStatus"
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -92,9 +92,6 @@ const StatusContent = {
 | 
			
		|||
    StatusBody
 | 
			
		||||
  },
 | 
			
		||||
  methods: {
 | 
			
		||||
    setHeadTailLinks (headTailLinks) {
 | 
			
		||||
      this.$emit('parseReady', headTailLinks)
 | 
			
		||||
    },
 | 
			
		||||
    setMedia () {
 | 
			
		||||
      const attachments = this.attachmentSize === 'hide' ? this.status.attachments : this.galleryAttachments
 | 
			
		||||
      return () => this.$store.dispatch('setMedia', attachments)
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -5,7 +5,7 @@
 | 
			
		|||
      :status="status"
 | 
			
		||||
      :single-line="singleLine"
 | 
			
		||||
      :hide-mentions="hideMentions"
 | 
			
		||||
      @parseReady="setHeadTailLinks"
 | 
			
		||||
      @parseReady="$emit('parseReady', $event)"
 | 
			
		||||
    >
 | 
			
		||||
      <div v-if="status.poll && status.poll.options">
 | 
			
		||||
        <poll :base-poll="status.poll" />
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -16,6 +16,7 @@ describe('RichContent', () => {
 | 
			
		|||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: true,
 | 
			
		||||
        handleLinks: true,
 | 
			
		||||
        greentext: true,
 | 
			
		||||
        emoji: [],
 | 
			
		||||
| 
						 | 
				
			
			@ -38,6 +39,34 @@ describe('RichContent', () => {
 | 
			
		|||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: true,
 | 
			
		||||
        handleLinks: true,
 | 
			
		||||
        greentext: true,
 | 
			
		||||
        emoji: [],
 | 
			
		||||
        html
 | 
			
		||||
      }
 | 
			
		||||
    })
 | 
			
		||||
 | 
			
		||||
    expect(wrapper.html()).to.eql(compwrap(expected))
 | 
			
		||||
  })
 | 
			
		||||
 | 
			
		||||
  it('replaces first mention with mentionsline if hideMentions=false', () => {
 | 
			
		||||
    const html = p(
 | 
			
		||||
      makeMention('John'),
 | 
			
		||||
      ' how are you doing thoday?'
 | 
			
		||||
    )
 | 
			
		||||
    const expected = p(
 | 
			
		||||
      '<span class="h-card">',
 | 
			
		||||
      '<mentionsline-stub mentions="',
 | 
			
		||||
      '[object Object]',
 | 
			
		||||
      '"></mentionsline-stub>',
 | 
			
		||||
      '</span>',
 | 
			
		||||
      'how are you doing thoday?'
 | 
			
		||||
    )
 | 
			
		||||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: false,
 | 
			
		||||
        handleLinks: true,
 | 
			
		||||
        greentext: true,
 | 
			
		||||
        emoji: [],
 | 
			
		||||
| 
						 | 
				
			
			@ -68,6 +97,7 @@ describe('RichContent', () => {
 | 
			
		|||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: true,
 | 
			
		||||
        handleLinks: true,
 | 
			
		||||
        greentext: true,
 | 
			
		||||
        emoji: [],
 | 
			
		||||
| 
						 | 
				
			
			@ -78,6 +108,44 @@ describe('RichContent', () => {
 | 
			
		|||
    expect(wrapper.html()).to.eql(compwrap(expected))
 | 
			
		||||
  })
 | 
			
		||||
 | 
			
		||||
  it('replaces mentions at the end of the hellpost if hideMentions=false (<p>)', () => {
 | 
			
		||||
    const html = [
 | 
			
		||||
      p('How are you doing today, fine gentlemen?'),
 | 
			
		||||
      p(
 | 
			
		||||
        makeMention('John'),
 | 
			
		||||
        makeMention('Josh'),
 | 
			
		||||
        makeMention('Jeremy')
 | 
			
		||||
      )
 | 
			
		||||
    ].join('')
 | 
			
		||||
    const expected = [
 | 
			
		||||
      p(
 | 
			
		||||
        'How are you doing today, fine gentlemen?'
 | 
			
		||||
      ),
 | 
			
		||||
      // TODO fix this extra line somehow?
 | 
			
		||||
      p(
 | 
			
		||||
        '<mentionsline-stub mentions="',
 | 
			
		||||
        '[object Object],',
 | 
			
		||||
        '[object Object],',
 | 
			
		||||
        '[object Object]',
 | 
			
		||||
        '"></mentionsline-stub>'
 | 
			
		||||
      )
 | 
			
		||||
    ].join('')
 | 
			
		||||
 | 
			
		||||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: false,
 | 
			
		||||
        handleLinks: true,
 | 
			
		||||
        greentext: true,
 | 
			
		||||
        emoji: [],
 | 
			
		||||
        html
 | 
			
		||||
      }
 | 
			
		||||
    })
 | 
			
		||||
 | 
			
		||||
    expect(wrapper.html()).to.eql(compwrap(expected))
 | 
			
		||||
  })
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
  it('removes mentions from the end of the hellpost (<br>)', () => {
 | 
			
		||||
    const html = [
 | 
			
		||||
      'How are you doing today, fine gentlemen?',
 | 
			
		||||
| 
						 | 
				
			
			@ -96,6 +164,7 @@ describe('RichContent', () => {
 | 
			
		|||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: true,
 | 
			
		||||
        handleLinks: true,
 | 
			
		||||
        greentext: true,
 | 
			
		||||
        emoji: [],
 | 
			
		||||
| 
						 | 
				
			
			@ -124,6 +193,7 @@ describe('RichContent', () => {
 | 
			
		|||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: true,
 | 
			
		||||
        handleLinks: true,
 | 
			
		||||
        greentext: true,
 | 
			
		||||
        emoji: [],
 | 
			
		||||
| 
						 | 
				
			
			@ -165,6 +235,7 @@ describe('RichContent', () => {
 | 
			
		|||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: true,
 | 
			
		||||
        handleLinks: true,
 | 
			
		||||
        greentext: true,
 | 
			
		||||
        emoji: [],
 | 
			
		||||
| 
						 | 
				
			
			@ -199,6 +270,7 @@ describe('RichContent', () => {
 | 
			
		|||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: true,
 | 
			
		||||
        handleLinks: true,
 | 
			
		||||
        greentext: true,
 | 
			
		||||
        emoji: [],
 | 
			
		||||
| 
						 | 
				
			
			@ -240,6 +312,7 @@ describe('RichContent', () => {
 | 
			
		|||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: true,
 | 
			
		||||
        handleLinks: true,
 | 
			
		||||
        greentext: true,
 | 
			
		||||
        emoji: [],
 | 
			
		||||
| 
						 | 
				
			
			@ -267,6 +340,7 @@ describe('RichContent', () => {
 | 
			
		|||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: true,
 | 
			
		||||
        handleLinks: false,
 | 
			
		||||
        greentext: true,
 | 
			
		||||
        emoji: [],
 | 
			
		||||
| 
						 | 
				
			
			@ -290,6 +364,7 @@ describe('RichContent', () => {
 | 
			
		|||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: true,
 | 
			
		||||
        handleLinks: false,
 | 
			
		||||
        greentext: true,
 | 
			
		||||
        emoji: [],
 | 
			
		||||
| 
						 | 
				
			
			@ -309,6 +384,7 @@ describe('RichContent', () => {
 | 
			
		|||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: true,
 | 
			
		||||
        handleLinks: false,
 | 
			
		||||
        greentext: false,
 | 
			
		||||
        emoji: [],
 | 
			
		||||
| 
						 | 
				
			
			@ -329,6 +405,7 @@ describe('RichContent', () => {
 | 
			
		|||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: true,
 | 
			
		||||
        handleLinks: false,
 | 
			
		||||
        greentext: false,
 | 
			
		||||
        emoji: [{ url: 'about:blank', shortcode: 'spurdo' }],
 | 
			
		||||
| 
						 | 
				
			
			@ -345,6 +422,7 @@ describe('RichContent', () => {
 | 
			
		|||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: true,
 | 
			
		||||
        handleLinks: false,
 | 
			
		||||
        greentext: false,
 | 
			
		||||
        emoji: [],
 | 
			
		||||
| 
						 | 
				
			
			@ -407,6 +485,7 @@ describe('RichContent', () => {
 | 
			
		|||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: true,
 | 
			
		||||
        handleLinks: true,
 | 
			
		||||
        greentext: true,
 | 
			
		||||
        emoji: [],
 | 
			
		||||
| 
						 | 
				
			
			@ -425,10 +504,18 @@ describe('RichContent', () => {
 | 
			
		|||
      makeMention('bar'),
 | 
			
		||||
      makeMention('baz')
 | 
			
		||||
    ].join('<br>')
 | 
			
		||||
    const expected = [
 | 
			
		||||
      'Bruh',
 | 
			
		||||
      'Bruh',
 | 
			
		||||
      stubMention('foo'),
 | 
			
		||||
      stubMention('bar'),
 | 
			
		||||
      stubMention('baz')
 | 
			
		||||
    ].join('<br>')
 | 
			
		||||
 | 
			
		||||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: true,
 | 
			
		||||
        handleLinks: true,
 | 
			
		||||
        greentext: true,
 | 
			
		||||
        emoji: [],
 | 
			
		||||
| 
						 | 
				
			
			@ -436,7 +523,7 @@ describe('RichContent', () => {
 | 
			
		|||
      }
 | 
			
		||||
    })
 | 
			
		||||
 | 
			
		||||
    expect(wrapper.html()).to.eql(compwrap(html))
 | 
			
		||||
    expect(wrapper.html()).to.eql(compwrap(expected))
 | 
			
		||||
  })
 | 
			
		||||
 | 
			
		||||
  it('Don\'t remove last mentions if there are more than one first mention - remove first instead', () => {
 | 
			
		||||
| 
						 | 
				
			
			@ -471,6 +558,7 @@ describe('RichContent', () => {
 | 
			
		|||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: true,
 | 
			
		||||
        handleLinks: true,
 | 
			
		||||
        greentext: true,
 | 
			
		||||
        emoji: [],
 | 
			
		||||
| 
						 | 
				
			
			@ -506,6 +594,7 @@ describe('RichContent', () => {
 | 
			
		|||
    const wrapper = shallowMount(RichContent, {
 | 
			
		||||
      localVue,
 | 
			
		||||
      propsData: {
 | 
			
		||||
        hideMentions: true,
 | 
			
		||||
        handleLinks: true,
 | 
			
		||||
        greentext: true,
 | 
			
		||||
        emoji: [],
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -11,7 +11,7 @@ const mapOnlyText = (processor) => (input) => {
 | 
			
		|||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
describe.only('html_line_converter', () => {
 | 
			
		||||
describe('html_line_converter', () => {
 | 
			
		||||
  describe('with processor that keeps original line should not make any changes to HTML when', () => {
 | 
			
		||||
    const processorKeep = (line) => line
 | 
			
		||||
    it('fed with regular HTML with newlines', () => {
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Loading…
	
		Reference in a new issue