Visual Studio からの Web アプリのデプロイ では Visual Studio で作成したスケルトン プロジェクトを使って、「空の Azure Node.js Web アプリケーション」テンプレートが生成した簡単な Web アプリを Azure にデプロイする手順をご案内しました。
今回は、同じ手順で作成したプロジェクトに、Forge Node.js クイックスタート ~ その1 や Forge SDK を使用した 3-legged OAuth Access Token 取得 で使った Forge Node.js SDK を組み込み、Basic Application 相当のコードを Web アプリに実装してデプロイします。なお、表示する 3D モデルは、あらかじめ変換済の URN があることを前提とします。
- Visual Studio からの Web アプリのデプロイ でご案内した手順で「空の Azure Node.js Web アプリケーション」テンプレートを使ったスケルトン プロジェクトを作成します。ここでは、プロジェクト名を NodejsWebApp3 とします。
- スケルトン プロジェクトに Forge Node.js SDK パッケージを追加します。[ソリューション エクスプローラ] 上の npm を見つけてマウスの右ボタンでクリックしたら、[新しい npm パッケージをインストールする(N)…] を選択してください。

- [新しい npm パッケージのインストール] ダイアログが表示されたら、左上の検索ボックスに Autodesk Forge を入力して(①)、リストアップされてくる中から「forge-apis x.x.x Autodesk Inc.」 を見つけて選択し(②)、 [パッケージのインストール(I)] ボタンをクリックします(③)。

- [ソリューション エクスプローラ] 上の npm 下に「forge-apis@x.x.x」が追加されたのを確認したら、[新しい npm パッケージのインストール] ダイアログを閉じてください。

