본문 바로가기
Vue.js

Vue.js] 12. Component > 등록, Props

by Fastlane 2024. 12. 31.
728x90
반응형

1. 전역등록

.component() 메서드를 사용해서 Vue앱에서 컴포넌트를 전역으로 사용할 수 있도록 할 수 있다. 

import { createApp } from 'vue'

const app = createApp({})

app.component(
  // 등록될 이름
  'MyComponent',
  // 구현체
  {
    /* ... */
  }
)

또는 가져온 .vue 파일을 등록한다. 

import MyComponent from './App.vue'

app.component('MyComponent', MyComponent)

전역으로 등록된 컴포넌트는 앱 내의 모든 컴포넌트 템플릿에서 사용할 수 있다. 

 

2. 로컬등록

전역 등록에는 몇 가지 단점이 있다. 

1) 전역등록은 빌드 시스템이 사용하지 않는 컴포넌트를 제거하는 것을 방지한다. 

2) 대규모 앱에서 의존 관계를 덜 명확하게 만든다. 장기적인 유지 관리 측면에 영향을 줄 수 있다. 

 

로컬 등록은 의존 관계가 더 명시적이다. 

<script>
import ComponentA from './ComponentA.vue'

export default {
  components: {
    ComponentA
  }
}
</script>

<template>
  <ComponentA />
</template>

로컬로 등록된 컴포넌트는 자식 컴포넌트에서 사용할 수 없다. 

 

3. Props 선언

Vue컴포넌트는 명시적인 props 선언을 요구하는데, 이렇게 함으로 외부에서 컴포넌트에 props를 넘길 때 어떤 속성이 fallthrough 속성으로 처리되어야 하는지 알 수 있다. 

 

export default {
  props: ['foo'],
  created() {
    // props는 `this`에 노출됩니다.
    console.log(this.foo)
  }
}

export default {
  props: {
    title: String,
    likes: Number
  }
}

객체 선언 시, key는 props의 이름이 되며 value는 type에 해당하는 생성자 함수이다. 

 

컴포넌트를 사용하는 개발자가 잘못된 유형을 전달할때 브라우저 콘솔에 경고를 출력한다. 

 

4. Props Passing Details

정적 vs. 동적 Props

<BlogPost title="Vue와 함께한 나의 여행" />
<!-- 변수 값을 동적으로 할당 -->
<BlogPost :title="post.title" />

<!-- 복잡한 표현식의 값을 동적으로 할당 -->
<BlogPost :title="post.title + ' by ' + post.author.name" />

 

다양한 타입의 값 전달

위에서 문자열 값을 전달했지만, 어떠한 타입의 값도 prop로 전달할 수 있다. 

숫자

<!-- `42`는 정적이지만 Vue에 이것이 문자열이 아닌          -->
<!-- JavaScript 표현식임을 알려주려면 v-bind가 필요합니다. -->
<BlogPost :likes="42" />

<!-- 변수 값을 동적으로 할당 -->
<BlogPost :likes="post.likes" />

Boolean

<!-- 값이 없는 prop는 `true`가 전달됩니다. -->
<BlogPost is-published />

<!-- `false`는 정적이지만 Vue에 이것이 문자열이 아닌       -->
<!-- JavaScript 표현식임을 알려주려면 v-bind가 필요합니다. -->
<BlogPost :is-published="false" />

<!-- 변수 값을 동적으로 할당 -->
<BlogPost :is-published="post.isPublished" />

배열

<!-- 배열이 정적이더라도 Vue에 이것이 문자열이 아닌         -->
<!-- JavaScript 표현식임을 알려주려면 v-bind가 필요합니다. -->
<BlogPost :comment-ids="[234, 266, 273]" />

<!-- 변수 값을 동적으로 할당 -->
<BlogPost :comment-ids="post.commentIds" />

객체

<!-- 객체가 정적이더라도 Vue에 이것이 문자열이 아닌         -->
<!-- JavaScript 표현식임을 알려주려면 v-bind가 필요합니다. -->
<BlogPost
  :author="{
    name: '신형만',
    company: '떡잎 상사'
  }"
 />

<!-- 변수 값을 동적으로 할당 -->
<BlogPost :author="post.author" />

객체의 여러 속성 바인딩하기

객체의 모든 속성을 props로 전달하려면 

