Category Archives: #SQLServer

All about Microsoft SQL Server

#0291 – SQL Server – sp_rename – Renaming SQL Server objects – Do’s and Dont’s


Renaming a SQL Server object is a fairly common operation when working with a product. Overtime, objects need to be enhanced as and when new features are introduced. One of the most frequently used mechanisms to rename objects is to use the system stored procedure: sp_rename.


However, this system stored procedure comes with a word of caution – it is not applicable to all SQL Server object types. Here’s an example:


Renaming a Column


To demonstrate the renaming of a column using sp_rename, let us first create a simple table with 2 columns:

USE tempdb;
GO

–Safety Check
IF OBJECT_ID(‘dbo.Student’,’U’) IS NOT NULL
DROP TABLE dbo.Student;
GO

–Create the test Table
CREATE TABLE dbo.Student (StudentId INT IDENTITY(1,1),
SchoolId INT,
CONSTRAINT pk_StudentId PRIMARY KEY CLUSTERED (StudentId)
);
GO


Let us now check the table properties:

USE tempdb;
GO

–Check the table values
SELECT sc.name,
sc.object_id,
sc.column_id
FROM sys.columns AS sc
WHERE sc.object_id = OBJECT_ID(‘dbo.Student’,’U’);
GO


image


Now, let us rename the column – SchoolId to EstablishmentId and check the table properties again.

USE tempdb;
GO

–Rename a column: SchoolId to EstablishmentId
sp_rename ‘dbo.Student.SchoolId’,’EstablishmentId’,’COLUMN’;
GO

–Check if the column has been renamed
SELECT sc.name,
sc.object_id,
sc.column_id
FROM sys.columns AS sc
WHERE sc.object_id = OBJECT_ID(‘dbo.Student’,’U’);
GO


image


As can be seen from the screenshot above, the column renaming was successful. Now, let us extend this example to rename a stored procedure.


Renaming a Stored Procedure


Using sp_rename




Let us first create a new stored procedure using the table created above.

USE tempdb;
GO

–Creat the test procedure
CREATE PROCEDURE dbo.proc_GetStudents
AS
BEGIN
SELECT s.StudentId,
s.EstablishmentId
FROM dbo.Student AS s;
END;
GO


Let us take a look at the object definition in the sql_modules:

USE tempdb;
GO

–Check the procedure properties
SELECT sm.object_id AS ObjectId,
OBJECT_NAME(sm.object_id) AS ProcedureName,
sm.definition AS ObjectDefinition
FROM sys.sql_modules AS sm;
GO


image


Now, let us rename the stored procedure using sp_rename and check the stored procedure properties.

USE tempdb;
GO

–Rename the procedure from proc_GetStudents to proc_GetAllStudents
sp_rename ‘proc_GetStudents’,’proc_GetAllStudents’,’OBJECT’;
GO

–Check the procedure properties
SELECT sm.object_id AS ObjectId,
OBJECT_NAME(sm.object_id) AS ProcedureName,
sm.definition AS ObjectDefinition
FROM sys.sql_modules AS sm;
GO


image


As can be seen from the screenshot above, SQL Server is left in a state of partial meta-data update. This is therefore, not the correct way to rename a stored procedure.


The Correct Way to Rename a Stored Procedure


The correct way to rename a stored procedure is to drop and recreate the object. To demonstrate this, let us re-create the stored procedure first.

USE tempdb;
GO

IF OBJECT_ID(‘dbo.proc_GetStudents’,’P’) IS NOT NULL
DROP PROCEDURE dbo.proc_GetStudents;
GO

IF OBJECT_ID(‘dbo.proc_GetAllStudents’,’P’) IS NOT NULL
DROP PROCEDURE dbo.proc_GetAllStudents;
GO

–Creat the test procedure
CREATE PROCEDURE dbo.proc_GetStudents
AS
BEGIN
SELECT s.StudentId,
s.EstablishmentId
FROM dbo.Student AS s;
END;
GO

–Check the procedure properties
SELECT sm.object_id AS ObjectId,
OBJECT_NAME(sm.object_id) AS ProcedureName,
sm.definition AS ObjectDefinition
FROM sys.sql_modules AS sm;
GO


