Hi, apparently even though we have a load of advisory hours etc the azure website won't let us create a technical ticket.
Out trouble is with our cloud services project (Subscription Id : cd33d216-583d-46d2-accf-1b1fb2a2d703, DeploymentId : 3978abe26c2249a6b6c66a836a7a9d7a). We have 4 instances, a web role, wcf role and two worker roles.
The wcf role needs to add service host and service endpoints at runtime. It's a callback service so we need to create a service endpoint per client due to the strict security binding and its not feasible to put this in a config file as there will too many.
On my local azure emulator it works fine, but when I deploy I get HttpListener Access Denied Error message. I've elevated the role in the config and done full publishes through VS2012 and the azure console.
I am launching the service hosts in global.asax (so my tracing works without any hassle) but it also didn't work in the webrole.cs, same error.
Is there any way I can check to see if the process is elevating correctly? I've tried all different namespaces / ports etc and it's always the same and I'm going mad. Any Ideas?
exception:
System.ServiceModel.AddressAccessDeniedException: HTTP could not register URL https://+:5000/Manufacturers/Reporting8535/. Your process does not have access rights to this namespace
System.Net.HttpListenerException: Access is denied at System.Net.HttpListener.AddAllPrefixes() at System.Net.HttpListener.Start() at System.ServiceModel.Channels.SharedHttpTransportManager.OnOpen() --- End of inner exception stack trace --- at System.ServiceModel.Channels.SharedHttpTransportManager.OnOpen() at …..
csdef:
<WebRole name="OutProject.Wcf" vmsize="ExtraSmall">
<Runtime executionContext="elevated" />
<Sites>
<Site name="Web">
<Bindings>
<Binding name="Endpoint1" endpointName="SslEndpoint" />
<Binding name="Endpoint1" endpointName="WorkerEndpoint" />
</Bindings>
</Site>
</Sites>
<Endpoints>
<InputEndpoint name="SslEndpoint" protocol="https" port="5000" certificate="MeliorEUSSL" />
<InternalEndpoint name="WorkerEndpoint" protocol="http" port="6000" />
</Endpoints>
<Imports>
<Import moduleName="RemoteAccess" />
<Import moduleName="Diagnostics" />
</Imports>
<LocalResources>
</LocalResources>
<Certificates>
<Certificate name="MeliorEUSSL" storeLocation="LocalMachine" storeName="My" />
</Certificates>
</WebRole>
Code for my ServiceHostWrapper :
public class HostService<TServiceInterface, TServiceImplementation>where TServiceImplementation : TServiceInterface
{
private Uri address;
private ContractDescription contract;
private ServiceHost host;
private bool isOpen;
private bool isFaulted;
private int endpointCount;
public HostService(Uri address, X509Certificate2 serviceCertificate)
{
this.isOpen = false;
this.isFaulted = false;
this.address = address;
this.contract = ContractDescription.GetContract(typeof(TServiceInterface));
this.host = new ServiceHost(typeof(TServiceImplementation), address);
this.host.Faulted += HostFaulted;
this.host.Credentials.ServiceCertificate.Certificate = serviceCertificate;
this.host.Description.Behaviors.Find<ServiceMetadataBehavior>().HttpGetEnabled = false;
this.host.Description.Behaviors.Find<ServiceMetadataBehavior>().HttpsGetEnabled = true;
this.host.Description.Behaviors.Find<ServiceMetadataBehavior>().HttpsGetUrl = address;
this.host.Description.Behaviors.Find<ServiceDebugBehavior>().IncludeExceptionDetailInFaults = true;
}
public void AddServiceEndpoint(string clientId, X509Certificate2 clientCertificate)
{
try
{
this.host.AddServiceEndpoint(new ServiceEndpoint(
this.contract,
new CustomHubBinding(),
new EndpointAddress(new Uri(this.address + clientId), EndpointIdentity.CreateX509CertificateIdentity(clientCertificate)))
);
this.endpointCount++;
Trace.TraceInformation("HostService.AddServiceEndpoint: {0}: endpoint added for client {1}", contract.Name, clientId);
}
catch(Exception ex)
{
Trace.TraceError("HostService.AddServiceEndpoint: {0}: endpoint failed for client {1} : {2}", contract.Name, clientId, ex.ToString());
}
}
public void Open()
{
if (this.isOpen || this.isFaulted) return;
if(endpointCount > 0)
{
try
{
this.host.Open();
Trace.TraceInformation("HostService.Open: {0}: service opened successfully", this.contract.Name);
}
catch(Exception ex)
{
Trace.TraceError("HostService.Open: {0}: service failed to open: {1}", this.contract.Name, ex.ToString());
}
}
}
private void HostFaulted(object sender, EventArgs args)
{
ServiceHost host = (ServiceHost)sender;
try
{
host.Close();
}
catch { host.Abort(); }
Trace.TraceError("HostService.HostFaulted: {0}: service faulted", this.contract.Name);
this.isFaulted = true;
this.host = null;
}
}