Windows용 Qt - 배포

이 문서는 Windows용 배포 프로세스에 대해 설명합니다. 배포 과정을 설명하기 위해 문서 전체에 걸쳐 플러그 앤 페인트 예제 애플리케이션을 참조합니다.

참고: 시스템에서 실행되는 안티바이러스 애플리케이션의 제외 디렉토리 목록에 Qt 빌드 디렉터리를 추가하세요.

Windows 배포 도구

Windows 배포 도구( windeployqt )는 해당 폴더에서 애플리케이션을 실행하는 데 필요한 Qt 관련 종속성(라이브러리, QML 임포트, 플러그인 및 번역)을 포함하는 배포 가능한 폴더를 생성하는 프로세스를 자동화하도록 설계되었습니다. 이 도구는 설치 패키지로 쉽게 번들링할 수 있는 Windows 데스크톱 애플리케이션용 설치 트리를 생성합니다.

이 도구는 QTDIR/bin/windeployqt 에서 찾을 수 있으며, 제대로 작동하려면 빌드 환경 내에서 실행해야 합니다. Qt Online Installer 을 사용하는 경우 QTDIR/bin/qtenv2.bat 스크립트를 사용하여 설정해야 합니다.

windeployqt .exe 파일 또는 .exe 파일이 포함된 디렉터리를 인수로 받아 실행 파일에서 종속성을 검사합니다. --qmldir 인자와 함께 디렉터리가 전달되면 windeployqtqmlimportscanner 도구를 사용하여 디렉터리 내의 QML 파일에서 QML 가져오기 종속성을 검사합니다. 그런 다음 확인된 종속성은 실행 파일의 디렉터리에 복사됩니다.

Qt가 구성 스위치 -relocatable 가 꺼진 상태로 빌드된 경우, windeployqt 은 Qt6Core.dll의 하드코딩된 로컬 경로를 상대 경로로 대체합니다.

Windows 데스크톱 애플리케이션의 경우 컴파일러에 필요한 런타임 파일도 기본적으로 배포 가능한 폴더에 복사됩니다( --no-compiler-runtime 옵션이 지정되지 않은 경우). Microsoft Visual C++를 사용하는 릴리스 빌드의 경우, 대상 시스템에서 애플리케이션의 인스톨러가 재귀적으로 설치하기 위한 Visual C++ 재배포 가능 패키지로 구성됩니다. 그렇지 않으면 컴파일러 런타임의 공유 라이브러리가 사용됩니다.

애플리케이션에 추가 타사 라이브러리(예: 데이터베이스 라이브러리)가 필요할 수 있으며, 이러한 라이브러리는 windeployqt에서 고려되지 않습니다.

추가 인수는 도구의 도움말 출력에 설명되어 있습니다:

Usage: windeployqt [options] [files]
Qt Deploy Tool 6.0.0

The simplest way to use windeployqt is to add the bin directory of your Qt
installation (e.g. <QT_DIR\bin>) to the PATH variable and then run:
  windeployqt <path-to-app-binary>
If ICU, etc. are not in the bin directory, they need to be in the PATH
variable. If your application uses Qt Quick, run:
  windeployqt --qmldir <path-to-app-qml-files> <path-to-app-binary>

