1

I have a library project that includes a standard web service base class. I then inherit that base class for the specific websites that implement the web service.

Here is a simplified example:

[WebService(
     Namespace = "http://CanI.InheritThis.com/",
     Name = "WebServiceBaseClass",
     Description = "This Webservice is overloaded on specific websites")]
public abstract class CustomWebServiceBase : WebService
{
    //shared web service guts
}

public class MyService : CustomWebServiceBase
{
     //overloaded items
}

When I open up myservice.asmx it still says I'm using the default namespace (http://tempuri.org). How do I get the webservice to show the inherited namespace(http://CanI.InheritThis.com/)?

Update: I attempted to create a custom attribute that inherits from the WebServiceAttribute class but found that WebServiceAttribute is sealed.

Is there a way to add Inherited = true to WebServiceAttribute?

Update 2: Even more confusing I followed J0e3gan's advice and created the following in linqpad (with the System.Web.Services.dll added and namespace added.

void Main()
{
    Console.WriteLine(typeof(MyService).GetCustomAttributes().First());
}
[WebService(
     Namespace = "http://CanI.InheritThis.com/",
     Name = "WebServiceBaseClass",
     Description = "This Webservice is overloaded on specific websites")]
public abstract class CustomWebServiceBase : WebService
{
    //shared web service guts
}

public class MyService : CustomWebServiceBase
{
     //overloaded items
}

Which says it's getting the correct attribute, however the asmx page still claims to be using the default namespace.

Update 3: restarted from scratch, checked into bitbucket, same issue Update 4: As @J0e3gan pointed out, the bitbucket project was missing the class library, I've fixed that.

SumGuy
  • 602
  • 7
  • 18

2 Answers2

1

Initial Answer

WebServiceAttribute already supports its inheritance by subclasses of classes to which it is applied.

Maybe you just need to rebuild your library and service projects? A related SO question outlines some other possibilities that may explain why browsing to your service still shows the default namespace http://tempuri.org/.

See the following LINQPad 4 program (with System.Web.Services.dll referenced and the System.Web.Services namespace imported) for an example of WebServiceAttribute applied to a base class with subclasses inheriting and overriding the attribute:

void Main()
{
    Console.WriteLine(typeof(CustomWebServiceBase).GetCustomAttributes().First());
    Console.WriteLine(typeof(SomeSiteService).GetCustomAttributes().First());
    Console.WriteLine(typeof(AnotherSiteService).GetCustomAttributes().First());
}

[WebService(
     Namespace = "http://CanI.InheritThis.com/",
     Name = "WebServiceBaseClass",
     Description = "This Webservice is overloaded on specific websites")]
public class CustomWebServiceBase : WebService
{
}

public class SomeSiteService : CustomWebServiceBase
{
}

[WebService(
     Namespace = "http://YesU.Can.AndOverride.it/",
     Name = "WebServiceDerivedClass",
     Description = "This Webservice is for a specific website")]
public class AnotherSiteService : CustomWebServiceBase
{
}

It yields the following output:

WebServiceAttribute Inheritance Results

Follow-Up to Bitbucket Solution

Looking at the Bitbucket solution that displays the issue, I was able to reproduce it by building and running it as-is:

Issue Rero

