0.7.0 • Published 5 months ago

evolutility-ui-react v0.7.0

Weekly downloads
13
License
AGPL-3.0
Repository
github
Last release
5 months ago

Evolutility-UI-React · GitHub license npm version

Evolutility-UI-React is a set of model-driven views to Browse, Edit, List, Cards, Charts, Stats, Overview, and Activity.

With it you can easily build CRUD applications by writing models rather than code. It uses Hasura GraphQL backend. No hand-coding is necessary!

Check out the live demos.

Edit

Table of Contents

  1. Installation
  2. Configuration
  3. Views for One, Many records, and for Comfort
  4. Models
  5. Backend
  6. License

Installation

Download or clone from GitHub.

# To get the latest stable version, use git from the command line.
git clone https://github.com/evoluteur/evolutility-ui-react

or use the npm package:

# To get the latest stable version, use npm from the command line.
npm install evolutility-ui-react

In the Evolutility-UI-React directory, use the command line to type the following:

# Install dependencies
npm install

# Run the node.js server
npm start

In a web browser, go to the url [http://localhost:3000/ the REST endpoints, you also need to install and run Evolutility-Server-Node which provides the matching REST endpoints based on the same metadata.

Configuration

Configurations options are specified in the file /src/config.js. They apply to all apps (app specific options are specified in models).

OptionDescriptionExample
apiPathPath to GraphQL API."https://myapp.hasura.app/v1/graphql"
adminSecretToken for Hasura.
useCacheEnable/disable data caching.true
cacheDurationCache duration in seconds.120 (for 2 minutes)
filesUrlPath to upload files to."/pix/"
pageSizePage size in pagination.50
withActivityTracks and shows records activity (last visited and most visited). Currently implemented w/ the browser's localStorage, it will be moved to the server later.true
queryModelsGet models from JSON files or from the database through the API. (not implemented yet)
withTimestampTracks and shows timestamp for creation date and last update for every record. The DB tables need timestamp columns "updated_at" and "created_at" for the feature to work. (partial implementation)true

Views

For any object, a single model defines UI elements across views in a simple declarative way.

Evolutility-UI-React provides different types of view:

Evolutility uses GraphQL with Hasura.

Notes: Views for actions (search, filter, export) will come later.

Views for One object

Browse - Edit

Browse

Shows all fields for viewing (read only). Fields are grouped in panels.

Browse

Code: /src/components/views/one/Browse/Browse.jsx

Route: "/{entity}/browse/{id}"

Edit

This view shows all fields for edition to create or update records. It automatically performs validation based on the model. Fields are grouped in panels and tabs.

Edit

Code: /src/components/views/one/Edit/Edit.jsx

Route: "/{entity}/edit/{id}"

Views for Many objects

List - Cards - Charts - Stats

List

Gives a tabular view of a collection.

List

Code: /src/components/views/many/List/List.jsx

Route: "/{entity}/list"

Cards

Shows records side by side as cards.

Cards

Code: /src/components/views/many/Cards/Cards.jsx

Route: "/{entity}/cards"

Charts

Draws charts about the collection. Currently bars and pie charts are implemented, a list with count and percentages is also available. Only provided for fields of types like boolean, lov, integer, decimal, date... (not text or textmultilines).

Charts

Code: /src/components/views/analytics/Charts/Charts.jsx

Route: "/{entity}/charts"

Note: The "Charts" view is currently only implemented for REST, not available with GraphQL yet.

Stats

Display last update, number of updates in the last week, and for numeric fields the min, max, count, average.

Stats

Code: /src/components/views/analytics/Stats/Stats.jsx

Route: "/{entity}/stats"

"Comfort" views

Display a summary of the object and the latest activity on it.

Overview

Display a summary of the object and the latest activity on it.

Overview

Code: /src/components/views/comfort/Overview/Overview.jsx

Route: "/{entity}/"

Activity

Show list of "last visited" and "most visited" records for the object (stored in the browser's localStorage).

Activity

Code: /src/components/views/comfort/Activity/Activity.jsx

Route: "/{entity}/activity"

Models

Each model describe an object and its list of fields. A single model is used for all views (Browse, Edit, List, Cards...).

For any object, all UI views (List, Cards, Edit, Charts...) share the same model. All Fields are present in the Edit and Browse views. Fields can be flagged with "inMany" to be included in the List and Cards views, or "noCharts" and "noStats" to be excluded from the Charts or Stats views.

Object

PropertyMeaning
idUnique key to identify the entity (used in route and as API parameter).
qidEntity ID used in GraphQL (may be different from id in route).
iconIcon file name for the entity (example: "cube.gif").
nameObject name (singular).
namePluralObject name (plural).
titleApplication name.
fieldsArray of Fields.
groupsArray of Groups. If not provided a single group will be used.
collectionsArray of Collections.
titleFieldId of the field which value is used as record title. titleField can also be a function.
titleFunctionFunction to calculate the record title based it's data. Example: titleFunction = (data, model) => data.firstname + " " + data.lastname;XX
defaultViewOneTo have List and Cards link to Edit instead of Browse, set defaultViewOne="edit".

Field

Objects have fields.

PropertyMeaning
idUnique key for the field (can be the same as column but doesn't have to be).
typeField type to show in the UI. Possible field types: boolean (yes/no)datedecimaldocumentemailimageintegerjsonlov (list of values)moneytexttextmultilinetimeurl
labelField description (displayed with an asterisk for required fields).
labelShortOptional shorter version of the labels (used in List and Cards views).
requiredDetermines if the field is required for saving.
readOnlyIf set to true, the field value cannot be changed.
defaultValueDefault field value for new records.
formatField format (using moment for date values and numeral for numeric values).
max, minMaximum/Minimum value allowed (only applies to numeric fields).
maxLength, minLengthMaximum/Minimum length allowed (only applies to text fields).
regExpRegular expression used to validate the field value.
listList of items in the dropdown as an array of id-text objects (only for fields of "lov" type). If ommited, the list will be retrieved in the first query by id on that object.
lovIconSet to True to include icon with LOV items(only for fields of "lov" type).
objectModel id for the object to link to (only for fields of "lov" type).
chartObjectOptional overide for object name in charts (only for "lov" fields).
aggregateOptional overide for aggregation name in charts (only for "lov" fields).
inManyDetermines if the field is present (by default) in lists of records.
inSearchDetermine if the field is used in text searches.
heightFor fields of type "textmultiline", number of lines used in the field (in Browse and Edit views).
widthField width in Browse and Edit views (in percent of parent width).
helpOptional help on the field.
chartTypeDefault charts type used for the field ("Bars", "Pie", or "Table"). "Bars" is used if not specified.
noChartsExclude field from charts (only applies to fields of type integer, decimal, money, boolean, list of values which are "chartable").
noStatsExclude field from Stats.

Field Group

Field Groups are used to separate Fields into panels in the Edit and Browse views.

PropertyMeaning
idUnique key for the group. It is optional.
typeType of fields group. Only "panel" is currently supported (tab and other types of groups will be added later).
labelGroup title displayed in the group header.
fieldsArray of field ids.
widthWidth (in % of the container total width).
helpOptional help tooltip text.
headerOptional text displayed at the top of the group (just below the group title).
footerOptional text displayed below the group.

Notes:

  • Field Groups are optional. By default a single group holds all fields.
  • Field Groups are positioned based on their "width" property the same way than fields are positioned inside groups.

Collection

Multiple details tables can be specified with "collections".

PropertyMeaning
idUnique key for the collection.
titleCollection title.
objectModel.id for the Object to link to.
fieldsArray of fields (objects or ids). Fields in collections can be field objects or just ids of fields in the collection's object.
readOnlySpecify if the collection is readOnly.
hideIfEmptyHide Collection when it is empty in Edit view (always hidden when empty in Browse view).
helpOptional help tooltip text.
headerText to be displayed before the collection.
footerText to be displayed below the collection.

Sample model using collections: Wine Cellar.

Sample model

The following example is the model for a simple graphic novels inventory app.

{
    id: "comics",
    title: "Graphic Novels",
    name: "graphic novel serie",
    namePlural: "graphic novel series",
    icon: "comics.png",
    titleField: "title",
    fields:[
      {
          id: "title", type: "text",
          label: "Title",
          required: true, maxLength: 255,
          width: 100, inMany: true,
      },
      {
          id: "authors", type: "text",
          label: "Authors",
          inMany: true, width: 62,

      },
      {
          id: "genre", type: "lov",
          label: "Genre",
          width: 38, inMany: true,
          list: [
            {id: 1, text: "Adventure"},
            {id: 2, text: "Fairy tale"},
            {id: 3, text: "Erotic"},
            {id: 4, text: "Fantastic"},
            {id: 5, text: "Heroic Fantasy"},
            {id: 6, text: "Historic"},
            {id: 7, text: "Humor"},
            {id: 8, text: "One of a kind"},
            {id: 9, text: "Youth"},
            {id: 10, text: "Thriller"},
            {id: 11, text: "Science-fiction"},
            {id: 12, text: "Super Heros"},
            {id: 13, text: "Western"}
          ]
      },
      {
          id: "serie_nb", type: "integer",
          label: "Albums", noCharts: true,
          width: 15, inMany: false
      },
      {
          id: "have_nb", type: "integer",
          label: "Owned",
          width: 15, inMany: false, noCharts: true
      },
      {
          id: "have", type: "text",
          label: "Have",
          width: 15, inMany: false
      },
      {
          id: "language", type: "lov",
          label: "Language",
          width: 17, inMany: true,
          lovIcon: true,
          list: [
            {id: 2, text: 'French', icon:'comics/flags/fr.png'},
            {id: 1, text: 'American', icon:'comics/flags/us.png'}
          ]
      },
      {
          id: "complete", type: "boolean",
          label: "Complete",
          width: 19, inMany: false
      },
      {
          id: "finished", type: "boolean",
          label: "Finished",
          width: 19, inMany: false
      },
      {
          id: "pix", type: "image",
          label: "Cover",
          width: 30, inMany: true
      },
      {
          id: "notes", type: "textmultiline",
          label: "Notes",
          width: 70, height: 7, maxLength: 5000,
          inMany: false
      }
  ],

  groups: [
      {
        id:"serie", type: "panel", label: "Serie", width: 70,
        fields: ["title", "authors", "genre",
              "serie_nb", "have_nb", "have",
              "language", "complete", "finished", "notes"
        ]
      },
      {
        id:"pix", type: "panel", label: "Cover", width: 30,
        fields: ["pix"]
      }
  ]
}

More sample models: To-do list, Address book, Restaurants list, Wine cellar.

Backend

You will need to setup the GraphQL backend on Hasura with the Evolutility demo database.

License

Copyright (c) 2023 Olivier Giulieri.

Evolutility-UI-React is released under the AGPL-3.0 license.

To suggest a feature or report a bug: https://github.com/evoluteur/evolutility-ui-react/issues