Integrowanie wielu zasobów Czytnik immersyjny

W omówieniu przedstawiono informacje o Czytnik immersyjny oraz o tym, jak implementuje sprawdzone techniki w celu poprawy zrozumienia czytania dla osób uczących się języka, nowych czytelników i uczniów z różnicami w uczeniu się. W przewodniku Szybki start pokazano, jak używać Czytnik immersyjny z pojedynczym zasobem. W tym samouczku opisano sposób integrowania wielu zasobów Czytnik immersyjny w tej samej aplikacji.

Z tego samouczka dowiesz się, jak wykonywać następujące czynności:

  • Utwórz wiele zasobów Czytnik immersyjny w istniejącej grupie zasobów.
  • Uruchom Czytnik immersyjny przy użyciu wielu zasobów.

Wymagania wstępne

  • Subskrypcja platformy Azure. Jeśli jej nie masz, utwórz bezpłatne konto.
  • Pojedynczy zasób Czytnik immersyjny skonfigurowany do uwierzytelniania w usłudze Microsoft Entra. Postępuj zgodnie z tymi instrukcjami , aby skonfigurować.
  • Aplikacja internetowa NodeJS uruchamiana Czytnik immersyjny.

Tworzenie wielu zasobów

Wykonaj te instrukcje ponownie, aby utworzyć każdy zasób Czytnik immersyjny. Skrypt Create-ImmersiveReaderResource ma ResourceNameparametry , ResourceSubdomaini ResourceLocation . Te parametry powinny być unikatowe dla każdego tworzonego zasobu. Pozostałe parametry powinny być takie same jak te, które były używane podczas konfigurowania pierwszego zasobu Czytnik immersyjny. Dzięki temu każdy zasób może być połączony z tą samą grupą zasobów platformy Azure i aplikacją Microsoft Entra.

W poniższym przykładzie pokazano, jak utworzyć dwa zasoby: jeden w regionie WestUS, a drugi w regionie EastUS. Każdy zasób ma unikatowe wartości dla ResourceName, ResourceSubdomaini ResourceLocation.

Create-ImmersiveReaderResource
  -SubscriptionName <SUBSCRIPTION_NAME>
  -ResourceName Resource_name_westus
  -ResourceSubdomain resource-subdomain-westus
  -ResourceSKU <RESOURCE_SKU>
  -ResourceLocation westus
  -ResourceGroupName <RESOURCE_GROUP_NAME>
  -ResourceGroupLocation <RESOURCE_GROUP_LOCATION>
  -AADAppDisplayName <MICROSOFT_ENTRA_DISPLAY_NAME>
  -AADAppIdentifierUri <MICROSOFT_ENTRA_IDENTIFIER_URI>
  -AADAppClientSecret <MICROSOFT_ENTRA_CLIENT_SECRET>

Create-ImmersiveReaderResource
  -SubscriptionName <SUBSCRIPTION_NAME>
  -ResourceName Resource_name_eastus
  -ResourceSubdomain resource-subdomain-eastus
  -ResourceSKU <RESOURCE_SKU>
  -ResourceLocation eastus
  -ResourceGroupName <RESOURCE_GROUP_NAME>
  -ResourceGroupLocation <RESOURCE_GROUP_LOCATION>
  -AADAppDisplayName <MICROSOFT_ENTRA_DISPLAY_NAME>
  -AADAppIdentifierUri <MICROSOFT_ENTRA_IDENTIFIER_URI>
  -AADAppClientSecret <MICROSOFT_ENTRA_CLIENT_SECRET>

Dodawanie zasobów do konfiguracji środowiska

W przewodniku Szybki start utworzono plik konfiguracji środowiska zawierający TenantIdparametry , ClientId, ClientSecreti Subdomain . Ponieważ wszystkie zasoby korzystają z tej samej aplikacji firmy Microsoft Entra, możesz użyć tych samych wartości dla TenantId, ClientIdi ClientSecret. Jedyną zmianą, którą należy wprowadzić, jest wyświetlenie listy każdej poddomeny dla każdego zasobu.

