Sharepoint: exécution de stsadm à partir d'un travail du minuteur + SHAREPOINT \ Droits système

Translate

J'ai une situation inhabituelle dans laquelle j'ai besoin d'un travail de minuteur SharePoint pour avoir à la fois des privilèges d'administrateur local et pour avoirSHAREPOINT\SystemPrivilèges SharePoint.

Je peux obtenir les privilèges Windows en configurant simplement le service de minuterie pour utiliser un compte qui est membre des administrateurs locaux. Je comprends que ce n'est pas une bonne solution car cela donne au service de minuterie SharePoint plus de droits qu'il est censé en avoir. Mais cela permet au moins à mon travail du minuteur SharePoint de s'exécuterstsadm.

Un autre problème lié à l'exécution du service de minuterie sous l'administrateur local est que cet utilisateur n'aura pas nécessairementSHAREPOINT\SystemPrivilèges SharePoint dont j'ai également besoin pour ce travail SharePoint. Il se trouve queSPSecurity.RunWithElevatedPrivilegesne fonctionnera pas dans ce cas. Le réflecteur montre queRunWithElevatedPrivilegesvérifie si le processus actuel estowstimer(le processus de service qui exécute les travaux SharePoint) et n'effectue aucune élévation, c'est le cas (le rationnel ici, je suppose, est que le service de minuterie est censé fonctionner sousNT AUTHORITY\NetworkServicecompte Windows qui aSHAREPOINT\SystemPrivilèges SharePoint, et il n'est donc pas nécessaire d'élever les privilèges pour un travail du minuteur).

La seule solution possible ici semble être d'exécuter le service de minuterie sous son compte Windows NetworkService habituel et d'exécuter stsadm en tant qu'administrateur local en stockant les informations d'identification de l'administrateur quelque part et en les transmettant à System.Diagnostics.Process.Run () via le nom d'utilisateur de StarInfo , domaine et mot de passe.

Il semble que tout devrait fonctionner maintenant, mais voici un autre problème avec lequel je suis actuellement coincé. Stsamd échoue avec la fenêtre contextuelle d'erreur suivante (!) (Winternals filemon montre que stsadm s'exécute sous l'administrateur dans ce cas):

The application failed to initialize properly (0x0c0000142).
Click OK to terminate the application.

L'Observateur d'événements n'enregistre rien sauf le popup.

L'utilisateur administrateur local est mon compte et quand je viens de courirstsadminteractivement sous ce compte tout va bien. Cela fonctionne également très bien lorsque je configure le service de minuterie pour qu'il s'exécute sous ce compte.

Toutes les suggestions sont appréciées :)

This question and all comments follow the "Attribution Required."

Toutes les réponses

Translate

Je ne suis pas au travail, donc cela me vient à l'esprit, mais: si vous obtenez une référence au site, pouvez-vous essayer de créer un nouveau SPSite avec le SYSTEM-UserToken?

SPUserToken sut = thisSite.RootWeb.AllUsers["SHAREPOINT\SYSTEM"].UserToken;

using (SPSite syssite = new SPSite(thisSite.Url,sut)
{
    // Do what you have to do
}
La source
Translate

Les travaux du minuteur SharePoint s'exécutent avec les informations d'identification de l'administrateur du cabinet SharePoint, car les informations entrent dans la base de données SharePoint Config. Ainsi, le pool d'applications n'aura pas accès.

Pour tester le travail du minuteur dans l'environnement de développement, nous pouvons temporairement remplacer le compte du pool d'applications par le compte du pool d'applications utilisé pour l'administration centrale.

La source
axk
Translate

D'autres applications, si elles sont exécutées de cette façon (c'est-à-dire à partir d'un travail de minuterie avec des informations d'identification explicites) échouent de la même manière avec "L'application n'a pas pu s'initialiser correctement". Je veux juste une application simple qui prend le chemin d'un autre exécutable et ses arguments en tant que paramètres et lorsqu'elle est exécutée à partir de ce travail de minuterie, elle échoue de la même manière.

internal class ExternalProcess
{
    public static void run(String executablePath, String workingDirectory, String programArguments, String domain, String userName,
                           String password, out Int32 exitCode, out String output)
    {
        Process process = new Process();

        process.StartInfo.UseShellExecute = false;
        process.StartInfo.RedirectStandardError = true;
        process.StartInfo.RedirectStandardOutput = true;

        StringBuilder outputString = new StringBuilder();
        Object synchObj = new object();

        DataReceivedEventHandler outputAppender =
            delegate(Object sender, DataReceivedEventArgs args)
                {
                    lock (synchObj)
                    {
                        outputString.AppendLine(args.Data);
                    }
                };

        process.OutputDataReceived += outputAppender;
        process.ErrorDataReceived += outputAppender;

        process.StartInfo.FileName = @"C:\AppRunner.exe";
        process.StartInfo.WorkingDirectory = workingDirectory;
        process.StartInfo.Arguments = @"""" + executablePath + @""" " + programArguments;

        process.StartInfo.UserName = userName;
        process.StartInfo.Domain = domain; 
        SecureString passwordString = new SecureString();

        foreach (Char c in password)
        {
            passwordString.AppendChar(c);
        }

        process.StartInfo.Password = passwordString;

        process.Start();

        process.BeginOutputReadLine();
        process.BeginErrorReadLine();

        process.WaitForExit();

        exitCode = process.ExitCode;
        output = outputString.ToString();
    }
}

AppRunner fait essentiellement la même chose que le fragment ci-dessus, mais sans nom d'utilisateur ni mot de passe

La source