'use strict';
var http = require('http');
var ForgeSDK = require('forge-apis');
var port = process.env.PORT || <<YOUR PORT NUMBER>>;
var CLIENT_ID = '<<YOUR CLIENT ID>>',
CLIENT_SECRET = '<<YOOUE CLIENT SECRET>>',
ENCODED_URN = '<<YOUR BASE64 ENCODED URN>>';
http.createServer(function (req, res) {
var oAuth2TwoLegged = new ForgeSDK.AuthClientTwoLeggedV2(CLIENT_ID, CLIENT_SECRET, ['viewables:read'], true);
oAuth2TwoLegged.authenticate().then(function (credentials) {
console.log("**** Got Credentials", credentials);
var token = credentials["access_token"];
var data = [
'<head>',
' <meta name="viewport" content="width=device-width, minimum-scale=1.0, initial-scale=1, user-scalable=no" />',
' <meta charset="utf-8">',
'',
' <!-- The Viewer CSS -->',
' <link rel="stylesheet" href="https://developer.api.autodesk.com/modelderivative/v2/viewers/6.*/style.min.css" type="text/css">',
'',
' <!-- Developer CSS -->',
' <style>',
' body {',
' margin: 0;',
' }',
' #MyViewerDiv {',
' width: 100%;',
' height: 100%;',
' margin: 0;',
' background-color: #F0F8FF;',
' }',
' </style>',
'</head>',
'<body>',
'',
' <!-- The Viewer will be instantiated here -->',
' <div id="MyViewerDiv"></div>',
'',
' <!-- The Viewer JS -->',
' <script src="https://developer.api.autodesk.com/modelderivative/v2/viewers/6.*/viewer3D.min.js"></script>',
'',
' <!-- Developer JS -->',
' <script>',
" var token = '" + token + "';",
" var urn = '" + ENCODED_URN + "';",
'',
' var viewerApp;',
' var _viewer;',
' var options = {',
" env: 'AutodeskProduction',",
' getAccessToken: function(onGetAccessToken) {',
' //',
' // TODO: Replace static access token string below with call to fetch new token from your backend',
" // Both values are provided by Forge's Authentication (OAuth) API.",
' //',
" // Example Forge's Authentication (OAuth) API return value:",
' // {',
' // "access_token": "<YOUR_APPLICATION_TOKEN>",',
' // "token_type": "Bearer",',
' // "expires_in": 86400',
' // }',
' //',
' var accessToken = token;',
' var expireTimeSeconds = 60 * 30;',
' onGetAccessToken(accessToken, expireTimeSeconds);',
' }',
'',
' };',
'',
" var documentId = 'urn:' + urn;",
' Autodesk.Viewing.Initializer(options, function onInitialized(){',
' var avp = Autodesk.Viewing.Private;',
' avp.logger.setLevel( avp.LogLevels.Debug );',
' var config3d = {',
" extensions: ['Autodesk.Viewing.Collaboration']",
' };',
" viewerApp = new Autodesk.Viewing.ViewingApplication('MyViewerDiv');",
' viewerApp.registerViewer(viewerApp.k3D, Autodesk.Viewing.Private.GuiViewer3D, config3d);',
' viewerApp.loadDocument(documentId, onDocumentLoadSuccess, onDocumentLoadFailure);',
' });',
'',
' function onDocumentLoadSuccess(doc) {',
'',
' // We could still make use of Document.getSubItemsWithProperties()',
' // However, when using a ViewingApplication, we have access to the **bubble** attribute,',
' // which references the root node of a graph that wraps each object from the Manifest JSON.',
" var viewables = viewerApp.bubble.search({'type':'geometry'});",
' if (viewables.length === 0) {',
" console.error('Document contains no viewables.');",
' return;',
' }',
'',
' // Choose any of the avialble viewables',
' viewerApp.selectItem(viewables[1].data, onItemLoadSuccess, onItemLoadFail);',
' }',
'',
' function onDocumentLoadFailure(viewerErrorCode) {',
" console.error('onDocumentLoadFailure() - errorCode:' + viewerErrorCode);",
' }',
'',
' function onItemLoadSuccess(viewer, item) {',
" console.log('onItemLoadSuccess()!');",
' console.log(viewer);',
' console.log(item);',
'',
' // Congratulations! The viewer is now ready to be used.',
" console.log('Viewers are equal: ' + (viewer === viewerApp.getCurrentViewer()));",
' _viewer = viewer',
" viewer.search('LDK 202', onSearchResult);",
' }',
'',
' function onItemLoadFail(errorCode) {',
" console.error('onItemLoadFail() - errorCode:' + errorCode);",
' }',
'',
'function onSearchResult(idArray) {',
// ' _viewer.isolate(idArray);',
// ' _viewer.clearSelection();',
// ' _viewer.select(idArray, Autodesk.Viewing.SelectionMode.OVERLAYED);',
' var col = new THREE.Vector4(0, 0, 1, 0.3);',
' _viewer.show(idArray[0]);',
' _viewer.setThemingColor(idArray[0], col);',
'}',
'',
'',
' </script>',
'</body>'
].join('\n');
res.writeHead(200, { 'Content-Type': 'text/html' });
res.write(data);
res.end();
}, function (err) {
res.writeHead(200, { 'Content-Type': 'text/html' });
res.write('ERROR: ' + err.errorCode);
res.end();
console.error('\x1b[31m Error:', err, '\x1b[0m');
});
}).listen(port);
- server.js を修正したプロジェクト(NodejsWebApp3 プロジェクト)の実行をテストしてみます。[デバッグ(D)] メニューから [▶ デバッグッグの開始(S)] を選択して、Web ブラウザが起動後に server.js で指定した URN を持つ 3D モデルが表示されることを確認してください。

- プロジェクトのローカルでの実行が正常なら、Visual Studio からの Web アプリのデプロイ で の手順に沿って Azure へのデプロイをおこないます。ここでは、[App Service の作成] ダイアログで、Visual Studio が自動設定したアプリ名を書き換え、NodejsWebApp3-app に書き換えることにします。リソース グループも NodejsWebApp3-app 名で新規作成することにします。

- [発行] ダイアログでは、各項目を既定値のまま [発行(P)] ボタンをクリックします。

- 発行が正常に完了すると、Azure 上の URL(ここでは https://nodejswebapp3-app.azurewebsites.net/)で指定した 3D モデルを表示されるはずです。

もちろん、WebGL 対応の Web ブラウザさえあれば、デプロイされた Web アプリはデバイスを問わず参照出来るはずです。
今回の例では、Node.js で構築した Web サーバー実装で Forge Node.js SDK を使った Authentication(Forge Web アプリ認証)を経て Access Token を取得し、クライアントからのWeb サーバー リクエスト(URL 入力)に対するレスポンスとして、Basic_Application の内容となる HTML と内包する JavaScript コードを返す(表示させる)コードを作成してみました。

この他にも、多様な Web サーバーを実装することが出来るはずです。
By Toshiaki Isezaki

You must be logged in to post a comment.