EntityFramework.psm1 29 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777
  1. # Copyright (c) Microsoft Corporation. All rights reserved.
  2. $InitialDatabase = '0'
  3. $knownExceptions = @(
  4. 'System.Data.Entity.Migrations.Infrastructure.MigrationsException',
  5. 'System.Data.Entity.Migrations.Infrastructure.AutomaticMigrationsDisabledException',
  6. 'System.Data.Entity.Migrations.Infrastructure.AutomaticDataLossException',
  7. 'System.Data.Entity.Migrations.Infrastructure.MigrationsPendingException',
  8. 'System.Data.Entity.Migrations.ProjectTypeNotSupportedException'
  9. )
  10. <#
  11. .SYNOPSIS
  12. Enables Code First Migrations in a project.
  13. .DESCRIPTION
  14. Enables Migrations by scaffolding a migrations configuration class in the project. If the
  15. target database was created by an initializer, an initial migration will be created (unless
  16. automatic migrations are enabled via the EnableAutomaticMigrations parameter).
  17. .PARAMETER ContextTypeName
  18. Specifies the context to use. If omitted, migrations will attempt to locate a
  19. single context type in the target project.
  20. .PARAMETER EnableAutomaticMigrations
  21. Specifies whether automatic migrations will be enabled in the scaffolded migrations configuration.
  22. If omitted, automatic migrations will be disabled.
  23. .PARAMETER MigrationsDirectory
  24. Specifies the name of the directory that will contain migrations code files.
  25. If omitted, the directory will be named "Migrations".
  26. .PARAMETER ProjectName
  27. Specifies the project that the scaffolded migrations configuration class will
  28. be added to. If omitted, the default project selected in package manager
  29. console is used.
  30. .PARAMETER StartUpProjectName
  31. Specifies the configuration file to use for named connection strings. If
  32. omitted, the specified project's configuration file is used.
  33. .PARAMETER ConnectionStringName
  34. Specifies the name of a connection string to use from the application's
  35. configuration file.
  36. .PARAMETER ConnectionString
  37. Specifies the the connection string to use. If omitted, the context's
  38. default connection will be used.
  39. .PARAMETER ConnectionProviderName
  40. Specifies the provider invariant name of the connection string.
  41. .PARAMETER Force
  42. Specifies that the migrations configuration be overwritten when running more
  43. than once for a given project.
  44. #>
  45. function Enable-Migrations
  46. {
  47. [CmdletBinding(DefaultParameterSetName = 'ConnectionStringName')]
  48. param (
  49. [string] $ContextTypeName,
  50. [alias('Auto')]
  51. [switch] $EnableAutomaticMigrations,
  52. [string] $MigrationsDirectory,
  53. [string] $ProjectName,
  54. [string] $StartUpProjectName,
  55. [parameter(ParameterSetName = 'ConnectionStringName')]
  56. [string] $ConnectionStringName,
  57. [parameter(ParameterSetName = 'ConnectionStringAndProviderName',
  58. Mandatory = $true)]
  59. [string] $ConnectionString,
  60. [parameter(ParameterSetName = 'ConnectionStringAndProviderName',
  61. Mandatory = $true)]
  62. [string] $ConnectionProviderName,
  63. [switch] $Force
  64. )
  65. $runner = New-MigrationsRunner $ProjectName $StartUpProjectName $null $ConnectionStringName $ConnectionString $ConnectionProviderName
  66. try
  67. {
  68. Invoke-RunnerCommand $runner System.Data.Entity.Migrations.EnableMigrationsCommand @( $EnableAutomaticMigrations.IsPresent, $Force.IsPresent ) @{ 'ContextTypeName' = $ContextTypeName; 'MigrationsDirectory' = $MigrationsDirectory }
  69. $error = Get-RunnerError $runner
  70. if ($error)
  71. {
  72. if ($knownExceptions -notcontains $error.TypeName)
  73. {
  74. Write-Host $error.StackTrace
  75. }
  76. throw $error.Message
  77. }
  78. $(Get-VSComponentModel).GetService([NuGetConsole.IPowerConsoleWindow]).Show()
  79. }
  80. finally
  81. {
  82. Remove-Runner $runner
  83. }
  84. }
  85. <#
  86. .SYNOPSIS
  87. Scaffolds a migration script for any pending model changes.
  88. .DESCRIPTION
  89. Scaffolds a new migration script and adds it to the project.
  90. .PARAMETER Name
  91. Specifies the name of the custom script.
  92. .PARAMETER Force
  93. Specifies that the migration user code be overwritten when re-scaffolding an
  94. existing migration.
  95. .PARAMETER ProjectName
  96. Specifies the project that contains the migration configuration type to be
  97. used. If omitted, the default project selected in package manager console
  98. is used.
  99. .PARAMETER StartUpProjectName
  100. Specifies the configuration file to use for named connection strings. If
  101. omitted, the specified project's configuration file is used.
  102. .PARAMETER ConfigurationTypeName
  103. Specifies the migrations configuration to use. If omitted, migrations will
  104. attempt to locate a single migrations configuration type in the target
  105. project.
  106. .PARAMETER ConnectionStringName
  107. Specifies the name of a connection string to use from the application's
  108. configuration file.
  109. .PARAMETER ConnectionString
  110. Specifies the the connection string to use. If omitted, the context's
  111. default connection will be used.
  112. .PARAMETER ConnectionProviderName
  113. Specifies the provider invariant name of the connection string.
  114. .PARAMETER IgnoreChanges
  115. Scaffolds an empty migration ignoring any pending changes detected in the current model.
  116. This can be used to create an initial, empty migration to enable Migrations for an existing
  117. database. N.B. Doing this assumes that the target database schema is compatible with the
  118. current model.
  119. #>
  120. function Add-Migration
  121. {
  122. [CmdletBinding(DefaultParameterSetName = 'ConnectionStringName')]
  123. param (
  124. [parameter(Position = 0,
  125. Mandatory = $true)]
  126. [string] $Name,
  127. [switch] $Force,
  128. [string] $ProjectName,
  129. [string] $StartUpProjectName,
  130. [string] $ConfigurationTypeName,
  131. [parameter(ParameterSetName = 'ConnectionStringName')]
  132. [string] $ConnectionStringName,
  133. [parameter(ParameterSetName = 'ConnectionStringAndProviderName',
  134. Mandatory = $true)]
  135. [string] $ConnectionString,
  136. [parameter(ParameterSetName = 'ConnectionStringAndProviderName',
  137. Mandatory = $true)]
  138. [string] $ConnectionProviderName,
  139. [switch] $IgnoreChanges)
  140. $runner = New-MigrationsRunner $ProjectName $StartUpProjectName $ConfigurationTypeName $ConnectionStringName $ConnectionString $ConnectionProviderName
  141. try
  142. {
  143. Invoke-RunnerCommand $runner System.Data.Entity.Migrations.AddMigrationCommand @( $Name, $Force.IsPresent, $IgnoreChanges.IsPresent )
  144. $error = Get-RunnerError $runner
  145. if ($error)
  146. {
  147. if ($knownExceptions -notcontains $error.TypeName)
  148. {
  149. Write-Host $error.StackTrace
  150. }
  151. throw $error.Message
  152. }
  153. $(Get-VSComponentModel).GetService([NuGetConsole.IPowerConsoleWindow]).Show()
  154. }
  155. finally
  156. {
  157. Remove-Runner $runner
  158. }
  159. }
  160. <#
  161. .SYNOPSIS
  162. Applies any pending migrations to the database.
  163. .DESCRIPTION
  164. Updates the database to the current model by applying pending migrations.
  165. .PARAMETER SourceMigration
  166. Only valid with -Script. Specifies the name of a particular migration to use
  167. as the update's starting point. If omitted, the last applied migration in
  168. the database will be used.
  169. .PARAMETER TargetMigration
  170. Specifies the name of a particular migration to update the database to. If
  171. omitted, the current model will be used.
  172. .PARAMETER Script
  173. Generate a SQL script rather than executing the pending changes directly.
  174. .PARAMETER Force
  175. Specifies that data loss is acceptable during automatic migration of the
  176. database.
  177. .PARAMETER ProjectName
  178. Specifies the project that contains the migration configuration type to be
  179. used. If omitted, the default project selected in package manager console
  180. is used.
  181. .PARAMETER StartUpProjectName
  182. Specifies the configuration file to use for named connection strings. If
  183. omitted, the specified project's configuration file is used.
  184. .PARAMETER ConfigurationTypeName
  185. Specifies the migrations configuration to use. If omitted, migrations will
  186. attempt to locate a single migrations configuration type in the target
  187. project.
  188. .PARAMETER ConnectionStringName
  189. Specifies the name of a connection string to use from the application's
  190. configuration file.
  191. .PARAMETER ConnectionString
  192. Specifies the the connection string to use. If omitted, the context's
  193. default connection will be used.
  194. .PARAMETER ConnectionProviderName
  195. Specifies the provider invariant name of the connection string.
  196. #>
  197. function Update-Database
  198. {
  199. [CmdletBinding(DefaultParameterSetName = 'ConnectionStringName')]
  200. param (
  201. [string] $SourceMigration,
  202. [string] $TargetMigration,
  203. [switch] $Script,
  204. [switch] $Force,
  205. [string] $ProjectName,
  206. [string] $StartUpProjectName,
  207. [string] $ConfigurationTypeName,
  208. [parameter(ParameterSetName = 'ConnectionStringName')]
  209. [string] $ConnectionStringName,
  210. [parameter(ParameterSetName = 'ConnectionStringAndProviderName',
  211. Mandatory = $true)]
  212. [string] $ConnectionString,
  213. [parameter(ParameterSetName = 'ConnectionStringAndProviderName',
  214. Mandatory = $true)]
  215. [string] $ConnectionProviderName)
  216. $runner = New-MigrationsRunner $ProjectName $StartUpProjectName $ConfigurationTypeName $ConnectionStringName $ConnectionString $ConnectionProviderName
  217. try
  218. {
  219. Invoke-RunnerCommand $runner System.Data.Entity.Migrations.UpdateDatabaseCommand @( $SourceMigration, $TargetMigration, $Script.IsPresent, $Force.IsPresent, $Verbose.IsPresent )
  220. $error = Get-RunnerError $runner
  221. if ($error)
  222. {
  223. if ($knownExceptions -notcontains $error.TypeName)
  224. {
  225. Write-Host $error.StackTrace
  226. }
  227. throw $error.Message
  228. }
  229. $(Get-VSComponentModel).GetService([NuGetConsole.IPowerConsoleWindow]).Show()
  230. }
  231. finally
  232. {
  233. Remove-Runner $runner
  234. }
  235. }
  236. <#
  237. .SYNOPSIS
  238. Displays the migrations that have been applied to the target database.
  239. .DESCRIPTION
  240. Displays the migrations that have been applied to the target database.
  241. .PARAMETER ProjectName
  242. Specifies the project that contains the migration configuration type to be
  243. used. If omitted, the default project selected in package manager console
  244. is used.
  245. .PARAMETER StartUpProjectName
  246. Specifies the configuration file to use for named connection strings. If
  247. omitted, the specified project's configuration file is used.
  248. .PARAMETER ConfigurationTypeName
  249. Specifies the migrations configuration to use. If omitted, migrations will
  250. attempt to locate a single migrations configuration type in the target
  251. project.
  252. .PARAMETER ConnectionStringName
  253. Specifies the name of a connection string to use from the application's
  254. configuration file.
  255. .PARAMETER ConnectionString
  256. Specifies the the connection string to use. If omitted, the context's
  257. default connection will be used.
  258. .PARAMETER ConnectionProviderName
  259. Specifies the provider invariant name of the connection string.
  260. #>
  261. function Get-Migrations
  262. {
  263. [CmdletBinding(DefaultParameterSetName = 'ConnectionStringName')]
  264. param (
  265. [string] $ProjectName,
  266. [string] $StartUpProjectName,
  267. [string] $ConfigurationTypeName,
  268. [parameter(ParameterSetName = 'ConnectionStringName')]
  269. [string] $ConnectionStringName,
  270. [parameter(ParameterSetName = 'ConnectionStringAndProviderName',
  271. Mandatory = $true)]
  272. [string] $ConnectionString,
  273. [parameter(ParameterSetName = 'ConnectionStringAndProviderName',
  274. Mandatory = $true)]
  275. [string] $ConnectionProviderName)
  276. $runner = New-MigrationsRunner $ProjectName $StartUpProjectName $ConfigurationTypeName $ConnectionStringName $ConnectionString $ConnectionProviderName
  277. try
  278. {
  279. Invoke-RunnerCommand $runner System.Data.Entity.Migrations.GetMigrationsCommand
  280. $error = Get-RunnerError $runner
  281. if ($error)
  282. {
  283. if ($knownExceptions -notcontains $error.TypeName)
  284. {
  285. Write-Host $error.StackTrace
  286. }
  287. throw $error.Message
  288. }
  289. }
  290. finally
  291. {
  292. Remove-Runner $runner
  293. }
  294. }
  295. function New-MigrationsRunner($ProjectName, $StartUpProjectName, $ConfigurationTypeName, $ConnectionStringName, $ConnectionString, $ConnectionProviderName)
  296. {
  297. $startUpProject = Get-MigrationsStartUpProject $StartUpProjectName $ProjectName
  298. Build-Project $startUpProject
  299. $project = Get-MigrationsProject $ProjectName
  300. Build-Project $project
  301. $installPath = Get-EntityFrameworkInstallPath $project
  302. $toolsPath = Join-Path $installPath tools
  303. $info = New-Object System.AppDomainSetup -Property @{
  304. ShadowCopyFiles = 'true';
  305. ApplicationBase = $installPath;
  306. PrivateBinPath = 'tools';
  307. ConfigurationFile = ([AppDomain]::CurrentDomain.SetupInformation.ConfigurationFile)
  308. }
  309. $targetFrameworkVersion = (New-Object System.Runtime.Versioning.FrameworkName ($project.Properties.Item('TargetFrameworkMoniker').Value)).Version
  310. if ($targetFrameworkVersion -lt (New-Object Version @( 4, 5 )))
  311. {
  312. $info.PrivateBinPath += ';lib\net40'
  313. }
  314. else
  315. {
  316. $info.PrivateBinPath += ';lib\net45'
  317. }
  318. $domain = [AppDomain]::CreateDomain('Migrations', $null, $info)
  319. $domain.SetData('project', $project)
  320. $domain.SetData('startUpProject', $startUpProject)
  321. $domain.SetData('configurationTypeName', $ConfigurationTypeName)
  322. $domain.SetData('connectionStringName', $ConnectionStringName)
  323. $domain.SetData('connectionString', $ConnectionString)
  324. $domain.SetData('connectionProviderName', $ConnectionProviderName)
  325. [AppDomain]::CurrentDomain.SetShadowCopyFiles()
  326. $utilityAssembly = [System.Reflection.Assembly]::LoadFrom((Join-Path $toolsPath EntityFramework.PowerShell.Utility.dll))
  327. $dispatcher = $utilityAssembly.CreateInstance(
  328. 'System.Data.Entity.Migrations.Utilities.DomainDispatcher',
  329. $false,
  330. [System.Reflection.BindingFlags]::Instance -bor [System.Reflection.BindingFlags]::Public,
  331. $null,
  332. $PSCmdlet,
  333. $null,
  334. $null)
  335. $domain.SetData('efDispatcher', $dispatcher)
  336. return @{
  337. Domain = $domain;
  338. ToolsPath = $toolsPath
  339. }
  340. }
  341. function Remove-Runner($runner)
  342. {
  343. [AppDomain]::Unload($runner.Domain)
  344. }
  345. function Invoke-RunnerCommand($runner, $command, $parameters, $anonymousArguments)
  346. {
  347. $domain = $runner.Domain
  348. if ($anonymousArguments)
  349. {
  350. $anonymousArguments.GetEnumerator() | %{
  351. $domain.SetData($_.Name, $_.Value)
  352. }
  353. }
  354. $domain.CreateInstanceFrom(
  355. (Join-Path $runner.ToolsPath EntityFramework.PowerShell.dll),
  356. $command,
  357. $false,
  358. 0,
  359. $null,
  360. $parameters,
  361. $null,
  362. $null) | Out-Null
  363. }
  364. function Get-RunnerError($runner)
  365. {
  366. $domain = $runner.Domain
  367. if (!$domain.GetData('wasError'))
  368. {
  369. return $null
  370. }
  371. return @{
  372. Message = $domain.GetData('error.Message');
  373. TypeName = $domain.GetData('error.TypeName');
  374. StackTrace = $domain.GetData('error.StackTrace')
  375. }
  376. }
  377. function Get-MigrationsProject($name, $hideMessage)
  378. {
  379. if ($name)
  380. {
  381. return Get-SingleProject $name
  382. }
  383. $project = Get-Project
  384. $projectName = $project.Name
  385. if (!$hideMessage)
  386. {
  387. Write-Verbose "Using NuGet project '$projectName'."
  388. }
  389. return $project
  390. }
  391. function Get-MigrationsStartUpProject($name, $fallbackName)
  392. {
  393. $startUpProject = $null
  394. if ($name)
  395. {
  396. $startUpProject = Get-SingleProject $name
  397. }
  398. else
  399. {
  400. $startupProjectPaths = $DTE.Solution.SolutionBuild.StartupProjects
  401. if ($startupProjectPaths)
  402. {
  403. if ($startupProjectPaths.Length -eq 1)
  404. {
  405. $startupProjectPath = $startupProjectPaths[0]
  406. if (!(Split-Path -IsAbsolute $startupProjectPath))
  407. {
  408. $solutionPath = Split-Path $DTE.Solution.Properties.Item('Path').Value
  409. $startupProjectPath = Join-Path $solutionPath $startupProjectPath -Resolve
  410. }
  411. $startupProject = Get-SolutionProjects | ?{
  412. try
  413. {
  414. $fullName = $_.FullName
  415. }
  416. catch [NotImplementedException]
  417. {
  418. return $false
  419. }
  420. if ($fullName -and $fullName.EndsWith('\'))
  421. {
  422. $fullName = $fullName.Substring(0, $fullName.Length - 1)
  423. }
  424. return $fullName -eq $startupProjectPath
  425. }
  426. }
  427. else
  428. {
  429. Write-Verbose 'More than one start-up project found.'
  430. }
  431. }
  432. else
  433. {
  434. Write-Verbose 'No start-up project found.'
  435. }
  436. }
  437. if (!($startUpProject -and (Test-StartUpProject $startUpProject)))
  438. {
  439. $startUpProject = Get-MigrationsProject $fallbackName $true
  440. $startUpProjectName = $startUpProject.Name
  441. Write-Warning "Cannot determine a valid start-up project. Using project '$startUpProjectName' instead. Your configuration file and working directory may not be set as expected. Use the -StartUpProjectName parameter to set one explicitly. Use the -Verbose switch for more information."
  442. }
  443. else
  444. {
  445. $startUpProjectName = $startUpProject.Name
  446. Write-Verbose "Using StartUp project '$startUpProjectName'."
  447. }
  448. return $startUpProject
  449. }
  450. function Get-SolutionProjects()
  451. {
  452. $projects = New-Object System.Collections.Stack
  453. $DTE.Solution.Projects | %{
  454. $projects.Push($_)
  455. }
  456. while ($projects.Count -ne 0)
  457. {
  458. $project = $projects.Pop();
  459. # NOTE: This line is similar to doing a "yield return" in C#
  460. $project
  461. if ($project.ProjectItems)
  462. {
  463. $project.ProjectItems | ?{ $_.SubProject } | %{
  464. $projects.Push($_.SubProject)
  465. }
  466. }
  467. }
  468. }
  469. function Get-SingleProject($name)
  470. {
  471. $project = Get-Project $name
  472. if ($project -is [array])
  473. {
  474. throw "More than one project '$name' was found. Specify the full name of the one to use."
  475. }
  476. return $project
  477. }
  478. function Test-StartUpProject($project)
  479. {
  480. if ($project.Kind -eq '{cc5fd16d-436d-48ad-a40c-5a424c6e3e79}')
  481. {
  482. $projectName = $project.Name
  483. Write-Verbose "Cannot use start-up project '$projectName'. The Windows Azure Project type isn't supported."
  484. return $false
  485. }
  486. return $true
  487. }
  488. function Build-Project($project)
  489. {
  490. $configuration = $DTE.Solution.SolutionBuild.ActiveConfiguration.Name
  491. $DTE.Solution.SolutionBuild.BuildProject($configuration, $project.UniqueName, $true)
  492. if ($DTE.Solution.SolutionBuild.LastBuildInfo)
  493. {
  494. $projectName = $project.Name
  495. throw "The project '$projectName' failed to build."
  496. }
  497. }
  498. function Get-EntityFrameworkInstallPath($project)
  499. {
  500. $package = Get-Package -ProjectName $project.FullName | ?{ $_.Id -eq 'EntityFramework' }
  501. if (!$package)
  502. {
  503. $projectName = $project.Name
  504. throw "The EntityFramework package is not installed on project '$projectName'."
  505. }
  506. return Get-PackageInstallPath $package
  507. }
  508. function Get-PackageInstallPath($package)
  509. {
  510. $componentModel = Get-VsComponentModel
  511. $packageInstallerServices = $componentModel.GetService([NuGet.VisualStudio.IVsPackageInstallerServices])
  512. $vsPackage = $packageInstallerServices.GetInstalledPackages() | ?{ $_.Id -eq $package.Id -and $_.Version -eq $package.Version }
  513. return $vsPackage.InstallPath
  514. }
  515. Export-ModuleMember @( 'Enable-Migrations', 'Add-Migration', 'Update-Database', 'Get-Migrations' ) -Variable InitialDatabase
  516. # SIG # Begin signature block
  517. # MIIanQYJKoZIhvcNAQcCoIIajjCCGooCAQExCzAJBgUrDgMCGgUAMGkGCisGAQQB
  518. # gjcCAQSgWzBZMDQGCisGAQQBgjcCAR4wJgIDAQAABBAfzDtgWUsITrck0sYpfvNR
  519. # AgEAAgEAAgEAAgEAAgEAMCEwCQYFKw4DAhoFAAQUhBFz4Itt1wDYyur2mJt4qMN2
  520. # aESgghV5MIIEujCCA6KgAwIBAgIKYQKSSgAAAAAAIDANBgkqhkiG9w0BAQUFADB3
  521. # MQswCQYDVQQGEwJVUzETMBEGA1UECBMKV2FzaGluZ3RvbjEQMA4GA1UEBxMHUmVk
  522. # bW9uZDEeMBwGA1UEChMVTWljcm9zb2Z0IENvcnBvcmF0aW9uMSEwHwYDVQQDExhN
  523. # aWNyb3NvZnQgVGltZS1TdGFtcCBQQ0EwHhcNMTIwMTA5MjIyNTU5WhcNMTMwNDA5
  524. # MjIyNTU5WjCBszELMAkGA1UEBhMCVVMxEzARBgNVBAgTCldhc2hpbmd0b24xEDAO
  525. # BgNVBAcTB1JlZG1vbmQxHjAcBgNVBAoTFU1pY3Jvc29mdCBDb3Jwb3JhdGlvbjEN
  526. # MAsGA1UECxMETU9QUjEnMCUGA1UECxMebkNpcGhlciBEU0UgRVNOOkI4RUMtMzBB
  527. # NC03MTQ0MSUwIwYDVQQDExxNaWNyb3NvZnQgVGltZS1TdGFtcCBTZXJ2aWNlMIIB
  528. # IjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAzWPD96K1R9n5OZRTrGuPpnk4
  529. # IfTRbj0VOBbBcyyZj/vgPFvhokyLsquLtPJKx7mTUNEm9YdTsHp180cPFytnLGTr
  530. # YOdKjOCLXsRWaTc6KgRdFwHIv6m308mro5GogeM/LbfY5MR4AHk5z/3HZOIjEnie
  531. # DHYnSY+arA504wZVVUnI7aF8cEVhfrJxFh7hwUG50tIy6VIk8zZQBNfdbzxJ1QvU
  532. # dkD8ZWUTfpVROtX/uJqnV2tLFeU3WB/cAA3FrurfgUf58FKu5s9arOAUSqZxlID6
  533. # /bAjMGDpg2CsDiQe/xHy56VVYpXun3+eKdbNSwp2g/BDBN8GSSDyU1pEsFF6OQID
  534. # AQABo4IBCTCCAQUwHQYDVR0OBBYEFM0ZrGFNlGcr9q+UdVnb8FgAg6E6MB8GA1Ud
  535. # IwQYMBaAFCM0+NlSRnAK7UD7dvuzK7DDNbMPMFQGA1UdHwRNMEswSaBHoEWGQ2h0
  536. # dHA6Ly9jcmwubWljcm9zb2Z0LmNvbS9wa2kvY3JsL3Byb2R1Y3RzL01pY3Jvc29m
  537. # dFRpbWVTdGFtcFBDQS5jcmwwWAYIKwYBBQUHAQEETDBKMEgGCCsGAQUFBzAChjxo
  538. # dHRwOi8vd3d3Lm1pY3Jvc29mdC5jb20vcGtpL2NlcnRzL01pY3Jvc29mdFRpbWVT
  539. # dGFtcFBDQS5jcnQwEwYDVR0lBAwwCgYIKwYBBQUHAwgwDQYJKoZIhvcNAQEFBQAD
  540. # ggEBAFEc1t82HdyAvAKnxpnfFsiQBmkVmjK582QQ0orzYikbeY/KYKmzXcTkFi01
  541. # jESb8fRcYaRBrpqLulDRanlqs2KMnU1RUAupjtS/ohDAR9VOdVKJHj+Wao8uQBQG
  542. # cu4/cFmSXYXtg5n6goSe5AMBIROrJ9bMcUnl2h3/bzwJTtWNZugMyX/uMRQCN197
  543. # aeyJPkV/JUTnHxrWxRrDSuTh8YSY50/5qZinGEbshGzsqQMK/Xx6Uh2ca6SoD5iS
  544. # pJJ4XCt4432yx9m2cH3fW3NTv6rUZlBL8Mk7lYXlwUplnSVYULsgVJF5OhsHXGpX
  545. # KK8xx5/nwx3uR/0n13/PdNxlxT8wggTsMIID1KADAgECAhMzAAAAsBGvCovQO5/d
  546. # AAEAAACwMA0GCSqGSIb3DQEBBQUAMHkxCzAJBgNVBAYTAlVTMRMwEQYDVQQIEwpX
  547. # YXNoaW5ndG9uMRAwDgYDVQQHEwdSZWRtb25kMR4wHAYDVQQKExVNaWNyb3NvZnQg
  548. # Q29ycG9yYXRpb24xIzAhBgNVBAMTGk1pY3Jvc29mdCBDb2RlIFNpZ25pbmcgUENB
  549. # MB4XDTEzMDEyNDIyMzMzOVoXDTE0MDQyNDIyMzMzOVowgYMxCzAJBgNVBAYTAlVT
  550. # MRMwEQYDVQQIEwpXYXNoaW5ndG9uMRAwDgYDVQQHEwdSZWRtb25kMR4wHAYDVQQK
  551. # ExVNaWNyb3NvZnQgQ29ycG9yYXRpb24xDTALBgNVBAsTBE1PUFIxHjAcBgNVBAMT
  552. # FU1pY3Jvc29mdCBDb3Jwb3JhdGlvbjCCASIwDQYJKoZIhvcNAQEBBQADggEPADCC
  553. # AQoCggEBAOivXKIgDfgofLwFe3+t7ut2rChTPzrbQH2zjjPmVz+lURU0VKXPtIup
  554. # P6g34S1Q7TUWTu9NetsTdoiwLPBZXKnr4dcpdeQbhSeb8/gtnkE2KwtA+747urlc
  555. # dZMWUkvKM8U3sPPrfqj1QRVcCGUdITfwLLoiCxCxEJ13IoWEfE+5G5Cw9aP+i/QM
  556. # mk6g9ckKIeKq4wE2R/0vgmqBA/WpNdyUV537S9QOgts4jxL+49Z6dIhk4WLEJS4q
  557. # rp0YHw4etsKvJLQOULzeHJNcSaZ5tbbbzvlweygBhLgqKc+/qQUF4eAPcU39rVwj
  558. # gynrx8VKyOgnhNN+xkMLlQAFsU9lccUCAwEAAaOCAWAwggFcMBMGA1UdJQQMMAoG
  559. # CCsGAQUFBwMDMB0GA1UdDgQWBBRZcaZaM03amAeA/4Qevof5cjJB8jBRBgNVHREE
  560. # SjBIpEYwRDENMAsGA1UECxMETU9QUjEzMDEGA1UEBRMqMzE1OTUrNGZhZjBiNzEt
  561. # YWQzNy00YWEzLWE2NzEtNzZiYzA1MjM0NGFkMB8GA1UdIwQYMBaAFMsR6MrStBZY
  562. # Ack3LjMWFrlMmgofMFYGA1UdHwRPME0wS6BJoEeGRWh0dHA6Ly9jcmwubWljcm9z
  563. # b2Z0LmNvbS9wa2kvY3JsL3Byb2R1Y3RzL01pY0NvZFNpZ1BDQV8wOC0zMS0yMDEw
  564. # LmNybDBaBggrBgEFBQcBAQROMEwwSgYIKwYBBQUHMAKGPmh0dHA6Ly93d3cubWlj
  565. # cm9zb2Z0LmNvbS9wa2kvY2VydHMvTWljQ29kU2lnUENBXzA4LTMxLTIwMTAuY3J0
  566. # MA0GCSqGSIb3DQEBBQUAA4IBAQAx124qElczgdWdxuv5OtRETQie7l7falu3ec8C
  567. # nLx2aJ6QoZwLw3+ijPFNupU5+w3g4Zv0XSQPG42IFTp8263Os8lsujksRX0kEVQm
  568. # MA0N/0fqAwfl5GZdLHudHakQ+hywdPJPaWueqSSE2u2WoN9zpO9qGqxLYp7xfMAU
  569. # f0jNTbJE+fA8k21C2Oh85hegm2hoCSj5ApfvEQO6Z1Ktwemzc6bSY81K4j7k8079
  570. # /6HguwITO10g3lU/o66QQDE4dSheBKlGbeb1enlAvR/N6EXVruJdPvV1x+ZmY2DM
  571. # 1ZqEh40kMPfvNNBjHbFCZ0oOS786Du+2lTqnOOQlkgimiGaCMIIFvDCCA6SgAwIB
  572. # AgIKYTMmGgAAAAAAMTANBgkqhkiG9w0BAQUFADBfMRMwEQYKCZImiZPyLGQBGRYD
  573. # Y29tMRkwFwYKCZImiZPyLGQBGRYJbWljcm9zb2Z0MS0wKwYDVQQDEyRNaWNyb3Nv
  574. # ZnQgUm9vdCBDZXJ0aWZpY2F0ZSBBdXRob3JpdHkwHhcNMTAwODMxMjIxOTMyWhcN
  575. # MjAwODMxMjIyOTMyWjB5MQswCQYDVQQGEwJVUzETMBEGA1UECBMKV2FzaGluZ3Rv
  576. # bjEQMA4GA1UEBxMHUmVkbW9uZDEeMBwGA1UEChMVTWljcm9zb2Z0IENvcnBvcmF0
  577. # aW9uMSMwIQYDVQQDExpNaWNyb3NvZnQgQ29kZSBTaWduaW5nIFBDQTCCASIwDQYJ
  578. # KoZIhvcNAQEBBQADggEPADCCAQoCggEBALJyWVwZMGS/HZpgICBCmXZTbD4b1m/M
  579. # y/Hqa/6XFhDg3zp0gxq3L6Ay7P/ewkJOI9VyANs1VwqJyq4gSfTwaKxNS42lvXlL
  580. # cZtHB9r9Jd+ddYjPqnNEf9eB2/O98jakyVxF3K+tPeAoaJcap6Vyc1bxF5Tk/TWU
  581. # cqDWdl8ed0WDhTgW0HNbBbpnUo2lsmkv2hkL/pJ0KeJ2L1TdFDBZ+NKNYv3LyV9G
  582. # MVC5JxPkQDDPcikQKCLHN049oDI9kM2hOAaFXE5WgigqBTK3S9dPY+fSLWLxRT3n
  583. # rAgA9kahntFbjCZT6HqqSvJGzzc8OJ60d1ylF56NyxGPVjzBrAlfA9MCAwEAAaOC
  584. # AV4wggFaMA8GA1UdEwEB/wQFMAMBAf8wHQYDVR0OBBYEFMsR6MrStBZYAck3LjMW
  585. # FrlMmgofMAsGA1UdDwQEAwIBhjASBgkrBgEEAYI3FQEEBQIDAQABMCMGCSsGAQQB
  586. # gjcVAgQWBBT90TFO0yaKleGYYDuoMW+mPLzYLTAZBgkrBgEEAYI3FAIEDB4KAFMA
  587. # dQBiAEMAQTAfBgNVHSMEGDAWgBQOrIJgQFYnl+UlE/wq4QpTlVnkpDBQBgNVHR8E
  588. # STBHMEWgQ6BBhj9odHRwOi8vY3JsLm1pY3Jvc29mdC5jb20vcGtpL2NybC9wcm9k
  589. # dWN0cy9taWNyb3NvZnRyb290Y2VydC5jcmwwVAYIKwYBBQUHAQEESDBGMEQGCCsG
  590. # AQUFBzAChjhodHRwOi8vd3d3Lm1pY3Jvc29mdC5jb20vcGtpL2NlcnRzL01pY3Jv
  591. # c29mdFJvb3RDZXJ0LmNydDANBgkqhkiG9w0BAQUFAAOCAgEAWTk+fyZGr+tvQLEy
  592. # tWrrDi9uqEn361917Uw7LddDrQv+y+ktMaMjzHxQmIAhXaw9L0y6oqhWnONwu7i0
  593. # +Hm1SXL3PupBf8rhDBdpy6WcIC36C1DEVs0t40rSvHDnqA2iA6VW4LiKS1fylUKc
  594. # 8fPv7uOGHzQ8uFaa8FMjhSqkghyT4pQHHfLiTviMocroE6WRTsgb0o9ylSpxbZsa
  595. # +BzwU9ZnzCL/XB3Nooy9J7J5Y1ZEolHN+emjWFbdmwJFRC9f9Nqu1IIybvyklRPk
  596. # 62nnqaIsvsgrEA5ljpnb9aL6EiYJZTiU8XofSrvR4Vbo0HiWGFzJNRZf3ZMdSY4t
  597. # vq00RBzuEBUaAF3dNVshzpjHCe6FDoxPbQ4TTj18KUicctHzbMrB7HCjV5JXfZSN
  598. # oBtIA1r3z6NnCnSlNu0tLxfI5nI3EvRvsTxngvlSso0zFmUeDordEN5k9G/ORtTT
  599. # F+l5xAS00/ss3x+KnqwK+xMnQK3k+eGpf0a7B2BHZWBATrBC7E7ts3Z52Ao0CW0c
  600. # gDEf4g5U3eWh++VHEK1kmP9QFi58vwUheuKVQSdpw5OPlcmN2Jshrg1cnPCiroZo
  601. # gwxqLbt2awAdlq3yFnv2FoMkuYjPaqhHMS+a3ONxPdcAfmJH0c6IybgY+g5yjcGj
  602. # Pa8CQGr/aZuW4hCoELQ3UAjWwz0wggYHMIID76ADAgECAgphFmg0AAAAAAAcMA0G
  603. # CSqGSIb3DQEBBQUAMF8xEzARBgoJkiaJk/IsZAEZFgNjb20xGTAXBgoJkiaJk/Is
  604. # ZAEZFgltaWNyb3NvZnQxLTArBgNVBAMTJE1pY3Jvc29mdCBSb290IENlcnRpZmlj
  605. # YXRlIEF1dGhvcml0eTAeFw0wNzA0MDMxMjUzMDlaFw0yMTA0MDMxMzAzMDlaMHcx
  606. # CzAJBgNVBAYTAlVTMRMwEQYDVQQIEwpXYXNoaW5ndG9uMRAwDgYDVQQHEwdSZWRt
  607. # b25kMR4wHAYDVQQKExVNaWNyb3NvZnQgQ29ycG9yYXRpb24xITAfBgNVBAMTGE1p
  608. # Y3Jvc29mdCBUaW1lLVN0YW1wIFBDQTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCC
  609. # AQoCggEBAJ+hbLHf20iSKnxrLhnhveLjxZlRI1Ctzt0YTiQP7tGn0UytdDAgEesH
  610. # 1VSVFUmUG0KSrphcMCbaAGvoe73siQcP9w4EmPCJzB/LMySHnfL0Zxws/HvniB3q
  611. # 506jocEjU8qN+kXPCdBer9CwQgSi+aZsk2fXKNxGU7CG0OUoRi4nrIZPVVIM5AMs
  612. # +2qQkDBuh/NZMJ36ftaXs+ghl3740hPzCLdTbVK0RZCfSABKR2YRJylmqJfk0waB
  613. # SqL5hKcRRxQJgp+E7VV4/gGaHVAIhQAQMEbtt94jRrvELVSfrx54QTF3zJvfO4OT
  614. # oWECtR0Nsfz3m7IBziJLVP/5BcPCIAsCAwEAAaOCAaswggGnMA8GA1UdEwEB/wQF
  615. # MAMBAf8wHQYDVR0OBBYEFCM0+NlSRnAK7UD7dvuzK7DDNbMPMAsGA1UdDwQEAwIB
  616. # hjAQBgkrBgEEAYI3FQEEAwIBADCBmAYDVR0jBIGQMIGNgBQOrIJgQFYnl+UlE/wq
  617. # 4QpTlVnkpKFjpGEwXzETMBEGCgmSJomT8ixkARkWA2NvbTEZMBcGCgmSJomT8ixk
  618. # ARkWCW1pY3Jvc29mdDEtMCsGA1UEAxMkTWljcm9zb2Z0IFJvb3QgQ2VydGlmaWNh
  619. # dGUgQXV0aG9yaXR5ghB5rRahSqClrUxzWPQHEy5lMFAGA1UdHwRJMEcwRaBDoEGG
  620. # P2h0dHA6Ly9jcmwubWljcm9zb2Z0LmNvbS9wa2kvY3JsL3Byb2R1Y3RzL21pY3Jv
  621. # c29mdHJvb3RjZXJ0LmNybDBUBggrBgEFBQcBAQRIMEYwRAYIKwYBBQUHMAKGOGh0
  622. # dHA6Ly93d3cubWljcm9zb2Z0LmNvbS9wa2kvY2VydHMvTWljcm9zb2Z0Um9vdENl
  623. # cnQuY3J0MBMGA1UdJQQMMAoGCCsGAQUFBwMIMA0GCSqGSIb3DQEBBQUAA4ICAQAQ
  624. # l4rDXANENt3ptK132855UU0BsS50cVttDBOrzr57j7gu1BKijG1iuFcCy04gE1CZ
  625. # 3XpA4le7r1iaHOEdAYasu3jyi9DsOwHu4r6PCgXIjUji8FMV3U+rkuTnjWrVgMHm
  626. # lPIGL4UD6ZEqJCJw+/b85HiZLg33B+JwvBhOnY5rCnKVuKE5nGctxVEO6mJcPxaY
  627. # iyA/4gcaMvnMMUp2MT0rcgvI6nA9/4UKE9/CCmGO8Ne4F+tOi3/FNSteo7/rvH0L
  628. # QnvUU3Ih7jDKu3hlXFsBFwoUDtLaFJj1PLlmWLMtL+f5hYbMUVbonXCUbKw5TNT2
  629. # eb+qGHpiKe+imyk0BncaYsk9Hm0fgvALxyy7z0Oz5fnsfbXjpKh0NbhOxXEjEiZ2
  630. # CzxSjHFaRkMUvLOzsE1nyJ9C/4B5IYCeFTBm6EISXhrIniIh0EPpK+m79EjMLNTY
  631. # MoBMJipIJF9a6lbvpt6Znco6b72BJ3QGEe52Ib+bgsEnVLaxaj2JoXZhtG6hE6a/
  632. # qkfwEm/9ijJssv7fUciMI8lmvZ0dhxJkAj0tr1mPuOQh5bWwymO0eFQF1EEuUKyU
  633. # sKV4q7OglnUa2ZKHE3UiLzKoCG6gW4wlv6DvhMoh1useT8ma7kng9wFlb4kLfchp
  634. # yOZu6qeXzjEp/w7FW1zYTRuh2Povnj8uVRZryROj/TGCBI4wggSKAgEBMIGQMHkx
  635. # CzAJBgNVBAYTAlVTMRMwEQYDVQQIEwpXYXNoaW5ndG9uMRAwDgYDVQQHEwdSZWRt
  636. # b25kMR4wHAYDVQQKExVNaWNyb3NvZnQgQ29ycG9yYXRpb24xIzAhBgNVBAMTGk1p
  637. # Y3Jvc29mdCBDb2RlIFNpZ25pbmcgUENBAhMzAAAAsBGvCovQO5/dAAEAAACwMAkG
  638. # BSsOAwIaBQCggbAwGQYJKoZIhvcNAQkDMQwGCisGAQQBgjcCAQQwHAYKKwYBBAGC
  639. # NwIBCzEOMAwGCisGAQQBgjcCARUwIwYJKoZIhvcNAQkEMRYEFFBDOjk/emNHMZT1
  640. # P/+oO2RnNhndMFAGCisGAQQBgjcCAQwxQjBAoCKAIABFAG4AdABpAHQAeQAgAEYA
  641. # cgBhAG0AZQB3AG8AcgBroRqAGGh0dHA6Ly9tc2RuLmNvbS9kYXRhL2VmIDANBgkq
  642. # hkiG9w0BAQEFAASCAQDgYhnIDKloOR+xIYEZs8gHHGpsLveWUIzcplKikvP8qEpA
  643. # wfxIGbBlKVdMbegetdNCXjp1693blqScWOeWkCgHHN3Um+NKA5YQmDPBb5oyGnIu
  644. # U0dXVoLsbxgFW1kGl3nwIIGO9FupcmGYIp/KO1teZwPtEUCTAyhTvYhNPdTZ8C68
  645. # Y+u/oAap3zPRvV01oXzCEMeCmdE+1PACq5zvJVwkArvn8z1P5Yss/Edb+7Afm3sU
  646. # jdqxg2Xe3yf8nXyReoa80vAGVojsGwgvztvI8dElKmGSFUFJH71I+LcHa/FpYTr/
  647. # XwDbPR2PD7GEP0IMbdH0YqESFFmLP8KOl8o95UsAoYICHzCCAhsGCSqGSIb3DQEJ
  648. # BjGCAgwwggIIAgEBMIGFMHcxCzAJBgNVBAYTAlVTMRMwEQYDVQQIEwpXYXNoaW5n
  649. # dG9uMRAwDgYDVQQHEwdSZWRtb25kMR4wHAYDVQQKExVNaWNyb3NvZnQgQ29ycG9y
  650. # YXRpb24xITAfBgNVBAMTGE1pY3Jvc29mdCBUaW1lLVN0YW1wIFBDQQIKYQKSSgAA
  651. # AAAAIDAJBgUrDgMCGgUAoF0wGAYJKoZIhvcNAQkDMQsGCSqGSIb3DQEHATAcBgkq
  652. # hkiG9w0BCQUxDxcNMTMwMjIyMTkxMTA2WjAjBgkqhkiG9w0BCQQxFgQUmW7sRqG8
  653. # eSOCjAFX0gZ7T1shm28wDQYJKoZIhvcNAQEFBQAEggEAo0K+BgNxnEtg02oxycUT
  654. # 442aVruVBTf8egY0GFthF4jgMdegRW/+e1U4jpOfONuNKEe2sdvB6jwPJ9ZQy2W6
  655. # kwnSQ8JrWXUgdnLAuDRYsCp1X4xO/HfsfX9i8WLWJVgUasgmKAkaywCdazeeF6YD
  656. # vtGVGNCXnxdvtmTmhVgICU0099NOEcs7M/nU3puc7qCt9ozwJYeeGQrG6VFQEzye
  657. # HHN0Ooumxjlkro5w6OWNV4ASkc4zpz5JWfGGCe7aw+KV5J+FapyeMXFykdG35MK8
  658. # RlAKqatsLQRWVpyGbHVEEn6UIbgxqJAuQtS7BRApgzOg6M3HNFxnIZcJ8QkVc74h
  659. # Jg==
  660. # SIG # End signature block