Pergunta

Estou em uma equipe que desenvolve um "portal" para o SharePoint Foundation 2010.Sou responsável por fazer o instalador que configura uma nova instância do SharePoint.Ele lida com mais do que apenas a instalação dos arquivos da solução e a configuração do SharePoint.O instalador cuida da implantação de arquivos no GAC e da criação de nosso cliente de segurança federado (usado para nossa autenticação baseada em declarações do SharePoint).

Durante a instalação de uma instância, concluo algumas tarefas especificamente relacionadas ao SharePoint e uso a API do SharePoint no .NET 3.5:

  1. Criar/Configurar confiança
  2. Crie um aplicativo da web.
  3. Implantar soluções para farm e aplicativos web
  4. Criar conjunto de sites padrão
  5. Ativar recursos padrão no conjunto de sites
  6. Atualize as "propriedades" do aplicativo da web

Até agora, consegui fazer uma instalação funcionar corretamente em um único servidor SharePoint, ou seja, um servidor hospeda o banco de dados do farm e outro é a pilha completa de serviços do SharePoint.Comecei a testar uma configuração que imitará a configuração real do SharePoint em nosso ambiente de hospedagem.Lá temos um servidor de banco de dados e pelo menos três servidores SharePoint, dos quais apenas um possui Administração Central.

O problema que encontrei é que neste caso posso executar corretamente e sem erros todos os passos acima, exceto a ativação de recursos.Removi o código que executa esta etapa e verifiquei se o aplicativo da web, o conjunto de sites, a confiança etc. (exceto as "propriedades") foram criados corretamente iniciando o site, autenticando e vendo o tema "equipe" padrão .No entanto, depois de ativar os recursos padrão, seja por meio da API ou das configurações do conjunto de sites, não consigo mais acessar o site e recebo uma mensagem de erro.

Isso chega ao cerne do meu problema e ao problema que enfrento ao explicá-lo aqui.Nossa solução é altamente complexa porque envolve muitas configurações de aspectos de segurança e dependência de outros serviços fora do SharePoint.Não sei se algumas de nossas configurações não estão se propagando pelos servidores causando um erro interno em nossa solução para causar a página de erro.Também não sei se quando estou definindo as "propriedades" se elas ficam grudadas na situação da fazenda.Tive um problema em que não estava configurando isso corretamente quando comecei esta tarefa e isso causou um problema semelhante ao que estou vendo agora.

Também não tenho certeza se as soluções estão sendo implantadas corretamente, corrompendo os recursos.Configurei o visualizador ULS em cada um dos servidores do SharePoint, mas não consigo encontrar nada relacionado ao ID de correlação do erro que recebo na página de erro.Na verdade, não recebo eventos no visualizador ULS no servidor SharePoint "mestre".Posso ver a implantação e retração de soluções no visualizador nos outros dois servidores.

Devo estar faltando alguma coisa que acontece em um farm com vários servidores.Espero que alguém possa dar uma olhada no código que uso para implantar soluções e definir propriedades para me ajudar.Eu também gostaria de descobrir por que não consigo ver o erro que estou recebendo em nenhum dos visualizadores ULS.Alguém pode explicar isso para mim?

Também estou procurando exemplos mais definitivos de como configurar e configurar o SharePoint por meio da API C#.Até este ponto, tenho descompilado o código dos commandlets e replicado o que posso no código.Ainda não tenho uma maneira "correta" de ativar um recurso via C# e estou apenas criando um processo executando stsadm.exe para ativar os recursos.

Aqui está meu código para adicionar e implantar uma solução:

      SPSolution newSolution = SPFarm.Local.Solutions.Add(Path.Combine(this.SharePointPointRootFolder, solutionDefinition.filename));

      if (!solutionDefinition.webApplicationSpecific)
      {
        Console.WriteLine("Adding a farm specific solution.");

        newSolution.Deploy(DateTime.Now, true, true);

        this.WaitForSolutionJobsToComplete(newSolution.Id);

        newSolution.Synchronize();
      }
      else //specific to a web application.  Load the new solution.
      {
        Console.WriteLine("Adding web application specific solution.");

        Collection<SPWebApplication> webAppCol = new Collection<SPWebApplication>();
        webAppCol.Add(this.WebApplication);

        newSolution.Deploy(DateTime.Now, true, webAppCol, true);

        this.WaitForSolutionJobsToComplete(newSolution.Id);

        newSolution = SPFarm.Local.GetObject(newSolution.Id) as SPSolution;

        newSolution.Synchronize();

        this.WaitForSolutionJobsToComplete(newSolution.Id);

        newSolution.Update();
      }

Aqui está meu código para ativar recursos.Ele apenas usa um processo para usar STSADM.EXE:

void UpdateFeatures(SPSite site)
{
  Console.WriteLine("Updating features.");

  SPSolutionDefinitionCollection collection = SolutionConfigurer.LoadSolutionDefinitions();

  foreach (SPSolutionDefinition solutionDefinition in collection.spSolutionDefinition)
  {

    Guid id = new Guid(solutionDefinition.ID);

    if (solutionDefinition.spFeatureDefinition != null && solutionDefinition.spFeatureDefinition.Length > 0)
    {
      foreach (Models.SPFeatureDefinition fDef in solutionDefinition.spFeatureDefinition)
      {
        Guid fDefId = new Guid(fDef.ID);

        //this.Activate(fDefId, site);

        Process stsadmP = WebApplicationConfigurer.GetSTSADMProcess(this.STSADMPath, "-o activatefeature -id " + fDef.ID + " -url " + this.SiteCollectionUrl + " -force");

        Console.WriteLine(string.Format("Invoking STSADM.EXE for feature deployment: {0} with arguments:{1}", stsadmP.StartInfo.FileName, stsadmP.StartInfo.Arguments));

        stsadmP.Start();
        stsadmP.WaitForExit();

        if (stsadmP.ExitCode == 0)
        {
          Console.WriteLine(string.Format("STSADM.EXE successfully ran for feature id {0} and produced this output: {1}", fDefId, stsadmP.StandardOutput.ReadToEnd()));
        }
        else
        {
          Console.WriteLine(string.Format("STSADM.EXE did not produce a successful exit code for feature id {0} and produced this output: {1} + {2}", fDefId, 
            stsadmP.StandardOutput.ReadToEnd(), stsadmP.StandardError.ReadToEnd()));
        }
      }
    }
  }
}

