Skip to content

Fix PostGIS loading to use async WASM precompilation#895

Closed
larsmennen wants to merge 3 commits intoelectric-sql:tdrz/frontend-try-postgis2from
cogna-public:larsmennen/async-postgis-precompilation
Closed

Fix PostGIS loading to use async WASM precompilation#895
larsmennen wants to merge 3 commits intoelectric-sql:tdrz/frontend-try-postgis2from
cogna-public:larsmennen/async-postgis-precompilation

Conversation

@larsmennen
Copy link

This aims to fix loading of PostGIS in Chrome using async wasm precompilation to get around the 8mb browser limit.

Problem seemed to be that createPreloadedFile was called with the filename stripped of .so. Emscripten's wasm preload plugin checks name.endsWith('.so') in canHandle(), so it never activated. That's the main fix applied here and in the accompanying PR: electric-sql/postgres-pglite#63

With the pglite-socket fix applied from #807 and muting the DEBUG messages as per same PR, I get the following test results:

packages/pglite-postgis:

  ✓ tests/postgis.test.ts       (5 tests)

  Test Files: 1 passed / Tests: 5 passed

PostGIS regression suite:  
   regress/core/regress  .. ok in 220 ms
   regress/core/wkt      .. ok in 37 ms
   regress/core/measures .. ok in 117 ms
   regress/core/geography.. ok in 124 ms
   regress/core/operators.. ok in 71 ms
   regress/uninstall     .. failed (Object count pre-install 5456 != post-uninstall 5458)

  Run tests: 6 / Failed: 1

The failing uninstall test is pre-existing I believe, as per similar comment in #807, though I can't get it to pass by turning off the DEBUG messages (seems to work for the other tests), but let me know if you think this might be related to this change.

As a test, this works in Chrome:

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>PostGIS Chrome Test</title>
  <style>
    body { font-family: monospace; padding: 20px; background: #1a1a1a; color: #eee; }
    h1 { color: #aaa; font-size: 1.2em; }
    #log { white-space: pre-wrap; font-size: 13px; }
    .ok  { color: #4caf50; }
    .err { color: #f44336; }
    .inf { color: #64b5f6; }
    .dim { color: #888; }
  </style>
</head>
<body>
  <h1>PostGIS async preload plugin test</h1>
  <div id="log"></div>
  <script type="module">
    const log = document.getElementById('log')
    const append = (cls, msg) => {
      const span = document.createElement('span')
      span.className = cls
      span.textContent = msg + '\n'
      log.appendChild(span)
    }
    const info = m => append('inf', m)
    const ok   = m => append('ok',  '✓ ' + m)
    const err  = m => append('err', '✗ ' + m)
    const dim  = m => append('dim', m)

    info('Importing pglite…')
    try {
      // Import pglite and postgis from their dist directories
      const { PGlite } = await import('./pglite/dist/index.js')
      const { postgis }  = await import('./pglite-postgis/dist/index.js')

      info('Creating PGlite instance with postgis extension…')
      const db = new PGlite({ extensions: { postgis } })

      info('Waiting for db.ready…')
      await db.waitReady

      ok('PGlite ready')

      info('Running: CREATE EXTENSION postgis;')
      await db.exec('CREATE EXTENSION postgis;')
      ok('CREATE EXTENSION postgis succeeded')

      info('Running: SELECT postgis_full_version();')
      const result = await db.query('SELECT postgis_full_version() AS v;')
      ok('postgis_full_version: ' + result.rows[0].v)

      info('Running: SELECT ST_AsText(ST_MakePoint(1,2));')
      const pt = await db.query("SELECT ST_AsText(ST_MakePoint(1,2)) AS wkt;")
      ok('ST_MakePoint: ' + pt.rows[0].wkt)

      ok('All tests passed')
    } catch (e) {
      err('Error: ' + e.message)
      dim(e.stack || '')
      console.error(e)
    }
  </script>
</body>
</html>

@tdrz
Copy link
Collaborator

tdrz commented Feb 24, 2026

@larsmennen Really cool, thank you!

Problem seemed to be that createPreloadedFile was called with the filename stripped of .so.

Why wouldn't we remove the stripping instead?

@tdrz
Copy link
Collaborator

tdrz commented Feb 24, 2026

Hm, we're moving away from modifying the SDK (ie we don't want any hotfixes in the future) so ideally we wouldn't work on those files. @larsmennen with your change we're very close to having this working, just need to find a way without modifying the sdk (and btw this makes sense why it didn't already work - yet another reason to stay away from modifying the SDK).

@tdrz
Copy link
Collaborator

tdrz commented Feb 24, 2026

file.name.split('/').pop()!.slice(0, -3)
->
file.name.split('/').pop()
i guess...

@larsmennen
Copy link
Author

Thanks, that makes sense -- would be simpler. let me give that a go

@larsmennen
Copy link
Author

@tdrz that did the trick i think. i've removed the stripping of .so but kept in awaiting the precompilations. also that means we don't need any changes in hotfix/library_dylink.js so I've closed the accompanying PR. FWIW, now all tests pass for me as well... haven't investigated if the previous failure was related to changes or flaky, but they seem to pass now:

  Summary of results:

   regress/core/regress  .. ok in 248 ms
   regress/core/wkt      .. ok in 45 ms
   regress/core/measures .. ok in 120 ms
   regress/core/geography .. ok in 126 ms
   regress/core/operators .. ok in 81 ms
   regress/uninstall     .. ok (5458)

  Run tests: 7 / Failed: 0

Browser test (the HTML in the PR description) also works.

@tdrz
Copy link
Collaborator

tdrz commented Feb 24, 2026

pnpm -r stylecheck --write

@larsmennen
Copy link
Author

thx, done

@tdrz
Copy link
Collaborator

tdrz commented Feb 24, 2026

@larsmennen Build fails ... weird. I'll try to have a look this week, but can't promise anything.

@larsmennen larsmennen force-pushed the larsmennen/async-postgis-precompilation branch from 11a42e3 to 9690184 Compare February 24, 2026 21:40
@tdrz
Copy link
Collaborator

tdrz commented Feb 26, 2026

@larsmennen I've integrated your changes + fixes in the main PostGIS branch, thank you for finding the issue!

@tdrz tdrz closed this Feb 26, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants