Question

I have in my sharepoint application an external source that must be accessed by 2 parts of my application

The first part is a page, where the users can search on a form, the external data. The second part is a timer job that synchronizes external data with some sharepoint sites.

TO do so, I added the following code in my Entity Framework Connection constructor.

It works perfect for the page, but it does not work for the timer job.

As everybody knows the app page runs under the context of the application poool account, I added that account in the the secure store service administrator, and also in the Target Application.

However, for the timer service I checked on services.msc and it runs under the farm account, which should have permissions already.

BY checking some posts, I read that the timer service runs under SHAREPOINT\System, but this is not an account I can grant access to, it says that the account does not exist.

The specified user or domain group was not found.  or Claim is null on the resolved pickerentity.

I need to be able that my timer job reads that data.

/// <summary>
        /// Gets the database server and database name from the property bag
        /// </summary>
        /// <returns></returns>
        public static string GetDMSConnectionStringFromSecureStore()
        {
            var entityBuilder = new EntityConnectionStringBuilder();
            try
            {
                const string providerName = "System.Data.SqlClient";
                var dic = GetCredentialsFromSecureApp(Constants.SecureStore.ApplicationId);
                var serverName = string.Empty;
                var databaseName = string.Empty;
                var databaseUserName = string.Empty;
                var databasePassword = string.Empty;

                foreach (var item in dic)
                {
                    if (item.Key == Constants.SecureStore.DatabaseServerField)
                    {
                        serverName = item.Value;
                    }
                    if (item.Key == Constants.SecureStore.DatabaseNameField)
                    {
                        databaseName = item.Value;
                    }
                    if (item.Key == Constants.SecureStore.UserNameField)
                    {
                        databaseUserName = item.Value;
                    }
                    if (item.Key == Constants.SecureStore.PasswordField)
                    {
                        databasePassword = item.Value;
                    }
                }

                // Initialize the connection string builder for the underlying provider.
                var sqlBuilder = new SqlConnectionStringBuilder
                {
                    DataSource = serverName,
                    InitialCatalog = databaseName,
                    UserID = databaseUserName,
                    Password = databasePassword
                };

                // Build the SqlConnection connection string.
                var providerString = sqlBuilder.ToString();

                // Initialize the EntityConnectionStringBuilder.
                entityBuilder.Provider = providerName;
                entityBuilder.ProviderConnectionString = providerString;
                entityBuilder.Metadata = @"res://*/DMSModel.csdl|res://*/DMSModel.ssdl|res://*/DMSModel.msl";
            }
            catch (Exception ex)
            {
                LoggingService.LogError(LoggingCategory.Security, ex);
            }

            return entityBuilder.ToString();
        }

        private static SecureString CreateSecureString(string unsecureString)
        {
            var secureString = new SecureString();
            foreach (var c in unsecureString/*.ToCharArray()*/)
            {
                secureString.AppendChar(c);
            }
            return secureString;
        }

        public static SPSite GetCentralAdminSite()
        {
            var adminWebApp = SPAdministrationWebApplication.Local;
            if (adminWebApp == null)
            {
                throw new InvalidProgramException("Unable to get the admin web app");
            }

            SPSite adminSite;
            var adminSiteUri = adminWebApp.GetResponseUri(SPUrlZone.Default);
            if (adminSiteUri != null)
            {
                adminSite = adminWebApp.Sites[adminSiteUri.AbsoluteUri];
            }
            else
            {
                throw new InvalidProgramException("Unable to get Central Admin Site.");
            }

            return adminSite;
        }

        private static string GetStringFromSecureString(SecureString secStr)
        {
            if (secStr != null)
            {
                var pPlainText = IntPtr.Zero;
                try
                {
                    pPlainText = Marshal.SecureStringToBSTR(secStr);
                    return Marshal.PtrToStringBSTR(pPlainText);
                }
                finally
                {
                    if (pPlainText != IntPtr.Zero)
                    {
                        Marshal.FreeBSTR(pPlainText);
                    }
                }
            }

            return null;
        }
Was it helpful?

Solution

The SharePoint System Account is the farm account. A quick way to identify this is in Central Admin. Goto Security > Configure Service Accounts. Select Farm Account. It will display which account is being used. Ensure that account has the appropriate permissions to the secure store entry.

Licensed under: CC-BY-SA with attribution
Not affiliated with sharepoint.stackexchange
scroll top