今日

WinRM:Windowsリモート管理

EC2でwindowsを扱う。 AMIは名前で検索して日付が最新のものを使う。
Windows_Server-2012-R2_RTM-Japanese-64Bit-Base

amazon AMIで用意されていることの一覧 イメージの変更点

WinRMは構成済み。構成済みのファイアウォールではローカルサブネットからの受信のみが許可されている。インスタンスファイアウォールでは制限をせずに、セキュリティグループで許可するIPアドレスを指定することにする。

ちなみに、LocalAccountTokenFilterPolicy(リモートUAC)は1(無効)に設定されている。ドメイン環境でなくてもリモートから管理者権限で操作ができる。 HKLM\SOFTWARE\Microsoft\Windows\CurrentVersion\policies\system

アカウント名とパスワードでリモートにログインすることになるので、送信側のTrustedHostに送信先を登録する必要がある。ホスト名でもIPアドレスでも*(ワイルドカード)でも可。
winrm set winrm/config/client @{TrustedHosts="Server0"}
既にある値に追記するならpowershell
Set-Item wsman:\localhost\Client\TrustedHosts Server0 -Concatenate -Force

これから

  • WinRM HTTPSトランスポートの構成と-useSSL
  • DSCとWebPIを使って最新AMIからWebサーバーを用意する手順
  • Route53へのパブリックIPの登録の自動化
  • Route53のプライベートホストゾーンを使ってサーバー間を固定の名前で接続する

いま

とりあえずこんな感じでできた。呼ばれるまで接続したまま待つハンドラー。

  • staticフィールドでTaskCompletionSourceとGUIDのリストを持つ。
  • リクエストがきたらGUIDとTaskCompletionSourceを作ってリストに追加して待機。
    • 別のリクエストでGUIDを指定してリストからTaskCompletionSourceをSetResultする。
  • 再開されてレスポンスが返る。

gist3d97435824e4a04761dfe04612aca9b4

いま

CMS(コンテンツマネジメントシステム)の開発をしている。
ASP.NETSQLServer

MSDNマガジン2008年7月 トランザクション:データを失うことなく障害に対処するスケーラブルなシステムを構築する Udi Dahan

現状はWebアプリケーションとデータベースがべったりくっついていることが前提になっている。管理ページのaspxでトランザクションを実行して同期的に結果を返す。 更新プロセスのプログラミングが窮屈なので開発の機動性、発想の柔軟性を鈍らせる。

ビジネスプロセスの実行主体を独立させる。今後のシステム開発の可能性を広げる。AWSやAzureで提供されるPaaSを段階的に利用していくための準備でもある。

管理ページで受付をした更新要求をWebアプリケーションとは切り離されたプロセスに投入する。結果は投入したプロセスからは受け取らない。 結果は結果を待つプロセスへ通知される。

今のWebアプリケーションから小さく変更を入れていく。管理ページでは結果をロングポーリングで待つ。HTTPの接続は結果の通知を受けるかタイムアウトまで持続する。

ASP.NETで待機するやりかた。 ASP.NETでCometを利用したチャットを実装する:CodeZine(コードジン) HttpContextの参照をStaticで保持して待てばいいことがわかった。

いまからやること

  • 参考にしたものは、IHttpAsyncHandlerなので、HttpTaskAsyncHandlerに書き換える
  • 待機している複数の接続からレスポンスを返す接続を選択する仕組みを作る