Veja como atualizo uma propriedade.Faço isso por último porque estava fazendo isso depois de implantar as soluções, mas parece que a ativação de recursos estava redefinindo os valores.

public void UpdatePropertiesWebApplication()
{
  string dnsName = this.SigningCertificate.GetNameInfo(X509NameType.DnsName, false);

  SPWebApplication webApplication = SPFarm.Local.GetObject(this.WebApplicationId) as SPWebApplication;

  if (webApplication != null)
  {
    Console.WriteLine("Updating property information for the web application.");

    if (!webApplication.Properties.ContainsKey(Constants.PropertyBagKeys.ESB_ROOT))
    {
      webApplication.Properties.Add(Constants.PropertyBagKeys.ESB_ROOT, this.ESBUrl);
    }
    else
    {
      Console.WriteLine("Updating ESB Root URL. " + this.ESBUrl);
      webApplication.Properties[Constants.PropertyBagKeys.ESB_ROOT] = this.ESBUrl;
    }

    Console.WriteLine("ESB Root Url: " + webApplication.Properties[Constants.PropertyBagKeys.ESB_ROOT]);

    if (!webApplication.Properties.ContainsKey(Constants.PropertyBagKeys.REALM))
    {
      webApplication.Properties.Add(Constants.PropertyBagKeys.REALM, this.SharePointTrustPoint);
    }
    else
    {
      Console.WriteLine("Updating realm. " + this.SharePointTrustPoint);
      webApplication.Properties[Constants.PropertyBagKeys.REALM] = this.SharePointTrustPoint;
    }

    Console.WriteLine("Realm: " + webApplication.Properties[Constants.PropertyBagKeys.REALM]);

    if (!webApplication.Properties.ContainsKey(Constants.PropertyBagKeys.SSO_ROOT))
    {
      webApplication.Properties.Add(Constants.PropertyBagKeys.SSO_ROOT, this.SSOUrl);
    }
    else
    {
      Console.WriteLine("Updating the broker url. " + this.SSOUrl);
      webApplication.Properties[Constants.PropertyBagKeys.SSO_ROOT] = this.SSOUrl;
    }

    Console.WriteLine("Broker Url: " + webApplication.Properties[Constants.PropertyBagKeys.SSO_ROOT]);

    if (!webApplication.Properties.ContainsKey(Constants.PropertyBagKeys.TRUSTED_CERT_DNS_IDENT))
    {
      webApplication.Properties.Add(Constants.PropertyBagKeys.TRUSTED_CERT_DNS_IDENT, dnsName);
    }
    else
    {
      Console.WriteLine("Updating trusted cert dns identity. " + dnsName);
      webApplication.Properties[Constants.PropertyBagKeys.TRUSTED_CERT_DNS_IDENT] = dnsName;
    }

    Console.WriteLine("Trusted Certificate Identity: " + webApplication.Properties[Constants.PropertyBagKeys.TRUSTED_CERT_DNS_IDENT]);

    webApplication.Update(true);
  }
}
Foi útil?

Solução

Para responder à sua pergunta geral, a maneira recomendada de implantar a solução no SharePoint 2010 é usar o PowerShell.

De O que há de novo:Windows PowerShell para SharePoint:

O Windows PowerShell substitui a ferramenta de administração Stsadm.exe.A partir de agora, você deverá usar a tecnologia de script do Windows PowerShell para desenvolver novos scripts de linha de comando no SharePoint Foundation 2010.

Aqui estão alguns exemplos e scripts para implantação com PowerShell:

E aqui estão informações sobre como ativar recursos no PowerShell:

Para responder sua pergunta específica, é possível ativar um recurso em C#:

Guid fDefId = new Guid(fDef.ID);
site.Features.Add(fDefId);

Para mais informações, veja SPSite.Recursos e SPFeatureCollection.Adicionar.

Outras dicas

para ser totalmente honesto, nunca vejo mais sentido em fazer qualquer coisa no código que possa fazer diretamente com o stsadm.

Então, eu sempre uso o equivalente ao que preciso:

stsadm -o deletesolution -name solution.wsp -override
stsadm -o addsolution -filename c:\path\solution.wsp
stsadm -o deploysolution -name solution.wsp -allowgacdeployment -local -force

Então...

Ativar recursos
Opções de solução de configuração
Aplicar modelo mestre
Crie subsites
Crie listas
Adicionar Web Parts
Definir permissões
Ocultar/Mostrar navegação e colunas
Adicione todos os dados necessários à implantação
Terminar

Tive muitos problemas ao tentar implantar uma solução usando o método que você usa (basta pesquisar que postei aqui e não encontrei soluções)

Licenciado em: CC-BY-SA com atribuição
Não afiliado a sharepoint.stackexchange
scroll top