feat: ✨ convert redcap data dict to resource properties#35
feat: ✨ convert redcap data dict to resource properties#35martonvago wants to merge 4 commits intomainfrom
Conversation
| def _map(x: Iterable[In], fn: Callable[[In], Out]) -> list[Out]: | ||
| return list(map(fn, x)) | ||
|
|
||
|
|
||
| def _filter(x: Iterable[In], fn: Callable[[In], bool]) -> list[In]: | ||
| return list(filter(fn, x)) | ||
|
|
||
|
|
||
| def _flat_map(items: Iterable[In], fn: Callable[[In], Iterable[Out]]) -> list[Out]: | ||
| """Maps and flattens the items by one level.""" | ||
| return list(chain.from_iterable(map(fn, items))) |
There was a problem hiding this comment.
These could come from soil.
Or we could decide #34 and put them in internals.py
| form_name: str, fields: list[dict[str, str]] | ||
| ) -> sp.ResourceProperties: | ||
| visit_field = sp.FieldProperties( | ||
| name="visit", |
There was a problem hiding this comment.
Or event?
Could contain the unique_event_name or event_id of a REDCap event
| ), | ||
| ) | ||
|
|
||
| # Discard fields displayed for information only |
There was a problem hiding this comment.
descriptive fields are there to give information/instructions to people filling in the form, as far as I understand.
checkbox fields are treated separately. See #32 (comment) for details.
| form_redcap_fields, | ||
| lambda field: sp.FieldProperties( | ||
| name=field["field_name"], | ||
| title=field["field_name"], |
There was a problem hiding this comment.
I couldn't find a better equivalent for title. There's field_label but that's often a long question or explanation in Danish.
| constraints=sp.ConstraintsProperties( | ||
| required=_get_required(field), | ||
| enum=_get_categories(field), | ||
| ), |
There was a problem hiding this comment.
Don't know if we want constraints.
The enum constraint is the same as categories above.
| title=form_name, | ||
| description=form_name, |
There was a problem hiding this comment.
The title could be the instrument_label that we can get by making another API call (it's not in the data dict).
I wasn't able to find an equivalent for description.
| """Parses the choices into the choice number and choice value. | ||
|
|
||
| E.g.: | ||
| Input: "1, first choice|2, second choice|3, third choice" |
There was a problem hiding this comment.
My understanding is that choices usually look like this but that basically anything can be entered in the UI. This function throws an error if an unexpected format is given because I thought that was better than potentially making a silent mistake somewhere.
Does anyone know if we expect other formats? E.g. A, first choice|B, second choice|C, third choice?
| return _map( | ||
| _get_choices(checkbox_field), | ||
| lambda choice: sp.FieldProperties( | ||
| name=f"{checkbox_field['field_name']}___{choice[0]}", |
There was a problem hiding this comment.
This is how the data is structured by REDCap
|
|
||
|
|
||
| def _get_description(redcap_field: dict[str, str]) -> str: | ||
| description = redcap_field["field_annotation"] |
There was a problem hiding this comment.
This seemed to be the property that was almost always filled in and in English.
There is also field_note, which is not always filled in and in Danish.
| title=field["field_name"], | ||
| type=_get_type(field), | ||
| description=_get_description(field), | ||
| categories=_get_categories(field), |
There was a problem hiding this comment.
This is a list of strings.
We can also have a list of objects like {"value": 1, "label": "apple"} to keep track of the REDCap number of the choices as well.
| case "slider": | ||
| return "number" | ||
| case _: | ||
| raise NotImplementedError(_get_error_message(redcap_field, "field_type")) |
There was a problem hiding this comment.
I only included the field types that were in the test data. There are some more.
| case "text" | "calc" | "radio" | "notes" | "file": | ||
| return "string" | ||
| case "slider": | ||
| return "number" |
There was a problem hiding this comment.
I think slider can be integer or float, both are included in number
Description
This PR adds the ability to convert a saved REDCap data dict to resource properties.
Followed this plan: #23 (comment)
Does not include a resource for events/visits. Not sure if we want that?
Closes #25 closes #26
This PR needs an in-depth review.
Checklist
just run-all