Giter Club home page Giter Club logo

adminjs's Introduction

AdminJS

AdminJS is an automatic admin interface that can be plugged into your application. You, as a developer, provide database models (like posts, comments, stores, products or whatever else your application uses), and AdminJS generates UI which allows you (or other trusted users) to manage content.

Inspired by: django admin, rails admin and active admin.

Example application

Check out our demo application:

https://demo.adminjs.co

You can also have a look at our customized AdminJS dashboard which shows various library statistics:

https://stats.adminjs.co

Getting started

Our open source community on Discord

What kind of problems it solves

So you have a working service built in Node.js. It uses (for example) Hapi.js for rendering a couple of REST routes and mongoose as the connector to the database.

Everything works fine, but now you would like to:

  • view all the data in the app,
  • perform custom business actions on objects in the database,
  • bootstrap the tables with the initial data,
  • build custom report pages,
  • allow other team members (not necessary programmers) to see what is going on in the application.

And all these cases can be solved by AdminJS. By adding couple of lines of code you have a running admin interface.

Features

  • CRUD any data in any resource
  • Custom actions
  • Form validation based on schema in your resources
  • Full featured dashboard with widgets
  • Custom resource decorators

Contribute

If you would like work on an AdminJS and develop new features please check out our Contribution Guide

There you can find instructions on how to run AdminJS locally for development.

If you're searching for tasks you can contribute to, we currently accept contributions to issues in our Kanban Board.

Any small or large contribution or any input into discussion is welcome!

License

AdminJS is copyrighted © 2023 rst.software. It is a free software, and may be redistributed under the terms specified in the LICENSE file.

About rst.software

We’re an open, friendly team that helps clients from all over the world to transform their businesses and create astonishing products.

  • We are available for hire.
  • If you want to work for us - check out the career page.

adminjs's People

Contributors

arcanediver avatar ariansobczak-rst avatar arronhunt avatar ashotn avatar barejapawel avatar bartlomiejlechowski avatar cscovinopsh avatar dependabot[bot] avatar destyk avatar dziraf avatar frontkickit avatar jonaszjestem avatar jwasiak avatar krzysztofstudniarek avatar leibowitz avatar matex1024 avatar michlask avatar mohd-akram avatar noisethanks avatar paweljaroszsb avatar przemyslaw-szejna-sb avatar riledupcrow avatar sbross avatar semantic-release-bot avatar simonb407 avatar smacker avatar szymonpoltorakrst avatar tomaszbanasiak avatar tomasztunik avatar wojtek-krysiak avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

adminjs's Issues

pre-bundle custom components in production

Currently, we are bundling users components on every page refresh - this can take a while at some point. That is why we will have to somehow cache the results on production.

implement frontend framework

Right now everything is static - rendered from pug to an html. All dynamic elements are based on jquery. We have to change that to some frontend framework (preferably react)

Acceptance criteria

  • rewrite all views.
  • implement server-side rendering.
  • hydrate on the frontend.
  • allow developers to pass their components in options.

Actions custom validation improvements

Currently there is only one possibility to add custom validation when overwriting actions. If something is not valid we can only return in action object like this:
{ record: { errors: { <fieldName>: <validationMessage> } } }
Also there is no possibility to show Notification for general issue in form, but notification is there, because it is displaying for other build in informations.

Better handle errors in custom components

Business Value
RIght now when user makes a mistake in his custom component (AdminBro.require(...)) all interface goes white. We have to change this behaviour and show errors instead of freazing UI.

Acceptance criteria
Implement ErrorBoundry component

Refused to execute script errors

I've upgraded from 0.6.0 to 0.8.2 and now I'm getting 2 errors that prevent the UI from loading after login (buildAuthenticatedRouter):

Refused to execute script from 'http://localhost:3000/admin/frontend/assets/app.bundle.js' because its MIME type ('application/octet-stream') is not executable, and strict MIME type checking is enabled.

