How Access Uses SQL Server Connections 

Summary:

This article describes how Access uses connections to SQL Server and
how application developers can minimize use of these connections.

This article assumes the reader is highly knowledgeable about the low
level interaction between applications and SQL Server.

More Information:

The conventional application that accesses a server does it in a
simple single-tasking manner, requiring a single connection to the
server. Access, however, is not the typical conventional server
front-end. Many of its features, including updatable views (dynasets),
joins between local and server data, execution of complex expressions
that the server may not be able to handle, and seamless transition
from one server to another, require Access to obtain more connections
than the conventional front-end needs.

Although some servers, such as Microsoft SQL Server, are not too
stingy on giving out connections, there are servers that place strict
limits on the number of connections an application can open. (In some
installations, SQL Server also places absolute restrictions on
connections.) When designing applications for the more restrictive
servers, it is important to understand how Access uses connections.

Connections are opened by Access when it needs to execute a query on
the server (which it must do to build dynasets or static views),
obtain the data in a dynaset, or update data on the server. These
connections can be categorized into two types: connections needed to
build the working set, and connections needed to service dynasets.

Both types of views available in Access (static views and dynasets)
are built by executing a query (called a "local" query to
differentiate it from other types of queries discussed below). This
local query processes Access and foreign ISAM data (both locally and
file server based) and remote server data, and pulls it into a
temporary table that represents the view. To build static views, the
actual data is stored in the temporary table, whereas to build
dynasets, pointers to the actual data are stored.

When server data is included in the local query, execution of the
query involves asking the server (or servers) for data, which is done
by opening connections and sending queries to the server. Each query
sent to the server requires that a connection be opened.  If more than
one query is to be sent to the server, a single connection could be
used and the queries executed serially. However, this would typically
require the user to wait for all of the server queries to complete
before any data would appear. Therefore, Access executes the server
queries in parallel, requiring a connection for each.

The number of queries sent to a server may not be entirely obvious.
Much of the time, access to all of the remote base tables will be
combined into a single query, if all of the base tables reside on the
same server. In the worst case, each server base table referenced by
the local query will require a connection. There are several factors
that could compel Access to split a local query into several server
queries:

 - If server data is joined to data from other sources (that is,
   local, foreign ISAM, and other servers), the Access optimizer may
   decide that it is more efficient not to combine references to two
   tables on the same server into a single query. For example, if the
   Customers and Order Items tables are on a server and the Orders
   table is in a local Microsoft Access database, then it is likely
   that the optimizer will decide to ask for the Customers and Order
   Items tables separately, rather than asking for the cross-product
   of the two, to join to the Orders table. As you can tell from this
   example, this is unlikely to happen in a real scenario.

 - If an expression involved in the query cannot be executed on the
   server (either because the server doesn't support it or because the
   semantics provided by the server differ greatly with those provided
   by Access), the expression will be executed locally. An extreme
   example of this is a local query with a restriction that calls a
   user-defined function. Although this may not require separating
   remote tables into separate server queries, it will if the
   expression that isn't executable on the server is somehow involved
   with the join between the two tables. Note that in Access,
   expressions containing a conjunction that can be executed on the
   server will be executed locally in their entirety. These
   expressions are not split to execute part locally and part on the
   server.

 - The parameters used to attach tables on the same server to an
   Access database differ. For example, if two tables are in different
   databases, or if they are being accessed using different user names
   and passwords, then separate connections will be required to
   execute a local query referencing both of them.

   Connections opened in the execution of a local query will be kept
   open until the working set containing the queries is closed.

   Connections are also opened in support of dynasets. But, unlike the
   server queries sent during the execution of a local query, the
   queries sent to the server in support of a dynaset are executed
   entirely and very quickly.  This is because they are used to fill
   portions of the dynaset with data (given the pointers to the data
   provided by the local query), and to do updates to the server.
   Therefore, Access opens only one connection per attached server,
   provided that the link attachment information is the same for each
   server tables.

As a result of the above rules, when an Access query is executed, it
typically requires only one (for a static view or two (for a dynaset)
connection. This doesn't represent an extravagant use of server
connections, but good applications could involve the execution of many
Access queries that could occupy many server connections very quickly.
There are some steps the designer can take to minimize the use of
connections:

 - Reduce the number of queries required by the application. Each
   form, subform, data sheet, report, and list box requires a query,
   and each of these queries that accesses server data will require at
   least one or two connections. Close forms, data sheets, and reports
   as soon as they are no longer needed. Also, bring server data to a
   local database where practical, especially for filling list boxes.

 - Avoid queries that join server data to local data to server data,
   as described above. These type of queries will most likely be
   executed using a connection for each server table.

 - Avoid expressions that must be executed locally when joining server
   data together. Each of the tables involved with such a join
   expression, or that is restricted by a WHERE clause containing such
   an expression, will need to be executed locally. It should be noted
   that separating expressions into separate query objects will not
   help alleviate this problem, because the optimizer combines all
   query objects in a single query before execution for efficiency.

 - Use static working sets when seeing other users' changes, or when
   making changes yourself is not required. This will avoid the
   connections needed to support dynasets.

With an understanding of how Access uses connections, and with prudent
application design, you should not run out of server connections.
