warningReviewAction.test.mjs 4.7 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495
  1. import test from 'node:test'
  2. import assert from 'node:assert/strict'
  3. import { readFileSync } from 'node:fs'
  4. import { computed, nextTick, reactive, ref } from 'vue'
  5. import { parse } from '@vue/compiler-sfc'
  6. import AsyncValidator from 'async-validator'
  7. const read = path => readFileSync(new URL(path, import.meta.url), 'utf8')
  8. const script = parse(read('../src/views/subSystem/lifeCompany/components/WarningReviewAction.vue')).descriptor.scriptSetup.content
  9. .replace(/^import .*\r?\n/gm, '')
  10. const workflowSource = read('../src/views/subSystem/lifeCompany/warningWorkflow.js')
  11. const workflowActions = new Function(`${workflowSource.slice(workflowSource.indexOf('export function workflowActions')).replace('export ', '')}; return workflowActions`)()
  12. const Validator = AsyncValidator.default || AsyncValidator
  13. // Execute the component's setup with real Vue reactivity and the form validator;
  14. // replace only browser stores, messages and network requests.
  15. function setup({ permission = 'warning:warning:audit', row = {}, request } = {}) {
  16. const user = reactive({ name: 'reviewer', permissions: [permission] })
  17. const props = reactive({ row: { warningId: 'w1', status: 'HANDLED', handler: 'handler', reviewer: 'reviewer', ...row } })
  18. const calls = [], messages = [], events = []
  19. const api = kind => async data => {
  20. calls.push({ kind, data })
  21. return request ? request() : { code: 200 }
  22. }
  23. const auth = new Function('useUserStore', read('../src/plugins/auth.js')
  24. .replace(/^import .*\r?\n/gm, '').replace('export default', 'return'))(() => user)
  25. const factory = new Function('computed', 'nextTick', 'reactive', 'ref', 'ElMessage', 'auth', 'useUserStore',
  26. 'clearWarningData', 'returnWarningData', 'workflowActions', 'defineProps', 'defineEmits',
  27. `${script}; return { canReview, visible, busy, formRef, form, rules, open, submit, close }`)
  28. const state = factory(computed, nextTick, reactive, ref,
  29. { success: text => messages.push(text), error: text => messages.push(text), warning: text => messages.push(text) },
  30. auth, () => user, api('clear'), api('return'), workflowActions, () => props, () => event => events.push(event))
  31. state.formRef.value = { clearValidate() {}, validate: () => new Validator(state.rules).validate(state.form).then(() => true) }
  32. return { ...state, user, props, calls, messages, events }
  33. }
  34. test('核验仅对指定核验人、已处置状态及核验权限开放,处置权限不能替代', () => {
  35. assert.equal(setup().canReview.value, true)
  36. assert.equal(setup({ permission: 'warning:warning:handle' }).canReview.value, false)
  37. assert.equal(setup({ row: { reviewer: 'someone-else' } }).canReview.value, false)
  38. assert.equal(setup({ permission: '*:*:*', row: { reviewer: 'someone-else' } }).canReview.value, false)
  39. assert.equal(setup({ row: { status: 'PROCESSING' } }).canReview.value, false)
  40. assert.equal(setup({ row: { todo_type: 'DONE' } }).canReview.value, false)
  41. assert.equal(setup({ row: { reviewer: '', publisher: 'reviewer' } }).canReview.value, true)
  42. })
  43. test('每次打开清空结果和意见,未选结果或空白意见不能提交', async () => {
  44. const s = setup()
  45. await s.open()
  46. assert.equal(s.form.result, '')
  47. await s.submit()
  48. s.form.result = 'CLEAR'
  49. s.form.opinion = ' '
  50. await s.submit()
  51. assert.deepEqual(s.calls, [])
  52. s.form.opinion = '旧意见'
  53. await s.open()
  54. assert.deepEqual({ ...s.form }, { result: '', opinion: '' })
  55. })
  56. test('核查解除与退回办理分别调用既有接口,成功后关闭并刷新', async () => {
  57. for (const [result, kind, field] of [['CLEAR', 'clear', 'clearRemark'], ['RETURN', 'return', 'disposalContent']]) {
  58. const s = setup()
  59. await s.open()
  60. s.form.result = result
  61. s.form.opinion = ' 核验意见 '
  62. await s.submit()
  63. assert.deepEqual(s.calls, [{ kind, data: { warningId: 'w1', [field]: '核验意见' } }])
  64. assert.equal(s.visible.value, false)
  65. assert.deepEqual(s.events, ['changed'])
  66. }
  67. })
  68. test('接口失败保留表单,提交期间禁止重复提交或关闭', async () => {
  69. let resolveRequest
  70. const s = setup({ request: () => new Promise(resolve => { resolveRequest = resolve }) })
  71. await s.open()
  72. s.form.result = 'RETURN'
  73. s.form.opinion = '需要补充处置'
  74. const first = s.submit()
  75. await nextTick()
  76. await new Promise(resolve => setImmediate(resolve))
  77. assert.equal(s.busy.value, true)
  78. await s.submit()
  79. let closed = false
  80. s.close(() => { closed = true })
  81. assert.equal(closed, false)
  82. assert.equal(s.calls.length, 1)
  83. resolveRequest({ code: 500, msg: '状态已经改变' })
  84. await first
  85. assert.equal(s.busy.value, false)
  86. assert.equal(s.visible.value, true)
  87. assert.equal(s.form.opinion, '需要补充处置')
  88. assert.deepEqual(s.events, [])
  89. })