Skip to content

Releases: bknd-io/bknd

v0.9.1

10 Mar 11:37
b786fbc
Compare
Choose a tag to compare

What's Changed

  • fix: docker fails due to trying to open a browser by @dswbx in #107

Full Changelog: v0.9.0...v0.9.1

v0.9.0

05 Mar 09:12
01cb9d2
Compare
Choose a tag to compare

🚀 New Features

Create a local API (#89)

When deploying bknd in a full stack framework, you may want to make use of the API SDK without traveling the network. It was possible before, but not so handy. Now you can create a local API from the app instance easily:

// check your frameworks' doc
const app = createApp(); 

// this api instance won't travel the network!
const api = app.getApi();

// you can also pass `headers` or the `request` object to get the API tied to a specific user for authorization
app.getApi({ request });
app.getApi({ headers });

Next.js App Router support (#89)

The Next.js example and CLI starter template has been updated to App Router. Get started by running:

npx bknd create -i nextjs

CleanShot 2025-03-05 at 09 40 26

AWS Lambda adapter (#102)

The official AWS Lambda adapter is now available in the docs and CLI starter:

npx bknd create -i aws

The CLI starter also includes a deploy.sh script that automatically pulls static assets, bundles the lambda and creates all required AWS resources. But make sure to create a Turso database first (database as file is generally possible but increases the deployment size and causes issues with concurrency).

import { serveLambda } from "bknd/adapter/aws";

export const handler = serveLambda({
   connection: {
      url: process.env.DB_URL!,
      authToken: process.env.DB_AUTH_TOKEN!
   },
   assets: {
      mode: "local",
      root: "./static"
   }
});

Data Bulk Updates & more (#99 & #104)

The data API and controller has been updated to allow bulk insertions, updates and deletions:

// many insertions
await api.data.createMany("posts", [
   { title: "Hello, World!" },
   { title: "Again, Hello." },
]);

// many updates
await api.data.updateMany("posts", { views: { $gt: 1 } }, {
   title: "viewed more than once"
});

// many deletions
await api.data.deleteMany("posts", { views: { $lte: 1 } });

Furthermore, a new readOneBy() method has been added to retrieve a single item by any given query. It's a convenience wrapper around readMany but always returns a single item:

await api.data.readOneBy("posts", { title: "Hello, World!" });

Auth UI improvements (#98)

Authentication settings and strategies are now directly inside /auth (still available in advanced settings) with a more appealing UX/UI.

SettingsStrategies
Auth Settings Auth Strategies

Report of unindexed fields (#96)

If you're like me, you just forget about adding indices when implementing a new feature quickly until you inspect the performance or the overall reads. That's not an issue with only a few queries, but as you keep adding, it's hard to keep track and spot bottlenecks. The with property already reduces the amount of queries you need to execute, and now, bknd will automatically log a warning into the console every time you're using an attribute for sorting or filtering that hasn't been indexed:

[WRN] 2025-03-05 10:02:37 Field "posts.title" used in "where" is not indexed

So now, to spot potential performance bottlenecks you only have to keep an eye on the console! You can add new indices by heading to the advanced settings at /settings/data/indices (documentation is coming soon, the UI will also be updated to make it even easier).

Other Changes

  • improve console with timestamps by @dswbx in #94
  • media more mime types and add dropzone mime checker by @dswbx in #95
  • fix ManyToManyRelation to respect select from with query by @dswbx in #92
  • feat/ci-tests by @dswbx in #97
  • fix active sidebar active item, added error boundaries for relational form fields, fixed schema diagram for m:n relations by @dswbx in #100
  • added missing cache directives to media adapter serving by @dswbx in #101

Full Changelog: v0.8.1...v0.9.0

v0.8.1

21 Feb 07:20
9ecfcb3
Compare
Choose a tag to compare

Fixes

  • media mime guessing when uploading to entity
  • media upload without name
  • media data upload db result wasn't included in response
  • Api import in App to reduce build size

Full Changelog: v0.8.0...v0.8.1

v0.8.0

19 Feb 18:50
89871a8
Compare
Choose a tag to compare

🚧 Breaking changes

Data API Endpoint changed #83

Data Entity API routes are now prefixed with /entity – this is required to add more data API routes without conflicting with entity names. If you were using HTTP endpoints, change as follows:

-[...]/api/data/posts?[...]
+[...]/api/data/entity/posts?[...]

If you were using the Admin Panel or the included SDK, there is no change required.

Module Manager Configuration relocation #85

If you were creating an app using module manager options, these have moved now in order to allow future app configuration options.

const app = createApp({
  connection: { /* ... */ },
  initialConfig: { /* ... */ },
  {
-    /* ... manager options ... */
-    verbosity: 2
+    manager: {
+      /* ... manager options ... */
+      verbosity: 2
+    }
  }
});

🚀 New Features

The CLI now includes project starters! #79

v0.8_cli_create.mp4

To start off a new project with bknd, you can run (in the video you see a different command, it was recorded during development):

npx bknd create

Currently these starters are available: Node.js, Bun, Cloudflare, Next.js, Remix and Astro. There will be more in the future! It's also planned to include community built templates.

Connection is now set to libsql by default #77

You can now omit the type for the connection object, since it's all libsql by default. Custom connections must be used with Connection instances directly. Adding the type of libsql is still supported but will be removed in future releases.

serve({
   connection: {
-     type: "libsql",
-     config: {
-       url: "..."
-     }
+     url: "..."
   }
});

Added Cloudflare D1 and R2 bindings #73

If you're using the Cloudflare adapter, you can now use D1 as your database and R2 binding for media assets. The adapter automatically scans your environment for D1 and R2 bindings:

  • if you haven't specified any connection, it uses the first D1 binding it finds
  • you can manually specify a D1 binding using the binding option
  • if you want to use LibSQL instead, you can define a connection object
import { serve, d1 } from "bknd/adapter/cloudflare";

// scans your environment for the first D1 binding it finds
export default serve();

// manually specifying a D1 binding:
export default serve<Env>({
  app: ({ env }) => d1({ binding.your_d1_binding })
});

// or specify binding using `bindings`
export default serve<Env>({
  bindings: ({ env }) => ({ db: env.your_d1_binding })
});

// or use LibSQL
export default serve<Env>({
  app: ({ env }) => ({ url: env.DB_URL })
});

R2 bindings are also automatically discovered and offered as selection choices when configuring an adapter in UI:
CleanShot 2025-02-19 at 19 33 04

Media API improvements #80

Previously, there wasn't a way of using the API to upload media assets. That has changed! And since you may not know in which situation you need a file to be uploaded, you can literally pass any argument to the upload handler for it to land on bknd:

// via external url
api.media.upload("https://example.com/image.png", "image.png");

// via request
api.media.upload(fetch("https://example.com/image.png"), "image.png");

// via response
api.media.upload(await fetch("https://example.com/image.png"), "image.png");

// via readable stream
api.media.upload((await fetch("https://example.com/image.png")).body, "image.png");

// via file input
<input type="file" onChange={async (e) => {
  const file = e.target.files?.[0];
  if (file) {
    // file name not required, as it can be extracted from `File`
    await api.upload(file);
  }
}} />

Configuration changes now run in sandbox first #76

If you make any configuration change like adding an entity, enabling auth, or changing the theme: Configuration changes now run sandboxed before they get applied and stored. If it fails, the previous (well, actually "current") state is kept and continued.

CLI now checks env #78

Previously, to run bknd using the CLI, you had to specify the --db-url (and --db-token) in order to point to your instance. You can still do this, but if these options aren't present, the CLI now checks for DB_URL and DB_TOKEN environment variables (let me know if you encounter any conflicts with the name, we could also prefix them with BKND_*).

Instead of running:

npx bknd run --db-url file:data.db

You can now create an .env file, and start it directly:

DB_URL=file:data.db
npx bknd run

This will be especially useful for future commands which lets you directly interact with your app without a GUI.

CLI prefers a database file by default #86

Previously, if you ran npx bknd run without any argument, it was launching with an in-memory database. Now instead, it creates a database using a data.db file in the directly where you run the command. This is more intuitive. You can still choose an in-memory database by running npx bknd run --memory.

Other Changes

  • fixing ui modal styling and make sure schema reloads on media setting changes by @dswbx in #74
  • moved auth ctx to request context by @dswbx in #81
  • add admin "system" theme option that checks user prefs by @dswbx in #82
  • added debug routes cli action by @dswbx in #84
  • fix persisting of many to many entity by @dswbx in #87
  • refactor/improve-remix-example by @dswbx in #88

Full Changelog: v0.7.1...v0.8.0

v0.7.1

10 Feb 13:55
1e5c0db
Compare
Choose a tag to compare

What's Changed

  • fix: popover regression & dropzone rerender lost state by @dswbx in #72

Full Changelog: v0.7.0...v0.7.1

v0.7.0

08 Feb 15:59
09d35d3
Compare
Choose a tag to compare

Breaking Changes

Removed Api export from bknd, so you now have to import it from bknd/client:

-import { Api } from "bknd";
+import { Api } from "bknd/client";

If you were using Astro, you'd now need to await the getApi helper. This ensures that authentication is always verified:

import { getApi } from "bknd/adapter/astro";

+const api = await getApi(Astro, { mode: "dynamic" });
-const api = getApi(Astro, { mode: "dynamic" });
-await api.verifyAuth();
const user = api.getUser();

New Form component

bknd is extensively using JSON Schema, and is also using form generators to automatically generate them mainly for the advanced settings. But these forms don't really look and feel good, so I've made a custom implementation that is highly adjustable. It automatically infers the types from the JSON Schema and validates it according to your needs. The new media settings were built using it, here is a general demo:

form_demo.mp4

Improved Media Settings

Previously, the only way to enable media was to go over to Advanced Settings. Since these are mainly auto generated, the experience wasn't very nice. Check here how it is improved now using the custom JSON Schema form generator implementation:

image

Full Changelog

  • Adapter: verified auth & env-specific construction by @dswbx in #59
  • adapter(cloudflare): add supports for the new assets feature by @dswbx in #61
  • optimize adapter imports to deduplicate by @dswbx in #62
  • fix/api-and-adapter by @dswbx in #63
  • updated API instantiation, and update user on verify by @dswbx in #64
  • feat/auth-redirect-param by @dswbx in #65
  • also sending cookies on json auth requests by @dswbx in #66
  • fix clearing schema on unauthorized secrets fetching by @dswbx in #69
  • fix/api-query-with-string-object by @dswbx in #67
  • Improved media settings UI/UX by @dswbx in #68
  • Feat/optimize form renders by @dswbx in #70
  • feat/elements-native-form by @dswbx in #71
  • Release 0.7 by @dswbx in #60

Full Changelog: 0.6.2...v0.7.0

0.6.2

25 Jan 08:41
3d1d52c
Compare
Choose a tag to compare

What's Changed

  • bknd/plasmic: added helper functions for integration by @dswbx in #55
  • fixed schema updates to fail in nextjs envs due to lodash's merge by @dswbx in #54
  • restructured elements for better customization by @dswbx in #57

Full Changelog: 0.6.1...0.6.2

0.6.1

21 Jan 16:14
24542f3
Compare
Choose a tag to compare

What's Changed

  • fix auth screens' missing config permission, and media URL resolution by @dswbx in #53

Full Changelog: v0.6.0...0.6.1

v0.6.0

21 Jan 07:07
42f935a
Compare
Choose a tag to compare

What's Changed

  • update plasmic package to omit cjs by @dswbx in #45
  • refactor event system to support returnable events by @dswbx in #46
  • fix advanced flow creation due to schema mismatches by @dswbx in #44
  • optimize elements by reducing the bundle size required by @dswbx in #42
  • recursive with by @dswbx in #48
  • DataApi: automatically switch to POST if the URL is too long by @dswbx in #49
  • Create users in Admin UI by @dswbx in #50
  • Admin UI improvements by @dswbx in #51
  • Admin UI: Adding context menu to entities list by @dswbx in #52
  • reduce ui bundle size by @dswbx in #43

Full Changelog: v0.5.0...v0.6.0

v0.5.0

14 Jan 11:30
4e923bf
Compare
Choose a tag to compare

What's Changed

  • refactor module schema handling and add sync mechanism by @dswbx in #41
  • refactor: remove cjs from build to reduce package size by @dswbx in #35
  • refactor: extracted auth as middleware to be added manually to endpoints by @dswbx in #36
  • feat: allow data query to have single string as sort by @dswbx in #37
  • optimized vite adapter with better defaults by @dswbx in #38
  • React Elements: Auth, Media by @dswbx in #39

Full Changelog: v0.4.0...v0.5.0