Execute a SQL stored proc from a SQL view - sql-server

I am finding that calling a stored proc in Excel is not as easy as it should be, but calling a view, or a direct table is very easy. So, how can I create a view that will call a stored proc with no params?
I know I won't be able to pass any values into the view, and I don't need or want to, Just want to wrap a stored proc in a view.
something like select exec MyStoredProc() would be great.

iirc (I don't have a copy to hand) if you happen to be in T-SQL it should be possible to select * from a user defined table function (which are for most intents and purposes identical to sprocs) which returns a table variable.

You should be able to put a trigger on a dummy table, and call the proc inside the trigger.
This is definitely a hack, and you would want to really lock down permissions on the table and proc.

Related

Why ,when and where we will use stored procedures, views and functions?

I often use a stored procedure for data access purpose but don't know which one is best - a view or a stored procedure or a function?
Please tell me which one of the above is best for data access purpose and why it is best, list down the reason with the example please.
I searched Google to learn which one is best but got no expected answer
View
A view is a “virtual” table consisting of a SELECT statement, by means of “virtual”
I mean no physical data has been stored by the view -- only the definition of the view is stored inside the database; unless you materialize the view by putting an index on it.
By definition you can not pass parameters to the view
NO DML operations (e.g. INSERT, UPDATE, and DELETE) are allowed inside the view; ONLY SELECT statements.
Most of the time, view encapsulates complex joins so it can be reusable in the queries or stored procedures. It can also provide level of isolation and security by hiding sensitive columns from the underlying tables.
Stored procedure
A stored procedure is a group of Transact-SQL statements compiled into a single execution plan or in other words saved collection of Transact-SQL statements.
A stored procedure:
accepts parameters
can NOT be used as building block in a larger query
can contain several statements, loops, IF ELSE, etc.
can perform modifications to one or several tables
can NOT be used as the target of an INSERT, UPDATE or DELETE statement
A view:
does NOT accept parameters
can be used as building block in a larger query
can contain only one single SELECT query
can NOT perform modifications to any table
but can (sometimes) be used as the target of an INSERT, UPDATE or DELETE statement.
Functions
Functions are subroutines made up of one or more Transact-SQL statements that can be used to encapsulate code for reuse
There are three types (scalar, table valued and inline mutlistatement) UDF and each of them server different purpose you can read more about functions or UDF in BOL
UDF has a big limitation; by definition it cannot change the state of the database. What I mean by this you cannot perform data manipulation operation inside UDF (INSERT, UPDATE , DELETE) etc.
SP are good for doing DDL statements that you can't do with functions. SP and user defined functions accept parameters and can returns values but they can't do the same statements.
User defined functions can only do DML statements.
View doesn't accept parameters, and only accept DML statements.
I hope below information will help you to understand the use of the SQL procedure, view, and function.
Stored Procedure - Stored Procedure can be used for any database operation like insert, update, delete and fetch which you mentioned that you are already using.
View - View only can be used to fetch the data but it has limitations as you can't pass the parameters to the view. e.g. filter the data based on the passed parameter
Function - Function usually used for a specific operation like you have many in-built SQL server functions also for the date, for math, for string manipulation etc.
I'll make it very short and straight.
When you are accessing data from different tables and don't want to pass parameter use View.
When you want to perform DML statement go for Function.
When you want to perform DDL statement go for Stored Procedure.
Rest is upon your knowledge and idea hit in your mind at particular point of time.
And for performance reasons many would argue
- avoid functions (especially scalar) if possible
It's easier to tweak stored procedures (query plans) and views
IMO, View (and Indexed View) are just Fancier SELECT
Stored Procedure are versatile as you can transform/manipulate within

is it possible to invoke SQL trigger programmatically?

I know under such circumstances, I have to use Stored Procedures,
but still I want to know if it is possible? If NO, Why? If YES, How?
First thing that comes to mind is
update yourtable
set yourcolumn = yourcolumn
-- consider a 'where' statement
I imagine this would invoke the trigger without changing anything. Thus being invoked with code.
You cannot call triggers directly. They are fired automatically when you perform an insert/update or delete on a table that has triggers. Therefore, you cannot call a trigger in a stored procedure.
Trigger needs to have deleted or inserted record when executes, and I cannot see how it can be passed...
By definition "a trigger" is a procedure that fires when a table is changed. I guess you could make it fire programmatically by doing update/delete/create on a table that has a trigger.
If you want a procedure that can be executed manually, then as you pointed out, you should just create a stored procedure.
If you want a procedure that can be executed as a trigger and manually, why not create a stored procedure and then create a trigger that simply has one line that fires that procedure?
If you are writing some test/diagnostics code and really need to invoke some trigger code, you might be able to use some meta API (I remember Oracle had something like that. Not sure about sql server, but it's got to have something) to extract the code out and massage it into a stored procedure. If you do this, as Alex_L already mentioned, you will have to somehow fake out the pseudo update rows which are typically accessible only to triggers.

Why can we not execute a stored procedure inside a function in SQL Server

Why can we not execute a stored procedure inside a function when the opposite is possible?
You cannot execute a stored procedure inside a function, because a function is not allowed to modify database state, and stored procedures are allowed to modify database state.
This is by definition (see CREATE FUNCTION - Limitations and Restrictions).
User-defined functions cannot be used to perform actions that modify the database state.
A stored procedure might modify database state, or it might not. But the SQL Server compiler shouldn't have to analyze the stored procedure to know whether or not it modifies database state. Therefore, it is not allowed to execute a stored procedure from within a function.
Functions exist to simply calculate something, a value or a table result, nothing more than that. These functions can be called within a SELECT query for instance, e.g.
SELECT calculate_something(a) FROM some_table;
Now consider what would happen if the function calculate_something were allowed to execute a stored procedure which would delete all rows in some_table. Your intention is to calculate something using the value of the some_table.a columns, but you end up... deleting all rows in some_table. That is clearly not something you want to happen.
I know this is already been answered but in SQL server the function is not suppose to change the data but the procedure is meant to.
In addition to this i like to add that we cannot select a procedure or put it in a where clause but we can do this with a function.
We use function to shorten the code so its greatly helpful as it reduces a lot of query for the coder.
Hope this helps.
I suspect this is because the execution of a function is not supposed to modify data in any way, and allowing you to run a stored procedure would let you do this...
You would need to change your stored procedure to a Function to call it from within a Function.
Or, one way is to use xp_cmdshell to call a batch file where the batch file contains the execute procedure statement. In the function you can call the extended proc.
eg.
Create Function...
EXEC master.sys.xp_cmdshell 'C:\test.bat'
RETURN...
I am in no way saying that this is good practice but am just saying it's a possibility.
We cannot call store procedure within a function. However, we can call a function within a store procedure.
Functions are extremely limited. They cannot perform any operation in any way that can change data. This means that you can't use dynamic sql or call other objects (except functions)
Some restrictions are their for functions,like (i) it should not change any table structure .It should readonly table. But Stored Procedure can change. Stored procedure can do any changes. So we cant call a Stored Procedure from function.
We can call procedure inside function but that function cannot be called through select statement.The function works fine if you call it through another calling program.Same is the case with dml operations.Functions can have dml operations but it cannot be called through select statement.Whereas if you call the function through another program, the dml gets executed
Technically, calling a stored procedure from a function is possible.
But remember the purpose of the stored procedure and functions.
Purpose of function: The function is used to compute a value and hence must return a value. A function can be called from a select statement as long as it does not alter data. (Permanent table data, not temp tables)
Purpose of Stored procedure: The stored procedure is used to execute business logic and hence may or may not return a value.

Returning a subset of a stored procedure

I have an application that (unfortunately) contains a lot of its business logic is stored procedures.
Some of these return masses of data. Occassionally the code will need a small amount of the data returned from the stored procedure. To get a single clients name, I need to call a stored procedure that returns 12 tables and 950 rows.
I am not able (due to project politics) to change the existing stored procedures or create a replacement stored procedure - the original massive procedure must be called as that contains the logic to find the correct client. I can create a new procedure as long as it uses the original massive procedure.
Is there anyway I can get SQL server to return only a subset, (a single table, or even better a single row of a single table) of a stored procedure?
I have to support sql server 2000 +
It is not possible to conditionally modify the query behaviour of a procedure whose source code you cannot change.
However, you can create a new procedure that calls the original then trims down the result. A SQL 2000 compatible way of doing this might be:
declare #OriginalResult table (
// manually declare every column that is returned in the original procedure's resultset, with the correct data types, in the correct order
)
insert into #OriginalResult execute OriginalProcedure // procedure parameters go here
select MyColumns from #OriginalResult // your joins, groups, filters etc go here
You could use a temporary table instead of a table variable. The principle is the same.
You will definitely pay a performance penalty for this. However, you will only pay the penalty inside the server, you will not have to send lots of unnecessary data over the network connection to the client.
EDIT - Other suggestions
Ask for permission to factor out the magic find client logic into a separate procedure. You can then write a replacement procedure that follows the "rules" instead of bypassing them.
Ask whether support for SQL 2000 can be dropped. If the answer is yes, then you can write a CLR procedure to consume all 12 resultsets, take only the one you want, and filter it.
Give up and call the original procedure from your client code, but find a way of measuring the performance drop, so that you can exert some influence on the decision-making backed up with hard data.
No, you can't. A stored procedure is a single executable entity.
You have to create a new stored proc (to return what you want) or modify the current one (to branch) if you want to do this: project politics can not change real life
Edit: I didn't tell you this...
For every bit of data you need from the database, call the stored procedure each time and use the bit you want.
Don't "re-use" a call to get more data and cache it. After all, this is surely the intention of your Frankenstein stored procedure to give a consistent contract between client and databases...?
You can try to make SQL CLR stored procedure for handle all tables returned by your stored procdure and
in C# code to find data you need and return what you need. But I think that is just is going to make things more complicated.
When you fill your dataset with sored procedure which return more results sets in data set you get for each
result set one DataTable.

grabbing first result set from a stored proc called from another stored proc

I have a SQL Server 2005 stored proc which returns two result sets which are different in schema.
Another stored proc executes it as an Insert-Exec. However I need to insert the first result set, not the last one. What's a way to do this?
I can create a new stored proc which is a copy of the first one which returns just the result set I want but I wanted to know if I can use the existing one which returns two.
Actually, INSERT..EXEC will try to insert BOTH datasets into the table. If the column counts match and the datatype can be implicitly converted, then you will actually get both.
Otherwise, it will always fail because there is no way to only get one of the resultsets.
The solution to this problem is to extract the functionality that you want from the called procedure and incorporate it into the (formerly) calling procedure. And remind yourself while doing it that "SQL is not like client code: redundant code is more acceptable than redundant data".
In case this was not clear above, let me delineate the facts and options available to anyone in this situation:
1) If the two result sets returned are compatible, then you can get both in the same table with the INSERT and try to remove the ones that you do not want.
2) If the two result sets are incompatible then INSERT..EXEC cannot be made to work.
3) You can copy the code out of the called procedure and re-use it in the caller, and deal with the cost of dual-editing maintenance.
4) You can change the called procedure to work more compatibly with your other procedures.
Thats it. Those are your choices in T-SQL for this situation. There are some additional tricks that you can play with SQLCLR or client code but they will involve going about this a little bit differently.
Is there a compelling reason why you can't just have that first sproc return only one result set? As a rule, you should probably avoid having one sproc do both an INSERT and a SELECT (the exception is if the SELECT is to get the newly created row's identity).
Oo to prevent code from getting out of synch between the two processes, why not write a proc that does what you want to for the insert, call that in your process and have the orginal proc call that to get the first recordset and then do whatever else it needs to do.
Depending on how you get to this select, it is possible it might be refactored to a table-valued function instead of a proc that both processes would call.

Resources