Freigeben über


Verwenden der winapp CLI mit C++ und CMake

In diesem Handbuch wird veranschaulicht, wie Sie die winapp CLI mit einer C++-Anwendung verwenden, um mit Paketidentität zu debuggen und Ihre Anwendung als MSIX zu verpacken.

Die Paketidentität ist ein Kernkonzept im Windows app-Modell. Sie ermöglicht Ihrer Anwendung den Zugriff auf bestimmte Windows-APIs (z. B. Benachrichtigungen, Sicherheit, KI-APIs usw.), eine einfache Installation/Deinstallation und vieles mehr.

Eine Standard-Ausführungsdatei (wie eine, die mit cmake --build erstellt wurde) hat keine Paketidentität. In diesem Handbuch wird gezeigt, wie Sie es zum Debuggen hinzufügen und dann für die Verteilung verpacken.

Voraussetzungen

  1. Buildtools: Verwenden Sie eine Compilertoolkette, die von CMake unterstützt wird. In diesem Beispiel wird Visual Studio verwendet. Sie können die Community-Edition folgendermaßen installieren:

    winget install --id Microsoft.VisualStudio.Community --source winget --override "--add Microsoft.VisualStudio.Workload.NativeDesktop --includeRecommended --passive --wait"
    

    Neustart nach der Installation.

  2. CMake: CMake installieren:

    winget install Kitware.CMake --source winget
    
  3. winapp CLI: Installieren Sie die winapp CLI über winget:

    winget install Microsoft.winappcli --source winget
    

1. Erstellen einer neuen C++-App

Erstellen Sie zunächst eine einfache C++-Anwendung. Erstellen Sie ein neues Verzeichnis für Ihre project:

mkdir cpp-app
cd cpp-app

Erstellen Sie eine main.cpp Datei mit einem einfachen Programm "Hello, world!":

#include <iostream>

int main() {
    std::cout << "Hello, world!" << std::endl;
    return 0;
}

Erstellen Sie eine CMakeLists.txt Datei zum Konfigurieren des Builds:

cmake_minimum_required(VERSION 3.20)
project(cpp-app)

set(CMAKE_CXX_STANDARD 20)
set(CMAKE_CXX_STANDARD_REQUIRED ON)

add_executable(cpp-app main.cpp)

Erstellen Sie es und führen Sie es aus, um sicherzustellen, dass alles funktioniert:

cmake -B build
cmake --build build --config Debug
.\build\Debug\cpp-app.exe

2. Aktualisieren von Code zum Überprüfen der Identität

Aktualisieren Sie die App, um zu überprüfen, ob sie mit der Paketidentität mithilfe der Windows Runtime C++-API ausgeführt wird.

Aktualisieren Sie zunächst Ihre CMakeLists.txt, um einen Link mit der Windows App Modellbibliothek zu erstellen:

cmake_minimum_required(VERSION 3.20)
project(cpp-app)

set(CMAKE_CXX_STANDARD 20)
set(CMAKE_CXX_STANDARD_REQUIRED ON)

add_executable(cpp-app main.cpp)

# Link Windows Runtime libraries
target_link_libraries(cpp-app PRIVATE WindowsApp.lib OneCoreUap.lib)

Ersetzen Sie als Nächstes den Inhalt von main.cpp:

#include <iostream>
#include <windows.h>
#include <appmodel.h>

int main() {
    UINT32 length = 0;
    LONG result = GetCurrentPackageFamilyName(&length, nullptr);

    if (result == ERROR_INSUFFICIENT_BUFFER) {
        std::wstring familyName;
        familyName.resize(length);

        result = GetCurrentPackageFamilyName(&length, familyName.data());

        if (result == ERROR_SUCCESS) {
            std::wcout << L"Package Family Name: " << familyName.c_str() << std::endl;
        } else {
            std::wcout << L"Error retrieving Package Family Name" << std::endl;
        }
    } else {
        std::cout << "Not packaged" << std::endl;
    }

    return 0;
}

3. Ohne Identität ausführen

Bauen Sie die App neu auf und führen Sie sie aus:

cmake --build build --config Debug
.\build\Debug\cpp-app.exe

Es sollte "Nicht verpackt" angezeigt werden. Dadurch wird bestätigt, dass die standardmäßige ausführbare Datei ohne Paketidentität ausgeführt wird.

4. Initialisiere das Projekt mit winapp CLI

Der Befehl winapp init richtet alles ein, was Sie benötigen: App-Manifest, Ressourcen und optional Windows App SDK Header für die C++-Entwicklung.

winapp init

Wenn Sie dazu aufgefordert werden:

  • Paketname: Drücken Sie die EINGABETASTE, um die Standardeinstellung zu akzeptieren (cpp-app)
  • Publisher Name: Drücken Sie die EINGABETASTE, um die Standardeinstellung zu akzeptieren oder Ihren Namen einzugeben.
  • Version: Drücken Sie die EINGABETASTE, um 1.0.0.0 zu akzeptieren.
  • Einstiegspunkt: Drücken Sie die EINGABETASTE, um die Standardeinstellung zu übernehmen (cpp-app.exe)
  • Setup-SDKs: Wählen Sie "Stable SDKs" aus, um Windows App SDK herunterzuladen und Header zu generieren.

