How to declare a variable in the global scope?

M

Miguel Dias Moura

Hello,

I am working on an ASP.NET / VB page and I created a variable "query":

Sub Page_Load(sender As Object, e As System.EventArgs)
Dim query as String = String.Empty
...
query = String.Format("SELECT * FROM dbo.documents WHERE ") & query
End Sub

I need "query" to be global and accessible everywhere.
How can I do this?

Thanks,
Miguel
 
S

Saravana

If you want query variable to be accessed in all the pages then declare that
variable in application scope or put it in cache.
 
S

Steve C. Orr [MVP, MCSD]

With a web app, generally your global variables should be stored in the
Application Object or Cache object. This way they are explicity made
accessible to all code in your app.
 
M

Miguel Dias Moura

Hello,

Can you tell me how to store the global variables in the Application
Object?
What should the code be and where should I place it?

I am just starting with ASP.NET.

Thanks,
Miguel
 
J

Juan T. Llibre

You could also insert a key in the application's
web.config and read it whenever you need it.

First, include this in your web.config :

<appSettings>
<add key="query1" value="SELECT * FROM dbo.documents WHERE"/>
</appSettings>

Then, retrieve it with this :

Dim query1 As String = System.Configuration.ConfigurationSettings.AppSettings("query1")

The value for query1 will be available at the Application scope level.
Values read from the web.config file are always of type String.

This method has the advantage that you can have multiple
queries stored in web.config, to be used as needed.




Juan T. Llibre
===========
 
S

Steve C. Orr [MVP, MCSD]

'To store a variable:
Application.Lock()
Application("MyVar")="whatever"
Application.Unlock()

'to retrieve the variable:
Dim s as String = Application("MyVar").ToString()

--
I hope this helps,
Steve C. Orr, MCSD, MVP
http://Steve.Orr.net
 
K

Kevin Spencer

Wouldn't it be better to use Cache?

--
HTH,
Kevin Spencer
..Net Developer
Microsoft MVP
Neither a follower
nor a lender be.
 
J

Juan T. Llibre [MVP]

Steve,

Doesn't serializing the access to the Application object
using the Lock and UnLock methods mean you have to
accept a considerable performance hit ?

It seems to me that, although using the Application object
gets the job done, it does so in a very inefficient way.

That's why I suggested adding a key in web.config,
and retrieving *that* whenever needed.



Juan T. Llibre
===========
 
J

John Saunders

Juan T. Llibre said:
Steve,

Doesn't serializing the access to the Application object
using the Lock and UnLock methods mean you have to
accept a considerable performance hit ?

Steve, why do you need to serialize writes? Updates maybe, but why simple
writes?

John Saunders
 
S

Scott Allen

Searching the underlying data structure to see if and where the key
exists wouldn't be an atomic operation, something could change in
betwen the 'find the entry' and the 'insert' or 'write' operation.

Fortunately, the docs say the Application object is safe for
multi-threaded access. The Lock / Unlock would't be required for a
single write operation. Reflector shows it uses a slightly more
granular reader/writer lock underneath for thread safety:

this._lock.AcquireWrite();
try
{
base.BaseSet(name, value);

}
finally
{
this._lock.ReleaseWrite();
}
 
M

Miguel Dias Moura

Guys,

I am even more confused than I was before...
....i am just starting.

So Aplication, Cache or Web.Config?

Maybe I should mention that I only need to access the query variable in
the same page where I have this script.

Basically this script creates the SQL code to be used on a dataset on
that page using the values passed on the URL and a list of rules.

Web.Config seems a really general solution because, if I am not wrong,
it makes available the variable to all pages.

Do you think it's a bad solution when I only need it on the same page of
the script?

About Aplication I am a little bit confused to. :). I should place the
code you mention just before the function PAGE_LOAD.

Sorry for so many questions but I am starting ASP.NET and something seem
really obvious and easy to me but other are completely strange even if
they are simple.

Thanks,
Miguel
 
J

Juan T. Llibre [MVP]

Hi, Miguel.

re:
So Aplication, Cache or Web.Config?

Application would be overkill, and consumes the most
resources both in terms of ram and cpu contention.

