472,807 Members | 1,828 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 472,807 software developers and data experts.

public function from class in other namespace inaccessible

I have a little problem with a webservice. I reproduced the problem in the
following simplified example.

I just create a new C# ASP.NET webservice and a c# console application.
I added a new class test to the namespace of the webservice which I try to
access from the console
application.
//Service1.asmx.cs
using System;
using System.Collections;
using System.ComponentModel;
using System.Data;
using System.Diagnostics;
using System.Web;
using System.Web.Services;

namespace WebService2
{

public class Service1 : System.Web.Services.WebService
{
public Service1()
{
InitializeComponent();
}

#region Component Designer generated code

private IContainer components = null;

private void InitializeComponent()
{
}

protected override void Dispose( bool disposing )
{
if(disposing && components != null)
{
components.Dispose();
}
base.Dispose(disposing);
}

#endregion

[WebMethod]
public string HelloWorld(test t)
{
return "Hello World";
}
}
public class test
{
public test(){}
public int someInt;
private int anotherInt;
public int TheInt
{
get
{
return anotherInt;
}
set
{
anotherInt=value;
}
}
public int returnInt()
{
return 4;
}

}
}


//Class1.cs
using System;
// I added Webservice2 as web reference ws1
using ConsoleApplication1.ws1;

namespace ConsoleApplication1
{

class Class1
{
static void Main(string[] args)
{
test t=new test();
int a=t.someInt;
int b=t.returnInt(); //this produces an error CS0117
Console.WriteLine("Returned value="+b.ToString());
}
}
}

2 things are bugging me:

First: it does not compile! It gives me the following error:

Class1.cs(21): error CS0117: 'ConsoleApplication1.ws1.test' does not contain
a definition for 'returnInt'

The console application does not seem to have access to the public functions
of the class test, but it does have
access to the public properties.

Is this how it is supposed to be or am I doing something wrong?
Does anyone have a solution?

Pleas don't just point me to http://support.microsoft.com/?id=821175 since I
already saw this, I
only don't see how this fits in here.

Second: why can the console application only see the class test when I use
it as a parameter
in a [webmethod]? If I remove
"test t"
from
public string HelloWorld(test t),
I get:
Class1.cs(20): The type or namespace name 'test' could not be found (are you
missing a using directive or an assembly reference?)

Nov 17 '05 #1
4 2343
Hello Peter,

Visual studio has written some code for you, and you are getting confused by
it.

First off, if you want to use a class to pass data to a web service, you
need to put that class into a seperate assembly and reference the assembly
from both the web service code and the client code. Do not assume that you
can define it in one and use it in the other.

A web reference is not the same as a referenced assembly. A web reference
will look at the WSDL file that was generated when the web service was
compiled. It will then WRITE CODE for you in your project. If you want to
see that code, go to the solution explorer, select the project and take a
look at the two unlabeled icons just above the treeview itself. Hover over
them to see the tooltip. One will say "Show all" or something like that.
Click it. A little "+" sign will appear next to the web reference. Expand
it and you will see the code that the web reference wrote for you.

In that code, you will see that any class that is used in a parameter, and
therefore defined in the WSDL, is described, again, in the generated code.
Note that the properties will be reproduced, but not the methods. This is
why you cannot count on the code that is generated by the web service if you
want to use an actual class to pass data.

First bit of advice: when passing data through a web service, use a
serializable object that holds data but doesn't have many methods (except
those used to access the data).

Second bit of advice: define your class in a seperate assembly and reference
it from both places.

Third bit of advice, if you want the deserializer to put data back into the
correct class, you need to study up on the correct attributes to associate
with the class itself that you use to pass data. This will allow the
serializer and deserializer to use your class without having to recode it
from the description in the WSDL file.

I hope this helps you to understand what you are seeing.

--- Nick

--
--- Nick Malik [Microsoft]
MCSD, CFPS, Certified Scrummaster
http://blogs.msdn.com/nickmalik

Disclaimer: Opinions expressed in this forum are my own, and not
representative of my employer.
I do not answer questions on behalf of my employer. I'm just a
programmer helping programmers.
--
"Peter Speybrouck" <Peter Sp********@discussions.microsoft.com> wrote in
message news:A3**********************************@microsof t.com...
I have a little problem with a webservice. I reproduced the problem in the
following simplified example.

I just create a new C# ASP.NET webservice and a c# console application.
I added a new class test to the namespace of the webservice which I try to
access from the console
application.
//Service1.asmx.cs
using System;
using System.Collections;
using System.ComponentModel;
using System.Data;
using System.Diagnostics;
using System.Web;
using System.Web.Services;

