MS Access - Date as Table Field Name - ms-access

I need to create a table in MS Access, then append columns with DATES as the field names based upon a user-provided date range (StartDate, EndDate), like this:
LastName | FirstName | Role | 10/01/2017 | 10/02/2017 | ....
The following snippet comes close, but can only use dates formatted as "Oct01" (mmmdd), vs the desired "10/01/2017". I swear my earliest attempts did produce the desired date format as the field name, but I cannot seem to reproduce - guessing a syntax issue on "format";
Dim db As Database
Dim StartDate As Date
Dim EndDate As Date
Dim strDate As String
Set db = CurrentDb
StartDate = #10/1/2017#
strDate = Format(StartDate, "mmmdd")
db.Execute "CREATE TABLE MyTable " & _
"(LastName CHAR, FirstName CHAR, Role CHAR);"
db.Close
CurrentDb.Execute "ALTER TABLE myTable ADD COLUMN " & Format(StartDate, "mmmdd") & " CHAR"
StartDate = StartDate + 1
CurrentDb.Execute "ALTER TABLE myTable ADD COLUMN " & Format(StartDate, "mmmdd") & " CHAR"
...

Enclose the field name in square brackets like this:
CurrentDb.Execute "ALTER TABLE myTable ADD COLUMN [10/02/1017] CHAR"
The square brackets allow you to use spaces or other special characters in identifiers. You will need to ensure you also use the brackets when referencing the field name in any other SQL Statements.
Even though you can do this, it is really not recommended practice to use special characters in identifier names.

Related

MS Access vba to change values in a column

I need to change values in a column titled "CURRENT QUARTER" from .NULL. to "2017 Q2" the number of values is very large so I am trying to more than 10,000 so need to do it via a macro. Any one knows how to do this? I only have experience on VBA in excel
You can create a saved update query and run it. Or:
Dim sqltext as string
sqltext = "Update tablename SET [CURRENT QUARTER] = " & chr(34) & 2017 Q2 &chr(34) & "WHERE [CURRENT QUARTER] Is Null;"
Docmd.RunSql sqltext
Replace tablename with the name of your table.

How to insert a date value into an MDB database using VBScript?