To fix the issue, I simply decorated MyService with WebServiceAttribute (in the MyServiceWebApp project's MyService.asmx.cs) as follows:

// NOTE: necessary using directive - requiring a corresponding reference to
// System.Web.Services.dll
using System.Web.Services;

namespace MyServiceWebApp
{
    // NOTE: the key - the overriding decoration of the derived web-service
    // class with WebServiceAttribute
    [WebService(
     Namespace = "http://YesU.Can.AndOverride.it/",
     Name = "WebServiceDerivedClass",
     Description = "This Webservice is for a specific website")]
    public class MyService : WebServiceClassLibrary.CustomWebServiceBase
    {

    }
}

Here are screenshots of the fix's results:

Issue Fix

Issue Fix - WSDL

Issue Fix - HelloWorld Operation

You can clearly see that MyService.asmx no longer reports the default namespace http://tempuri.org/, and its WSDL reveals that its default namespace is now http://YesU.Can.AndOverride.it/ as expected.

Community
  • 1
  • 1
J0e3gan
  • 8,740
  • 10
  • 53
  • 80
  • even though `Console.WriteLine(typeof(CustomWebServiceBase).GetCustomAttributes().First());` yields the proper attribute, I'm still getting `This web service is using http://tempuri.org/ as its default namespace.` Which is the heart of my question. – SumGuy Aug 02 '14 at 03:16
  • @SumGuy: Your question is stated 3 ways: *Can I inherit the attributes from the base class in the library project?* *Is it possible to inherit the namespace, name, and description from the base class?* *Is there a way to add `Inherited = true` to `WebServiceAttribute`?* My answers are "Yes; yes; and not necessary" - but also that you probably have a simple problem underlying the strangeness you still observe (e.g. needing to rebuild). A [related SO question](http://stackoverflow.com/q/2898466/1810429) may help with the strangeness you're still trying to shake. – J0e3gan Aug 02 '14 at 03:35
  • 1
    I restated the question to just ask how to get the inherited namespace to show up on the asmx. I checked the items in the related SO question. I only have a single class in each file. I verified the markup matches the code-behind on the asmx. I'm at a loss. – SumGuy Aug 02 '14 at 03:54
  • @SumGuy: Understood. If it's IIS-hosted, maybe the virtual directory is not mapped to the physical directory that you think it is? Maybe you changed configurations in VS - e.g. from Release to Debug - and the output from the last configuration is being invoked when you browse to the service? – J0e3gan Aug 02 '14 at 04:01
  • 1
    I rebuilt a minimal example from scratch to flush out your suggestions ran in the same problem, so I put the whole new minimal project into a public [bitbucket](https://bitbucket.org/SumGuy/myservicewebapp) Thanks for all your help! – SumGuy Aug 02 '14 at 05:08
  • @SumGuy: I cloned your `MyWebServiceApp` Hg repo (to `C:\Hg\mywebserviceapp`) and tried loading `MyWebServiceApp.sln` but got the following error: `C:\Hg\ClassLibrary1\WebServiceClassLibrary.csproj : error : The project file could not be loaded. Could not find a part of the path 'C:\Hg\ClassLibrary1\WebServiceClassLibrary.csproj'. C:\Hg\ClassLibrary1\WebServiceClassLibrary.csproj` – J0e3gan Aug 03 '14 at 05:28
  • 1
    Thanks for letting me know, I pulled the project up and the whole directory was missing. I rearranged and re-added the project. Thanks for all the time you've put in on this!!! – SumGuy Aug 04 '14 at 00:33
  • @SumGuy: No problem. Thanks for following with an update in Bitbucket, which I was able to build: I will follow with an edit since I was able to reproduce the problem you described - and fix it. – J0e3gan Aug 04 '14 at 20:07
  • I marked this as the answer, it seems that it is not possible to inherit the web attribute, and therefore must be overridden, as you've shown in you solution to the bitbucket. Thanks for your help! – SumGuy Aug 06 '14 at 16:22
0

The custom attribute you are applying would need to be configured like this[AttributeUsage(System.AttributeTargets.Class, Inherited = true)]

see previous thread

How does inheritance work for attribtues?

Community
  • 1
  • 1
gudatcomputers
  • 2,822
  • 2
  • 20
  • 27
  • 1
    I'm not using a custom attribute, I'm using the web service attribute (this one http://msdn.microsoft.com/en-us/library/czf3k293(v=vs.90).aspx ) I'll try making a custom attribute and inherit from the web service attribute – SumGuy Aug 02 '14 at 02:16
  • As it turns out System.Web.Services.WebServiceAttribute is a sealed class and I cannot inherit from it – SumGuy Aug 02 '14 at 02:20