Skip to content

Commit

Permalink
chore(tickets): react update on ticket deleted
Browse files Browse the repository at this point in the history
  • Loading branch information
polonel committed Apr 12, 2019
1 parent b73c353 commit fd20ff2
Show file tree
Hide file tree
Showing 6 changed files with 141 additions and 75 deletions.
5 changes: 4 additions & 1 deletion src/client/actions/tickets.js
Original file line number Diff line number Diff line change
Expand Up @@ -27,14 +27,17 @@ import {
FETCH_TICKETS,
UNLOAD_TICKETS,
TICKET_UPDATED,
DELETE_TICKET
DELETE_TICKET,
TICKET_EVENT
} from 'actions/types'

export const fetchTickets = createAction(FETCH_TICKETS.ACTION)
export const createTicket = createAction(CREATE_TICKET.ACTION)
export const ticketUpdated = createAction(TICKET_UPDATED.ACTION)
export const deleteTicket = createAction(DELETE_TICKET.ACTION)
export const unloadTickets = createAction(UNLOAD_TICKETS.ACTION, payload => payload, () => ({ thunk: true }))
export const ticketEvent = createAction(TICKET_EVENT.ACTION)

export const createTicketType = createAction(CREATE_TICKET_TYPE.ACTION, input => ({ name: input.name }))
export const renameTicketType = createAction(RENAME_TICKET_TYPE.ACTION, input => ({ name: input.name }))
export const deleteTicketType = createAction(DELETE_TICKET_TYPE.ACTION, (id, newTypeId) => ({ id, newTypeId }))
Expand Down
2 changes: 2 additions & 0 deletions src/client/actions/types.js
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,8 @@ export const CREATE_TICKET = defineAction('CREATE_TICKET', [PENDING, SUCCESS, ER
export const DELETE_TICKET = defineAction('DELETE_TICKET', [SUCCESS, PENDING, ERROR])
export const UNLOAD_TICKETS = defineAction('UNLOAD_TICKETS', [SUCCESS])
export const TICKET_UPDATED = defineAction('TICKET_UPDATED', [SUCCESS])
export const TICKET_EVENT = defineAction('TICKET_EVENT', [SUCCESS])

export const CREATE_TICKET_TYPE = defineAction('CREATE_TICKET_TYPE', [SUCCESS, ERROR])
export const RENAME_TICKET_TYPE = defineAction('RENAME_TICKET_TYPE', [SUCCESS, ERROR])
export const DELETE_TICKET_TYPE = defineAction('DELETE_TICKET_TYPE', [SUCCESS, ERROR])
Expand Down
12 changes: 10 additions & 2 deletions src/client/containers/TicketsContainer.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ import { each, without, uniq } from 'lodash'

import Log from '../logger'
import axios from 'axios'
import { fetchTickets, deleteTicket, unloadTickets, ticketUpdated } from 'actions/tickets'
import { fetchTickets, deleteTicket, ticketEvent, unloadTickets, ticketUpdated } from 'actions/tickets'
import { showModal } from 'actions/common'

import PageTitle from 'components/PageTitle'
Expand Down Expand Up @@ -48,9 +48,11 @@ class TicketsContainer extends React.Component {
super(props)

this.onTicketUpdated = this.onTicketUpdated.bind(this)
this.onTicketDeleted = this.onTicketDeleted.bind(this)
}
componentDidMount () {
socket.socket.on('$trudesk:client:ticket:updated', this.onTicketUpdated)
socket.socket.on('$trudesk:client:ticket:deleted', this.onTicketDeleted)

this.props.fetchTickets({ limit: 50, page: this.props.page, type: this.props.view })
}
Expand Down Expand Up @@ -85,12 +87,17 @@ class TicketsContainer extends React.Component {
this.timeline = null
this.props.unloadTickets()
socket.socket.off('$trudesk:client:ticket:updated', this.onTicketUpdated)
socket.socket.off('$trudesk:client:ticket:deleted', this.onTicketDeleted)
}

onTicketUpdated (data) {
this.props.ticketUpdated(data)
}

onTicketDeleted (id) {
this.props.ticketEvent({ type: 'deleted', data: id })
}

onTicketCheckChanged (e, id) {
if (e.target.checked) this.selectedTickets.push(id)
else this.selectedTickets = without(this.selectedTickets, id)
Expand Down Expand Up @@ -341,6 +348,7 @@ TicketsContainer.propTypes = {
loading: PropTypes.bool.isRequired,
fetchTickets: PropTypes.func.isRequired,
deleteTicket: PropTypes.func.isRequired,
ticketEvent: PropTypes.func.isRequired,
unloadTickets: PropTypes.func.isRequired,
ticketUpdated: PropTypes.func.isRequired,
showModal: PropTypes.func.isRequired,
Expand All @@ -361,5 +369,5 @@ const mapStateToProps = state => ({

export default connect(
mapStateToProps,
{ fetchTickets, deleteTicket, unloadTickets, ticketUpdated, showModal }
{ fetchTickets, deleteTicket, ticketEvent, unloadTickets, ticketUpdated, showModal }
)(TicketsContainer)
29 changes: 28 additions & 1 deletion src/client/reducers/ticketsReducer.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,14 @@
import { fromJS, List } from 'immutable'
import { handleActions } from 'redux-actions'
import isUndefined from 'lodash/isUndefined'
import { CREATE_TICKET, FETCH_TICKETS, TICKET_UPDATED, UNLOAD_TICKETS, DELETE_TICKET } from 'actions/types'
import {
CREATE_TICKET,
FETCH_TICKETS,
TICKET_UPDATED,
UNLOAD_TICKETS,
DELETE_TICKET,
TICKET_EVENT
} from 'actions/types'

const initialState = {
tickets: List([]),
Expand Down Expand Up @@ -106,6 +113,26 @@ const reducer = handleActions(
}
},

[TICKET_EVENT.SUCCESS]: (state, action) => {
const type = action.payload.type
switch (type) {
case 'deleted': {
const id = action.payload.data
const idx = state.tickets.findIndex(ticket => {
return ticket.get('_id') === id
})
return {
...state,
tickets: state.tickets.delete(idx)
}
}
default:
return {
...state
}
}
},

[TICKET_UPDATED.SUCCESS]: (state, action) => {
const ticket = action.payload.ticket
const inView = hasInView(
Expand Down
13 changes: 12 additions & 1 deletion src/client/sagas/tickets/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,8 @@ import {
FETCH_TICKETS,
UNLOAD_TICKETS,
TICKET_UPDATED,
DELETE_TICKET
DELETE_TICKET,
TICKET_EVENT
} from 'actions/types'

import helpers from 'lib/helpers'
Expand Down Expand Up @@ -97,6 +98,15 @@ function * ticketUpdated ({ payload }) {
}
}

function * ticketEvent ({ payload }) {
try {
const sessionUser = yield select(getSessionUser)
yield put({ type: TICKET_EVENT.SUCCESS, payload, sessionUser })
} catch (error) {
Log.error(error)
}
}

function * createTicketType ({ payload }) {
try {
const response = yield call(api.tickets.createTicketType, payload)
Expand Down Expand Up @@ -200,6 +210,7 @@ export default function * watcher () {
yield takeEvery(DELETE_TICKET.ACTION, deleteTicket)
yield takeLatest(UNLOAD_TICKETS.ACTION, unloadThunk)
yield takeEvery(TICKET_UPDATED.ACTION, ticketUpdated)
yield takeEvery(TICKET_EVENT.ACTION, ticketEvent)
yield takeLatest(CREATE_TICKET_TYPE.ACTION, createTicketType)
yield takeLatest(DELETE_TICKET_TYPE.ACTION, deleteTicketType)
yield takeLatest(CREATE_PRIORITY.ACTION, createPriority)
Expand Down
155 changes: 85 additions & 70 deletions src/emitter/events.js
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ var util = require('../helpers/utils')
var templateSchema = require('../models/template')
var ticketSchema = require('../models/ticket')
var userSchema = require('../models/user')
var departmentSchema = require('../models/department')
var NotificationSchema = require('../models/notification')
var settingsSchema = require('../models/setting')
var Email = require('email-templates')
Expand Down Expand Up @@ -64,83 +65,96 @@ var notifications = require('../notifications') // Load Push Events
function (c) {
var mailer = require('../mailer')
var emails = []
async.each(
ticket.group.sendMailTo,
function (member, cb) {
if (_.isUndefined(member.email)) return cb()
if (member.deleted) return cb()

emails.push(member.email)
departmentSchema.getDepartmentsByGroup(ticket.group._id, function (err, departments) {
if (err) return c(err)

return cb()
},
function (err) {
if (err) return c(err)

emails = _.uniq(emails)

var email = null
if (betaEnabled) {
email = new Email({
// views: {
// root: templateDir,
// options: {
// extension: 'handlebars'
// }
// }
render: function (view, locals) {
return new Promise(function (resolve, reject) {
if (!global.Handlebars) return reject(new Error('Could not load global.Handlebars'))
templateSchema.findOne({ name: view }, function (err, template) {
if (err) return reject(err)
if (!template) return reject(new Error('Invalid Template'))
var html = global.Handlebars.compile(template.data['gjs-fullHtml'])(locals)
email.juiceResources(html).then(resolve)
})
})
}
})
} else {
email = new Email({
views: {
root: templateDir,
options: {
extension: 'handlebars'
}
}
var members = _.flattenDeep(
departments.map(function (department) {
return department.teams.map(function (team) {
return team.members.map(function (member) {
return member
})
})
}
templateSchema.findOne({ name: 'new-ticket' }, function (err, template) {
})
)

members = _.uniqBy(members, function (i) {
return i._id
})

async.each(
members,
function (member, cb) {
if (_.isUndefined(member.email)) return cb()
if (member.deleted) return cb()

emails.push(member.email)

return cb()
},
function (err) {
if (err) return c(err)
if (!template) return c()

var context = { base_url: baseUrl, ticket: ticket }

email
.render('new-ticket', context)
.then(function (html) {
var subjectParsed = global.HandleBars.compile(template.subject)(context)
var mailOptions = {
to: emails.join(),
subject: subjectParsed,
html: html,
generateTextFromHTML: true
}

mailer.sendMail(mailOptions, function (err) {
if (err) winston.warn('[trudesk:events:ticket:created] - ' + err)
})
})
.catch(function (err) {
winston.warn('[trudesk:events:ticket:created] - ' + err)
return c(err)
emails = _.uniq(emails)

var email = null
if (betaEnabled) {
email = new Email({
render: function (view, locals) {
return new Promise(function (resolve, reject) {
if (!global.Handlebars) return reject(new Error('Could not load global.Handlebars'))
templateSchema.findOne({ name: view }, function (err, template) {
if (err) return reject(err)
if (!template) return reject(new Error('Invalid Template'))
var html = global.Handlebars.compile(template.data['gjs-fullHtml'])(locals)
email.juiceResources(html).then(resolve)
})
})
}
})
.finally(function () {
return c()
} else {
email = new Email({
views: {
root: templateDir,
options: {
extension: 'handlebars'
}
}
})
})
}
)
}
templateSchema.findOne({ name: 'new-ticket' }, function (err, template) {
if (err) return c(err)
if (!template) return c()

var context = { base_url: baseUrl, ticket: ticket }

email
.render('new-ticket', context)
.then(function (html) {
var subjectParsed = global.HandleBars.compile(template.subject)(context)
var mailOptions = {
to: emails.join(),
subject: subjectParsed,
html: html,
generateTextFromHTML: true
}

mailer.sendMail(mailOptions, function (err) {
if (err) winston.warn('[trudesk:events:ticket:created] - ' + err)
})
})
.catch(function (err) {
winston.warn('[trudesk:events:ticket:created] - ' + err)
return c(err)
})
.finally(function () {
return c()
})
})
}
)
})
},
function (c) {
if (!ticket.group.public) return c()
Expand Down Expand Up @@ -327,6 +341,7 @@ var notifications = require('../notifications') // Load Push Events

emitter.on('ticket:deleted', function (oId) {
io.sockets.emit('ticket:delete', oId)
io.sockets.emit('$trudesk:client:ticket:deleted', oId)
})

emitter.on('ticket:subscriber:update', function (data) {
Expand Down

0 comments on commit fd20ff2

Please sign in to comment.