我从VBA调用Python脚本。这个Python脚本的结构是一个没有其他功能的单一函数:
def myFunction():
# do stuff
return stuff_output
我知道这个函数正常工作,因为如果添加,print(myFunction())
会在命令行中生成正确的输出(JSON响应)。
在我的VBA代码中,'RetVal`始终是一个4位整数值。也许Python函数甚至没有被执行?
我应该修复哪些代码以使其正常工作?我很感激一个接近我当前代码的解决方案,如果可能的话没有外部库。
Option Explicit
Sub RunPython()
Dim RetVal
Dim scriptPath As String
scriptPath = "C:\Users\Rychu\Desktop\python\myPythonScript.py"
RetVal = Shell("C:\Python36-32\python.exe" & " " & scriptPath, vbHide)
If RetVal = 0 Then
MsgBox "Couldn't run python script!", vbOKOnly
Else
Debug.Print RetVal
End If
End Sub
答案 0 :(得分:1)
我无法找到传递Python函数返回值的直接方法,因此我通过将Python结果保存到桌面上的文本文件并使用VBA读取+删除相同文件来处理它。
重要的是:
shellObj.Run
不同的 Shell
允许设置一个布尔参数以等待返回True
,以便其余的VBA代码不会尝试获取数据来自文本文件,但还没有创建。
如果文本文件没有指定完整的文件路径,只有文件名,Python不会在Python脚本所在的目录中创建文本文件,就像我运行时一样脚本通过命令行或Visual Studio。显然,当从VBA调用时,Python对默认目录有不同的看法,它也不是VBA文件的目录。
这是我的Python代码:
def myFunction():
# do stuff
return stuff_output
import os
f = open(os.path.expanduser("~\Desktop") + "\myTemp.txt","w") #create a new text file on Desktop in write mode
f.write(str(myFunction())) #write output to created text file
f.close() #close file object
这是我的VBA代码:
Option Explicit
Sub RunPython()
Dim shellObj As Object: Set shellObj = CreateObject("WScript.Shell")
Dim tempTxtPath As String
Const scriptPath As String = "C:\Users\Rychu\Desktop\python\myPythonScript.py"
Const pythonPath As String = "C:\Python36-32\python.exe"
tempTxtPath = CreateObject("WScript.Shell").specialfolders("Desktop") & "\myTemp.txt"
shellObj.Run pythonPath & " " & scriptPath, vbHide, True
Debug.Print (getTextAndDelete(tempTxtPath))
End Sub
Function getTextAndDelete(filePath) As String
Dim fileNum As Long
Dim myData As String
fileNum = FreeFile
Open filePath For Binary As #fileNum
myData = Space$(LOF(1))
Get #fileNum, , myData
Close #fileNum
Kill filePath
getTextAndDelete = myData
End Function