Access denied when code is executed remotely as a wcf service

Yanıt Access denied when code is executed remotely as a wcf service

  • 04 Mayıs 2012 Cuma 13:51
     
      Kod İçerir

    The folowing code when executed locally as a console app is working fine, But when I include the same code in a WCF service, I am getting Access is denied exception.

    using (SPSite newspSite = new SPSite(siteurl))
    {
         foreach (SPService service in newspSite.WebApplication.Farm.Services)
         {
    
                 foreach (SPJobDefinition jobDefinition in service.JobDefinitions)
                 {
    
                      if (jobDefinition.Name == "Word Automation Services")
                      {
                             jobDefinition.RunNow();
                             break;
                      }
    
                 }
          }
    }


    Basically, I am trying to start a Word Conversion timer job manually whenever I need to convert a .docx to .pdf. The above code even when tried wrapping inside

    SPSecurity.RunWithElevatedPrivileges(delegate{ [code] })

    is still giving Access Denied exception when used inside a wcf service deployed on sharepoint.

    This code is giving problems as it is not possible to run Microsoft.SharePoint.Administration methods remotely. The workarounds for this as mentioned here is only working for SPWebService and is not available for WordService.

    Update:


    Tried some of the troubleshooting tips without any luck.

    Are there any alternatives or workarounds for this???

    Any pointers or help is highly appreciated. 

    Thank you.




    • Düzenleyen Raj Adigopula 08 Mayıs 2012 Salı 10:05 screenshot
    •  

