MS Access의 VBA를 사용하여 한 레코드 세트의 레코드에서 다른 레코드의 첨부 파일을 복사합니다.

MS Access의 VBA를 사용하여 한 레코드 세트의 레코드에서 다른 레코드의 첨부 파일을 복사합니다.

나는 거의 이 작업을 수행했습니다. 나는 이것에 대해 또 다른 눈이 필요하다고 생각합니다. 내 문제는 단순한 프로그래밍 구조 문제일 뿐이라고 생각합니다. 루프가 너무 많거나 레코드 세트를 잘못된 순서로 열거나 닫습니다.

한 dao 레코드세트의 레코드에 포함된 모든 첨부 파일을 다른 dao 레코드세트의 해당 레코드로 복사하려고 합니다. 두 레코드 세트 모두 동일한 테이블에서 데이터를 가져옵니다. 첫 번째 레코드 집합(rstOld)에는 작년의 날짜 값이 있는 레코드가 포함되어 있으며 해당 레코드에는 첨부 파일이 얼마든지 포함될 수 있습니다. 두 번째 레코드 집합(rstNew)에는 올해의 날짜 값이 있는 레코드가 포함되어 있으며 해당 레코드에는 첨부 파일이 없습니다.

이를 달성하기 위해 rstNew의 각 레코드를 통해 루프를 시작합니다. rstNew의 각 레코드에 대해 이름 필드의 값을 수집한 다음 두 번째 루프를 시작합니다. 두 번째 루프는 일치하는 Name 필드가 있는 rstOld의 레코드를 찾습니다. 그런 다음 rstOld의 레코드에 있는 모든 첨부 파일을 rstNew의 레코드로 복사하면 됩니다.

이상한 점은 일치하는 항목을 찾은 rstNew의 첫 번째 첫 번째 레코드에서 올바르게 작동한다는 것입니다. 그 후에는 후속 레코드에 대해 더 이상 작동하지 않습니다.

지금까지 내 코드는 다음과 같습니다.

    Dim db As Database
    Dim strOldSQL As String
    Dim rstOld As DAO.Recordset2
    Dim strNewSQL As String
    Dim rstNew As DAO.Recordset2
    Dim rstOldAttachments As DAO.Recordset2
    Dim rstNewAttachments As DAO.Recordset2
    Dim strCurrentSiteName As String
    Dim strOldSiteName As String
Set db = CurrentDb()

    'First let's open a recordset that contains all of the records from this year.
    strNewSQL = "SELECT tblAuditForms.SiteName, tblAuditForms.Attachments, tblAuditForms.AuditYear FROM tblAuditForms WHERE AuditYear = #" & Format(cboMyDate, "mm/dd/yyyy") & "# ORDER By tblAuditForms.SiteName;"
    Set rstNew = db.OpenRecordset(strNewSQL)
    rstNew.MoveFirst
    rstNew.Edit
    
    Do While Not rstNew.EOF 'Now we need to loop through these records.
    
        strCurrentSiteName = rstNew.Fields("SiteName").Value 'Get the name of the site for the current record that we're on. We'll use this to compare with the sites in the previous audit.
                    
        'Now let's open a recordset that contains all records from the previous audit.
        strOldSQL = "SELECT tblAuditForms.SiteName, tblAuditForms.Attachments, Year([AuditYear]) FROM tblAuditForms WHERE Year([AuditYear]) = " & Me.cboPreviousDate & " ORDER BY tblAuditForms.SiteName;"
        Set rstOld = db.OpenRecordset(strOldSQL)
        rstOld.MoveFirst
        
        Do While Not rstOld.EOF 'Loop through each of the records from the previous audit until we find a record that matches the current site name.
        
            strOldSiteName = rstOld.Fields("SiteName").Value
        
            If strCurrentSiteName = strOldSiteName Then 'If this is true, then we've found a record from the previous audit that matches the one from our current audit.
                'Now it's just a matter of copying the attachments from the old record into the new one.  Working with attachments is annoying though.
                
                'This next block should loop through the attachments (if any) in the old record and copy them into the new record.
                Set rstOldAttachments = rstOld.Fields("Attachments").Value
                rstOldAttachments.MoveFirst
                
                Set rstNewAttachments = rstNew.Fields("Attachments").Value

                Do While Not rstOldAttachments.EOF
                    
                    rstNewAttachments.AddNew
                    rstNewAttachments.Fields("FileData").Value = rstOldAttachments.Fields("FileData").Value
                    rstNewAttachments.Fields("FileName").Value = rstOldAttachments.Fields("FileName").Value
                    rstNewAttachments.Fields("FileType").Value = rstOldAttachments.Fields("FileType").Value
                    rstNewAttachments.Update
                
                    rstOldAttachments.MoveNext
                Loop
                
                'Now that we've found the site from the previous audit and copied its attachments into the new record we can close the old recordset and move onto the next site in the current audit.
                rstOldAttachments.Close
                rstNewAttachments.Close
                Exit Do
            
            End If
                        
            rstOld.MoveNext
        Loop
         
        rstOld.Close
        rstNew.Update
        rstNew.MoveNext
    Loop
        
    'If we've gotten this far then we've looped through all of the new records that we just created from the weekly staffing workbook.
    rstNew.Close
    
    