Options:
  -?, -h, --help              Displays help on commandline options.
  --help-all                  Displays help including Qt specific options.
  -v, --version               Displays version information.
  --dir <directory>           Use directory instead of binary directory.
  --qmake <path>              Use specified qmake instead of qmake from PATH.
  --libdir <path>             Copy libraries to path.
  --plugindir <path>          Copy plugins to path.
  --debug                     Assume debug binaries.
  --release                   Assume release binaries.
  --pdb                       Deploy .pdb files (MSVC).
  --force                     Force updating files.
  --dry-run                   Simulation mode. Behave normally, but do not
                              copy/update any files.
  --no-patchqt                Do not patch the Qt6Core library.
  --ignore-library-errors     Ignore errors when libraries cannot be found.
  --no-plugins                Skip plugin deployment.
  --no-libraries              Skip library deployment.
  --qmldir <directory>        Scan for QML-imports starting from directory.
  --qmlimport <directory>     Add the given path to the QML module search
                              locations.
  --no-quick-import           Skip deployment of Qt Quick imports.
  --translations <languages>  A comma-separated list of languages to deploy
                              (de,fi).
  --no-translations           Skip deployment of translations.
  --no-system-d3d-compiler    Skip deployment of the system D3D compiler.
  --compiler-runtime          Deploy compiler runtime (Desktop only).
  --no-virtualkeyboard        Disable deployment of the Virtual Keyboard.
  --no-compiler-runtime       Do not deploy compiler runtime (Desktop only).
  --json                      Print to stdout in JSON format.
  --no-opengl-sw              Do not deploy the software rasterizer library.
  --list <option>             Print only the names of the files copied.
                              Available options:
                               source:   absolute path of the source files
                               target:   absolute path of the target files
                               relative: paths of the target files, relative
                                         to the target directory
                               mapping:  outputs the source and the relative
                                         target, suitable for use within an
                                         Appx mapping file
  --verbose <level>           Verbose level (0-2).

Qt libraries can be added by passing their name (-xml) or removed by passing
the name prepended by --no- (--no-xml). Available libraries:
bluetooth concurrent core declarative designer designercomponents gui qthelp
multimedia multimediawidgets multimediaquick network nfc opengl openglwidgets
positioning printsupport qml qmltooling quick quickparticles quickwidgets script
scripttools sensors serialport sql svg svgwidgets test websockets widgets xml
webenginecore webengine webenginewidgets 3dcore 3drenderer 3dquick
3dquickrenderer 3dinput 3danimation 3dextras geoservices webchannel serialbus
webview

Arguments:
  [files]                     Binaries or directory containing the binary.

정적 연결

정적 응용 프로그램을 빌드하려면 -static 로 Qt를 구성하여 정적으로 빌드합니다:

cd C:\path\to\Qt
configure -static <any other options you need>

나중에 같은 위치에서 Qt를 재구성하고 다시 빌드해야 하는 경우, 빌드 디렉터리로 들어가 nmake distclean 또는 mingw32-make distclean 을 실행하여 이전 구성의 모든 흔적을 제거한 후 configure 을 다시 실행하십시오.

애플리케이션을 정적 버전의 Qt에 연결하기

예를 들어 이 섹션에서는 플러그 앤 페인트 예제를 정적으로 빌드합니다.

Qt 빌드가 완료되면 플러그 앤 페인트 애플리케이션을 빌드합니다. 먼저 애플리케이션이 들어 있는 디렉토리로 이동해야 합니다:

cd examples\tools\plugandpaint

qmake 을 실행하여 애플리케이션에 대한 새 메이크파일을 생성하고 클린 빌드를 수행하여 정적으로 링크된 실행 파일을 생성합니다:

nmake clean
qmake -config release
nmake

릴리스 라이브러리에 대해 링크하고 싶을 수 있으며 qmake 을 호출할 때 이를 지정할 수 있습니다. 이제 모든 것이 오류 없이 컴파일되고 링크되었다면 배포할 준비가 된 plugandpaint.exe 파일이 있을 것입니다. 애플리케이션에 필요한 라이브러리가 있는지 확인하려면 실행 파일을 Qt 또는 Qt 애플리케이션이 설치되지 않은 머신에 복사하고 해당 머신에서 실행합니다.

애플리케이션이 컴파일러 특정 라이브러리에 의존하는 경우에도 해당 라이브러리를 애플리케이션과 함께 재배포해야 한다는 점을 기억하세요. depends 도구를 사용하여 애플리케이션이 링크하는 라이브러리를 확인할 수 있습니다. 자세한 내용은 애플리케이션 종속성 섹션을 참조하세요.