Tüm Yanıtlar

  • 04 Mayıs 2012 Cuma 15:23
     
     
    Try to set trust to full in the web.config of that site

    If the reply was helpful or informative, please remember to mark it as answer or vote as helpful. MCITP SHAREPOINT

  • 04 Mayıs 2012 Cuma 17:27
     
     
    Does the application pool account (the account that runs when you run with elevated privileges) have the appropriate permissions to trigger the Word Automation Service? You could try logging into central administration as the application pool account and triggering the job manually to see if it has access (as a quick test).

    Doug Hemminger http://www.sharepointdoug.com

  • 04 Mayıs 2012 Cuma 17:55
     
     
    Yes, the app pool  where "Word Automation service" is running has limited access, but I have given it full access before deploying my custom wcf service. I even tried changing the application pool where the "Word Automation Service" is running and also tried creating a new app pool for the service with an account having full access to the Farm and site. Running the job from central administration manually is also working. But it is not starting when tried to do it using the above code - which is working in a console app but failing with "Access is denied" exception when used in an operation inside a custom WCF service.
  • 04 Mayıs 2012 Cuma 17:58
     
     
    had u tried to set trust to full ?

    If the reply was helpful or informative, please remember to mark it as answer or vote as helpful. MCITP SHAREPOINT

  • 04 Mayıs 2012 Cuma 18:00
     
     

    No, But I searched online how to do that as I am fairly new to sharepoint development, But i didn't find how to do it! :(. 

    But I guess its not a good workaround as it is going to change the permissions for the whole site isn't it?


  • 04 Mayıs 2012 Cuma 18:05
     
     

    Just open web.config and search for the word trust you will fin it set to WSS_Meduim or somthing like that set it to full

    Its not related to the site permission check it if it work we can dig more in it


    If the reply was helpful or informative, please remember to mark it as answer or vote as helpful. MCITP SHAREPOINT

  • 04 Mayıs 2012 Cuma 18:06
     
     
    But I couldn't locate the web.config file, tried in 14 hive, ISAPI etc. folders. There are lot of web.config files but how to locate the one for my site? 
  • 04 Mayıs 2012 Cuma 18:08
     
     

    its

    C:\inetpub\wwwroot\wss\VirtualDirectories\yorsite

    web.config is here


    If the reply was helpful or informative, please remember to mark it as answer or vote as helpful. MCITP SHAREPOINT

  • 04 Mayıs 2012 Cuma 18:13
     
     
    Thank you. I will try changing it and will update here accordingly. But unfortunately I can't do it till I get back to work on Tuesday. Once again thanks for the help.
  • 06 Mayıs 2012 Pazar 02:52
     
     
    I guess I misread a bit the first time I read your post. What account is used for the WCF service? This account needs to have the ability to start timer jobs on the farm. When you run it as a console app, I am guessing, you are running it with a farm administrator account, which has access to start timer jobs. But the WCF service account needs to have this same access. Can check to make sure that the account the WCF service is running under has access to start timer jobs for the farm?

    Doug Hemminger http://www.sharepointdoug.com

  • 06 Mayıs 2012 Pazar 16:13
     
     

    Hey Raj,

    Could you please clarify one very important point. Are you getting:

    • An AccessDeniedException (Obsolete) http://msdn.microsoft.com/en-us/library/ms580250.aspx
    • A System.Security.SecurityException
    • This: System.UnauthorizedAccessException: Access is denied. (Exception from
      HRESULT: 0x80070005 (E_ACCESSDENIED))
    • Or an HTTP 401 Unauthorized
    • Any other perhaps?

    There's a huge difference in the cause of these, so that info would help.

    Are you also doing this on a GET? you might need to POST if you are creating jobs (and registering them in the database!).


    Independant SharePoint Consultant. Feel free to contact me. Blog: http://www.sharepoint.bg/radi Twitter: @RadiAtanassov

  • 08 Mayıs 2012 Salı 08:45
     
     
    @Ramez Al kara I have changed the permission from "WSS_Medium" to "full" in web.config and its still giving same access denied error.
  • 08 Mayıs 2012 Salı 09:01
     
      Kod İçerir

    @Radi.A I guess its the second case,  System.Security.SecurityException, please check the screenshot,.

    Stack trace below:

    Access is denied.
    
    Server stack trace: 
       at System.ServiceModel.Channels.ServiceChannel.ThrowIfFaultUnderstood(Message reply, MessageFault fault, String action, MessageVersion version, FaultConverter faultConverter)
       at System.ServiceModel.Channels.ServiceChannel.HandleReply(ProxyOperationRuntime operation, ProxyRpc& rpc)
       at System.ServiceModel.Channels.ServiceChannel.Call(String action, Boolean oneway, ProxyOperationRuntime operation, Object[] ins, Object[] outs, TimeSpan timeout)
       at System.ServiceModel.Channels.ServiceChannelProxy.InvokeService(IMethodCallMessage methodCall, ProxyOperationRuntime operation)
       at System.ServiceModel.Channels.ServiceChannelProxy.Invoke(IMessage message)
    
    Exception rethrown at [0]: 
       at System.Runtime.Remoting.Proxies.RealProxy.HandleReturnMessage(IMessage reqMsg, IMessage retMsg)
       at System.Runtime.Remoting.Proxies.RealProxy.PrivateInvoke(MessageData& msgData, Int32 type)
       at IDocConverter.Convert()
       at DocConverterClient.Convert()


    The fault response:

     <s:Fault>
          <faultcode xmlns:a="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd">a:FailedAuthentication</faultcode>
          <faultstring xml:lang="en-GB">Access is denied.</faultstring>
     </s:Fault>

    The request which is working when I comment out the above code:

    <s:Envelope xmlns:s="http://schemas.xmlsoap.org/soap/envelope/">
      <s:Header>
        <Action s:mustUnderstand="1" xmlns="http://schemas.microsoft.com/ws/2005/05/addressing/none">http://tempuri.org/IDocConverter/Convert</Action>
      </s:Header>
      <s:Body>
        <Convert xmlns="http://tempuri.org/" />
      </s:Body>
    </s:Envelope>
    Thanking you for your help.


  • 08 Mayıs 2012 Salı 09:56
     
     

    It looks like the credential under which the WCF service is running is overriding your impersonation logic (SPSecurity.RunWithElevatedPrivileges).

    Can you check under which identity the WCF service is running ?

    Use the this code ServiceSecurityContext.Current.PrimaryIdentity to find out identity under which the WCF service is running. Based on that you can provide the appropriate permission for that identiy.


    Sundar Narasiman

  • 08 Mayıs 2012 Salı 10:13
     
     

    ServiceSecurityContext.Current.PrimaryIdentity is returning System.Security.Principal.WindowsIdentity which i guess is my windows login, And I am farm admin, and I am in site collection admin for the site I am working on. And I can manually go and run any of the timer jobs manually including the one I am trying to run in my code. 

    And when I use SPSecurity.RunWithElevatedPrivileges it is running is Sharepoint\system accoount. I am trying all the possible solutions with and without elevated previlages for the code I am getting problem with.

  • 08 Mayıs 2012 Salı 14:23
     
     
    I am still confused about what account you are using to run the WCF service. Is the service hosted in IIS? If so, what is the application pool account?

    Doug Hemminger http://www.sharepointdoug.com

  • 08 Mayıs 2012 Salı 15:52
     
     

    @Doug Hemminger The service is not hosted separately but it is hosted to ISAPI folder of the sharepoint site (http://myspsite/_vti_bin/Converter/DocConverter.svc) and is globally deployed. And is using impersonation to get user id and its windows authentication (ntlm). And I can run other operations of the service without any error. 

    How do i know the app pool account on which my custom service is running? Btw, just browsing through your blog and is really cool.

    Thank you..

  • 08 Mayıs 2012 Salı 17:06
     
     Yanıt

    This is treading a little bit out of my territory, but if you are hosting the site under the SharePoint site, the identity of the WCF service when you elevate privileges should be the application pool account of the SharePoint site. Normally application pool accounts don't have access to timer jobs or the SharePoint config database.

    You can find the application pool account by opening up IIS on the SharePoint server and following the instructions here: http://technet.microsoft.com/en-us/library/cc771170(v=WS.10).aspx

    Once you know the identity of the application pool account, you need to test if the account has the ability to trigger the timer job. If it doesn't, that is the problem.

    Here is a blog post on the issue with a proposed solution: http://jasear.wordpress.com/2010/11/27/custom-action-to-trigger-a-sharepoint-timer-job/

    The solution in the blog post is a little complicated, but should work fine. If you wanted something simpler, you could give the application pool account access to the config database. But I don't recommend that as that represents a potential security issue.


    Doug Hemminger http://www.sharepointdoug.com

    • Yanıt Olarak İşaretleyen Shimin Huang 11 Mayıs 2012 Cuma 07:24
    •