image


Let us now drop and recreate the procedure:

USE tempdb;
GO

–Rename the procedure from proc_GetStudents to proc_GetAllStudents
IF OBJECT_ID(‘dbo.proc_GetStudents’,’P’) IS NOT NULL
DROP PROCEDURE dbo.proc_GetStudents;
GO
–Creat the test procedure
CREATE PROCEDURE dbo.proc_GetAllStudents
AS
BEGIN
SELECT s.StudentId,
s.EstablishmentId
FROM dbo.Student AS s;
END;
GO

–Check the procedure properties
SELECT sm.object_id AS ObjectId,
OBJECT_NAME(sm.object_id) AS ProcedureName,
sm.definition AS ObjectDefinition
FROM sys.sql_modules AS sm;
GO


image


As can be seen from the screenshot above, the stored procedure rename has now succeeded.


Conclusion


In conclusion, the following thumb rules can be established:



  • The sp_rename can be used to rename a column, database, index, statistics and/or user defined data types
  • The sp_rename can also be used to rename constraints (check, primary-key, foreign-key and unique-key), user tables and rules
  • The sp_rename should NOT be used for renaming stored procedures, functions, views and triggers. They MUST be dropped and recreated

Further Reading



Until we meet next time,


Be courteous. Drive responsibly.

#0291 – SQL Server – sp_rename – Renaming SQL Server objects – Do’s and Dont’s


Renaming a SQL Server object is a fairly common operation when working with a product. Overtime, objects need to be enhanced as and when new features are introduced. One of the most frequently used mechanisms to rename objects is to use the system stored procedure: sp_rename.


However, this system stored procedure comes with a word of caution – it is not applicable to all SQL Server object types. Here’s an example:


Renaming a Column


To demonstrate the renaming of a column using sp_rename, let us first create a simple table with 2 columns:

~~~USE tempdb;
GO

–Safety Check
IF OBJECT_ID(‘dbo.Student’,’U’) IS NOT NULL
DROP TABLE dbo.Student;
GO

–Create the test Table
CREATE TABLE dbo.Student (StudentId INT IDENTITY(1,1),
SchoolId INT,
CONSTRAINT pk_StudentId PRIMARY KEY CLUSTERED (StudentId)
);
GO~~~

Let us now check the table properties:

~~~USE tempdb;
GO

–Check the table values
SELECT sc.name,
sc.object_id,
sc.column_id
FROM sys.columns AS sc
WHERE sc.object_id = OBJECT_ID(‘dbo.Student’,’U’);
GO~~~

image


Now, let us rename the column – SchoolId to EstablishmentId and check the table properties again.

~~~USE tempdb;
GO

–Rename a column: SchoolId to EstablishmentId
sp_rename ‘dbo.Student.SchoolId’,’EstablishmentId’,’COLUMN’;
GO

–Check if the column has been renamed
SELECT sc.name,
sc.object_id,
sc.column_id
FROM sys.columns AS sc
WHERE sc.object_id = OBJECT_ID(‘dbo.Student’,’U’);
GO~~~

image


As can be seen from the screenshot above, the column renaming was successful. Now, let us extend this example to rename a stored procedure.


Renaming a Stored Procedure


Using sp_rename




Let us first create a new stored procedure using the table created above.

~~~USE tempdb;
GO

–Creat the test procedure
CREATE PROCEDURE dbo.proc_GetStudents
AS
BEGIN
SELECT s.StudentId,
s.EstablishmentId
FROM dbo.Student AS s;
END;
GO~~~

Let us take a look at the object definition in the sql_modules:

~~~USE tempdb;
GO

–Check the procedure properties
SELECT sm.object_id AS ObjectId,
OBJECT_NAME(sm.object_id) AS ProcedureName,
sm.definition AS ObjectDefinition
FROM sys.sql_modules AS sm;
GO~~~

image


Now, let us rename the stored procedure using sp_rename and check the stored procedure properties.

~~~USE tempdb;
GO

–Rename the procedure from proc_GetStudents to proc_GetAllStudents
sp_rename ‘proc_GetStudents’,’proc_GetAllStudents’,’OBJECT’;
GO

