SafeExecTests.js 3.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105
  1. const chai = require('chai')
  2. const should = chai.should()
  3. const { expect } = chai
  4. const modulePath = '../../../app/js/SafeExec'
  5. const SandboxedModule = require('sandboxed-module')
  6. describe('SafeExec', function() {
  7. let settings, options, safeExec
  8. beforeEach(function() {
  9. settings = { enableConversions: true }
  10. options = { timeout: 10 * 1000, killSignal: 'SIGTERM' }
  11. safeExec = SandboxedModule.require(modulePath, {
  12. requires: {
  13. 'settings-sharelatex': settings
  14. }
  15. })
  16. })
  17. describe('safeExec', function() {
  18. it('should execute a valid command', function(done) {
  19. safeExec(['/bin/echo', 'hello'], options, (err, stdout, stderr) => {
  20. stdout.should.equal('hello\n')
  21. stderr.should.equal('')
  22. should.not.exist(err)
  23. done()
  24. })
  25. })
  26. it('should error when conversions are disabled', function(done) {
  27. settings.enableConversions = false
  28. safeExec(['/bin/echo', 'hello'], options, err => {
  29. expect(err).to.exist
  30. done()
  31. })
  32. })
  33. it('should execute a command with non-zero exit status', function(done) {
  34. safeExec(['/usr/bin/env', 'false'], options, err => {
  35. expect(err).to.exist
  36. expect(err.name).to.equal('FailedCommandError')
  37. expect(err.code).to.equal(1)
  38. expect(err.stdout).to.equal('')
  39. expect(err.stderr).to.equal('')
  40. done()
  41. })
  42. })
  43. it('should handle an invalid command', function(done) {
  44. safeExec(['/bin/foobar'], options, err => {
  45. err.code.should.equal('ENOENT')
  46. done()
  47. })
  48. })
  49. it('should handle a command that runs too long', function(done) {
  50. safeExec(
  51. ['/bin/sleep', '10'],
  52. { timeout: 500, killSignal: 'SIGTERM' },
  53. err => {
  54. expect(err).to.exist
  55. expect(err.name).to.equal('FailedCommandError')
  56. expect(err.code).to.equal('SIGTERM')
  57. done()
  58. }
  59. )
  60. })
  61. })
  62. describe('as a promise', function() {
  63. beforeEach(function() {
  64. safeExec = safeExec.promises
  65. })
  66. it('should execute a valid command', async function() {
  67. const { stdout, stderr } = await safeExec(['/bin/echo', 'hello'], options)
  68. stdout.should.equal('hello\n')
  69. stderr.should.equal('')
  70. })
  71. it('should throw a ConversionsDisabledError when appropriate', async function() {
  72. settings.enableConversions = false
  73. try {
  74. await safeExec(['/bin/echo', 'hello'], options)
  75. } catch (err) {
  76. expect(err.name).to.equal('ConversionsDisabledError')
  77. return
  78. }
  79. expect('method did not throw an error').not.to.exist
  80. })
  81. it('should throw a FailedCommandError when appropriate', async function() {
  82. try {
  83. await safeExec(['/usr/bin/env', 'false'], options)
  84. } catch (err) {
  85. expect(err.name).to.equal('FailedCommandError')
  86. expect(err.code).to.equal(1)
  87. return
  88. }
  89. expect('method did not throw an error').not.to.exist
  90. })
  91. })
  92. })