Notatka
Dostęp do tej strony wymaga autoryzacji. Może spróbować zalogować się lub zmienić katalogi.
Dostęp do tej strony wymaga autoryzacji. Możesz spróbować zmienić katalogi.
W tym przewodniku Szybki start pokazano, jak zaimplementować wzorzec inicjowania klienta używany przez zestaw MIP C++ SDK w czasie wykonywania.
Uwaga / Notatka
Każda aplikacja kliencka korzystająca z pakietu MIP File SDK, MIP Policy SDK lub MIP Protection SDK wymaga wykonania kroków opisanych w tym przewodniku Szybki start. Chociaż w tym przewodniku Szybki start pokazano, jak używać zestawów SDK do obsługi plików, ten sam schemat ma zastosowanie do klientów korzystających z zestawów SDK zasad i ochrony. Ukończ pozostałe przewodniki z serii Szybki start po kolei, ponieważ każdy kolejny opiera się na poprzednim, a ten jest pierwszym z nich.
Wymagania wstępne
Jeśli jeszcze tego nie zrobiono, upewnij się, że:
- Wykonaj kroki opisane w artykule Konfiguracja i konfiguracja zestawu SDK usługi Microsoft Information Protection (MIP). Ten przewodnik Quickstart "Inicjowanie aplikacji klienckiej" opiera się na właściwym przygotowaniu i konfiguracji zestawu SDK.
- Opcjonalnie:
- Przejrzyj obiekty profilu i silnika. Obiekty profilu i silnika są uniwersalnymi pojęciami wymaganymi przez klientów korzystających z zestawów SDK MIP do plików, zasad i ochrony.
- Zapoznaj się z pojęciami dotyczącymi uwierzytelniania , aby dowiedzieć się, jak zestaw SDK i aplikacja kliencka implementują uwierzytelnianie i wyrażanie zgody.
- Zapoznaj się z pojęciami obserwatora , aby dowiedzieć się więcej na temat obserwatorów i sposobu ich implementacji. Zestaw MIP SDK używa wzorca obserwatora do implementowania asynchronicznych powiadomień o zdarzeniach.
Tworzenie rozwiązania i projektu programu Visual Studio
Najpierw utwórz i skonfiguruj początkowe rozwiązanie oraz projekt programu Visual Studio, na których opierają się pozostałe przewodniki Szybki start.
Otwórz program Visual Studio 2022 lub nowszy, wybierz menu Plik , Nowy, Projekt. W oknie dialogowym Nowy projekt :
W okienku po lewej stronie w obszarze Zainstalowaneinne języki wybierz pozycję Visual C++.
W środkowym okienku wybierz pozycję Aplikacja konsolowa systemu Windows
W dolnym okienku zaktualizuj odpowiednio nazwę projektu,lokalizację i nazwę rozwiązania zawierającego.
Po zakończeniu kliknij przycisk OK w prawym dolnym rogu.
Dodaj pakiet NuGet dla zestawu MIP File SDK do projektu:
W Eksploratorze rozwiązań kliknij prawym przyciskiem myszy węzeł projektu (bezpośrednio w węźle u góry/rozwiązania), a następnie wybierz polecenie Zarządzaj pakietami NuGet...:
Po otwarciu karty Menedżer pakietów NuGet w obszarze kart grupy edytora:
- Wybierz przycisk Przeglądaj.
- Wprowadź ciąg "Microsoft.InformationProtection" w polu wyszukiwania.
- Wybierz pakiet "Microsoft.InformationProtection.File".
- Kliknij "Zainstaluj", a następnie kliknij "OK", gdy zostanie wyświetlone okno dialogowe potwierdzenia podglądu zmian.
Zaimplementuj klasę obserwatora do monitorowania profilu pliku i obiektów silnika
Teraz utwórz podstawową implementację klasy obserwatora profilu File, rozszerzając klasę mip::FileProfile::Observer z zestawu SDK. Następnie tworzysz instancję obserwatora i używasz jej do monitorowania ładowania obiektu profilu File oraz dodawania obiektu silnika do profilu.
Dodaj nową klasę do projektu, która generuje pliki header/.h i implementation/.cpp dla Ciebie:
W Eksploratorze rozwiązań ponownie kliknij prawym przyciskiem myszy węzeł projektu, wybierz polecenie Dodaj, a następnie wybierz pozycję Klasa.
W oknie dialogowym Dodawanie klasy :
- W polu Nazwa klasy wprowadź "profile_observer". Zwróć uwagę, że zarówno plik h , jak i pola pliku .cpp są wypełniane automatycznie na podstawie wprowadzonej nazwy.
- Po zakończeniu kliknij przycisk OK .
Po wygenerowaniu plików h i .cpp dla klasy Visual Studio otwiera oba pliki na kartach Grupy edytora. Teraz zaktualizuj każdy plik, aby zaimplementować nową klasę obserwatora:
Zaktualizuj element "profile_observer.h", wybierając/usuwając wygenerowaną
profile_observerklasę. Nie usuwaj dyrektyw preprocesora wygenerowanych w poprzednim kroku (#pragma, #include). Następnie skopiuj/wklej następujące źródło do pliku po istniejących dyrektywach preprocesora:#include <memory> #include "mip/file/file_profile.h" class ProfileObserver final : public mip::FileProfile::Observer { public: ProfileObserver() { } void OnLoadSuccess(const std::shared_ptr<mip::FileProfile>& profile, const std::shared_ptr<void>& context) override; void OnLoadFailure(const std::exception_ptr& error, const std::shared_ptr<void>& context) override; void OnAddEngineSuccess(const std::shared_ptr<mip::FileEngine>& engine, const std::shared_ptr<void>& context) override; void OnAddEngineFailure(const std::exception_ptr& error, const std::shared_ptr<void>& context) override; };Zaktualizuj "profile_observer.cpp", wybierając/usuwając wygenerowaną implementację klasy
profile_observer. Nie usuwaj dyrektyw preprocesora wygenerowanych w poprzednim kroku (#pragma, #include). Następnie skopiuj/wklej następujące źródło do pliku po istniejących dyrektywach preprocesora:#include <future> using std::promise; using std::shared_ptr; using std::static_pointer_cast; using mip::FileEngine; using mip::FileProfile; void ProfileObserver::OnLoadSuccess(const shared_ptr<FileProfile>& profile, const shared_ptr<void>& context) { auto promise = static_pointer_cast<std::promise<shared_ptr<FileProfile>>>(context); promise->set_value(profile); } void ProfileObserver::OnLoadFailure(const std::exception_ptr& error, const shared_ptr<void>& context) { auto promise = static_pointer_cast<std::promise<shared_ptr<FileProfile>>>(context); promise->set_exception(error); } void ProfileObserver::OnAddEngineSuccess(const shared_ptr<FileEngine>& engine, const shared_ptr<void>& context) { auto promise = static_pointer_cast<std::promise<shared_ptr<FileEngine>>>(context); promise->set_value(engine); } void ProfileObserver::OnAddEngineFailure(const std::exception_ptr& error, const shared_ptr<void>& context) { auto promise = static_pointer_cast<std::promise<shared_ptr<FileEngine>>>(context); promise->set_exception(error); }
Opcjonalnie użyj F6 (Kompiluj rozwiązanie), aby uruchomić kompilowanie/łącze testowe rozwiązania, aby upewnić się, że kompilacja została pomyślnie skompilowana przed kontynuowaniem.
Implementowanie delegata uwierzytelniania
Zestaw SDK MIP implementuje uwierzytelnianie za pomocą mechanizmu rozszerzania klas, który umożliwia współdzielenie obsługi uwierzytelniania z aplikacją kliencką. Klient musi uzyskać odpowiedni token dostępu OAuth2 i udostępnić go zestawowi MIP SDK w czasie wykonywania.
Teraz utwórz implementację dla delegata uwierzytelniania, rozszerzając klasę zestawu SDK mip::AuthDelegate i przesłaniając lub implementując czystą funkcję wirtualną mip::AuthDelegate::AcquireOAuth2Token() . Obiekty File profile i File engine tworzą instancję delegata uwierzytelniania i używają go na późniejszym etapie.
Używając tej samej funkcji "Dodaj klasę" programu Visual Studio, której użyliśmy w kroku 1 poprzedniej sekcji, dodaj kolejną klasę do projektu. Tym razem wprowadź "auth_delegate" w polu Nazwa klasy.
Teraz zaktualizuj każdy plik, aby zaimplementować nową klasę delegata uwierzytelniania:
Zaktualizuj plik "auth_delegate.h", zastępując cały wygenerowany
auth_delegatekod klasy przykładowym kodem. Nie usuwaj dyrektyw preprocesora wygenerowanych w poprzednim kroku (#pragma, #include):#include <string> #include "mip/common_types.h" class AuthDelegateImpl final : public mip::AuthDelegate { public: AuthDelegateImpl() = delete; // Prevents default constructor AuthDelegateImpl( const std::string& appId) // AppID for registered Microsoft Entra app : mAppId(appId) {}; bool AcquireOAuth2Token( // Called by MIP SDK to get a token const mip::Identity& identity, // Identity of the account to be authenticated, if known const OAuth2Challenge& challenge, // Authority (Microsoft Entra tenant issuing token), and resource (API being accessed; "aud" claim). const std::shared_ptr<void>& context, // Opaque context passed by the host application through the MIP API OAuth2Token& token) override; // Token handed back to MIP SDK private: std::string mAppId; std::string mToken; std::string mAuthority; std::string mResource; };Zaktualizuj element "auth_delegate.cpp", zastępując całą implementację wygenerowanej
auth_delegateklasy następującym źródłem. Nie usuwaj dyrektyw preprocesora wygenerowanych w poprzednim kroku (#pragma, #include).Ważne
Poniższy kod pozyskiwania tokenu nie jest odpowiedni do użytku produkcyjnego. W środowisku produkcyjnym zastąp go kodem, który dynamicznie uzyskuje token przy użyciu:
- appId i URI odpowiedzi/przekierowania określone w rejestracji aplikacji Microsoft Entra (URI odpowiedzi/przekierowania musi być zgodny z rejestracją aplikacji)
- Adres URL autorytetu i zasobu, przekazany przez SDK w argumencie
challenge, (adres URL zasobu musi być zgodny z API/uprawnieniami rejestracji aplikacji) - Prawidłowe poświadczenia aplikacji/użytkownika, w których konto jest zgodne z argumentem
identityprzekazanym za pomocą SDK. Klienci OAuth2 "wbudowani" powinni prosić o poświadczenia użytkownika i używać przepływu "kodu autoryzacji". Protokół OAuth2 "konfidencjonalni klienci" mogą używać własnych bezpiecznych poświadczeń w przepływie "poświadczeń klienta" (takim jak usługa) lub żądać poświadczeń użytkownika przy użyciu przepływu "kodu autoryzacyjnego" (na przykład aplikacji internetowej).
Pozyskiwanie tokenu OAuth2 jest złożonym protokołem i jest zwykle realizowane przy użyciu biblioteki. TokenAcquireOAuth2Token() jest wywoływany tylko przez zestaw MIP SDK, zgodnie z wymaganiami.
#include <iostream> using std::cout; using std::cin; using std::string; bool AuthDelegateImpl::AcquireOAuth2Token(const mip::Identity& identity, const OAuth2Challenge& challenge, const std::shared_ptr<void>& context, OAuth2Token& token) { (void)context; // Acquire a token manually, reuse previous token if same authority/resource. In production, replace with token acquisition code. string authority = challenge.GetAuthority(); string resource = challenge.GetResource(); if (mToken == "" || (authority != mAuthority || resource != mResource)) { cout << "\nRun the PowerShell script to generate an access token using the following values, then copy/paste it below:\n"; cout << "Set $authority to: " + authority + "\n"; cout << "Set $resourceUrl to: " + resource + "\n"; cout << "Sign in with user account: " + identity.GetEmail() + "\n"; cout << "Enter access token: "; cin >> mToken; mAuthority = authority; mResource = resource; system("pause"); } // Pass access token back to MIP SDK token.SetAccessToken(mToken); // True = successful token acquisition; False = failure return true; }
Opcjonalnie użyj F6 (Kompiluj rozwiązanie), aby uruchomić kompilowanie/łącze testowe rozwiązania, aby upewnić się, że kompilacja została pomyślnie skompilowana przed kontynuowaniem.
Zaimplementować delegata zgody
Teraz utwórz implementację delegata zgody, dziedzicząc po klasie mip::ConsentDelegate z pakietu SDK i nadpisując lub implementując czysto wirtualną funkcję mip::AuthDelegate::GetUserConsent(). Obiekty File profile i File engine tworzą instancję delegata zgody i używają go później.
Korzystając z tej samej funkcji "Dodaj klasę" programu Visual Studio, której użyliśmy wcześniej, dodaj kolejną klasę do projektu. Tym razem wprowadź tekst "consent_delegate" w polu Nazwa klasy.
Teraz zaktualizuj każdy plik, aby zaimplementować nową klasę delegata zgody:
Zaktualizuj "consent_delegate.h", zastępując cały wygenerowany kod klasy
consent_delegatenastępującym kodem źródłowym. Nie usuwaj dyrektyw preprocesora wygenerowanych w poprzednim kroku (#pragma, #include):#include "mip/common_types.h" #include <string> class ConsentDelegateImpl final : public mip::ConsentDelegate { public: ConsentDelegateImpl() = default; virtual mip::Consent GetUserConsent(const std::string& url) override; };Zaktualizuj plik "consent_delegate.cpp", zastępując całą implementację klasy
consent_delegatewygenerowanej kodem następującym. Nie usuwaj dyrektyw preprocesora wygenerowanych w poprzednim kroku (#pragma, #include).#include <iostream> using mip::Consent; using std::string; Consent ConsentDelegateImpl::GetUserConsent(const string& url) { // Accept the consent to connect to the url std::cout << "SDK will connect to: " << url << std::endl; return Consent::AcceptAlways; }
Opcjonalnie użyj F6 (Kompiluj rozwiązanie), aby uruchomić kompilowanie/łącze testowe rozwiązania, aby upewnić się, że kompilacja została pomyślnie skompilowana przed kontynuowaniem.
Tworzenie profilu pliku i silnika
Jak wspomniano, klienci zestawu SDK korzystający z interfejsów API MIP wymagają obiektów profilu i silnika. Ukończ część tego przewodnika szybkiego startu dotyczącą kodu, dodając kod w celu utworzenia instancji obiektów profilu i silnika:
W Eksploratorze rozwiązań otwórz plik .cpp w projekcie zawierający implementację
main()metody . Domyślnie ma taką samą nazwę jak projekt zawierający go, który został określony podczas tworzenia projektu.Usuń wygenerowaną implementację elementu
main(). Nie usuwaj dyrektyw preprocesora generowanych przez program Visual Studio podczas tworzenia projektu (#pragma, #include). Dołącz następujący kod po wszelkich dyrektywach preprocesora:
#include "mip/mip_context.h"
#include "auth_delegate.h"
#include "consent_delegate.h"
#include "profile_observer.h"
using std::promise;
using std::future;
using std::make_shared;
using std::shared_ptr;
using std::string;
using std::cout;
using mip::ApplicationInfo;
using mip::FileProfile;
using mip::FileEngine;
int main()
{
// Construct/initialize objects required by the application's profile object
// ApplicationInfo object (App ID, name, version)
ApplicationInfo appInfo{"<application-id>",
"<application-name>",
"<application-version>"};
// Create MipConfiguration object.
std::shared_ptr<mip::MipConfiguration> mipConfiguration = std::make_shared<mip::MipConfiguration>(appInfo,
"mip_data",
mip::LogLevel::Trace,
false,
mip::CacheStorageType::OnDisk);
std::shared_ptr<mip::MipContext> mMipContext = mip::MipContext::Create(mipConfiguration);
auto profileObserver = make_shared<ProfileObserver>(); // Observer object
auto authDelegateImpl = make_shared<AuthDelegateImpl>("<application-id>"); // Authentication delegate object (App ID)
auto consentDelegateImpl = make_shared<ConsentDelegateImpl>(); // Consent delegate object
// Construct/initialize profile object
FileProfile::Settings profileSettings(
mMipContext,
mip::CacheStorageType::OnDisk,
consentDelegateImpl,
profileObserver);
// Set up promise/future connection for async profile operations; load profile asynchronously
auto profilePromise = make_shared<promise<shared_ptr<FileProfile>>>();
auto profileFuture = profilePromise->get_future();
try
{
mip::FileProfile::LoadAsync(profileSettings, profilePromise);
}
catch (const std::exception& e)
{
cout << "An exception occurred... are the Settings and ApplicationInfo objects populated correctly?\n\n" << e.what() << "'\n";
system("pause");
return 1;
}
auto profile = profileFuture.get();
// Construct/initialize engine object
FileEngine::Settings engineSettings(
mip::Identity("<engine-account>"), // Engine identity (account used for authentication)
authDelegateImpl, // Token acquisition implementation
"<engine-state>", // User-defined engine state
"en-US"); // Locale (default = en-US)
// Set the engineId for caching.
engineSettings.SetEngineId("<engine-account>");
// Set up promise/future connection for async engine operations; add engine to profile asynchronously
auto enginePromise = make_shared<promise<shared_ptr<FileEngine>>>();
auto engineFuture = enginePromise->get_future();
profile->AddEngineAsync(engineSettings, enginePromise);
std::shared_ptr<FileEngine> engine;
try
{
engine = engineFuture.get();
}
catch (const std::exception& e)
{
cout << "An exception occurred... is the access token incorrect/expired?\n\n" << e.what() << "'\n";
system("pause");
return 1;
}
// Application shutdown. Null out profile and engine, call ReleaseAllResources();
// Application may crash at shutdown if resources aren't properly released.
// handler = nullptr; // This will be used in later quick starts.
engine = nullptr;
profile = nullptr;
mMipContext->ShutDown();
mMipContext = nullptr;
return 0;
}
Zastąp wszystkie wartości zastępcze w kodzie źródłowym, który wkleiłeś, za pomocą stałych znakowych:
Placeholder Wartość Example <identyfikator aplikacji> Identyfikator aplikacji (GUID) Microsoft Entra przypisany do aplikacji zarejestrowanej w kroku 2 artykułu "Konfiguracja i konfiguracja zestawu MIP SDK". Zastąp 2 wystąpienia. "00001111-aaaa-2222-bbbb-3333cccc4444"<nazwa aplikacji> Przyjazna nazwa aplikacji zdefiniowana przez użytkownika. Musi zawierać prawidłowe znaki ASCII (z wyłączeniem znaku ";") i najlepiej odpowiada nazwie aplikacji użytej w rejestracji firmy Microsoft Entra. "AppInitialization"<wersja aplikacji> Informacje o wersji zdefiniowanej przez użytkownika dla aplikacji. Musi zawierać prawidłowe znaki ASCII (z wyłączeniem znaku ";"). "1.1.0.0"<konto silnika> Konto używane dla tożsamości silnika. Podczas uwierzytelniania przy użyciu konta użytkownika podczas pozyskiwania tokenu musi być zgodna z tą wartością. "user1@tenant.onmicrosoft.com"<stan silnika> Stan zdefiniowany przez użytkownika do skojarzenia z silnikiem. "My App State"Wykonaj ostateczną kompilację aplikacji i rozwiąż wszelkie błędy. Kod powinien zostać skompilować pomyślnie, ale nie został jeszcze uruchomiony poprawnie. Nie masz tokenu dostępu, który można podać, dopóki nie ukończysz następnego przewodnika Szybki start.
Następne kroki
Teraz, gdy Twój kod inicjalizacyjny jest gotowy, możesz przejść do następnego przewodnika Szybki start, w którym zaczniesz poznawać zestaw SDK MIP File.