Unit test code can not access gdb

3051
9
03-18-2011 09:21 AM
by Anonymous User
Not applicable
Original User: Julie6

How can I access a gdb in Unit Test method so I can get some testing feature classes to test spatial operations in my ArcObject extension project. I'm using VS 2010 with ArcGIS 10 on Window 7 machine to create a Desktop component.

Right now I'm getting COMException from HRESULT: 0x80040258 when I call "workspaceFactory.OpenFromFile(path, 0)".


Thanks!


Julie
0 Kudos
9 Replies
by Anonymous User
Not applicable
Original User: agray1

I use unit tests with VS2008.  The trick is to check out a license.  If you are using ArcGIS 10, you need to bind with the product too.  I do it in the class initialize.  I used NUnit in the past, it has similar tags to run things before and after your tests.

  Private Shared m_aoInit As IAoInitialize
  '
  ' You must initialize an ArcGIS License to test ArcObjects code
  '
  'Use ClassInitialize to run code before running the first test in the class
  <ClassInitialize()> Public Shared Sub MyClassInitialize(ByVal testContext As TestContext)
    ESRI.ArcGIS.RuntimeManager.Bind(ESRI.ArcGIS.ProductCode.Desktop)
    m_aoInit = New AoInitialize
    m_aoInit.Initialize(esriLicenseProductCode.esriLicenseProductCodeArcInfo)
  End Sub

  'Use ClassCleanup to run code after all tests in a class have run
  <ClassCleanup()> Public Shared Sub MyClassCleanup()
    m_aoInit.Shutdown()
  End Sub
0 Kudos
VivekPrasad
Occasional Contributor
How can I access a gdb in Unit Test method so I can get some testing feature classes to test spatial operations in my ArcObject extension project. I'm using VS 2010 with ArcGIS 10 on Window 7 machine to create a Desktop component.

Right now I'm getting COMException from HRESULT: 0x80040258 when I call "workspaceFactory.OpenFromFile(path, 0)".


Thanks!


Julie


Hi,

Is your machine 64 Bit or 32 Bit?
0 Kudos
by Anonymous User
Not applicable
Original User: Julie6

Alex,

You are right. The license make me to be able to get the feature classes. But this line gave an error:

public static void ClassCleanup() {
            fileGDB = null;
            m_aoInit.Shutdown();    //ERROR: COM object that has been separated from its underlying RCW cannot be used.
        }

my m_aoInit was defined in ClassInitialize, just like yours.


Vara,

The Window 7 machine is 64 bit.



Thanks for your help!


Julie
0 Kudos
VivekPrasad
Occasional Contributor
Alex,

You are right. The license make me to be able to get the feature classes. But this line gave an error:

public static void ClassCleanup() {
            fileGDB = null;
            m_aoInit.Shutdown();    //ERROR: COM object that has been separated from its underlying RCW cannot be used.
        }

my m_aoInit was defined in ClassInitialize, just like yours.


Vara,

The Window 7 machine is 64 bit.



Thanks for your help!


Julie


Hi,

Did you change the Platform property value from "Project Properties > Compile Tab > Platfrom" to X86??
0 Kudos
by Anonymous User
Not applicable
Original User: agray1

Vara is right, you have to change the project properties to run in 32 bit.  That for the DLL your are testing as well as the unit test project too.   I have not done this in VS2010 so I am not 100% sure how it will work.  The error you are getting happens when you explicitly release an com objects or when the reference got broken (cross thread for instance.)  I am not sure what is happening for you.
0 Kudos
LukeBadgerow
New Contributor
so any advice on this error:

   Failed InitGeoDataServerFromWorkspaceTest TestPostReconcile Test method TestPostReconcile.ArcSDEUtilitiesTest.InitGeoDataServerFromWorkspaceTest threw exception:  System.InvalidCastException: No such interface supported (Exception from HRESULT: 0x80004002 (E_NOINTERFACE)).

The code:

        private IGeoDataServer InitGeoDataServerFromWorkspace(IWorkspace geodatabase)
        {
            // Create the GeoDataServer and cast to the the IGeoDataServerInit interface.
            IGeoDataServer geoDataServer = new GeoDataServerClass();
            IGeoDataServerInit geoDataServerInit = (IGeoDataServerInit)geoDataServer;

            // Initialize the GeoDataServer and return it.
            geoDataServerInit.InitWithWorkspace(geodatabase);
            return geoDataServer;
        }


The test:
        [TestMethod()]
        //[DeploymentItem("Batch Reconcile and Post.exe")]
        public void InitGeoDataServerFromWorkspaceTest()
        {
            ArcSDEUtilities_Accessor target = new ArcSDEUtilities_Accessor();
            IWorkspace geodatabase = (IWorkspace)iworkspacemock.MockInstance;
            IGeoDataServer expected = (IGeoDataServer)geodataservermock.MockInstance;
            IGeoDataServer actual;
            actual = target.InitGeoDataServerFromWorkspace(geodatabase);
            Assert.AreEqual(expected, actual);
        }


the initialize logic helped clear my first hurdle with this.  thanks much for that.  I'm just getting tripped up on how this all plays out, I'm brand new to unit testing (been trying to implement for about a year now, just getting to it).
0 Kudos
by Anonymous User
Not applicable
Original User: agray1

It is hard to tell exactly but my guess is the IGeoDataServerInit.InitWithWorkspace is trying to cast a the workspace or an object that is a property of the workspace to an interface that the mock class does not implement.  The workspace class itself implements 30 interfaces.  Then there are the interfaces implemented the properties classes...   Judging from what a geodataserver does (replication, table search, version, import etc.) I would suspect that not all workspaces are suitable for a geodataserver (raster workspace, file workspace, etc.)
0 Kudos
LukeBadgerow
New Contributor
awesome!  Thanks for the response.  That'll teach me to code without regard for maintaining it down the road.
0 Kudos
by Anonymous User
Not applicable
Original User: agray1

yes, that is quite the challenge with ArcObjects.  Dave Bouwman had done some interesting work on the subject, I haven't checked in in a while... 
In my experience, the problem is implementing complete enough mock objects becomes just so much work that it is hardly worth it.  You don't really know how the esri code interacts with an object when you pass it in.  In some cases, I think they don't use the published interfaces and use a deeper level API for performance reasons, so fat chance in making a mock object for that.  That said if you maintain a set of test databases you can open them and use them in the unit tests.  It is a lot of overhead and maintenance but it can still be done.
0 Kudos