2

I have an ASP.NET MVC application which is trying to open below OLE DB connection:

string conString = @"Provider=Advantage OLE DB Provider;Data Source=" + dbfFilePath + ";Extended Properties=dBASE IV;";

using (dBaseConnection = new OleDbConnection(conString))
{
   dBaseConnection.Open();
   // Some stuff
}

I have installed below package from here.

I am using this provider in order to access a dbf file (specified on the dbfFilePath variable) and then later add some information into it. When I perform the Open command on the above code snippet I get below exception message:

Error 6420: The 'Discovery' process for the Advantage Database Server failed. Unable to connect to the Advantage Database Server. axServerConnect AdsConnect.

Previously I was using VFPOLEDB.4 provider and it was working ok when reading and modifying the dbf file. The problem is that it is only available in 32-bit (there is no version in 64-bit) and now I need it to be in 64-bit so I decided to use Advantage OLE DB provider that is available in 64-bit and as far as I know it does the same as VFPOLEDB.

What am I doing wrong?

UPDATE 2020/11/16: If I add some parameters to connection string:

string conString = @"Provider=Advantage OLE DB Provider;Data Source=" + dbfFilePath + ";ServerType=ADS_LOCAL_SERVER;TableType=ADS_VFP;Extended Properties=dBASE IV;";

Then when opening connection I get below exception:

Error 7077: The Advantage Data Dictionary cannot be opened. axServerConnect AdsConnect

UPDATE 2020/11/20:

var dbfFilePath =@"C:\MyApp\Temp"; // using c:\MyApp\Temp\myTable.dbf does not work (below open command fails)

string conString = @"Provider=Advantage OLE DB Provider;Data Source=" + dbfFilePath + ";ServerType=ADS_LOCAL_SERVER; TableType=ADS_VFP;";

using (dBaseConnection = new OleDbConnection(conString))
{
   dBaseConnection.Open();
   OleDbCommand insertCommand = dBaseConnection.CreateCommand();
   insertCommand.CommandText = "INSERT INTO [myTable] VALUES (2,100)";
   insertCommand.ExecuteNonQuery();
}

Note: [myTable] has the same name that the dbf file within C:\MyApp\Temp.

Now open command works but when performing insertCommand.ExecuteNonQuery() it gets stuck (it does nothing).

UPDATE 2020/11/27:

Ok,I think I have detected what is happening. It works ok when using Advantage OLE DB provider in 32-bit, however, using Advantage OLE DB provider in 64-bit is not working. In both cases I use it on Windows Server 2012 R2 Standard 64-Bit and Advantage OLE DB provider is version 11.10.

I have checked this using LINQPad 5, and it works but when performing

insertCommand.ExecuteNonQuery()

... and before doing the insert to the dbf file below warning modal window appears waiting for you to click on 'Accept' button. Once you click on the button, insert is done in dbf file correctly.

enter image description here

So, I guess that when running my web application (ASP.NET MVC app) in production environment this warning modal windows does not appear but in fact, it is waiting for you to click on the button to proceed inserting data in the dbf file but as this warning window is not visible (it is not shown) I can click on that button and consequently ExecuteNonQuery never ends (it stalls) and it stays waiting for you to click that button indefinitely.

How can I solve this error? can I modify ads.ini in some way in order to avoid this waring message to appear so application can work?

Willy
  • 9,848
  • 22
  • 141
  • 284
  • I am encountering this same problem under a similar scenario. Unfortunately for my setup a restful API really is a terrible solution. My application is a c# desktop application that needs to upgrade to an x64 setup due to memory constraints from x86, and works with files in the dbf format. I also was using the VFPOLEDB driver for the x86 architecture, and I know that I have permissions to access the files, in fact the modal error window only pops up about 75% of the time, occasionally it works without error, and I always do still get the data back from the query with or without error. – Matt Steadman Jan 05 '22 at 19:34

1 Answers1

2

I see you removed the VFP tag which I think most relevant to this question :)

I again tested that with these codes as a sample and it worked without a glitch:

