Global DataSet in asp.net Threat-Safety

  • Thread starter Thread starter Thomas Gasser
  • Start date Start date
T

Thomas Gasser

Hello,

i have defined a dataset in the HttpApplicatonState, which is
generated on startup (only the schema) the filling of the dataset
happens on demand (on first time the spezified data is requested). so
the data writes have to be synchronized, how is this done?

Other requirements of the global DataSet:
I have to implement a GarbageCollector, which removes infrequently
accessed data, older then x hours or x days ... something like this.

The Data in Database can also changed by other applications, this data
has to be synchronized with the global dataset ... sounds complicated
....

i have looked around, but i found no solution/answers for my problems
....

any ideas how to synchronize datawrites and enforce threadsafety for
the dataset...

thank you and best regards!
Thomas Gasser
 
The DataSet is not thread-safe for writes, so if you'll have writes at
unpredictable points in your app you'll have to synchronize access
always -even for readers-, which might hurt performance.

The simplest way to synchronize all access to the dataset (or to any other
thing for that matter) is to have an additional global variable (or a
variable stored in the app state if you want to) and use it as a lock. For
example, you can simply have an instance of object (i.e.
state["dataset_lock"] = new object(); or myglobal = new object();). Then
make sure that at every point, before using the dataset, you lock on the
object (i.e. lock(state["dataset_lock"]) { // do stuff... }, or
lock(myglobal) { ... })

The problem with this approach is that if you have mostly reads and a only a
few writes, all the readers contain (block) each other, slowing down your
application.

An alternate approach, a little more complicated, is to do the following:
- have a global (or app state) with a read-only version of the dataset. The
contents of this dataset are NEVER updated. As long as that holds, you can
use the dataset without any locking, so your readers will never see
contention.
- every time you need to update the dataset, the writer locks on a separate
writer lock (so you never have multiple writers running at the same time).
Then it clones the dataset, and performs the changes on the clone. So far,
no one can see the changes because they are done in a copy, so no lock is
needed for readers. Finally, to "publish" the changes, use
Interlocked.Exchange to swap the value of the reference.

--
Pablo Castro
Program Manager - ADO.NET Team
Microsoft Corp.

This posting is provided "AS IS" with no warranties, and confers no rights.
 
Forgot to ask: I'm curious about your scenario. You're using DataSet as a
cache in the web server right? How big are those DataSets? How often are
they updated?

Thanks,

--
Pablo Castro
Program Manager - ADO.NET Team
Microsoft Corp.

This posting is provided "AS IS" with no warranties, and confers no rights.


Pablo Castro said:
The DataSet is not thread-safe for writes, so if you'll have writes at
unpredictable points in your app you'll have to synchronize access
always -even for readers-, which might hurt performance.

The simplest way to synchronize all access to the dataset (or to any other
thing for that matter) is to have an additional global variable (or a
variable stored in the app state if you want to) and use it as a lock. For
example, you can simply have an instance of object (i.e.
state["dataset_lock"] = new object(); or myglobal = new object();). Then
make sure that at every point, before using the dataset, you lock on the
object (i.e. lock(state["dataset_lock"]) { // do stuff... }, or
lock(myglobal) { ... })

The problem with this approach is that if you have mostly reads and a only a
few writes, all the readers contain (block) each other, slowing down your
application.

An alternate approach, a little more complicated, is to do the following:
- have a global (or app state) with a read-only version of the dataset. The
contents of this dataset are NEVER updated. As long as that holds, you can
use the dataset without any locking, so your readers will never see
contention.
- every time you need to update the dataset, the writer locks on a separate
writer lock (so you never have multiple writers running at the same time).
Then it clones the dataset, and performs the changes on the clone. So far,
no one can see the changes because they are done in a copy, so no lock is
needed for readers. Finally, to "publish" the changes, use
Interlocked.Exchange to swap the value of the reference.

--
Pablo Castro
Program Manager - ADO.NET Team
Microsoft Corp.

This posting is provided "AS IS" with no warranties, and confers no rights.


Thomas Gasser said:
Hello,

i have defined a dataset in the HttpApplicatonState, which is
generated on startup (only the schema) the filling of the dataset
happens on demand (on first time the spezified data is requested). so
the data writes have to be synchronized, how is this done?

Other requirements of the global DataSet:
I have to implement a GarbageCollector, which removes infrequently
accessed data, older then x hours or x days ... something like this.

The Data in Database can also changed by other applications, this data
has to be synchronized with the global dataset ... sounds complicated
...

i have looked around, but i found no solution/answers for my problems
...

any ideas how to synchronize datawrites and enforce threadsafety for
the dataset...

thank you and best regards!
Thomas Gasser
 
Pablo Castro said:
Forgot to ask: I'm curious about your scenario. You're using DataSet as a
cache in the web server right? How big are those DataSets? How often are
they updated?

Thanks,

--
Pablo Castro
Program Manager - ADO.NET Team
Microsoft Corp.

This posting is provided "AS IS" with no warranties, and confers no rights.

Hallo Pablo,

thank you for your answer, I will think about it ...

Forgot to ask: I'm curious about your scenario. You're using DataSet as a
cache in the web server right? How big are those DataSets? How often are
they updated?


Thats the big problem, we have only one dataset in the whole
application and that will be very big, i think of 1 GB (a lot of
DataTables in this DataSet are only accessed for read ...).
I think 40 percent of the DataTables are read/write. Updates of this
happens very often.
Performance is a very important criteria for this application.

Thomas Gasser
 
Back
Top