The {{<csv>}}
shortcode provides a simple way to embed CSV files in your documentation from a global static/csv
directory. This approach works well for large and/or complex tables that you want to keep separate from your markdown files.
Using this shortcode also enables you to update your CSV files programmatically without needing to update the markdown files that reference them.
How it works #
The {{<csv>}}
shortcode accepts 3 positional arguments: filename
, delimiter
, and excludedColumns
.
filename
specifies the CSV file to embed. The file resides in thestatic/csv
directory. You don’t need to include the.csv
extension.delimiter
defines the character that separates columns in the CSV file. Default:,
.excludedColumns
accepts a comma-separated list of column numbers to exclude from the table. This parameter has case-sensitivity and defaults to an empty string.
Examples #
The table in the following examples comes from /static/csv/food.csv
.
Full table with default delimiter #
{{<csv food>}}
Error: CSV file "food" not found in the csv directory.
Full table with excluded column #
{{<csv food "," "Origin">}}
Error: CSV file "food" not found in the csv directory.
Source code #
{{$filename := .Get 0}}
{{- $delimiter := .Get 1 | default "," -}}
{{- $skipColumns := split (.Get 2 | default "") "," -}}
{{- $csvResource := resources.Get (printf "csv/%s" $filename) -}}
{{- if not $csvResource -}}
<div class="error">Error: CSV file "{{ $filename }}" not found in the csv directory.</div>
{{- else -}}
{{- $csvData := $csvResource | transform.Unmarshal (dict "delimiter" $delimiter) -}}
{{- if not $csvData -}}
<div class="error">Error: Failed to parse CSV data from "{{ $filename }}". The file may be empty or incorrectly formatted.</div>
{{- else -}}
<div class="overflow-x-auto">
<table class="min-w-full divide-y divide-zinc-200">
<thead>
<tr>
{{- range $index, $col := index $csvData 0 -}}
{{- if not (in $skipColumns $col) -}}
<th scope="col" class="px-3 py-2 text-left text-sm font-semibold text-black uppercase tracking-wider">
{{- $col -}}
</th>
{{- end -}}
{{- end -}}
</tr>
</thead>
<tbody class="divide-y divide-zinc-200">
{{- range $rowIndex, $row := after 1 $csvData -}}
<tr class="{{ cond (modBool $rowIndex 2) "bg-zinc-50" "bg-white" }}">
{{- range $colIndex, $col := $row -}}
{{- if not (in $skipColumns (index (index $csvData 0) $colIndex)) -}}
<td class="px-3 py-2 whitespace-nowrap text-sm text-black">
{{- $col | markdownify -}}
</td>
{{- end -}}
{{- end -}}
</tr>
{{- end -}}
</tbody>
</table>
</div>
{{- end -}}
{{- end -}}