Windows AzureのCloud ServicesではWindows Server 2012ベースのGuest OS 3.xを使用してPaaSなWebやWorkerを作れます。
さてさてこのGuest OS 3.xなCloud Servicesですが、意外な嵌りどころがあるようなので注意が必要です。結構クリティカル。※2013年2月現在。
Windows AzureのCloud ServicesではWindows Server 2012ベースのGuest OS 3.xを使用してPaaSなWebやWorkerを作れます。
さてさてこのGuest OS 3.xなCloud Servicesですが、意外な嵌りどころがあるようなので注意が必要です。結構クリティカル。※2013年2月現在。
2月1日はWindows Azureの商用サービスが開始された日です。なので今日は3周年記念日。
あっという間でしたね。
まだまだPreviewの機能があるし、今後も拡張されていくでしょうから楽しみです。
GAは唐突に。そう唐突に。
ScottGu’s Blog (日本語訳)にもある通り、Windows Azure Media Servicesが一般提供(General Availability)されました。

一般提供が開始されたということは、SLAが付いたということです。ちょっと日本語のフォントがおかしいですがSLAはこちらから入手できます。
※フォント指定しなおしたらちゃんと見えます。
SLAは2種類あって1つはオンデマンドストリーミングの月間稼働時間、もう1つはメディアサービスのエンコードREST APIのトランザクション数のようです。どちらも99.9%を下回ると10%返金のようですね。気になる人はちゃんと読みましょう。
気になるお値段ですが、以下の4種類で変わりますので注意。
とりあえずメディアサービスのエンコードに関しては2013年2月17日までは課金されないようです。課金単位は「処理されたデータ量」で、データの入力とエンコードされたデータの出力両方が対象です。※保存先のストレージとそれにかかるデータ転送料も別途かかります。
最初の5TBまでは 173.95円/GByte。
占有ユニットを使用してエンコードの並列処理ができますが、その占有ユニットあたり8,653.59円/月かかります。ちょっと計算がややこしいようです。
アカウントでプロビジョニングされた状態の占有ユニットの最大数を使用して日割りで計算されます (24 時間単位)。たとえば、11:00 にエンコードの占有ユニットを 5 個購入した後、15:00 にその数を 3 個に減らした場合、その日は 5 個の占有ユニットに対して料金が発生します。23:00 にエンコードの占有ユニットを 5 個購入した後、翌日 10:00 にその数を 3 個に減らした場合、1 日目は 5 個の占有ユニットに対して料金が発生し、2 日目も、最初の 10 時間は 5 個の占有ユニットを所有していたため同様の料金が発生します。
まぁ、注意しましょう、ということですね。占有ユニットを使わない場合はこの費用は掛からないみたいです。
オンデマンドストリーミングする場合、ユニットあたり17,394.59円/月かかります。アクティブだった占有ユニットの最大数の24時間単位な日割りで計算なのでこちらも注意。またAzureからのデータ送信は別途費用が発生します。
パッケージングそのものは無料でOK
というわけで料金詳細はこちら。
ちなみにオンデマンドストリーミング、エンコーディングについては管理ポータルの「スケール」で変更することができます。既定はどちらも占有ゼロ状態なので安心ですね(?)
Windows Azure Media Servicesを使ったサービスを開発する場合、Media Services libraries for .NET (Windows Azure Media Services .NET SDK) とMedia Services libraries for Javaの2種類があるようです。JavaのほうはAzure SDKに含まれてるからそっち見てね。とのこと。
Java使えるから一応WIndows/Mac/Linuxで開発できますね。
動画を見るクライアント側のSDKとしてはSmooth Streaming Client SDKがWindows 8用、SilverlightとWindows Phone用の2種類、それからOSMF向けPluginとiOS Media Player Frameworkが提供されています。
ということで、以下のようなクライアントたちをターゲットに配信できちゃいます。
やったね☆