Refused to execute script from 'http://localhost:3000/admin/frontend/assets/components.bundle.js' because its MIME type ('text/html') is not executable, and strict MIME type checking is enabled.

I'm not entirely sure what's causing this, unfortunately.
I'm using admin-bro-expressjs and admin-bro-mongoose as well.

Add default server

Currently AdminBro requires external plugin to be rendered. This is awesome but not very straightforward. The developer should be able to run the server in the easiest way possible.

const adminBro = new AdminBro(options)
await adminBro.start({ port: process.env.PORT || 8080 })

where other options still are possible.

Acceptance criteria

  • we have to choose default framework and use it (bet it would be expressjs)
  • we have to update documentation

Sub-Document Error

Sub-Documents are not visible in the panel instead an empty column is shown.

Role based access control

hi can we add role based access control using admin bro? i need to create mulitple roles like super admin ,admin,user...is it gonna help on it?

Improve the design of login page

Business value

Right now login page is super simple, and since it is usually the first page users will see after visiting AdminBro we have to make it more appealing.

Acceptance criteria

  • add AdminBro logo in the background
  • add information about what user is doing (Logging in to the admin panel).
  • improve other part of the current design (when you fill like it requires that)

Add notices

When something happens in the system (user creates record etc) there should be a notice saying: 'record has been created'

Warning messages and failure to run admin-bro

When I use yarn/npm to install the packages I get the following warning:

warning admin-bro > react-router-dom > react-router > create-react-context > fbjs > [email protected]: core-js@<2.6.5 is no longer maintained. Please, upgrade to core-js@3 or at least to actual version of core-js@2.

Also I am using Node v12.2.0. When I try to follow the example steps I get an error:

import React from 'react'
^^^^^

SyntaxError: Unexpected identifier
at Module._compile (internal/modules/cjs/loader.js:703:23)
at Module._compile (D:\Dev\Projects\NodeJS\testAdminBro2\node_modules\pirates\lib\index.js:99:24)
at Module._extensions..js (internal/modules/cjs/loader.js:770:10)
at Object.newLoader [as .js] (D:\Dev\Projects\NodeJS\testAdminBro2\node_modules\pirates\lib\index.js:104:7)
at Module.load (internal/modules/cjs/loader.js:628:32)
at Function.Module._load (internal/modules/cjs/loader.js:555:12)
at Module.require (internal/modules/cjs/loader.js:666:19)
at require (internal/modules/cjs/helpers.js:16:16)
at Object. (D:\Dev\Projects\NodeJS\testAdminBro2\node_modules\admin-bro\src\admin-bro.js:5:23)
at Module._compile (internal/modules/cjs/loader.js:759:30)

Can this be fixed as admin-bro is not working. I can run everything well without the admin-bro packages.

Admin UI works but can't update records

I can access /admin and see all my resources but when I edit something and and save it, it gives "There were errors in the record object. Check them out" no matter which record I try to update from different collections (some created only with one field of String for example for testing)

this is my admin.js route

const AdminBro = require("admin-bro");
const AdminBroExpress = require("admin-bro-expressjs");

const AdminBroMongoose = require("admin-bro-mongoose");
const mongoose = require("mongoose");

const User = require("../models/user.js");
const Api = require("../models/api.js");
const Query = require("../models/query.js");
const Company = require("../models/company.js");
const Collection = require("../models/collection.js");
const Comment = require("../models/comment.js");

AdminBro.registerAdapter(AdminBroMongoose);


// Passing resources one by one
const adminBro = new AdminBro({
	resources: [Api, User, Query, Company, Collection, Comment],
	rootPath: "/admin"
});

const router = AdminBroExpress.buildRouter(adminBro);

module.exports = router;

Password field

There is no possibility to set input field type as password.

remove gif movie from the repo

it should be placed somewhere else because it occupies a npm package or add npmignore.
Also add engines into a package.json

Change the way how notice information are presented

Business value

