2019-04-09 23:17:03 -06:00
|
|
|
import { Everything, TimeSettings } from "../interfaces";
|
2019-01-10 20:10:55 -07:00
|
|
|
import {
|
2020-02-28 09:35:32 -07:00
|
|
|
Props, RegimenItem, RegimenItemCalendarRow, CalendarRow,
|
2019-01-10 20:10:55 -07:00
|
|
|
} from "./interfaces";
|
2017-06-29 12:54:02 -06:00
|
|
|
import {
|
|
|
|
selectAllSequences,
|
|
|
|
selectAllRegimens,
|
|
|
|
maybeGetSequence,
|
|
|
|
maybeGetRegimen,
|
|
|
|
findId,
|
2019-01-10 20:10:55 -07:00
|
|
|
findSequence,
|
2019-04-09 23:17:03 -06:00
|
|
|
findSequenceById,
|
2020-02-28 09:35:32 -07:00
|
|
|
maybeGetTimeSettings,
|
2017-06-29 12:54:02 -06:00
|
|
|
} from "../resources/selectors";
|
2019-06-28 13:05:19 -06:00
|
|
|
import { TaggedRegimen, TaggedSequence } from "farmbot";
|
2019-02-04 13:54:17 -07:00
|
|
|
import moment from "moment";
|
2019-01-10 20:10:55 -07:00
|
|
|
import { ResourceIndex, UUID, VariableNameSet } from "../resources/interfaces";
|
2019-12-27 11:37:54 -07:00
|
|
|
import { randomColor, timeFormatString } from "../util";
|
2018-11-18 09:29:06 -07:00
|
|
|
import { resourceUsageList } from "../resources/in_use";
|
2019-02-06 18:36:11 -07:00
|
|
|
import { groupBy, chain, sortBy } from "lodash";
|
2019-12-27 11:37:54 -07:00
|
|
|
import { getShouldDisplayFn } from "../farmware/state_to_props";
|
2017-06-29 12:54:02 -06:00
|
|
|
|
|
|
|
export function mapStateToProps(props: Everything): Props {
|
2017-08-28 05:49:13 -06:00
|
|
|
const { resources, dispatch, bot } = props;
|
2019-04-09 19:45:59 -06:00
|
|
|
const {
|
|
|
|
weeks, dailyOffsetMs, selectedSequenceUUID, currentRegimen, schedulerOpen
|
|
|
|
} = resources.consumers.regimens;
|
2017-08-28 05:49:13 -06:00
|
|
|
const { index } = resources;
|
|
|
|
const current = maybeGetRegimen(index, currentRegimen);
|
2019-04-09 23:17:03 -06:00
|
|
|
const timeSettings = maybeGetTimeSettings(props.resources.index);
|
2017-08-28 05:49:13 -06:00
|
|
|
const calendar = current ?
|
2019-04-09 23:17:03 -06:00
|
|
|
generateCalendar(current, index, dispatch, timeSettings) : [];
|
2017-06-29 12:54:02 -06:00
|
|
|
|
2019-01-10 20:10:55 -07:00
|
|
|
const calledSequences = (): UUID[] => {
|
|
|
|
if (current) {
|
|
|
|
const sequenceIds = current.body.regimen_items.map(x => x.sequence_id);
|
|
|
|
return Array.from(new Set(sequenceIds)).map(x =>
|
|
|
|
findSequenceById(props.resources.index, x).uuid);
|
|
|
|
}
|
|
|
|
return [];
|
|
|
|
};
|
|
|
|
|
|
|
|
const variableData: VariableNameSet = {};
|
|
|
|
calledSequences().map(uuid =>
|
|
|
|
Object.entries(props.resources.index.sequenceMetas[uuid] || {})
|
|
|
|
.map(([key, value]) => !variableData[key] && (variableData[key] = value)));
|
|
|
|
|
2017-06-29 12:54:02 -06:00
|
|
|
return {
|
|
|
|
dispatch: props.dispatch,
|
|
|
|
sequences: selectAllSequences(index),
|
2019-01-10 20:10:55 -07:00
|
|
|
variableData,
|
2017-06-29 12:54:02 -06:00
|
|
|
resources: index,
|
|
|
|
auth: props.auth,
|
|
|
|
current,
|
|
|
|
regimens: selectAllRegimens(index),
|
|
|
|
selectedSequence: maybeGetSequence(index, selectedSequenceUUID),
|
|
|
|
dailyOffsetMs,
|
|
|
|
weeks,
|
|
|
|
bot,
|
2018-11-18 09:29:06 -07:00
|
|
|
calendar,
|
2019-01-10 20:10:55 -07:00
|
|
|
regimenUsageStats: resourceUsageList(props.resources.index.inUse),
|
2019-12-27 11:37:54 -07:00
|
|
|
shouldDisplay: getShouldDisplayFn(props.resources.index, props.bot),
|
2019-04-09 19:45:59 -06:00
|
|
|
schedulerOpen,
|
2017-06-29 12:54:02 -06:00
|
|
|
};
|
|
|
|
}
|
|
|
|
|
|
|
|
const SORT_KEY: keyof RegimenItemCalendarRow = "sortKey";
|
|
|
|
|
|
|
|
/** Does all the heavy lifting related to joining regimen items with their
|
|
|
|
* appropriate sequence meta data like "sequence name" and the like.
|
|
|
|
*/
|
|
|
|
function generateCalendar(regimen: TaggedRegimen,
|
|
|
|
index: ResourceIndex,
|
2019-04-09 23:17:03 -06:00
|
|
|
dispatch: Function,
|
|
|
|
timeSettings: TimeSettings): CalendarRow[] {
|
|
|
|
const mapper = createRows(index, dispatch, regimen, timeSettings);
|
2017-08-28 05:49:13 -06:00
|
|
|
const rows = regimen.body.regimen_items.map(mapper);
|
2019-02-04 07:32:26 -07:00
|
|
|
const dict = groupBy(rows, "day");
|
2017-08-28 05:49:13 -06:00
|
|
|
const makeRows = (day: string): CalendarRow => ({ day: day, items: dict[day] });
|
2019-02-04 07:32:26 -07:00
|
|
|
const days = chain(dict)
|
2017-06-29 12:54:02 -06:00
|
|
|
.keys()
|
|
|
|
.map(x => parseInt(x))
|
|
|
|
.sort((a, b) => a - b)
|
|
|
|
.map(x => "" + x)
|
|
|
|
.value();
|
|
|
|
return days
|
|
|
|
.map(makeRows)
|
|
|
|
.map((x) => {
|
2019-02-06 18:36:11 -07:00
|
|
|
x.items = sortBy(x.items, SORT_KEY);
|
2017-06-29 12:54:02 -06:00
|
|
|
return x;
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
2019-04-09 23:17:03 -06:00
|
|
|
const createRows = (
|
|
|
|
index: ResourceIndex, dispatch: Function, regimen: TaggedRegimen,
|
2020-02-28 09:35:32 -07:00
|
|
|
timeSettings: TimeSettings,
|
2019-04-09 23:17:03 -06:00
|
|
|
) =>
|
2017-06-29 12:54:02 -06:00
|
|
|
(item: RegimenItem): RegimenItemCalendarRow => {
|
2017-10-27 07:31:25 -06:00
|
|
|
const uuid = findId(index, "Sequence", item.sequence_id);
|
2017-08-28 05:49:13 -06:00
|
|
|
const sequence = findSequence(index, uuid);
|
2019-06-28 13:05:19 -06:00
|
|
|
const variable = getParameterLabel(sequence);
|
2017-08-28 05:49:13 -06:00
|
|
|
const { time_offset } = item;
|
2019-02-06 18:36:11 -07:00
|
|
|
const d = moment.duration(time_offset);
|
2017-08-28 05:49:13 -06:00
|
|
|
const { name } = sequence.body;
|
|
|
|
const color = sequence.body.color || randomColor();
|
2019-04-09 23:17:03 -06:00
|
|
|
const FORMAT = timeFormatString(timeSettings);
|
|
|
|
const hhmm = moment({ hour: d.hours(), minute: d.minutes() }).format(FORMAT);
|
2019-02-06 18:36:11 -07:00
|
|
|
const day = Math.floor(moment.duration(time_offset).asDays()) + 1;
|
2019-06-28 13:05:19 -06:00
|
|
|
return {
|
|
|
|
name, hhmm, color, day, dispatch, regimen, item, variable,
|
|
|
|
sortKey: time_offset
|
|
|
|
};
|
2017-06-30 14:24:09 -06:00
|
|
|
};
|
2019-06-28 13:05:19 -06:00
|
|
|
|
|
|
|
const getParameterLabel = (sequence: TaggedSequence): string | undefined =>
|
|
|
|
(sequence.body.args.locals.body || [])
|
|
|
|
.filter(variable => variable.kind === "parameter_declaration")
|
|
|
|
.map(variable => variable.args.label)[0];
|