Nowy plik env powinien teraz wyglądać mniej więcej tak:

TENANT_ID={YOUR_TENANT_ID}
CLIENT_ID={YOUR_CLIENT_ID}
CLIENT_SECRET={YOUR_CLIENT_SECRET}
SUBDOMAIN_WUS={YOUR_WESTUS_SUBDOMAIN}
SUBDOMAIN_EUS={YOUR_EASTUS_SUBDOMAIN}

Uwaga

Pamiętaj, aby nie zatwierdzać tego pliku w kontroli źródła, ponieważ zawiera wpisy tajne, które nie powinny być upublicznione.

Następnie zmodyfikuj plik routes\index.js utworzony w celu obsługi wielu zasobów. Zastąp jego zawartość następującym kodem.

Tak jak wcześniej ten kod tworzy punkt końcowy interfejsu API, który uzyskuje token uwierzytelniania entra firmy Microsoft przy użyciu hasła jednostki usługi. Tym razem umożliwia użytkownikowi określenie lokalizacji zasobu i przekazanie jej jako parametru zapytania. Następnie zwraca obiekt zawierający token i odpowiednią poddomenę.

var express = require('express');
var router = express.Router();
var request = require('request');

/* GET home page. */
router.get('/', function(req, res, next) {
  res.render('index', { title: 'Express' });
});

router.get('/GetTokenAndSubdomain', function(req, res) {
    try {
        request.post({
            headers: {
                'content-type': 'application/x-www-form-urlencoded'
            },
            url: `https://login.windows.net/${process.env.TENANT_ID}/oauth2/token`,
            form: {
                grant_type: 'client_credentials',
                client_id: process.env.CLIENT_ID,
                client_secret: process.env.CLIENT_SECRET,
                resource: 'https://cognitiveservices.azure.com/'
            }
        },
        function(err, resp, tokenResult) {
            if (err) {
                console.log(err);
                return res.status(500).send('CogSvcs IssueToken error');
            }

            var tokenResultParsed = JSON.parse(tokenResult);

            if (tokenResultParsed.error) {
                console.log(tokenResult);
                return res.send({error :  "Unable to acquire Azure AD token. Check the debugger for more information."})
            }

            var token = tokenResultParsed.access_token;

            var subdomain = "";
            var region = req.query && req.query.region;
            switch (region) {
                case "eus":
                    subdomain = process.env.SUBDOMAIN_EUS
                    break;
                case "wus":
                default:
                    subdomain = process.env.SUBDOMAIN_WUS
            }

            return res.send({token, subdomain});
        });
    } catch (err) {
        console.log(err);
        return res.status(500).send('CogSvcs IssueToken error');
    }
});

module.exports = router;

Punkt getimmersivereaderlaunchparams końcowy interfejsu API powinien być zabezpieczony za jakąś formą uwierzytelniania (na przykład OAuth), aby uniemożliwić nieautoryzowanym użytkownikom uzyskiwanie tokenów do użycia w usłudze Czytnik immersyjny i rozliczeniach; praca ta wykracza poza zakres tego samouczka.

Dodawanie przykładowej zawartości

Otwórz plik views\index.pug i zastąp jego zawartość następującym kodem. Ten kod wypełnia stronę przykładową zawartością i dodaje dwa przyciski uruchamiające Czytnik immersyjny. Taki, który uruchamia Czytnik immersyjny dla zasobu EastUS, a drugi dla zasobu WestUS.

