Export table to another access database - vba

I have a query in my Access database and a table with absolutely the same structure in another Access database.
I'm need to write a script which adds all entries from the query to the table. How can I do this?
The difference between my task and functionality of Extarnal Data -> Export -> Access Database is that I need to add new entries and save the old, but this tool can only replace old entries to new.

Create a linked table in the source database, to the destination table.
Then, use an append query to insert the results from your query into the linked table.
Edit: You can also do this with a single SQL statement:
INSERT INTO DestinationTable (Field1, Field2)
IN "C:\path\to\file.accdb"
SELECT Field1,Field2
FROM SourceTable
But the reference says:
For improved performance and ease of use, use a linked table instead of IN.

For anyone looking to link the table in VBA...
strDbName = "C:\FolderPath\DatabaseName.mdb"
strLinkTbl = "tblNameOfTableYouWantToLink"
strNameTbl = "tblWhatYouWantToNameIt" ' This can be the actual
' table name or something different
DoCmd.TransferDatabase acLink, "Microsoft Access", strDbName, _
acTable, strLinkTbl, strNameTbl
Then your SQL looks like:
CurrentDb.Execute "INSERT INTO " & strNameTbl _
& " (Field1, Field) SELECT Field1, Field2 FROM SourceTable

Related

How to append to existing TEXT row [sqlite3]

I would like to take an existing TEXT field/row and append to it with sqlite3. I'm finding it somewhat difficult, I've seen some stuff with "upsert."
SQLite - UPSERT *not* INSERT or REPLACE
The specific database I'm working with has no relational connections to any other tables.
Assuming the ideal (pseudo code) UPDATE Table APPEND row values(" text")
assuming row contains "my " I would like it to result in "my text"
Ideally I would like to do this in a single query, but until then I'm left to selecting and using update set
You can use the current values of columns in an update:
UPDATE yourtable SET somecol = somecol || 'text' WHERE somecondition;

Filling current database with records from another database under certain conditions

