我正在尝试自动将SAP导出到Excel文件,然后另一个Excel文件使用VBA代码自动过滤和格式化数据。
除了一个(看起来很小的)问题之外,我已经让它全部运行起来了:SAP总是自动打开导出的Excel文件,似乎无法停止,因为它似乎发生在Excel VBA中导入数据的子例程完成之后(它们包含SAP GUI脚本)。
如果我只运行sap_export
子例程,那么Excel文件就会打开,这很烦人,但是如果我运行refresh_sap()
,它调用sap_export()
,然后运行refresh()
,它访问导出的Excel文件导入数据,我会得到提示,告诉我该文件已经在使用中。
我发现无法阻止SAP GUI脚本打开该文件,因为它似乎不会在运行时打开。我怀疑这就是我无法找到任何方法使用Application.Wait或DoEvents解决此问题的原因。无论我等待多长时间,它都不会工作,因为该文件在运行时之前根本不会打开。
Sub refresh_sap()
Call sap_export
Call refresh
End Sub
Sub refresh()
'refreshes the connection to the SAP-exported Excel-file
ActiveWorkbook.Connections("export").refresh
'deleting unwanted data
ActiveWorkbook.Sheets("PC-Liste komplett").Select
Selection.AutoFilter
ActiveSheet.ListObjects("Tabelle_export").Range.AutoFilter Field:=4, Criteria1:="Löschen"
Range("A2").Select
Range(Selection, Selection.End(xlDown)).Select
Range(Selection, Selection.End(xlToRight)).Select
Selection.EntireRow.Delete
ActiveSheet.ListObjects("Tabelle_export").Range.AutoFilter Field:=4
Range("A1").Select
End Sub
Sub sap_export()
Dim set0 As Integer
Dim set1 As String
Dim set2 As Boolean
'vbs-script recorded with the SAP-GUI
If Not IsObject(sapp) Then
Set SapGuiAuto = GetObject("SAPGUI")
Set sapp = SapGuiAuto.GetScriptingEngine
End If
If Not IsObject(Scon) Then
Set Scon = sapp.Children(0)
End If
If Not IsObject(session) Then
Set session = Scon.Children(0)
End If
If IsObject(WScript) Then
WScript.connectobject session, "on"
WScript.connectobject sapp, "on"
End If
session.findById("wnd[0]/tbar[0]/okcd").Text = "/n KE5X"
session.findById("wnd[0]").sendVKey 0
session.findById("wnd[0]/usr/ctxtGT_PRCTR-LOW").Text = "*"
session.findById("wnd[0]").sendVKey 8
session.findById("wnd[0]/usr/cntlGRID1/shellcont/shell/shellcont[1]/shell").contextMenu
session.findById("wnd[0]/usr/cntlGRID1/shellcont/shell/shellcont[1]/shell").selectContextMenuItem "&XXL"
If session.findById("wnd[1]/usr/radRB_1").Selected = True Then
set0 = 0
ElseIf session.findById("wnd[1]/usr/radRB_2").Selected = True Then
set0 = 1
ElseIf session.findById("wnd[1]/usr/radRB_OTHERS").Selected = True Then
set0 = 2
End If
set1 = session.findById("wnd[1]/usr/cmbG_LISTBOX").Key
set2 = session.findById("wnd[1]/usr/chkCB_ALWAYS").Selected
session.findById("wnd[1]/usr/radRB_OTHERS").Select
session.findById("wnd[1]/usr/cmbG_LISTBOX").Key = "10"
session.findById("wnd[1]/usr/chkCB_ALWAYS").Selected = False
session.findById("wnd[1]").sendVKey 0
session.findById("wnd[1]/usr/ctxtDY_PATH").Text = "S:\FIN-Alle\Kostenstellen - Innenauftragsliste\SAP"
session.findById("wnd[1]/tbar[0]/btn[11]").press
session.findById("wnd[0]/usr/cntlGRID1/shellcont/shell/shellcont[1]/shell").contextMenu
session.findById("wnd[0]/usr/cntlGRID1/shellcont/shell/shellcont[1]/shell").selectContextMenuItem "&XXL"
Select Case set0
Case 0
session.findById("wnd[1]/usr/radRB_1").Select
Case 1
session.findById("wnd[1]/usr/radRB_2").Select
Case 2
session.findById("wnd[1]/usr/radRB_OTHERS").Select
End Select
session.findById("wnd[1]/usr/cmbG_LISTBOX").Key = set1
session.findById("wnd[1]/usr/chkCB_ALWAYS").Selected = set2
session.findById("wnd[1]").sendVKey 12
session.findById("wnd[0]/tbar[0]/okcd").Text = "/n"
session.findById("wnd[0]").sendVKey 0
End Sub
由于我的印象是我无法在子例程中关闭文件(因为它只在运行时之后打开),我目前正在寻找一种方法:告诉SAP根本不要打开该文件,或者禁止它访问Excel,或者干脆完全关闭SAP,看看这样做是否有效--尽管我不希望这样做。
4条答案
按热度按时间m528fe3b1#
据我所知,SAP SDK导出函数总是使用一个虚拟文件来处理数据的导出。这是通过自动打开导出文件调用创建的。您可以尝试允许这样做,以便在调用refresh()方法后打开新的导出文件。请参见http://rmps.cygnaltech.net/?p=779
s3fp2yjn2#
在我将SAP输出保存为Excel格式后,VBA例程通常会执行大量工作。与您的经验类似,Excel会在宏完成后立即尝试打开文件。我通常会直接在其他VBA例程中对数据进行后期处理。我发现,如果我在VBA算法中执行两项操作,则不会打开文件,也不会中断VBA。下面是我的操作:
1.从SAP导出文件后,我立即通过在文件名中.XLS之前连接日期和时间来重命名该文件。我将该名称保存在Excel文件中,并单独打开它。如果VBA在导出后结束,您将在Excel中得到一个找不到文件的错误。
1.重命名后,我立即继续打开重命名的文件或VBA中的其他例程,大多数情况下,打开找不到的文件名不会中断VBA处理。
yhqotfr83#
我想出了一个解决办法,有一次我用SAP脚本运行VBA,Excel忙碌,无法响应SAP的打开文件请求。因此,当SAP打开文件时,它会尝试在Excel的最新示例中打开它。如果您的脚本在旧示例中的电子表格中运行,SAP会将打开文件命令发送给新示例。这意味着Excel打开错误消息将显示在较新的单独Excel示例中。操作方法如下:
1.使用宏打开电子表格
1.打开后,按住ALT键
1.仍然按住ALT键,鼠标右键单击任务栏中的Excel图标
1.按住ALT键,从弹出菜单中选择Excel图标
1.仍然按住ALT键,最终将出现一条消息,询问您是否需要一个新示例,请回答Yes
1.显示绿色Excel启动消息时,释放ALT键确保新示例已打开到空白电子表格
1.现在像平常一样运行宏/脚本。
在Excel 365中工作起来很有魅力。我还没有在旧版本中测试过它。最终,你必须转到Excel的新示例,一个接一个地清除所有错误信息。
除此之外,您可能需要防止新示例打开文件。我通过在导出文件后立即在目录中重命名SAP导出文件来处理此问题。我通过在文件名中添加日期戳来重命名文件。这样,我可以确保新示例不会偶然打开导出的文件。因此,如果我总是导出到SAP_MMUsers. xlsx,我在VBA编码中将其重命名为SAP_MMUsers_0312.xlsx。因此,我总是导出到SAP_MMUsers.xlsx,并且只需在第一次运行宏/脚本时回答SAP GUI“允许”问题。导出文件名不应存在于目录中,这样我就不必为Replace选项编写代码,而且如果需要返回查看原始数据,我会保存带有时间戳的输出。我总是删除目录中符合我的SAP导出命名约定的所有SAP导出文件(它们总是以“SAP_”开始)。这样,该过程在VBA代码中内置了一些冗余,以避免处理中断。
643ylb084#
我通常发现将ALV表加载到数组中,然后将数组导出到Excel中所需的位置会更快。这样就不需要打开额外的工作簿进行处理。如果行数小于约1000行,这种方法通常会更快。