defter 0.1.0

Self-hosted Zotero sync and file storage server, with metadata in SQLite and attachments in S3.
<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <meta name="robots" content="noindex" />
    <title>defter</title>
    <link rel="icon" type="image/svg+xml" href="data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 32 32'%3E%3Crect width='32' height='32' rx='6' fill='%230d9488'/%3E%3Cpath d='M10 7h9a5 5 0 0 1 5 5v13H13a3 3 0 0 1-3-3z' fill='white'/%3E%3Cpath d='M14 12h6M14 16h6M14 20h4' stroke='%230d9488' stroke-width='1.5' stroke-linecap='round'/%3E%3C/svg%3E" />
    <script>
      (function () {
        const stored = localStorage.getItem('defter-dark')
        const prefersDark = window.matchMedia('(prefers-color-scheme: dark)').matches
        if (stored === 'true' || (stored === null && prefersDark)) {
          document.documentElement.classList.add('dark')
        }
      })()
    </script>
  </head>
  <body>
    <div id="app"></div>
    <script type="module" src="/src/main.js"></script>
  </body>
</html>