在 Azure 中将应用程序池的标识设置为 LocalSystem

发布于 2025-01-06 10:20:06 字数 4072 浏览 1 评论 0原文

有没有办法在 ServiceDefinition.csdef 或其他地方执行此操作,而无需转到 IIS 并手动调整?

我尝试了 executionContext="elevated" 的 webrole,但不起作用。

更新

如果您在 Azure IIS 上安装“IIS 6 Metabase Compatibility”,下面显示的错误将会消失。

这引发了另一个问题,如何在 Azure 上的部署阶段自动安装“IIS 6 Metabase Compatibility”。


@astaykov,我喜欢评论,但下面的代码太大,所以我使用这个地方。

我使用 Wade Wagner 编写的相同代码:

public override bool OnStart()
        {
            // http://code.msdn.microsoft.com/windowsazure/CSAzureChangeAppPoolIdentit-27099828
            // This variable is used to iterate through list of Application pools 
            string metabasePath = "IIS://localhost/W3SVC/AppPools";
            string appPoolName;
            using (ServerManager serverManager = new ServerManager())
            {
                //Get the name of the appPool that is created by Azure 
                appPoolName = serverManager.Sites[RoleEnvironment.CurrentRoleInstance.Id + "_Web"].Applications.First().ApplicationPoolName;
                // Get list of appPools at specified metabasePath location 
                using (DirectoryEntry appPools = new DirectoryEntry(metabasePath))
                {
                    // From the list of appPools, Search and get the appPool that is created by Azure  
                    using (DirectoryEntry azureAppPool = appPools.Children.Find(appPoolName, "IIsApplicationPool"))
                    {
                        if (azureAppPool != null)
                        {
                            // Refer to: 
                            // http://www.microsoft.com/technet/prodtechnol/WindowsServer2003/Library/IIS/e3a60d16-1f4d-44a4-9866-5aded450956f.mspx?mfr=true,  
                            // http://learn.iis.net/page.aspx/624/application-pool-identities/  
                            // for more info on AppPoolIdentityType 
                            azureAppPool.InvokeSet("AppPoolIdentityType", new Object[] { 0 });  // MD_APPPOOL_IDENTITY_TYPE_LOCALSYSTEM
                            // Write above settings to IIS metabase 
                            azureAppPool.Invoke("SetInfo", null);
                            // Commit the above configuration changes that are written to metabase 
                            azureAppPool.CommitChanges();
                        }
                    }
                }
            }
            RoleInRun = true;
            TaskInRun = false;
            return base.OnStart();
        }

我可以在 appPoolName 处获取正确的值,但这里发生了错误: using (DirectoryEntry azureAppPool = appPools.Children.Find(appPoolName, "IIsApplicationPool"))

我正在到处搜索解决方案,但仍然找不到线索 以下错误来自 IIS 事件:

Application: WaIISHost.exe
Framework Version: v4.0.30319
Description: The process was terminated due to an unhandled exception.
Exception Info: System.Runtime.InteropServices.COMException
Stack:
   at System.DirectoryServices.DirectoryEntry.Bind(Boolean)
   at System.DirectoryServices.DirectoryEntry.Bind()
   at System.DirectoryServices.DirectoryEntry.get_IsContainer()
   at System.DirectoryServices.DirectoryEntries.Find(System.String, System.String)
   at GimmeRank.Redirector.WebRole.OnStart()
   at Microsoft.WindowsAzure.ServiceRuntime.RoleEnvironment.InitializeRoleInternal(Microsoft.WindowsAzure.ServiceRuntime.Implementation.Loader.RoleType)
   at Microsoft.WindowsAzure.ServiceRuntime.Implementation.Loader.RoleRuntimeBridge.<InitializeRole>b__0()
   at System.Threading.ExecutionContext.runTryCode(System.Object)
   at System.Runtime.CompilerServices.RuntimeHelpers.ExecuteCodeWithGuaranteedCleanup(TryCode, CleanupCode, System.Object)
   at System.Threading.ExecutionContext.Run(System.Threading.ExecutionContext, System.Threading.ContextCallback, System.Object, Boolean)
   at System.Threading.ExecutionContext.Run(System.Threading.ExecutionContext, System.Threading.ContextCallback, System.Object)
   at System.Threading.ThreadHelper.ThreadStart()

