Problem Description
I have a Windows service which is hosting an NServiceBus endpoint in NServiceBus.Host.exe.
The binaries are deployed to c:\inetpub\bus\services\myService folder on the server.
A DSC script makes sure the Windows service is created/exists on the server, with the "path to executable" property of the service set to "c:\inetpub\bus\services\myService´NServiceBus.Host.exe" -service NServicebus.Production.
Note! The -service switch is added when installing the service by using the built-in NServiceBus.Host.exe /install parameter, which is why I added it to the Windows service executable path in the DSC script.
Now, when I try to start the service manually on the server, it yields the following error message
Windows could not start the <service name> service on the Local Computer.
Error 1053: The service did not respond to the start or control request in a timely fashion.
Debugging Steps
I have looked through the event log and the following two error messages sticks out:
NServiceBust.Host.exe error:
Application: NServiceBus.Host.exe
Framework Version: v4.0.30319
Description: The process was terminated due to an unhandled exception.
Exception Info:
Topshelf.Exceptions.ConfigurationException
at Topshelf.Internal.Actions.RunAsServiceAction.Do(Topshelf.Configuration.IRunConfiguration)
at Topshelf.Runner.Host(Topshelf.Configuration.IRunConfiguration, System.String[])
at NServiceBus.Host.Program.Main(System.String[])
Local Activation permission error:
The application-specific permission settings do not grant Local
Activation permission for the COM Server application with CLSID
{D63B10C5-BB46-4990-A94F-E40B9D520160}
and APPID
{9CA88EE3-ACB7-47C8-AFC4-AB702511C276}
to the user <my_service_account_user> SID (<service_account_SID>) from
address LocalHost (Using LRPC) running in the application container
Unavailable SID (Unavailable). This security permission can be modified
using the Component Services administrative tool.`
Note! The error above only occurs once, i.e. the first time I try to start the service. It does not appear again in the event log for any subsequent attempts of starting the service.
What I have done so far:
Tried the suggestions in a closely related post here on SO, none of which were working.
Tried to install the service by using using the NServiceBus.Host.exe /install parameter. In this case, the service name is created with its name on the following format: MyService.EndpointConfig_v1.0.0.0. Using this approach, the service starts successfully without any error message
Stopping the service and then try to start the service created by the DSC script (with a different name) => success
Removing the service created by NServiceBus and then trying to start the DSC-created service again => failure
Tried granting the service account used for logon when running the service various privileges (neither of which yielded any success), among others:
Membership in the Administrators group
Membership in the Performance Log Users group
Full DCOM permissions via "Launch and Activation Permissions" in dcomcnfg
Tried running c:\inetpub\bus\services\myService´NServiceBus.Host.exe NServicebus.Production from the CLI => success
Code
My Init() method for the service looks like this:
namespace MyService
{
public class EndpointConfig : IConfigureThisEndpoint, AsA_Server, IWantCustomLogging, IWantCustomInitialization
{
public void Init()
{
Directory.SetCurrentDirectory(System.AppDomain.CurrentDomain.BaseDirectory);
SetLoggingLibrary.Log4Net(() => XmlConfigurator.Configure(File.OpenRead(#"log4net.config")));
GlobalContext.Properties["Hostname"] = Dns.GetHostName();
GlobalContext.Properties["Service"] = typeof(EndpointConfig).Namespace;
var container = new WindsorContainer(new XmlInterpreter());
Configure.With()
.CastleWindsorBuilder(container)
.XmlSerializer()
.MsmqTransport()
.IsTransactional(true)
.PurgeOnStartup(false)
.IsolationLevel(System.Transactions.IsolationLevel.RepeatableRead);
var connectionString = ConfigurationManager.ConnectionStrings["<some_conn_string>"].ConnectionString;
container.Register(
Component.For<IDatabaseProvider>()
.ImplementedBy<DatabaseProvider>()
.DependsOn(Property.ForKey("connectionString").Eq(connectionString)));
}
}
}
Theory
When installing the service using /install I assume that NServiceBus.Host.exe does some black magic under the hood - e.g. grants some necessary permissions - to make the service able to start.
Note! On the server, the latest version of NServiceBus is installed (v6.x). However, in my solution/service project version 2.x is used (please, do not ask if I can upgrade - unfortunately, that is not an option).
Appreciate any help I can get, as I am running out of ideas.
EDIT 1
I was asked why I can't just use the /install parameter of NServiceBus and be happy with that. The answer to that is that I could (and, actually, I currently am).
The reason I have still posted this question is split:
I wish to understand why one of two seemingly equivalent approaches fails
I am not completely happy with using the /install parameter. The reason? It boils down to a "chicken or the egg" problem. I use Powershell DSC to provision servers in Azure and I believe that ensuring that Windows Services exists on the server is the responsibility of DSC. However, the first time a server is provisioned the services cannot exist unless I script their creation with DSC, and point the executable path to where the service binaries will be deployed whenever that happens. The other alternative is to skip service creation in DSC, and run the NServiceBus.Host.exe /install as a part of the service/application deployment script instead. Obviously, deployment cannot happen until after a server has been provisioned. Thus, it requires the Windows Service part of the DSC script being stripped down to e.g. merely ensuring the service exist - a verification which will fail until a first time deployment of the application has been performed.
Related
I have followed this guide to Enable virtual network integration in my Azure Function.
https://learn.microsoft.com/en-us/azure/azure-functions/functions-networking-options?tabs=azure-cli#enable-virtual-network-integration
At first it looks good and my Virtual network with a Virtual network gateway configured with Point to Site VPN shows up as expected:
However on add it fails with the following message:
If I then look at Activity log it does say Succeeded.
Looking at VNet Integration for the Azure Function it has been set up and I get GATEWAY STATUS Online but CERTIFICATE STATUS Certificates not in sync.
Looking at the Networking tab it also says VNet integration Off.
Now looking at the subscription that has the virtual network I did receive the following error the first time I tried to set up the VLAN:
Operation name Creates or updates a VirtualNetworkGateway
Error code UpdateOnResourceNotAllowedWithApiVersion
Message Resource /subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/my-resource-group/providers/Microsoft.Network/virtualNetworkGateways/my-virtual-network-gateway
cannot be updated using API version 2016-09-01 since it uses the
property VpnClientConfiguration AAD authentication parameters which
has been set using a higher API version 2019-04-01. Please use api
version greater than or equal to 2019-04-01 to update the resource.
Does this mean that Azure GUI uses API version 2016-09-01? Can I set the GUI to use API version 2019-04-01 or how can I manually add the configuration needed to make this work?
I have tried to use Sync Network from App Service Plan Network GUI but it fails as well.
There I get the following errors:
Operation name Creates or updates a VirtualNetworkGateway
Error code UpdateOnResourceNotAllowedWithApiVersion
Message Resource /subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/my-resource-group/providers/Microsoft.Network/virtualNetworkGateways/my-virtual-network-gateway
cannot be updated using API version 2016-09-01 since it uses the
property VpnClientConfiguration AAD authentication parameters which
has been set using a higher API version 2019-04-01. Please use api
version greater than or equal to 2019-04-01 to update the resource.
And:
Operation name Generate VpnClient package for virtualNetworkGateway
Error code VpnClientCMakGenerationNotSupportedForVpnClientProtocol
Message Legacy Cmak generation is not supported for gateway id
/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/my-resource-group/providers/Microsoft.Network/virtualNetworkGateways/my-virtual-network-gateway
when vpn client protocol OpenVPN is configured. Please use vpn profile
package option instead.
Created a new Function App located in the same subscription and region as the Virtual network that I wanted to use.
From here I could use Add VNet Integration and select which subnet I wanted to use. When doing this everything worked.
I wrote a Windows Service to run on Win10, and it worked perfectly fine until I decided to change it a bit. I rewrote some logic, tested it in both Debug and Release configurations, and everything was fine. Then I uninstalled the current version of the service using installutil.exe /u %servicename.exe% and reinstalled it again using installutil.exe %servicename.exe%.
For some reason, this new version cannot start, and it crashes with Error 1064. This is the full error text:
Windows could not start %servicename% service on Local Computer. Error 1064: An exception occurred in the service when handling the control request.
The last time I installed this service, I ran into some difficulties, but quickly fixed them by changing the Log On properties. This time, it is not working. Please help with this issue.
Thanks.
Update 1
Here are my Main() and OnStart() service methods:
Main()
static void Main()
{
#if DEBUG
var service = new SalesforceToJiraService();
service.OnDebug();
Thread.Sleep(Timeout.Infinite);
#else
ServiceBase[] ServicesToRun;
ServicesToRun = new ServiceBase[]
{
new SalesforceToJiraService()
};
ServiceBase.Run(ServicesToRun);
#endif
}
OnStart()
protected override void OnStart(string[] args)
{
this.ConfigureServices();
this.timer.Start();
this.logger.Information("SalesforceToJira service started.");
}
Update 2
More code:
ConfigureServices()
protected void ConfigureServices()
{
this.configuration = ConfigurationHelper.LoadConfiguration(ConfigurationPath);
this.logger = ConfigurationHelper.ConfigureLogger(this.configuration.Logs.LogsPath);
this.timer = ConfigurationHelper.ConfigureTimer(this.configuration.ProcessInterval.TotalMilliseconds,
(sender, eventArgs) => this.ProcessCasesAsync(sender, eventArgs).GetAwaiter().GetResult());
this.salesforceClient = new SalesforceCliClient(this.configuration.Salesforce.CliPath);
this.jiraClient = Jira.CreateRestClient(
this.configuration.Jira.Url,
this.configuration.Jira.Username,
this.configuration.Jira.Password);
}
I'm using Newtonsoft.JSON for deserializing a JSON configuration file, Serilog for logging, System.Timers.Timer for periodic events, AtlassianSDK for the Jira API and some wrappers over Salesforce CLI for Salesforce.
Thanks to #Siderite Zackwehdex's comment, I was able to find the full stack trace of the underlying exception in EventViewer, under:
Windows Logs\Application
In my case, my service is named "HttpDispatcher", which appears in the "Source" column in the top pane.
I could see immediately it was due to a dependency issue where my .NET 4.7.2 project was not pulling across my .NET Standard references. (That ol' chestnut).
I faced the same issue. The reason was I forgot to set the Database connection properly in configurations.
I had this exact same error 1064 starting my service. For me the user I had the service registered as was not a valid user in the database. Once added, it worked great.
I also had the same error in my Windows Service.
The reason was it can't read a configuration parameter, so it crash.
Adding some validation (bugfixing), the Windows Services can start it correctly.
In my case the error was due to issues with Event log name
It got fixed after I went to RegEdit and deleted old service name from HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services
I have also faced this issue. In my case it is due to connection fail with the data base. I think it is due to code throw the exception.
My error :
Windows could not start the service1 service on local computer.
Error 1064: An exception occured in the service when handling the control request
I corrected my issue by updating the third party DLL.
I faced the same issue, here is how I resolved it after troubleshooting.
If you are running service on the Server with multiple users, make
sure to run the service as admin user. Click on the service
properties and then on Log on tab click on this account and provide
the admin user name and password.
And If your service is accessing some shared drive, then make sure
you have a general user on all servers for accessing the shared
drives and add the user as local admin as well.
For me it happened when I tried to restart a process. Turned out the process was hanging in 'Stopping' so I had to kill it manually via command line and the PID.
I've been working to try and convert Microsoft's EWS Streaming Notification Example to a service
( MS source http://www.microsoft.com/en-us/download/details.aspx?id=27154).
I tested it as a console app. I then used a generic service template and got it to the point it would compile, install, and start. It stops after about 10 seconds with the ubiquitous "the service on local computer started and then stopped."
So I went back in and upgraded to C# 2013 express and used NLog to put a bunch of log trace commands to so I could see where it was when it exited.
The last place I can find it is in the example code, SynchronizationChanges function,
public static void SynchronizeChanges(FolderId folderId)
{
logger.Trace("Entering SynchronizeChanges");
bool moreChangesAvailable;
do
{
logger.Trace("Synchronizing changes...");
//Console.WriteLine("Synchronizing changes...");
// Get all changes since the last call. The synchronization cookie is stored in the
// _SynchronizationState field.
// Only the the ids are requested. Additional properties should be fetched via GetItem
//calls.
logger.Trace("Getting changes into var changes.");
var changes = _ExchangeService.SyncFolderItems(folderId, PropertySet.IdOnly, null, 512,
SyncFolderItemsScope.NormalItems,
_SynchronizationState);
// Update the synchronization cookie
logger.Trace("Updating _SynchronizationState");
the log file shows the trace message ""Getting changes into var changes." but not the "Updating _SynchronizationState" message.
so it never gets past var changes = _ExchangeService.SyncFolderItems
I cannot for the life figure out why its just exiting. There are many examples of EWS streaming notifications. I have 3 that compile and run just fine but nobody as far as I can tell has posted an example of it done as a service.
If you don't see the "Updating..." message it's likely the sync threw an exception. Wrap it in a try/catch.
OK, so now that I see the error, this looks like your garden-variety permissions problem. When you ran this as a console app, you likely presented the default credentials to Exchange, which were for your login ID. For a Windows service, if you're running the service with one of the built-in accounts (e.g. Local System), your default credentials will not have access to Exchange.
To rectify, either (1) run the service under the account you did the console app with, or (2) add those credentials to the Exchange Service object.
I created a Windows Service which Access File from Remote Machine. but It gives error in Log file that File Does Not Exist.When i deployed it then and then only it gives error otherwise when i am debugging from Visual Studio 2005 then it is working fine.
I tried to change Properties of Service from Log On tab. gives Logon as: then choose this Account and Gives Name of Remote Machine and Password Still it is not working. Please Help me out.
Code:
if (File.Exists(FileName))
{
}
else
{
Log.append("File Not Exist Path=:" + FileName, 75);
}
Error:
File Not Exist Path=: \Computer-01\Trend Till_04Feb\Trend Till_04Feb\TREND\128.DBF
I assume you are using ServiceProcessInstaller and ServiceInstaller.
The most important property is Account within the ServiceProcessInstaller class. It specifies the Windows account under which the service runs (security context). The following options are available:
LocalService: Service presents the computer's credentials to remote servers.
LocalSystem: Service presents anonymous credentials to remote servers.
NetworkService: Service has limited local privileges and presents the computer's credentials to remote servers.
User: A local or network account is specified. You may specify the necessary username and password via properties, or you may type them during installation. The Service uses the security context of the specified user account.
Following three options are provided to specify how your service is started.
Manual :- The user starts the service.
Automatic :- The service starts automatically when the system starts.
Disabled :- The service is not available for use.
Go to Properties of ServiceInstaller object and set ServiceName and StartType to Automatic.
Go to Properties of ServiceProcessInstaller and set Account property to LocalService. This causes the service to run on local service account.
HTH
I'm playing around with WCF Data Services (ADO.NET Data Services). I have an entity framework model pointed at the AdventureWorks database.
When I debug my svc file from within Visual Studio, it works great. I can say /awservice.svc/Customers and get back the ATOM feed I expect.
If I publish the service (hosted in an ASP.NET web application) to IIS7, the same query string returns a 500 fault. The root svc page itself works as expected and successfully returns ATOM. The /Customers path fails.
Here is what my grants look like in the svc file:
public class AWService : DataService<AWEntities>
{
public static void InitializeService( DataServiceConfiguration config )
{
config.SetEntitySetAccessRule( "*", EntitySetRights.All );
config.SetServiceOperationAccessRule( "*", ServiceOperationRights.All );
config.DataServiceBehavior.MaxProtocolVersion = DataServiceProtocolVersion.V2;
}
}
Update: I enabled verbose errors and get the following in the XML message:
<innererror>
<message>The underlying provider failed on Open.</message>
<type>System.Data.EntityException</type>
<stacktrace>
at System.Data.EntityClient.EntityConnection.OpenStoreConnectionIf(
...
...
<internalexception>
<message>
Login failed for user 'IIS APPPOOL\DefaultAppPool'.
</message>
<type>System.Data.SqlClient.SqlException</type>
<stacktrace>
at System.Data.SqlClient.SqlInternalConnection.OnError(SqlException exception, ...
It looks to me like this is a SQL authentication error, IIS is running its appPool under a user that does not have access to your SQL server, when you ruin in Visual Studio (locally) it will be a different user. Check the user that the IIS on the server is using and make sure it has rights to do what you want in SQL.
Try to change the connection string attribute Integrated security to False
Quick solution with IIS Express
Create a firewall exception to allow HTTP requests through the firewall on the port that IIS Express is using.
Get the IP address of the development computer, if necessary, by running ipconfig.
Find the IIS Express configuration file, applicationhost.config, in the folder %USERPROFILE%\Documents\IISExpress\config. The USERPROFILE environment variable typically has a value of C:\Users\.
Open applicationhost.config with Notepad or another text editor and make the following changes.
Find the site element for the web service, WebServiceForTesting.
If you don’t see the site element for the web service, you have to deploy the service at least one time to create the element.
Within the bindings section of the site element, copy the binding element and paste a copy directly below the existing binding element to create a second binding.
In the new binding element, replace localhost with the computer’s IP address.
Save the changes.
Run Visual Studio as administrator and open the Visual Studio solution.
In the phone app project, remove the service reference to the service if you have previously added it.
Add a new service reference to the reconfigured web service. In the Add Service Reference dialog box, in the Address box, replace localhost with the IP address of your development computer. Click Go.
The second binding for the service in the WCF project is discovered and displayed. Click OK.
A new service reference that uses the IP address of the development computer is added to the Windows Phone project.