2014-04-08 19:26:19 -07:00
Patch = require ( ' ./Patch ' )
2014-04-17 17:09:01 -07:00
User = require ' ../users/User '
2014-04-08 19:26:19 -07:00
Handler = require ( ' ../commons/Handler ' )
2014-04-12 10:51:02 -07:00
schema = require ' ../../app/schemas/models/patch '
2014-04-08 19:26:19 -07:00
{ handlers } = require ' ../commons/mapping '
mongoose = require ( ' mongoose ' )
2014-04-17 17:09:01 -07:00
log = require ' winston '
sendwithus = require ' ../sendwithus '
2014-04-08 19:26:19 -07:00
PatchHandler = class PatchHandler extends Handler
modelClass: Patch
editableProperties: [ ]
2014-04-10 13:09:44 -07:00
postEditableProperties: [ ' delta ' , ' target ' , ' commitMessage ' ]
2014-04-12 10:51:02 -07:00
jsonSchema: require ' ../../app/schemas/models/patch '
2014-04-08 19:26:19 -07:00
makeNewInstance: (req) ->
patch = super ( req )
patch . set ' creator ' , req . user . _id
patch . set ' created ' , new Date ( ) . toISOString ( )
patch . set ' status ' , ' pending '
patch
getByRelationship: (req, res, args...) ->
return @ setStatus ( req , res , args [ 0 ] ) if req . route . method is ' put ' and args [ 1 ] is ' status '
super ( arguments . . . )
setStatus: (req, res, id) ->
newStatus = req . body . status
unless newStatus in [ ' rejected ' , ' accepted ' , ' withdrawn ' ]
return @ sendBadInputError ( res , " Status must be ' rejected ' , ' accepted ' , or ' withdrawn ' " )
@ getDocumentForIdOrSlug id , (err, patch) =>
return @ sendDatabaseError ( res , err ) if err
return @ sendNotFoundError ( res ) unless patch ?
targetInfo = patch . get ( ' target ' )
targetHandler = require ( ' ../ ' + handlers [ targetInfo . collection ] )
targetModel = targetHandler . modelClass
query = { ' original ' : targetInfo . original }
sort = { ' version.major ' : - 1 , ' version.minor ' : - 1 }
targetModel . findOne ( query ) . sort ( sort ) . exec (err, target) =>
return @ sendDatabaseError ( res , err ) if err
return @ sendNotFoundError ( res ) unless target ?
return @ sendUnauthorizedError ( res ) unless targetHandler . hasAccessToDocument ( req , target , ' get ' )
if newStatus in [ ' rejected ' , ' accepted ' ]
return @ sendUnauthorizedError ( res ) unless targetHandler . hasAccessToDocument ( req , target , ' put ' )
if newStatus is ' withdrawn '
return @ sendUnauthorizedError ( res ) unless req . user . get ( ' _id ' ) . equals patch . get ( ' creator ' )
# these require callbacks
patch . update { $set : { status : newStatus } } , { } , ->
target . update { $pull : { patches : patch . get ( ' _id ' ) } } , { } , ->
@ sendSuccess ( res , null )
2014-04-17 17:09:01 -07:00
onPostSuccess: (req, doc) ->
log . error " Error sending patch created: could not find the loaded target on the patch object. " unless doc . targetLoaded
return unless doc . targetLoaded
2014-04-17 17:30:55 -07:00
watchers = doc . targetLoaded . get ( ' watchers ' ) or [ ]
watchers = ( w for w in watchers when not w . equals ( editor . get ( ' _id ' ) ) )
2014-04-17 17:09:01 -07:00
return unless watchers ? . length
User . find ( { _id : { $in : watchers } } ) . select ( { email : 1 , name : 1 } ) . exec (err, watchers) =>
for watcher in watchers
@ sendPatchCreatedEmail req . user , watcher , doc , doc . targetLoaded , req . body . editPath
2014-04-08 19:26:19 -07:00
2014-04-17 17:09:01 -07:00
sendPatchCreatedEmail: (patchCreator, watcher, patch, target, editPath) ->
# return if watcher._id is patchCreator._id
context =
email_id: sendwithus . templates . patch_created
recipient:
address: watcher . get ( ' email ' )
name: watcher . get ( ' name ' )
email_data:
doc_name: target . get ( ' name ' ) or ' ??? '
submitter_name: patchCreator . get ( ' name ' ) or ' ??? '
doc_link: " http://codecombat.com #{ editPath } "
commit_message: patch . get ( ' commitMessage ' )
sendwithus . api . send context , (err, result) ->
2014-04-08 19:26:19 -07:00
module.exports = new PatchHandler ( )