Field types available for use with "CREATE TABLE" in Microsoft Access - sql

I have the displeasure of generating table creation scripts for Microsoft Access. I have not yet found any documentation describing what the syntax is for the various types. I have found the documentation for the Create Table statement in Access but there is little mention of the types that can be used. For example:
CREATE TABLE Foo (MyIdField *FIELDTYPE*)
Where FIELDTYPE is one of...? Through trial and error I've found a few like INTEGER, BYTE, TEXT, SINGLE but I would really like to find a page that documents all to make sure I'm using the right ones.

I've found the table in the link below pretty useful:
http://allenbrowne.com/ser-49.html
It lists what Access's Gui calls each data type, the DDL name, DAO name and ADO name (they are all different...).

Some of the best documentation from Microsoft on the topic of SQL Data Definition Language (SQL DDL) for ACE/Jet can be found here:
Intermediate Microsoft Jet SQL for Access 2000
Of particular interest are the synonyms, which are important for writing portable SQL code.
One thing to note is that the Jet 4.0 version of the SQL DDL syntax requires the interface to be in ANSI-92 Query Mode; the article refers to ADO because ADO always uses ANSI-92 Query Mode. The default option for the MS Access interface is ANSI-89 Query Mode, however from Access2003 onwards the UI can be put into ANSI-92 Query Mode. All versions of DAO use ANSI-89 Query Mode. I'm not sure whether SQL DDL syntax was extended for ACE for Access2007.
For more details about query modes, see
About ANSI SQL query mode (MDB)

This has it all. It's direct from MS, and actually tells you what the SQL datatype is that correlates to the GUI name.

Related

Migrate data from SQL Server to PostgreSQL

I have a stored procedure function as well as table in the SQL Server enterprise 2014. I also have data in the table. Now I need same table and data in PostgreSql(pgAdmin4).
Can anyone suggest to me the idea to migrate data to POSTGRESQL or any idea on creating the SQL script so that I can use psql to run the script?
Depending on how much data you have, you could script out the table and data. Then you could tweak the script as needed for PostgreSQL:
Right click on the SQL database > Tasks > Generate Scripts
On the "Choose Objects" screen, select your specific table then select "Next>"
On the "Set Scripting Options" screen, select "Advanced"
Find the option called "Types of data to script", then select "Schema and data" and select "OK"
Set the filename and continue through the dialog until the file is generated
Tweak the sql script for any specific PostgreSQL syntax
If there is a larger amount of data, you might look into some type of data transfer tool like SSIS.
Exporting the table structure and data as Josh Jay describes will likely require some fixes where the syntax doesn't match, but it should be doable if not tedious. Luckily there are existing conversion tools available to help.
You could also try using a foreign data wrapper to map the tables in SQL Server to a running instance of PostgreSQL. Then it's just a matter of copying tables. Depends on your needs and where each database server is located relative to one another.
The stored procedures will be far more difficult to handle unfortunately. While Oracle's pl/sql language is substantially similar to PostgreSQL's pl/pgsql, MS SQL Server/Sybase's TransactSQL dialect on the other hand is different enough to require rewrites. If the TransactSQL functions also access .Net objects, the migration task may end up far more difficult as you reimplement dependencies or find logical equivalents.

CREATE VIEW in MS ACCESS with SQL returning Syntax error CREATE TABLE

I am trying to CREATE VIEW in access in SQL view but I am getting a syntax error for CREATE TABLE which is highlighting the word VIEW. This is in Access 2016 via Office 365 (latest update as of 2/11/2019). The SELECT statement works by itself, but the CREATE VIEW command isn't. My book (Concepts of Database Management) is designed for use specifically alongside Access. My code is as such:
CREATE VIEW TopLevelCust AS
SELECT CustomerNum, CustomerName, Street, Balance, CreditLimit
FROM Customer
WHERE CreditLimit>=10000
;
As already stated in Lynn's answer, if you want to execute this query, you can do that after turning on SQL server compatible syntax.
However, you can also execute the query using an OLEDB connection to the Access database.
You can even do this using VBA and the already preset CurrentProject.Connection object:
CurrentProject.Connection.Execute "CREATE VIEW Query1 AS SELECT 1"
Without turning on SQL server compatible syntax, DDL statements executed from Access itself are fairly limited (for example, you can also not use the Decimal data type). But these DDL statements are not really meant to be executed from Access itself, VBA provides way better tools to create queries (that also allows creating pass-through queries, for example).
According to the asker and other users, enabling ANSI-92 SQL in the database options will allow you to execute the DDL statement CREATE VIEW.
File > Options > Object Designers > Query Design.
According to Wolfgang, under the hood, this actually creates a query.
<SoapBox>
It surprises me that your text reference requests you to execute statements that aren't enabled by default in Access, especially without a special note screaming at you that you need to enable a special option before database creation. ¯\_(ツ)_/¯
</SoapBox>

