Update tests, showFilterPostsDropdown only on route

This commit is contained in:
Matt Rider 2019-08-02 15:41:19 +02:00
parent afb9dbe241
commit ec7a5865f7
11 changed files with 112 additions and 70 deletions

View File

@ -13,57 +13,39 @@ describe('FilterMenu.vue', () => {
let mocks
let propsData
const createWrapper = mountMethod => {
return mountMethod(FilterMenu, {
propsData,
mocks,
localVue,
})
}
beforeEach(() => {
mocks = { $t: () => {} }
propsData = {}
})
describe('given a user', () => {
beforeEach(() => {
propsData = {
user: {
id: '4711',
},
hashtag: {},
}
})
describe('mount', () => {
const Wrapper = () => {
return mount(FilterMenu, { mocks, localVue, propsData })
}
beforeEach(() => {
wrapper = createWrapper(mount)
wrapper = Wrapper()
})
it('renders a card', () => {
it('does not render a card if there are no hashtags', () => {
expect(wrapper.is('.ds-card')).toBe(true)
})
describe('click "filter-by-followed-authors-only" button', () => {
it('emits filterBubble object', () => {
wrapper.find({ name: 'filter-by-followed-authors-only' }).trigger('click')
expect(wrapper.emitted('changeFilterBubble')).toBeTruthy()
})
it('renders a card if there are hashtags', () => {
propsData.hashtag = { hashtag: 'Frieden' }
wrapper = Wrapper()
expect(wrapper.is('.ds-card')).toBe(true)
})
it('toggles filterBubble.author property', () => {
wrapper.find({ name: 'filter-by-followed-authors-only' }).trigger('click')
expect(wrapper.emitted('changeFilterBubble')[0]).toEqual([
{ author: { followedBy_some: { id: '4711' } } },
])
wrapper.find({ name: 'filter-by-followed-authors-only' }).trigger('click')
expect(wrapper.emitted('changeFilterBubble')[1]).toEqual([{}])
})
it('makes button primary', () => {
wrapper.find({ name: 'filter-by-followed-authors-only' }).trigger('click')
expect(
wrapper.find({ name: 'filter-by-followed-authors-only' }).classes('ds-button-primary'),
).toBe(true)
describe('click "clear-search-button" button', () => {
it('emits clearSearch', () => {
wrapper.find({ name: 'clear-search-button' }).trigger('click')
expect(wrapper.emitted().clearSearch).toHaveLength(1)
})
})
})

View File

@ -14,7 +14,7 @@
placement: 'left',
delay: { show: 500 },
}"
name="filter-by-followed-authors-only"
name="clear-search-button"
icon="close"
@click="clearSearch"
/>
@ -28,14 +28,8 @@
<script>
export default {
props: {
user: { type: Object, required: true },
hashtag: { type: Object, default: null },
},
data() {
return {
filter: {},
}
},
methods: {
clearSearch() {
this.$emit('clearSearch')

View File

@ -54,6 +54,11 @@ describe('FilterPosts.vue', () => {
mutations: {
'posts/SET_POSTS': mutations.SET_POSTS,
},
getters: {
'auth/user': () => {
return { id: 'u34' }
},
},
})
const Wrapper = () => {
return mount(FilterPosts, { mocks, localVue, propsData, store })
@ -130,5 +135,41 @@ describe('FilterPosts.vue', () => {
const filterPostsMenuItem = wrapper.find(FilterPostsMenuItem)
expect(filterPostsMenuItem.vm.selectedCategoryIds).toEqual([])
})
describe('click "filter-by-followed-authors-only" button', () => {
it('calls the filterPost query', () => {
wrapper.find({ name: 'filter-by-followed-authors-only' }).trigger('click')
expect(mocks.$apollo.query).toHaveBeenCalledWith(
expect.objectContaining({
variables: {
filter: { author: { followedBy_some: { id: 'u34' } } },
first: expect.any(Number),
offset: expect.any(Number),
},
}),
)
})
it('toggles filterBubble.author property', async () => {
await wrapper.find({ name: 'filter-by-followed-authors-only' }).trigger('click')
await wrapper.find({ name: 'filter-by-followed-authors-only' }).trigger('click')
expect(mocks.$apollo.query).toHaveBeenCalledWith(
expect.objectContaining({
variables: {
filter: {},
first: expect.any(Number),
offset: expect.any(Number),
},
}),
)
})
it("sets the button's class to primary when clicked", async () => {
await wrapper.find({ name: 'filter-by-followed-authors-only' }).trigger('click')
expect(
wrapper.find({ name: 'filter-by-followed-authors-only' }).classes('ds-button-primary'),
).toBe(true)
})
})
})
})

View File

@ -44,7 +44,6 @@ export default {
setPosts: 'posts/SET_POSTS',
}),
filterPosts(filter) {
// const filter = categoryIds.length ? { categories_some: { id_in: categoryIds } } : {}
this.$apollo
.query({
query: filterPosts(this.$i18n),

View File

@ -57,22 +57,18 @@
</ds-flex>
<ds-space />
<ds-flex id="filter-posts-by-followers-header">
<ds-heading tag="h4">
{{
filteredByFollowers ? $t('filter-posts.followers.header') : $t('filter-posts.all.header')
}}
</ds-heading>
<ds-heading tag="h4">{{ $t('filter-posts.general.header') }}</ds-heading>
<ds-space margin-bottom="large" />
</ds-flex>
<ds-flex>
<ds-flex-item
:width="{ base: '100%', sm: '100%', md: '100%', lg: '5%' }"
:width="{ base: '100%', sm: '100%', md: '100%', lg: '10%' }"
class="categories-menu-item"
>
<ds-flex>
<ds-flex-item width="10%" />
<ds-flex-item width="100%">
<div class="filter-menu-buttons">
<div class="follow-button">
<ds-button
v-tooltip="{
content: this.$t('contribution.filterFollow'),
@ -81,14 +77,18 @@
}"
name="filter-by-followed-authors-only"
icon="user-plus"
:primary="!filteredByFollowers"
:primary="filteredByFollowers"
@click="toggleOnlyFollowed"
/>
<ds-flex-item>
<label class="follow-label">{{ $t('filter-posts.followers.label') }}</label>
</ds-flex-item>
<ds-space />
</div>
<ds-space margin-bottom="large" />
</ds-flex-item>
</ds-flex>
</ds-flex-item>
<ds-space margin-bottom="large" />
</ds-flex>
</ds-container>
</template>
@ -132,7 +132,7 @@ export default {
} else if (this.filter.author) {
this.filter.categories_some = { id_in: this.selectedCategoryIds }
} else {
this.filter = { categories_some: { followedBy_some: { id: this.user.id } } }
this.filter = { categories_some: { id_in: this.selectedCategoryIds } }
}
this.$emit('filterPosts', this.filter)
},
@ -167,7 +167,8 @@ export default {
justify-content: center;
}
.category-labels {
.category-labels,
.follow-label {
font-size: $font-size-small;
}
@ -182,5 +183,8 @@ export default {
#filter-posts-header {
text-align: center;
}
.follow-button {
float: left;
}
}
</style>

View File

@ -37,7 +37,12 @@
:class="{ 'hide-mobile-menu': !toggleMobileMenu }"
>
<no-ssr>
<filter-posts placement="top-start" offset="8" :categories="categories" />
<filter-posts
v-show="showFilterPostsDropdown"
placement="top-start"
offset="8"
:categories="categories"
/>
</no-ssr>
</ds-flex-item>
<ds-flex-item :width="{ base: '100%', sm: '100%', md: '10%', lg: '2%' }" />
@ -176,6 +181,7 @@ export default {
isAdmin: 'auth/isAdmin',
quickSearchResults: 'search/quickResults',
quickSearchPending: 'search/quickPending',
showFilterPostsDropdown: 'default/showFilterPostsDropdown',
}),
userName() {
const { name } = this.user || {}

View File

@ -9,11 +9,11 @@
"header": "Themenkategorien",
"all": "Alle"
},
"all": {
"header": "Alle Beiträge des Benutzers"
"general": {
"header": "Filtern nach..."
},
"followers": {
"header": "Die Beiträge meiner Anhänger"
"label": "Benutzern, denen ich folge"
}
},
"site": {

View File

@ -9,11 +9,11 @@
"header": "Categories of Content",
"all": "All"
},
"all": {
"header": "All user's contributions"
"general": {
"header": "Filter by..."
},
"followers": {
"header": "My followers contributions"
"label": "Users I follow"
}
},
"site": {

View File

@ -5,6 +5,7 @@ import Styleguide from '@human-connection/styleguide'
import Filters from '~/plugins/vue-filters'
import VTooltip from 'v-tooltip'
import FilterMenu from '~/components/FilterMenu/FilterMenu'
import { mutations } from '~/store/default'
const localVue = createLocalVue()
@ -41,6 +42,9 @@ describe('PostIndex', () => {
return { id: 'u23' }
},
},
mutations: {
'default/SET_SHOW_FILTER_POSTS_DROPDOWN': mutations.SET_SHOW_FILTER_POSTS_DROPDOWN,
},
})
mocks = {
$t: key => key,
@ -95,11 +99,6 @@ describe('PostIndex', () => {
wrapper = Wrapper()
})
it('refetches Posts when changeFilterBubble is emitted', () => {
wrapper.find(FilterMenu).vm.$emit('changeFilterBubble')
expect(mocks.$apollo.queries.Post.refetch).toHaveBeenCalledTimes(1)
})
it('clears the search when the filter menu emits clearSearch', () => {
wrapper.find(FilterMenu).vm.$emit('clearSearch')
expect(wrapper.vm.hashtag).toBeNull()

View File

@ -2,12 +2,7 @@
<div>
<ds-flex :width="{ base: '100%' }" gutter="base">
<ds-flex-item>
<filter-menu
:user="currentUser"
@changeFilterBubble="changeFilterBubble"
:hashtag="hashtag"
@clearSearch="clearSearch"
/>
<filter-menu :hashtag="hashtag" @clearSearch="clearSearch" />
</ds-flex-item>
<ds-flex-item>
<div class="sorting-dropdown">
@ -97,10 +92,14 @@ export default {
}
},
mounted() {
this.toggleShowFilterPostsDropdown(true)
if (this.hashtag) {
this.changeFilterBubble({ tags_some: { name: this.hashtag } })
}
},
beforeDestroy() {
this.toggleShowFilterPostsDropdown(false)
},
watch: {
Post(post) {
this.setPosts(this.Post)
@ -121,6 +120,7 @@ export default {
methods: {
...mapMutations({
setPosts: 'posts/SET_POSTS',
toggleShowFilterPostsDropdown: 'default/SET_SHOW_FILTER_POSTS_DROPDOWN',
}),
changeFilterBubble(filter) {
if (this.hashtag) {

17
webapp/store/default.js Normal file
View File

@ -0,0 +1,17 @@
export const state = () => {
return {
showFilterPostsDropdown: false,
}
}
export const getters = {
showFilterPostsDropdown(state) {
return state.showFilterPostsDropdown || false
},
}
export const mutations = {
SET_SHOW_FILTER_POSTS_DROPDOWN(state, boolean) {
state.showFilterPostsDropdown = boolean || null
},
}