diff --git a/client/coral-framework/store/actions/items.js b/client/coral-framework/store/actions/items.js index c292426d1..e51e1573e 100644 --- a/client/coral-framework/store/actions/items.js +++ b/client/coral-framework/store/actions/items.js @@ -24,13 +24,14 @@ export const APPEND_ITEM_ARRAY = 'APPEND_ITEM_ARRAY' * */ -export const addItem = (item) => { +export const addItem = (item, item_type) => { if (!item.id) { console.warn('addItem called without an item id.') } return { type: ADD_ITEM, - item: item, + item, + item_type, id: item.id } } @@ -47,22 +48,24 @@ export const addItem = (item) => { */ -export const updateItem = (id, property, value) => { +export const updateItem = (id, property, value, item_type) => { return { type: UPDATE_ITEM, id, property, - value + value, + item_type } } -export const appendItemArray = (id, property, value, addToFront) => { +export const appendItemArray = (id, property, value, add_to_front, item_type) => { return { type: APPEND_ITEM_ARRAY, id, property, value, - addToFront + add_to_front, + item_type } } @@ -93,7 +96,7 @@ export function getStream (assetId) { const itemTypes = Object.keys(json); for (let i=0; i < itemTypes.length; i++ ) { for (var j=0; j < json[itemTypes[i]].length; j++ ) { - dispatch(addItem(json[itemTypes[i]][j])); + dispatch(addItem(json[itemTypes[i]][j], itemTypes[i])); } } @@ -118,18 +121,18 @@ export function getStream (assetId) { dispatch(addItem({ id: assetId, - comments: rootComments - })) + comments: rootComments, + }, 'assets')) const childKeys = Object.keys(childComments) for (var i=0; i < childKeys.length; i++ ) { - dispatch(updateItem(childKeys[i], 'children', childComments[childKeys[i]].reverse())) + dispatch(updateItem(childKeys[i], 'children', childComments[childKeys[i]].reverse(), 'comments')) } /* Hydrate actions on comments */ const actions = Object.keys(json.actions) for (var i=0; i < actions.length; i++ ) { - dispatch(updateItem(actions[i].item_id, actions[i].type, actions[i].id)) + dispatch(updateItem(actions[i].item_id, actions[i].type, actions[i].id, 'actions')) } return (json) @@ -195,7 +198,6 @@ export function postItem (item, type, id) { 'Content-Type':'application/json' } } - console.log('postItem', options); return fetch('/api/v1/' + type, options) .then( response => { @@ -204,7 +206,7 @@ export function postItem (item, type, id) { } ) .then((json) => { - dispatch(addItem({...item, id:json.id})) + dispatch(addItem({...item, id:json.id}, type)) return json.id }) } @@ -227,7 +229,7 @@ export function postItem (item, type, id) { * */ -export function postAction (id, type, user_id) { +export function postAction (item_id, type, user_id) { return (dispatch) => { const action = { type, @@ -238,13 +240,14 @@ export function postAction (id, type, user_id) { body: JSON.stringify(action) } - dispatch(appendItemArray(id, type, user_id)) - return fetch('/api/v1/comments/' + id + '/actions', options) + return fetch('/api/v1/comments/' + item_id + '/actions', options) .then( response => { - return response.ok ? response.text() + return response.ok ? response.json() : Promise.reject(response.status + ' ' + response.statusText) } - ) + ).then((json)=>{ + return json.id + }) } } diff --git a/client/coral-framework/store/reducers/items.js b/client/coral-framework/store/reducers/items.js index d3eb4d3af..d1fcd6b43 100644 --- a/client/coral-framework/store/reducers/items.js +++ b/client/coral-framework/store/reducers/items.js @@ -3,26 +3,23 @@ import { Map, fromJS } from 'immutable' import * as actions from '../actions/items' -const initialState = fromJS({}) +const initialState = Map({}); export default (state = initialState, action) => { switch (action.type) { case actions.ADD_ITEM: - return state.set(action.id, fromJS(action.item)) + return state.setIn([action.item_type, action.id], fromJS(action.item)); case actions.UPDATE_ITEM: - return state.updateIn([action.id, action.property], () => - fromJS(action.value) - ) + return state.setIn([action.item_type, action.id, action.property], fromJS(action.value)); case actions.APPEND_ITEM_ARRAY: - return state.updateIn([action.id, action.property], (prop) => { - if (action.addToFront) { - return prop ? prop.unshift(action.value) : fromJS([action.value]) + return state.updateIn([action.item_type, action.id, action.property], (prop) => { + console.log(prop); + if (action.add_to_front) { + return prop ? prop.unshift(fromJS(action.value)) : fromJS([action.value]); } else { - return prop ? prop.push(action.value) : fromJS([action.value]) + return prop ? prop.push(fromJS(action.value)) : fromJS([action.value]); } - - } - ) + }); default: return state } diff --git a/tests/client/coral-framework/store/itemActions.spec.js b/tests/client/coral-framework/store/itemActions.spec.js index 124174f36..360f6b79a 100644 --- a/tests/client/coral-framework/store/itemActions.spec.js +++ b/tests/client/coral-framework/store/itemActions.spec.js @@ -11,74 +11,88 @@ const mockStore = configureStore() describe('itemActions', () => { let store - const host = 'http://test.host' beforeEach(() => { store = mockStore(new Map({})) fetchMock.restore() }) - describe('getItemsQuery', () => { - const query = 'all' - const rootId = '1234' - const view = 'testView' - const response = {results: [ - {Docs: [ - {type: 'comment', data: {content: 'stuff'}, item_id: '123'}, - {type: 'comment', data: {content: 'morestuff'}, item_id: '456'} - ]} - ]} + describe('getStream', () => { + const rootId = '1234'; + const response = { + comments: [ + { body: 'stuff', id: '123'}, + { body: 'morestuff', id: '456'} + ], + actions: [ + { + type: 'like', + id: '123', + count: 1, + current_user: false + }, + { + type: 'flag', + id: '456', + count: 5, + current_user: true + } + ] + }; - it('should get an item from a query and send the appropriate dispatches', () => { - fetchMock.get('*', JSON.stringify(response)) - return actions.getItemsQuery(query, rootId, view, host)(store.dispatch) + it('should get an stream from an asset_id and send the appropriate dispatches', () => { + fetchMock.get('*', JSON.stringify(response)); + return actions.getStream(rootId)(store.dispatch) .then((res) => { - expect(fetchMock.calls().matched[0][0]).to.equal('http://test.host/v1/exec/all/view/testView/1234') - expect(res).to.deep.equal(response.results[0].Docs) + expect(fetchMock.calls().matched[0][0]).to.equal('/api/v1/stream?asset_id=1234') + expect(res).to.deep.equal(response); expect(store.getActions()[0]).to.deep.equal({ type: actions.ADD_ITEM, - item: response.results[0].Docs[0], - item_id: '123' - }) + item: response.comments[0], + item_type: 'comments', + id: '123' + }); expect(store.getActions()[1]).to.deep.equal({ type: actions.ADD_ITEM, - item: response.results[0].Docs[1], - item_id: '456' - }) - }) + item: response.comments[1], + item_type: 'comments', + id: '456' + }); + }); }) it('should handle an error', () => { fetchMock.get('*', 404) - return actions.getItemsQuery(query, rootId, view, host)(store.dispatch) + return actions.getStream(rootId)(store.dispatch) .catch((err) => { - expect(err).to.be.truthy - }) - }) - }) + expect(err).to.be.truthy; + }); + }); + }); - describe('getItemsArray', () => { - const response = {items: [{type: 'comment', item_id: '123'}, {type: 'comment', item_id: '456'}]} + //Disabling tests for this function until is is used again. + xdescribe('getItemsArray', () => { + const response = {items: [{type: 'comment', id: '123'}, {type: 'comment', id: '456'}]} const ids = [1, 2] it('should get an item from an array of ids and send the appropriate dispatches', () => { fetchMock.get('*', JSON.stringify(response)) - return actions.getItemsArray(ids, host)(store.dispatch) + return actions.getItemsArray(ids)(store.dispatch) .then((res) => { expect(res).to.deep.equal(response.items) expect(store.getActions()[0]).to.deep.equal({ type: actions.ADD_ITEM, item: { type: 'comment', - item_id: '123' + id: '123' }, - item_id: '123' + id: '123' }) expect(store.getActions()[1]).to.deep.equal({ type: actions.ADD_ITEM, item: { - type: 'comment', item_id: '456' + type: 'comment', id: '456' }, - item_id: '456' + id: '456' }) }) }) @@ -93,37 +107,38 @@ describe('itemActions', () => { describe('postItem', () => { const item = { - type: 'comment', - data:{content: 'stuff'} + type: 'comments', + data: {body: 'stuff'} } it ('should post an item, return an id, then dispatch that item to the store', () => { - fetchMock.post('*', {item_id: '123', type: 'comment', data: {content: 'stuff'}}) - return actions.postItem(item.data, item.type, undefined, host)(store.dispatch) + fetchMock.post('*', {id: '123'}) + return actions.postItem(item.data, item.type, undefined)(store.dispatch) .then((id) => { expect(fetchMock.calls().matched[0][1]).to.deep.equal( { method: 'POST', - body: JSON.stringify({...item, version: 1}) + headers: { + 'Content-Type':'application/json' + }, + body: JSON.stringify(item.data) } ) expect(id).to.equal('123') expect(store.getActions()[0]).to.deep.equal({ type: actions.ADD_ITEM, item: { - type: 'comment', - data: { - content: 'stuff' - }, - item_id: '123' + body: 'stuff', + id: '123' }, - item_id: '123' + item_type: 'comments', + id: '123' }) }) }) it('should handle an error', () => { fetchMock.post('*', 404) - return actions.postItem(item, host)(store.dispatch) + return actions.postItem(item)(store.dispatch) .catch((err) => { expect(err).to.be.truthy }) @@ -132,17 +147,26 @@ describe('itemActions', () => { describe('postAction', () => { it ('should post an action', () => { - fetchMock.post('*', 200) - return actions.postAction('abc', 'flag', '123', host)(store.dispatch) + fetchMock.post('*', {id: '456'}) + return actions.postAction('abc', 'flag', '123')(store.dispatch) .then(response => { - expect(fetchMock.calls().matched[0][0]).to.equal('http://test.host/v1/action/flag/user/123/on/item/abc') - expect(response).to.equal('') + expect(fetchMock.calls().matched[0][0]).to.equal('/api/v1/comments/abc/actions') + expect(response).to.equal('456') + // expect(store.getActions()[0]).to.deep.equal({ + // type: actions.ADD_ITEM, + // item: { + // type: 'flag', + // item_id: 'abc', + // id: '123' + // }, + // id: '123' + // }) }) }) it('should handle an error', () => { fetchMock.post('*', 404) - return actions.postItem('abc', 'flag', '123', host)(store.dispatch) + return actions.postAction('abc', 'flag', '123')(store.dispatch) .catch((err) => { expect(err).to.be.truthy }) diff --git a/tests/client/coral-framework/store/itemReducer.spec.js b/tests/client/coral-framework/store/itemReducer.spec.js index bd7b74b6c..97482137c 100644 --- a/tests/client/coral-framework/store/itemReducer.spec.js +++ b/tests/client/coral-framework/store/itemReducer.spec.js @@ -9,22 +9,17 @@ describe ('itemsReducer', () => { const action = { type: 'ADD_ITEM', item: { - type: 'comment', - data: { - content: 'stuff' - }, - item_id: '123' + body: 'stuff', + id: '123' }, - item_id: '123' + item_type: 'comments', + id: '123' } const store = new Map({}) const result = itemsReducer(store, action) - expect(result.get('123').toJS()).to.deep.equal({ - type: 'comment', - data: { - content: 'stuff' - }, - item_id: '123' + expect(result.getIn(['comments','123']).toJS()).to.deep.equal({ + body: 'stuff', + id: '123' }) }) }) @@ -35,22 +30,21 @@ describe ('itemsReducer', () => { type: 'UPDATE_ITEM', property: 'stuff', value: 'things', - item_id: '123' + item_type: 'comments', + id: '123' } const store = fromJS({ - '123': { - item_id: '123', - data: { + 'comments': { + '123': { + id: '123', stuff: 'morestuff' } } - }) + }); const result = itemsReducer(store, action) - expect(result.get('123').toJS()).to.deep.equal({ - item_id: '123', - data: { - stuff: 'things' - } + expect(result.getIn(['comments','123']).toJS()).to.deep.equal({ + id: '123', + stuff: 'things' }) }) }) @@ -64,12 +58,13 @@ describe ('itemsReducer', () => { type: 'APPEND_ITEM_ARRAY', property: 'stuff', value: 'things', - item_id: '123' + id: '123', + item_type: 'comments' } store = fromJS({ - '123': { - item_id: '123', - data: { + 'comments': { + '123': { + id: '123', stuff: ['morestuff'] } } @@ -77,73 +72,25 @@ describe ('itemsReducer', () => { }) it ('should append to an existing array', () => { const result = itemsReducer(store, action) - expect(result.get('123').toJS()).to.deep.equal({ - item_id: '123', - data: { - stuff: ['morestuff', 'things'] - } + expect(result.getIn(['comments','123']).toJS()).to.deep.equal({ + id: '123', + stuff: ['morestuff', 'things'] }) }) it ('should create a new array', () => { store = fromJS({ - '123': { - item_id: '123', - data: {} - } - }) - const result = itemsReducer(store, action) - expect(result.get('123').toJS()).to.deep.equal({ - item_id: '123', - data: { - stuff: ['things'] - } - }) - }) - }) - - describe('APPEND_ITEM_RELATED', () => { - let action - let store - - beforeEach (() => { - action = { - type: 'APPEND_ITEM_RELATED', - property: 'stuff', - value: 'things', - item_id: '123' - } - store = fromJS({ - '123': { - item_id: '123', - related: { - stuff: ['morestuff'] + 'comments': { + '123': { + id: '123' } } }) - }) - it ('should append to an existing array', () => { const result = itemsReducer(store, action) - expect(result.get('123').toJS()).to.deep.equal({ - item_id: '123', - related: { - stuff: ['morestuff', 'things'] - } - }) - }) - it ('should create a new array', () => { - store = fromJS({ - '123': { - item_id: '123', - related: {} - } - }) - const result = itemsReducer(store, action) - expect(result.get('123').toJS()).to.deep.equal({ - item_id: '123', - related: { - stuff: ['things'] - } + expect(result.getIn(['comments','123']).toJS()).to.deep.equal({ + id: '123', + stuff: ['things'] }) }) }) + })