본문 바로가기
프로젝트관리

Tuist Shared Layer - ExternalModule 만들기

by zinozino 2025. 1. 10.

Tuist Shared Layer - ExternalModule 만들기

Tuist 프로젝트에서 외부 모듈을 관리하기 위한 Shared Layer를 구성하는 방법에 대해 알아보겠습니다.

1. Shared Layer 정의하기

Shared Layer는 Source 타겟과 Tests 타겟으로 구성되며, 이를 통해 프로젝트 전반에서 재사용 가능한 외부 모듈을 관리할 수 있습니다.

프로젝트 구조 설정

프로젝트에서 필요한 디렉토리 구조를 아래와 같이 생성합니다:

Manifests/
├── ProjectDescriptionHelpers/
│   └── SharedLayer.swift        # Shared Layer 설정을 위한 헬퍼 파일
└── Projects/
    └── Shared/
        └── ThirdParty/
            └── Project.swift    # 실제 프로젝트 설정 파일

SharedLayer 모듈 구현

SharedLayer.swift

public func makeSharedLayer(name: String, dependencies: [TargetDependency] = []) -> Project {
    // 설정 정의
    let thirdPartySetting: Settings = .settings(
        configurations: [
            .debug(name: "Debug", xcconfig: .relativeToRoot("Configurations/\(name)/\(name)-Debug.xcconfig")),
            .release(name: "Release", xcconfig: .relativeToRoot("Configurations/\(name)/\(name)-Release.xcconfig"))
        ],
        defaultSettings: .recommended
    )

    // Source 타겟 설정
    let sourcesTarget = Target.target(
        name: name,
        destinations: .iOS,
        product: .framework,
        bundleId: AppConfiguration.baseBundleId + ".\(name)",
        deploymentTargets: AppConfiguration.miniumTarget,
        dependencies: dependencies
    )

    // Tests 타겟 설정
    let tests = Target.target(
        name: "\(name)Tests",
        destinations: .iOS,
        product: .unitTests,
        bundleId: AppConfiguration.baseBundleId + ".\(name)Tests"
    )

    // Scheme 설정
    let thirdPartyScheme = Scheme.scheme(
        name: name,
        shared: true,
        buildAction: .buildAction(targets: [.target(name)]),
        runAction: .runAction(configuration: "Debug"),
        archiveAction: .archiveAction(configuration: "Inhouse")
    )

    return Project.init(
        name: name,
        organizationName: AppConfiguration.baseBundleId,
        settings: thirdPartySetting,
        targets: [sourcesTarget, tests],
        schemes: [thirdPartyScheme]
    )
}

ThirdParty 프로젝트 설정

Project.swift

import ProjectDescription
import ProjectDescriptionHelpers

let project = makeSharedLayer(
    name: "ThirdParty", 
    dependencies: [.external(name: "ComposableArchitecture")]
)

이렇게 설계한 이유

Shared레이어 계층의 특징

  • 레이어중 가장 최하단에 위치한 레이어
  • 모든 레이어계층의 모듈이 접근한 모듈을 정의
  • Tuist의 TMA(The Modular Architecture)의 Sources, tests만 필요

의존성 관리

  • 외부 모듈(ComposableArchitecture)을 명시적으로  한 곳에서 관리
  • 하나의 모듈로 프로젝트 전반에서 일관된 의존성 사용 가능