         @mutateSelection(selection, stopMutation)
       @restoreCursorPositionsIfNecessary()
 
-    @editor.groupChangesSinceCheckpoint(@getBufferCheckpoint('undo'))
+    @groupChangesSinceBufferCheckpoint('undo')
 
     # Even though we fail to select target and fail to mutate,
     # we have to return to normal-mode from operator-pending or visual

      row = cursor.getBufferRow()
      switch @location
        when 'before'
          setTextAtBufferPosition(@editor, [row, 0], text)
        when 'after'
          unless isEndsWithNewLineForBufferRow(@editor, row)
            eol = getEndOfLineForBufferRow(@editor, row)
            range = setTextAtBufferPosition(@editor, eol, "\n" + text.trimRight())
            range.traverse([1, 0], [0, 0])
          else
            setTextAtBufferPosition(@editor, [row + 1, 0], text)
    else
      if @isMode('visual', 'linewise')
        unless selection.getBufferRange().end.column is 0

  getBufferCheckpoint: (purpose) ->
    @bufferCheckpointByPurpose?[purpose]

  deleteBufferCheckpoint: (purpose) ->
    if @bufferCheckpointByPurpose?
      delete @bufferCheckpointByPurpose[purpose]

  groupChangesSinceBufferCheckpoint: (purpose) ->
    console.log "called groupChangesSinceCheckpoint #{purpose}"
    if checkpoint = @getBufferCheckpoint(purpose)
      console.log "checkpoint found: #{purpose}"
      @editor.groupChangesSinceCheckpoint(checkpoint)
    else
      console.log "checkpoint NOT found: #{purpose}"
    @deleteBufferCheckpoint(purpose)

  # Main
  execute: ->
    canMutate = true
