ASP.NET State Management
A Web application is stateless. For example, by default if a user enters information into a text box on an HTML Web page, that information is sent to the server. However, it is not returned to the browser in the response. ASP.NET help you preserve data on both a per-page basis and an application-wide basis. These features are as follows:
View state, control state, hidden fields, cookies, and query strings all involve storing data on the client in various ways.
Application state, session state, and profile properties all store data in memory on the server.
Client-Based State Management Options
Storing information either in the page or on the client computer. For these options, no information is maintained on the server between round trips.
1. View State - The ViewState property provides a dictionary(key/value pair) object for retaining values between multiple requests for the same page. View state provides state information for a specific ASP.NET page. View state information is serialized into XML and then encoded by using base-64 encoding, which can generate large amounts of data. View state is enabled by default.
When the page is processed, the current state of the page and controls is hashed into a string (base64-encoded) and saved in the page as a hidden field, or multiple hidden fields if the amount of data stored in the ViewState property exceeds the specified value in the MaxPageStateFieldLength property. When the page is posted back to the server, the page parses the view-state string at page initialization and restores property information in the page.
Disable/Enable view state for a control
<%@ Page ... ViewStateMode="Disabled" %>
<asp:Label runat="server" ID="Label2" ViewStateMode="Enabled" ... />
Enabled- Enable view state for the control even if the parent control has view state disabled.
Disabled - Disable view state for this control even if the parent control has view state enabled
Inherit - Inherit the value of ViewStateMode from the parent, this is the default value.
Even when you explicitly turn view state off, a hidden field is still sent to the browser to indicate that postback is occurring for the page.
MaxPageStateFieldLength
Asp.net - <asp:Page MaxPageStateFieldLength="Int32" />
If the amount of data that is stored in the ViewState property exceeds the value specified in the page's MaxPageStateFieldLength property, the page splits view state into multiple hidden fields.
web.config
<configuration>
<system.web>
<pages maxPageStateFieldLength="1000" />
</system.web>
</configuration>
You can store values in view state as well.
ViewState["Text"]
(ArrayList)ViewState["arrayListInViewState"];
Encrypting view state data can affect the performance of your application. Therefore, do not use encryption unless you need it.
<asp:Page ViewStateEncryptionMode="ViewStateEncryptionMode" />
<%@ Page Language="C#" ViewStateEncryptionMode="Always" %>
<system.web>
<pages viewStateEncryptionMode="Always" />
</system.web>
Advantages of using view state are:
No server resources are required.
Simple implementation,no custom programming.
Enhanced security features - The values in view state are hashed, compressed, and encoded for Unicode implementations, which provides more security than using hidden fields.
Disadvantages of using view state are:
Performance considerations - Storing large values can cause the page to slow down when users display it and when they post it.
Device limitations - Mobile devices might not have the memory capacity to store a large amount of view-state data. Some mobile devices do not allow hidden fields at all. Therefore, view state will not work for those devices.
Potential security risks - The view state is stored in one or more hidden fields on the page. The information in the hidden field can be seen if the page output source is viewed directly, creating a potential security issue.
2. Control State - If ViewState is turned off at a page level, it will breaking your control. To solve this, to store control-state data in order for a control to work properly.The ControlState property allows you to persist property information that is specific to a control and cannot be turned off like the ViewState property.
Advantages of using control state are:
No server resources are required
Reliability - Because control state cannot be turned off like view state, control state is a more reliable method for managing the state of controls.
Versatility - Custom adapters can be written to control how and where control-state data is stored.
Disadvantage of using control state are: Write custom code to save and load control state.
Example
http://msdn.microsoft.com/en-us/library/1whwt1k7%28v=vs.100%29.aspx
3. Hidden Fields - ASP.NET allows you to store information in a HiddenField control, which renders as a standard HTML hidden field. Not visibly in the browser, but you can set its properties just as you can with a standard html control.
When a page is submitted to the server, the content of a hidden field is sent in the HTTP form collection along with the values of other controls. The hidden fields will be available for HTTP POST command not HTTP GET command
<asp:hiddenfield id="ValueHiddenField" onvaluechanged="ValueHiddenField_ValueChanged" value="" runat="server"/>
Advantages of using hidden fields are:
No server resources are required
Widespread support - Almost all browsers and client devices support forms with hidden fields.
Simple implementation - Hidden fields are standard HTML controls.
Disadvantages of using hidden fields are:
Potential security risks - Easily can access the hidden field value
Simple storage architecture - Does not support rich data types, a single string value field in which to place information. To store multiple values, use delimited strings
Performance considerations - Storing large values can cause the page to slow down when users display it and when they post it.
Cookies - A cookie is a small amount of data that is stored either in a text file on the client file system or in-memory in the client browser session. It contains site-specific information that the server sends to the client along with page output. Cookies can be temporary (with specific expiration times and dates) or persistent.
The browser can only send the data back to the server that originally created the cookie. Hackers can access cookies, not good for sensitive information
HttpCookie MyCookie = new HttpCookie("LastVisit");
DateTime now = DateTime.Now;
MyCookie.Value = now.ToString();
MyCookie.Expires = now.AddHours(1); //Delete cookies
Response.Cookies.Add(MyCookie);
Response.Cookies["userName"].Value = "patrick";
Advantages of using cookies are:
Configurable expiration rules - The cookie can expire when the browser session ends, or it can exist indefinitely on the client computer, subject to the expiration rules on the client.
No server resources are required - The cookie is stored on the client and read by the server after a post.
Simplicity - The cookie is a lightweight, text-based structure with simple key-value pairs.
Data persistence
Disadvantages of using cookies are:
Size limitations
User-configured refusal - Users disable cookie.
Potential security risks - Easily can access the hidden field value
4. Query Strings - A query string is information that is appended to the end of a page URL.
example - http://www.microsoft.com/softwarelist.aspx?category=software&type=cloud
Query strings provide a simple but limited way to maintain state information. For example, they are an easy way to pass information from one page to another, a 2083-character limit on the length of the URL.
Use HTTP GET command - query string values to be available during page processing
HTTP POST command - cannot take advantage of a query string
Advantages of using query strings are: No server resources are required, Widespread support, Simple implementation
Disadvantages of using query strings are: Potential security risks, Limited capacity - a 2083-character limit on the length of URLs.
Server-Based State Management Options
5. Application State Application state is used to store data on the application machine.
Application state is stored in memory on the server and is faster than storing and retrieving information in a database.
Unlike session state, which is specific to a single user session, application state applies to all users and sessions.
Application state is a global storage mechanism that is accessible from all pages in the Web application.
Application state is stored in a key/value dictionary that is created during each request to a specific URL.
When request a page from client machine, an instance will create at application machine by the help of HttpApplicationState class.
Entire application will have only one instance which is provided by HttpContext property named Application.
Application state is a useful place to store small amounts of often-used data that does not change from one user to another.
Application.Add("MyAppVar1", MyObject1);
Application.Clear();
Object MyObject = Application.Get(0);
Object MyObject = Application.Get("MyAppVar1");
for (Loop1 = 0; Loop1 < Application.Count; Loop1++) StateVars[Loop1] = Application.GetKey(Loop1);
Application.Lock();
Application["MyCode"] = 21;
Application.UnLock();
//the above 3 lines - to avoid deadlock occurrence while we updating application variable by multiple users
Application.Remove("MyAppVar1");
Application.RemoveAll();
Application.Set("MyAppVar1", MyNewObjectValue);
Advantages of using application state are:
Simple implementation - Application state is easy to use.
Application object memory relased when we removed.
Multi user can able to access application variable.
To avoid deadlock or conflict we should use Lock and Unlock when we use write or update in the application object.
Other application can't access this application values.
Disadvantages of using application state are:
Application variable will exists until exit our application.
If we do not have Lock() and Unlock, deadlock will occur.
Its gloable variable so anyone can access within this application.
6. Session State - Session state is similar to application state, except that it is scoped to the current browser session. Each user session will have a different session state. Session state is structured as a key/value dictionary for storing session-specific information.
Session.Add(itemName, itemValue);
Session.Remove();
A SessionID values are stored in a cookie or in the URL for a "cookieless" session.
<configuration>
<system.web>
<sessionState cookieless="true"
regenerateExpiredSessionId="true" />
</system.web>
</configuration>
Regenerating Expired Session Identifiers - The session ID values that are used in cookieless sessions are recycled. That is, if a request is made with a session ID that has expired, a new session is started by using the SessionID value that is supplied with the request. This can result in a session unintentionally being shared when a link that contains a cookieless SessionID value is used by multiple browsers.
CreateSessionID - To create custom session id
Session Modes
InProc mode - which stores session state in memory on the Web server. This is the default.
StateServer mode - which stores session state in a separate process called the ASP.NET state service. This ensures that session state is preserved if the Web application is restarted and also makes session state available to multiple Web servers in a Web farm.
To use StateServer mode, you must first be sure the ASP.NET state service is running on the server used for the session store. The ASP.NET state service is installed as a service when ASP.NET and the .NET Framework are installed. The ASP.Net state service is installed at the following location: systemroot\Microsoft.NET\Framework\versionNumber\aspnet_state.exe
SQLServer mode - stores session state in a SQL Server database. This ensures that session state is preserved if the Web application is restarted and also makes session state available to multiple Web servers in a Web farm.
Custom mode - which enables you to specify a custom storage provider.
<configuration>
<connectionStrings>
<add name="OdbcSessionServices"
connectionString="DSN=SessionState;" />
</connectionStrings>
<system.web>
<sessionState
mode="Custom"
customProvider="OdbcSessionProvider">
<providers>
<add name="OdbcSessionProvider"
type="Samples.AspNet.Session.OdbcSessionStateStore"
connectionStringName="OdbcSessionServices"
writeExceptionsToEventLog="false" />
</providers>
</sessionState>
</system.web>
</configuration>
Off mode - which disables session state.
Session Events - ASP.NET provides two events that help you manage user sessions.
The Session_OnStart event is raised when a new session starts.
the Session_OnEnd event is raised when a session is abandoned or expires.
Session events are specified in the Global.asax file for an ASP.NET application.
If the Global.asax file or Web.config file for an ASP.NET application is modified, the application will be restarted and any values stored in application state or session state will be lost.
The Session_OnEnd event is not supported if the session Mode property is set to a value other than InProc, which is the default mode.
Configuring Session State
<sessionState mode="SQLServer"
cookieless="true "
regenerateExpiredSessionId="true "
timeout="30"
sqlConnectionString="Data Source=MySqlServer;Integrated Security=SSPI;"
stateNetworkTimeout="30"/>
Advantages of using session state are: Platform scalability. Cookieless support, Extensibility - store custom data format,
Disadvantage of using session state are: Performance considerations Session-state variables stay in memory until they are either removed or replaced.
7. Profile Properties - similar to session state, except that the profile data is not lost when a user's session expires.
The profile-properties feature uses an ASP.NET profile, which is stored in a persistent format and associated with an individual user.
The ASP.NET profile allows you to easily manage user information without requiring you to create and maintain your own database.
The profile makes the user information available using a strongly typed API that you can access from anywhere in your application.
To use profile properties, you must configure a profile provider. ASP.NET includes a SqlProfileProvider class that allows you to store profile data in a SQL database, but you can also create your own profile provider class that stores profile data in a custom format and to a custom storage mechanism such as an XML file, or even to a web service.
Because data that is placed in profile properties is not stored in application memory, it is preserved through Internet Information Services (IIS) restarts and worker-process restarts without losing data. Profile properties can be persisted across multiple processes such as in a Web farm or a Web garden.
Advantages of using profile properties are: Data persistence
Platform scalability - can be used in both multi-computer and multi-process configurations
Extensibility - ASP.NET includes a SqlProfileProvider class, you can create custom
Disadvantages of using profile properties are:
Performance considerations - Slower than using session state because instead of storing data in memory, the data is persisted to a data store.
Additional configuration requirements -
Data maintenance
Securing the Session ID
Protect your application with Secure Sockets Layer (SSL).
Specify a smaller value for the session Timeout. - Response.AddHeader("Refresh", Session.Timeout + ";URL=Logoff.htm";
Avoid using cookieless sessions.
Avoid specifying cookie modes of AutoDetect and UseDeviceProfile.
Allow users to log out, at which point you should call theHttpSessionState.Abandon method. Warn the user to close his or her browser after logging out.
When using cookieless sessions, configure regenerateExpiredSessionID as true to always start a new session when an expired session identifier is supplied.
http://msdn.microsoft.com/en-us/library/75x4ha6s%28v=vs.100%29.aspx
A Web application is stateless. For example, by default if a user enters information into a text box on an HTML Web page, that information is sent to the server. However, it is not returned to the browser in the response. ASP.NET help you preserve data on both a per-page basis and an application-wide basis. These features are as follows:
- View state
- Control state
- Hidden fields
- Cookies
- Query strings
- Application state
- Session state
- Profile Properties
View state, control state, hidden fields, cookies, and query strings all involve storing data on the client in various ways.
Application state, session state, and profile properties all store data in memory on the server.
Client-Based State Management Options
Storing information either in the page or on the client computer. For these options, no information is maintained on the server between round trips.
1. View State - The ViewState property provides a dictionary(key/value pair) object for retaining values between multiple requests for the same page. View state provides state information for a specific ASP.NET page. View state information is serialized into XML and then encoded by using base-64 encoding, which can generate large amounts of data. View state is enabled by default.
When the page is processed, the current state of the page and controls is hashed into a string (base64-encoded) and saved in the page as a hidden field, or multiple hidden fields if the amount of data stored in the ViewState property exceeds the specified value in the MaxPageStateFieldLength property. When the page is posted back to the server, the page parses the view-state string at page initialization and restores property information in the page.
Disable/Enable view state for a control
<%@ Page ... ViewStateMode="Disabled" %>
<asp:Label runat="server" ID="Label2" ViewStateMode="Enabled" ... />
Enabled- Enable view state for the control even if the parent control has view state disabled.
Disabled - Disable view state for this control even if the parent control has view state enabled
Inherit - Inherit the value of ViewStateMode from the parent, this is the default value.
Even when you explicitly turn view state off, a hidden field is still sent to the browser to indicate that postback is occurring for the page.
MaxPageStateFieldLength
Asp.net - <asp:Page MaxPageStateFieldLength="Int32" />
If the amount of data that is stored in the ViewState property exceeds the value specified in the page's MaxPageStateFieldLength property, the page splits view state into multiple hidden fields.
web.config
<configuration>
<system.web>
<pages maxPageStateFieldLength="1000" />
</system.web>
</configuration>
You can store values in view state as well.
ViewState["Text"]
(ArrayList)ViewState["arrayListInViewState"];
Encrypting view state data can affect the performance of your application. Therefore, do not use encryption unless you need it.
<asp:Page ViewStateEncryptionMode="ViewStateEncryptionMode" />
<%@ Page Language="C#" ViewStateEncryptionMode="Always" %>
<system.web>
<pages viewStateEncryptionMode="Always" />
</system.web>
Advantages of using view state are:
No server resources are required.
Simple implementation,no custom programming.
Enhanced security features - The values in view state are hashed, compressed, and encoded for Unicode implementations, which provides more security than using hidden fields.
Disadvantages of using view state are:
Performance considerations - Storing large values can cause the page to slow down when users display it and when they post it.
Device limitations - Mobile devices might not have the memory capacity to store a large amount of view-state data. Some mobile devices do not allow hidden fields at all. Therefore, view state will not work for those devices.
Potential security risks - The view state is stored in one or more hidden fields on the page. The information in the hidden field can be seen if the page output source is viewed directly, creating a potential security issue.
2. Control State - If ViewState is turned off at a page level, it will breaking your control. To solve this, to store control-state data in order for a control to work properly.The ControlState property allows you to persist property information that is specific to a control and cannot be turned off like the ViewState property.
Advantages of using control state are:
No server resources are required
Reliability - Because control state cannot be turned off like view state, control state is a more reliable method for managing the state of controls.
Versatility - Custom adapters can be written to control how and where control-state data is stored.
Disadvantage of using control state are: Write custom code to save and load control state.
Example
http://msdn.microsoft.com/en-us/library/1whwt1k7%28v=vs.100%29.aspx
3. Hidden Fields - ASP.NET allows you to store information in a HiddenField control, which renders as a standard HTML hidden field. Not visibly in the browser, but you can set its properties just as you can with a standard html control.
When a page is submitted to the server, the content of a hidden field is sent in the HTTP form collection along with the values of other controls. The hidden fields will be available for HTTP POST command not HTTP GET command
<asp:hiddenfield id="ValueHiddenField" onvaluechanged="ValueHiddenField_ValueChanged" value="" runat="server"/>
Advantages of using hidden fields are:
No server resources are required
Widespread support - Almost all browsers and client devices support forms with hidden fields.
Simple implementation - Hidden fields are standard HTML controls.
Disadvantages of using hidden fields are:
Potential security risks - Easily can access the hidden field value
Simple storage architecture - Does not support rich data types, a single string value field in which to place information. To store multiple values, use delimited strings
Performance considerations - Storing large values can cause the page to slow down when users display it and when they post it.
Cookies - A cookie is a small amount of data that is stored either in a text file on the client file system or in-memory in the client browser session. It contains site-specific information that the server sends to the client along with page output. Cookies can be temporary (with specific expiration times and dates) or persistent.
The browser can only send the data back to the server that originally created the cookie. Hackers can access cookies, not good for sensitive information
HttpCookie MyCookie = new HttpCookie("LastVisit");
DateTime now = DateTime.Now;
MyCookie.Value = now.ToString();
MyCookie.Expires = now.AddHours(1); //Delete cookies
Response.Cookies.Add(MyCookie);
Response.Cookies["userName"].Value = "patrick";
Advantages of using cookies are:
Configurable expiration rules - The cookie can expire when the browser session ends, or it can exist indefinitely on the client computer, subject to the expiration rules on the client.
No server resources are required - The cookie is stored on the client and read by the server after a post.
Simplicity - The cookie is a lightweight, text-based structure with simple key-value pairs.
Data persistence
Disadvantages of using cookies are:
Size limitations
User-configured refusal - Users disable cookie.
Potential security risks - Easily can access the hidden field value
4. Query Strings - A query string is information that is appended to the end of a page URL.
example - http://www.microsoft.com/softwarelist.aspx?category=software&type=cloud
Query strings provide a simple but limited way to maintain state information. For example, they are an easy way to pass information from one page to another, a 2083-character limit on the length of the URL.
Use HTTP GET command - query string values to be available during page processing
HTTP POST command - cannot take advantage of a query string
Advantages of using query strings are: No server resources are required, Widespread support, Simple implementation
Disadvantages of using query strings are: Potential security risks, Limited capacity - a 2083-character limit on the length of URLs.
Server-Based State Management Options
5. Application State Application state is used to store data on the application machine.
Application state is stored in memory on the server and is faster than storing and retrieving information in a database.
Unlike session state, which is specific to a single user session, application state applies to all users and sessions.
Application state is a global storage mechanism that is accessible from all pages in the Web application.
Application state is stored in a key/value dictionary that is created during each request to a specific URL.
When request a page from client machine, an instance will create at application machine by the help of HttpApplicationState class.
Entire application will have only one instance which is provided by HttpContext property named Application.
Application state is a useful place to store small amounts of often-used data that does not change from one user to another.
Application.Add("MyAppVar1", MyObject1);
Application.Clear();
Object MyObject = Application.Get(0);
Object MyObject = Application.Get("MyAppVar1");
for (Loop1 = 0; Loop1 < Application.Count; Loop1++) StateVars[Loop1] = Application.GetKey(Loop1);
Application.Lock();
Application["MyCode"] = 21;
Application.UnLock();
//the above 3 lines - to avoid deadlock occurrence while we updating application variable by multiple users
Application.Remove("MyAppVar1");
Application.RemoveAll();
Application.Set("MyAppVar1", MyNewObjectValue);
Advantages of using application state are:
Simple implementation - Application state is easy to use.
Application object memory relased when we removed.
Multi user can able to access application variable.
To avoid deadlock or conflict we should use Lock and Unlock when we use write or update in the application object.
Other application can't access this application values.
Disadvantages of using application state are:
Application variable will exists until exit our application.
If we do not have Lock() and Unlock, deadlock will occur.
Its gloable variable so anyone can access within this application.
6. Session State - Session state is similar to application state, except that it is scoped to the current browser session. Each user session will have a different session state. Session state is structured as a key/value dictionary for storing session-specific information.
Session.Add(itemName, itemValue);
Session.Remove();
A SessionID values are stored in a cookie or in the URL for a "cookieless" session.
<configuration>
<system.web>
<sessionState cookieless="true"
regenerateExpiredSessionId="true" />
</system.web>
</configuration>
Regenerating Expired Session Identifiers - The session ID values that are used in cookieless sessions are recycled. That is, if a request is made with a session ID that has expired, a new session is started by using the SessionID value that is supplied with the request. This can result in a session unintentionally being shared when a link that contains a cookieless SessionID value is used by multiple browsers.
CreateSessionID - To create custom session id
Session Modes
InProc mode - which stores session state in memory on the Web server. This is the default.
StateServer mode - which stores session state in a separate process called the ASP.NET state service. This ensures that session state is preserved if the Web application is restarted and also makes session state available to multiple Web servers in a Web farm.
To use StateServer mode, you must first be sure the ASP.NET state service is running on the server used for the session store. The ASP.NET state service is installed as a service when ASP.NET and the .NET Framework are installed. The ASP.Net state service is installed at the following location: systemroot\Microsoft.NET\Framework\versionNumber\aspnet_state.exe
SQLServer mode - stores session state in a SQL Server database. This ensures that session state is preserved if the Web application is restarted and also makes session state available to multiple Web servers in a Web farm.
Custom mode - which enables you to specify a custom storage provider.
<configuration>
<connectionStrings>
<add name="OdbcSessionServices"
connectionString="DSN=SessionState;" />
</connectionStrings>
<system.web>
<sessionState
mode="Custom"
customProvider="OdbcSessionProvider">
<providers>
<add name="OdbcSessionProvider"
type="Samples.AspNet.Session.OdbcSessionStateStore"
connectionStringName="OdbcSessionServices"
writeExceptionsToEventLog="false" />
</providers>
</sessionState>
</system.web>
</configuration>
Off mode - which disables session state.
Session Events - ASP.NET provides two events that help you manage user sessions.
The Session_OnStart event is raised when a new session starts.
the Session_OnEnd event is raised when a session is abandoned or expires.
Session events are specified in the Global.asax file for an ASP.NET application.
If the Global.asax file or Web.config file for an ASP.NET application is modified, the application will be restarted and any values stored in application state or session state will be lost.
The Session_OnEnd event is not supported if the session Mode property is set to a value other than InProc, which is the default mode.
Configuring Session State
<sessionState mode="SQLServer"
cookieless="true "
regenerateExpiredSessionId="true "
timeout="30"
sqlConnectionString="Data Source=MySqlServer;Integrated Security=SSPI;"
stateNetworkTimeout="30"/>
Advantages of using session state are: Platform scalability. Cookieless support, Extensibility - store custom data format,
Disadvantage of using session state are: Performance considerations Session-state variables stay in memory until they are either removed or replaced.
7. Profile Properties - similar to session state, except that the profile data is not lost when a user's session expires.
The profile-properties feature uses an ASP.NET profile, which is stored in a persistent format and associated with an individual user.
The ASP.NET profile allows you to easily manage user information without requiring you to create and maintain your own database.
The profile makes the user information available using a strongly typed API that you can access from anywhere in your application.
To use profile properties, you must configure a profile provider. ASP.NET includes a SqlProfileProvider class that allows you to store profile data in a SQL database, but you can also create your own profile provider class that stores profile data in a custom format and to a custom storage mechanism such as an XML file, or even to a web service.
Because data that is placed in profile properties is not stored in application memory, it is preserved through Internet Information Services (IIS) restarts and worker-process restarts without losing data. Profile properties can be persisted across multiple processes such as in a Web farm or a Web garden.
Advantages of using profile properties are: Data persistence
Platform scalability - can be used in both multi-computer and multi-process configurations
Extensibility - ASP.NET includes a SqlProfileProvider class, you can create custom
Disadvantages of using profile properties are:
Performance considerations - Slower than using session state because instead of storing data in memory, the data is persisted to a data store.
Additional configuration requirements -
Data maintenance
Securing the Session ID
Protect your application with Secure Sockets Layer (SSL).
Specify a smaller value for the session Timeout. - Response.AddHeader("Refresh", Session.Timeout + ";URL=Logoff.htm";
Avoid using cookieless sessions.
Avoid specifying cookie modes of AutoDetect and UseDeviceProfile.
Allow users to log out, at which point you should call theHttpSessionState.Abandon method. Warn the user to close his or her browser after logging out.
When using cookieless sessions, configure regenerateExpiredSessionID as true to always start a new session when an expired session identifier is supplied.
http://msdn.microsoft.com/en-us/library/75x4ha6s%28v=vs.100%29.aspx
No comments:
Post a Comment