Create table - dynamic name of table - sql

I've got some problem with creating a query in Access.
I'd like to have a query, which after running will ask about name and surname of new record in table Buyers, and then create new table for this buyer(e.g. for John Smith - called SmiJoh - 3 letters from Surname and 3 from Name).
Any ideas how to do that without VBA, using only SQL?
PS. If there's no chance to do all of this using SQL is there any possibility to do only query creating a table with this name?

You asked whether you can do something like this with SQL in Access, where table_name is a value you supply when the statement executes.
CREATE TABLE [table_name](
id COUNTER CONSTRAINT pkey PRIMARY KEY,
date_field DATETIME);
No, Access' database engine will not allow you to use a parameter for the table name.
But like the comments you've received, I encourage you to re-consider your plan to create a separate table for each buyer. That will be a complicated mess to build and maintain.
Use a single table to hold data from all buyers. Include a field to identify the buyer. Then use a query which retrieves only the rows where the buyer_id field matches the current user's buyer_id. Build a form with that query as its record source. Here is a sample table where the uname field holds the Windows account name.
id uname time_only
5018 fred 7:00:00 AM
5063 hans 2:00:00 AM
5072 hans 3:00:00 AM
With Dev Ashish's fOSUserName() function (Get Login name), this query returns only the rows where uname matches my Windows user name (hans).
SELECT d.id, d.uname, d.time_only
FROM discardme AS d
WHERE d.uname = fOSUserName();
I created a form based on that query which includes a text box bound to uname with these properties on the Data tab of its property sheet: Default Value =fOSUserName(); and Enabled No. If you don't want the user to even see the uname value, set Visible No on the Format tab.
You would still need to lock down the application to prevent the users from opening the table directly. But that would also be required with your original scheme to create a separate table for each buyer.
A similar approach could work if you have set up ULS (user-level security), which requires an MDB format db; it's not supported in the newer ACCDB db format. In that case the, the VBA CurrentUser() function will return the name of the Access security user name. Change the query accordingly:
SELECT d.id, d.uname, d.time_only
FROM discardme AS d
WHERE d.uname = CurrentUser();
Note that without ULS, CurrentUser() will give you the name of the default user account, Admin.
Finally consider your security requirements. Doing this with Access' Jet/ACE for data storage will amount to offering guidance to cooperative users. However, whether or not you adopt ULS, you can't absolutely prevent a user from viewing any of the data. If your security requirements are more stringent, move the data storage to a client-server database (SQL Server, for example). You can still use your Access application as a front-end by substituting ODBC links to the server tables for the existing native Jet/ACE tables.

