Usage
Squeeze packages selected assets into a ZIP download. For example, a Resources entry might have an Assets field with the handle downloads. Fetch those files in the entry's Twig template before using any of the examples below:
{% set assets = entry.downloads.all() %}Select at least one file on the entry and save it. The examples use archive as the download name; replace it with a name meaningful to your visitors.
Downloads must be authorised. Anonymous users need a signed token. Logged-in users may pass raw asset IDs only when they can view each asset.
Signed Tokens (Required for Anonymous Downloads)
Mint a token in Twig for the assets you intend to expose. Pass either Asset elements or asset IDs:
{# Direct download link #}
<a href="{{ craft.squeeze.getDownloadUrl(assets, 'archive') }}">Download</a>
{# Form with a fixed set of files #}
<form method="post" target="_blank">
{{ csrfInput() }}
{{ actionInput('squeeze/download') }}
{{ hiddenInput('downloadToken', craft.squeeze.createToken(assets, 'archive')) }}
<input type="submit" value="Download!">
</form>Checkbox / Subset Selection
Mint a token for every asset shown on the page, then let the user choose a subset via files[]. Only IDs included in the token can be downloaded:
<form method="post" target="_blank">
{{ csrfInput() }}
{{ actionInput('squeeze/download') }}
{{ hiddenInput('downloadToken', craft.squeeze.createToken(assets, 'archive')) }}
{% for asset in assets %}
<label>
<input type="checkbox" name="files[]" value="{{ asset.id }}">
{{ asset.title }}
</label>
{% endfor %}
<input type="submit" value="Download!">
</form>Open the link as a logged-out visitor and inspect the ZIP: it should contain the assets selected on the entry. For the checkbox form, select a subset and check that only those files are included.
Tokens are signed with a Squeeze-specific key derived from Craft’s security key and expire after one hour by default (defaultTokenDuration in Configuration). If a previously working link expires, reload the page to obtain a fresh token. When caching a page containing a token, ensure the cache lifetime does not outlast the token.
Shareable and User-Bound Links
Signed links are bearer links by default: anyone who receives the URL can download its exact asset set until the token expires. Keep lifetimes short and avoid logging or publishing tokenised URLs.
For a member-only link, pass true as the fourth argument. The user must be signed in both when the token is created and when it is used:
<a href="{{ craft.squeeze.getDownloadUrl(assets, 'member-files', null, true) }}">Download</a>User binding prevents a copied link from working in another account. It does not replace careful asset selection when the token is created.
Authenticated Downloads
Logged-in users with view permission on the assets may still post raw IDs:
<form method="post" target="_blank">
{{ csrfInput() }}
{{ actionInput('squeeze/download') }}
{{ hiddenInput('archivename', 'archive') }}
{% for asset in assets %}
<input type="checkbox" name="files[]" value="{{ asset.id }}">
{% endfor %}
<input type="submit" value="Download!">
</form>Archive Contents
Squeeze uses each asset's filename inside the ZIP. When two selected assets have the same filename, including names that differ only by letter case, Squeeze keeps both by adding a number to the later file. For example, two assets named Report.pdf and report.pdf become Report.pdf and report (2).pdf.
Archive creation is atomic. If Squeeze can't read one of the selected assets, it stops the download and removes the partial archive instead of returning an incomplete ZIP. The maxFiles and maxArchiveSize settings described in Configuration protect the server from unexpectedly large requests.
Access Control
For each asset Squeeze will:
- Reject it when
allowedVolumesis set (not*) and the asset’s volume is not listed - Allow it when the request includes a valid signed token that includes that asset ID
- Otherwise allow it only when the current user can view the asset