I would like to know what I should do to insert some dates into a table. My table has 4 columns:
ID (AutoNumber)
First_Name
Last_Name
Date
I would like to insert some data with VBScript. Here is what I have so far:
sub DBinsert(fname, lname)
Set objCon= CreateObject("ADODB.Connection")
Set RS1 = CreateObject("ADODB.Recordset")
WScript.echo "DBInsert"
objCon.Open "Provider = Microsoft.Jet.OLEDB.4.0; Data Source = C:\Users\bonhkarl01\Desktop\Blank database.mdb"
objCon.execute(" Insert into table3(First_Name, Last_Name, Date) Values ('" & fname & "','" & lname & "','" & Date() & "') ")
End sub
It worked so far when I tried without the "Date" in another table... Is there anything wrong with the objCon.execute command?
The error I am getting is
Syntax error in INSERT INTO statement.
Date is a reserved word in Access SQL. If you need to refer to a column named Date then you must enclose it in square brackets.
objCon.execute(" Insert into table3 (First_Name, Last_Name, [Date]) Values ...

Using SQL in Query that auto updates

Thank you beforehand for your assistance. I know enough about Access, SQL, and VBA to get myself into trouble. Here is what I want to do.
I want to create a query that starts with a certain year and then lists each year up until the current year. The problem is that I want the query to automatically update as time progresses. In other words, say the start year is 2009, I want my query to list 2009, 2010, 2011, 2012, and 2013 since we are currently in the year 2013. Next year, the list will expand to include 2014. I suspect this is possible using a query in SQL but not sure how to go about coding it properly.
I bet that there is no simple solution for this simple process. We must use VBA to perform following steps:
Create a temporary table:
CREATE Table tblTmpYears (
ID COUNTER CONSTRAINT PrimaryKey PRIMARY KEY,
Year Long
);
In VBA:
Dim strSQL
strSQL = "CREATE Table tblTmpYears (" _
& " ID COUNTER CONSTRAINT PrimaryKey PRIMARY KEY," _
& " Year Long" _
& ");"
CurrentDb.Execute strSQL, dbFailOnError
Fill the temporary table:
INSERT INTO tblTmpYears (year) VALUES (2009);
INSERT INTO tblTmpYears (year) VALUES (2010);
INSERT INTO tblTmpYears (year) VALUES (2011);
INSERT INTO tblTmpYears (year) VALUES (2012);
INSERT INTO tblTmpYears (year) VALUES (2013);
In VBA, for 5 years, valid even after 100 years after our life existence:
Dim y as long, ymin, ymax, strSQL
ymax = Year(Date)
ymin = ymax - 4
For y = ymin to ymax
strSQL = "INSERT INTO tblTmpYears (Year) VALUES (" & y & ");"
CurrentDb.Execute strSQL, dbFailOnError
Next
Create a query for listing with the temporary table:
SELECT * FROM tblStudents INNER JOIN tblTmpYears
ON tblStudents.Year=tblTmpYears.Year
ORDER BY Year;
In VBA like this:
Dim qdf, strSQL
strSQL = "SELECT * FROM tblStudents INNER JOIN tblTmpYears" _
& " ON tblStudents.Year=tblTmpYears.Year" _
& " ORDER BY Year;"
Set qdf = CurrentDB.CreateQueryDef("qrySelTemporary", strSQL)
DoCmd.OpenQuery qdf.Name
Here you will have the Query Datasheet Windows with your students's list, it's printable. Even better, you can use it as
MyReport.RecordSource = "qrySelTemporary"
in an Access Report with a beautiful presentation.
Delete the temporary table after printing, for example:
DROP TABLE tblTmpYears;
In VBA:
Dim strSQL
strSQL = "DROP TABLE tblTmpYears;"
CurrentDb.Execute strSQL, dbFailOnError
Only VBA can accomplish this... rather than a single SQL query.
How about this - a small VBA function that outputs the SQL for an appropriate UNION query, which you can then assign as the RowSource for a combo box, use as a sub-query inside another dynamically generated query, or whatever:
Function CreateYearsToCurrentSQL(From As Integer) As String
Dim I As Integer, S As String
For I = From To Year(Date)
If I <> From Then S = S + "UNION "
S = S + "SELECT " & I & " AS Year FROM MSysObjects" + vbNewLine
Next I
CreateYearsToCurrentSQL = S
End Function
The FROM MSysObjects is because Access will whinge about no FROM clause if one isn't there, and MSysObjects is bound to be an existing table in an Access context (if you prefer though, replace it with the name of any other table).
So I managed to create a Query Criteria that does what I need.
Like (Right(Year(Now()),2)-3) & "-" Or Like (Right(Year(Now()),2)-2) & "-" Or Like (Right(Year(Now()),2)-1) & "-" Or Like Right(Year(Now()),2) & "-"
Thank you everyone for your efforts.

Do While Loop not giving me correct output string

I'm trying to assign a list of Names to a combobox control in Access VBA.
My problem is that the output string of names is not correct.
Here is my code:
Private Sub command186_click()
Dim firstName As String
Dim lastName As String
Dim rst As Object
Dim rowSourceText As String
Dim fullName As String
Set rst = CurrentDb.OpenRecordset("Pool_Contact")
Do While Not rst.EOF
firstName = rst("FName").Value
lastName = rst("LName").Value
fullName = firstName + " " + lastName
rst.MoveNext
Loop
Forms(FrmDaysAvailable).Controls("Combo202").rowSource = fullName
Debug.Print fullName
End Sub
I know that the error is somewhere inside of my loop, where the variable fullName is written over by the second result.
how can I fix this loop to produce a string that looks like fullName , fullName, fullName ...
Thanks for all your help
This can be a lot simpler:
Forms(FrmDaysAvailable).Controls("Combo202").rowSource = _
"SELECT ID, FName & ' ' & LName FROM Pool_Contact"
Or
Forms!FrmDaysAvailable.Combo202.rowSource = _
"SELECT ID, FName & ' ' & LName FROM Pool_Contact"
Or
Me.Combo202.rowSource = "SELECT ID, FName & ' ' & LName FROM Pool_Contact"
Furthermore, use & not + to concatenate. Plus (+) will give you problems with nulls.
You must add each item to the ComboBox, instead you are only adding the last one
Do While Not rst.EOF
firstName = rst("FName").Value
lastName = rst("LName").Value
fullName = firstName & " " & lastName
Me!Combo202.AddItem(fullName)
rst.MoveNext
Loop
Also you should declare rst as DAO.Recordset not as object. (You might have to add a reference to the DAO dll).
Optionally you can assign a table or a query directly to the row source of the ComboBox and drop the loop completely
Me!Combo202.RowSource = "Pool_Contact"
But you can do that in the form designer and do not need to do it in VBA at all. If you need to refresh the contents of the ComboBox you can simply write
Me!Combo202.Requery
Note: I assume that Forms(FrmDaysAvailable) is the current form. In that case you can simply address it through Me. Further, the Controls collection is the default property of a form. Forms(FrmDaysAvailable).Controls("Combo202") can be simplyfied to Me("Combo202") or even to Me!Combo202 with the VBA collection access operator !.
I also suggest you to give your ComboBox (and other controls) meaningful names like cboFullName. This makes the code more readable. I usually make a query corresponding to the ComboBox with the same name prefixed with "q": qcboFullName and assign this to the RowSource of the combo in the properties window. A query has the advantage over a table that you can apply a "ORDER BY" and select exactly the columns needed for the ComboBox.
Typically you would have a hidden ID column (enter 0 in the column width property) as result of the user selection and a string column for display.
SELECT PersonID, firstName & ' ' & lastName AS Display
FROM tblPerson
ORDER BY firstName, lastName

Loop through Access tables

I'm creating a database in Access that will have many similar tables with identical and the names of them will all be named in sequential order, such as table_0, table_1...
I wanted to know if there is a way to make a loop in VBA to first make the tables, and them altering them, such as adding a field easier.
So if I were to make the tables, this would be the process, but in VBA
while(i=0, i<20,i++){
CREATE TABLE table_i(
field_1 int PRIMARY KEY,
field_2 CHAR(255));
}
In VBA, you can loop through your numbered table names like this ...
Dim strTable As String
Dim i As Long
For i = 0 To 20
strTable = "table_" & CStr(i)
Debug.Print strTable
Next i
But you want to do something with each table name other than print it. So say you've already worked out your CREATE TABLE statement. Maybe it looks like this ...
CREATE TABLE table_name (
field_1 INTEGER PRIMARY KEY,
field_2 TEXT(255));
So you could load that DDL statement into a string variable, then each time through your For loop replace table_name with the current value of strTable, and execute that DDL statement.
Dim strTable As String
Dim i As Long
Dim strSql As String
strSql = "CREATE TABLE table_name (" & vbCrLf & _
"field_1 INTEGER PRIMARY KEY," & vbCrLf & _
"field_2 TEXT(255));"
For i = 0 To 20
strTable = "table_" & CStr(i)
CurrentProject.Connection.Execute Replace(strSql, _
"table_name", strTable)
Next i
That Replace() function first became available with Access 2000. If you're using an older Access version, you'll need a different method to handle your SQL string.
If you want to execute an ALTER TABLE statement, you could do that instead.
So I think doing what you want can be easily done with VBA. However I'm uncertain whether you should do it. Multiple tables with identical structure is generally a red flag signalling a design error. There is no evidence to conclude it's a design error in your case. OTOH, there is no evidence to conclude it's not a design error. ;-)