void Main()
{
    string dbfFilesPath = @"C:\PROGRAM FILES (X86)\MICROSOFT VISUAL FOXPRO 9\SAMPLES\Data";
    string conString = $@"Provider=Advantage OLE DB Provider;Data Source={dbfFilesPath};ServerType=ADS_LOCAL_SERVER;TableType=ADS_VFP;";
    DataTable t = new DataTable();
    using (OleDbConnection cn = new OleDbConnection(conString))
    using (OleDbCommand cmd = new OleDbCommand($@"insert into Customer 
        (cust_id, company, contact)
        values
        (?,?,?)", cn))
    {
        cmd.Parameters.Add("@cId", OleDbType.VarChar);
        cmd.Parameters.Add("@company", OleDbType.VarChar);
        cmd.Parameters.Add("@contact", OleDbType.VarChar);

        cn.Open();
        for (int i = 0; i < 10; i++)
        {
            cmd.Parameters["@cId"].Value = $"XYZ#{i}";
            cmd.Parameters["@company"].Value = $"Company XYZ#{i}";
            cmd.Parameters["@contact"].Value = $"Contact XYZ#{i}";
            cmd.ExecuteNonQuery();
        }

        t.Load(new OleDbCommand($"select * from Customer order by cust_id desc", cn).ExecuteReader());
        cn.Close();
    }
    t.Dump(); // tested in LinqPad AnyCPU version
}

Here is the partial result I got:

XYZ#9  Company XYZ#9                            Contact XYZ#9                                                                                                                                                                                                                           0.0000 
XYZ#8  Company XYZ#8                            Contact XYZ#8                                                                                                                                                                                                                           0.0000 
XYZ#7  Company XYZ#7                            Contact XYZ#7                                                                                                                                                                                                                           0.0000 
XYZ#6  Company XYZ#6                            Contact XYZ#6                                                                                                                                                                                                                           0.0000 
XYZ#5  Company XYZ#5                            Contact XYZ#5                                                                                                                                                                                                                           0.0000 
XYZ#4  Company XYZ#4                            Contact XYZ#4                                                                                                                                                                                                                           0.0000 
XYZ#3  Company XYZ#3                            Contact XYZ#3                                                                                                                                                                                                                           0.0000 
XYZ#2  Company XYZ#2                            Contact XYZ#2                                                                                                                                                                                                                           0.0000 
XYZ#1  Company XYZ#1                            Contact XYZ#1                                                                                                                                                                                                                           0.0000 
XYZ#0  Company XYZ#0                            Contact XYZ#0                                                                                                                                                                                                                           0.0000 
XXXXXX Linked Server Company                                                                                                                                                                                                                                                            0.0000 
WOLZA  Wolski  Zajazd                           Zbyszek Piestrzeniewicz        Owner                          ul. Filtrowa 68                                              Warszawa                        01-012     Poland          (26) 642-7012            (26) 642-7012            3694 
WINCA  Wenna Wines                              Vladimir Yakovski              Owner                                                                                                                                                                                                    0.0000 
WILMK  Wilman Kala                              Matti Karttunen                Owner/Marketing Assistant      Keskuskatu 45                                                Helsinki                        21240      Finland         90-224 8858              90-224 8858              4400 
WHITC  White Clover Markets                     Karl Jablonski                 Owner                          305 - 14th Ave. S., Suite 3B                                 Seattle         WA              98128      USA             (206) 555-4112           (206) 555-4115           38900 
WELLI  Wellington Importadora                   Paula Parente                  Sales Manager                  Rua do Mercado, 12                                           Resende         SP              08737-363  Brazil          (14) 555-8122                                     3600 
WARTH  Wartian Herkku                           Pirkko Koskitalo               Accounting Manager             Torikatu 38                                                  Oulu                            90110      Finland         981-443655               981-443655               24200 

As it is not working for you, I think it might have to do with:

  • Access rights. You say, you use with ASP.Net MVC, I wonder if the 'connecting account' has only read access? In IIS, basic settings as I remember there were a setting for connect as. You might at least set it to connect by an account that has full rights to that directory.
  • Sharing. The file might be in use shared elsewhere and for some reason your insert is waiting trying to get lock?
  • SET NULL ON ? Another slight possibility. You might need to execute this first, on the same connection. If there are fields that you are not supplying a value in insert but "not null" in table structure would otherwise cause it to fail.

You might start testing the same file from say within LinqPad running with administrator rights to eliminate the access rights stuff alltogether (if data directory is under program files or program files (x86), then it is a problem by itself.

I would expect an immediate error message, but who knows maybe driver is waiting for a timeout in case of write access failure?

Some ideas (the way I do it:) Instead of trying to use VFP data with 64 bits access, you might create a server that runs in 32 bits IIS Application pool (or use its own web serving) and handles the data access via REST API (or WCF). I use 32 bits ASP.Net MVC application(s) since years with success using VFOLEDB itself. If you think of REST API path, you might either use ASP.Net core (which is fast unlike the pre core) or use something else, say Go for building it. Go and Iris framework, for an example is an excellent fit to build a REST API server for your data over night (unlikely you would think Go, but if you do, remember to compile with x86 architecture).

Cetin Basoz
  • 22,495
  • 3
  • 31
  • 39
  • I have check my piece of code in LINQPad 5 and it is working ok. I have inserted the same values into the table and it works. However from my ASP.NET MVC app, if I try to insert exactly the same values for fields it does not work. The folder C:\MyApp\Temp has access right (full permissions for application pool identity). The fields that I am supplying all have values (Not nulls). When executing the executeNonQuery command it does the same, it gets stucks but no exception or error is thrown. It seems executeNonQuery never ends, it does not return the control. – Willy Nov 24 '20 at 00:47
  • @Ralph, I would think it is rights. Instead of checking just identity in pool, would you check and at least temporarily change the "connect as" in website settings (basic?). – Cetin Basoz Nov 24 '20 at 09:14
  • I cannot see any "connect as" in website. I am using IIS 8.5. What I see is a feature in website called "access physical path using credentials" and in there I indicate the same user as I indicate in the application pool identity. This user has full access rights (modify, read, write) to the folder where dbf file is. Also I have monitored this folder using process monitor and when accessing to this folder the result is 'SUCCESS'. In process monitor I don't observe any weird things. It is werid, it executes the insert statement and no errors appears but my web page stalls, it never finishes – Willy Nov 26 '20 at 09:24
  • Also I have attached remotely to the application from Visual Studio. I have set a breakpoint after the statement ExecuteNonQuery and I have noticed that this breakpoint is never reached. As said in previous comments it seems like it stalls while executing ExecuteNonQuery and it never ends. – Willy Nov 26 '20 at 09:40
  • I forgot to say that the user being used to access the folder where dbf file is located, is local administrator. – Willy Nov 26 '20 at 11:04
  • I have discovered what is happening. Please see my last update "UPDATE 2020/11/27". It seems it stalls when performing ExecuteNonQuery because a waning message appears in background (not visible) waiting for you to click a button in order to proceed with the insert. I am using version 11.10 of Advantage OLE DB Provider driver. I have seen there is a new version 12 but it seems it is not free. How can I avoid this warning modal window to appear? maybe setting somewhat in the ads.ini file? – Willy Nov 27 '20 at 11:29
  • @Ralph, I don't know. I have no idea what the modal is saying. As I said before, I would go for a VFPOLEDB + REST API implementation instead which would be easier and painless compared to ADS. – Cetin Basoz Nov 27 '20 at 12:05
  • I was using VFPOLEDB before but this driver is only available in 32-bit, not 64-bit and I need a driver with support for 64-bit so for this reason I changed to Advantage OLE DB Provider because it is available in 64-bit. – Willy Nov 27 '20 at 15:02
  • Yes VFPOLEDB is 32 bits and well enough to build a REST API service. I don't understand why you need to have it in 64 bits only. – Cetin Basoz Nov 27 '20 at 23:43
  • I need to have the driver in 64-bit because my ASP.NET MVC app is in 64-bit for memory reasons (a process running in 32-bit could not address more than 4GB of memory and it is not enough for us. In 64-bit a process can address more than 4GB) and other things so application pool is set to run in 64-bit, not 32-bit. – Willy Nov 28 '20 at 19:26
  • 1
    @Ralph, but you can access a REST API running 32 bit, no? Sorry I can't understand why you can't use 32 bıt REST API. – Cetin Basoz Nov 30 '20 at 00:24
  • Application pool is set to run only in 64-bit so worker process w3wp.exe is running only in 64 bits, it cannot execute 32-bit code. – Willy Nov 30 '20 at 09:04
  • 1
    @Ralph, I understand that. Your ASP.Net MVC project runs 64 bit. What I am saying, you can also have a REST API service which handles data layer and that can be 32 bits. It would be bits and language neutral. – Cetin Basoz Nov 30 '20 at 12:21
  • Ok, I understand. Yes, you are right. From ASP.NET MVC project running on 64-bit you can call and execute code from a REST API service in 32-bit. This would be a solution but I would like to avoid to create a REST API service only for this purpose. – Willy Dec 01 '20 at 18:50