Where is the table/view script generated and how to get it? - sql

Say I have written a Create Table script in a query window and run it. So the table got created. Now, where is this script file being generated (system table). I mean if I do a
select * from sys.syscomments
I will get the script for stored procedure or function in the "Text" column. Likewise any way of getting the same for table or view?
Any DMV etc...
Thanks in advance

I'm not sure where the script is stored, but if you're looking to be able to view the scripted language to create the table, in SQL2008 R2 (and I'm pretty sure SQL2008) SSMS can generate the script on the fly. Just select your Table (or View, SP, etc...) and right click. From the context menu, choose Script Table as Create To (or whatever other modification you choose from the list). Then you have a choice of output locations-the New Query Editor Window is probably easiest to see your results. From there you have the base language for that table's creation and you can modify or save it from there.

below query is also works for views
select * from sys.syscomments
For getting script of tables , you have to
Right Click on database >> tasks >> Generate Scripts >> choose objects (select tables)
I think that is the possible way of getting table scripts.

For views you can use the column VIEW_DEFINITION in:
SELECT *
FROM INFORMATION_SCHEMA.VIEWS
I don't think there is an equivalent for tables because tables don't require a stored definition because the table itself is the definition. If you need to copy table structures then the best method is probably to use:
SELECT *
INTO NewTable
FROM OldTable
WHERE 0 = 1
You could try generating your own scripts using the system views and creating dynamic SQL, something like this would get you started
This does not create constraints, and there maybe things I've missed, or cause it to break but the general gist is there. You could also do this outside of SQL as demonstrated quite nicely In this Answer.
HOWEVER I should add I do not condone the use of these methods. There are few scenarios I can think of where it would be necessary to programatically copy a tables structure in this fashion. If it is necessary to copy structures as a one off you'd be better off doing this using the generate script functions that are built into SSMS.

Related

How to quickly generate SELECT statement for a table in DataGrip?

In Microsoft SQL Server Management Studio (SSMS), you can right-click on a table, then go to Script Table as -> SELECT To, and then choose a destination for the generated script.
Is there anything similar in DataGrip, or can one be custom created in some way?
The reason I find this useful is because I often find that I'm working with a table with a lot of columns, and I want to select all but a few of them. So it's easier to just have it generate the SELECT statement with all the columns explicitly listed out, so that I can just go through and delete the ones I don't want.
Currently, my workaround in DataGrip is to right-click the table, then choose Copy DDL. This generates the CREATE TABLE statement, which lists out all the columns, but it also includes the column definitions. So I have to do a regex replace or run a macro to get rid of the extra info, which is kind of a pain. Does anyone have a better solution?
In DataGrip as other intellij-based IDEs everything is about source editing. So that can be achieved that way:
Open console
Start typing sel, you'll get completion popup (if not, hit Ctrl+Space)
Select sel here, which is live-template for select statement
Select statement will be generated, asking for table name and column list
Select desired table from completion, as column list provide *
Then hit Alt+Enter on asterisk and select Expand column list
I suggest you to look through https://www.jetbrains.com/datagrip/features/
In DataGrip 2018.3 you can use postfix completion. This is the flexible way to get needed queries.
Try typing
SELECT %table_name%.from
SELECT %table_name%.afrom
SELECT %table_name%.join
And this will be expanded to the needed queries. In the case of from completion you'll be able to write columns.
This makes writing SQL more logical: first, you point table, then columns.
See gif:

Renaming a column without breaking the scripts and stored procedures

I want to modify a column name to new name present in a table
but here problem i want to manually modify the column name present in Triggers or SP's.
Is there a any better way of doing it.
To rename a column am using this
sp_RENAME 'Tablename.old_Column', 'new_column' , 'COLUMN';
similarly how can i do it for triggers or SP's.? without opening each script?
Well, there are a bunch of 3rd party tools that are promising this type of "safe rename", some for free and some are not:
ApexSQL has a free tool for that, as MWillemse wrote in his answer,
RedGate have a commercial tool called SQLPrompt that also have a safe renaming feture, However it is far from being free.
Microsoft have a visual studio add-in called SQL Server Data Tools (or SSDT in the short version), as Dan Guzman wrote in his comment.
I have to say I've never tried any of these specific tools for that specific task, but I do have some experience with SSDT and some of RedGate's products and I consider them to be very good tools. I know nothing about ApexSQL.
Another option is to try and write the sql script yourself, However there are a couple of things to take into consideration before you start:
Can your table be accessed directly from outside the sql server? I mean, is it possible that some software is executing sql statement directly on that table? If so, you might break it when you rename that column, and no sql tool will help in this situation.
Are your sql scripting skills really that good? I consider myself to be fairly experienced with sql server, but I think writing a script like that is beyond my skills. Not that it's impossible for me, but it will probably take too much time and effort for something I can get for free.
Should you decide to write it yourself, there are a few articles that might help you in that task:
First, Microsoft official documentation of sys.sql_expression_dependencies.
Second, an article called Different Ways to Find SQL Server Object Dependencies that is written by a 13 years experience DBA,
and last but not least, a related question on StackExchange's Database Administrator's website.
You could, of course, go with the safe way Gordon Linoff suggested in his comment, or use synonyms like destination-data suggested in his answer, but then you will have to manually modify all of the columns dependencies manually, and from what I understand, that is what you want to avoid.
Renaming the Table column
Deleting the Table column
Alter Table Keys
Best way use Database Projects in Visual Studio.
Refer this links
link 1
link 2
you can do what #GorDon suggested.
Apart from this,you can also play with this query,
select o.name, sc.* from sys.syscomments sc inner join sys.objects o
on sc.id=o.object_id where sc.text like '%oldcolumnname%'
this will return list of all proc and trigger.Also you can modify filter to get exact list.then it will be very easy for you to modify,manually.
But whatever you decide,don't simply drop old column.
To be safe,even keep back up.
This suggestion relates to Oracle DB, however there may be equivalent solutions in other DBMS's.
A temporary solution to your issue is to create a pseudocolumn. This solution looks a little hacky because the syntax for a pseudocolumn requires an expression. The simplest expression I can think of is the case statement below. Let me know if you can make it more simple.
ALTER TABLE <<tablename>> ADD (
<<new_column_name>> AS (
CASE
WHEN 1=1 THEN <<tablename>>.<<old_column_name>>
END)
);
This strategy basically creates a new column on the fly by evaluating the case statement and copying the value of <<old_column_value>> to <<new_column_value>>. Because you are dynamically interpolating this column there is a performance penalty vs just selecting the original column.
The one gotcha is that this will only work if you are duplicating a column once. Multiple pseudocolumns cannot contain duplicate expressions in Oracle.
The other strategy you can consider is to create a view and you can name the columns whatever you want. You can even INSERT/UPDATE/DELETE (execute DML) against views, but this would give you a whole new table_name, not just a new column. You could however rename the old table, and name your view the same as your old table. This also has a performance penalty vs just accessing the underlying table.
You might want to replace that text in definition. However, you will be needing a dedicated administrator connection in sql server. Versions also vary in setting up a dedicated administrator connection. Setting up the startup parameter by adding ;-T7806 under advanced. And by adding Admin: before the servername upon logging in. By then, you may be able to modify the value of the definition.

How do I programmatically run a complex query on an as400?

I'm new at working on an as400 and I have a query the joins across 4 tables. The query itself is fine, it runs in STRSQL and displays the results.
What I am in struggling with is getting the query to be able to run programmatically (it will eventually be run from a scheduled CL script).
I tried have creating a physical file that contains the query running it with RUNQRY, but it simply displays the query itself, not the actual result set.
Does anyone know what I am doing wrong?
UPDATE
Thanks everyone for the direction and the resources, with them I was able to reach my goal. In case it helps anyone, this is what I ended up doing (all of this was done in it's own library, ALLOCATE):
Created a source physical file (using CRTSRCPF): QSQLSRC, and created a member named SQLLEAGSEA, with the type of TXT, that contains the SQL statement.
Created another source physical file: QCLSRC, and created a member named POPLEAGSEA, with the type of CLP, that changes the current library to ALLOCATE then runs the query using RUNSQLSTM (more detail on this below). Here is the actual command:
RUNSQLSTM SRCFILE(QSQLSRC) SRCMBR(SQLLEAGSEA) COMMIT(*NONE) NAMING(*SYS)
Added the CLP to the scheduled jobs (using ADDJOBSCDE), running the following command:
CALL PGM(ALLOCATE/POPLEAGSEA)
With regard to RUNSQLSTM, my research indicated that I wasn't going to be able to use this function, because it didn't support SELECT statements. What I didn't indicate in my question was what I needed to do with the the result - I was going to be inserting the resultant data into another table (had I done that I'm sure the help could have figured that out a lot quicker). So effectively, I wasn't going to be doing an SELECT, my end result is actually an INSERT. So my SQL statement (in SQLLEAGSEA) begins with:
INSERT INTO
ALLOCATE/LEAGSEAS
SELECT
...
BLAH BLAH BLAH
...
From my research, I gather that RUNSQLSTM doesn't support SELECT because it doesn't have a mechanism to do anything with the results. Once I stopped taking baby steps and realized I needed to SELECT AND INSERT in the same statement, it solved my main problem.
Thanks again everyone!
The command is RUNSQLSTM to run a static SQL statement in a physical file member or stream file.
It is a non-interactive command so it will not execute sql statements that attempt to return a result set.
If you want more control, including the ability to run interactive statements, see the Qshell db2 utility.
For example:
QSH CMD('db2 -f /QSYS.LIB/MYLIB.LIB/MYSRCFILE.FILE/MYSQL.MBR')
Note that the db2 utility only accepts the *SQL naming convention.
QM Query
If all the SQL you need is the single complex SQL statement, and this is what it sounds like, then your best bet is to use Query Management Query (see QM Query manual here).
The results can be directed to a display, a spool file, or a physical file (ie a DB2 table). The default output when run interactively is to the screen, but when run in a (scheduled) batch job it will default to a spool file report.
You can create the QM Query interactively via WRKQMQRY, in prompted mode (much like Query/400) or in SQL mode. Or you can compile the QM Query from source, with the CRTQMQRY command.
To run your QM Query, STRQMQRY command.
RUNSQL cmd
If you are using a system that has IBM i 7.1 fully up-to-date, and has Technology Refresh 4 (TR4) installed, then you could also use the new RUNSQL command to execute a single statement. (see discussion in developerWorks)
SQL Scripting w/ RUNSQLSTM cmd
From CL you can run SQL scripts of multiple SQL statements from a source file member. There is no standard default source file name for this, but QSQLSRC is commonly used. The source member can contain multiple non-interactive SQL statements. This means you cannot use a SELECT statement (directly) since theoretically it will not know where to send the results. CL commands are even allowed if given a CL: prefix. Both SQL and CL statements should be terminated with a semicolon ;. While the SQL statements cannot display data directly to the screen, the same restriction does not apply to the scripted CL commands.
The STRQMQRY command can be embedded in the RUNSQLSTM script, by placing the prefix "CL: " in front of the command. Since STRQMQRY can direct output to the screen, a report, or an output table, this can come in very useful.
Remember that to direct your output from a SELECT query to a file you can use either the INSERT or CREATE TABLE statements.
CREATE TABLE newtbl AS
( full-select )
WITH DATA;
Or, to put the results into a table you create in your job's QTEMP library:
DECLARE GLOBAL TEMPORARY TABLE AS
( full-select )
WITH DATA;
[Note: If you create the source to be used by CRTQMQRY, you are advised to create it as CRTSRCPF yourlib/QQMQRYSRC RCDLEN(91), since the compiler will only use 79 columns of your source data (adding 12 for sequence and change date =91). However for QM Forms, which can be used to provide additional formatting, the CRTQMFORM compiler will use 81 columns so RCDLEN(93) is advised for QQMFORMSRC.]
RUNQRY is a utility that lets you execute a query that was created by another utility named WRKQRY. If you really want to process SQL statements held in a file try RUNSQLSTM. It uses a source physical file to store the statements, not a database file. The standard name for that source physical file is QQMQRYSRC. To create that file, CRTSRCPF yourlib/QQMQRYSRC. Then you can use PDM to work with that source PF. WRKMBRPDM yourlib/QQMQRYSRC. Use F6 to create a new source member. Make it source type TXT. Then use option 2 to will start an editor called SEU. Copy/paste your SQL statements into this editor. F3 to save the source. Once the source is saved, use RUNSQLSTM to execute it.
It is (now) possible to run SQL directly in a CL program without using QM Query, RUNSQLSTM or QShell.
Here is an article that discusses the RUNSQL statement in CL programs...
http://www.mcpressonline.com/cl/the-cl-corner-introducing-the-new-run-sql-command.html
The article contains information on what OS levels are supported as well as clear examples of several ways to use the RUNSQL statement.
This will work in two steps:
RUNSQL SQL('CREATE TABLE QTEMP/REPORT AS (SELECT +
EXTRACT_DATE , SYSTEM, ODLBNM, SUM( +
OBJSIZE_MB ) AS LIB_SIZE FROM +
ZSYSCOM/DISKRPTHST WHERE ODLBNM LIKE +
''SIS%'' GROUP BY EXTRACT_DATE, SYSTEM, +
ODLBNM ORDER BY LIB_SIZE DESC) WITH +
DATA') COMMIT(*NONE) DATFMT(*USA) DATSEP(/)
RUNQRY QRYFILE((QTEMP/REPORT)) OUTTYPE(*PRINTER) +
OUTFORM(*DETAIL) PRTDFN(*NO) PRTDEV(*PRINT)
The first step creates a temporary table result in qtemp and the second step/line runs an adhoc query over just the temporary table to a spool file.
Thanks,
Michael Frilot
There is of course a totally different solution: You could write and compile a program containing the statement. It requires some longer reading into, especially if you are new to the platform, but it should give you most flexibility over what you do with results. You can use SQL in C, C++, RPG, RPG/LE, REXX, PL (of which I don't know, what it is) and COBOL. Doing that, you can react in any processable way on results from one query and start/create other queries based on what you get.
Although some oldfashioned RPG-programmers try everything to deny SQL in RPG exists, it is possible today for many cases, to write RPG-programs with SQL only and no direct file access (without F-Specs, for those who know RPG).
If your solution works for you, perfect. If you need to do something else, try a look into this pdf: http://publib.boulder.ibm.com/infocenter/iseries/v5r3/topic/rzajp/rzajp.pdf
The integration into RPG is not too bad. It works with the normal program flow. Would look something like this (in free form):
/free
// init search values:
searchval = 'Someguy';
// so the sql query:
exec sql
SELECT colum1, colum2
INTO :var1, :var2
FROM somelib/somefile
WHERE keycol=:searchval;
// now do something with the values:
some_proc(var1);
/end-free
In this, var1, var2, and searchval are ordinary RPG-variables. No quoting needed. Works also with datastructures (externally defined e.g., the record format of the file itself fits well). You can work with cursors and loops, too, of course. I feel that RPG-programs tend to be easier to read with this.

Changing Column Ordinal_position Positions

My scenario:
I can change the ordinal position of a column in a table.Is there a way to change the ordinal position of a column in a table without recreating the table?
No, you have to recreate the table if you wish to achieve this. (SQL SERVER)
Even when you do this in SSMS, you will see that the script that is generated also recreates the table.
Not in SQL Server - Not sure about other RDBMSs.
You can create a View with the desired ordinal positions but the only time I can think that would be useful is if you are using SELECT * which is a practice that should be avoided anyway.
Hi it depends on the database system you use.
For example in some it is possible to remove and add a column and you can do it in a procedure part where you also can refill it.
But in general it shouldn't matter as you can define the returned data order in your select statement. Is not that enough for you?
Without recreating the Table is Not possible. However, if your concern is about loosing the data here is an option provided by SQl Server Management Studio.
Note: I have used Sql Server 2019 Developer Edition.
Right Click on the Table name and Choose Design Option
Using your Cursor Drag the position of your Column to your desired Position
SQlServer Table Design Options
If you want to do it at script level, You can see the idea below provided by SSMS
Enable the "Auto Generate Change Script" Option available in Tools Menu --> Options --> Designers --> Table and Database Designers.
Enabling the Auto Generate Change Script Option
When you drag the Column in SSMS it will automatically creates the Script for you.
The High level Idea in the auto generated Script is,
Creating a Table with Temp_YourTableName with desired Order of Columns
Copying all the Data from the Original Table to new Temp_YourTableName
Drop the Original Table
Renaming the Temp_YourTableName to Original YourTableName
of course doing everything with Transaction scope to avoid any data loss while the script is executing.
I found a good reason why some time we need to do this here. Interestingly, it is based on Context and not to do anything with Technical.
Say for example, Original Address Table Contains, Street Address 1, City, State, Zip and Country columns. If the requirement Changes to include a new Columns like Street Address 2 this would be meaning full.

PL/SQL Developer - ignore/limit large data in queries

In PL/SQL Developer v7.1.x, is there way way to ignore large data types in queries or the "Query Data" feature. For example: If you right click on table FOO, and select "Query Data" this will execute a SELECT * FROM FOO. If that table contains BLOB data the query will take a while to complete and temporarily lock up the application. This is especially problematic when querying remote databases (for obvious reasons).
I would like a way to tell PL/SQL Developer not to retrieve large data by default. I know there is a way to limit the ResultSet size but this doesn't do what I am looking for.
I could just select each column I wanted ignoring certain ones but then I couldn't use the "Query Data" feature.
Thanks.
No, the Query Data feature does one thing and one thing only - queries all the data.
What you might find useful is that you can drag the name of a table or view from the Browser into a SQL Window, choose "Select" from the menu that pops up, and it will generate a SELECT statement on the table with all the column names included - but does not execute the query straight away. You can then edit it however you like (e.g. comment out the LOB columns) before you run it.
I know that Toad has something like that built in, but I'm not aware of a PL/SQL Developer option that disables BLOBS.
The option you are left with, for now, is to simply select all the columns individually and truncate the blob.
ie:
select foo, bar, trunc(baz,100) from foo where ...
Create a View that doesn't contain the blob column or whatever columns you don't routinely want to look at.