Author Topic: C# Addin with GUI (windows): Make a repository.SqlQuery(sql) in the background  (Read 1839 times)

Helmut Ortmann

  • EA User
  • **
  • Posts: 967
  • Karma: +42/-1
    • View Profile
Hello,

Can a long-running EA API SQL (repository.SqlQuery(sql))) be put in the background of the C# AddIn? During running this SQL, the AddIn GUI should be responsive for other tasks.

I have tried the BackgroundWorker. The BackgroundWorker works fine for not EA API calls. However, in the case of the API call 'repository.SqlQuery(sql)', it blocks the AddIn until the call is finished.

For other tasks, which may include short EA API Calls, the BackgroundWorker works fine. For example, I use it to load model content while starting the AddIn.

STA Threads may be a solution. But does anyone have experience with such background work?

Thanks and Best Regards,

Helmut
Coaching, Training, Workshop (Addins: hoTools, Search&Replace, LineStyle)

qwerty

  • EA Guru
  • *****
  • Posts: 13516
  • Karma: +394/-299
  • I'm no guru at all
    • View Profile
I guess you would have to run it in a 2nd (spawned) instance?

q.

Geert Bellekens

  • EA Guru
  • *****
  • Posts: 12936
  • Karma: +538/-33
  • Make EA work for YOU!
    • View Profile
    • Enterprise Architect Consultant and Value Added Reseller
Hi Helmut,

Using a backgroundworker works just fine for me.
I do something similar in the EA Navigator.
I load the details of an element in a background thread (which probably includes calls to Repository.SQLQuery) and once finished I show the result in EA.
This makes sure my add-in (that reacts to the ContextChanged event) doesn't block normal user interaction with EA.

Same story witht he quicksearch.

The relevant code can be found here: https://github.com/GeertBellekens/Enterprise-Architect-Toolpack/blob/master/EANavigator/NavigatorControl.cs

Geert

Helmut Ortmann

  • EA User
  • **
  • Posts: 967
  • Karma: +42/-1
    • View Profile
Hi Geert,

Thanks for your answer.

It works pretty well for things like doing a lot in the background. I've already done such things, and I'm happy with this. A lot of short-running EA API calls are no issue.

Sadly, this approach doesn't work for a long-lasting API call to EA COM-Object like 'repository.SqlQuery()', which, in my case, may need minutes to complete. During the time to complete the method call, the main thread with the GUI is blocked by the BackgroundWorker. After the call, the main thread can run until the following API call to COM occurs.

In the meantime, I've googled and tested a bit.

Using the EA COM-Object (Repository) runs in a STAThread, which essentially states that this is a thread-unsafe call.

The BackgroundWorker is a MTA thread. The MTA background thread blocks the main thread until the call is finished to ensure that the thread-unsafe COM object will not cause any harm.

That's what I have understood.

The solution could be:
Making an own STAThread as a background thread.

I made a little test and confirmed the blocking of the main thread and the thread types (main: STAThread, background: MTA).

It all looks a little complicated and unpredictable (Thread handling, ????)

Best regards,

Helmut



Coaching, Training, Workshop (Addins: hoTools, Search&Replace, LineStyle)

Helmut Ortmann

  • EA User
  • **
  • Posts: 967
  • Karma: +42/-1
    • View Profile
Hi,

If you want to run long-running SQL in parallel, you can use the BackgroundWorker, as Geert suggests.

You will get real parallel processing if you create a second EA.Repository object and use this in the background. Be aware, That you then have to ensure thread safety and the disposal of the second EA.Repository object.

I've tried it, and in my case, it works.

Best regards,

Helmut
Coaching, Training, Workshop (Addins: hoTools, Search&Replace, LineStyle)

qwerty

  • EA Guru
  • *****
  • Posts: 13516
  • Karma: +394/-299
  • I'm no guru at all
    • View Profile
Just as I thought... As long as you just query, there will not be many issues, except for the one thread changing things which the other relies on in cascaded queries. To make it clean you need semaphores. But I'd guess in the most cases that's just overkill.

q.

Helmut Ortmann

  • EA User
  • **
  • Posts: 967
  • Karma: +42/-1
    • View Profile
I agree!
Coaching, Training, Workshop (Addins: hoTools, Search&Replace, LineStyle)