有什么想法吗?

Is there a way to do this in ServiceDefinition.csdef or other place without go to the IIS and adjust by hand?

I tried executionContext="elevated" for webrole, not working.

UPDATE

If you install "IIS 6 Metabase Compatibility" on Azure IIS, the error I shown below will gone.

This raise another issue, howto install "IIS 6 Metabase Compatibility" automatically at deployment stage on Azure.


@astaykov, I like to comment but the code below too big, so I use this place.

I use the same code that wrote by Wade Wagner as:

public override bool OnStart()
        {
            // http://code.msdn.microsoft.com/windowsazure/CSAzureChangeAppPoolIdentit-27099828
            // This variable is used to iterate through list of Application pools 
            string metabasePath = "IIS://localhost/W3SVC/AppPools";
            string appPoolName;
            using (ServerManager serverManager = new ServerManager())
            {
                //Get the name of the appPool that is created by Azure 
                appPoolName = serverManager.Sites[RoleEnvironment.CurrentRoleInstance.Id + "_Web"].Applications.First().ApplicationPoolName;
                // Get list of appPools at specified metabasePath location 
                using (DirectoryEntry appPools = new DirectoryEntry(metabasePath))
                {
                    // From the list of appPools, Search and get the appPool that is created by Azure  
                    using (DirectoryEntry azureAppPool = appPools.Children.Find(appPoolName, "IIsApplicationPool"))
                    {
                        if (azureAppPool != null)
                        {
                            // Refer to: 
                            // http://www.microsoft.com/technet/prodtechnol/WindowsServer2003/Library/IIS/e3a60d16-1f4d-44a4-9866-5aded450956f.mspx?mfr=true,  
                            // http://learn.iis.net/page.aspx/624/application-pool-identities/  
                            // for more info on AppPoolIdentityType 
                            azureAppPool.InvokeSet("AppPoolIdentityType", new Object[] { 0 });  // MD_APPPOOL_IDENTITY_TYPE_LOCALSYSTEM
                            // Write above settings to IIS metabase 
                            azureAppPool.Invoke("SetInfo", null);
                            // Commit the above configuration changes that are written to metabase 
                            azureAppPool.CommitChanges();
                        }
                    }
                }
            }
            RoleInRun = true;
            TaskInRun = false;
            return base.OnStart();
        }

I can get rigth value at appPoolName, But error happened here:
using (DirectoryEntry azureAppPool = appPools.Children.Find(appPoolName, "IIsApplicationPool"))

I am searching solutions everywhere but still cannot find a clue
Error below, from IIS events:

Application: WaIISHost.exe
Framework Version: v4.0.30319
Description: The process was terminated due to an unhandled exception.
Exception Info: System.Runtime.InteropServices.COMException
Stack:
   at System.DirectoryServices.DirectoryEntry.Bind(Boolean)
   at System.DirectoryServices.DirectoryEntry.Bind()
   at System.DirectoryServices.DirectoryEntry.get_IsContainer()
   at System.DirectoryServices.DirectoryEntries.Find(System.String, System.String)
   at GimmeRank.Redirector.WebRole.OnStart()
   at Microsoft.WindowsAzure.ServiceRuntime.RoleEnvironment.InitializeRoleInternal(Microsoft.WindowsAzure.ServiceRuntime.Implementation.Loader.RoleType)
   at Microsoft.WindowsAzure.ServiceRuntime.Implementation.Loader.RoleRuntimeBridge.<InitializeRole>b__0()
   at System.Threading.ExecutionContext.runTryCode(System.Object)
   at System.Runtime.CompilerServices.RuntimeHelpers.ExecuteCodeWithGuaranteedCleanup(TryCode, CleanupCode, System.Object)
   at System.Threading.ExecutionContext.Run(System.Threading.ExecutionContext, System.Threading.ContextCallback, System.Object, Boolean)
   at System.Threading.ExecutionContext.Run(System.Threading.ExecutionContext, System.Threading.ContextCallback, System.Object)
   at System.Threading.ThreadHelper.ThreadStart()

Anyideas?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

孤蝉 2025-01-13 10:20:06

executionContext="elevated" 只会将您的 RoleEntryPoint 作为本地 SYSTEM 帐户运行,但它不是 IIS 池标识。