Currently all information like: 'successfully created record' etc. are shown in the action header. This place is not very good because it occupies too much space (especially when messages are more than 1). The second problem is with navigation, whenever the user changes the route messages are redrawn.

We have to change that they appear in a compressed way above the header.

Add information of how to contribute

Right now there is no information about how developers can start working on it - how to setup environment etc.

In this task we should:

  • add information to the documentation about the admin-bro-dev repo
  • checkout admin-bro-dev and update its description

Unhandled type: Array

I have a couple of properties in my mongoose model that are Arrays. Right now, I get a lot of warnings: Unhandled type: Array. I'm not sure if I missed something in the configuration or if the way I use arrays are not supported (yet).

Example from the model:
ArrayOfNumbers: [Number]

Refactor filters to an object

After adding relations filters (passed to the adapter and to the view) should not only contain raw data but also populated fields.

Trying to add a sequelize model as a resource, UnhandledPromiseRejectionWarning: TypeError: Cannot convert undefined or null to object.

First of thanks for this well done project,
I got an issue trying to add a Sequelize model as a resource,

The error is:

UnhandledPromiseRejectionWarning: TypeError: Cannot convert undefined or null to object
    at Function.keys (<anonymous>)
    at Resource.properties (webpack:///./node_modules/admin-bro-sequelizejs/src/resource.js?:42:19)
    at ResourceDecorator.decorateProperties (/Users/kiarashws/dev/qukip/backend/node_modules/admin-bro/src/backend/decorators/resource-decorator.js:105:47)
    at new ResourceDecorator (/dev/node_modules/admin-bro/src/backend/decorators/resource-decorator.js:61:28)
    at Resource.assignDecorator (/dev/node_modules/admin-bro/src/backend/adapters/base-resource.js:234:23)
    at resources.map (/dev/node_modules/admin-bro/src/backend/utils/resources-factory.js:102:16)
    at Array.map (<anonymous>)
    at ResourcesFactory._decorateResources (/dev/node_modules/admin-bro/src/backend/utils/resources-factory.js:100:22)
    at ResourcesFactory.buildResources (/dev/node_modules/admin-bro/src/backend/utils/resources-factory.js:35:17)
    at new AdminBro (/dev/node_modules/admin-bro/src/admin-bro.js:111:39)
    at configAdmin (webpack:///./admin/config.js?:52:20)
    at runServer (webpack:///./server.js?:115:69)
    at process._tickCallback (internal/process/next_tick.js:178:7)

I followed example express app

import AdminBro from 'admin-bro'
import AdminBroExpress from 'admin-bro-expressjs'
import AdminBroSequelize from 'admin-bro-sequelizejs'
import sqModels from '../sq-models'

AdminBro.registerAdapter(AdminBroSequelize)

  const adminBro = new AdminBro({
    resources: [
      {
        resource: sqModels.User, options: {}
      }
    ],
    rootPath: '/admin',
    branding: {
      logo: '/logo.png',
      companyName: 'Admin'
    },
    dashboard: DashboardPage
  })

Any help would be appreciated.

Support for custom actions on collections

Is there any planned support for custom actions on collections?

Example proposal:

  • Add a CollectionDecorator base class or add a prop of this.collectionActions to BaseDecorator.
  • Allow developer to define a custom form to show int the action, then the handler function that will be defined in this.collectionActions will get the params from the defined form. also override to Create new should be allowed. f.e:

Form definition for action:

const fields = [
  {
    field: 'Business Name',
    description: 'Business Name.',
    type: 'Enum', // String, Number, Boolean, Enum or CustomHtml
    enums: ['hi', 'bb'],
    isRequired: true,
    customHtmlField: `<input ...>`
  }
...
]

Action Definition:

const addNewBusinessAction = {
      id: 'publish',
      icon: 'fas fa-share',
      label: 'Publish',
      formFields: fields, //from the top example
      action: (request, response, data) => {
        // request.body Will be filled with form data with the fields defined above
        const { method } = request
        if (method === 'GET') {
          return 'Some content or form which you want to place here'
        }
        return 'PUBLISH ACTION WORKS'
      },
    }
this.collectionActions = [addNewBusinessAction]
  • UI: a dropdown on top of the collection filled with the custom actions.

auto-capitalize error

I checked this out on mobile and phone keyboards will auto-capitalize the first letter, which in turn said i had the wrong credentials when i didnt.

Add different options for filtering integers and strings

Business value

Right now number can be filter, only by giving an actual value. So for example there is no way to filter out (as an example) all products with price above some value.

In this task we should add an option to filter by:

  • less than
  • less or equal than
  • more than
  • more or equal than

Add options to property types

Usually, when a user uses a particular type for the property he might want to change its behaviour. For instance:

  • he might want to change the size of the WYSIWYG or available buttons
  • he also might want to change text field to select and add available options

That is why we should allow to pass options along with the type.

Unexpected Identifier in login-template.js

This is the error i get after trying to start the server using "node app.js"
:\Users\Rares\Desktop\UNI\ONE FELL SWOOP new\node_modules\admin-bro\src\frontend\login-template.js:1
(function (exports, require, module, __filename, __dirname) { import React from 'react'
^^^^^

SyntaxError: Unexpected identifier
at new Script (vm.js:84:7)
at createScript (vm.js:264:10)
at Object.runInThisContext (vm.js:312:10)
at Module._compile (internal/modules/cjs/loader.js:684:28)
at Module._compile (C:\Users\Rares\Desktop\UNI\ONE FELL SWOOP new\node_modules\pirates\lib\index.js:99:24)
at Module._extensions..js (internal/modules/cjs/loader.js:732:10)
at Object.newLoader [as .js] (C:\Users\Rares\Desktop\UNI\ONE FELL SWOOP new\node_modules\pirates\lib\index.js:104:7)
at Module.load (internal/modules/cjs/loader.js:620:32)
at tryModuleLoad (internal/modules/cjs/loader.js:560:12)
at Function.Module._load (internal/modules/cjs/loader.js:552:3)
at Module.require (internal/modules/cjs/loader.js:657:17)
at require (internal/modules/cjs/helpers.js:22:18)
at Object. (C:\Users\Rares\Desktop\UNI\ONE FELL SWOOP new\node_modules\admin-bro\src\admin-bro.js:5:23)
at Module._compile (internal/modules/cjs/loader.js:721:30)
at Module._compile (C:\Users\Rares\Desktop\UNI\ONE FELL SWOOP new\node_modules\pirates\lib\index.js:99:24)
at Module._extensions..js (internal/modules/cjs/loader.js:732:10)

This is the code from my app.js file

`var express = require("express"),
app = express(),
bodyParser = require("body-parser"),
mongoose = require("mongoose"),
passport = require("passport"),
LocalStrategy = require("passport-local"),
methodOverride = require("method-override"),
seedDB = require("./seedDB"),
Testimonial = require("./models/Testimonial");

//Route import
var indexRoutes = require("./routes/index");
var testimonialRoutes = require("./routes/testimonials/testimonials");
var adminRoutes = require("./routes/admin");
// var testimonials = require("./routes/testimonials");

//Database connect
mongoose.connect("mongodb://localhost/One-fell-swoop", {
useNewUrlParser: true
});
seedDB();

app.set("view engine", "ejs");
app.use(bodyParser.urlencoded({
extended: true
}));
app.use(express.static(__dirname + "/css"));
app.use(methodOverride("_method"));
app.use(indexRoutes);
app.use("/testimonials", testimonialRoutes);
app.use("/admin", adminRoutes);

//Port setup
var port = process.env.PORT || 3000;
app.listen(port, function () {
console.log("Server is up");
});`

And this is the code from my admin.js file where i connected mongoose to admin-bro

`const AdminBro = require('admin-bro');
const AdminBroExpress = require('admin-bro-expressjs');

const express = require('express');
const app = express();
const mongoose = require('mongoose');

AdminBro.registerAdapter(AdminBroMongoose);

const adminBro = new AdminBro({
databases: [mongoose],
rootPath: '/admin',
})

const router = AdminBroExpress.buildRouter(adminBro)

module.exports = router;`

Could you help me understand what is going on?

Admin Bro doesn't execute post save hooks on defined schemas

I can update records from the admin but the post save hooks on my schema won't execute when updating from admin bros, is there a fix for this?

this is my code so far:

const AdminBroExpress = require("admin-bro-expressjs");

const AdminBroMongoose = require("admin-bro-mongoose");
const mongoose = require("mongoose");

const User = require("../models/user.js");
const Api = require("../models/api.js");
const Query = require("../models/query.js");
const Company = require("../models/company.js");
const Collection = require("../models/collection.js");
const Comment = require("../models/comment.js");

AdminBro.registerAdapter(AdminBroMongoose);

// Passing resources one by one
const adminBro = new AdminBro({
	resources: [
		{
			resource: Api,
			options: {
				listProperties: ["title", "approved", "updatedAt"],
				filterProperties: [
					"title",
					"approved",
					"updatedAt",
					"createdAt",
					"url",
					"totalUpvotes",
					"upvotes",
					"_id"
				]
			}
		},
		Company,
		{
			resource: Collection,
			options: {
				editProperties: ["title", "apis", "description"],
				// listProperties: ["title", "apis", "description"],
				properties: { description: { type: "richtext" } }
			}
		},
		Comment,
		{
			resource: Query,
			options: {
				listProperties: ["query", "createdAt"],
				editProperties: ["query", "approved"]
			}
		}
	],
	rootPath: "/admin",
	loginPath: "/login",
	branding: {
		companyName: "API List"
	}
});

router = AdminBroExpress.buildRouter(adminBro);

module.exports = router;

Improve filter that it doesn't overlay the main container

Business value

Currently, the filter sidebar overlays the content so users, when using a filter, cannot fully see all the data.

In this task, we shall change the design that filter simply shows on the left and causes an entire results table to resize itself.

Acceptance criteria

  • change position for filter from absolute to relative
  • style results table that it appears as container with overflow-x property, but with sticky first column.

Custom actions http method

Maybe I'm missing something but is it possible to specify what http method is used when calling custom action or is limited to GET only?

"SyntaxError: Unexpected identifier" thrown when importing admin-bro

Running with node JS file which contains only:

const AdminBro = require('admin-bro')

results in following exception being thrown:

C:\...\node_modules\admin-bro\src\frontend\login-template.js:1
(function (exports, require, module, __filename, __dirname) { import React from 'react'
                                                                     ^^^^^

SyntaxError: Unexpected identifier
    at new Script (vm.js:80:7)
    at createScript (vm.js:274:10)
    at Object.runInThisContext (vm.js:326:10)
    at Module._compile (internal/modules/cjs/loader.js:664:28)
    at Module._compile (C:\...\node_modules\pirates\lib\index.js:99:24)
    at Module._extensions..js (internal/modules/cjs/loader.js:712:10)
    at Object.newLoader [as .js] (C:\...\node_modules\pirates\lib\index.js:104:7)
    at Module.load (internal/modules/cjs/loader.js:600:32)
    at tryModuleLoad (internal/modules/cjs/loader.js:539:12)
    at Function.Module._load (internal/modules/cjs/loader.js:531:3)

Looks like AdminBro front-end code is not transpiled by Babel.
I hope there's nothing wrong with my setup.

λ node --version
v10.15.3

Pozdrawiam.

Allow override of CSS theme values

Looking through the docs, it looks like we're very limited on customizations when it comes to brand, specifically only being able to override logo and companyName. Since all the branding colors are being pulled from src/frontend/styles/variables.js it stands to reason it should be simple to allow for an override for these default variables.

Filters 500

Assuming field

price: {
  value: Number,
  currency: String
}

and trying to use filters on price.value admin response is 500

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.