I am trying to retrieve employeeIDs using the following sql script:
SELECT * from tblEmployees
GO
CREATE PROCEDURE spGetEmployeeID10
AS
BEGIN
SELECT employeeID
FROM tblEmployees
END
The script runs but returns the entire table with all of the columns' names: employeeID, lastName, firstName, Comment. However, it should only return the employeeID column, no? Am I making an obvious mistake? I am using SQL server management studio 2014. Also, whenever I modify a script and try to re-run it again, I get an error saying that the script already exits. Is there a way to simply edit the script and re-run it with the same name?
Thank you!
"Am I making an obvious mistake?" yes, I'm afraid so, the first select statement is returning everything, an the second is creating a stored procedure. My best guess is that you want this:
CREATE PROCEDURE spGetEmployeeID10
AS
BEGIN
SELECT employeeID
FROM tblEmployees
--my guesswork come further and I added next line
where employeeID = 10
END
GO
EXEC spGetEmployeeID10
GO
What you have is two different operations going on.
The first is your select * which will return everything. The second is the stored procedure creation, which will not return anything. That is why you are seeing the select * results and not the results that are in the stored procedure query.
Related
I am inside a SQLScript procedure and would like to return the last SQL Statement from this procedure, like the last rowcount:
/********* Begin Procedure Script ************/
BEGIN
select 1 as "my_data" from dummy;
select '::last_SQL' as "last executed sql" from dummy;
select ::ROWCOUNT as "rowcount" from dummy;
END;
/********* End Procedure Script ************/
The column "last executed SQL" should be populated with select 1 as "my_data" from dummy in this case. Is there any variable holding the last statement (or any easy way to retrieve the query plan)?
Maybe you can query sys.m_sql_plan_cache system view
Please check following SELECT statement
select
statement_string, last_execution_timestamp
from SYS.M_SQL_PLAN_CACHE
where user_name = 'KODYAZ'
order by last_execution_timestamp desc;
I believe you can improve the query by introducing new filter criteria.
There is no way to programmatically get the last executed SQL statement in SQLScript. This is due to the fact that not all statements will be executed in the form and order as they appear in the source code.
If you want to analyse the performance of a procedure, you can run PlanViz against the procedure call. Generally, there is no such thing as "the performance of a procedure/function" as they always occur in a specific context.
If used within a SQL query, things like query-transformation can radically change the way certain results are computed.
I have written a parameterized transact SQL query for a member of our finance department and several times during the month I run it and copy the raw output with headers into excel for him. Now that department is being regionalised and I've got several finance departments all wanting the same thing.
I know that SSRS will be deployed eventually but our infrastructure team are building a new environment and don't want any new installations in the 'old world' for the moment.
I just need a way to give select individuals access to run that parameterized query against the database. I had thought about turning the query into a view and creating logins for their network accounts with access only to that view but I don't think you can use parameters with views. I wondered if there is a simple interface that can allow them to enter parameters against a stored query or view without using SSRS. It seems so simple but I'm not having much luck finding out.
Sorry if this is a stupid question but I've just moved from server admin to a DBA role and I've only just scratched the surface!
Create a view and called that in SP with Parameter:-
Sample would be
Create View [dbo].[vw_sampleView]
AS
BEGIN
SELECT * FROM tblSample
END
CREATE PROC [dbo].[proc_GetData]
#id int
AS
BEGIN
SELECT * FROM vw_sampleView where id= #id
END
Then this SP retunred filtered data. Grant the permission to execute this SP to different users.
GRANT EXECUTE ON [dbo].[proc_GetData] TO [user_logins]
You can create a UDF which will return a table based on the parameters. For example:
CREATE FUNCTION [dbo].[fnt_myfunction]( #id INT)
RETURNS TABLE
AS
RETURN (
SELECT *
FROM myTable
WHERE id = #id
);
DECLARE #id INT = 1;
SELECT * FROM [dbo].[fnt_myfunction](#id);
Hope that helps.
I have a select statement that needs to look up a customer ID from a customer name. If an ID does not exist for that name, a new record needs to be created in the customer table. this has to be done as part of a select statement (related to the app its being run from).
I tried looking at a UDF that returned either the existing ID or a new ID, before realizing that you can't modify tables from a function.
any idea how to accomplish this?
EDIT:
I think i need to clarify things a bit more. The select statement can and will change on a per-implementation basis. What I'm looking for is a generic way of looking up or creating the customer id (that table and the need to do the lookup does not change) as part of a larger select statement.
the app that is using the sql loads the select statement from a config file, and has 'SELECT' hard coded, so there's no chance of adding an exec before the select etc.
It looks like what I need is something like 'select a.1 (exec dotheLookup(name)) as customerID, a.2 FROM table, but I'm not sure how to go about that.
I suggest you to Create a stored procedure for this. Something like
Create procedure customer
--parameters
AS
Begin
IF exists(Select lookup(customerName) as customerID from table)
BEGIN
--Your select goes here
END
ELSE
BEGIN
--Insert into customer table and return scopeidentity
--Select goes here
END
END
Updated Answer:
You cannot perform data manipulation using select statement.
You could execute a stored procedure before you execute the SELECT statement, the run a function that returns ID from name:
exec CheckForCustomerByNameAndAddIDIfItDoesntExist(customerName)
declare iCustomerID int
select iCustomerID = GetCustomerIDFromName(customerName)
select a.1, a.2, iCustomerID as customerID from table
Something like that
Can you modify the database server? If so, add a linked server pointing to the local server.
EXEC master.dbo.sp_addlinkedserver #server = N'LinkedLocal', #srvproduct=N'', #provider=N'SQLNCLI', #datasrc=N'LocalServerName'
EXEC master.dbo.sp_addlinkedsrvlogin #rmtsrvname=N'LinkedLocal',#useself=N'True',#locallogin=NULL,#rmtuser=NULL,#rmtpassword=NULL
Then just run an OPENQUERY that invokes a stored procedure that does your work:
select * from OPENQUERY("LinkedLocal", 'exec Database.Schema.StoredProcedure ''Param1'', ''Param2'')
The issue I'm facing is that I have a stored procedure (lets call it sp_one), which during it's run calls another stored procedure (lets call it sp_two).
I'd only like the resultset from sp_one to be returned at the end, and not those from sp_two. I imagine there is a way to capture the results from sp_two that will prevent them from also being returned but haven't been able to figure the syntax for this.
Any ideas?
Some pseudo code which captures the essence of what is going on (not my actual code):
CREATE PROCEDURE sp_two AS
BEGIN
update Users
set is_valid = 0
select * from Users
END
CREATE PROCEDURE sp_one
AS
BEGIN
exec sp_two
select * from Users
END
exec sp_one
The result of running exec sp_one is the resultset from sp_two, then the results from sp_one. (eg. the users table twice).
First of all, here is a similiar question
I don't recommand to use this kind of solution, because it could be a bottleneck easily. I would say you should focus on to make the dataprocessing on a much clearer way (however I understand that your question's example is just a theoretical example)
But if you really want to use something like this I would say measure the danger of the returning rows:
1: How many rows returns?
2: How wide is the returning set?
And if you think "ok it is not a big deal", then I would say use a memory table instead of temp table (do not make physical writes):
DECLARE #users TABLE (...fields here...)
INSERT INTO #users
EXEC sp_two
In sp_one, you can use
CREATE TABLE #temporaryusers (Usertable fields here)
INSERT INTO #temporaryusers
EXEC sp_two
DROP TABLE #temporaryusers
to swallow your results.
I need to make a SELECT with a call of a stored procedure in the WHERE clause.
It should be something like that....
SELECT distinct top 10 i.x, d.droit
FROM v_droit d, v_info i
WHERE d.nomdroit='yy'
AND i.id<>2
AND (select val from (exec up_droits(i.x, d.droit)) <>3
But it does not work...
Any idea?
Don't say to replace the stored procedure with a function because is not possible to use the existing code in a function. So the function is not a valid option. I really need to be able to use a stored procedure
This is achieved by first executing the stored procedure, capturing the output into a #temp table or a #tabel variable, then running your query against the table. Something like this:
declare #droits_table (val ,... );
insert into #droits_table
exec up_droits(param, param);
SELECT distinct top 10 i.x, d.droit FROM v_droit d, v_info i WHERE d.nomdroit='yy' AND i.id<>2 AND (select val from #droits) <>3
Of course this will not work for you because the up_droits needs the i.x and d.droit parameters from the query. This indicates that your stored procedure should probably be a a view or table valued function.
Sorry but, make it a table valued function rather than stored procedure.
Eg:
Scalar - SELECT id, name FROM test WHERE id < (SELECT dbo.mytestfunction())
Table - SELECT id, name FROM test WHERE id = (SELECT col1 from dbo.mytestfunction())
You can't. The content of the WHERE clause must be a search expression.
Is the reason that the code doesn't work as a function because it modifies some data? If so, then you're out of luck, functions used in where clauses must be immutable.
If the stored procedure doesn't modify any data, you may be able to wrap it inside of a function.
If you are on SQL Server I don't think you can do what you propose.
But one thing you can do is build dynamic queries, but be careful doing it because they open up many interesting problemareas.
The syntax is :
EXEC #<query>
But anotherthing you can do, which is probably much better for you, is to make the up_droits function deliver it's results in a temp table, if you select into a #table it is temporary for the duration of your function/procedure scope
declare procedure up_droits() as
select val .. into #temp
So what you do is create a procedure
create procedure Top10FromDroit
begin
exec up_droits
SELECT distinct top 10 i.x, d.droit FROM v_droit d, v_info i WHERE d.nomdroit='yy' AND i.id2 AND (select val from (#temp) 3
Hopefully that will give you the results you want to achieve.
If at first you don't succeed, code around it^^
Could anyone of you explain reasons for executing dynamic SQl inside stored procedure. I know very few situations when you need them - but really very few. 99.9% (or 999 of a 1000) of execute strings could be rewritten as normal sql statements with parameters.
The very same is with Selects that have functions inside select or where clauses.
Try to think about your sets of data, not about procedural ways how to solve it.