您可能需要查看 韦德·瓦格纳的这篇博文。他在那里描述的内容可以在您的 OnStart 方法中与executionContext="elevated" 一起运行(因为只有管理员可以更改池身份)。如果这对本地系统不起作用,您可以为 RDP 创建一个用户,它将添加到管理员组中,并且您可以将 iis 应用程序池标识设置为该用户。

更新

嗯,我使用了以下方法(类似)并且效果很好:

private void SetAppPoolIdentity()
{
    string appPoolUser = "myRDP_admin_user";
    string appPoolPass = "my_super_secure_password";

    Action<string> iis7fix = (appPoolName) =>
    {
        bool committed = false;
        while (!committed)
        {
            try
            {
                using (ServerManager sm = new ServerManager())
                {
                    var applicationPool = sm.ApplicationPools[appPoolName];
                    applicationPool.ProcessModel.IdentityType = ProcessModelIdentityType.SpecificUser;
                    applicationPool.ProcessModel.UserName = appPoolUser;
                    applicationPool.ProcessModel.Password = appPoolPass;
                    sm.CommitChanges();
                    committed = true;
                }
            }
            catch (FileLoadException fle)
            {
                Trace.TraceError("Trying again because: " + fle.Message);
            }
        }
    };

    // ServerManager in %WinDir%System32InetSrvMicrosoft.Web.Administration.dll
    var sitename = RoleEnvironment.CurrentRoleInstance.Id + "_Web";
    var appPoolNames = new ServerManager().Sites[sitename].Applications.Select(app => app.ApplicationPoolName).ToList();
    appPoolNames.ForEach(iis7fix);
}

你能尝试一下吗?请注意,它不适用于本地系统帐户,因为它不是真实帐户,我们不能以这种方式设置它(至少我不知道如何做到这一点,但对于 RDP 的特定帐户,它可以正常工作)。

executionContext="elevated" will only run your RoleEntryPoint as the local SYSTEM account, but it is not the IIS pool identity.

You may want to check out this blog post by Wade Wagner. What he describes there, can be run in your OnStart method along with executionContext="elevated" (because only admin can change pool identity). If that does not work for Local System, you can create a user for RDP, it will added in the Administrators group, and you can set the iis app pool identity to that user.

UPDATE

Hm, I used the following method (which is similar) and it worked fine:

private void SetAppPoolIdentity()
{
    string appPoolUser = "myRDP_admin_user";
    string appPoolPass = "my_super_secure_password";

    Action<string> iis7fix = (appPoolName) =>
    {
        bool committed = false;
        while (!committed)
        {
            try
            {
                using (ServerManager sm = new ServerManager())
                {
                    var applicationPool = sm.ApplicationPools[appPoolName];
                    applicationPool.ProcessModel.IdentityType = ProcessModelIdentityType.SpecificUser;
                    applicationPool.ProcessModel.UserName = appPoolUser;
                    applicationPool.ProcessModel.Password = appPoolPass;
                    sm.CommitChanges();
                    committed = true;
                }
            }
            catch (FileLoadException fle)
            {
                Trace.TraceError("Trying again because: " + fle.Message);
            }
        }
    };

    // ServerManager in %WinDir%System32InetSrvMicrosoft.Web.Administration.dll
    var sitename = RoleEnvironment.CurrentRoleInstance.Id + "_Web";
    var appPoolNames = new ServerManager().Sites[sitename].Applications.Select(app => app.ApplicationPoolName).ToList();
    appPoolNames.ForEach(iis7fix);
}

Could you try that? Note that it will not work with Local System account, as it is not real account and we cannot set it this way (at least I don't know how to do it, but with specific account for RDP it works fine).

离鸿 2025-01-13 10:20:06

创建start.cmd:

FOR /F "tokens=*" %%A IN ('%windir%/system32/inetsrv/APPCMD list wp /text:apppool.name') DO (

%systemroot%/system32/inetsrv/APPCMD set config /section:applicationPools /[name='%%A%':'].processModel.identityType:LocalSystem

)

Create start.cmd:

FOR /F "tokens=*" %%A IN ('%windir%/system32/inetsrv/APPCMD list wp /text:apppool.name') DO (

%systemroot%/system32/inetsrv/APPCMD set config /section:applicationPools /[name='%%A%':'].processModel.identityType:LocalSystem

)
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文