This guide provides a quick overview of how to set up and start using GroupDocs.Assembly for Python via .NET. The library fills templates, ordinary Word, Excel, PowerPoint, email, HTML or text documents with tags in them, with your data, and saves the result as a report.
For best practices, use a virtual environment to manage dependencies in Python applications. Learn more about virtual environments at the Create and Use Virtual Environments documentation topic.
Create and Activate a Virtual Environment
Create a virtual environment:
py-mvenv.venv
python3 -m venv .venv
python3 -m venv .venv
Activate a virtual environment:
.venv\Scripts\activate
source .venv/bin/activate
source .venv/bin/activate
Install groupdocs-assembly-net Package
After activating the virtual environment, run the following command in your terminal to install the latest version of the package:
py-mpipinstallgroupdocs-assembly-net
python3 -m pip install groupdocs-assembly-net
python3 -m pip install groupdocs-assembly-net
Ensure the package is installed successfully. You should see the message
Successfully installed groupdocs-assembly-net-*
Example 1: Fill a Word table from a list of dicts
To quickly test the library, let’s fill the table of a Word template with the orders of one customer. The template, order-table.docx, has a heading, a table whose second row repeats for each order, and a total:
Orders of <<[customer]>>
| Order | Product | Quantity | Price |
| <<foreach [o in orders]>><<[o.Number]>> | <<[o.Product]>> | <<[o.Quantity]>> | <<[o.Price]:"0.00">><</foreach>> |
Total: <<[orders.Sum(o => o.Price)]:"0.00">> USD
importosfromgroupdocs.assemblyimportDataSourceInfo,DocumentAssembler,Licensedeftable_report():# Optionally set a licenselicense_path=os.path.abspath("./GroupDocs.Assembly.lic")ifos.path.exists(license_path):License().set_license(license_path)# The data: one dict per table row, with the keys the template readsorders=[{"Number":10001,"Product":"Harbor Blend whole bean coffee","Quantity":30,"Price":552.0},{"Number":10004,"Product":"Aged harbour cheddar","Quantity":8,"Price":132.0},{"Number":10006,"Product":"Cold-pressed olive oil","Quantity":40,"Price":516.0},]# Each data source has the name the template uses for itassembler=DocumentAssembler()assembler.assemble_document("order-table.docx","order-table-report.docx",[DataSourceInfo("Quayside Bistro","customer"),DataSourceInfo(orders,"orders"),])print("The report is saved to order-table-report.docx")if__name__=="__main__":table_report()
The following sample file is used in this example: order-table.docx
DocumentAssembler(): The class that builds reports. One instance can build any number of them.
DataSourceInfo(orders, "orders"): A data source and the name the template’s tags use for it. A list of dicts is a collection: the <<foreach [o in orders]>> band repeats the table row once for each dict, and o.Number reads the dict’s "Number" key.
assemble_document(template, report, sources): Fills the template and writes the report. The data sources go as a list, or as one DataSourceInfo when there is only one.
<<[orders.Sum(o => o.Price)]:"0.00">>: Template expressions can compute: Sum, Count, Where, OrderBy, GroupBy and more work on the Python list, and :"0.00" formats the number.
Example 2: Turn a JSON file into a PDF report
The data often comes from a file. This example reads the customers of Harbor Lane Provisions and their orders from customers.json, and the template orders-by-customer.docx lists the orders of each customer:
Harbor Lane Provisions: orders by customer
<<foreach [c in customers]>>
<<[c.CustomerName]>>
• <<foreach [o in c.Order]>><<[o.Product.ProductName]>>: <<[o.ProductQuantity]>> units, <<[o.Price]>> USD, shipped <<[o.ShippingDate]:"d MMMM yyyy">>
<</foreach>>Total: <<[c.Order.Sum(o => o.Price)]>> USD
<</foreach>>
importjsonfromdatetimeimportdatetimefromgroupdocs.assemblyimportDataSourceInfo,DocumentAssemblerdefparse_dates(item):# JSON has no dates: turn the order dates into datetime objects for the templateforkeyin("OrderDate","ShippingDate"):ifkeyinitem:item[key]=datetime.strptime(item[key],"%Y-%m-%dT%H:%M:%S")returnitemdefjson_to_pdf():withopen("customers.json",encoding="utf-8")asf:customers=json.load(f,object_hook=parse_dates)# A Word template, a PDF report: the report's extension picks the formatassembler=DocumentAssembler()assembler.assemble_document("orders-by-customer.docx","orders-by-customer.pdf",DataSourceInfo(customers,"customers"))print("Customers:",len(customers))if__name__=="__main__":json_to_pdf()
json.load(f, object_hook=parse_dates): Reads the file into dicts and lists, which DataSourceInfo takes as they are. JSON has no date type, so the hook turns the date strings into datetime objects: the template formats ShippingDate as a date ("d MMMM yyyy").
c.Order and o.Product.ProductName: Nested dicts and lists are read with dots, as in the JSON.
"orders-by-customer.pdf": The report is saved in the format of its extension. The same template gives DOCX, PDF, HTML, XPS and the other supported formats.
Example 3: Fill an Excel sheet
Templates can be spreadsheets too. The template stock-sheet.xlsx has a header row and a row that repeats for each product of products.json:
Harbor Lane Provisions: stock
| Product | In stock | Discount, % | Price |
| <<foreach [p in products]>><<[p.ProductName]>> | <<[p.UnitInStock]>> | <<[p.Discount]>> | <<[p.ProductPrice]>><</foreach>> |
importjsonfromgroupdocs.assemblyimportDataSourceInfo,DocumentAssembler,DocumentAssemblyOptionsdeffill_spreadsheet():withopen("products.json",encoding="utf-8")asf:products=json.load(f)# Write numbers as numbers: by default every value goes into a text cellassembler=DocumentAssembler()assembler.options=DocumentAssemblyOptions.USE_SPREADSHEET_DATA_TYPESassembler.assemble_document("stock-sheet.xlsx","stock-sheet-report.xlsx",DataSourceInfo(products,"products"))print("Products:",len(products))if__name__=="__main__":fill_spreadsheet()
The following sample file is used in this example: stock-sheet.xlsx
The following sample file is used in this example: products.json
stock-sheet.xlsx: In a spreadsheet the data band is a row of cells, from the cell that opens <<foreach>> to the cell that closes it; the report gets one row per product.
DocumentAssemblyOptions.USE_SPREADSHEET_DATA_TYPES: Writes each value as its type, so UnitInStock and Discount are number cells that formulas can use, and ProductPrice (a string in the JSON) is a text cell. Without the option, every value is written as text.