정적 링크 방식을 사용하여 플러그인을 배포할 수 없으므로 준비한 애플리케이션이 불완전합니다. 실행은 되지만 누락된 플러그인으로 인해 기능이 비활성화됩니다. 플러그인 기반 애플리케이션을 배포하려면 공유 라이브러리 접근 방식을 사용해야 합니다.

공유 라이브러리

공유 라이브러리 접근 방식을 사용하여 plugandpaint 애플리케이션을 배포할 때 두 가지 문제가 있습니다: Qt 런타임을 애플리케이션 실행 파일과 함께 올바르게 재배포해야 하고, 플러그인을 애플리케이션이 찾을 수 있도록 대상 시스템의 올바른 위치에 설치해야 합니다.

Qt를 공유 라이브러리로 빌드하기

이 예제에서는 Qt를 설치할 때 기본값인 공유 라이브러리로 C:\path\to\Qt 디렉터리에 설치한다고 가정합니다.

애플리케이션을 공유 라이브러리로 Qt에 연결하기

Qt가 공유 라이브러리로 빌드되었는지 확인한 후 plugandpaint 애플리케이션을 빌드할 수 있습니다. 먼저 애플리케이션이 들어 있는 디렉토리로 이동해야 합니다:

cd examples\tools\plugandpaint

이제 qmake 을 실행하여 애플리케이션의 새 메이크파일을 생성하고 클린 빌드를 수행하여 동적으로 링크된 실행 파일을 생성합니다:

nmake clean
qmake -config release
nmake

이렇게 하면 핵심 애플리케이션이 빌드되고 다음은 플러그인을 빌드합니다:

cd ..\plugandpaint/plugins
nmake clean
qmake -config release
nmake

모든 것이 오류 없이 컴파일되고 연결되면 plugandpaint.exe 실행 파일과 pnp_basictools.dllpnp_extrafilters.dll 플러그인 파일을 얻게 됩니다.

애플리케이션 패키지 만들기

애플리케이션을 배포하려면 애플리케이션에 사용된 Qt 모듈에 해당하는 관련 Qt DLL과 Windows 플랫폼 플러그인 qwindows.dll, 실행 파일을 release 하위 디렉터리의 동일한 디렉토리 트리에 복사해야 합니다.

사용자 플러그인과 달리 Qt 플러그인은 플러그인 유형과 일치하는 하위 디렉터리에 넣어야 합니다. 플랫폼 플러그인의 올바른 위치는 platforms 이라는 하위 디렉터리입니다. Qt 플러그 인 섹션에는 플러그인에 대한 추가 정보와 Qt가 플러그인을 검색하는 방법이 나와 있습니다.

동적 OpenGL을 사용하는 경우, 애플리케이션이 호환되는 경우 소프트웨어 기반 OpenGL에 필요한 라이브러리를 추가로 포함할 수 있습니다.

Qt가 ICU 또는 OpenSSL에 대해 링크하도록 구성된 경우, 해당 DLL도 release 폴더에 추가해야 합니다. 그러나 Windows의 Qt용 바이너리 패키지는 이 작업이 필요합니다. 자세한 내용은 타사 라이브러리를 참조하세요.

애플리케이션이 컴파일러 특정 라이브러리에 의존하는 경우 해당 라이브러리를 애플리케이션과 함께 재배포해야 한다는 점을 기억하세요. depends 도구를 사용하여 애플리케이션이 어떤 라이브러리와 연결되는지 확인할 수 있습니다. 자세한 내용은 애플리케이션 종속성 섹션을 참조하세요.

플러그인에 대해서는 곧 다루겠지만 먼저 애플리케이션이 배포된 환경에서 작동하는지 확인하겠습니다: 실행 파일과 Qt DLL을 Qt나 Qt 애플리케이션이 설치되지 않은 머신에 복사하거나 빌드 머신에서 테스트하려면 해당 머신의 환경에 Qt가 없는지 확인합니다.