–Check the procedure properties
SELECT sm.object_id AS ObjectId,
OBJECT_NAME(sm.object_id) AS ProcedureName,
sm.definition AS ObjectDefinition
FROM sys.sql_modules AS sm;
GO~~~

image


As can be seen from the screenshot above, SQL Server is left in a state of partial meta-data update. This is therefore, not the correct way to rename a stored procedure.


The Correct Way to Rename a Stored Procedure


The correct way to rename a stored procedure is to drop and recreate the object. To demonstrate this, let us re-create the stored procedure first.

~~~USE tempdb;
GO

IF OBJECT_ID(‘dbo.proc_GetStudents’,’P’) IS NOT NULL
DROP PROCEDURE dbo.proc_GetStudents;
GO

IF OBJECT_ID(‘dbo.proc_GetAllStudents’,’P’) IS NOT NULL
DROP PROCEDURE dbo.proc_GetAllStudents;
GO

–Creat the test procedure
CREATE PROCEDURE dbo.proc_GetStudents
AS
BEGIN
SELECT s.StudentId,
s.EstablishmentId
FROM dbo.Student AS s;
END;
GO

–Check the procedure properties
SELECT sm.object_id AS ObjectId,
OBJECT_NAME(sm.object_id) AS ProcedureName,
sm.definition AS ObjectDefinition
FROM sys.sql_modules AS sm;
GO~~~

image


Let us now drop and recreate the procedure:

~~~USE tempdb;
GO

–Rename the procedure from proc_GetStudents to proc_GetAllStudents
IF OBJECT_ID(‘dbo.proc_GetStudents’,’P’) IS NOT NULL
DROP PROCEDURE dbo.proc_GetStudents;
GO
–Creat the test procedure
CREATE PROCEDURE dbo.proc_GetAllStudents
AS
BEGIN
SELECT s.StudentId,
s.EstablishmentId
FROM dbo.Student AS s;
END;
GO

–Check the procedure properties
SELECT sm.object_id AS ObjectId,
OBJECT_NAME(sm.object_id) AS ProcedureName,
sm.definition AS ObjectDefinition
FROM sys.sql_modules AS sm;
GO~~~

image


As can be seen from the screenshot above, the stored procedure rename has now succeeded.


Conclusion


In conclusion, the following thumb rules can be established:



  • The sp_rename can be used to rename a column, database, index, statistics and/or user defined data types
  • The sp_rename can also be used to rename constraints (check, primary-key, foreign-key and unique-key), user tables and rules
  • The sp_rename should NOT be used for renaming stored procedures, functions, views and triggers. They MUST be dropped and recreated

Further Reading



Until we meet next time,


Be courteous. Drive responsibly.

#0290 – SQL Server – How to get the IP address associated with a connection and of the server using DMVs


Helping people on the various forums gives me a great sense of satisfaction. Recently, I was looking going through the unanswered questions section in the Ask module of this site, when I stumbled across a very interesting question:



How to get the IP address associated to the SQL Server without the use of xp_cmdshell?


Now, the solution that I am going to present today is a way of getting the client connection and SQL server IP address using DMVs. I myself have never used this in production, because all of our servers are on static IPs, so we knew and planned the IPs even before the systems were ever built. Hence, if you notice any obvious flaws in this approach, please feel free to discuss them in the comments section below.


You can customize the script provided below as per your need. Basically, you need to connect to your instance of SQL Server with a user having VIEW SERVER STATE rights (required by the DMV) and simply run the script.

USE tempdb;
GO
SELECT sec.client_net_address,
sec.client_tcp_port,
sec.local_net_address,
sec.local_tcp_port,
st.text,
ses.session_id,
ses.login_time,
ses.original_login_name,
ses.nt_domain,
ses.nt_user_name,
ses.host_name,
ses.program_name,
ses.host_process_id,
ses.client_version,
ses.client_interface_name,
ses.ansi_defaults,
ses.ansi_null_dflt_on,
ses.ansi_nulls,
ses.ansi_padding,
ses.ansi_warnings,
ses.arithabort,
ses.open_transaction_count,
ses.concat_null_yields_null,
ses.transaction_isolation_level,
ses.lock_timeout
FROM sys.dm_exec_sessions AS ses
INNER JOIN sys.dm_exec_connections AS sec ON ses.session_id = sec.session_id
INNER JOIN sys.dm_exec_requests AS ser ON sec.connection_id = ser.connection_id
CROSS APPLY sys.dm_exec_sql_text(ser.plan_handle) AS st
WHERE ses.is_user_process = 1;
GO

