David Matsumoto
asked on
Workaround for Concatation Expression that Truncates a Memo Field
The following is truncating exp_UpdateDateNotes:
fld_ActionPlanTargetCloseN otes is the memo field being truncated in exp_UpdateDateNotes.
How can I prevent this truncation?
(Please don't post any links to other workarounds. I'm an auditor, not a programmer. I pay for this service to have my solutions customized and hand-fed to me. I can do my own searches if I'm wanting general answers. I'm not trying to be difficult...just saying, for whichever solution I mark as being correct.)
SELECT tbl_ActionPlanUpdates.fld_ ActionPlan Number, "As of " & [tbl_ActionPlanUpdates]![f ld_ActionP lanUpdateD ate] & " >> " & [tbl_ActionPlanUpdates]![f ld_ActionP lanTargetC loseNotes] AS exp_UpdateDateNotes
FROM tbl_ActionPlanUpdates
WHERE (((tbl_ActionPlanUpdates.f ld_ActionP lanTargetC loseNotes) <>IsEmpty( [tbl_Actio nPlanUpdat es]![fld_A ctionPlanT argetClose Notes])))
ORDER BY tbl_ActionPlanUpdates.fld_ ActionPlan Number, tbl_ActionPlanUpdates.fld_ ActionPlan UpdateDate DESC;
FROM tbl_ActionPlanUpdates
WHERE (((tbl_ActionPlanUpdates.f
ORDER BY tbl_ActionPlanUpdates.fld_
fld_ActionPlanTargetCloseN
How can I prevent this truncation?
(Please don't post any links to other workarounds. I'm an auditor, not a programmer. I pay for this service to have my solutions customized and hand-fed to me. I can do my own searches if I'm wanting general answers. I'm not trying to be difficult...just saying, for whichever solution I mark as being correct.)
What are you doing with the results of this query?
Memo fields normally get truncated when you try to use them in queries that include DISTINCT, or Group By clauses, but this particular query doesn't appear to have that issue.
They will also be truncated when used as a field in a listbox or combo box (max field width in those controls is 255), or if you try to simply use a TransferSpreadsheet to export this to EXCEL.
Memo fields normally get truncated when you try to use them in queries that include DISTINCT, or Group By clauses, but this particular query doesn't appear to have that issue.
They will also be truncated when used as a field in a listbox or combo box (max field width in those controls is 255), or if you try to simply use a TransferSpreadsheet to export this to EXCEL.
ASKER
Okay - try this variation:
SELECT tbl_ActionPlanUpdates.fld_ActionPlanNumber, [tbl_ActionPlanUpdates]![fld_ActionPlanTargetCloseNotes], tbl_ActionPlanUpdates.fld_ActionPlanUpdateDate FROM tbl_ActionPlanUpdates WHERE (False)
UNION ALL
SELECT tbl_ActionPlanUpdates.fld_ActionPlanNumber, "As of " & [tbl_ActionPlanUpdates]![fld_ActionPlanUpdateDate] & " >> " & [tbl_ActionPlanUpdates]![fld_ActionPlanTargetCloseNotes] AS exp_UpdateDateNotes, tbl_ActionPlanUpdates.fld_ActionPlanUpdateDate
FROM tbl_ActionPlanUpdates
WHERE tbl_ActionPlanUpdates.fld_ActionPlanTargetCloseNotes & "" <> ""
ORDER BY tbl_ActionPlanUpdates.fld_ActionPlanNumber, tbl_ActionPlanUpdates.fld_ActionPlanUpdateDate DESC
ASKER
fyed,
I'm using this first query in a subsequent query:
This second query is used in a third query:
I did all this with the Access query builders - hence, why it's not pretty at all.
I'm using this first query in a subsequent query:
SELECT qry_CurrentActionPlans_Not es_Detail. fld_Action PlanNumber , fConcatFld("qry_CurrentAct ionPlans_N otes_Detai l","fld_Ac tionPlanNu mber","exp _UpdateDat eNotes","s tring",[fl d_ActionPl anNumber]) AS exp_FullNotes
FROM qry_CurrentActionPlans_Not es_Detail
GROUP BY qry_CurrentActionPlans_Not es_Detail. fld_Action PlanNumber ;
FROM qry_CurrentActionPlans_Not
GROUP BY qry_CurrentActionPlans_Not
This second query is used in a third query:
SELECT qry_CurrentActionPlans_Max UpdateDate .MaxOffld_ ActionPlan UpdateDate , tbl_ActionPlans.fld_Action PlanNumber , qry_CurrentActionPlans_Max UpdateDate .exp_Attes tUpdateCon tact, tbl_ActionPlans.fld_Action PlanTitle, qry_CurrentActionPlans_Des cription.e xp_FullDes cription, qry_CurrentActionPlans_Max TargetClos eDate.MaxO ffld_Actio nPlanTarge tCloseDate , qry_CurrentActionPlans_Not es.exp_Ful lNotes, tbl_ActionPlans.fld_Action PlanActual CloseDate, tbl_ActionPlans.fld_IssueN umber
FROM (((qry_CurrentActionPlans_ MaxUpdateD ate RIGHT JOIN tbl_ActionPlans ON qry_CurrentActionPlans_Max UpdateDate .fld_Actio nPlanNumbe r = tbl_ActionPlans.fld_Action PlanNumber ) LEFT JOIN qry_CurrentActionPlans_Des cription ON tbl_ActionPlans.fld_Action PlanNumber = qry_CurrentActionPlans_Des cription.f ld_ActionP lanNumber) LEFT JOIN qry_CurrentActionPlans_Max TargetClos eDate ON tbl_ActionPlans.fld_Action PlanNumber = qry_CurrentActionPlans_Max TargetClos eDate.fld_ ActionPlan Number) LEFT JOIN qry_CurrentActionPlans_Not es ON tbl_ActionPlans.fld_Action PlanNumber = qry_CurrentActionPlans_Not es.fld_Act ionPlanNum ber;
FROM (((qry_CurrentActionPlans_
I did all this with the Access query builders - hence, why it's not pretty at all.
@songwritingcpa
I get the issue with the "pretty" and all of the ( ) in the joins.
It is the Group By clause in your 2nd query that is causing the truncation. What I would consider is trying to see if you can remove the fnconcat( ) function from the 2nd query, and incorporate that into the 3rd, somehow.
I get the issue with the "pretty" and all of the ( ) in the joins.
It is the Group By clause in your 2nd query that is causing the truncation. What I would consider is trying to see if you can remove the fnconcat( ) function from the 2nd query, and incorporate that into the 3rd, somehow.
ASKER
mbizup,
exp_UpdateDateNotes yields no values (they look blank in datasheet view). Also, I'm not sure if this is relevant or not -- the column ends up being titled "tbl_ActionPlanUpdates]![f ld_ActionP lanTargetC loseNotes" .
exp_UpdateDateNotes yields no values (they look blank in datasheet view). Also, I'm not sure if this is relevant or not -- the column ends up being titled "tbl_ActionPlanUpdates]![f
for readability (in code and in the ACCESS SQL query window) you might also want to consider inserting hard breaks in your SQL statements to make them more readable. Makes is significantly easier to read and edit in the Access SQL view:
SELECT qry_CurrentActionPlans_Max UpdateDate .MaxOffld_ ActionPlan UpdateDate
, tbl_ActionPlans.fld_Action PlanNumber
, qry_CurrentActionPlans_Max UpdateDate .exp_Attes tUpdateCon tact
, tbl_ActionPlans.fld_Action PlanTitle
, qry_CurrentActionPlans_Des cription.e xp_FullDes cription
Another suggestion would be to use aliases for your query and table names.
SELECT qry_CurrentActionPlans_Max
, tbl_ActionPlans.fld_Action
, qry_CurrentActionPlans_Max
, tbl_ActionPlans.fld_Action
, qry_CurrentActionPlans_Des
Another suggestion would be to use aliases for your query and table names.
The group by in the second query is definitely problematic... however I believe the concatenation in the first query is at issue too.
Try this, independently of the outer queries
Anyhow - I'm going to step back and let Dale follow up here to avoid confusing you with two people independently working on different parts of your query.
Try this, independently of the outer queries
SELECT tbl_ActionPlanUpdates.fld_ActionPlanNumber, [tbl_ActionPlanUpdates]![fld_ActionPlanTargetCloseNotes] AS exp_UpdateDateNotes, tbl_ActionPlanUpdates.fld_ActionPlanUpdateDate FROM tbl_ActionPlanUpdates WHERE (False)
UNION ALL
SELECT tbl_ActionPlanUpdates.fld_ActionPlanNumber, "As of " & [tbl_ActionPlanUpdates]![fld_ActionPlanUpdateDate] & " >> " & [tbl_ActionPlanUpdates]![fld_ActionPlanTargetCloseNotes] AS exp_UpdateDateNotes, tbl_ActionPlanUpdates.fld_ActionPlanUpdateDate
FROM tbl_ActionPlanUpdates
WHERE tbl_ActionPlanUpdates.fld_ActionPlanTargetCloseNotes <>IsEmpty([tbl_ActionPlanUpdates]![fld_ActionPlanTargetCloseNotes])
ORDER BY tbl_ActionPlanUpdates.fld_ActionPlanNumber, tbl_ActionPlanUpdates.fld_ActionPlanUpdateDate DESC
Anyhow - I'm going to step back and let Dale follow up here to avoid confusing you with two people independently working on different parts of your query.
ASKER
Okay, y'all, don't hate me. I'm discovering that the problem isn't with the first query. The raw data appears truncated in some of the Excel files that I received from our global team members. I copy/paste these into the Access record, though when the Excel cell does exceed 255, the copy/paste still works. Indeed, as fyed claims, the problem is with the "Group By" query.
fyed,
How do you suggest that I overcome the truncation problem in the second query? The whole purpose of the second query is concatenating the many instances of exp_UpdateDateNotes into one field (grouped by fld_ActionPlanNumber) that can be used for other queries. If I tried to incorporate the concatenation into the third query, wouldn't I run into the same problem? (Not to mention, it would be that much harder to keep track of what was happening in a more complex query.)
See screenshots of the Access query builders for #2 and #3, if that helps overcome the mess of SQL.
2nd-Query---Group-By.jpg
3rd-Query.jpg
fyed,
How do you suggest that I overcome the truncation problem in the second query? The whole purpose of the second query is concatenating the many instances of exp_UpdateDateNotes into one field (grouped by fld_ActionPlanNumber) that can be used for other queries. If I tried to incorporate the concatenation into the third query, wouldn't I run into the same problem? (Not to mention, it would be that much harder to keep track of what was happening in a more complex query.)
See screenshots of the Access query builders for #2 and #3, if that helps overcome the mess of SQL.
2nd-Query---Group-By.jpg
3rd-Query.jpg
Miriam,
I've never tried that technique to force a field to a particular data type when doing a concatenation. I'll have to play with that later.
@songwritingcpa,
Lets do this one step at a time.
When you run the first query, by itself, is the field concatenated?
If so, I would definitely try Miriam's technique of the union query. My perception of what Miriam (mbizup) is trying to accomplish with the first part of the union is to force Access to interpret that 2nd field as a string (without concatenation). I have not tried that, but it might work.
Personally, I would replace the IsEmpty part of that query with
WHERE tbl_ActionPlanUpdates.fld_ ActionPlan TargetClos eNotes & "" <> ""
This syntax will take what is in the CloseNotes field and append an empty string to it so that you can compare it to an empty string. If ...CloseNotes contains a NULL, attempting to compare it to anything will result in a NULL, so you need this type of context to make the test. I see Miriam also used that syntax in one of her sample queries above as well.
After we have determined that the first part of the query works, then we will work on rewriting the 2nd and 3rd parts.
I've never tried that technique to force a field to a particular data type when doing a concatenation. I'll have to play with that later.
@songwritingcpa,
Lets do this one step at a time.
When you run the first query, by itself, is the field concatenated?
If so, I would definitely try Miriam's technique of the union query. My perception of what Miriam (mbizup) is trying to accomplish with the first part of the union is to force Access to interpret that 2nd field as a string (without concatenation). I have not tried that, but it might work.
Personally, I would replace the IsEmpty part of that query with
WHERE tbl_ActionPlanUpdates.fld_
This syntax will take what is in the CloseNotes field and append an empty string to it so that you can compare it to an empty string. If ...CloseNotes contains a NULL, attempting to compare it to anything will result in a NULL, so you need this type of context to make the test. I see Miriam also used that syntax in one of her sample queries above as well.
After we have determined that the first part of the query works, then we will work on rewriting the 2nd and 3rd parts.
ASKER
The two columns of my original query (that I first posted) and Miriam's union query (minus the third column) produce the same exact results -- same number of records, and same number of characters (per a word count in Word).
I have multiple dimensions of concatenation going, so I want to clarify. The first query is concatenated in the simple sense. For example, [Date] & " >> " & [Notes] works.
The second query is where the more complex "vertical" concatenation occurs, with the fConcatFld function.
I have multiple dimensions of concatenation going, so I want to clarify. The first query is concatenated in the simple sense. For example, [Date] & " >> " & [Notes] works.
The second query is where the more complex "vertical" concatenation occurs, with the fConcatFld function.
Since the purpose of Query2 is to concatenate all of the [...CloseNotes] fields for a particular [fld_ActionPlanNumber], I believe you can forgo that query entirely. The fConcatFld function does the aggregation for you, so you may be able to simply add the concatenation function to Query3.
What I'm not sure of is whether qry_CurrentActionPlans, qry_CurrentActionPlans_Des cription, qry_CurrentActionPlans_Max TargetClos eDate, and qry_CurrentActionPlans_Not es play in this.
If query #2 above is the "qry_CurrentActionPlans_No tes" query (and it appears to be), then you would need to drop that query it from the SQL below.
Try:
What I'm not sure of is whether qry_CurrentActionPlans, qry_CurrentActionPlans_Des
If query #2 above is the "qry_CurrentActionPlans_No
Try:
SELECT qry_CurrentActionPlans_MaxUpdateDate.MaxOffld_ActionPlanUpdateDate
, tbl_ActionPlans.fld_ActionPlanNumber
, qry_CurrentActionPlans_MaxUpdateDate.exp_AttestUpdateContact
, tbl_ActionPlans.fld_ActionPlanTitle
, qry_CurrentActionPlans_Description.exp_FullDescription
, qry_CurrentActionPlans_MaxTargetCloseDate.MaxOffld_ActionPlanTargetCloseDate
, qry_CurrentActionPlans_Notes.exp_FullNotes
, tbl_ActionPlans.fld_ActionPlanActualCloseDate
, tbl_ActionPlans.fld_IssueNumber
, fConcatFld("qry_CurrentActionPlans_Notes_Detail","fld_ActionPlanNumber", "exp_UpdateDateNotes","string",[fld_ActionPlanNumber]) AS exp_FullNotes
FROM (((qry_CurrentActionPlans_MaxUpdateDate
RIGHT JOIN tbl_ActionPlans
ON qry_CurrentActionPlans_MaxUpdateDate.fld_ActionPlanNumber = tbl_ActionPlans.fld_ActionPlanNumber)
LEFT JOIN qry_CurrentActionPlans_Description
ON tbl_ActionPlans.fld_ActionPlanNumber = qry_CurrentActionPlans_Description.fld_ActionPlanNumber)
LEFT JOIN qry_CurrentActionPlans_MaxTargetCloseDate
ON tbl_ActionPlans.fld_ActionPlanNumber = qry_CurrentActionPlans_MaxTargetCloseDate.fld_ActionPlanNumber)
LEFT JOIN qry_CurrentActionPlans_Notes
ON tbl_ActionPlans.fld_ActionPlanNumber = qry_CurrentActionPlans_Notes.fld_ActionPlanNumber;
ASKER
"The specified field '[fld_ActionPlanNumber]' could refer to more than one table listed in the FROM clause of your SQL statement".
I copy/pasted your SQL into a new query. Was that correct?
Error-Message.jpg
I copy/pasted your SQL into a new query. Was that correct?
Error-Message.jpg
Yes, the problem now becomes that all of your queries contain that ActionPlanNumber field, so the fConcatFld function needs to know which table/query to take that field from. My guess is that it should be the base table. Try:
fConcatFld("qry_CurrentAct ionPlans_N otes_Detai l","fld_Ac tionPlanNu mber", "exp_UpdateDateNotes","str ing",[tbl_ ActionPlan s].[fld_Ac tionPlanNu mber]) AS exp_FullNotes
fConcatFld("qry_CurrentAct
Gotta run, it will be 3-4 hours before I can get back to my computer.
ASKER
The new SQL works, and it produces the same results as my previous Query #3. However, that's the problem - it produces the same results, including the truncation.
Was the new SQL meant to resolve the truncation? Or was that simply an interim step?
Was the new SQL meant to resolve the truncation? Or was that simply an interim step?
I was hoping that would resolve the truncation issue. Lets try something simple:
SELECT tbl_ActionPlans.fld_Action PlanNumber
, fConcatFld("qry_CurrentAct ionPlans_N otes_Detai l","fld_Ac tionPlanNu mber", "exp_UpdateDateNotes","str ing",[fld_ ActionPlan Number]) AS exp_FullNotes
FROM tbl_ActionPlans
Also, can you post the code you are using for the fConcatFld() function. There are a variety of concatenation functions floating around, so it might be good to see if that is where your problem is.
SELECT tbl_ActionPlans.fld_Action
, fConcatFld("qry_CurrentAct
FROM tbl_ActionPlans
Also, can you post the code you are using for the fConcatFld() function. There are a variety of concatenation functions floating around, so it might be good to see if that is where your problem is.
ASKER
The simple SQL statement above still truncates.
Here is the fConcatFld function:
Here is the fConcatFld function:
Option Compare Database
'************ Code Start **********
'This code was originally written by Dev Ashish
'It is not to be altered or distributed,
'except as part of an application.
'You are free to use it in any application,
'provided the copyright notice is left unchanged.
'
'Code Courtesy of
'Dev Ashish
'
Function fConcatFld(stTable As String, _
stForFld As String, _
stFldToConcat As String, _
stForFldType As String, _
vForFldVal As Variant) _
As String
'Returns mutiple field values for each unique value
'of another field in a single table
'in a semi-colon separated format.
'
'Usage Examples:
' ?fConcatFld(("Customers","ContactTitle","CustomerID", _
' "string","Owner")
'Where Customers = The parent Table
' ContactTitle = The field whose values to use for lookups
' CustomerID = Field name to concatenate
' string = DataType of ContactTitle field
' Owner = Value on which to return concatenated CustomerID
'
Dim lodb As Database, lors As Recordset
Dim lovConcat As Variant, loCriteria As String
Dim loSQL As String
Const cQ = """"
On Error GoTo Err_fConcatFld
lovConcat = Null
Set lodb = CurrentDb
loSQL = "SELECT [" & stFldToConcat & "] FROM ["
loSQL = loSQL & stTable & "] WHERE "
Select Case stForFldType
Case "String":
loSQL = loSQL & "[" & stForFld & "] =" & cQ & vForFldVal & cQ
Case "Long", "Integer", "Double": 'AutoNumber is Type Long
loSQL = loSQL & "[" & stForFld & "] = " & vForFldVal
Case Else
GoTo Err_fConcatFld
End Select
Set lors = lodb.OpenRecordset(loSQL, dbOpenSnapshot)
'Are we sure that duplicates exist in stFldToConcat
With lors
If .RecordCount <> 0 Then
'start concatenating records
Do While Not .EOF
lovConcat = lovConcat & lors(stFldToConcat) & Chr(13) & Chr(10) & Chr(13) & Chr(10)
.MoveNext
Loop
Else
GoTo Exit_fConcatFld
End If
End With
'That's it... you should have a concatenated string now
'Just Trim the trailing ;
fConcatFld = Left(lovConcat, Len(lovConcat) - 2)
Exit_fConcatFld:
Set lors = Nothing: Set lodb = Nothing
Exit Function
Err_fConcatFld:
MsgBox "Error#: " & Err.Number & vbCrLf & Err.Description
Resume Exit_fConcatFld
End Function
'************ Code End **********
I'm thinking the problem may be in qry_CurrentActionPlans_Not es (which is what fConcatFld is trying to meld into a single record by ActionPlanNumber). Was that the original query posted above, or is it something else?
OK, Mine is slightly different, but what you have should work fine.
Have you tried calling fConcatFld from the immediate window with a specific value of the ActionPlanNumber that you know should return a very long string?
Is your ActionPlanNumber field actually a string? Or is it more likely a "Long". If it is an autonumber, replace "string" in your function call with "Long"
Have you tried calling fConcatFld from the immediate window with a specific value of the ActionPlanNumber that you know should return a very long string?
Is your ActionPlanNumber field actually a string? Or is it more likely a "Long". If it is an autonumber, replace "string" in your function call with "Long"
dale,
regarding forcing the memo type take a look at allan brownes article about truncation memo and text fields. I am posting by cell phone right now and don't have the link handy but believe you need to address that in the first query before processing the concatenated data further in the outer query. Even if the first query is not in itself truncating the data.
regarding forcing the memo type take a look at allan brownes article about truncation memo and text fields. I am posting by cell phone right now and don't have the link handy but believe you need to address that in the first query before processing the concatenated data further in the outer query. Even if the first query is not in itself truncating the data.
ASKER CERTIFIED SOLUTION
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
ASKER
The problem does start occurring in qry_CurrentActionPlans_Not es. (I was mistaken about where the problem originates - see this previous comment.)
I'm not sure what you mean:
ActionPlanNumber is a string (data type is "Text") (e.g., "ADPA.12.01_001"), not a literal number.
I'm not sure what you mean:
Have you tried calling fConcatFld from the immediate window with a specific value of the ActionPlanNumber that you know should return a very long string?
ActionPlanNumber is a string (data type is "Text") (e.g., "ADPA.12.01_001"), not a literal number.
songwritingcpa,
Is this resolved or did you inadvertently close the question? Did that base query help resolve it?
Is this resolved or did you inadvertently close the question? Did that base query help resolve it?
ASKER
It worked! Thank you!
@song,
Recommend you re-allocate those points. The solution you accepted was basically the Sam as Miriam recommended in one of her initial posts.
To do this, click the "request attention" hyperlink in your original post and indicate you would like to reopen the question to rearward points. Glad we were able to help.
Recommend you re-allocate those points. The solution you accepted was basically the Sam as Miriam recommended in one of her initial posts.
To do this, click the "request attention" hyperlink in your original post and indicate you would like to reopen the question to rearward points. Glad we were able to help.
Open in new window