openlang

Java 의존성은 두 번 선언되고 두 목록은 어긋난다

모듈을 쓰는 Java 프로젝트는 의존성을 두 번 적습니다. 빌드 스크립트는 어떤 아티팩트를 받아서 어느 경로에 둘지 말하고, module-info.java는 이 모듈이 어떤 모듈을 requires 하는지 말합니다. 두 목록이 일치하도록 강제하는 것은 없고, 실제로 어긋납니다.

실패 양상은 대칭이 아닙니다. requires에 적었는데 빌드가 공급하지 않는 모듈은 컴파일 시점에 분명한 메시지로 실패합니다. 빌드가 공급했는데 어떤 requires에도 없는 JAR는 그냥 내 모듈에서 읽을 수 없고, 컴파일러도 그렇게 알려 줍니다. 헷갈리는 쪽은 module-info.class가 없는 의존성입니다. 모듈 경로에 두면 자동 모듈이 되는데, 매니페스트에 Automatic-Module-Name 항목이 있으면 그 이름을, 없으면 JAR 파일 이름에서 유도한 이름을 씁니다. 파일 이름을 바꾸면 requires 줄이 가리키는 이름이 바뀔 수 있습니다.

같은 JAR를 클래스 경로에 두면 이름 없는 모듈로 들어가고, 이름 있는 모듈은 그것을 아예 의존 대상으로 선언할 수 없습니다.

그래서 저는 빌드 스크립트를 무엇이 존재하는지에 대한 기준으로 두고, module-info.java는 제가 손댈 수 있는 범위에 대한 선언으로 봅니다. 하는 일이 다릅니다. 플러그인 없이 둘을 서로 대조해 보는 분이 계십니까?

영어에서 번역원문 보기

이어지는 대화 1

서로의 근거를 따라
  1. 고유 링크

    두 목록은 지금처럼 둬도 될 것 같아요. 어느 한쪽이 전부를 말해 준다고 기대하지만 않으면요. 빌드 파일은 무엇을 쓸 수 있는지에 답하고, module-info.java는 이 모듈이 무엇을 읽는지에 답해요. 둘이 어긋나면 대부분은 컴파일러가 이미 알려 줘요. 고정해 둘 만한 곳은 자동 모듈 이름 하나고, 누가 의존하기 전에 내 라이브러리에 Automatic-Module-Name을 넣어 두는 건 작은 습관인데 나중에 보답해요.

    영어에서 번역원문 보기

같은 질문의 다른 갈래

  1. Kotlin DSL로 옮기자 서브프로젝트가 implementation을 못 찾는다

    오래된 멀티 프로젝트 빌드를 Groovy DSL에서 Kotlin DSL로 옮기는 중입니다. 루트 build.gradle에는 이런 블록이 있었습니다. 루트는 기계적으로 옮겼습니다. 순서대로 정리하겠습니다. 루트 스크립트는 컴파…

  2. 일부러 망가뜨린 패키지가 tryEval을 통과했다

    오버레이의 패키지마다 builtins.tryEval을 씌우고 실패하는 것만 나열하는 작은 점검 스크립트를 짰어요. 그런데 전부 괜찮다고 나왔어요. 의존성 목록에 throw를 넣어 일부러 망가뜨린 패키지까지요. 항목을 끝까지…

    답글 4nix
  3. for_each 키는 이름표가 아니라 주소다

    for_each 키를 이름표로 보면 안 된다. 리소스 주소의 절반이다. terraform_data.queue["prod-orders"] 같은 주소로 state가 객체를 추적한다. 키를 바꾸면 plan은 이름이 바뀌었다고 보지…

    답글 6hcl