namespace WebService2
{

public class Service1 : System.Web.Services.WebService
{
public Service1()
{
InitializeComponent();
}

#region Component Designer generated code

private IContainer components = null;

private void InitializeComponent()
{
}

protected override void Dispose( bool disposing )
{
if(disposing && components != null)
{
components.Dispose();
}
base.Dispose(disposing);
}

#endregion

[WebMethod]
public string HelloWorld(test t)
{
return "Hello World";
}
}
public class test
{
public test(){}
public int someInt;
private int anotherInt;
public int TheInt
{
get
{
return anotherInt;
}
set
{
anotherInt=value;
}
}
public int returnInt()
{
return 4;
}

}
}


//Class1.cs
using System;
// I added Webservice2 as web reference ws1
using ConsoleApplication1.ws1;

namespace ConsoleApplication1
{

class Class1
{
static void Main(string[] args)
{
test t=new test();
int a=t.someInt;
int b=t.returnInt(); //this produces an error CS0117
Console.WriteLine("Returned value="+b.ToString());
}
}
}

2 things are bugging me:

First: it does not compile! It gives me the following error:

Class1.cs(21): error CS0117: 'ConsoleApplication1.ws1.test' does not
contain
a definition for 'returnInt'

The console application does not seem to have access to the public
functions
of the class test, but it does have
access to the public properties.

Is this how it is supposed to be or am I doing something wrong?
Does anyone have a solution?

Pleas don't just point me to http://support.microsoft.com/?id=821175 since
I
already saw this, I
only don't see how this fits in here.

Second: why can the console application only see the class test when I use
it as a parameter
in a [webmethod]? If I remove
"test t"
from
public string HelloWorld(test t),
I get:
Class1.cs(20): The type or namespace name 'test' could not be found (are
you
missing a using directive or an assembly reference?)

Nov 17 '05 #2
Hello,

Thanks for the thorough reply, I understand the problem now.
To solve it, I created a new class library dataLib containing the class test
from above.
I added the dll as a new reference to both projects and both have indeed
access to all properties and method.

But this brings me to a new problem.
If I define the following webmethod:
[WebMethod]
public string HelloWorld(dataLib.test b)
{
return "Hello World";
}

and try to call this webmethod like this:
dataLib.test b=new dataLib.test();
int a = b.returnInt();
Service1 myService=new Service1();
myService.HelloWorld(b);
This fails because HelloWorld is expecting an argument of type ws1.test
instead of dataLib.test.
I can solve this by creating a new object of type ws1.test and copying all
properties seperately from the object b.

Is there an easier way to pass the correct object to the webservice or to
copy all properties at once?

I suppose this is where you meant to use serializable classes, but the only
thing I can think of is to create a serializable class test and use this
class.
Then to pass the object to the webservice: serialize the object to a
SerializationInfo object and deserialize the object with the ws1.test
deserializer.

Is my thinking correct? If so, can someone give me a small example of how
exactly I can serialize and deserialize without writing it to a file?
Nov 17 '05 #3
There are a couple of solutions to this problem. I haven't looked into the
attributes well enough, but I'm willing to bet that there is an attribute
for this that will keep the web service proxy from regenerating the class in
the proxy code.

However, the easier way is to follow this advice that I clipped from a blog
thread:

<clip>
I am in process of solving the same problem. At present, my solution is to
manually modify the VS.NET generated client-side proxy code (Reference.cs).
I have the same assembly on both client and webservice. This assembly has a
class named DictionaryPair, which is returned by a web method. I added a
reference to my assembly to the generated proxy code, left the
[System.Xml.Serialization.XmlIncludeAttribute(typeo f(DictionaryPair))] as
is, but removed the DictionaryPair class definition from the proxy. So far
everything has compiled and my initial tests indicate things are working.

