I have observed the following feature when I rename a stored procedure.
sp_RENAME 'User_Validate', 'sp_UserValidate'
And when I do sp_helptext sp_UserValidate the procedure's name that i see is
CREATE PROCEDURE User_Validate
(#userEmail nvarchar(200),
#userPassword nvarchar(32))....
Why doesn't the name get updated in the stored procedure?
But when I check
select * from sys.procedures
I find the name field being updated? What's the reason behind it? The only logical conclusion I can draw is it's better to drop the procedure and recreate with a new name.
edit 1:
If I do sp_helptext User_Validate it returns "The object 'User_Validate' does not exist in database 'Process' or is invalid for this operation." But when I view the stored procedure the name User_Validate is still there.
Note: I know that renaming stored procedures is not a good practice, the question I asked is out of curiosity.
sp_helptext does not reverse engineer the procedure, it simply shows the original T-SQL batch that created the procedure, including comments and white spaces.
sp_rename is not recommended for renaming stored procedures, views, triggers, and user defined functions
Your conclusion is right, you should drop and re-create it with a new name. The same is stated in BOL - Rename a Stored Procedure
You should also check the dependencies of a stored procedure because renaming a stored procedure may cause dependent objects to fail if they are not updated to match the change
Hope this helps
Related
I'm doing investigation of code repo and find one thing that make me confused. SQL Server stored procedures are contained in a repo as a set of queries with following structure:
IF OBJECT_ID(N'[dbo].[sp_ProcTitle]', N'P') IS NULL
BEGIN
EXEC dbo.sp_executeSQL N'CREATE PROCEDURE [dbo].[sp_ProcTitle] AS dummy:;';
END
ALTER PROCEDURE dbo.sp_ProcTitle
#ParamOne int,
#ParamTwo date,
#ParamThree int
AS
SET NOCOUNT ON
-- some procedure body
END
Never before I saw AS dummy:; and now I'm a little confused, I can't find any good explanation what is it and how it works. Could anybody tell me what does it mean this statement? How it works? What is the reason to have it? Any thought would be good to hear. Or, please, advise me some link where I can find good explanation.
This is simply a label, such that could be used in a GOTO statement.
The word "dummy" is unimportant. It's simply trying to create the stored procedure if it doesn't exist, with a minimal amount of text. The content is then filled in with the ALTER.
Conceivably, the dummy text could later be searched for to see if any procedures were created and didn't have their content filled in, to check against failed deployments, etc.
Why do this? Well, it preserve the creation time of the stored procedure in metadata (which can be useful in administration or tracking down problems), and is compatible with versions of SQL Server that lack the CREATE OR ALTER... support.
This might make a little more sense if we add a little formatting to the CREATE:
CREATE PROCEDURE [dbo].[sp_ProcTitle]
AS
dummy:
This is, effectively, an empty procedure with a label called dummy. The user appears to be using this to ensure that the procedure exists first, and the ALTERing it. In older versions of SQL Server, such methods were needed because it didn't support CREATE OR ALTER syntax. As such, if you tried to ALTER a procedure that didn't exist the statement failed, and likewise if you try to CREATE a procedure that already exists it fails.
If you are on a recent version of SQL Server, I'd suggest changing to CREATE OR ALTER and getting rid of the call to sys.sp_executesql.
I encountered a strange problem today.... I did an sp_helptext on a stored procedure but the stored procedure name in the CREATE PROCEDURE statement (in the result) did not correspond to the name I used in the sp_helptext statement (see screenshot below). I tried selecting from the sys.all_sql_modules and also OBJECT_DEFINITION but it gave the same result.
In my example below I used InvIRCode_GetByInvIRID but the result gave me InvIRCode_GetListByInvIRID
I did a bit of research and it seems it is a known SQL Server bug and happens when a stored procedure was renamed.
My question is this: How can I get the correct source code for a stored procedure?
The interesting thing is that when I right-click on the sp in the Object Explorer of SQL Server Management Studio and select to script the procedure to a new window, it does give the correct code.
Note this warning message is returned by sp_rename:
Caution: Changing any part of an object name could break scripts and stored procedures.
The text in the catalog views is not changed by sp_rename. The proc name will be corrected when you script the proc via SSMS or SMO. You can alter (or drop/create) modules using that script to fix the text in the catalog views after a rename.
I have changed the name of a stored procedure in SQL Server using the GUI and it changed, but whenever I try to modify procedure code with sp_helptext, in the query editor, it was showing the old procedure name.
How to get rid of the problem?
It seems that this definition is being updated only when you run ALTER statement..
Do not use use sp_helptext for scripting!
If you want to modify the procedure code, use SSMS GUI: right click on procedure > alter to > new query.
Or use one the following to acquire the defition from T-SQL:
select object_definition(object_id('uspTestProc'))
select * from sys.sql_modules where object_id = object_id('uspTestProc')
Apart from the problem you're experiencing, in sp_help docs you can read about sp_help result: "Each row contains 255 characters of the Transact-SQL definition". This means that if you have lines longer than 255 character in procedure code, such line will be broken down into 255 char chunks. In best case scenario your code won't work, but if you're unlucky it will work and produce incorrect result, for example if some code that you had in a comment will be movde to new line and become uncommented.
Renaming Procedure names in SQL Server is not a good option as it does not update the procedure text.
Avoid renaming procedures and prefer DROP and CREATE.
The MS SQL Server version in question is 8.
In the context of database other than master if I call stored procedures from master database, for some of them I must append master.. prefix (otherwise I get Could not find stored procedure 'procname' error), for some of them I don't.
For example, I can call --
EXEC sp_addlogin 'user' 'pass';
-- and it works, but --
EXEC xp_cmdshell 'command';
-- doesn't. I have to prepend master.. for it to work --
EXEC master..xp_cmdshell 'command';
I may be wrong here but I observed that one have to add master.. to only those stored procedures that start with xp_ (as opposed to sp_).
Why do I have to call some of them with master.. prepended while some of them can be called without?
Procedures in the master database whose name begin with sp_ can be called in any other user database without having to add the master.. prefix. Since procedures beginning with xp_ don't follow that rule, you still need to add the master.. prefix when calling them.
See this link for more information.
The xp_ stands for extended stored procedures. They are stored in the master database.
The sp_ are for "special". They are Microsoft-shipped procedures that exist in every database. You can see them in the Object Explorer by going (Database Name) > Programmability > Stored Procedures > System Stored Procedures. Because they are in the same database as your query, you don't need to add master..
As a side note, it would be wise to NOT name your own stored procedures with sp_.... See explanation here.
So, not sure what is happening. But I have stored procedure and it keeps disappearing out of my DB in SQL 2k.
I can add it again and then try to execute it from my web app and i get an exception saying the stored procedure cant be found. So then ill go back to management and refresh and its gone again !?!
here is the config for the stored proc:
set ANSI_NULLS OFF
set QUOTED_IDENTIFIER ON
GO
ALTER PROCEDURE [dbo].[USP_Equipment_Delete]
#EquipmentID int
AS
DELETE FROM [dbo].[Equipment]
WHERE
[EquipmentID] = #EquipmentID
None of my other stored procedure disappear. This is the only one. I have easily 100 in there. They all use the same SQLHelper class. This one just keeps disappearing!!!??!!
Any help or suggestions are appreciated!
Thanks so much!
You were creating this or another stored proc and at the end of your code, maybe after a comment, where you did not see it you have a drop of this proc.
Take a look at your db using:
select syo.name
from syscomments syc
join sysobjects syo on
syo.id = syc.id
where syc.[text] like '%DROP PROC%'
I had the same problem and I just fixed it:
In the script file it was missing the "GO" statement between the end of the stored procedure and the beginning of the next "IF EXIST THEN DROP" statement.
So what happened was that the drop statement was getting appended to the end of whatever stored procedure was above it in the script. So when the software ran the stored procedure it would drop whatever stored procedure was below it in the script.
It seems so obvious to us now but didn't make any sense at the time. We found it running the SQL profiler against a customer's database that was having the problem in the field.
Are you using the correct database?
Try
using [database name]
prior to executing your stored procedure, just to make sure.
Do you have a CREATE PROCEDURE anywhere? You can't ALTER a procedure if it doesn't exist.
Perhaps the code to access the stored procedure is using a different context other than dbo. Make sure to add dbo.USP_Equipment_Delete to the code using it.
I was facing the problem that all Stored Procedures with a create statement disappeared from the database after execution.
The Solution was: The database user should have the rights to drop,create and alter on the database in which the "Stored Procedures" are going to be created.
Perhaps there's a job thats restoring an old backup periodically?
Check if the "Initial Catalog" in your connection string is set to the correct database.
Put the database in single user mode (and make sure you're the single user) and check if the procedure still disappears every hour?
If it's there, then this query must return a record:
SELECT * FROM sysobjects
WHERE id = OBJECT_ID('USP_Equipment_Delete')
AND OBJECTPROPERTY(id, N'IsProcedure') = 1