abstractMenuBuilder.test.ts 5.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230
  1. import { describe, test, expect, vi, beforeEach } from 'vitest'
  2. import type { RuntimeConfig } from '@nuxt/schema'
  3. import type { AnyAbility } from '@casl/ability'
  4. import type { Router } from 'vue-router'
  5. import AbstractMenuBuilder from '~/services/layout/menuBuilder/abstractMenuBuilder'
  6. import type { IconItem, MenuGroup, MenuItem, MenuItems } from '~/types/layout'
  7. import { MENU_LINK_TYPE } from '~/types/enum/layout'
  8. import type { AccessProfile, organizationState } from '~/types/interfaces'
  9. class TestableAbstractMenuBuilder extends AbstractMenuBuilder {
  10. static readonly menuName = 'TestableMenu'
  11. public build(): MenuItem | MenuGroup | null {
  12. return { label: 'my_menu' }
  13. }
  14. public createGroup(
  15. label: string,
  16. icon?: IconItem,
  17. children: MenuItems = [],
  18. actions: Array<MenuItem> = [],
  19. ): MenuGroup {
  20. return super.createGroup(label, icon, children, actions)
  21. }
  22. public createItem(
  23. label: string,
  24. icon?: IconItem,
  25. to: string = '',
  26. type: MENU_LINK_TYPE = MENU_LINK_TYPE.INTERNAL,
  27. ): MenuItem {
  28. return super.createItem(label, icon, to, type)
  29. }
  30. public buildSubmenu(menuBuilder: typeof AbstractMenuBuilder) {
  31. return super.buildSubmenu(menuBuilder)
  32. }
  33. public makeChildren(items: Array<{ pageName: string; icon?: string }>) {
  34. return super.makeChildren(items)
  35. }
  36. }
  37. let runtimeConfig: RuntimeConfig
  38. let ability: AnyAbility
  39. let organizationProfile: organizationState
  40. let accessProfile: AccessProfile
  41. let menuBuilder: TestableAbstractMenuBuilder
  42. let router: Router
  43. beforeEach(() => {
  44. runtimeConfig = vi.fn() as any as RuntimeConfig
  45. ability = vi.fn() as any as AnyAbility
  46. organizationProfile = vi.fn() as any as organizationState
  47. accessProfile = vi.fn() as any as AccessProfile
  48. // @ts-ignore
  49. router = vi.fn() as Router
  50. menuBuilder = new TestableAbstractMenuBuilder(
  51. runtimeConfig,
  52. ability,
  53. organizationProfile,
  54. accessProfile,
  55. router,
  56. )
  57. })
  58. describe('getMenuName', () => {
  59. test('get name', () => {
  60. expect(menuBuilder.getMenuName()).toEqual('TestableMenu')
  61. })
  62. })
  63. describe('createGroup', () => {
  64. test('simple group', () => {
  65. const label = 'my_menu'
  66. const icon = { name: 'my_icon' }
  67. const children = [
  68. { label: 'submenu', type: MENU_LINK_TYPE.INTERNAL, active: true },
  69. ]
  70. const actions = [
  71. { label: 'action', type: MENU_LINK_TYPE.INTERNAL, active: true },
  72. ]
  73. const result = menuBuilder.createGroup(label, icon, children, actions)
  74. expect(result).toEqual({ label, icon, children, actions })
  75. })
  76. test('default values', () => {
  77. const result = menuBuilder.createGroup('my_menu')
  78. expect(result).toEqual({
  79. label: 'my_menu',
  80. icon: undefined,
  81. children: [],
  82. actions: [],
  83. })
  84. })
  85. })
  86. describe('createItem', () => {
  87. test('simple item', () => {
  88. const label = 'my_menu'
  89. const icon = { name: 'my_icon' }
  90. const to = 'https://domain.com/foo/bar'
  91. const type = MENU_LINK_TYPE.EXTERNAL
  92. const result = menuBuilder.createItem(label, icon, to, type)
  93. expect(result).toEqual({ icon, label, to, type, active: false })
  94. })
  95. test('default values', () => {
  96. const result = menuBuilder.createItem('my_menu')
  97. expect(result).toEqual({
  98. label: 'my_menu',
  99. icon: undefined,
  100. to: '',
  101. type: MENU_LINK_TYPE.INTERNAL,
  102. active: false,
  103. })
  104. })
  105. test('prepend https on external url', () => {
  106. const item = menuBuilder.createItem(
  107. 'my_menu',
  108. undefined,
  109. 'domain.com',
  110. MENU_LINK_TYPE.EXTERNAL,
  111. )
  112. expect(item.to).toEqual('https://domain.com')
  113. })
  114. test('complete V1 links (server side)', () => {
  115. runtimeConfig.baseUrlAdminLegacy = 'https://admin.opentalent.fr'
  116. const item = menuBuilder.createItem(
  117. 'my_menu',
  118. undefined,
  119. '/my_page',
  120. MENU_LINK_TYPE.V1,
  121. )
  122. expect(item.to).toEqual('https://admin.opentalent.fr/#/my_page')
  123. })
  124. test('complete V1 links (client side)', () => {
  125. runtimeConfig.baseUrlAdminLegacy = ''
  126. // @ts-ignore
  127. runtimeConfig.public = { baseUrlAdminLegacy: 'https://admin.opentalent.fr' }
  128. const item = menuBuilder.createItem(
  129. 'my_menu',
  130. undefined,
  131. '/my_page',
  132. MENU_LINK_TYPE.V1,
  133. )
  134. expect(item.to).toEqual('https://admin.opentalent.fr/#/my_page')
  135. })
  136. })
  137. describe('buildSubmenu', () => {
  138. test('should call given menu build method', () => {
  139. expect(menuBuilder.buildSubmenu(TestableAbstractMenuBuilder)).toEqual({
  140. label: 'my_menu',
  141. })
  142. })
  143. })
  144. describe('makeChildren', () => {
  145. test('simple call', () => {
  146. ability.can = vi.fn(() => true)
  147. // @ts-ignore
  148. router.resolve = vi.fn(() => {
  149. return { href: 'foo' }
  150. })
  151. const children: MenuItems = menuBuilder.makeChildren([
  152. { pageName: 'foo_page', icon: 'fas fa-dog' },
  153. ])
  154. expect(children).toEqual([
  155. {
  156. label: 'foo_page',
  157. icon: { name: 'fas fa-dog' },
  158. to: 'foo',
  159. type: 0,
  160. active: false,
  161. },
  162. ])
  163. })
  164. test('no icon', () => {
  165. ability.can = vi.fn(() => true)
  166. // @ts-ignore
  167. router.resolve = vi.fn(() => {
  168. return { href: 'foo' }
  169. })
  170. const children: MenuItems = menuBuilder.makeChildren([
  171. { pageName: 'foo_page' },
  172. ])
  173. expect(children).toEqual([
  174. { label: 'foo_page', icon: undefined, to: 'foo', type: 0, active: false },
  175. ])
  176. })
  177. test('not allowed', () => {
  178. ability.can = vi.fn(() => false)
  179. const children: MenuItems = menuBuilder.makeChildren([
  180. { pageName: 'foo_page' },
  181. ])
  182. expect(children).toEqual([])
  183. })
  184. test('unknown page name', () => {
  185. ability.can = vi.fn(() => true)
  186. // @ts-ignore
  187. router.resolve = vi.fn(() => {
  188. return null
  189. })
  190. expect(() =>
  191. menuBuilder.makeChildren([{ pageName: 'foo_page' }]),
  192. ).toThrowError()
  193. })
  194. })