Bagikan melalui


Mulai cepat: Inisialisasi aplikasi klien (C++)

Mulai cepat ini menunjukkan kepada Anda cara menerapkan pola inisialisasi klien, yang digunakan oleh MIP C++ SDK saat runtime.

Catatan

Langkah-langkah yang diuraikan dalam mulai cepat ini diperlukan untuk aplikasi klien apa pun yang menggunakan SDK File, Kebijakan, atau Perlindungan MIP. Meskipun Mulai Cepat ini menunjukkan penggunaan SDK File, pola yang sama ini berlaku untuk klien yang menggunakan SDK Kebijakan dan Perlindungan. Selesaikan Quickstarts yang tersisa secara serial, karena masing-masing dibuat pada yang sebelumnya, dengan yang ini menjadi yang pertama.

Prasyarat

Jika Anda belum melakukannya, pastikan untuk:

  • Selesaikan langkah-langkah dalam penyiapan dan konfigurasi SDK Microsoft Information Protection (MIP). Mulai Cepat "Inisialisasi aplikasi klien" ini bergantung pada penyiapan dan konfigurasi SDK yang tepat.
  • Opsional:
    • Tinjau Profil dan objek mesin. Objek profil dan mesin adalah konsep universal, yang diperlukan oleh klien yang menggunakan SDK File/Kebijakan/Perlindungan MIP.
    • Tinjau konsep Autentikasi untuk mempelajari bagaimana autentikasi dan persetujuan diterapkan oleh SDK dan aplikasi klien.
    • Tinjau konsep Observer untuk mempelajari lebih lanjut tentang pengamat, dan bagaimana penerapannya. MIP SDK menggunakan pola pengamat untuk mengimplementasikan pemberitahuan peristiwa asinkron.

Membuat solusi dan proyek Visual Studio

Pertama, kita membuat dan mengonfigurasi solusi dan proyek Visual Studio awal, di mana Mulai Cepat lainnya dibuat.

  1. Buka Visual Studio 2017, pilih menu File , Baru, Proyek. Dalam dialog Proyek Baru:

    • Di panel kiri, di bawah Terinstal, Bahasa Lain, pilih Visual C++.

    • Di panel tengah, pilih Aplikasi Konsol Windows

    • Di panel bawah, perbarui nama proyek, Lokasi, dan nama Solusi yang berisi yang sesuai.

    • Setelah selesai, klik tombol OK di kanan bawah.

      Visual Studio solution creation

  2. Tambahkan paket Nuget untuk MIP File SDK ke proyek Anda:

    • Di Penjelajah Solusi, klik kanan simpul proyek (langsung di bawah node atas/solusi), dan pilih Kelola paket NuGet...:

    • Saat tab Pengelola Paket NuGet terbuka di area tab Grup Editor:

      • Pilih Telusur.
      • Masukkan "Microsoft.InformationProtection" di kotak pencarian.
      • Pilih paket "Microsoft.InformationProtection.File".
      • Klik "Instal", lalu klik "OK" saat dialog Konfirmasi perubahan pratinjau ditampilkan.

      Visual Studio add NuGet package

Menerapkan kelas pengamat untuk memantau profil file dan objek mesin

Sekarang buat implementasi dasar untuk kelas pengamat profil File, dengan memperluas kelas SDK mip::FileProfile::Observer . Pengamat dibuat dan digunakan nanti, untuk memantau pemuatan objek profil File, dan menambahkan objek mesin ke profil.

  1. Tambahkan kelas baru ke proyek Anda, yang menghasilkan file header/.h dan implementasi/.cpp untuk Anda:

    • Di Penjelajah Solusi, klik kanan simpul proyek lagi, pilih Tambahkan, lalu pilih Kelas.

    • Pada dialog Tambahkan Kelas:

      • Di bidang Nama Kelas, masukkan "profile_observer". Perhatikan bahwa bidang file .h dan file .cpp diisi secara otomatis, berdasarkan nama yang Anda masukkan.
      • Setelah selesai, klik tombol OK .

      Visual Studio add class

  2. Setelah membuat file .h dan .cpp untuk kelas , kedua file dibuka di tab Grup Editor. Sekarang perbarui setiap file untuk mengimplementasikan kelas pengamat baru Anda:

    • Perbarui "profile_observer.h", dengan memilih/menghapus kelas yang dihasilkan profile_observer . Jangan hapus arahan preproscessor yang dihasilkan oleh langkah sebelumnya (#pragma, #include). Kemudian salin/tempel sumber berikut ke dalam file, setelah direktif praprosesor yang ada:

      #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;
      };
      
    • Perbarui "profile_observer.cpp", dengan memilih/menghapus implementasi kelas yang dihasilkan profile_observer . Jangan hapus arahan preproscessor yang dihasilkan oleh langkah sebelumnya (#pragma, #include). Kemudian salin/tempel sumber berikut ke dalam file, setelah direktif praprosesor yang ada:

      #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);
      }
      
  3. Secara opsional, gunakan F6 (Build Solution) untuk menjalankan kompilasi/tautan pengujian solusi Anda, untuk memastikannya berhasil dibangun sebelum melanjutkan.