export default {
  data() {
    return {
      post: {
        id: 1,
        title: 'Vue와 함께하는 나의 여정'
      }
    }
  }
}
<BlogPost v-bind="post" />
<!-- 이것은 다음과 동일하다 -->
<BlogPost :id="post.id" :title="post.title" />

 

단방향 데이터 흐름

모든 props는 하향식 단방향 바인딩을 형성한다. 부모 컴포넌트가 업데이트 때마다 자식 컴포넌트의 모든 props가 최신 값으로 업데이트 된다. 따라서 자식 컴포넌트 내부에서 props를 변경하려 하면 안된다. 

export default {
  props: ['foo'],
  created() {
    // ❌ 경고, props는 읽기 전용입니다!
    this.foo = 'bar'
  }
}

일반적으로 prop을 변경하고 싶은 두 가지 경우는 다음과 같이 처리한다. 

1) prop의 초기값을 사용하려 할때

export default {
  props: ['initialCounter'],
  data() {
    return {
      // props.initialCounter는 counter의 초기 값으로 사용됩니다.
      // 추후 props가 갱신되어도 counter 값이 업데이트 되지 않습니다.
      counter: this.initialCounter
    }
  }
}

2) 계산이 필요한 prop

export default {
  props: ['size'],
  computed: {
    // prop이 변경될 때, 계산된 속성은 자동으로 업데이트 됩니다.
    normalizedSize() {
      return this.size.trim().toLowerCase()
    }
  }
}

 

Prop 유효성 검사

export default {
  props: {
    // 기본 타입 검사
    // (`null` 및 `undefined` 값은 모든 타입을 허용)
    propA: Number,
    // 여러 가지 가능한 타입
    propB: [String, Number],
    // 필수 문자열
    propC: {
      type: String,
      required: true
    },
    // 필수이지만 널 허용 문자열
    propD: {
      type: [String, null],
      required: true
    },
    // 기본값이 있는 숫자
    propE: {
      type: Number,
      default: 100
    },
    // 기본값이 있는 객체
    propF: {
      type: Object,
      // 객체 또는 배열 기본값은
      // 팩토리 함수에서 반환되어야 합니다. 이 함수는
      // 컴포넌트가 받은 원시 props를 인수로 받습니다.
      default(rawProps) {
        return { message: '안녕!' }
      }
    },
    // 사용자 정의 검증 함수
    // 3.4+ 버전에서는 전체 props가 두 번째 인수로 전달됨
    propG: {
      validator(value, props) {
        // 값은 이 문자열 중 하나와 일치해야 합니다
        return ['성공', '경고', '위험'].includes(value)
      }
    },
    // 기본값이 있는 함수
    propH: {
      type: Function,
      // 객체 또는 배열 기본값과 달리, 이는 팩토리 함수가 아닌
      // 기본값으로 사용할 함수입니다.
      default() {
        return 'Default function'
      }
    }
  }
}
  • required : true 가 지정되지 않은 모든 prop은 기본적으로 선택 사항(optional)이다. 
  • prop의 타입이 Boolean이 아니고 선택사항인 경우, 누락되면 undefined이고 Boolean이고 누락되면 false가 기본값이 된다. 
  • prop이 누락되었거나 명시적으로 선언된 값이 undefined이고 default값이 정의되어 있으면 default값이 사용된다.

type은 다음 중 하나이며 사용자 정의 클래스 또는 생성자 함수일 수도 있다. 

  • String
  • Number
  • Boolean
  • Array
  • Object
  • Date
  • Function
  • Symbol
  • Error
  •  
class Person {
  constructor(firstName, lastName) {
    this.firstName = firstName
    this.lastName = lastName
  }
}
export default {
  props: {
    author: Person
  }
}

 

Nullable Type

타입이 필수이지만 널 허용인 경우, null을 포함한 배열 구문을 사용할 수 있습니다:

export default {
  props: {
    id: {
      type: [String, null],
      required: true
    }
  }
}

type이 배열 구문 없이 null만인 경우 모든 타입 허용이다. 

 

 

728x90
반응형

'Vue.js' 카테고리의 다른 글

Vue.js] 14. Component > v-model, Fallthrough 속성  (0) 2024.12.31
Vue.js] 13. Component > Events  (0) 2024.12.31
Vue.js] 11. ref, component  (0) 2024.12.27
Vue.js] 10. 생명 주기 훅, Watchers  (0) 2024.12.27
Vue.js] 9. Form 입력 바인딩  (0) 2024.12.27

댓글