The output looks similar to the one shown in the screen-shot below:


image


The columns of interest are:



  • client_net_address = IP address of the client who established the connection
  • client_tcp_post = TCP Port number over which the client established the connection
  • local_net_address = Represents the IP address on the server that this connection targeted
  • local_tcp_port = Represents the Server TCP port that the connection targetted

Please note: The IP addresses and port information will only be available in case of TCP/IP connections. Shared Memory and Named Pipes do not use IP addresses to establish the connection.


Further Reading



  • sys.dm_exec_connections [Link]

Until we meet next time,



Be courteous. Drive responsibly.

#0289 – SQL Server – Deprecated features – Numbered Stored Procedures


Throughout my years of work in the IT industry, I have learnt that hanging around in the forums is always a learning experience. Recently, I was looking for a bit of a challenge and went to the unanswered questions section in the Ask module of this site. I stumbled across this question.

The Question

The person who posted the query had inherited a 3rd party database where he found three (3) different stored procedures with the same schema, same name, but with different functionality. However counter-intuitive it may seem, it’s quite possible. Try it out for yourself by using the script shown below:

USE tempdb;
GO

IF OBJECT_ID('dbo.proc_ManipulateNumbers','P') IS NOT NULL
    DROP PROCEDURE dbo.proc_ManipulateNumbers;
GO

--SP #1 - Addition
CREATE PROCEDURE dbo.proc_ManipulateNumbers; 1 
    @iA INT,
    @iB INT
AS
BEGIN
    SET NOCOUNT ON;
    SELECT @@PROCID AS ProcedureId,
           'SP #1 - (@iA + @iB) = ' AS Operation, 
           (@iA + @iB) AS Value;
END
GO

--SP #2 - Multiplication
CREATE PROCEDURE dbo.proc_ManipulateNumbers; 2
    @iA INT,
    @iB INT
AS
BEGIN
    SET NOCOUNT ON;
    SELECT @@PROCID AS ProcedureId, 
           'SP #2 - (@iA * @iB) = ' AS Operation, 
           (@iA * @iB) AS Value;
END
GO

--SP #3 - Division
CREATE PROCEDURE dbo.proc_ManipulateNumbers; 3 
    @iA INT,
    @iB INT
AS
BEGIN
    SET NOCOUNT ON;
    SELECT @@PROCID AS ProcedureId,
           'SP #3 - (@iA / @iB) = ' AS Operation,
           (@iA / @iB) AS Value;
END
GO

/************** The Test *****************/
--Run the first procedure
EXEC dbo.proc_ManipulateNumbers;1 @iA = 10, @iB = 2;
GO

--Run the second procedure
EXEC dbo.proc_ManipulateNumbers;2 @iA = 10, @iB = 2;
GO

--Run the third procedure
EXEC dbo.proc_ManipulateNumbers;3 @iA = 10, @iB = 2;
GO

--Check the ObjectId of the procedure
SELECT OBJECT_ID('dbo.proc_ManipulateNumbers','P') AS ProcedureObjectId;
GO

If you run the script provided above, this is what you would find as the output:

image

The output tells us that we have three stored procedures with the same schema, same name, same ObjectId, but different functionality – one adds two numbers whereas the others either multiply or divide them.

(If you are getting a headache by looking at the output, a sip of coffee might help)

The question therefore is:

How is it possible to have multiple stored procedures with different logic, but the same name?

How can the same ObjectId be assigned to all these mysterious procedures?

Numbered Stored Procedures – The Answer

The answer resides in a little known feature of SQL Server – numbered stored procedures.

Notice the use of semi-colon (;) followed by a number in the CREATE PROCEDURE statement. The semi-colon is not used as a statement terminator here, but is used to indicate that the definition is actually a different version of a stored procedure with the same name and should be grouped together.