애플리케이션이 문제 없이 시작되면 plugandpaint 애플리케이션의 동적 링크 버전을 성공적으로 만든 것입니다. 하지만 아직 관련 플러그인을 배포하지 않았기 때문에 애플리케이션의 기능은 여전히 누락될 수 있습니다.

플러그인은 일반 DLL과 다르게 작동하므로 Qt DLL에서 했던 것처럼 애플리케이션의 실행 파일과 같은 디렉터리에 플러그인을 복사할 수 없습니다. 플러그인을 찾을 때 애플리케이션은 애플리케이션 실행 파일 디렉터리 내의 plugins 하위 디렉터리에서 검색합니다.

따라서 애플리케이션에서 플러그인을 사용할 수 있게 하려면 plugins 하위 디렉터리를 만들고 관련 DLL을 복사해야 합니다:

plugins\pnp_basictools.dll
plugins\pnp_extrafilters.dll

플러그 앤 페인트 애플리케이션을 실행하는 데 필요한 모든 Qt DLL과 애플리케이션별 플러그인을 배포하는 아카이브에는 다음 파일이 포함되어야 합니다:

컴포넌트파일 이름
실행 파일plugandpaint.exe
기본 도구 플러그인plugins\pnp_basictools.dll
엑스트라 필터 플러그인plugins\pnp_extrafilters.dll
Qt 윈도우 플랫폼 플러그인platforms\qwindows.dll
Qt 윈도우 비스타 스타일 플러그인styles\qwindowsvistastyle.dll
Qt Core 모듈Qt6Core.dll
Qt GUI 모듈Qt6Gui.dll
Qt Widgets 모듈Qt6Widgets.dll

애플리케이션이 사용하는 기능에 따라 다른 플러그인이 필요할 수 있습니다(iconengines, imageformats).

또한 아카이브에는 다음 컴파일러별 라이브러리가 포함되어야 합니다(Visual Studio 17(2022) 가정):

컴포넌트파일 이름
C 런타임vcruntime140.dll
C++ 런타임msvcp170.dll

동적 OpenGL을 사용한 경우 아카이브에 추가로 포함될 수 있습니다:

컴포넌트파일 이름
OpenGL 소프트웨어 렌더러 라이브러리opengl32sw.dll

마지막으로, Qt가 ICU를 사용하도록 구성되었다면 아카이브에 반드시 포함되어야 합니다:

파일 이름
icudtXX.dllicuinXX.dllicuucXX.dll

이제 애플리케이션이 성공적으로 배포되는지 확인하려면 Qt가 없고 컴파일러가 설치되지 않은 시스템에서 이 아카이브를 추출하여 실행해 볼 수 있습니다.

플러그인을 플러그인 하위 디렉터리에 넣는 대신 QCoreApplication::addLibraryPath() 또는 QCoreApplication::setLibraryPaths()을 사용하여 애플리케이션을 시작할 때 사용자 지정 검색 경로를 추가하는 방법도 있습니다.

QCoreApplication::addLibraryPath("C:/some/other/path");

플러그인 사용의 한 가지 장점은 전체 애플리케이션 제품군에서 쉽게 사용할 수 있다는 것입니다.

QApplication 객체가 생성된 직후 애플리케이션의 main() 함수에서 경로를 추가하는 것이 가장 편리합니다. 경로가 추가되면 애플리케이션은 애플리케이션 자체 디렉토리의 plugins 하위 디렉터리에서 플러그인을 검색할 뿐만 아니라 해당 경로에서 플러그인을 찾습니다. 추가 경로는 얼마든지 추가할 수 있습니다.

매니페스트 파일

Visual Studio로 컴파일된 애플리케이션을 배포할 때는 몇 가지 추가 단계를 수행해야 합니다.

