Category Archives: #SQLServer

All about Microsoft SQL Server

#0247-SQL Server – sp_refreshview – Refresh metadata for non-schema bound view


Database objects often undergo changes to their structure over the life-cycle of the product. These changes include, but are not limited to, the addition and removal of columns and parameters. Whenever such changes are made, the meta-data for any dependent database objects also needs to be updated if they are not schema-bound. Here’s a small example.

Let us create a data view on the HumanResources.Employee table as shown below:

USE AdventureWorks2012 ;
GO

--Create a non-schema bound view for the HumanResources.Employee table
CREATE VIEW HumanResources.uview_Employee
AS  SELECT  he.*
    FROM    HumanResources.Employee AS he ;
GO

--Select data from the data-view
SELECT  TOP 1 *
FROM    HumanResources.uview_Employee ;
GO

image

Now, let us add a column to the HumanResources.Employee table. This would be a common scenario is a service release – as new functionality gets introduced to the system, tables are modified to accommodate to the changes.

USE AdventureWorks2012 ;
GO
--Add a dummy column to the underlying table
ALTER TABLE HumanResources.Employee
ADD ExternalReferenceNumber VARCHAR(20);
GO

--Add some default data to the table
UPDATE HumanResources.Employee
SET ExternalReferenceNumber = ('EXT' + CAST(BusinessEntityID AS VARCHAR(10)));
GO

Because the data view has been created using a SELECT * clause, one would assume that the newly added column will be available in the results. Let us execute the view to confirm this assumption:

USE AdventureWorks2012 ;
GO
--Select data from the data-view
--Notice that the newly added column is not available
SELECT  TOP 1 BusinessEntityID, ExternalReferenceNumber
FROM    HumanResources.uview_Employee ;
GO

Msg 207, Level 16, State 1, Line 3

Invalid column name ‘ExternalReferenceNumber’.

As can be seen from the message above, the newly added column is in fact NOT included in the results. This is because the view is not schema-bound and the underlying meta-data is not yet updated.

To explicitly refresh the view meta-data (in cases where the view cannot be rebuilt), a system stored procedure sp_refreshview needs be used.

--Now, execute sp_refreshview
EXEC sp_refreshview N'HumanResources.uview_Employee' ;
GO

Now, let us attempt to select data from the view again:

--Select data from the data-view
--Notice that the newly added column is now available
SELECT  TOP 1 BusinessEntityID, ExternalReferenceNumber
FROM    HumanResources.uview_Employee ;
GO

image

As can be seen from the screenshot above, the newly added column is now available in the results of the view.

A word of caution

While this particular example uses SELECT * in the view definition for demonstration purposes, it is recommended to always define the columns explicitly. Explicitly defining columns required will cause errors if a column is dropped and will prevent any unexpected behavior if new columns are added. Alternatively, schema binding can be used.

Until we meet next time,

Be courteous. Drive responsibly.

#0246 – SQL Server 2012 – FileStream and FileTable related DMVs and Catalog Views


SQL Server Catalog Views & Dynamic Management Views (DMVs) take an administrator to the very heart of SQL Server. DMVs expose vital diagnostic information which are not only useful to indicate the overall health of the SQL Server, but also of the databases hosted by the given SQL Server instance. The list of DMVs that changed in SQL Server 2008 R2/2012 is available in one of my previous posts here: http://bit.ly/XobXup.


The storage of large object data like images, videos and other such non-relational objects in a relational databases has always been challenging. The biggest of these challenges come in the form of controlling the size of the transactions, storage and also the performance. Storing these object types on the file system overcomes these issues, but fails to provide basic data integrity and other management features that databases provide. Microsoft SQL Server 2008 introduced a new concept called FileStream which allows the SQL Server to work with large object data directly from the file-system in a transparent fashion.


A complete list of the FileStream and FileTable related DMVs and Functions is available at the link below:



  • FileStream and FileTable Catalog Views (Link)
  • FileStream and FileTable Dynamic Management Views (Link)

Let us first take a look at the newly introduced FileStream and FileTable related catalog views first.


Catalog Views


sys.database_filestream_options


Introduced In: SQL Server 2012


Purpose: For each database hosted on the given SQL Server instance, this catalog view contains one record showing the level of non-transactional access to FILESTREAM data in FileTables that is enabled by the administrator.

SELECT database_id AS DatabaseId,
DB_NAME(database_id) AS DatabaseName,
non_transacted_access AS NonTransactedAccessEnum,
non_transacted_access_desc AS NonTransactedAccessDescription
FROM sys.database_filestream_options
WHERE database_id <> 32767;