Mit diesem Befehl wird Folgendes erstellt:

  • appxmanifest.xml und Assets Ordner für Ihre App-Identität
  • Ein ordner .winapp mit Windows App SDK Headern und Bibliotheken
  • Eine winapp.yaml Konfigurationsdatei zum Fixieren von SDK-Versionen

5. Debuggen mit Identität

Verwenden Sie winapp create-debug-identityfolgendes, um Features zu testen, die eine Identität erfordern, ohne die App vollständig zu verpacken:

  1. Erstellen Sie die ausführbare Datei:

    cmake --build build --config Debug
    
  2. Debugidentität anwenden:

    winapp create-debug-identity .\build\Debug\cpp-app.exe
    
  3. Führen Sie die ausführbare Datei aus:

    .\build\Debug\cpp-app.exe
    

Nun sollte eine Ausgabe angezeigt werden, die ähnlich wie die folgende ist:

Package Family Name: cpp-app_12345abcde

Automatisieren der Debugidentität (optional)

Fügen Sie Ihrem Nachbuildbefehl einen Befehl hinzu CMakeLists.txt , um die Debugidentität automatisch anzuwenden:

add_custom_command(TARGET cpp-app POST_BUILD
    COMMAND $<$<CONFIG:Debug>:winapp>
            $<$<CONFIG:Debug>:create-debug-identity>
            $<$<CONFIG:Debug>:$<TARGET_FILE:cpp-app>>
    WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}
    COMMAND_EXPAND_LISTS
    COMMENT "Applying debug identity to executable..."
)

6. Verwenden von Windows App SDK (optional)

Wenn Sie ausgewählt haben, die SDKs während winapp init einzurichten, haben Sie Zugriff auf die Windows App SDK-Kopfzeilen im Ordner .winapp/include.

Aktualisieren Sie CMakeLists.txt, um die Kopfzeilen einzuschließen:

# Add Windows App SDK include directory
target_include_directories(cpp-app PRIVATE ${CMAKE_CURRENT_SOURCE_DIR}/.winapp/include)

Aktualisieren Sie main.cpp, um die Windows App-Runtime-API zu verwenden:

#include <iostream>
#include <windows.h>
#include <appmodel.h>
#include <winrt/Microsoft.Windows.ApplicationModel.WindowsAppRuntime.h>

int main() {
    winrt::init_apartment();

    UINT32 length = 0;
    LONG result = GetCurrentPackageFamilyName(&length, nullptr);

    if (result == ERROR_INSUFFICIENT_BUFFER) {
        std::wstring familyName;
        familyName.resize(length);

        result = GetCurrentPackageFamilyName(&length, familyName.data());

        if (result == ERROR_SUCCESS) {
            std::wcout << L"Package Family Name: " << familyName.c_str() << std::endl;

            auto runtimeVersion = winrt::Microsoft::Windows::ApplicationModel::WindowsAppRuntime::RuntimeInfo::AsString();
            std::wcout << L"Windows App Runtime Version: " << runtimeVersion.c_str() << std::endl;
        }
    } else {
        std::cout << "Not packaged" << std::endl;
    }

    return 0;
}

7. Wiederherstellen von Kopfzeilen bei Bedarf

.winapp-Ordner wird automatisch zu .gitignore hinzugefügt. Wenn andere Ihre project klonen, müssen sie diese Dateien wiederherstellen:

winapp restore
winapp cert generate --if-exists skip

8. Paket mit MSIX

Nachdem Sie bereit sind, zu verteilen, packen Sie als MSIX:

  1. Build für Release:

    cmake --build build --config Release
    
  2. Vorbereiten des Paketverzeichnisses:

    mkdir dist
    copy .\build\Release\cpp-app.exe .\dist\
    
  3. Generieren eines Entwicklungszertifikats:

    winapp cert generate --if-exists skip
    
  4. Packen und Signieren:

    winapp pack .\dist --cert .\devcert.pfx
    
  5. Installieren Sie das Zertifikat (als Administrator ausführen):

    winapp cert install .\devcert.pfx
    
  6. Installieren und Ausführen:

    Add-AppxPackage .\cpp-app.msix
    cpp-app
    

Tipp

  • Signieren Sie Ihr MSIX mit einem Codesignaturzertifikat von einer Zertifizierungsstelle für die Produktionsverteilung.
  • Der Microsoft Store signiert das MSIX für Sie, sodass Sie es nicht vor der Übermittlung signieren müssen.
  • Möglicherweise benötigen Sie separate MSIX-Pakete für jede architektur, die Sie unterstützen (x64, Arm64).