Backpex - a highly customizable admin panel for Phoenix LiveView applications

Hey!

I can see the problem that providing all the information can be tedious at first, but I also think that hiding the live resource configuration behind another module is not perfect either. Especially when it comes to supporting multiple data sources, like Ecto or Ash.

The setup is not that easy anyway, and creating another abstraction (live resources are already an abstraction for resources) makes it even more complicated.

I really appreciate your work and ideas to simplify the setup, but I guess we will not add such an auto live resources to the core at the moment. We are open to an add-on package if you need this feature and want to maintain such an automatic resource generation.

When it comes to making setup easier, I’d like to see Mix tasks that do the resource introspection and automatically generate live resources for you. The advantage of a Mix task is that we’d simplify the setup, but end up with the same configuration (both manually and programmatically via running a mix task).

Looking forward to hearing your thoughts!

1 Like

I understand. I have no interest in Ash, so I just want the simplest setup possible for Ecto schemas, which is what I actually use.

I aggree, but the disadvantage is that you have to do it all over again if you edit your schema. Again, that is a tradeoff and I certainly understand your position.

Writing a mix task to do what you want is actually not too hard. You could use the debug output from my AutoLiveResource module and replace some parts with the appropriate variables in an EEx template.

The code is neatly encapsulated in a single module, which means I can publish such package myself completely independently of Backpex. The only question is whether I should do it in a different top-level namespace (e.g. BackpeXtra) or whether it would be safe to do it under something like Backpex.Extra. I guess the first option is safer, and additionally, the second option could be seen as anedorsement by Backpex, which is not the intended idea.

1 Like

I have thought about it a bit more and I’ll publish my own package under the BackpexAuto so that I can have a BackpexAuto.EctoLiveResource module (as you say, my approach is specific to the Ecto adapter).

In order to make it closer to what @Flo0807 envisioned, I have changed my package’s functionality slightly to use my new CodeGen library, which is actually great for cases such as these, where you want automatic code generation, butr in which you want to minimize the actual amount of code in your project.

First, build the common LiveResource module for you application which encapsulates database and layout information (not that if you want two different layouts you can just define two of these modules and use them in the appropriate places):

defmodule MyAppWeb.LiveResource do
  use BackpexAuto.EctoLiveResource,
    repo: MyApp.Repo,
    layout: {MyAppWeb.Layouts, :admin},
    pubsub: MyApp.PubSub
end

This has now created a β€œmeta-module” which you will use to create the live resource modules, BUT not, instead of using, you’ll be using CodeGen from my CodeGen library:

defmodule MyAppWeb.MyContext.CountryLive do
  use CodeGen,
    module: MyAppWeb.LiveResource,
    options: [
      resource: MyApp.MyContext.Patient
    ]
end

The above is very similar to calling use MyAppWeb.LiveResource, ..., except a bit more verbose. However, it has the advantage that the generated AST is divided into blocks, which you can inspect in IEx and dump the source code of some of the blocks into your actual module.

iex(2)> CodeGen.block_names(MyAppWeb.MyContext.CountryLive)
["auto_live_resource:changesets", "auto_live_resource:names",
 "auto_live_resource:fields"]

iex(5)> CodeGen.show_block(MyAppWeb.MyContext.CountryLive, "auto_live_resource:fields") 
β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€
β”‚ Block: auto_live_resource:fields
β”œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€
β”‚ @impl Backpex.LiveResource
β”‚ def fields do
β”‚   [
β”‚     name: %{label: "Name", module: Backpex.Fields.Text},
β”‚     inserted_at: %{
β”‚       except: [:new],
β”‚       format: "%Y-%m-%d %H:%M:%S",
β”‚       label: "Inserted at",
β”‚       module: Backpex.Fields.DateTime,
β”‚       readonly: true
β”‚     },
β”‚     updated_at: %{
β”‚       except: [:new],
β”‚       format: "%Y-%m-%d %H:%M:%S",
β”‚       label: "Updated at",
β”‚       module: Backpex.Fields.DateTime,
β”‚       readonly: true
β”‚     }
β”‚   ]
β”‚ end
└───────────────────────────────────────────────────────

iex(4)> CodeGen.dump_source(MyAppWeb.MyContext.CountryLive, "auto_live_resource:fields")   

After dumping the source, the block is added to the module:

defmodule MyAppWeb.MyContext.CountryLive do
  use CodeGen,
    module: MyAppWeb.LiveResource,
    options: [
      resource: MyApp.MyContext.Country
    ]

  @impl Backpex.LiveResource
  def fields do
    [
      name: %{label: "Name", module: Backpex.Fields.Text},
      inserted_at: %{
        except: [:new],
        format: "%Y-%m-%d %H:%M:%S",
        label: "Inserted at",
        module: Backpex.Fields.DateTime,
        readonly: true
      },
      updated_at: %{
        except: [:new],
        format: "%Y-%m-%d %H:%M:%S",
        label: "Updated at",
        module: Backpex.Fields.DateTime,
        readonly: true
      }
    ]
  end
end
3 Likes

Backpex v0.9 release

A few days ago we’ve released Backpex v0.9.

Along with the new version, we’ve also published a redesign of our landing page: https://backpex.live/

Key highlights of v0.9:

  • New Backpex.Fields.Time field (thanks to @thanos :clap:)
  • Field option validation
  • Save & continue editing" button
  • Support for default ash destroy action

We noticed that there are many field options and you can easily get confused. So the field option validation ensures that you can only define options that are actually used by the corresponding field. It also ensures that configuration errors are caught earlier, increasing developer experience.

With large forms, you may want to save your changes more than once to ensure that you do not lose them. To address this, we’ve added a β€œSave & Continue Editing” button that allows you to save the form, but not be taken to the list view, and stay in the edit view. We have not added an option to hide the button, so we welcome feedback on this to decide whether we need to add such a configuration or not.

We also now support the basic ash destroy action, so you can now delete ash resources. We are still working on the ash integration as it is still very early days.

Breaking changes from v0.9:

  • Refactored of the field_input component to be more generic
  • Renamed the item and resource action init_change/1 callback to base_schema/1 to make it easier to understand what the function is used for
  • Changed the expected return values of the item and resource action handle functions.

Be sure to read the upgrade guide linked below, as you will need to make some changes to your code to make the latest version work.

Release Notes: Release 0.9.0 Β· naymspace/backpex Β· GitHub
Upgrade Guide: Upgrading to v0.9 β€” Backpex v0.9.1

6 Likes

Just dropped by to show my appreciation. I find the documentation to be excellent. I also find the separation of concerns to be excellent leading to it being easy enough to customize. Keep it up.

4 Likes

hi, looks really great and I am starting an Ash project right now and would like to use Backpex from day zero if possible. I see your demo code but it would be nice if you could drop some hints, perhaps even docs on how to install using Ash

Backpex v0.10 release - Phoenix LiveView 1.0

We have released Backpex version 0.10 which now supports and uses Phoenix LiveView 1.0 :tada:

This release also includes some minor documentation improvements. We’ve also relaxed the version requirements to fix dependency resolution bugs.

Note that you need to use Phoenix LiveView 1.0 in your application if you want to install Backpex v0.10.

Thanks to @thomas.fortes for the LiveView 1.0 upgrade! :raised_hands:

Release Notes: Release 0.10.0 Β· naymspace/backpex Β· GitHub

7 Likes

Hey!

Note that the Ash adapter is still a work in progress. Currently, you can only list, view and delete Ash resources, so the Ash integration in Backpex is very limited at the moment.

I think the best way to install Ash is to follow their documentation. But I also think we can improve the documentation for our adapter pattern in Backpex, I will add that to my to-do list.

Until then, feel free to ask if you have specific questions.

1 Like

Just curious: how does this compare to AshAdmin?
Hadn’t tried out neither yet but it seems similar.
Perhaps @zachdaniel would also know something.

how can we help get Ash integrated? can you create tasks or issues in GH?

Hey!

I’ve created a meta issue for Ash integration. The goal is to keep track of everything that needs to be done to support (basic) Ash support in Backpex. We intend to create additional sub-issues for certain tasks when it is more clear how we want to solve them.

Link to the meta issue: Ash support Β· Issue #823 Β· naymspace/backpex Β· GitHub

I’ve already created a sub-issue to support other (Ash) actions than the defaults, as it’s mostly clear what needs to be done: Ash: Support other actions than defaults Β· Issue #825 Β· naymspace/backpex Β· GitHub

You are welcome to help us by suggesting concrete ideas on how to tackle certain tasks from the meta issue, or by working on tasks that are already clear.

In any case, it is a good idea to send a short message so that we know what the community is working on and can provide some help with Backpex related stuff if needed :rocket:

4 Likes

AshAdmin can be used to automatically generate database-like views for your Ash resources. As far as I know, it was created mainly for testing purposes. It is a good way to visualize and test your Ash resources during development, but is not meant to be used by non-developers, for example. The advantage is that it doesn’t require much configuration.