Of course the down side to this is that if (when) I regenerate the proxy due
to additions to the web service (I've really just started coding it), I will
have to manually reapply my changes. Perhaps I'll try to write a VS.NET
macro for this...
</clip>

I hope this helps

--
--- Nick Malik [Microsoft]
MCSD, CFPS, Certified Scrummaster
http://blogs.msdn.com/nickmalik

Disclaimer: Opinions expressed in this forum are my own, and not
representative of my employer.
I do not answer questions on behalf of my employer. I'm just a
programmer helping programmers.
--
"Peter Speybrouck" <Pe*************@discussions.microsoft.com> wrote in
message news:D0**********************************@microsof t.com...
Hello,

Thanks for the thorough reply, I understand the problem now.
To solve it, I created a new class library dataLib containing the class
test
from above.
I added the dll as a new reference to both projects and both have indeed
access to all properties and method.

But this brings me to a new problem.
If I define the following webmethod:
[WebMethod]
public string HelloWorld(dataLib.test b)
{
return "Hello World";
}

and try to call this webmethod like this:
dataLib.test b=new dataLib.test();
int a = b.returnInt();
Service1 myService=new Service1();
myService.HelloWorld(b);
This fails because HelloWorld is expecting an argument of type ws1.test
instead of dataLib.test.
I can solve this by creating a new object of type ws1.test and copying all
properties seperately from the object b.

Is there an easier way to pass the correct object to the webservice or to
copy all properties at once?

I suppose this is where you meant to use serializable classes, but the
only
thing I can think of is to create a serializable class test and use this
class.
Then to pass the object to the webservice: serialize the object to a
SerializationInfo object and deserialize the object with the ws1.test
deserializer.

Is my thinking correct? If so, can someone give me a small example of how
exactly I can serialize and deserialize without writing it to a file?

Nov 17 '05 #4
Hello,

I found the blog you quoted, and it seems like I am not the only one with
this problem. I looked into your suggestion and actually got it to work.

I removed the entire occurence of the class in the reference.cs of the
client starting from
[System.Xml.Serialization.XmlTypeAttribute(Namespac e="bla")]
public class test {
//... class properties
}
and modified the type of some arguments of methods in this file to make sure
they could find the wanted type and it works now.

Would there be a way to prevent the service from generating the class? Now I
have to change it manually everytime I update the webservice.
Nov 17 '05 #5

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

3
by: Robert | last post by:
Python doesn't know the class of a method when container not direct class attribute: >>> class X: .... def f():pass .... g=f .... l= .... >>> X.g <unbound method X.f>
1
by: Christopher W. Douglas | last post by:
I'm working in VB.Net, using Visual Studio 2003. I have a project, let's call it Foo, that contains common methods, forms, and objects I use in other projects. It compiles as Foo.dll, which I...
19
by: qazmlp | last post by:
class base { // other members public: virtual ~base() { } virtual void virtualMethod1()=0 ; virtual void virtualMethod2()=0 ; virtual void virtualMethod3()=0 ;
5
by: zippy747 | last post by:
I have a high level class X. I have a lower level utility class Y. I want only class X to have access to method y in class Y. i.e. I want class Z to have access to most methods in Y but not...
3
by: Mat | last post by:
Hi, I am trying to create a set of global functions that are available to any page. However I am not really getting anywhere, even after looking at several examples. This is the code I have...
7
by: tron.thomas | last post by:
Please consider the following code: class Abstract { public: virtual ~Abstract() {} virtual void Method() = 0; }; class Concrete : public virtual Abstract
2
by: jason | last post by:
Please pardon my completely lack of understanding on the topic. I have a website I developed with another developer. We are both far from experts in VB.NET and OOP. We developed the site WITHOUT...
5
by: Ian Bicking | last post by:
I got a puzzler for y'all. I want to allow the editing of functions in-place. I won't go into the reason (it's for HTConsole -- http://blog.ianbicking.org/introducing-htconsole.html), except that...
9
by: Stefan Weber | last post by:
Hi, I have the following header file (named test.h): class Foo { public: Foo(void) {} virtual ~Foo(void) {} };
2
isladogs
by: isladogs | last post by:
The next Access Europe meeting will be on Wednesday 2 August 2023 starting at 18:00 UK time (6PM UTC+1) and finishing at about 19:15 (7.15PM) The start time is equivalent to 19:00 (7PM) in Central...
0
by: erikbower65 | last post by:
Using CodiumAI's pr-agent is simple and powerful. Follow these steps: 1. Install CodiumAI CLI: Ensure Node.js is installed, then run 'npm install -g codiumai' in the terminal. 2. Connect to...
0
by: erikbower65 | last post by:
Here's a concise step-by-step guide for manually installing IntelliJ IDEA: 1. Download: Visit the official JetBrains website and download the IntelliJ IDEA Community or Ultimate edition based on...
2
isladogs
by: isladogs | last post by:
The next Access Europe meeting will be on Wednesday 6 Sept 2023 starting at 18:00 UK time (6PM UTC+1) and finishing at about 19:15 (7.15PM) The start time is equivalent to 19:00 (7PM) in Central...
0
by: Taofi | last post by:
I try to insert a new record but the error message says the number of query names and destination fields are not the same This are my field names ID, Budgeted, Actual, Status and Differences ...
14
DJRhino1175
by: DJRhino1175 | last post by:
When I run this code I get an error, its Run-time error# 424 Object required...This is my first attempt at doing something like this. I test the entire code and it worked until I added this - If...
0
by: Rina0 | last post by:
I am looking for a Python code to find the longest common subsequence of two strings. I found this blog post that describes the length of longest common subsequence problem and provides a solution in...
0
by: lllomh | last post by:
How does React native implement an English player?
2
by: DJRhino | last post by:
Was curious if anyone else was having this same issue or not.... I was just Up/Down graded to windows 11 and now my access combo boxes are not acting right. With win 10 I could start typing...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.