Permissions: Visibility is limited to securables that the user owns or has been granted permission to.


BOL Link: http://msdn.microsoft.com/en-us/library/gg492071.aspx


sys.filetables


Introduced In: SQL Server 2012


Purpose: Returns a record for each FileTable in SQL Server 2012.

SELECT object_id,
is_enabled,
directory_name,
filename_collation_id,
filename_collation_name
FROM sys.filetables;

Permissions: Visibility is limited to securables that the user owns or has been granted permission to.


BOL Link: http://msdn.microsoft.com/en-us/library/gg492214.aspx


sys.filetable_system_defined_objects


Introduced In: SQL Server 2012


Purpose: When file tables are created, objects such as constraints and indexes are also created. This catalog view provides a list of all the system defined objects that are related to FileTables.

SELECT object_id,
parent_object_id
FROM sys.filetable_system_defined_objects;

Permissions: Visibility is limited to securables that the user owns or has been granted permission to.


BOL Link: http://msdn.microsoft.com/en-us/library/gg492092.aspx


Dynamic Management Views


sys.dm_filestream_non_transacted_handles


Introduced In: SQL Server 2012


Purpose: This DMV displays one row per currently open non-transactional file handle associated with FileTable data.


Permissions: No documentation available on BOL


BOL Link: http://msdn.microsoft.com/en-us/library/ff929168.aspx


Further Reading



  • The Art of SQL Server FILESTREAM [Amazon.com, book by Jacob Sebastian & Sven Aelterman – Link]
  • FILESTREAM Wait Types [Link]
  • Working with FileTables in SQL Server 2012 – Part 01 [Link]
  • Working with FileTables in SQL Server 2012 – Part 02 [Link]

Until we meet next time,


Be courteous. Drive responsibly.

#0245-SQL Server-CREATE DATABASE…ATTACH_REBUILD_LOG resets database recovery mode to SIMPLE


Today’s post is based on a conversation I had a while back with a colleague. They had received a database with pre-populated test data for use in their quality assurance environments. Because they had only received the data files, I had suggested them to use the ATTACH_REBUILD_LOG option of the CREATE DATABASE statement to rebuild the transaction log from scratch (Link). The conversation below took place the next day.

John: Thank-you for your help last night with the ATTACH_REBUILD_LOG option – we were able to successfully attach the database to our server and begin testing. However, I noticed something that appears to be an issue with SQL Server. When would you have a moment to discuss?

Me: You are welcome! While I do not see any obvious issues with the CREATE DATABASE statement in this scenario, it will be interesting to see if something is indeed broken. Let’s meet after lunch to discuss.

Just after lunch…

John: Thank-you for taking some time out to help clear my doubts. Let me first create a sample database, and check it’s recovery model.

--Step 01: Create a test database
USE master;
GO
CREATE DATABASE RecoveryModelTesting
ON PRIMARY (NAME = RecoveryModelTesting_Data,
            FILENAME='C:SQLDBsDataRecoveryModelTesting_Data.mdf')
LOG ON (NAME = RecoveryModelTesting_Log,
        FILENAME='C:SQLDBsLogsRecoveryModelTesting_Log.ldf');
GO
--Step 02: Check the recovery model of the database
USE RecoveryModelTesting;
GO
SELECT recovery_model, recovery_model_desc, name
FROM sys.databases
WHERE name = 'RecoveryModelTesting' OR name = 'model';
GO
/************************************************
Output
************************************************/
/*
recovery_model recovery_model_desc name
1 FULL model
1 FULL RecoveryModelTesting
*/

John: Notice that the recovery model for our test database is by default set to FULL, which is same as the model database. Now, allow me to detach the database and delete the transaction log file. We believe that this is the same process that was used to provide the database to us yesterday.

USE master;
GO
EXEC sp_detach_db @dbname = 'RecoveryModelTesting';
GO

John: Now that the database has been closed and detached from the SQL Server instance, let me delete the log file so that we can rebuild it when we CREATE the database using the ATTACH_REBUILD_LOG option.

image

(The screen-shot above is shows that the log file has been deleted by John.)

Me: So, the next step will now be to use the CREATE DATABASE statement with the ATTACH_REBUILD_LOG option just as you did yesterday, right?

John: That is correct. Let me attach the database by creating a new log file.

USE [master]
GO
CREATE DATABASE [RecoveryModelTesting]
ON  PRIMARY ( NAME = N'RecoveryModelTesting_Data',
              FILENAME = N'C:SQLDBsDataRecoveryModelTesting_Data.mdf')
