{"id":18647711,"url":"https://github.com/artcom/acms-ui","last_synced_at":"2025-11-05T07:30:30.589Z","repository":{"id":38242584,"uuid":"348349434","full_name":"artcom/acms-ui","owner":"artcom","description":"A web ui for https://github.com/artcom/acms-compose","archived":false,"fork":false,"pushed_at":"2022-11-23T10:50:21.000Z","size":4420,"stargazers_count":3,"open_issues_count":3,"forks_count":0,"subscribers_count":10,"default_branch":"master","last_synced_at":"2024-12-27T12:23:13.194Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/artcom.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2021-03-16T13:01:54.000Z","updated_at":"2022-04-05T10:01:57.000Z","dependencies_parsed_at":"2023-01-21T00:46:51.570Z","dependency_job_id":null,"html_url":"https://github.com/artcom/acms-ui","commit_stats":null,"previous_names":[],"tags_count":54,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/artcom%2Facms-ui","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/artcom%2Facms-ui/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/artcom%2Facms-ui/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/artcom%2Facms-ui/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/artcom","download_url":"https://codeload.github.com/artcom/acms-ui/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":239449684,"owners_count":19640565,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-11-07T06:27:37.209Z","updated_at":"2025-11-05T07:30:30.544Z","avatar_url":"https://github.com/artcom.png","language":"JavaScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# ACMS UI\n\nA webapp UI which allows browsing/editing the json content served by the [`acms-api`](https://github.com/artcom/acms-api) service.\n\n## Documentation\n\n### Config file\n\nCopy `config.json.template` into `/public/config.json` and change values accordingly. `config.json`is served by webpack dev server or provided in a production environment.\n\n`acmsAssetsUri`: Fully qualified URI to a WebDav enabled server, [`acms-assets`](https://github.com/artcom/acms-assets).  \n`acmsApiUri`: Fully qualified URI to the [`acms-api`](https://github.com/artcom/acms-api) service.  \n`acmsConfigPath`: Relative directory path inside the [`acms-config`](https://github.com/artcom/acms-config) to the ACMS UI configuration JSON file (usually `acmsConfig`, see below).\n\n### ACMS UI Configuration file\n\nCreate a configuration file (e.g. `acmsConfig.json`) inside the [`acms-config`](https://github.com/artcom/acms-config) repo:\n\n```jsonc\n{\n  \"title\": \"ACMS\",                           // title shown in the header, default: null\n  \"logoImageUri\": \"https://assets/logo.jpg\", // logo shown in the header, default: null\n  \"contentPath\": \"content\",                  // root directory containing the content data, default: \"content\"\n  \"templatesPath\": \"templates\",              // root directory containing the (nested) template files, default: \"templates\"\n  \"childrenLabel\": \"Children\",               // label shown above the children, default: \"Children\"\n  \"fieldsLabel\": \"Fields\",                   // label shown above the fields, default: \"Fields\"\n  \"saveLabel\": \"Save\",                       // label of the save button, default: \"Save\"\n  \"textDirection\": \"ltr\",                    // optional text direction for non localized text, default: \"ltr\", see https://developer.mozilla.org/de/docs/Web/CSS/\n  \"languages\": [                             // optional language configuration\n    {\n      \"id\": \"en\",                            // unique language id (e.g. \"en\"), see language subtag registry: https://www.iana.org/assignments/language-subtag-registry/language-subtag-registry\n      \"name\": \"English\",                     // language name, default: id\n      \"textDirection\": \"ltr\"                 // direction of the text, default: \"ltr\", see https://developer.mozilla.org/de/docs/Web/CSS/direction\n    }\n  ],\n  \"users\": [                                 // list of users, default: shown here\n    {\n      \"id\": \"admin\",                         // unique user id\n      \"name\": \"Admin\",                       // user name, default: id\n      \"permissions\": {                       // permission settings, default: shown here\n        \"include\": [\n          \"**\"                               // list of glob patterns defining which fields to include, default: shown here\n        ],\n        \"exclude\": []                        // list of glob patterns defining which fields to exclude, default: shown here\n      }\n    }\n  ],\n   \"customTypes\": {                          // a collection of custom types with preconfigured properties, the custom type id can be used in templates\n    \"myCustomString\": {\n      \"type\": \"string\",\n      \"maxLength\": 123,\n      \"multiline\": true\n    }\n  }\n}\n```\n\n### User Management\n\nThe user management is **not safe** and only meant to provide convenience views on the content. Its possible to filter fields and children by path (see `users/permissions`) to filter *internal* data.\n\n### Templates\n\nTemplate files specify the structure of the content data while the actual values are located in the `content` directory. Every template entity can have children which themself are structured by a template. Nested templates within the `templates` directory are referenced via local path. E.g.:\n\n```jsonc\n/templates/template1.json            // =\u003e `template1`\n/templates/template2.json            // =\u003e `template2`\n/templates/template3/index.json      // =\u003e `template3`\n/templates/template3/template4.json  // =\u003e `template3/template4`\n\n```\n\n#### Example\n```jsonc\n{\n  \"fields\": [                                                     // optional list of fields\n        {\n            \"id\": \"title\",                                        // unique id within the whole template\n            \"name\": \"Main Title\",                                 // optional display name shown in the ACMS UI, default startCase(id)\n            \"type\": \"string\",                                     // field type see below\n            \"maxLength\": 8,                                       // optional type specific properties\n            \"localization\": [\"en\", \"ar\"],                         // optional localization\n            \"preview\": \"https://previewer.de/?fieldValue=${value}\"// optional preview link\n        },\n        {\n            \"id\": \"enabled\",\n            \"name\": \"Page Enabled\",\n            \"type\": \"boolean\"\n        },\n        {\n            \"id\": \"numLoops\",\n            \"name\": \"Number of Loops performed\",\n            \"type\": \"number\",\n            \"integer\": true\n        }\n  ],\n  \"fixedChildren\": [                     // optional list of fixed/named children\n    {\n      \"id\": \"frontScreen\",               // unique id within the whole template\n      \"name\": \"Front of the Entry\",      // optional display name shown in the ACMS UI, default startCase(id)\n      \"template\": \"location\"             // template id/path\n    },\n    {\n      \"id\": \"backScreen\",\n      \"name\": \"Back of the Entry\",\n      \"template\": \"location\"\n    }\n  ],\n  \"children\": [                          // optional list of of allowed templates for the children \n    \"template1\",\n    \"template2\"\n  ],\n  \"enabledField\": \"enabled\",             // optional field reference defining if the instance is shown enabled or disabled in its parent children list\n  \"subtitleField\": \"title\"               // optional field reference defining a subtitle shown in its parent children list\n}\n```\n\n### Field Types\n\nThe following field types are supported:\n\n#### `audio`, `file`, `video`\nAn uploadable asset which is stored on the asset server with a unique (hashed) filename. \n\nExample:\n```jsonc\n{\n    \"id\": \"bachelorThesis\",\n    \"name\": \"Bachelor Thesis\",\n    \"type\": \"file\",\n    \"allowedMimeTypes\": [\"application/pdf\"]  // optional list of allowed mime types\n}\n```\n\n#### `image`\nAn uploadable asset which is stored on the asset server with a unique (hashed) filename\n* `allowedMimeTypes`: optional list of allowed mime types, default: `[\"image/*\"]`\n* `width`: optional width of the image\n* `minWidth`: optional minimum width of the image\n* `maxWidth`: optional maximum width of the image\n* `height`: optional height of the image\n* `minHeight`: optional minimum height of the image\n* `maxHeight`: optional maximum height of the image\n* `aspectRatio`: optional aspect ratio of the image\n\nExample:\t\n```jsonc\n{\n    \"id\": \"coverImage\",\n    \"name\": \"Front Cover Image\",\n    \"type\": \"image\",\n    \"allowedMimeTypes\" : [\"image/jpeg\", \"image/png\"],\n    \"width\": 1920,\n    \"minWidth\": 800,\n    \"maxWidth\": 2200,\n    \"height\": 1080,\n    \"minHeight\": 800,\n    \"maxHeight\": 1600,\n    \"aspectRatio\": \"16:9\"\n}\n```\n\n#### `string`, `markdown`\nA string type with the following otional properties:\n  * `multiline`: Defines wether the string can have multiple lines, default: `false`\n  * `maxLength`: Defines the maximum number of characters, default: `Infinity`\n\nExample:\n```jsonc\n{\n    \"id\": \"label\",\n    \"name\": \"Start Label\",\n    \"type\": \"string\",\n    \"maxLength\": 32,\n    \"multiline\": true\n}\n```\n\n#### `number`\nA number type with the following optional properties:\n* `min`: The minimum value, default `-Infinity`\n* `max`: The maximum value, default `Infinity`\n* `integer`: Defines wether the number is an integer, default: `false`\n\nExample:\n```jsonc\n{\n    \"id\": \"numLoops\",\n    \"name\": \"Number of loops\",\n    \"type\": \"number\",\n    \"min\": 0,\n    \"max\": 100\n}\n```\n\n#### `geolocation`\nA geolocation type with values for `lat` (Latitude) and `long` (Longitude).\n* `min`: The minimum value, default `lat: -90`, `long: -180`\n* `max`: The maximum value, default `lat: 90`, `long: 180`\n\nExample:\n```jsonc\n{\n  \"id\": \"location\",\n  \"type\": \"geolocation\"\n}\n```\n\n#### `boolean`\nA boolean either being `true` or `false`.\n\nExample:\n```jsonc\n{\n    \"id\": \"active\",\n    \"name\": \"Active State\",\n    \"type\": \"boolean\"\n}\n```\n\n### `enum`\nA list of selectable values.\n\nExample:\n```jsonc\n{\n    \"id\": \"myEnum\",\n    \"name\": \"My Enum Type\",\n    \"type\": \"enum\",\n    \"values\": [\n        {\n            \"value\": \"value1\",\n            \"name\": \"First Value\"\n        },\n        {\n            \"value\": [2, 3, 4],\n            \"name\": \"Second Value\"\n        },\n        {\n            \"value\": {\n              \"thirdValue\": \"thirdValue\"\n            },\n            \"name\": \"Third Value\"\n        },\n        {\n          \"value\": true,\n          \"name\": \"Fourth Value\"\n        },\n        {\n          \"value\": \"no name\"\n        }\n    ]\n}\n```\nNote: As shown in the last entry of the `values` array, the `name` property is not required. The displayed name will then be generated based on the type of `value`.\n\n\n### Field Condition\n\nIt is possible to hide/show fields in the CMS frontend depending on sibling fields value. A typical case is an `enum` field which specifies a layout type (e.g. `videoCover`/`imageCover`). Based on the field value you want to either show an `image` or `video` field. This can be achieved with the following `GET`and `EQUALS` operators:\n\n```jsonc\n{\n    \"id\": \"layoutType\",\n    \"type\": \"enum\",\n    \"values\": [\"videoCover\", \"imageCover\"]\n},\n{\n    \"id\": \"coverVideo\",\n    \"type\": \"video\",\n    \"condition\": [ \"EQUALS\", [ \"GET\", \"layoutType\" ], \"videoCover\" ]\n},\n{\n    \"id\": \"coverImage\",\n    \"type\": \"image\",\n    \"condition\": [ \"EQUALS\", [ \"GET\", \"layoutType\" ], \"imageCover\" ]\n\n}\n```\n\nIf several values should be considered you can use the `IN` and `LIST` operator:\n```jsonc\n{\n    \"id\": \"coverVideo\",\n    \"type\": \"string\",\n    \"condition\": [ \"IN\", [ \"GET\", \"layoutType\" ], [ \"LIST\", \"videoCover\", \"imageCover\" ] ]\n}\n```\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fartcom%2Facms-ui","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fartcom%2Facms-ui","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fartcom%2Facms-ui/lists"}