Generic SQL that both Access and ODBC/Oracle can understand

I have a MS Access query that is based on a linked ODBC table (Oracle).
I'm troubleshooting the poor performance of the query here: Access not properly translating TOP predicate to ODBC/Oracle SQL.
SELECT ri.*
FROM user1_road_insp AS ri
WHERE ri.insp_id = (
select
top 1 ri2.insp_id
from
user1_road_insp ri2
where
ri2.road_id = ri.road_id
and year(insp_date) between [Enter a START year:] and [Enter a END year:]
order by
ri2.insp_date desc,
ri2.length desc,
ri2.insp_id
);
The documentation says:
When you spot a problem, you can try to resolve it by changing the local query. This is often difficult to do successfully, but you may
be able to add criteria that are sent to the server, reducing the
number of rows retrieved for local processing.
In many cases you will find that, despite your best efforts, Office Access still retrieves some entire tables unnecessarily and
performs final query processing locally.
However, it's occurred to me that I don't really understand what sort of SQL I should be writing to make both Access and ODBC/Oracle happy.
Should I be writing some sort of generic SQL that Access can understand in a local query AND that can be easily translated to ODBC/Oracle SQL? Is generic SQL a real thing?
What kind of SQL does the ODBC driver use? It depends as typically MS Access has three types of external data connections that interfaces with different SQL dialects each with the ODBC API.
Linked tables that acts like local tables but are ODBC connected data sources and not stored locally. Once they are incorporated in an Access app, these tables can only use MS Access' SQL dialect. They can be joined with local or even other backend tables from other sources.
Hence, why TOP is available in MS Access and not Oracle. You are essentially using Access SQL to manipulate Oracle data. ODBC serves as the origin point of data while Access' Jet/ACE SQL engine does the processing and resultset viewing in cached memory.
Pass-through queries that do not see local tables or anything else in local app's environment. Such queries use the SQL dialect of the connected database here being Oracle.
Hence, why TOP is NOT available in Oracle and double quotes are allowed in column identifiers. Such quoting would fail in MS Access. Essentially, you are using Oracle SQL to manipulate Oracle data in an Access app. You can take the output of the sqlout.txt log and run it in a pass-through query ODBC-connected to your Oracle database.
ADO/DAO Recordsets that are run entirely via code such as VBA and are direct connections to data sources and uses the connecting database's dialect.
Here, you using Oracle SQL to manipulate Oracle data in an Access app via the ODBC API.
In each one of these types, you will have to connect to a backend ODBC data source. You do not even need to use the GUI but can use Access' object library to create linked tables (see DoCmd.TransferDatabase) and pass through querydefs (see QueryDef.Connect or .Execute).
I suspect the sqlout.txt log you see are translations of the ODBC calls to its native dialect.
To build on #Parfait's point #1:
From Microsoft Access Developer's Guide to SQL Server by Mary Chipman and Andy Baron:
Optimizing Access Queries:
There's a common misconception that the Jet engine always retrieves all the data in linked SQL Server tables and then processes the data locally. This is not usually true. Jet is perfectly capable of sending efficient queries to SQL Server over ODBC and retrieving only the rows required. However, in some cases, Jet will in fact be forced to fetch all the data in certain tables first and then process it. You should be aware of when you are forcing Jet to do this and be sure that it is justified. The following are some general guidelines to follow when creating your Access queries:
Using expressions that can't be evaluated by the server will cause Jet to retrieve all the data required to evaluate those expressions locally. The impact of using Access-specific expressions, such as domain aggregate functions, Access financial functions, or custom VBA functions will vary depending on where in your query the expressions are used. Using such an expression in the SELECT clause will usually not cause a problem because no extra data will be returned. However, if the expression is in the WHERE clause, that criterion cannot be applied on the server, and all the data evaluated by the expression will have to be returned.
With multiple criteria, as many as possible will be processed on the server. This means that even if you use criteria that you know include functions that will need to be processed by Jet, adding other criteria that can be handled by the server will reduce the number of records that Jet has to process. Adding criteria on indexed columns is especially helpful.
Query syntax that includes an Access-specific extension to SQL, not supported by the ODBC driver, may force processing to be done on the client by Access. For example, even though SELECT TOP 5 PERCENT is now supported by SQL Server, it is not supported by the ODBC driver. If you use that syntax in an Access query, Jet will need to retrieve all the records and calculate which ones are in the top 5 percent. On the other hand, even though crosstab queries are specific to Access, Jet will translate them into simple GROUP BY queries and fetch just the required data in one trip to the server unless problematic criteria is used.
Heterogeneous joins between local and remote tables or between remote tables that are in different data sources will, of course, have to be processed by Jet after the source data is retrieved. However, if the remote join field is indexed and the table is large, Jet will often use the index to retrieve only the required rows by making multiple calls to the remote table, one fore each row required.
Jet allows you to mix data types within [typo - fix later] of UNION queries and within expressions, but SQL server doesn't. Such mixing of data types will force processing to be done locally.
Multiple outer joins in one query will be processed locally.
The most important factor is reducing the total number of records being fetched. Jet will retrieve multiple batches of records in the background until the result set is complete, so even though you may seem to get results back immediately, a continuing load is being placed on the server for large result sets.
Note: this book is quite old (published in 2000) and is in reference to Jet Engine. I imagine things might be slightly different in newer versions of Access which use ACE, although I don't have a source to back this up.