FOR ATTACH_REBUILD_LOG
GO
/************************************************
Output
************************************************/
/*
File activation failure. The physical file name "C:SQLDBsLogsRecoveryModelTesting_Log.ldf" may be incorrect.
New log file 'C:SQLDBsDataRecoveryModelTesting_log.ldf' was created.
*/

John: Now, let me check the recovery model of the database.

USE RecoveryModelTesting;
GO
SELECT recovery_model, recovery_model_desc, name
FROM sys.databases
WHERE name = 'RecoveryModelTesting';
GO
/************************************************
Output
************************************************/
/*
recovery_model   recovery_model_desc    name
1                FULL                   model
3                SIMPLE                 RecoveryModelTesting
*/

John: This is where I get confused. Why did the recovery model of the database reset to SIMPLE when the recovery model of the “model” database is FULL?

Me: It is indeed a very interesting observation, John. Before I answer your question, I would like you to answer mine – What is the primary purpose of the transaction log?

John: To recover a database to a point in time in case something goes wrong.

Me: Correct. The log can only recover from the point in time it was created, and not to anytime before. In this case, the transaction log file was recreated when we used the CREATE DATABASE statement with the ATTACH_REBUILD_LOG option because the database did not come with a log file. Because the database log file has just been created, the recovery model is set to the simplest of all – the SIMPLE recovery model. The user can then manually choose the correct recovery model according to the requirement.

John: But, can’t SQL Server attempt to come close to the original recovery model?

Me: First of all, generally data files would be coming from a 3rd party (a vendor, or a completely different server). Therefore, there is no way of the system knowing the previous recovery model of the database.

Secondly, setting the recovery model to whatever is dictated by the model database might be too excessive. Let’s assume that the model database follows the FULL recovery model. In case the database is being attached is for reference or for read-only purposes, setting to FULL may not be required. Hence, it is always better to start off from the simplest – the SIMPLE recovery model and then allow the user to configure the recovery model to suit the purpose.

John: Now it makes complete sense. Thank-you very much for your time!

Me: I am glad I could help. Have a good afternoon!

Until we meet next time,

Be courteous. Drive responsibly.

#0245-SQL Server-CREATE DATABASE…ATTACH_REBUILD_LOG resets database recovery mode to SIMPLE


Today’s post is based on a conversation I had a while back with a colleague. They had received a database with pre-populated test data for use in their quality assurance environments. Because they had only received the data files, I had suggested them to use the ATTACH_REBUILD_LOG option of the CREATE DATABASE statement to rebuild the transaction log from scratch (Link). The conversation below took place the next day.


John: Thank-you for your help last night with the ATTACH_REBUILD_LOG option – we were able to successfully attach the database to our server and begin testing. However, I noticed something that appears to be an issue with SQL Server. When would you have a moment to discuss?


Me: You are welcome! While I do not see any obvious issues with the CREATE DATABASE statement in this scenario, it will be interesting to see if something is indeed broken. Let’s meet after lunch to discuss.


Just after lunch…


John: Thank-you for taking some time out to help clear my doubts. Let me first create a sample database, and check it’s recovery model.

~~~–Step 01: Create a test database
USE master;
GO
CREATE DATABASE RecoveryModelTesting
ON PRIMARY (NAME = RecoveryModelTesting_Data,
FILENAME=’C:SQLDBsDataRecoveryModelTesting_Data.mdf’)
LOG ON (NAME = RecoveryModelTesting_Log,
FILENAME=’C:SQLDBsLogsRecoveryModelTesting_Log.ldf’);
GO

–Step 02: Check the recovery model of the database
USE RecoveryModelTesting;
GO
SELECT recovery_model, recovery_model_desc, name
FROM sys.databases
WHERE name = ‘RecoveryModelTesting’ OR name = ‘model’;
GO
/************************************************
Output
************************************************/
/*
recovery_model recovery_model_desc name
1 FULL model
1 FULL RecoveryModelTesting
*/~~~

John: Notice that the recovery model for our test database is by default set to FULL, which is same as the model database. Now, allow me to detach the database and delete the transaction log file. We believe that this is the same process that was used to provide the database to us yesterday.

~~~USE master;
GO
EXEC sp_detach_db @dbname = ‘RecoveryModelTesting’;
GO~~~

John: Now that the database has been closed and detached from the SQL Server instance, let me delete the log file so that we can rebuild it when we CREATE the database using the ATTACH_REBUILD_LOG option.


image


(The screen-shot above is shows that the log file has been deleted by John.)


