perspective-python 4.4.1

A data visualization and analytics component, especially well-suited for large and/or streaming datasets.
Documentation
<script type="module" src="$psp_cdn_perspective"></script>
<script type="module" src="$psp_cdn_perspective_viewer"></script>
<script type="module" src="$psp_cdn_perspective_viewer_datagrid"></script>
<script type="module" src="$psp_cdn_perspective_viewer_d3fc"></script>
<link rel="stylesheet" crossorigin="anonymous" href="$psp_cdn_perspective_viewer_themes" />

<div class="perspective-envelope" id="perspective-envelope-$viewer_id">
    <script type="application/vnd.apache.arrow.file">
    $b64_data
    </script>
    <perspective-viewer style="height: 690px;"></perspective-viewer>
    <script type="module">
        // from MDN
        function base64ToBytes(base64) {
            const binString = atob(base64);
            return Uint8Array.from(binString, (m) => m.codePointAt(0));
        }

        import * as perspective from "$psp_cdn_perspective";
        const viewerId = $viewer_id;
        const currentScript = document.scripts[document.scripts.length - 1];
        const envelope = document.getElementById(`perspective-envelope-$${viewerId}`);
        const dataScript = envelope.querySelector('script[type="application/vnd.apache.arrow.file"]');;
        if (!dataScript)
            throw new Error('data script missing for viewer', viewerId);
        const data = base64ToBytes(dataScript.textContent);
        const viewerAttrs = $viewer_attrs;

        // Create a new worker, then a new table promise on that worker.
        const table = await perspective.worker().table(data.buffer);
        const viewer = envelope.querySelector('perspective-viewer');
        viewer.load(table);
        viewer.restore(viewerAttrs);
    </script>
</div>