2017-11-13 12 views
3

중첩 된 속성에 안전하고 쉽게 액세스하는 유일한 방법은 _.get입니다. 예 :안전한 버전의 lodash _get - 배열 유형을 조건부로 분해하십시오

_.get(obj, "Some.Nested[2].Property", defaultValue); 

위의 코드는 훌륭하게 작동하지만 속성 이름이 자주 바뀌지 않습니다.

function getSafe<TObject, P1 extends keyof TObject>(obj: TObject, p1: P1): TObject[P1]; 

function getSafe<TObject, P1 extends keyof TObject, P2 extends keyof TObject[P1]>(obj: TObject, p1: P1, p2: P2): TObject[P1][P2]; 
:

safeGet(obj, "Some", "Nested", 2, "Property", defaultValue); 

내가 배열 유형을 제외하고 모두를위한 이러한 입력을 만드는 데 성공했습니다 이론적으로는 암시를 확인 입력 타이프를 다음에 위의 변환 허용 할 수 있어야한다

깊이가있는 항목을 제대로 확인합니다 (이 문은 10 단계로 자동 생성됩니다). 다음 매개 변수에 전달 된 형식이 T[]이고 T이 아니기 때문에 배열 속성에서 실패합니다.

어떤 솔루션의 복잡성이나 자세한 정보는 코드가 자동 생성되므로 고려하지 않아도됩니다. 문제는 정수 매개 변수를 받아들이고 해체 할 수있는 형식 선언을 찾을 수없는 것입니다. 배열의 타입은 전방으로 이동합니다.

T[number]을 사용하여 배열 (여기서 T은 배열 임)을 해체 할 수 있습니다. 문제는 T이 중첩 된 속성의 배열 인 곳을 제약 할 방법이 없다는 것입니다. 실제로 콜 현장에서 작동

function getSafe<TObject, P1 extends keyof TObject, P2 extends keyof TObject[P1][number]>(obj: TObject, p1: P1, index: number, p2: P2): TObject[P1][number][P2]; 
                       ^^^^^^                ^^^^^^ 
const test2 = getSafe(obj, "Employment", 0, "Id"); // example usage 

가 (이 오류가 제대로 우리가 PARAM 및 형태를 돌려주지 않는다)하지만, 선언에 우리 자신을 오류를 제공하기 때문에 당신은 [number]와 인덱스 TObject[P1] 수없는 우리가 할 수있는 TObject[P1]은 배열입니다.

(참고 : TType[number]가 배열 유형의 요소 유형을 얻을 수있는 가능한 방법이지만, 우리는 우리가 배열이를하고있는 컴파일러 설득 할 필요가) 정말

문제는이다, TObject[P1]또는에 배열 제약 조건을 추가 할 수있는 방법이 있습니까?

답변

2

난 이후이 문제를 파악하고 여기에 NPM 패키지를 발표했습니다 ts-get-safe

중요한 점은 어떻게 조건 구조 조정 그것의 요소 타입으로 배열을 파악했다. 이를 위해서는 먼저 모든 속성이 배열 또는 never임을 주장해야합니다. 방정식을 해결 유형이었다

type GSArrEl<TKeys extends keyof TObj, TObj> = { [P in TKeys]: undefined[] & TObj[P] }[TKeys][number]; 

마법이 { [P in TKeys]: undefined[] & TObj[P] }에 어디 undefined[]-TObj의 우리 본질적으로 노동 조합 각 속성. 각 속성이 배열 또는 never (배열이 아닌 각 속성에 never이 될 것임)인지 확인하기 때문에 요소 형식을 얻기 위해 구조화 표현 [number]을 수행 할 수 있습니다.그러나 난, 배열 및 개체 속성의 조합

function getSafe<TObject, P0 extends keyof TObject, A1 extends GSArrEl<P0, TObject>, P2 extends keyof A1, P3 extends keyof A1[P2], A4 extends GSArrEl<P3, A1[P2]>>(obj: TObject, p0: P0, a1: number, p2: P2, p3: P3, a4: number): A4; 

수백 내 ts-get-safe 라이브러리 생성 및 사용할 준비가되었습니다 여기

두 배열 destructuring 동시에 발생의 예입니다 동일한 선언에서 동적 인 수의 매개 변수를 사용할 수 있도록 일반적인 방식으로이를 향상시키는 방법을 여전히 열어두고 있습니다. 배열과 속성 탐색을 동일한 유형 제약에 결합하여 배열 및 속성 액세스의 모든 변형을 생성 할 필요가 없습니다.