이전에 말했듯이 이 코드는 rstNew 레코드 세트를 통한 첫 번째 루프에서는 작동하지만 후속 루프에서는 작동하지 않습니다. 너무 빨리 루프에서 벗어나는 걸까요? 아니면 레코드세트를 너무 일찍 닫았나요?

답변1

나는 그것을 알아 냈습니다! 나는 내가 가까이 있다는 것을 알고 있었다. 나는 recordset.update(또는 내 경우에는 rstNew.update) 문을 실행하면 레코드 집합 editmode 속성이 0으로 돌아간다는 것을 배웠습니다. 이는 첫 번째 루프에서 첨부 파일을 성공적으로 복사했지만 실패하는 이유를 설명합니다. 후속 루프에서. 따라서 제가 해야 할 일은 "rstNew.Edit" 문을 "Set rstNewAttachments = rstNew.Fields("Attachments").Value" 행 바로 위로 이동하는 것이었습니다.

새로운 코드는 다음과 같습니다.

    Dim db As Database
    Dim strOldSQL As String
    Dim rstOld As DAO.Recordset2
    Dim strNewSQL As String
    Dim rstNew As DAO.Recordset2
    Dim rstOldAttachments As DAO.Recordset2
    Dim rstNewAttachments As DAO.Recordset2
    Dim strCurrentSiteName As String
    Dim strOldSiteName As String
Set db = CurrentDb()

    'First let's open a recordset that contains all of the records from this year.
    strNewSQL = "SELECT tblAuditForms.SiteName, tblAuditForms.Attachments, tblAuditForms.AuditYear FROM tblAuditForms WHERE AuditYear = #" & Format(cboMyDate, "mm/dd/yyyy") & "# ORDER By tblAuditForms.SiteName;"
    Set rstNew = db.OpenRecordset(strNewSQL)
    rstNew.MoveFirst
        
    Do While Not rstNew.EOF 'Now we need to loop through these records.
    
        strCurrentSiteName = rstNew.Fields("SiteName").Value 'Get the name of the site for the current record that we're on. We'll use this to compare with the sites in the previous audit.
                    
        'Now let's open a recordset that contains all records from the previous audit.
        strOldSQL = "SELECT tblAuditForms.SiteName, tblAuditForms.Attachments, Year([AuditYear]) FROM tblAuditForms WHERE Year([AuditYear]) = " & Me.cboPreviousDate & " ORDER BY tblAuditForms.SiteName;"
        Set rstOld = db.OpenRecordset(strOldSQL)
        rstOld.MoveFirst
        
        Do While Not rstOld.EOF 'Loop through each of the records from the previous audit until we find a record that matches the current site name.
        
            strOldSiteName = rstOld.Fields("SiteName").Value
        
            If strCurrentSiteName = strOldSiteName Then 'If this is true, then we've found a record from the previous audit that matches the one from our current audit.
                'Now it's just a matter of copying the attachments from the old record into the new one.  Working with attachments is annoying though.
                
                'This next block should loop through the attachments (if any) in the old record and copy them into the new record.
                Set rstOldAttachments = rstOld.Fields("Attachments").Value
                rstOldAttachments.MoveFirst
                
                rstNew.Edit
                Set rstNewAttachments = rstNew.Fields("Attachments").Value

                Do While Not rstOldAttachments.EOF
                    
                    rstNewAttachments.AddNew
                    rstNewAttachments.Fields("FileData").Value = rstOldAttachments.Fields("FileData").Value
                    rstNewAttachments.Fields("FileName").Value = rstOldAttachments.Fields("FileName").Value
                    rstNewAttachments.Fields("FileType").Value = rstOldAttachments.Fields("FileType").Value
                    rstNewAttachments.Update
                
                    rstOldAttachments.MoveNext
                Loop
                
                'Now that we've found the site from the previous audit and copied its attachments into the new record we can close the old recordset and move onto the next site in the current audit.
                rstOldAttachments.Close
                rstNewAttachments.Close
                Exit Do
            
            End If
                        
            rstOld.MoveNext
        Loop
         
        rstOld.Close
        rstNew.Update
        rstNew.MoveNext
    Loop
        
    'If we've gotten this far then we've looped through all of the new records that we just created from the weekly staffing workbook.
    rstNew.Close

관련 정보