Me: So, the next step will now be to use the CREATE DATABASE statement with the ATTACH_REBUILD_LOG option just as you did yesterday, right?


John: That is correct. Let me attach the database by creating a new log file.

~~~USE [master]
GO
CREATE DATABASE [RecoveryModelTesting]
ON PRIMARY ( NAME = N’RecoveryModelTesting_Data’,
FILENAME = N’C:SQLDBsDataRecoveryModelTesting_Data.mdf’)
FOR ATTACH_REBUILD_LOG
GO
/************************************************
Output
************************************************/
/*
File activation failure. The physical file name “C:SQLDBsLogsRecoveryModelTesting_Log.ldf” may be incorrect.
New log file ‘C:SQLDBsDataRecoveryModelTesting_log.ldf’ was created.
*/~~~

John: Now, let me check the recovery model of the database.

~~~USE RecoveryModelTesting;
GO
SELECT recovery_model, recovery_model_desc, name
FROM sys.databases
WHERE name = ‘RecoveryModelTesting’;
GO
/************************************************
Output
************************************************/
/*
recovery_model recovery_model_desc name
1 FULL model
3 SIMPLE RecoveryModelTesting
*/~~~

John: This is where I get confused. Why did the recovery model of the database reset to SIMPLE when the recovery model of the “model” database is FULL?


Me: It is indeed a very interesting observation, John. Before I answer your question, I would like you to answer mine – What is the primary purpose of the transaction log?


John: To recover a database to a point in time in case something goes wrong.


Me: Correct. The log can only recover from the point in time it was created, and not to anytime before. In this case, the transaction log file was recreated when we used the CREATE DATABASE statement with the ATTACH_REBUILD_LOG option because the database did not come with a log file. Because the database log file has just been created, the recovery model is set to the simplest of all – the SIMPLE recovery model. The user can then manually choose the correct recovery model according to the requirement.


John: But, can’t SQL Server attempt to come close to the original recovery model?


Me: First of all, generally data files would be coming from a 3rd party (a vendor, or a completely different server). Therefore, there is no way of the system knowing the previous recovery model of the database.


Secondly, setting the recovery model to whatever is dictated by the model database might be too excessive. Let’s assume that the model database follows the FULL recovery model. In case the database is being attached is for reference or for read-only purposes, setting to FULL may not be required. Hence, it is always better to start off from the simplest – the SIMPLE recovery model and then allow the user to configure the recovery model to suit the purpose.


John: Now it makes complete sense. Thank-you very much for your time!


Me: I am glad I could help. Have a good afternoon!


Until we meet next time,


Be courteous. Drive responsibly.

#0244 – SQL Server 2012 – Resource Governor DMVs & Catalog Views – sys.dm_resource_*


SQL Server Catalog Views & Dynamic Management Views (DMVs) take an administrator to the very heart of SQL Server. DMVs expose vital diagnostic information which are not only useful to indicate the overall health of the SQL Server, but also of the databases hosted by the given SQL Server instance. The list of DMVs that changed in SQL Server 2008 R2/2012 is available in one of my previous posts here: http://bit.ly/XobXup.

Before SQL Server 2008, there was no mechanism available within SQL Server to assign different resource “quota” to different components in order to better govern the resource utilization. Microsoft SQL Server 2008 introduced a new feature called “Resource Governor” which allows administrators to regulate (or govern) the CPU and memory consumption patterns for the given SQL Server instance. For a brief introduction to the resource governor, you can get a quick overview from Pinal Dave, a.k.a SQLAuthority (B|T) at SqlAuthority.com or the white-paper from Microsoft.

A complete list of the resource governor related DMVs and Catalog Views is available at:

  • Resource Governor DMVs (Link)
  • Resource Governor Catalog Views (Link)

Resource pools represent the physical resources available to the given SQL Server instance. Starting SQL Server 2012, resource pools can be affinitized to one or more schedules or NUMA nodes giving better isolation of the resources. The following new catalog view and DMV track the resource pool affinity:

  • New Catalog View: sys.resource_governor_resource_pool_affinity
  • New DMV: sys.dm_resource_governor_resource_pool_affinity (Link)

The above are not only similar sounding, but also appear to be similar in functionality as well (why this would be the case, I do not know – it looks like a bug to me).

The query below shows the usage and the screen-shot shows a sample result:

SELECT * FROM sys.resource_governor_resource_pool_affinity;
SELECT * FROM sys.dm_resource_governor_resource_pool_affinity;

image

Until we meet next time,

Be courteous. Drive responsibly.