Have you tried using an EXEC
DECLARE #Name VARCHAR(6)
SET #Name = 'SMIJOH' --Query your table name
EXEC ('CREATE TABLE ' + #Name + ' (ID INT IDENTITY(1,1), etc....)')

Related

If not exist clause SQL statement

so I found this sql query in a project I am succeeding. This is the first time I encountering this clause/statement. I understand that this is to look if the table exist before creating one and that Object_ID is the table name that is to be created.
My questions are:
Does sysobject mean the database?
What is the Object property?
I know that it is not the columns inside the table to be created.
The columns are : dtb_color_id and description.
can someone explain this to me. please?
IF NOT EXISTS(SELECT * FROM SYSOBJECTS WHERE ID = OBJECT_ID('DTB_COLOR') AND OBJECTPROPERTY(ID,'ISUserTable') = 1)
BEGIN
.......some query I understand
END
sysobjects, OBJECTPROPERTY and OBJECT_ID are used in Microsoft SQL Server. They are part of the SQL Server DMVs and system functions/procedures used to query and manipulate the metadata.
sys.sysobjects is simply the list of all objects (tables, views, SPs, functions, etc) on the server in the active database. Please note, that sys.sysobjects is deprecated and is only available for backward compatibility. Use sys.objects instead
https://learn.microsoft.com/en-us/sql/relational-databases/system-dynamic-management-views/system-dynamic-management-views?view=sql-server-ver16
It has (as far as I know) no meaning in MySQL, unless somebody specifically created them.
You can also use INFORMATION_SCHEMA which is available in MySQL too (however slightly different in different RDBMS).
MSSQL INFORMATION_SCHEMA: https://learn.microsoft.com/en-us/sql/relational-databases/system-information-schema-views/system-information-schema-views-transact-sql?view=sql-server-ver16
MySQL INFORMATION_SCHEMA: https://dev.mysql.com/doc/refman/8.0/en/information-schema.html
SQL Server has no CREATE TABLE IF NOT EXISTS construct, a variation of the mentioned condition is commonly used to imitate that.
This is a way in SQL Server to check if a table exists in the active database and to perform actions according to the result, like creating the table.
OBJECTPROPERTY simply checks (in this case) if the table is a user created one.
https://learn.microsoft.com/en-us/sql/t-sql/functions/objectproperty-transact-sql?view=sql-server-ver16
I would remove the OBJECTPROPERTY condition in case the part you understand is a CREATE TABLE statement. You don't want to create a table which has a similar name to any system table/view, also you don't want to execute the CREATE TABLE if there is a VIEW with the same name (table creation will fail)
Yes sysobject means database.
The OBJECTPROPERTY() function returns information about schema-
scoped objects in the current database. Use this to check if an
object is a table, view, stored procedure, etc. You can also use
it to check if a table has a primary key, foreign key, foreign
key reference, etc.
For more details : https://learn.microsoft.com/en-us/sql/t-sql/functions/objectpropertyex-transact-sql?view=sql-server-ver16
In this scenario it is used to check whether it is user table or
not. The result of the ISUserTable property is 1 when it is user
table otherwise returns 0.
Here the following steps are followed:
First, it executes the select statement inside the IF Exists
If the select statement returns a value that condition is TRUE for IF Exists
It starts the code inside a begin statement
DTB_COLOR - May be a stored procedure

What does double dots .. mean in SQL Server?

I am using SQL Server. I found the following way to backup a database table:
-- Taking a backup
SELECT * INTO MY_BACKUP_DATABASE..CustomersTemporaryTable FROM Customers
I am trying to understand the .. in the syntax. From what I understand, the sentence means that Customers is the table that is going to be backed-up by placing it all of its content into the database called MY_BACKUP_DATABASE using CustomersTemporaryTable as the destination table. I assume when executing the sentence, CustomersTemporaryTable must already exist. Is my understanding of the sentence to take a backup correct?
Each MS SQL Table identifiers can have a name compound of three parts separates with a dot :
the database name
the SQL schema name (by default dbo)
the table, view or Table UDF name
Syntax :
db_name.schema_name.table_name
But it is not always necessary to specify the three parts.
Inside the current database, no need to specify the db_name. It's implicit...
By default every SQL user is associate with a specific default schema (frequently dbo too...).
So you can specify a table name with :
schema_name.table_name
...SQL Server will try to find the table into the current DB
db_name..table_name
...SQL Server will try to find the table into the specified DB and the default user schema
table_name
...SQL Server will try to find the table into the current DB and the
default user schema
To know with SQL schema is associated with your SQL user, use :
SELECT SCHEMA_NAME() AS DEFAULT_CURRENT_USER_SCHEMA
To know all the associations between SQL users and SQL schemas, do :
SELECT name AS USER_NAME, default_schema_name
FROM sys.database_principals
WHERE type_desc LIKE '%?_USER' ESCAPE '?'
First of all, understand that what you are doing is not "taking a backup", it is inserting data into a table from another table. If you have not created the destination table the syntax is like this:
Select *
INTO Destination_Table
FROM Source_Table
The destination table will be created automatically. This doesn't necessarily work so well if you will be inserting additional data that might be different lengths or data types, but for a one of select should work fine.

Send additional data to SQL along with the query?

Simplified case:
Database table Cars
ID (int)
Name (varchar)
Model (varchar)
On this table there is a trigger on UPDATE that will insert something like 'Name of car with ID # has been changed' to another table
From the backend a simple query is run
UPDATE Cars SET Name='My First Car' WHERE ID = 1
What I would like to accomplish is to send an additional value alongside the query so I can alter the trigger to do something like this: 'Name of car with ID # has been changed by user with ID #'
I am using SQL SERVER 2017 (v14)
What are my options?
If using SQL Server 2016 use SESSION_CONTEXT otherwise use CONTEXT_INFO and store the user information before calling the update.
Then, either way, within the trigger extract the user information and use it for your logging information.
The information available to a trigger is limited to information in the table that the trigger is on, or information which is available to the system in general.
Since the user is not in the original table, you need the data to be available to the system in general. There's quite a lot of data like this. For example, you can know the name of the database you're in, using the built in db_name() function.
There is some information the system can give you based on the connection properties. For example, the orignal_login() function will give you the name of the user who actually made the connection to the SQL Server.
If you have a table of Users somewhere, that has, say, (UserName, UserId),and if the user names in that table match the actual login names of the sql server logins, then you could use the result of original_login() to join onto that table, pull out the username, and now you have the user id:
create trigger t on cars after update as begin
set nocount on;
insert myloggingtable(Message, EntryDateTime)
select concat('car with id ', inserted.id, ' was updated by ', u.UserId), getdate()
from inserted i
join Users u on u.UserName = original_login()
end
As mentioned in the comments, since your application is connecting as an application specific account, this of course won't help you. In which case you could try context_info

How to check quickly whether the user has write access to a particular db in sql server or not?

I have a requirement where in, I have to check whether the user has write access to a particular sql server or not.
I have done this with using Dir function for access db and other files
But SQL server, do I have to try and write a value to a table to see whether it allows me or not ?
You could try: fn_my_permissions. The following is based on an example from the web page.
SELECT * FROM fn_my_permissions('dbo.MyTable', 'OBJECT')
ORDER BY subentity_name, permission_name ;
This will return three columns:
entity_name (table in this case),
subentity_name (column in this table),
and permission_name (ALTER, SELECT, etc.).

Customized Table Names in Sql Server

I have a table called Table 1. I'm trying to create an after-insert trigger for a Table 1; whereby, whenever a user enters a record, the trigger will create a new table named after the record that triggered its creation.
Please help, I'm using SQL Server 2008
This sounds super non-relational-database-design-ish. I would heavily advise against this in almost every case. And I say "almost" only to allow for artistic freedom of development, I can't think of a single case where this would be appropriate.
That said, if you do in fact want this, you can use dynamic SQL to create a table.
You can build the SQL in your trigger, but basically you want something like:
EXEC 'CREATE TABLE ' + #tableName + ' (ID INT IDENTITY(1,1))';
Of course, the columns are up to you, but that should get you started.
But while we're at it, what you should (probably) be doing is using a single table with a one-to-many relationship to the table on which your trigger is currently assigned.
For instance, if you have a table Users with a column for email and you're looking to create a table for each user's favorites on your website, you should instead consider adding an identity column for user IDs, then reference that in a single UserFavorites table that has UserId and PostId columns, and the appropriate foreign keys implemented.