How to Run Personal Workbook Macro from Python? - python

H1! I get a file everyday that contains similar information. I wrote a Macro to automate the formatting process and now I want to run the macro using Python.
The Macro is in my personal Workbook since it is ran in different xlsx files everyday.
When I try to run my code I get 'The macro may not be available i this workbook or all macros may be disabled'
This is the my python code
import win32com.client
import os
import datetime
path_dir = r'C:\Users\myuser\Documents\me\directory1\directory2'
dt_today = datetime.date.today().strftime("%b%d")
file = r'{}\xlfile_{}.xlsx'.format(path_dir, dt_today)
Prs_wb_path =
r'C:\Users\myuser\AppData\Roaming\Microsoft\Excel\XLSTART'
xl = win32com.client.Dispatch("Excel.Application")
xlsPath = os.path.expanduser('{}').format(file)
wb = xl.Workbooks.Open(Filename=xlsPath)
xl.Application.Run(r'PERSONAL.XLSB!ContextualData_Formatting')
wb.Save()
xl.Quit()

Related

unable to save workbook in xlwings

Unable to save a workbook using xlwings. Below is the code, loc contains the excel file name
import xlwings as xw
from xlwings import Book
print(xw.__version__)
app = xw.App(visible=False)
wb = Book(loc)
wb.sheets['crosst'].range('AJ2:CH9999').value=''
wb.save(loc)
app.quit()
below is the response, but when I check the Excel file, the contents are not cleared?
0.24.6
Process finished with exit code 0
Save the file under a new name, not under the same name.
import xlwings as xw
from xlwings import Book
print(xw.__version__)
app = xw.App(visible=False)
wb = Book(loc)
wb.sheets['crosst'].range('AJ2:CH9999').value=''
wb.save(loc1)
app.quit()
where loc1 is another name.
Ensure also that your cells are correct.

How to create an Excel file and write VBA code in module using Python win32com?

Objective: To create an Excel file and write VBA code in an Excel module using Python win32com.
Problem: I use this code in Anaconda (Jupiter Notebook) without error. When I execute the code as .py format it is coming up with an error.
Python Code:
import win32com.client as win32
import comtypes, comtypes.client
xl = win32.gencache.EnsureDispatch('Excel.Application')
xl.Visible = True
ss = xl.Workbooks.Add()
sh = ss.ActiveSheet
xlmodule = ss.VBProject.VBComponents.Add(1) # vbext_ct_StdModule
sCode = '''sub VBAMacro()
msgbox "VBA Macro called"
end sub'''
xlmodule.CodeModule.AddFromString(sCode)
Error:

Retrieve Excel Workbook Connection Properties

I am attempting to grab the "Command Text" from the Connection Property window in an Excel file using python. However, I cannot find the object that contains this information. In the below picture I would like to retrieve the highlighted EXEC sp_FooBar as a string:
I am able to retrieve the Connection names with:
import odbc
import win32com.client
file = r'PATH_TO_FILE'
xl = win32com.client.DispatchEx('Excel.Application')
wb = xl.workbooks.open(file)
for x in wb.connections:
print(x)
But I'm not sure how to use the <COMObject <unknown>> object further to grab the command text. I'm thinking win32com may have something, but can't seem to crack the code.
You can get the CommandText property from a OLEDBConnectioninstance like this:
import odbc
import win32com.client
file = r'PATH_TO_FILE'
xl = win32com.client.DispatchEx('Excel.Application')
wb = xl.workbooks.open(file)
for x in wb.Connections:
print(x.OLEDBConnection.CommandText)
xl.Application.Quit()

Can excel CSV files be injected with macros?