doctype html
html
    head
        title Immersive Reader Quickstart Node.js

        link(rel='stylesheet', href='https://stackpath.bootstrapcdn.com/bootstrap/3.4.1/css/bootstrap.min.css')

        // A polyfill for Promise is needed for IE11 support.
        script(src='https://cdn.jsdelivr.net/npm/promise-polyfill@8/dist/polyfill.min.js')

        script(src='https://ircdname.azureedge.net/immersivereadersdk/immersive-reader-sdk.1.2.0.js')
        script(src='https://code.jquery.com/jquery-3.3.1.min.js')

        style(type="text/css").
            .immersive-reader-button {
            background-color: white;
            margin-top: 5px;
            border: 1px solid black;
            float: right;
            }
    body
        div(class="container")
            button(class="immersive-reader-button" data-button-style="icon" data-locale="en" onclick='handleLaunchImmersiveReader("wus")') WestUS Immersive Reader
            button(class="immersive-reader-button" data-button-style="icon" data-locale="en" onclick='handleLaunchImmersiveReader("eus")') EastUS Immersive Reader

            h1(id="ir-title") About Immersive Reader
            div(id="ir-content" lang="en-us")
            p Immersive Reader is a tool that implements proven techniques to improve reading comprehension for emerging readers, language learners, and people with learning differences. The Immersive Reader is designed to make reading more accessible for everyone. The Immersive Reader

                ul
                    li Shows content in a minimal reading view
                    li Displays pictures of commonly used words
                    li Highlights nouns, verbs, adjectives, and adverbs
                    li Reads your content out loud to you
                    li Translates your content into another language
                    li Breaks down words into syllables

            h3 The Immersive Reader is available in many languages.

            p(lang="es-es") El Lector inmersivo está disponible en varios idiomas.
            p(lang="zh-cn") 沉浸式阅读器支持许多语言
            p(lang="de-de") Der plastische Reader ist in vielen Sprachen verfügbar.
            p(lang="ar-eg" dir="rtl" style="text-align:right") يتوفر \"القارئ الشامل\" في العديد من اللغات.

script(type="text/javascript").
function getTokenAndSubdomainAsync(region) {
        return new Promise(function (resolve, reject) {
            $.ajax({
                url: "/GetTokenAndSubdomain",
                type: "GET",
                data: {
                    region: region
                },
                success: function (data) {
                    if (data.error) {
                        reject(data.error);
                    } else {
                        resolve(data);
                    }
                },
                error: function (err) {
                    reject(err);
                }
            });
        });
    }

    function handleLaunchImmersiveReader(region) {
        getTokenAndSubdomainAsync(region)
            .then(function (response) {
                const token = response["token"];
                const subdomain = response["subdomain"];
                // Learn more about chunk usage and supported MIME types https://learn.microsoft.com/azure/ai-services/immersive-reader/reference#chunk
                const data = {
                    title: $("#ir-title").text(),
                    chunks: [{
                        content: $("#ir-content").html(),
                        mimeType: "text/html"
                    }]
                };
                // Learn more about options https://learn.microsoft.com/azure/ai-services/immersive-reader/reference#options
                const options = {
                    "onExit": exitCallback,
                    "uiZIndex": 2000
                };
                ImmersiveReader.launchAsync(token, subdomain, data, options)
                    .catch(function (error) {
                        alert("Error in launching the Immersive Reader. Check the console.");
                        console.log(error);
                    });
            })
            .catch(function (error) {
                alert("Error in getting the Immersive Reader token and subdomain. Check the console.");
                console.log(error);
            });
    }

    function exitCallback() {
        console.log("This is the callback function. It is executed when the Immersive Reader closes.");
    }

Aplikacja internetowa jest teraz gotowa. Uruchom aplikację, uruchamiając polecenie:

npm start

Otwórz przeglądarkę i przejdź do http://localhost:3000adresu . Na stronie powinna zostać wyświetlona powyższa zawartość. Wybierz przycisk EastUS Czytnik immersyjny lub przycisk WestUS Czytnik immersyjny, aby uruchomić Czytnik immersyjny przy użyciu odpowiednich zasobów.

Następny krok