2016-11-18までのこと

  • ビルドを開発者のPCではなくてサーバーでする
  • PublishとDeployという言葉は何を指している?
    • VisualStudioの項目としては
      • Publish=発行
      • Deploy=配置
      • ?=公開
    • この周辺では同じ意味で使われているっぽい
  • VisualStudioの「発行」ダイアログで作った発行プロファイルを使ってデプロイパッケージを作りたい
    • コマンドラインオプションにDeployOnBuild=trueを足すことでVisualStudioの「発行」と同じことができる。
    • MSBuild
      • ログの出し方
        • /fl1 /flp1:logfile=file.txt;verbosity=diagnostic;summary;encoding=utf-8
        • visual studioでのビルドログは、「出力」ウィンドウからテキストをコピーして取得する
      • msbuildの応答ファイル ".rsp"
        • 改行できる。#でコメント。
        • >msbuild @file
      • 処理の追い方
        • AfterTargets
        • InitialTarget
        • DependsOnTargets
        • BeforeTarget
        • AfterTarget
    • ターゲットファイルを眺める
      • 標準ビルドプロセス
        • 標準ビルドプロセスからどうやって、DeployOnBuildの処理が実行されるの?
        • それは、/target=packageと関係あるの?
        • target"Package"は、VS2010からある。
        • /p:CreatePackageOnPublishは古いやりかた
      • Microsoft.Web.Publishing.targets
        • Line:2852 Target "Package"
        • Line:3852 Target "PackageUsingManifest"
        • <BuildDependOn> $(BuildDependsOn) Package </BuildDependOn>
        • Line:184
          • parameters.xmlってなに?
        • WPPとパブリッシュプロファイル
          • Line:429
        • パッケージ作成のプロパティ
          • Line:758
        • WebPublishMethodのtargetファイルをインポート
          • web\Deploy\Microsoft.Web.Publishing.Deploy.Package.targets
          • Line:2852
          • calltarget "PackageUsingManifest"
          • DeployOnBuildで、AfterTargets "PrepareForRun"で処理を差し込んでる。
        • 標準ビルドプロセス"Build"のDependsOnの"CoreBuild"のDependsOnの"PrepareForBuild"
      • デスクトップビルド
      • VisualStudioの"発行"機能(Web Publishing Pipeline "WPP")
      • 追加の設定ファイル
        • .publishsettings
        • .wpp.targets
        • .pubxml
        • 読み込まれるには、名前と場所の条件
    • パッケージってなんだ
    • パッケージの作り方を指定する
  • 結局このプロパティ
    • DeployOnBuild
    • DeployTarget
      • 既定値がPackageなので省略可能
    • PackageLocation
    • DeployAsIISApp
    • IncludeSetAclProviderOnDestination
  • pubxmlでConfigurationプロパティをReleaseに設定してもDebugでビルドされる。/p:Configuration=Release
  • どういうパッケージを作りたいか
    • 「発行」で作られるパッケージのバッチファイル
      • -source:package=[パッケージ] -dest:auto
      • 中にマニフェストが含まれている
        • iisAppプロバイダー
          • CreateAppプロバイダー
            • ApplicationHost.configにApplicationを作る
          • ContentPathプロバイダー
    • ファイルコピーだけにしたい
      • -source:contentPath=[フォルダのパス] -dest:contentPath=[Webアプリケーションの名前]
      • WPPのプロパティを使う
        • DeployAsIISApp=false
        • IncludeSetAclProviderOnDestination=false

リモートのSQLServerをManagement Studioから再起動させるにはWMIの構成が必要

Management StudioでリモートのSQLServerを再起動できなかった。
"sa"アカウントで接続してもメニューにある"再起動"がグレーアウトしていて選択できない。
SQLServerのあるローカルから"sa"で接続すると再起動できる。

f:id:azechi_n:20160917101731j:plain

クライアント側のイベントログにエラーも出てる

DistributedCOM

構成されているどのプロトコルを使っても、DCOM がコンピューター [リモートのコンピューター名] と通信できませんでした。要求元 PID 25f8 (C:\Program Files (x86)\Microsoft SQL Server\130\Tools\Binn\ManagementStudio\Ssms.exe)。

SQLServerの再起動はWMIという仕組みで使える機能だそうで、SQLServerとの接続とは別の仕組みでリモートのWindowsと通信する必要があるみたい。SQLServerの状態アイコンも同じ。

SQL Server ツールでサーバーの状態を表示できるようにする WMI の構成

ManagementStudioでは起動したwindowsアカウントで接続をするのかな だとしたら、ワークグループ環境では接続先にも同じ名前とパスワードのアカウントを作って...ってやる必要があるかも あとファイアウォールの設定とかも必要か。

いま扱ってるのはAWS EC2だからRunCommandでやることにする。

SQLServerのネットワーク構成をコマンドラインから変更した

AWS EC2でSQLServerインスタンスを作ったときにExpressエディションではリモートからアクセスできなかった。 Webエディションではできたのに。

エディションによって、ネットワーク構成の既定値が違うらしい。Expressエディションでは、TCP/IPが無効になっている。
SQL Server の既定のネットワーク構成

GUIの構成マネージャーから有効にすればOK。 でもコマンドラインからしたい。

SQLServer管理オブジェクト(SMO)が用意されているのでこれを使えばいいらしい。 SMOは.NET Framework アセンブリなのでPowerShellから使える。

サーバー ネットワーク プロトコルを有効または無効にする方法 (SQL Server PowerShell)
SQL Server 管理オブジェクト (SMO) プログラミング ガイド SQL Server PowerShell

#TCP/IPでの接続を有効にする(SQLServerの再起動が必要)
Set-ExecutionPolicy -Scope Process RemoteSigned -Force
Impoert-Module 'sqlps'
$wmi = New-Object 'Microsoft.SqlServer.Management.Smo.Wmi.ManagedComputer'
$tcp = $wmi.GetSmoObject("ManagedComputer[@Name='computerName']/ServerInstance[@Name='MSSQLSERVER']/ServerProtocol[@Name='Tcp']")
$tcp.IsEnabled = $true
$tcp.Alter()

今回は必要なSMOアセンブリだけを読み込めば十分なんだけど、sqlpsモジュールをインポートしとけばロードされるアセンブリに必要なものが含まれてるから便利。 初期値がListenAll=yesになっているので、IsEnable=trueにすれば全部のIPアドレスが有効になる。
ServerProtocol クラス (Microsoft.SqlServer.Management.Smo.Wmi)

::SQLServerを再起動する
net stop MSSQLSERVER /y
net start SQLSERVERAGENT

停止するときは、/yオプションでエージェントも停止させる。 エージェントを起動するとSQLServer本体も起動する。