Cache is doable, but the ram consumed is permanent.

I'd go with Web.config.
Maybe I should mention that I only need to access the query variable in
the same page where I have this script.

If that's the case, you don't need a variable.

However, you should consider not only placing
that query in web.config, but also placing your
database connection information in the web.config, too.

That will keep your server access info ( account and password )
away from prying eyes. If you place your account and password
in the page's code, it could be revealed.

A fourth alternative ( I hope this doesn't confuse you )
would be to create a database access class and compile
it as an assembly. Then, you could reference the assembly
any time you need to connect to your data.

For your purposes, using web.config is OK.
If traffic gets heavy, consider compiling a db access assembly.



Juan T. Llibre
===========
 
M

Miguel Dias Moura

Hi,

I already have the database connection information on my web.config
file.

I followed your advice and include the query (queryDocuments) variable
in the web.config. However it's not working.

My interpretation is that the script is not updating that value.
The SQL code used is always the same even if queryDocuments change.
I believe I am missing something here.

Here is the code on my page:

....
ConnectionString='<%#
System.Configuration.ConfigurationSettings.AppSettings("CON_STR_conTes")
%>'
DatabaseType='<%#
System.Configuration.ConfigurationSettings.AppSettings("CON_DBT_conTes")
%>'
CommandText='<%#
System.Configuration.ConfigurationSettings.AppSettings("queryDocuments")
%>'
....

See what I did on CommandText?

Now check my script also on that page:

<script runat="server">

Sub Page_Load(sender As Object, e As System.EventArgs)
Dim queryDocuments As String =
System.Configuration.ConfigurationSettings.AppSettings("queryDocuments")
If Request.QueryString("pesquisar") Is Nothing Then
queryDocuments = "SELECT * FROM dbo.documents"
Else
queryDocuments = ""
Dim keywords as string()
keywords = Request.QueryString("pesquisar").Split(CChar(" "))
Dim i As Int32
For i = 0 To keywords.Length
queryDocuments += String.Format("CONTAINS (*, '{0}') ",
keywords(i))
If i + 1 = keywords.Length Then
i = keywords.Length
Exit For
End If
queryDocuments += " AND "
Next
queryDocuments = String.Format("SELECT * FROM dbo.documents WHERE
") & queryDocuments
End If
Response.Write(queryDocuments)
Response.Write(System.Configuration.ConfigurationSettings.AppSettings("queryDocuments"))
End Sub

</script>

On the Web.Config I have this:

<add key="queryDocuments" value="SELECT * FROM dbo.documents"/>

What am I doing wrong?

Thanks,
Miguel
 
J

Juan T. Llibre [MVP]

Let's do this by parts, Miguel,
to see if we can nail the problem.

You do have

<?xml version="1.0"?>
<configuration>
<appSettings>
<add key="queryDocuments" value="SELECT * FROM dbo.documents"/>
</appSettings>
' other configuration stuff...
<system.web>
</system.web>
</configuration>

or similar, in your web.config, right ?
Make sure of the placement of <appSettings> ( below <configuration> )

Please write this code as a file "test.aspx", and run it,
to see if "SELECT * FROM dbo.documents" is written

test.aspx:
----------

<%@ Page Language="VB" %>
<head>
<title>Retrieve value from web.config</title>
</head>
<body>
<script runat="server">
Public Sub Page_Load(Sender As System.Object, E As System.EventArgs)
Dim queryDocs As String = System.Configuration.ConfigurationSettings.AppSettings("queryDocuments")
Label1.Text = queryDocs
End Sub
</script>
<form id="form1" runat="server">
<div>
<asp:Label ID="Label1" Runat="server" Text=""></asp:Label>
</div>
</form>
</body>
</html>

Run it, and let us know if the queryDocuments key is retrieved.

Then, once we know that, we can check other possibilities.




Juan T. Llibre
===========
 
M

Miguel Dias Moura

Hello,

About my web.config file is as you said.
I ran the test file you sent me and here is the result:

SELECT * FROM dbo.documents

I knew already this was going to be result because in my script I placed
the code line "
Response.Write(System.Configuration.ConfigurationSettings.AppSettings("queryDocuments"))"
right after "Sub Page_Load(sender As Object, e As System.EventArgs)" and
I got the value I have in web.config file.

What should I do know?

Thanks,
Miguel
 
J

Juan T. Llibre [MVP]

OK, that's good.

Next question:

You are retrieving the query's value twice.

Once with:
CommandText='<%# System.Configuration.ConfigurationSettings.AppSettings("queryDocuments") %>'

and you retrieve it again with
Dim queryDocuments As String = System.Configuration.ConfigurationSettings.AppSettings("queryDocuments")

Is it possible that the first time you retrive it
sets the value permanently ?

If you have a permanent value for CommandText,
then nothing you do with "queryDocuments", later,
will affect the value for "CommandText".

Why are you retrieving that value twice,
and assigning the same value to two different variables ?
( CommandText and queryDocuments )



Juan T. Llibre
===========
 
S

Steve C. Orr [MVP, MCSD]

Accessing the web.config is rather slow.
Application is faster because it's all in memory and doesn't need to access
the hard drive. (except maybe it's not fast when the server is under heavy
load.)

--
I hope this helps,
Steve C. Orr, MCSD, MVP
http://Steve.Orr.net
 
J

Juan T. Llibre [MVP]

re:
Application is faster because it's all in memory

Both cache data and compiled, cached,
aspx pages are also "in memory".

Regarding performance concerns, see :
http://msdn.microsoft.com/library/d.../en-us/cpguide/html/cpconApplicationState.asp

Application-state variables are, in effect, global variables for a given
ASP.NET application. Like client-side application developers,
ASP.NET programmers should always consider the impact of
storing anything as a global variable.

The following issues are particularly important in this context:

1. The memory impact of storing something in application state.
The memory occupied by variables stored in application state
is not released until the value is either removed or replaced

That is not a concern when using web.config.

2. The concurrency and synchronization implications of storing
and accessing a global variable within a multithreaded server environment.

That is not a concern when using web.config.

3. The scalability implications of storing and accessing
a global variable within a multithreaded server environment.

That is not a concern when using web.config.

Regarding Locks ( like the ones you recommended ) :
Application.Lock()
Application.Unlock()

Locks should be used whenever an attempt is made to write
or update a file. Locks that protect global resources are
themselves global, and code running on multiple threads
accessing global resources ultimately ends up contending
on these locks.

This causes the operating system to block the worker threads
until the lock becomes available. In high-load server environments,
this blocking can cause severe thread thrashing on the system.

On multiprocessor systems, it can lead to processor underutilization
(since all the threads for a processor theoretically can be stalled while
waiting for a shared lock) and significant drops in overall scalability.

That is not a concern when using web.config.

4. The life-cycle implications of information stored in application state.

That is not a concern when using web.config.

5. Application state is not shared across a Web farm
(in which an application is hosted by multiple servers)
or a Web garden (in which an application is hosted by
multiple processes on the same server).

Variables stored in application state in either of those scenarios
are global only to the particular process in which the application
is running.

Each application process can have different values.
Therefore, you cannot rely on application state to store
unique values or update global counters, for example,
in Web farm and Web garden scenarios.

That is not a concern when using web.config.

re:
(except maybe it's not fast when the server is under heavy load.)

That alone would make me shy away from the use of Global.asax's
Application_OnStart as a data repository to be accessed during
an application's lifetime.

In short, although speed is not the only consideration, I haven't
seen *anybody* recommending the use of variables stored
at the Global Application level, except for very small tidbits
which are updated once in a blue moon.

Probably the fastest way to retrieve a small amount of stored
data would be to declare it as a variable in an assembly,
and to retrieve and cache the result.

For not-too-intensive traffic websites, short strings stored in
web.config is one of the easiest storage/retrieval methods to
implement, is reliable, and is fast enough.




Juan T. Llibre
===========
 
K

Kevin Spencer

web.config is loaded into memory when the app starts, isn't that correct?

--
HTH,
Kevin Spencer
..Net Developer
Microsoft MVP
Neither a follower
nor a lender be.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,744
Messages
2,569,482
Members
44,901
Latest member
Noble71S45

Latest Threads

Top