먼저 애플리케이션을 연결할 때 생성된 매니페스트 파일을 복사해야 합니다. 이 매니페스트 파일에는 런타임 라이브러리와 같은 사이드 바이 사이드 어셈블리에 대한 애플리케이션의 종속성에 대한 정보가 포함되어 있습니다.

매니페스트 파일은 애플리케이션 실행 파일과 동일한 폴더에 복사해야 합니다. 공유 라이브러리(DLL)는 사용되지 않으므로 매니페스트 파일을 복사할 필요가 없습니다.

공유 라이브러리에 사용하는 애플리케이션과 다른 종속성이 있는 경우 매니페스트 파일을 DLL 바이너리에 임베드해야 합니다. 다음 CONFIG 옵션을 사용하여 매니페스트를 임베드할 수 있습니다:

embed_manifest_dll
embed_manifest_exe

두 옵션 모두 기본적으로 활성화되어 있습니다. 제거하려면 embed_manifest_exe, 추가

CONFIG -= embed_manifest_exe

를 추가합니다.

매니페스트 파일 및 나란히 배치된 어셈블리에 대한 자세한 내용은 나란히 배치된 어셈블리 문서 페이지에서 확인할 수 있습니다.

애플리케이션에 런타임 라이브러리를 포함하는 올바른 방법은 최종 사용자의 시스템에 런타임 라이브러리가 설치되어 있는지 확인하는 것입니다.

최종 사용자의 시스템에 런타임 라이브러리를 설치하려면 애플리케이션에 적절한 Visual C++ 재배포 가능 패키지(VCRedist) 실행 파일을 포함시키고 사용자가 애플리케이션을 설치할 때 해당 실행 파일이 실행되는지 확인해야 합니다.

재배포 파일의 이름은 vc_redist.x64.exe (64비트)이며 <Visual Studio install path>/VC/redist/<language-code> 폴더에서 찾을 수 있습니다.

