cleanup and document structure handling
This commit is contained in:
parent
82c98eec15
commit
c057271e37
|
@ -1,3 +1,40 @@
|
||||||
|
# structure
|
||||||
|
# below config we define the structure to be displayed
|
||||||
|
# basically there are 2 object types:
|
||||||
|
# children - a list of cfg objects that define the inputs to be shown
|
||||||
|
# if the parent is selected
|
||||||
|
# parameters:
|
||||||
|
# key: unique key - defines the name(part) in the cfg
|
||||||
|
# if not set a potential "value" is taken
|
||||||
|
# null (empty) is a valid key
|
||||||
|
# label: title to be shown, if unset key will be used
|
||||||
|
# resorce: a resource that is used by the value children
|
||||||
|
# simple string use as is
|
||||||
|
# string + ':' - add value to the resource
|
||||||
|
# type: if empty or 'frame' only the children are considered
|
||||||
|
# children: only for type empty or 'frame' - list of child objects
|
||||||
|
# target: how the selected child value should be stored:
|
||||||
|
# environment - set the environment to the child value
|
||||||
|
# define - add -D<childValue> to the flags
|
||||||
|
# define:name - add -D<name>=<childValue> to the flags
|
||||||
|
# values - a list of value objects for a particular config
|
||||||
|
# if the object is just a string it is converted to an object
|
||||||
|
# with value being set to the string
|
||||||
|
# parameters:
|
||||||
|
# key: unique key, defines the name(part) and the value store in cfg
|
||||||
|
# for the parent
|
||||||
|
# if not set, value is used
|
||||||
|
# null (empty) is a valid key
|
||||||
|
# value: the value (mandatory)
|
||||||
|
# if null the value will be set to undefined and ignored
|
||||||
|
# label: text to be shown
|
||||||
|
# if not set value will be used
|
||||||
|
# description,url
|
||||||
|
# resource: for parent-target environment:
|
||||||
|
# an object with allowed resource counts
|
||||||
|
# for other values: the resource to be counted
|
||||||
|
#
|
||||||
|
#
|
||||||
types:
|
types:
|
||||||
- &m5base
|
- &m5base
|
||||||
type: select
|
type: select
|
||||||
|
@ -71,13 +108,13 @@ types:
|
||||||
key: m5groove
|
key: m5groove
|
||||||
label: 'M5 groove type'
|
label: 'M5 groove type'
|
||||||
values:
|
values:
|
||||||
- label: 'CAN'
|
- key: 'CAN'
|
||||||
children:
|
children:
|
||||||
- *m5groovecan
|
- *m5groovecan
|
||||||
- label: 'I2C'
|
- key: 'I2C'
|
||||||
children:
|
children:
|
||||||
- *m5groovei2c
|
- *m5groovei2c
|
||||||
- label: 'Serial'
|
- key: 'Serial'
|
||||||
children:
|
children:
|
||||||
- *m5grooveserial
|
- *m5grooveserial
|
||||||
- &gpiopin
|
- &gpiopin
|
||||||
|
@ -95,10 +132,10 @@ types:
|
||||||
key: serial1
|
key: serial1
|
||||||
children:
|
children:
|
||||||
- <<: *gpiopin
|
- <<: *gpiopin
|
||||||
label: RX
|
key: RX
|
||||||
target: "define:GWSERIAL_RX"
|
target: "define:GWSERIAL_RX"
|
||||||
- <<: *gpiopin
|
- <<: *gpiopin
|
||||||
label: TX
|
key: TX
|
||||||
target: "define:GWSERIAL_TX"
|
target: "define:GWSERIAL_TX"
|
||||||
|
|
||||||
resources:
|
resources:
|
||||||
|
|
|
@ -113,10 +113,7 @@
|
||||||
margin-right: 0.5em;
|
margin-right: 0.5em;
|
||||||
z-index: unset;
|
z-index: unset;
|
||||||
}
|
}
|
||||||
.configui .selector {
|
|
||||||
padding-bottom: 0.5em;
|
|
||||||
border-bottom: 1px solid grey;
|
|
||||||
}
|
|
||||||
.configui .selector .title {
|
.configui .selector .title {
|
||||||
font-weight: bold;
|
font-weight: bold;
|
||||||
}
|
}
|
||||||
|
@ -133,10 +130,15 @@
|
||||||
padding-bottom: 0;
|
padding-bottom: 0;
|
||||||
border-bottom: unset;
|
border-bottom: unset;
|
||||||
}
|
}
|
||||||
.configui .selector.tdropdown {
|
.configui .childFrame {
|
||||||
padding-bottom: unset;
|
border-top: 1px solid grey;
|
||||||
border-bottom: unset;
|
margin-top: 0.3em;
|
||||||
}
|
}
|
||||||
|
.configui .tframe>.childFrame {
|
||||||
|
border-top: unset;
|
||||||
|
margin-top: 0.3em;
|
||||||
|
}
|
||||||
|
|
||||||
.configui .selector.tdropdown {
|
.configui .selector.tdropdown {
|
||||||
display: flex;
|
display: flex;
|
||||||
flex-direction: row;
|
flex-direction: row;
|
||||||
|
|
|
@ -243,16 +243,44 @@ class PipelineInfo{
|
||||||
let parsed=yamlLoad(config);
|
let parsed=yamlLoad(config);
|
||||||
return parsed;
|
return parsed;
|
||||||
}
|
}
|
||||||
const getVal=(cfg,keys)=>{
|
|
||||||
for (let i in keys){
|
|
||||||
let k=cfg[keys[i]];
|
|
||||||
if (k !== undefined) return k;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
const KEY_NAMES=['key','value','label'];
|
|
||||||
const LABEL_NAMES=['label','value'];
|
|
||||||
const PATH_ATTR='data-path';
|
const PATH_ATTR='data-path';
|
||||||
const SEPARATOR=':';
|
const SEPARATOR=':';
|
||||||
|
const expandObject=(obj,parent)=>{
|
||||||
|
if (typeof(obj) !== 'object'){
|
||||||
|
obj={value:obj}
|
||||||
|
}
|
||||||
|
let rt=Object.assign({},obj);
|
||||||
|
if (rt.value === undefined && rt.key !== undefined) rt.value=rt.key;
|
||||||
|
if (rt.key === undefined) rt.key=rt.value;
|
||||||
|
if (rt.value === null) rt.value=undefined;
|
||||||
|
if (rt.label === undefined){
|
||||||
|
if (rt.value !== undefined) rt.label=rt.value;
|
||||||
|
else rt.label=rt.key;
|
||||||
|
}
|
||||||
|
if (rt.resource === undefined && typeof(parent) === 'object'){
|
||||||
|
if (parent.resource !== undefined){
|
||||||
|
if (parent.resource.match(/:$/)){
|
||||||
|
if(rt.value !== undefined && rt.value !== null){
|
||||||
|
rt.resource=parent.resource+rt.value;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else{
|
||||||
|
rt.resource=parent.resource;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (rt.target === undefined && typeof(parent) === 'object' && parent.target !== undefined){
|
||||||
|
rt.target=parent.target;
|
||||||
|
}
|
||||||
|
return rt;
|
||||||
|
}
|
||||||
|
const expandList=(lst,parent)=>{
|
||||||
|
let rt=[];
|
||||||
|
if (! lst) return rt;
|
||||||
|
lst.forEach((e)=>rt.push(expandObject(e,parent)));
|
||||||
|
return rt;
|
||||||
|
}
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* @param {build a selector} parent
|
* @param {build a selector} parent
|
||||||
|
@ -262,27 +290,28 @@ class PipelineInfo{
|
||||||
* @param {*} callback will be called with: children,key,value,initial
|
* @param {*} callback will be called with: children,key,value,initial
|
||||||
* @returns
|
* @returns
|
||||||
*/
|
*/
|
||||||
const buildSelector=(parent,config,name,current,callback)=>{
|
const buildSelector=(parent,cfgBase,name,current,callback)=>{
|
||||||
|
let config=expandObject(cfgBase);
|
||||||
let rep=new RegExp("[^"+SEPARATOR+"]*","g");
|
let rep=new RegExp("[^"+SEPARATOR+"]*","g");
|
||||||
let level=name.replace(rep,'');
|
let level=name.replace(rep,'');
|
||||||
let frame=addEl('div','selector level'+level.length+' t'+config.type,parent);
|
let frame=addEl('div','selector level'+level.length+' t'+config.type,parent);
|
||||||
frame.setAttribute(PATH_ATTR,name);
|
frame.setAttribute(PATH_ATTR,name);
|
||||||
let title=addEl('div','title t'+config.type,frame,config.label);
|
let title=addEl('div','title t'+config.type,frame,config.label);
|
||||||
if (config.type === 'frame'){
|
let initialConfig=undefined
|
||||||
callback(config.children,true,true,undefined,true);
|
if (config.type === 'frame' || config.type === undefined){
|
||||||
|
initialConfig=config;
|
||||||
}
|
}
|
||||||
|
let expandedValues=expandList(config.values,config);
|
||||||
if (config.type === 'select') {
|
if (config.type === 'select') {
|
||||||
if (!config.values) return;
|
for (let idx=0;idx<expandedValues.length;idx++){
|
||||||
config.values.forEach((v) => {
|
let v=expandedValues[idx];
|
||||||
|
if (v.key === undefined) continue;
|
||||||
let ef = addEl('div', 'radioFrame', frame);
|
let ef = addEl('div', 'radioFrame', frame);
|
||||||
addEl('div', 'label', ef, getVal(v, LABEL_NAMES));
|
addEl('div', 'label', ef, v.label);
|
||||||
let re = addEl('input', 'radioCi', ef);
|
let re = addEl('input', 'radioCi', ef);
|
||||||
let val = v.value;
|
|
||||||
let key=getVal(v,KEY_NAMES);
|
|
||||||
if (val === undefined) val=key;
|
|
||||||
re.setAttribute('type', 'radio');
|
re.setAttribute('type', 'radio');
|
||||||
re.setAttribute('name', name);
|
re.setAttribute('name', name);
|
||||||
re.addEventListener('change', (ev) => callback(v.children,key,val,v.resource,false));
|
re.addEventListener('change', (ev) => callback(v,false));
|
||||||
if (v.description){
|
if (v.description){
|
||||||
if(v.url) {
|
if(v.url) {
|
||||||
let lnk = addEl('a', 'radioDescription', ef, v.description);
|
let lnk = addEl('a', 'radioDescription', ef, v.description);
|
||||||
|
@ -293,53 +322,35 @@ class PipelineInfo{
|
||||||
let de=addEl('span','radioDescription',ef,v.description);
|
let de=addEl('span','radioDescription',ef,v.description);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (key == current) {
|
if (v.key == current) {
|
||||||
re.setAttribute('checked','checked');
|
re.setAttribute('checked','checked');
|
||||||
callback(v.children,key,val,v.resource,true);
|
initialConfig=v;
|
||||||
}
|
}
|
||||||
});
|
};
|
||||||
}
|
}
|
||||||
if (config.type === 'dropdown'){
|
if (config.type === 'dropdown'){
|
||||||
if (!config.values) return;
|
|
||||||
const valForIdx=(idx)=>{
|
|
||||||
let v=config.values[idx];
|
|
||||||
if (typeof(v) !== 'object'){
|
|
||||||
v={label:v,value:v};
|
|
||||||
}
|
|
||||||
if (v.value === null) v.value=undefined;
|
|
||||||
if (v.key === null) v.key=undefined;
|
|
||||||
return v;
|
|
||||||
};
|
|
||||||
const resourceForVal=(v)=>{
|
|
||||||
if (v === undefined) return undefined;
|
|
||||||
let key=getVal(v,KEY_NAMES);
|
|
||||||
if (key === undefined) return key;
|
|
||||||
let resource=v.resource;
|
|
||||||
if (! resource && config.resource && config.resource.match(/:$/)){
|
|
||||||
resource=config.resource+key;
|
|
||||||
}
|
|
||||||
return resource;
|
|
||||||
};
|
|
||||||
let sel=addEl('select','t'+config.type,frame);
|
let sel=addEl('select','t'+config.type,frame);
|
||||||
for (let idx=0;idx<config.values.length;idx++){
|
for (let idx=0;idx<expandedValues.length;idx++){
|
||||||
let v=valForIdx(idx);
|
let v=expandedValues[idx];
|
||||||
|
if (v.key === undefined) continue;
|
||||||
let opt=addEl('option','',sel,v.label);
|
let opt=addEl('option','',sel,v.label);
|
||||||
let key=getVal(v,KEY_NAMES);
|
|
||||||
if (key === null) key=undefined;
|
|
||||||
opt.setAttribute('value',idx);
|
opt.setAttribute('value',idx);
|
||||||
if (key == current){
|
if (v.key == current){
|
||||||
opt.setAttribute('selected',true);
|
opt.setAttribute('selected',true);
|
||||||
callback(undefined,key,key,resourceForVal(v),true);
|
initialConfig=v;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
sel.addEventListener('change',(ev)=>{
|
sel.addEventListener('change',(ev)=>{
|
||||||
let resource;
|
let v=expandedValues[ev.target.value];
|
||||||
let v=valForIdx(ev.target.value);
|
|
||||||
if (! v) return;
|
if (! v) return;
|
||||||
callback(undefined,getVal(v,KEY_NAMES), v.value,resourceForVal(v),false);
|
callback(v,false);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
return frame;
|
let childFrame=addEl('div','childFrame',frame);
|
||||||
|
if (initialConfig !== undefined){
|
||||||
|
callback(initialConfig,true,childFrame);
|
||||||
|
}
|
||||||
|
return childFrame;
|
||||||
}
|
}
|
||||||
const removeSelectors=(prefix,removeValues)=>{
|
const removeSelectors=(prefix,removeValues)=>{
|
||||||
forEachEl('.selectorFrame',(el)=>{
|
forEachEl('.selectorFrame',(el)=>{
|
||||||
|
@ -363,20 +374,24 @@ class PipelineInfo{
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
const buildSelectors=(prefix,configList,initial)=>{
|
const buildSelectors=(prefix,configList,initial,parent)=>{
|
||||||
removeSelectors(prefix,!initial);
|
removeSelectors(prefix,!initial);
|
||||||
|
if (!parent) parent=document.getElementById("selectors");;
|
||||||
if (!configList) return;
|
if (!configList) return;
|
||||||
let parent=document.getElementById("selectors");
|
|
||||||
if (!parent) return;
|
|
||||||
let frame=addEl('div','selectorFrame',parent);
|
let frame=addEl('div','selectorFrame',parent);
|
||||||
frame.setAttribute(PATH_ATTR,prefix);
|
frame.setAttribute(PATH_ATTR,prefix);
|
||||||
configList.forEach((cfg)=>{
|
let expandedList=expandList(configList);
|
||||||
let key=getVal(cfg,KEY_NAMES);
|
expandedList.forEach((cfg)=>{
|
||||||
let name=prefix?(prefix+SEPARATOR+key):key;
|
if (cfg.key === undefined){
|
||||||
|
console.log("config without key",cfg);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
let name=prefix?(prefix+SEPARATOR+cfg.key):cfg.key;
|
||||||
let current=config[name];
|
let current=config[name];
|
||||||
buildSelector(frame,cfg,name,current,(children,key,value,resource,initial)=>{
|
let childFrame=buildSelector(frame,cfg,name,current,
|
||||||
buildSelectors(name,children,initial);
|
(child,initial,opt_frame)=>{
|
||||||
configStruct[name]={cfg:cfg, key: key, value:value,resource:resource};
|
buildSelectors(name,child.children,initial,opt_frame||childFrame);
|
||||||
|
configStruct[name]=child;
|
||||||
buildValues(initial);
|
buildValues(initial);
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
@ -396,10 +411,9 @@ class PipelineInfo{
|
||||||
//round2: really collect values
|
//round2: really collect values
|
||||||
for (let k in configStruct) {
|
for (let k in configStruct) {
|
||||||
let struct = configStruct[k];
|
let struct = configStruct[k];
|
||||||
if (!struct || !struct.cfg || struct.value === undefined) continue;
|
|
||||||
if (round > 0) config[k] = struct.key;
|
if (round > 0) config[k] = struct.key;
|
||||||
if (struct.cfg.target !== undefined) {
|
if (struct.target !== undefined) {
|
||||||
if (struct.cfg.target === 'environment') {
|
if (struct.target === 'environment') {
|
||||||
if (round > 0) environment = struct.value;
|
if (round > 0) environment = struct.value;
|
||||||
else allowedResources=struct.resource;
|
else allowedResources=struct.resource;
|
||||||
continue;
|
continue;
|
||||||
|
@ -413,13 +427,13 @@ class PipelineInfo{
|
||||||
}
|
}
|
||||||
resList.push(struct);
|
resList.push(struct);
|
||||||
}
|
}
|
||||||
if (struct.cfg.target === 'define') {
|
if (struct.target === 'define') {
|
||||||
flags += " -D" + struct.value;
|
flags += " -D" + struct.value;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
const DEFPRFX = "define:";
|
const DEFPRFX = "define:";
|
||||||
if (struct.cfg.target.indexOf(DEFPRFX) == 0) {
|
if (struct.target.indexOf(DEFPRFX) == 0) {
|
||||||
let def = struct.cfg.target.substring(DEFPRFX.length);
|
let def = struct.target.substring(DEFPRFX.length);
|
||||||
flags += " -D" + def + "=" + struct.value;
|
flags += " -D" + def + "=" + struct.value;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue