티스토리 뷰

Vue로 서비스를 개발하게 되면, 기존 v-for, v-if 등과 같이 기존에 디렉티브로 사용되는 기능들이 있습니다. 이와 같이 Vue에서는 디렉티브를 직접 정의하여 사용할 수 있습니다. 서비스에서는 권한을 대부분 적용하고, 버튼과 같이 DOM 내 엑션 포인트를 보여 주는 것을 권한으로 통제하곤 하는데, 이를 디렉티브로 편하게 구성한다면?

<button v-permission="['admin']" @click="actionA">엑숀 A</button> 

위 예제와 같이 정의한 디렉티브인 v-permission에 로그인 한 사용자 권한 목록과 부합된다면, 버튼이 출력되고, 반대의 경우 버튼이 출력되지 않는다면 간편하게 권한을 사용하는 것입니다.

이 기능을 구현하는 것으로 디렉티브를 구성하는 방법을 설명하겠습니다.

디렉티브를 구성하기 위해서는 여기에 있는 문서를 읽고 오는 것을 추천합니다. 디렉티브를 이해할 때 가장 중요한 부분은 훅 함수입니다. 훅을 통해 상태에 따라서 적절히 로직들을 반영 할 수 있습니다.

구현할 권한을 통하여 DOM에 출력 여부를 정하는 것은 componentUpdated 훅 함수를 통해 Children 항목이 있을 경우 모두 출력되고 적용되는 형식으로 구현하겠습니다. (불필요한 업데이트를 막기 위해서는 update 훅 함수를 사용하기도 합니다.)

훅 함수를 사용할 때 가장 중요한 Parameter들은 elbinding입니다. el은 디렉티브를 반영한 타겟 element이고, binding은 해당 디렉티브에 부여한 값을 의미합니다. 위의 예제를 기반으로 보면 el은 <button>이고, binding은 ['admin']입니다.

import store from '@/store'

let permission = {
  componentUpdated(el, binding, vnode) {
    const { value } = binding
    const roles = store.getters && store.getters.roles

    if (value && value instanceof Array && value.length > 0) {
      const permissionRoles = value

      const hasPermission = roles.some(role => {
        return permissionRoles.includes(role)
      })

      // permission이 없으면 해당 el은 삭제 되어야 한다.
      if (!hasPermission) {
        el.parentNode && el.parentNode.removeChild(el)
      }
    } else {
      throw new Error(`유저 그룹 설정이 필요합니다.! 예: v-permission="['admin','developer']"`)
    }
  }
}

const install = function (Vue) {
  Vue.directive('permission', permission)
}

permission.install = install
export default permission

위의 예제 내 Vuex(Store)를 통하여 로그인한 사용자에 부여된 권한을 가져옵니다. 이를 통해 디렉티브에 적용한 권한으로 사용자에 부여된 권한을 비교하여 같은 것이 하나도 없을 경우, 해당 ElementremoveChild(el)를 통하여 삭제하게 됩니다.

한편, 이렇게 구성된 .js 파일은 Vue.use()를 통해 Vue 전역에 적용하는데, install 항목을 위와 같이 정의하면 자동으로 이를 실행해 줍니다. Vue.directive('permission', permission)에 정의한 내역은 v-를 붙여서 사용할 수 있습니다.

이제 마지막으로 main.js와 같이 서비스 내 Vue 사용을 정의하는 곳에 사용 등록을 하면 됩니다.

Vue.use(permission)
댓글
댓글쓰기 폼