動画の処理はメディアサービスが行ってくれますが、実際に大量の動画データをAzure側に送り込む必要があるので大変です。そんなときは一括アップロードしちゃいましょう。またUDPを使ったAsperaで高速アップロードも使えるので必要に応じて使いましょう。
というわけで、GAされて一安心。動画配信プラットフォームはSmooth Streaming+Windows Azure Media Servicesでキマリですね。
むかーしむかーし、数多の質問があった(と思う)Mac OS XからRDPでWindows Azureのクラウドサービスは管理できないのか!?というお話ですが、ふと @kunyami としゃべっていてできそうな方法あったのでテストしてみました。
以前、「Windows Azureを作ってみた」で紹介したMicrosoft Hosting Solutions Servicesが無事GA(General Availability)されたようです!
( ゚Д゚ノノ”☆パチパチパチパチ
いわゆるクラウド事業者さん向けの、Windows Azure Webサイトや仮想マシンのホスティング環境を実現させるための機能集みたいなものです。
肝となるのは、すべてのベースとなるWindows Server 2012、ホストマシンを効率よく管理するためのSystem Center 2012(SP1)、それからユーザーにサービスを提供する入り口となる管理ポータルと管理用REST API集の3本です。
それぞれ細かいインストール方法などはMicrosoft Hosting Solutions Servicesのサイトにリンクがあるのでそちらを見てください。
雰囲気としては

こんな感じのインフラがゴールになります。
Multi-tenant PortalってのがWindows Azure管理ポータルっぽい画面ですね。
もちろんホスティング事業者向けなのでテナント別に機能制限かけたりすることもできます。
さぁこれであなたもAzureにならなイカ!
移行とかでDBはやむを得ずそのままでフロントは頑張った系の構成つくろう、つまり Windows Azureのクラウドサービス(Web RoleとかWorker Role)をVirtual Networkに参加させちゃおうという話です。
ついでに同じVirtual NetworkにWindows Azure 仮想マシンも参加させてサービス間通信もしちゃいましょう。
今回想定しているのはざっくり以下のような構成です。
バックエンドのVMはDBとかまぁそういうのを想定。通信の方向性としては双方向で通信できますが、今回はフロントのWebRoleからVMへのアクセスを想定します。
といっても対してすることは無く。Web RoleなどのCloud ServicesでのVirtual Networkへの参加方法と、VMのVirutla Networkへの参加方法、名前解決についてあたりを書こうと思います。
以前、ロール間通信の話をちょっと書きましたが、なんかもっと簡単にできそうでした。(クラウドサービスが対象です)
Windows Azureのクラウドサービス上で稼働するインスタンスのホスト名は伝統的なピンクぷーどrではなくRedDogの頭文字、RDで始まるランダムなもので、よくわかりませんでした。
ですが、サービス設定ファイル(*.cscfg)のRole要素でvmName属性を使用すると、指定した名前+連番でインスタンスを設定してくれるようです。
サービス設定ファイルの例↓
<?xml version="1.0" encoding="utf-8"?> <ServiceConfiguration serviceName="WindowsAzure18_45" xmlns="http://schemas.microsoft.com/ServiceHosting/2008/10/ServiceConfiguration" osFamily="3" osVersion="*" schemaVersion="2012-10.1.8"> <Role name="MvcWebRole1" vmName="KOSMOS"> <Instances count="3" /> <ConfigurationSettings> 以下略
ほうほう。実際にデプロイしてみましょう。
おお、確かにホスト名がvmNameで指定したもの+連番(ゼロオリジン)です!
ちなみにDNSサフィックスは
02158fc001144d09bf43a37f3660d936.penguindrum.3216464207.asiaeast.internal.cloudapp.net
となってますね。
最初の赤字部分はデプロイID、次の青字部分はクラウドサービスの名前です。asiaeastは配置場所(DC)、internal.cloudapp.netはまぁ固定でクラウドサービスの内部って意味でしょうけど、1つよくわからないのがありますね~。普通に考えるとDC内の何かの(たぶん論理)単位ですね。まぁ自身のDNSサフィックス調べれば生成する必要ないのであまり意味はありませんが。
もちろんクラウドサービス内で有効なだけですけど、ちゃんと名前解決もできる=ポートさえ空いていれば通信ができます。
これでHOSTSを弄ったり、変なEndpoint定義したりしなくてもいいですね!!
ちなみに、このvmName属性はSDK1.7以降で使えるようです。いろいろ増えてるんだなぁ~。
Windows Azure Advent Calrendar jp: 2012 の #24です。
みなさんご存知の通り、Windows Azureのクラウドサービスおよび仮想マシンでWindows Server 2012が利用できます。
※残念ながらAzure WebサイトはまだWindows Server 2008 R2ベース。
仮想マシンは自分でいろいろ設定して永続化しておけるのでどうってことは無いんですが、みんな大好きクラウドサービスはそういうわけにはいきません。
で、せっかくクラウドサービスのGuest OS 3.xで、Windows Server 2012つまりIIS8が使えるようになったので、ARR(Application Request Router)も対応したものを使いましょーというのが主旨です。
IIS8に対応したARRv3はExternal CacheやURL Rewriteもこれまで通り使えますし、なんといってもWebSocketに対応してるのが嬉しいですね。
とはいえ、IIS8に対応したARRv3はまだBetaなので利用には注意が必要ですが。
いつものように管理ポータルで操作してたらいきなり「新しいバージョンのポータルが利用できます」って表示されてリロードしたらいろいろ新しくなってました(
ということで簡単に気づいた点など。(※差分が分からないので前から実装されてたのがあるかもしれない。)
Windows Azure上でインスタンス間通信する場合、相手のIPアドレスがわからないと何もできません。通常IPアドレスはインスタンス起動時に適当に振られるので、RoleEnvironmentを使ってインスタンスのIPEndpointを取得するのですが、どうもInputEndpointから取れなくなったっぽい。
※インスタンスを列挙してそのインスタンスのIPEndpointを取得してIPアドレスをゲットする、という方法ですが他のインスタンスのInputEndpointが取れない。
ぽい、というのは昔とれた気がするんですけど、SDK1.8だと取れないんですよね。いつからか不明だけどVPNが来たりしたSpring Waveのときかなぁ?
というわけでSDK1.8時代のロール間通信はInternalEndpointを明示的に指定して、そいつのIPEndpointを参照しましょう、という感じになります。
取得するコード的にはこんな感じです。
var role = Microsoft.WindowsAzure.ServiceRuntime.RoleEnvironment.CurrentRoleInstance.Role;
foreach (var instance in role.Instances)
{
foreach (var s in instance.InstanceEndpoints.Values)
{
if (s != null)
{
Console.WriteLine("{0} = {1}:{2}", s.RoleInstance.Id, s.IPEndpoint.Address.ToString(),
s.IPEndpoint.Port);
}
}
}
サービス定義ファイル(CSDEF)はこんな感じ。
<?xml version="1.0" encoding="utf-8"?>
<ServiceDefinition name="WindowsAzure18_45" xmlns="http://schemas.microsoft.com/ServiceHosting/2008/10/ServiceDefinition" schemaVersion="2012-10.1.8">
<WebRole name="MvcWebRole1" vmsize="ExtraSmall">
<Sites>
<Site name="Web">
<Bindings>
<Binding name="Endpoint1" endpointName="Endpoint1" />
<Binding name="Endpoint2" endpointName="Endpoint2" />
</Bindings>
</Site>
</Sites>
<Endpoints>
<InputEndpoint name="Endpoint1" protocol="http" port="80" />
<InternalEndpoint name="Endpoint2" protocol="http" port="8002" />
</Endpoints>
<Imports>
<Import moduleName="RemoteAccess" />
<Import moduleName="RemoteForwarder" />
</Imports>
<Runtime executionContext="elevated">
</Runtime>
</WebRole>
</ServiceDefinition>
テストなので適当にInputEndpointとInternalEndpointを定義してみました。
で、結果はこう。
インスタンス0上で実行しました。他のインスタンスのInputEndpointは取れてないですね。でもInternalEndponitは取れてます。
ということで、何かインスタンス間通信したい場合はInternalEndpointをちゃんと定義しましょう、ということで。
ちなみにコンソールアプリとかで
Unhandled Exception: System.TypeInitializationException: The type initializer fo
r ‘Microsoft.WindowsAzure.ServiceRuntime.RoleEnvironment’ threw an exception. —
-> System.IO.FileLoadException: Could not load file or assembly ‘msshrtmi.dll’ o
r one of its dependencies. A dynamic link library (DLL) initialization routine f
ailed. (Exception from HRESULT: 0x8007045A)
at Microsoft.WindowsAzure.ServiceRuntime.RoleEnvironment.InitializeEnvironmen
t()
at Microsoft.WindowsAzure.ServiceRuntime.RoleEnvironment..cctor()
— End of inner exception stack trace —
at Microsoft.WindowsAzure.ServiceRuntime.RoleEnvironment.get_CurrentRoleInsta
nce()
とか出る場合は以下のようにuseLegacyV2RuntimeActivationPolicyをTrueにすればいいですよ。(結構悩んだ)
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<startup useLegacyV2RuntimeActivationPolicy="true">
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5" />
</startup>
</configuration>
まぁByDesignという感じみたいです。はい。(外部からの受付用のInputEndpointで内部用のIPアドレスが取れちゃうってのも変な話といえば変ですのでいいんですけどね。)