When attempting to access these procedures, all one needs to do is again use the semi-colon (;) followed by the stored procedure version number. Hence, when we execute the following, SQL Server knows to use version #2, i.e. the one where supplied inputs are multiplied.

--Run the second procedure
EXEC dbo.proc_ManipulateNumbers;2 @iA = 10, @iB = 2;
GO

Because they share the same objectId, they can be dropped with a single DROP PROCEDURE statement.

WARNING!

Per Books-On-Line, “This feature will be removed in a future version of Microsoft SQL Server. Avoid using this feature in new development work, and plan to modify applications that currently use this feature.

Hence, while as interesting as this feature may sound, please avoid using this feature in new development work. Also, as versions move along, start moving away from this implementation.

Further Reading:

  • Semi-colon as a statement terminator [Link]
  • CREATE PROCEDURE statement [Link]

I had never heard of numbered stored procedure before encountering the mentioned Ask post. Had you heard about this in the past? Have you ever used numbered stored procedures? Why? Do let me know.

Until we meet next time,

Be courteous. Drive responsibly.

#0288 – SQL Server – How To test database server connectivity without SSMS, SQLCMD or other applications


I am sure that many of my readers will be able to co-relate with the situation in today’s post.


We recently faced a situation at the office where one of our application servers was unable to communicate to the database server – the servers could “ping” each other just fine, but the SQL Server was inaccessible. While there were indications of connectivity being an issue, we did not have any definitive proof. The IT administrator continued to maintain that the server has been configured in the same way as all our other application servers were. We were therefore required to come up with a mechanism to test connectivity from the application server to the database server without the use of SSMS, SQLCMD (being the application server, it didn’t have any SQL client components installed) or any other applications. We had to use something that is shipped with the operating system.


Universal Data Link (UDL) file


Creation and Basic Configuration


The Microsoft Data Access Components (MDAC) provide the Data Link Properties dialog box as the common user interface for specifying connection information to a data provider on Windows 2000 and later operating systems. One can use the Data Link Properties dialog box to save connection information in a universal data link (.udl) file. We will be using this *.udl file to configure the most common connection string parameters and then help us test the connectivity to our database server.



















1. On the desktop, or any other folder, right-click and create a new Text document
2. Rename the newly created file to “Test Database Connectivity.udl” (you can have the file name of your choice, the extension has to be .udl)
3. Double-click the file to open the “Data Link Properties” dialog box
4. In the “Provider” tab, choose the appropriate provider in use by the application
image
5. Provide the connection information in the “Connection” tab
image
6. You can define the connection timeout value in the “Advanced” tab
image
7. Other connection properties can be defined in the “All” tab
image
8. Click “OK” to save the data link information into the UDL file






Advanced Editing


Under the covers, the UDL file is nothing but a connection string stored in plain text. For seasoned administrators, the UDL file can therefore be opened in NOTEPAD where advanced connection string parameters can be defined by simply editing the connection string.


Shown below is the information from the UDL file we just defined above:


[oledb]
; Everything after this line is an OLE DB initstring
Provider=SQLNCLI11.1;Integrated Security=SSPI;Persist Security Info=False;User ID=””;Initial Catalog=AdventureWorks2012;Data Source=W8SQLSERVERSQL2K12;Application Name=My Test Application;Initial File Name=””;Server SPN=””


image


Testing connectivity using the UDL file


Once the connection string definition in the UDL file has been finalized, one needs to double-click on the UDL file in the Windows explorer again to launch the “Data Link Properties” window.


To test the connection, we need to navigate out to the “Connection” tab and simply click “Test Connection” – If the connection succeeds, the underlying hardware, firewall and other configuration is as required.


image



Summary


The UDL file method of testing connection strings is not new. Yet, it is often forgotten as being one of the most easiest ways to test SQL Server connectivity. I would like to hear from you regarding the methods you use for testing connection strings when no SSMS, SQLCMD or other tools/applications are available at your disposal.


Further Reading:



  • Testing Connection Strings using SSMS [Link]

Until we meet next time,



Be courteous. Drive responsibly.