Moving from Oracle SQL to ANSI SQL pros and cons

I work in a project where the UI has direct access to the database through SQL code. The company has a framework where we create UI pages in xml and after that it is parsed and creates FLEX pages. If we want some data from the DB (Oracle) we add a sql query in the xml (instead of databinding with a datacontext object like we could do with WPF). If we want to add some logic, there is no code behind, we call store procedures. After we have the data we need the parser does the job.
The new requirements are to use the framework and create a new product that will be compatible with SQL Server and the thoughts are to start transforming the (Oracle)SQL queries to ANSI SQL.
Can somebody tell me the benefits and mainly the problems that we are going to face doing that?
Do you think there is a better way?
Note: The framework is really big and there are a lot of products built on that so managers are not keen to just throw it away(I tried but.. :))
Each dialect of SQL is different. You could use ANSI SQL but a) not all of ANSI SQL is implemented by most DBMS and b) most DBMS's have implementation-specific optimisations which will perform better for some cases.
So I'd say, don't go for ANSI SQL. It won't always work and sometimes it will work slower than taking advantage of a vendor's non-standard implementations.
Specifically, Oracle requires a StoredProcedure to return a REF_CURSOR from a stored procedure to fill a DataSet. SQL Server doesnt; the SP returns what the sp SELECTed. You're going to have to change your SP's to get rid of the returned REF_CURSOR.
Date handling is quite different: Oracle needs a to_date to turn a string into a date in where clauses etc; SQL Server just takes the string and converts it for you. And so on and so on. (I'm not at all sure what the ANSI Standard is, or even if it covers this!) To avoid changing your SQL you could add create SQL Server function called to_date, but this is now going to slow up your SQL.
If you have much PL/SQL in stored procedures, you have a big job converting it to T-SQL. They are quite different.
Good luck!

Are table names in query case-insensitive?

I have read the following article. They have quoted that,
SQL Server is a case-sensitive back-end application. This means that a
table named "addr" is distinguished from a table named "ADDR."
However, because Microsoft Query is an MS-DOS-based application, it is
unable to distinguish cases; therefore, Microsoft Query views "addr"
and "ADDR" as the same file.
Now I wanted to know what to they mean by case-sensitive back-end application? Is it safe to use the query with case-insensitivity?
Thanks in advance.
SQL Server with default collation will return you the same result, doesn't matter which case you use for your query.
Collation can be set at various levels
Server
Database
Column
For more info can be found out here
Please check Applies To section of the article you referenced. KB article applies to product from Microsoft for which they no longer provide any support.