inflearn logo
강의

Course

Instructor

Hodolman's Stomach-Turning Development Show (SpringBoot, Vue.JS, AWS)

Connect Post API

(솔루션 수정)'tsyringe' Error: TypeInfo not known for "클래스명"

713

Truestar

68 asked

0

진작에 질문을 남겼어야 했는데, 애러 해결이 어려워 너무 지체되네요. 첫 질문 남기게 되었습니다.

 

문제의 요지
: 추측 하기로container.resolve 가 vue 와 라이프사이클 에 순서때문인지, 다른 이유가 있는지 DI 가 안됩니다. 

 

Menu.vue 디버깅

강의내용에도 있듯 tsyringe 는@singleton 이 달려있는 클래스를 컨테이너에 등록 후, 클래스 자체를 DI 키로 사용할 수 있다고 알고있습니다. 디버깅 상황에서 보다시피container 내부 _registryMap 안에 AuthorityApi 클래스가 정상등록 된 것을 확인할 수 있었습니다.

image

 

하지만 Break-point 된 container.resolve 처리가 안되어 아래처럼 애러가 발생합니다. 아래는 다음줄로 가지않고, 이벨류에이터로 실행한 모습이구요, AuthorityApi를 찾아올 수 없다 합니다.

image.png

Error: TypeInfo not known for "AuthorityApi"
    at http://localhost:4000/node_modules/.vite/deps/tsyringe.js?v=a355aabe:746:17
    at InternalDependencyContainer2.construct (http://localhost:4000/node_modules/.vite/deps/tsyringe.js?v=a355aabe:751:6)
    at InternalDependencyContainer2.resolveRegistration (http://localhost:4000/node_modules/.vite/deps/tsyringe.js?v=a355aabe:573:90)
    at InternalDependencyContainer2.resolve (http://localhost:4000/node_modules/.vite/deps/tsyringe.js?v=a355aabe:500:25)
    at eval (eval at setup (http://localhost:4000/src/widgets/Menu.vue:28:26), <anonymous>:1:11)
    at setup (http://localhost:4000/src/widgets/Menu.vue:28:26)
    at callWithErrorHandling (http://localhost:4000/node_modules/.vite/deps/chunk-VJROVW5H.js?v=a355aabe:1884:19)
    at setupStatefulComponent (http://localhost:4000/node_modules/.vite/deps/chunk-VJROVW5H.js?v=a355aabe:8253:25)
    at setupComponent (http://localhost:4000/node_modules/.vite/deps/chunk-VJROVW5H.js?v=a355aabe:8214:36)
    at mountComponent (http://localhost:4000/node_modules/.vite/deps/chunk-VJROVW5H.js?v=a355aabe:5604:7)

 

해결방법을 tsyringe 공식 깃헙이슈, 구글링, 스택오버플로 몽창 뒤져봐도 힌트얻기가 참으로 힘드네요. AI 센세는 그저 스택오버플로 내용만 읊어줍니다.

이것에 원인을 알 수 있을까요? 실마리만 얻어도 해결하기 수월할텐데, 몇일 째 어째야 되나 고민입니다. 도움을 얻을 수 있을까요?

 

: Source-Code

src-front 소스코드

주의: 개인 npm lib 가 포함되어 node_modules 을 포함한 체 그대로 압축된 파일입니다. npm i 인스톨 없이 앱을 실행해야될거라 예상합니다.

 

도움을 구합니다. 감사드려요.

vue.js tsyringe typescript ts container resolve di inject

Answer 2

0

Truestar

솔루션 수정본

기존 댓글에 정리된 내용이 적절치 않아 삭제 후, 실제 동작하는 방법에 대해 다시 정리합니다.

다음은 알려진 OOP 인터페이스 분리 패턴(ISP)을 TS기반 tsyringe 에서 추상클래스를 InjectionToken 으로 사용하는 방법입니다.

 

updates: 

  • 24-09-19: InjectionToken 형 변환 시, as InjectionToken 에서 `as InjectionToken 또는 as unknown as InjectionToken 으로 변경

 

1. extends AbstractClass

: 추상클래스를 상속,확장합니다.

abstract class Super {}

class Impl extends Super {}

 

2. 구현체 클래스에 @registry([..]) 추가

@singleton()
// ✅ @registry 에 직접 연관된 부모클래스(추상체)를 지정해야 @inject 를 통해 주입이 가능해집니다.
@registry([
  {
    // 💡 tsyringe 는 추상클래스 등록을 지원하지 않아 타입미스매치 애러 발생.
    //    해결은 unknown as InjectionToken 으로 강제 케스팅 후 등록이 가능함.
    // 1안
    token: Super as InjectionToken, 
    // 또는 2안
    token: Super as unknown as InjectionToken,
    useClass: Impl,
  },
])
class Impl extends Super {}

 

3. 사용

export class ConstructorInjectionWithTsyringe {
  constructor(
    @inject(Impl)
    readonly sup: Super,
  ) {}
}

 

동작확인

아래는 질문의 소스코드 디버깅 상황에서 캡쳐된 이미지입니다. 추상클래스 HttpClient 타입 맴버변수에, 구현체 AxiosHttpClient 인스턴스가 정상 주입된 것을 확인할 수 있었습니다.

image.png

 

0

Truestar

:: 추가이슈 해결 ::


문제
: 추상클래스를 container.resolve 인수로 대입 시, 반환된 인스턴스가 any 타입으로 추론됩니다.

: AppLogger 가 추상클래스 일때, InjectionToken 으로 형변환 시, 변수 logany 타입으로 추론됩니다. 이로인해 IDE 의 메서드 추론기능을 사용할 수 없습니다.

// 🚫 log: any 
const log = container.resolve(AppLogger as InjectionToken)

 

해결:

InjectionToken 타입의 구성은 다음과 같습니다.

declare type InjectionToken<T = any> = constructor<T> | string | symbol | DelayedConstructor<T>;

이 중에 constructor<T> 를 사용해서 강제케스팅 합니다.

 

적용코드:
import { container } from 'tsyringe'
import type { constructor } from 'tsyringe/dist/typings/types'

// log: AppLogger ✅
const log = container.resolve(AppLogger as constructor<AppLogger>)  

 

0

hodolman888675

import {AxiosHttpClient, HttpClient, type ResponseHandlerOptions} from '@/features'

@singleton()
export class AuthorityApi {
  constructor(@inject(HttpClient) readonly httpClient: AxiosHttpClient) {}

    // 생략
}

AuthorityApi의 생성자 주입이 안되는 상태입니다.

때문에 외부에서 container.resolve(AuthorityApi)가 안먹히는 상황입니다.

위 코드와 같이 AxiosHttpClient를 직접 지정해서 해결할 수 있습니다.

혹은 tsyringe 예제 문서와 같이 interface를 이용해서 주입할수도 있긴합니다.

관련링크: https://github.com/microsoft/tsyringe?tab=readme-ov-file#example-with-interfaces

0

Truestar

앗... 한참 정리중에 답글을 달아주셨군요... 해결상태로 종결하겠습니다!

0

Truestar

일반적인 OOP 방식처럼, inject 데코레이터에 구현체클래스, 필드변수타입에 추상체클래스 선언이 가능한 방법이 있었습니다. 너무 해맨것 치고 너무 해결방법이 간단해 허탈했고, 알려주신 방법이 다른 경우에서 잘 안되는거 같아, 용법을 새-댓글에 다시 정리하게 되었어요.

참고: microsoft/tsyringe: @registry

Deprecated 관련 사항들

0

100

2

깃헙 collaboator 초대 관련

0

87

1

logout 후에 login 페이지 이동은 어디서 시켜주는건가요?

0

231

1

다중 데이터를 삭제 할 때

0

270

2

querydsl Q class 이슈

0

414

2

Windows WSL Vue 설정

2

246

1

Dip, @transactional

0

188

1

[vite] http proxy error: /auth/login

0

1043

2

로그인 하고 나서 GET요청으로 메인페이지 요청

0

234

2

GitHub Collaborator 초대 관련

0

256

2

Window에서 Vue.js 설정

0

321

2

collaboator로 초대받을 수 있을까요??

0

283

2

SecurityMockContext 로부터 유저 정보를 가져오기

0

261

1

섹션9 프론트의 코드를 보고싶습니다,,,

0

423

1

Spring Security - defaultSuccessUrl 질문

0

625

1

강의 화면이 나오지 않습니다. 음성과 자막만 나와요

0

302

1

JPAQueryFactory(em)의 객체 생성자 오류에 대해서 질문이 있습니다ㅜㅜ

0

690

2

ExceptionHandler가 AccessDeniedHandler(Http403Handler)를 먹어버리는 현상

0

1179

2

섹션10 언제 나오나요?

0

484

1

CommentService에서 Repository를 호출하지 않는데도

0

342

1

Editor....를 활용한 패턴에 질문있습니다.

0

494

1

섹션9 vue

0

453

2

Post에 edit 메서드 삼항연산자 질문

0

474

2

@Configuration WebMvcConfig클래스에대해

0

573

1