First of all, I'm very new with coding, so please bear with me, secondly;
I am currently trying to draw records from another database inside a network into my database. This has proved to be a little troublesome, because I would want to fill all fields in all tables that have the same primary key.
My current code looks like this
varPrimaryKey = InputBox("Specify primary key:")
strPrimaryKey = module1.Item1
If Not varPrimaryKey = "" Then
MsgBox ("Get data from: " & varPrimaryKey)
If Not (tdf.Name Like "MSys*" Or tdf.Name Like "~*") Then
For Each tdf In externalDb.TableDefs
For Each fld In tdf.Fields
db.Execute ("INSERT INTO CurrentDb.fld.Name SELECT fld.Name FROM tdf.Name WHERE fld.Name = 'Value' AND varPrimaryKey = 'Value'")
Next fld
Next tdf
End If
End If
Right now I'm getting a type mismatch error from .CurrentDb , but I have a feeling that there's something else wrong with this code too, just can't put my finger on it. If someone could help, I would really appreciate it!
Reconsider this entire approach. For user application needs, databases should not be copied versions of each other as gathered from above comment:
I meant that I would want to draw ALL records from ALL tables that
have the same primary key ID as the one that the user has entered
inside an input box
One of the central tenets of a relational database is to avoid duplication of data. Plus, if users add/edit data it will reflect live on the system. Data transference between databases should only be run for migration purposes where one is to be archived and other for production.
With that said, consider the following steps to build your user application:
Link all needed tables from network database. The GUI dialog allows a Select All feature or holding SHIFT and/or CTRL for multiple tables.
Build a temp table to hold current user's primary key and insert data value via VBA. This is the only table to hold data (one column/one row structure) in application database. See below steps:
Create a table with code or via Table Design (one row/one column)
CREATE TABLE TmpPrimaryKey (
PrimaryID Long
)
Append using user input as below shows with parameterization with VBA. This code should be run regularly for any change to PK. Ideally, run this at startup of application.
Dim qdef As QueryDef
Dim strSQL As String
Dim varPrimaryKey As Variant
varPrimaryKey = InputBox("Specify primary key:")
' CLEAN OUT TEMP TABLE
CurrentDb.Execute "DELETE FROM TmpPrimaryKey", dbFailOnError
' APPEND TO TEMP TABLE
strSQL = "PARAMETERS [PkParam] LONG;" _
& " INSERT INTO TmpPrimaryKey (PrimaryID) VALUES ([PkParam])"
Set qdef = CurrentDb.CreateQueryDef("", strSQL)
qdef![PkParam] = varPrimaryKey
qdef.Execute dbFailOnError
Set qdef = Nothing
Create a filtered query for every linked table aligning to TmpPrimaryKey (i.e., the target primary key). Doing so, the user will only see such records. Use these queries for forms/reports recordsources or module recordsets.
Queries can use the JOIN, IN, EXISTS clauses such as below examples of separate SQL statements. Tables below would be linked tables from network database (step #1).
Query1
SELECT src.*
FROM [Table1] src
INNER JOIN TmpPrimaryKey tmp ON src.ID = tmp.PrimaryID;
Query2
SELECT src.*
FROM [Table2] src
WHERE src.ID IN (SELECT PrimaryID FROM TmpPrimaryKey);
Query3
SELECT src.*
FROM [Table3] src
WHERE EXISTS
(SELECT 1 FROM TmpPrimaryKey tmp WHERE src.ID = tmp.PrimaryID);
Because you potentially have many tables, build above SQL queries in VBA loop using TableDefs and QueryDefs. NOTE: Below loop routine to create queries should be run only once.
Dim tdef As TableDef
Dim qdef As QueryDef
Dim strSQL As String
' LOOP THROUGH ALL TABLES OF APP DB (I.E., LINKED TABLES)
For Each tdef in CurrentDb.TableDefs
If tdef.Name <> "TmpPrimaryKey" And tdef.Name Not Like "MSys*" Then
' ASSUMING EACH TABLE'S PK IS NAMED ID
strSQL = "SELECT src.* FROM [" & tdef.Name & "] src" _
& " INNER JOIN TmpPrimaryKey tmp ON src.ID = tmp.PrimaryID;"
' NAME EACH QUERY SAME AS TABLE WITH "Q_PK" SUFFIX
Set qdef = CurrentDb.CreateQueryDef(tdef.Name & "Q_PK", strSQL)
Set qdef = Nothing
End If
Next tdef
Set tdef = Nothing
Again, set all needed application objects (forms, reports, modules, etc.) to point to these queries as the data sources and not linked tables, holding all data. Queries should be updateable for user to add/edit records.
From there, distribute copies of this application database to all users in a frontend/backend split architecture, maintaining one centralized and normalized database and many app files that hold no data (except of course, the temp PK value).
You just reference the table you want to INSERT into. What you need is path to the other db. Need to concatenate variables. You don't show declaring and setting variables db, tdf, fld, externalDB. Need to swap the If and first For lines. Your INSERT SELECT will not work the way you think, unless you really want each field inserted into its own record. Consider:
For Each tdf In CurrentDb.TableDefs
If Not (tdf.Name Like "MSys*" Or tdf.Name Like "~*") Then
CurrentDb.Execute ("INSERT INTO [" & tdf.Name & "] SELECT * FROM [" & tdf.Name & _
"] IN 'other db path\filename.accdb' WHERE [Value] = '" & varPrimaryKey & "'")
End If
Next tdf
However, autonumber fields will interfere with this simple INSERT SELECT. Also, fields in both tables must be arranged in same order in table design.
Value is a reserved word and really should avoid using reserved words as names for anything. If Value is a number data type then eliminate the apostrophe delimiters.
Why have that MsgBox?
But then why all this effort anyway and not just link to the backend tables?

How can I Automatically generate sql insert scripts when data is available in some specific template in microsoft excel?

How can I Automatically generate sql insert scripts when data is available in some specific template in microsoft excel?Say for example i have four columns in the excel file as table_name and the others as column_1,column_2 and column_3 and their respective values. Now based on the values present in these columns the insert scripts has to be generated, like insert into table_name (column_1,column_2,column_3) values('v1','v2','v3'); . Suggest me the best way by which i can do this? Instead of microsoft excel other options are also fine.
For Excel to create insert statements:
"INSERT INTO table_name VALUES('"&A1&"','"&B1&"','"&C1&"')"
or
"insert into product (product_id,name,date,price) values("&A1&",'" &B1& "','" &C1& "'," &D1& ");"

Insert into an access table from SQL using recordset

I am using the following code to insert data in an access table from SQL using a recordset. This table is further used for other operations. While this is inserting the data into the table perfectly, the time taken by this huge. Should I use any other method to insert data into the table to reduce the time taken?
Do Until rs.EOF
DoCmd.RunSQL "INSERT INTO Table (Alpha,Beta,Gamma) VALUES(" & _
rs.Fields(0).Value & ",'" & rs.Fields(1).Value & "'," & rs.Fields(2).Value _
& " );"
rs.MoveNext
Loop
Create a linked table to the SQL table, say it's called MyLinkedTable
Create an Append query to append to your local Access table from your linked table. It will look something like this: INSERT INTO MyAccessTable (Field1,Field2...) SELECT Field1,Field2... FROM MyLinkedTable;
If you could select the data in the SQL UPDATE statement instead looping in VBA it would take a fraction of the time as all the work would be done by the server side.
You just need to do an INSERT INTO SELECT. We need more information on your RecordSet but you probably do not need it.
'Here we go, with just one line!
DoCmd.RunSQL "INSERT INTO Table (Alpha,Beta,Gamma) SELECT column1, column2, column2 FROM YourTable"
The SELECT statement is probably the same as the one you used for opening your Recordset.
Good luck!

Is there a standard way to duplicate a row in a database table?

I want to duplicate a row, not the keys of course, without explicity using the field names.
Is there a SQL way or do I have to enumerate the field names through code?
I don't want to explicity use field names because I want to minimize code and db dependencies.
I am going to use it in the Ms Access 2003. I mention it in case that no standard way exists.
INSERT INTO `<table>` (column1, column2, ...) -- Not IDENTITY columns
SELECT column1, column2, ... FROM ...
This will also allow you to insert replacement values for the primary key columns, etc. I've used this, along with a common table expression, to take a set of test data from the month of February, and to pretend they're really from June.
I know you said you want to do it without the field names, but I don't think you can. It's also not a good idea, as it would tie you to the order of the columns.
If you don't have any uniques to worry about:
INSERT INTO <table> (SELECT * FROM <table> WHERE <condition>)
Otherwise, John Saunders' answer is probably your best bet.
If your primary key fields have automatic identifiers then you might well be able to script to interogate the system for fields which are not in the PK, and use the existing values for those that are not and only insert those ones (or to insert null for the PK fields).
Consequently I don't think there is going to be a "standard" way.
I'm not an Access person, but in SQL Server you can choose "Script table as --> Insert into" in SQL Server Management Studio. You can easily modify this to filter the rows you want into an INSERT INTO SELECT statement.
Perhaps something like this exists in Access?
Like folks have stated before me, you can do "INSERT INTO TBL SELECT * FROM TBL WHERE X=Y" and you will get one row. And this will fail if you have a primary key.
If you do not have a PK then you probably have bigger problems.
Is this a linked table? If so, there are no database dependencies, because you are dealing with an ODBC link. In that case, you can easily use this to get a list of columns for the table:
SELECT TOP 0 * FROM TBL (on linked tbl will need a round trip to server)
You get a blank recordset, and you just iterate through the columns.
Ms Access 2003 oriented solution
I have a form where the user can press a button to create a new version of the current record.
That part in Ms Access is easy:
DoCmd.GoToRecord , , acNewRec
Now I need to update all the fields on the form (controls are bind with table fields) except the key, ie "id" field, with data from some other record.
I came up with the below routine, which worked good for me:
Private Sub UpdateRow(tblname As String, key_name As String, key_value As String)
Dim Rst As Recordset
Dim field As field
Set DB = CurrentDb
Set Rst = DB.OpenRecordset("select * from " & tblname & " where " & _
key_name & "=" & key_value, dbOpenDynaset)
For Each field In Rst.Fields
If field.Name <> key_name Then
Form(field.Name) = field
End If
Next field
Rst.Close
Set Rst = Nothing
Set DB = Nothing
End Sub
And I use it like this:
DoCmd.GoToRecord , , acNewRec
UpdateRow "TableName", "KeyName", "some_previous_key_value"
Form.Refresh
You would need to explicitly supply the field names for the keys when you supply replacement values, therefore a 'standard' way is simply not possible.
...unless all you tables have a single key, all with the same name (ID is popular), and each key consists of a single column that has the IDENTITY (autonumber) property, in which case you would in fact have no keys at all, merely a way of using the IDENTITY value to uniquely identify your duplicate rows!