또는 웹(예: https: //support.microsoft.com/en-us/help/2977003/the-latest-supported-visual-c-downloads)에서 다운로드할 수 있습니다.

참고: 배포하는 애플리케이션은 동일한 C 런타임 버전에 대해 정확히 동일한 컴파일러 버전으로 컴파일해야 합니다. 이렇게 하면 다른 버전의 C 런타임 라이브러리로 인해 발생하는 배포 오류를 방지할 수 있습니다.

애플리케이션 종속성

추가 라이브러리

구성에 따라 컴파일러 특정 라이브러리를 애플리케이션과 함께 재배포해야 합니다.

의존성 검사 도구를 사용하여 애플리케이션이 어떤 라이브러리와 연결되는지 확인할 수 있습니다. 다음과 같이 실행하기만 하면 됩니다:

depends <application executable>

애플리케이션이 의존하는 라이브러리 목록과 기타 정보를 제공합니다.

depends 도구로 플러그 앤 페인트 실행 파일의 릴리스 빌드(plugandpaint.exe)를 보면 다음과 같은 비시스템 라이브러리에 대한 즉각적인 종속성이 나열됩니다:

QtVisual Studio 17 (2022)Mingw-w64
  • QT6CORE.DLL - QtCore 런타임
  • QT6GUI.DLL - QtGui 런타임
  • QT6WIDGETS.DLL - QtWidgets 런타임
  • VCCORLIB140.DLL, VCRUNTIME140D.DLL - C 런타임
  • MSVCP140.DLL - C++ 런타임
  • libwinpthread-1.dll
  • libgcc_s_seh-1.dll
  • libstdc++-6.dll

플러그인 DLL을 보면 정확히 동일한 종속성이 나열되어 있습니다.

Qt 플러그인

모든 Qt GUI 응용 프로그램에는 Qt에서 QPA(Qt 플랫폼 추상화 ) 계층을 구현하는 플러그인이 필요합니다. Windows의 경우, 플랫폼 플러그인의 이름은 qwindows.dll 입니다. 이 파일은 배포 디렉터리 아래의 특정 하위 디렉터리(기본값은 platforms)에 위치해야 합니다. 또는 아래 설명된 대로 Qt가 플러그인을 찾는 데 사용하는 검색 경로를 조정할 수 있습니다.

응용 프로그램이 인쇄 지원 플러그인, JPEG 이미지 포맷 플러그인 또는 SQL 드라이버 플러그인과 같은 하나 이상의 Qt 플러그인에 의존할 수도 있습니다. 애플리케이션에 필요한 모든 Qt 플러그인을 배포해야 합니다. 플랫폼 플러그인과 마찬가지로 각 플러그인 유형은 배포 디렉토리 내의 특정 하위 디렉토리(예: printsupport, imageformats 또는 sqldrivers)에 위치해야 합니다.

Qt가 구성 스위치 -relocatable 가 꺼진 상태로 빌드되지 않는 한 라이브러리는 재배치할 수 있습니다. Qt 플러그인의 검색 경로는 QtCore 라이브러리의 위치를 기준으로 하며, 대상 시스템에 애플리케이션을 설치한 후 플러그인을 찾기 위한 추가 단계는 필요하지 않습니다.

재배치 불가능한 빌드를 사용할 때 플러그인 찾기 보장하기

재배치 불가능한 빌드의 경우 대상 시스템에 애플리케이션을 설치한 후 플러그인을 찾기 위해 추가 단계를 수행해야 합니다.

이 경우 Qt 플러그인의 검색 경로는 QtCore 라이브러리에 하드코딩됩니다. 기본적으로 Qt 설치의 플러그인 하위 디렉터리가 첫 번째 플러그인 검색 경로입니다. 그러나 기본 경로와 같이 미리 결정된 경로에는 몇 가지 단점이 있습니다. 예를 들어 대상 머신에 존재하지 않을 수 있습니다. 따라서 다양한 대안을 검토하여 Qt 플러그인을 찾을 수 있는지 확인해야 합니다:

  • qt.conf 사용. 이 방법은 동일한 플러그인을 공유하는 실행 파일이 여러 위치에 있는 경우 권장됩니다.
  • QApplication::addLibraryPath() 또는 QApplication::setLibraryPaths() 사용. 이 방법은 플러그인을 사용할 실행 파일이 하나만 있는 경우에 권장됩니다.
  • 타사 설치 유틸리티를 사용하여 QtCore 라이브러리의 하드코딩된 경로를 변경합니다.

QApplication::addLibraryPath를 사용하여 사용자 지정 경로를 추가하면 다음과 같이 보일 수 있습니다:

QCoreApplication::addLibraryPath("C:/customPath/plugins");

그러면 QCoreApplication::libraryPaths()는 다음과 같이 반환됩니다:

  • C:/customPath/plugins
  • C:/Qt/%VERSION%/plugins
  • E:/myApplication/directory

실행 파일은 QCoreApplication::libraryPaths()에서 반환한 QStringList 과 동일한 순서로 이 디렉터리에서 플러그인을 찾습니다. 새로 추가된 경로는 QCoreApplication::libraryPaths() 앞에 추가되므로 이 경로가 먼저 검색됩니다. 그러나 QCoreApplication::setLibraryPaths()를 사용하면 검색할 경로와 검색 순서를 결정할 수 있습니다.

Qt 플러그인 생성 방법 문서는 Qt 애플리케이션용 플러그인을 빌드하고 배포할 때 주의해야 할 문제를 간략하게 설명합니다.

© 2025 The Qt Company Ltd. Documentation contributions included herein are the copyrights of their respective owners. The documentation provided herein is licensed under the terms of the GNU Free Documentation License version 1.3 as published by the Free Software Foundation. Qt and respective logos are trademarks of The Qt Company Ltd. in Finland and/or other countries worldwide. All other trademarks are property of their respective owners.