Transformations
Transformations let you prepare raw data before it reaches your slides. You chain simple steps - keep certain columns, filter rows, sort, combine tables, add calculated fields - on top of a base source (a data collection or another transformation). The result behaves like a data collection: it inherits parameters from its sources and can be linked to charts, tables, and text fields in workflows.
When to use a transformation
Use a transformation when the file in your collection is almost right, but you need to:
- Drop title rows, footnotes, or unused columns
- Keep only one fund, share class, or date range
- Sort ratings or maturity buckets in presentation order
- Combine two sources (for example performance rows plus a benchmark row)
- Add a label column built from existing values
- Rotate a table so rows become columns (like Excel transpose)
- Sum numeric columns into a single totals row
If the raw file already matches what the slide needs, connect the collection directly - no transformation required.
Creating a transformation
- Open Data → Transformations in your space.
- Create a new transformation and give it a clear name.
- Choose a base source - usually a data collection.
- Add steps in order. Each step changes the table; later steps see the result of earlier ones.
- Set preview parameters (inherited from the base source and any union sources) and click Run preview to check the output after each step. Parameter names are not edited on the transformation — change them on the underlying collection(s); the preview picks up the new names after the collection is saved.
- Save when the preview looks correct.
Steps can be reordered or deleted. Click a step to preview the table after that step.
Step types
Select columns
Keeps only the columns you list and optionally renames them. This is how presentation headers are set — the names that remain after Select (including renames) become the header row written into the PowerPoint table.
Columns - Enter column names separated by commas. You can also refer to columns by position (0, 1, …) or Excel-style letters (A, B, …) when headers are blank or unclear.
Renames - One per line: OldName=NewName. Leave the right side empty to blank a header (useful when a slide table should not show a column title). Use renames whenever the workbook/collection names differ from the labels on the slide (for example class_name=CLASS, SEC Yield=SEC 30-Day Yield (%), or after Remove header Column1=Class, Column2=Yield).
Example: Keep Fund Name, Return, and Class, and rename SEC Yield to Yield.
Onboarding / factsheet pattern: after filter/sort/transpose, end with a Select whose renames match the sample table's header row exactly. Skipping this step is the usual cause of Column1/Column2 or snake_case headers on an otherwise correct table.
Filter rows
Keeps only rows that match a condition. Think of it as “show rows where …”.
Example conditions:
| Goal | Expression |
|---|---|
| Positive returns only | Return > 0 |
| One share class | Class == 'A' |
| Several classes | Class in ['A', 'B', 'C'] |
| First row only | row_index == 0 |
| Last row only | row_index == -1 |
Column names with spaces are written with underscores in expressions (for example SEC_Yield for a column named SEC Yield).
See Writing expressions for the full reference.
Sort
Orders rows by one column.
- Direction - Ascending or descending.
- Order
- Alphabetic - Standard A–Z / Z–A text order.
- Natural - Numbers inside text sort sensibly (
3 to 5before10 to 15). - Custom - You provide the exact sequence (for example
AAA, AA, A, BBBfor credit ratings).
Computed column
Adds a new column whose value is built from other columns row by row.
Wrap each column reference in curly braces {ColumnName}. You can mix text and values:
| Goal | Expression |
|---|---|
| Copy current row's value | {NASDAQ} |
| First row's value | {NASDAQ[0]} |
| Last row's value | {NASDAQ[-1]} |
| Previous row (or default) | {A[row_index - 1] if row_index > 0 else 0} |
| Third character of current row | {NASDAQ[row_index][2]} |
| Combine text | {Class} - {Fund Name} |
| Conditional label | {Class if Class == 'Benchmark' else Class + ' (' + Inception_Date + ')'} |
| Round a number | {Return:.2f} |
In computed columns, a bare column name such as {A} is shorthand for the current row (A[row_index]). Subscripts address rows, not characters: {A[0]} is column A in the first row, {A[-1]} in the last row. To index into the current row's text value, use the row first: {A[row_index][2]} or {A[row_index][:4]}.
A single braced expression (with no surrounding text) keeps numeric values as numbers. Multiple parts are joined into text.
See Writing expressions for functions and date handling.
Union
Appends rows from another collection or transformation, aligning columns by name.
- Union with source - Pick the second table to append.
- Filter unioned rows (optional) - Keep only some rows from that second source before appending (for example
row_index == 0to add just the first row). - Rename source columns - Align mismatched column names (
1 YR=1 Year) so values land in the right columns.
Typical pattern: sort and filter the main table, then union a single benchmark or total row from the same collection with a row filter.
Transpose
Rotates the table like Excel Transpose: original column headers become the first column, and each original row becomes a new column (Column1, Column2, …). No settings required.
After Remove header, column names are already positional placeholders (Column1, Column2, …). Transpose then rotates data rows only-those synthetic names are not copied into the result as an extra column.
Remove header
Removes column names so the result is pure data rows with generic column labels (Column1, Column2, …). Use this only when the PowerPoint table has no header row in the sample (for example a two-column class/yield sidebar with just A / 10.33 and no CLASS/YIELD labels). Populate detects ColumnN and omits a header row.
If the sample table does show header labels, do not leave ColumnN as the final column names — add a Select step with Renames afterward (for example Column1=Share Class (Inception), Column2=NAV). The preview then shows normal headers again, and slides include a matching header row when connected.
Sum up
Collapses all rows into one totals row. Numeric columns are summed. For columns that should show a label instead of a number (for example Total in a name column), add a label mapping: class_name=Total.
Writing expressions
Filter and computed steps use a small, safe expression language. You do not need to know Python to use it - think in terms of column names, comparisons, and the helpers below.
Referencing columns
- In filter expressions, use the column name directly:
Return > 0,Class == 'A'. - In computed expressions, wrap names in braces:
{Return},{Fund Name}. - Spaces in column names become underscores in filter expressions (
SEC Yield→SEC_Yield). In computed braces you can use the real name:{SEC Yield}or{SEC_Yield}.
Comparisons and logic
| Operator | Meaning |
|---|---|
==, != | Equal, not equal |
>, >=, <, <= | Greater / less (numbers and dates) |
and, or, not | Combine conditions |
in, not in | Value in a list, e.g. Class in ['A', 'B'] |
Text values use single quotes: 'Benchmark'.
Row position
row_index is the row’s position in the current table, starting at 0. Use -1 for the last row. Helpful for keeping a header row, a total row, or a single benchmark line.
In filter expressions, row_index selects rows (for example row_index == 0).
In computed expressions, row_index is also available inside {…} so you can combine it with column vectors, for example {A[row_index - 1] if row_index > 0 else 0}.
Math helpers
round(), abs(), min(), max(), int(), float() - work on numeric column values.
Dates
Date cells are usually stored in ISO form (2026-03-31). You can:
| Function | Purpose |
|---|---|
from_isoformat({Date}) | Parse an ISO date/datetime cell |
strptime({Date}, '%m/%d/%Y') | Parse a text date with a format pattern |
strftime({Date}, '%d.%m.%Y') | Format a date for display |
datetime_add({Date}, months=-1) | Shift a date by days, weeks, months, or years |
In computed columns, put the column inside braces inside the function: strftime({Report Date}, '%B %Y').
The second argument to strftime and strptime is a format string using percent directives (same as Python’s datetime.strftime). The table below lists the directives required by the C standard; they work on all platforms. Locale-dependent codes (%a, %A, %b, %B, %c, %p, %x, %X) follow your system locale.
| Code | Meaning | Example |
|---|---|---|
%a | Weekday, abbreviated | Mon |
%A | Weekday, full name | Monday |
%w | Weekday as number (0 = Sunday) | 0 … 6 |
%d | Day of month, zero-padded | 01 … 31 |
%b | Month, abbreviated | Jan |
%B | Month, full name | January |
%m | Month, zero-padded | 01 … 12 |
%y | Year without century | 00 … 99 |
%Y | Year with century | 2026 |
%H | Hour (24-hour clock) | 00 … 23 |
%I | Hour (12-hour clock) | 01 … 12 |
%p | AM or PM | AM, PM |
%M | Minute | 00 … 59 |
%S | Second | 00 … 59 |
%f | Microsecond | 000000 … 999999 |
%z | UTC offset | +0000, -0400 |
%Z | Time zone name | UTC, EST |
%j | Day of year | 001 … 366 |
%U | Week number (Sunday first) | 00 … 53 |
%W | Week number (Monday first) | 00 … 53 |
%c | Locale date and time | Tue Aug 16 21:30:00 1988 |
%x | Locale date | 08/16/88 |
%X | Locale time | 21:30:00 |
%% | Literal % | % |
Common patterns: '%d.%m.%Y' → 31.03.2026, '%m/%d/%Y' → 03/31/2026, '%B %Y' → March 2026. See the Python datetime strftime reference for ISO 8601 extensions (%G, %u, %V) and platform notes.
datetime_add accepts days, weeks, hours, minutes, seconds, months, and years (use negative values to go backward).
Text and slices
Slice notation on a bare column applies to the current row's cell value: {Name[:4]} takes the first four characters of Name in the current row.
To index into text after reading another row, subscript the row first: {Ticker[row_index][0]} for the first character of the current row, {Ticker[0][:4]} for the first four characters of the first row.
Conditional values
Use value_if_true if condition else value_if_false inside braces:
{Class if Class == 'Benchmark' else Class + ' (' + Inception_Date + ')'}
Formatting numbers in computed columns
After an expression, add a format spec: {Return:.2f} for two decimal places, {Amount:,.0f} for thousands separators.
Filter expressions are compiled as Python eval over the current row’s column names (sanitized when they are keywords). Computed columns use f-string-style templates: literals plus {expression} segments, with optional :format_spec. Column names in computed expressions are column vectors: bare A reads A[row_index], while A[0] and A[-1] read other rows. Only a fixed allowlist of AST nodes and functions is permitted - no imports, attribute access, or arbitrary calls. row_index comparisons with negative indices are rewritten against the row count in filter expressions. This is intentionally narrower than full Python, but familiar syntax usually carries over.
Parameters and preview
Transformations do not define their own parameters. They inherit parameters from the base source (and from any unioned sources). Set preview values in the builder to match how you will configure the workflow later - for example report date and portfolio ID.
Sample defaults are derived from uploaded data when possible (skipping title rows according to the collection’s skip settings).
Using transformations in workflows
Transformations appear alongside data collections when you:
- Connect data to workflow shapes (Data Connections)
- Configure data before starting a slide deck
- Add data objects during the Build phase
Link a transformation the same way you link a collection. Users still enter parameter values; the system runs the transformation chain and fills the shape with the result.
For Data Driven Only workflows, connect every chart, table, or text field that should show live data. See Using Data in Presentations.
Tips
- Build incrementally - Add one step, preview, then add the next. Easier to spot which step changed the table.
- Name steps clearly - The step type label is fixed, but a good transformation name helps others find it.
- Prefer select before filter - Dropping unused columns first makes expressions easier to read.
- Union last - Finish shaping the main table before appending rows from another source.
- Headers last - End with Select + Renames when the sample table has a header row; end with Remove header only when it does not. Never leave
ColumnNor raw workbook ids as the final names if the slide shows real labels.
Troubleshooting
“Unknown column”
A step references a column that does not exist after previous steps. Check spelling, underscores for spaces, or whether a Select step removed that column.
Filter keeps no rows (or all rows)
- Verify comparison types (quote text values).
- Try previewing the step before the filter to see actual column values.
- A failed expression is treated as “false” for that row.
Union columns misaligned
Use Rename source columns on the union step so names match the base table.
Wrong or missing column headers on the slide
Resolved column names become the table's header row. If the preview shows Column1/Column2 (after Remove header) or workbook names like class_name while the sample shows CLASS / NAV / QTR, add a final Select with Renames to those presentation labels. Use Remove header alone only when the sample table has no header row.
Numbers sort as text
Ensure values are numeric in the source. The engine coerces plain numeric strings automatically; identifiers with leading zeros stay as text.
Next steps
- Data Collections - Configure base sources, sheets, and parsing
- Data Landing Zone - Bulk-upload files into collections
- Data Connections in Workflows - Link transformations to slides
- Configuring Data for Slides - Validate parameters before generation