Menerapkan delegasi autentikasi

MIP SDK menerapkan autentikasi menggunakan ekstensibilitas kelas, yang menyediakan mekanisme untuk berbagi pekerjaan autentikasi dengan aplikasi klien. Klien harus memperoleh token akses OAuth2 yang sesuai, dan menyediakan ke MIP SDK saat runtime.

Sekarang buat implementasi untuk delegasi autentikasi, dengan memperluas kelas SDK mip::AuthDelegate , dan menimpa/mengimplementasikan mip::AuthDelegate::AcquireOAuth2Token() fungsi virtual murni. Delegasi autentikasi dibuat dan digunakan nanti, oleh profil File dan objek Mesin file.

  1. Menggunakan fitur "Tambahkan Kelas" Visual Studio yang sama dengan yang kami gunakan di langkah #1 dari bagian sebelumnya, tambahkan kelas lain ke proyek Anda. Kali ini, masukkan "auth_delegate" di bidang Nama Kelas.

  2. Sekarang perbarui setiap file untuk mengimplementasikan kelas delegasi autentikasi baru Anda:

    • Perbarui "auth_delegate.h", dengan mengganti semua kode kelas yang dihasilkan auth_delegate dengan sumber berikut. Jangan hapus direktif pra-prosesor yang dihasilkan oleh langkah sebelumnya (#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 AAD 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 (AAD tenant issuing token), and resource (API being accessed; "aud" claim).
             OAuth2Token& token) override;     // Token handed back to MIP SDK
      
      private:
           std::string mAppId;
           std::string mToken;
           std::string mAuthority;
           std::string mResource;
      };
      
    • Perbarui "auth_delegate.cpp", dengan mengganti semua implementasi kelas yang dihasilkan auth_delegate dengan sumber berikut. Jangan hapus arahan preproscessor yang dihasilkan oleh langkah sebelumnya (#pragma, #include).

      Penting

      Kode akuisisi token berikut tidak cocok untuk penggunaan produksi. Dalam produksi, ini harus diganti dengan kode yang secara dinamis memperoleh token, menggunakan:

      • URI appId dan balasan/pengalihan yang ditentukan dalam pendaftaran aplikasi Microsoft Entra Anda (URI balasan/pengalihan harus cocok dengan pendaftaran aplikasi Anda)
      • OTORITAS dan URL sumber daya yang diteruskan oleh SDK dalam challenge argumen (URL sumber daya harus cocok dengan API/izin pendaftaran aplikasi Anda)
      • Kredensial aplikasi/pengguna yang valid, di mana akun cocok dengan argumen yang identity diteruskan oleh SDK. Klien "asli" OAuth2 harus meminta kredensial pengguna dan menggunakan alur "kode otorisasi". "Klien rahasia" OAuth2 dapat menggunakan kredensial aman mereka sendiri dengan alur "kredensial klien" (seperti layanan), atau meminta kredensial pengguna menggunakan alur "kode otorisasi" (seperti aplikasi web).

      Akuisisi token OAuth2 adalah protokol yang kompleks, dan biasanya dicapai dengan menggunakan pustaka. TokenAcquireOAuth2Token() hanya dipanggil oleh MIP SDK, sesuai kebutuhan.

      #include <iostream>
      using std::cout;
      using std::cin;
      using std::string;
      
      bool AuthDelegateImpl::AcquireOAuth2Token(const mip::Identity& identity, const OAuth2Challenge& challenge, OAuth2Token& token) 
      {
           // 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;
      }
      
  3. Secara opsional, gunakan F6 (Build Solution) untuk menjalankan kompilasi/tautan pengujian solusi Anda, untuk memastikannya berhasil dibangun sebelum melanjutkan.

Sekarang buat implementasi untuk delegasi persetujuan, dengan memperluas kelas SDK mip::ConsentDelegate , dan mengambil alih/menerapkan mip::AuthDelegate::GetUserConsent() fungsi virtual murni. Delegasi persetujuan dibuat dan digunakan nanti, oleh profil File dan objek mesin file.

  1. Menggunakan fitur "Tambahkan Kelas" Visual Studio yang sama dengan yang kami gunakan sebelumnya, tambahkan kelas lain ke proyek Anda. Kali ini, masukkan "consent_delegate" di bidang Nama Kelas.

  2. Sekarang perbarui setiap file untuk mengimplementasikan kelas delegasi persetujuan baru Anda:

    • Perbarui "consent_delegate.h", dengan mengganti semua kode kelas yang dihasilkan consent_delegate dengan sumber berikut. Jangan hapus direktif pra-prosesor yang dihasilkan oleh langkah sebelumnya (#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;
      };
      
    • Perbarui "consent_delegate.cpp", dengan mengganti semua implementasi kelas yang dihasilkan consent_delegate dengan sumber berikut. Jangan hapus arahan preproscessor yang dihasilkan oleh langkah sebelumnya (#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;
      }
      
  3. Secara opsional, gunakan F6 (Build Solution) untuk menjalankan kompilasi/tautan pengujian solusi Anda, untuk memastikannya berhasil dibangun sebelum melanjutkan.

Membuat profil dan mesin File

Seperti disebutkan, profil dan objek mesin diperlukan untuk klien SDK menggunakan API MIP. Lengkapi bagian pengkodean mulai cepat ini, dengan menambahkan kode untuk membuat instans profil dan objek mesin:

  1. Dari Penjelajah Solusi, buka file .cpp dalam proyek Anda yang berisi implementasi main() metode . Ini default ke nama yang sama dengan proyek yang berisinya, yang Anda tentukan selama pembuatan proyek.

  2. Hapus implementasi yang dihasilkan dari main(). Jangan hapus arahan preproscessor yang dihasilkan oleh Visual Studio selama pembuatan proyek (#pragma, #include). Tambahkan kode berikut setelah direktif praprosesor apa pun:

#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);


  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;
  }
  1. Ganti semua nilai tempat penampung dalam kode sumber yang baru saja Anda tempelkan, menggunakan konstanta string:

    Placeholder Nilai Contoh
    <application-id> ID Aplikasi Microsoft Entra (GUID) yang ditetapkan ke aplikasi yang terdaftar di langkah #2 dari artikel "Penyiapan dan konfigurasi SDK MIP" . Ganti 2 instans. "0edbblll-8773-44de-b87c-b8c6276d41eb"
    <nama aplikasi> Nama ramah yang ditentukan pengguna untuk aplikasi Anda. Harus berisi karakter ASCII yang valid (tidak termasuk ';'), dan idealnya cocok dengan nama aplikasi yang Anda gunakan dalam pendaftaran Microsoft Entra Anda. "AppInitialization"
    <versi aplikasi> Info versi yang ditentukan pengguna untuk aplikasi Anda. Harus berisi karakter ASCII yang valid (tidak termasuk ';'). "1.1.0.0"
    <akun mesin> Akun yang digunakan untuk identitas mesin. Saat Anda mengautentikasi dengan akun pengguna selama akuisisi token, itu harus cocok dengan nilai ini. "user1@tenant.onmicrosoft.com"
    <status mesin> Status yang ditentukan pengguna untuk dikaitkan dengan mesin. "My App State"
  2. Sekarang lakukan build akhir aplikasi dan atasi kesalahan apa pun. Kode Anda harus berhasil dibuat, tetapi belum akan berjalan dengan benar sampai Anda menyelesaikan Mulai Cepat berikutnya. Jika Anda menjalankan aplikasi, Anda akan melihat output yang mirip dengan yang berikut ini. Anda tidak akan memiliki token akses untuk disediakan, hingga Anda menyelesaikan Mulai Cepat berikutnya.

Langkah berikutnya

Setelah kode inisialisasi selesai, Anda siap untuk mulai cepat berikutnya, tempat Anda akan mulai mengalami SDK File MIP.