Backpex focuses on a cleaner UI that could also be used by customers. It offers many configuration options for fields and views. For example, you can define (custom) filters and item actions to be added to your page.

Both projects have different target groups and purposes, so I guess it is difficult to compare them side by side.

Many Backpex users have asked for an Ash support because they want to have the advantages of Backpex (customizable admin panel that can be used by non-developers) in their Ash projects.

5 Likes

Thanks for this post and the pointer on the watcher.

Installation was somewhat fiddly, but I believe that I found I needed to remove the --input=css/app.css line from the backpex tailwind config to get the backpex styles to show. At any rate, the Backpex styles are now ending up in the admin stylesheet okay without that line.

Backpex v0.11 release - removal of Alpine.js dependency

We’ve just released Backpex v0.11. This release focuses on the developer experience by removing Alpine.js as a dependency and making the installation process much easier.

So you can finally remove Alpine.js from your application if you only installed it because of Backpex :tada:

Note that you’ll now have to add our custom hooks (see the upgrade guide for more information).

Key Highlights:

  • Replace Alpine.js with JS hooks
  • Add external upload support for the upload field
  • Add after_main position to render_resource_slot/3

Make sure to read the full release notes for all changes and new features that have been added.

We’ve also continued development on the adapter pattern and fixed some bugs.

As always, thanks to all external contributors :star2:

Release Notes: Release 0.11.0 Β· naymspace/backpex Β· GitHub
Upgrade Guide: Upgrading to v0.11 β€” Backpex v0.11.0

10 Likes

Backpex v0.12 - Tailwind CSS v4 and daisyUI v5

Backpex v0.12 is released! This release includes two major dependency updates. Backpex is now updated to Tailwind CSS v4 and daisyUI v4 :art:

We require you to use this version as well. So if you have not yet updated, it might be a good idea to do so now :building_construction:

In addition to the dependency updates, this release also contains other key changes:

  • PubSub config is now optional - this allows you to remove the PubSub config from your LiveResources entirely
  • We have added a form_action parameter to the return_to callback - this allows you to customize the URL based on whether the user cancels or saves an item
  • We have disabled the β€œSave & Continue Editing” button by default

We’ve also updated the way translations work in Backpex. You can now change (almost) any text in Backpex per LiveResource with a new translate/1 callback :speech_balloon:

As this release contains some major changes, be sure to read the Upgrade Guide carefully.

Thanks to all the external contributors. This release alone has three new contributors. We greatly appreciate your work! :star2:

Release Notes: Release 0.12.0 Β· naymspace/backpex Β· GitHub
Upgrade Guide: Upgrading to v0.12 β€” Backpex v0.12.0

1 Like

Whats the status on connecting this to ash resources? Is there a tracker somewhere?

4 Likes

Anyone has an example how to use β€œsearch_condition” in a LiveResource field?

I’m using:

  myfield: %{
    module: Backpex.Fields.Text,
    label: "My Field",
    searchable: true,
    search_condition: &myfield_search_condition/3,
  },

and I’m getting:

Configuration error for field "myfield" in "Elixir.FocuLeadWeb.CaseLive".

unknown options [:search_condition], valid options are: [:module, :label, :default, :render, :render_form, :custom_alias, :align, :align_label, :searchable, :orderable, :visible, :can?, :panel, :index_editable, :index_column_class, :select, :only, :except, :translate_error, :placeholder, :debounce, :throttle, :readonly]

search_condition is a callback, which can be implemented by custom fields. You cannot set it as an option for existing fields.

Backpex v0.13: Refactoring…

Last week, we released Backpex v0.13, which features significant internal changes: A Backpex LiveResource module is no longer a single LiveView. We have split things up into Index, Form (Edit and New) and Show LiveViews, which are generated at compile time. These changes have had little impact on the configuration of the LiveResource for Backpex users. However, if you used LiveView callbacks (handle_event, handle_info, etc.) to add custom logic, there is now a new way to do so via the on_mount option. Make sure you read the Upgrade Guide.

This was an important step towards improving the code structure and making further improvements to the core codebase.

Other improvements include:

  • You can now add help text to fields, which is displayed below the input.
  • Server-error and client-error alerts have been added to the flash_messages component.

As always: Thanks to all contributors! :heart:

Release notes: https://github.com/naymspace/backpex/releases/tag/0.13.0
Upgrade guide: Upgrading to v0.13 β€” Backpex v0.13.0

5 Likes