I am trying to inject my csv files with a macro that automatically fits the column widths in excel but nothing is happening. I am using a code from a previous post (Use Python to Inject Macros into Spreadsheets). But here is the code
import os
import sys
# Import System libraries
import glob
import random
import re
#sys.coinit_flags = 0 # comtypes.COINIT_MULTITHREADED
# USE COMTYPES OR WIN32COM
#import comtypes
#from comtypes.client import CreateObject
# USE COMTYPES OR WIN32COM
import win32com
from win32com.client import Dispatch
desktop = os.path.join(os.path.join(os.environ['USERPROFILE']), 'Desktop')
x = r'C:\This\is\the\path'
scripts_dir = x
conv_scripts_dir = x
strcode = \
'''
sub test()
Column.Autofit
end sub
'''
#com_instance = CreateObject("Excel.Application", dynamic = True) # USING COMTYPES
com_instance = Dispatch("Excel.Application") # USING WIN32COM
com_instance.Visible = True#False
com_instance.DisplayAlerts = True#False
for script_file in glob.glob(os.path.join(scripts_dir, '*.csv')):
print("Processing: %s" % scr ipt_file)
# do the operation in background without actually opening Excel
(file_path, file_name) = os.path.split(script_file)
objworkbook = com_instance.Workbooks.Open(script_file)
xlmodule = objworkbook.VBProject.VBComponents.Add(1)
xlmodule.CodeModule.AddFromString(strcode.strip())
objworkbook.SaveAs(os.path.join(conv_scripts_dir, file_name))
com_instance.Quit()
This code actually opens the a file in excel, executes a macro, and then closes the excel window. Why doesn't the macro work from the python command line, but does work inside excel?
Exactly. There is not formats, whatsoever, in a CSV. It's like trying to add formatting to a Text file. You can't do that. You can convert CSV files to XLSM files (Excel Macro) or XLSB (Binary).
Sub CSVtoXLSB2()
Dim wb As Workbook
Dim CSVPath As String
Dim sProcessFile As String
CSVPath = "C:\your_path_here\"
sProcessFile = Dir(CSVPath & "*.csv")
Do Until sProcessFile = "" ' Loop until no file found.
Set wb = Application.Workbooks.Open(CSVPath & sProcessFile)
wb.SaveAs CSVPath & Split(wb.Name, ".")(0) & ".xlsb", FileFormat _
:=50, Password:="", WriteResPassword:="", ReadOnlyRecommended:=False, _
CreateBackup:=False
wb.Close
sProcessFile = Dir() ' Get next entry.
Loop
Set wb = Nothing
End Sub
Now, if you want to copy a Module from one Workbook to another, follow the steps listed below:
Copying a module from one workbook to another
Open both the workbook that contains the macro you want to copy, and the workbook where you want to copy it.
On the Developer tab, click Visual Basic to open the Visual Basic Editor.
In the Visual Basic Editor, on the View menu, click Project Explorer Project Explorer button image, or press CTRL+R.
In the Project Explorer pane, drag the module containing the macro you want to copy to the destination workbook. In this case, we're copying Module1 from Book2.xlsm to Book1.xlsm.
VBA Project Explorer
Module1 copied from Book2.xlsm
Copy of Module1 copied to Book1.xlsm

How to have python wait until an Excel Macro/Refresh is done

I am using Python to run a macro in excel. and I want Python to close excel. The macro refreshes a data connection in excel which can be slow.
How do I have python wait until the refresh is done to close. This is what I am using, I need something before the xl.Quit that will wait until the refresh in macro is done????
import win32com.client
import os
xl = win32com.client.DispatchEx("Excel.Application")
wb = xl.workbooks.open("X:\Backoffice\Options Trading\BloombergRate.xlsm")
xl.Visible = True
xl.run("Refresh")
xl.Quit()
Wait ways can I make this work?
Edit your Refresh macro to set QueryTable.BackgroundQuery property to False. This should cause the macro to block until it is done.
You don't even have to set up a macro to run this. win32com has a native method to refresh all data connections.
import win32com.client
import os
xl = win32com.client.DispatchEx("Excel.Application")
wb = xl.workbooks.open("X:\Backoffice\Options Trading\BloombergRate.xlsm")
xl.Visible = True
wb.RefreshAll()
xl.Quit()

Categories