Skip to content

Commit

Permalink
label multiple choice options for enablin data parsing of cross-langu…
Browse files Browse the repository at this point in the history
…age courses.
  • Loading branch information
anadis504 committed May 12, 2023
1 parent 8d77f84 commit 85e7fc4
Show file tree
Hide file tree
Showing 7 changed files with 84 additions and 71 deletions.
16 changes: 14 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
The factor-analysis-exercise-service is used for creating survey exercises.
The factor-analysis-exercise-service is used for creating survey exercises.

## Using the service for creating survey exercises

Expand All @@ -10,4 +10,16 @@ Run `npm ci` in the repo root

Run the development server with `npm run dev` the server is running on `localhost:3008`

###
## Expose the service to locally running secret-project minikube cluster

using [ktunnel](https://github.com/omrikiei/ktunnel). Allows you to test exercises that actually need the database, such as testing the `global variables`.

Run `bin/ktunnel` from repo root.

The adress to use in minikube is:

`http://factorial-analysis.default.svc.cluster.local:80/api/service-info`

When stopping the cluster, the best is to stop the ktunnel exposure before killing the minikube cluster.

If the service is active when minikube is stopped remember to either delete the service from the cluster (see commands in the bin/ktunnel [file](./bin/ktunnel)) or to update the name of the service (factorial-analysis2 for example) which will again affect the local cluster-adress.
4 changes: 2 additions & 2 deletions src/components/Survey/Editors/SelectItemCondition.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -25,14 +25,14 @@ export const SelectCondition: React.FC<React.PropsWithChildren<SelectorProps>> =
) {
return
}
sItem.answer.options.map((option) => {
sItem.answerSpec.options.map((option) => {
const condition: SurveyItemCondition = {
questionLabel: sItem.question.questionLabel,
triggeringOption: option,
}
possibleItems.push(condition)
})
sItem.answer.factorialOptions?.map((option) => {
sItem.answerSpec.factorialOptions?.map((option) => {
const condition: SurveyItemCondition = {
questionLabel: sItem.question.questionLabel,
triggeringOption: option.name,
Expand Down
12 changes: 6 additions & 6 deletions src/components/Survey/Editors/SurveyEditor.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ import CheckBox from "../../../shared-module/components/InputFields/CheckBox"
import TextField from "../../../shared-module/components/InputFields/TextField"
import { baseTheme, primaryFont } from "../../../shared-module/styles"
import {
Answer,
AnswerSpec,
AnswerType,
SumFactor,
Survey,
Expand Down Expand Up @@ -91,7 +91,7 @@ const SurveyEditor: React.FC<React.PropsWithChildren<Props>> = ({ state, setStat
...quest,
id: v4(),
question: { question: "", questionLabel: "", id: v4() },
answer: { ...quest.answer, id: v4() },
answer: { ...quest.answerSpec, id: v4() },
}
const currentIndex = state.content.indexOf(quest)
const newContent = state.content
Expand Down Expand Up @@ -140,14 +140,14 @@ const SurveyEditor: React.FC<React.PropsWithChildren<Props>> = ({ state, setStat
if (typeof newState.content === "undefined") {
newState.content = []
}
const answerObject: Answer = {
const answerObject: AnswerSpec = {
type: AnswerType.None,
options: [],
}
newState.content.push({
id: v4(),
question: { id: v4(), question: "", questionLabel: "" },
answer: answerObject,
answerSpec: answerObject,
conditional: false,
})
setState({ view_type: "exercise-editor", private_spec: newState })
Expand All @@ -168,14 +168,14 @@ const SurveyEditor: React.FC<React.PropsWithChildren<Props>> = ({ state, setStat
if (!e) {
return
}
const answerObject: Answer = {
const answerObject: AnswerSpec = {
type: AnswerType.None,
options: [],
}
newContent.push({
id: v4(),
question: { id: v4(), questionLabel: e[0], question: e[1] },
answer: answerObject,
answerSpec: answerObject,
conditional: false,
})
})
Expand Down
87 changes: 43 additions & 44 deletions src/components/Survey/Editors/SurveyItemEditor.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import CheckBox from "../../../shared-module/components/InputFields/CheckBox"
import TextArea from "../../../shared-module/components/InputFields/TextAreaField"
import { baseTheme, primaryFont } from "../../../shared-module/styles"
import { respondToOrLarger } from "../../../shared-module/styles/respond"
import { Answer, AnswerType, Survey, SurveyItem } from "../../../util/spec-types/privateSpec"
import { AnswerSpec, AnswerType, Survey, SurveyItem } from "../../../util/spec-types/privateSpec"
import {
insertVariablesToText,
parseLabelQuestion,
Expand Down Expand Up @@ -107,23 +107,23 @@ const SurveyItemEditor: React.FC<React.PropsWithChildren<Props>> = ({
},
}
if (newItem.question.questionLabel === "info") {
newItem.answer.type = AnswerType.None
newItem.answer.options = []
newItem.answerSpec.type = AnswerType.None
newItem.answerSpec.options = []
delete newItem.globalVariable
delete newItem.question.mandatory
}
if (newItem.question.questionLabel === "info-header") {
newItem.answer.type = AnswerType.ConsentCheckbox
newItem.answer.options = []
newItem.answerSpec.type = AnswerType.ConsentCheckbox
newItem.answerSpec.options = []
delete newItem.globalVariable
delete newItem.question.mandatory
}
if (
newItem.answer.type === AnswerType.ConsentCheckbox &&
newItem.answerSpec.type === AnswerType.ConsentCheckbox &&
newItem.question.questionLabel !== "info-header"
) {
newItem.answer.type = AnswerType.None
newItem.answer.options = []
newItem.answerSpec.type = AnswerType.None
newItem.answerSpec.options = []
}
onChangeSurveyItem(newItem)
}}
Expand All @@ -146,22 +146,22 @@ const SurveyItemEditor: React.FC<React.PropsWithChildren<Props>> = ({
/>
{item.question.questionLabel && item.question.questionLabel !== "info" && (
<select
aria-label={`select-answer-type-${item.question.questionLabel}.`}
aria-label={`select-answerSpec-type-${item.question.questionLabel}.`}
onChange={(event) => {
const answer: Answer = item.answer
const answerSpec: AnswerSpec = item.answerSpec
const answerType: AnswerType = event.target.value as unknown as AnswerType
if (!answerType) {
return
}
onChangeSurveyItem({
...item,
answer: {
...answer,
answerSpec: {
...answerSpec,
options:
answerType === AnswerType.Dropdown ||
answerType === AnswerType.MultiChoice ||
answerType === AnswerType.RadioGroup
? ([...answer.options] as string[])
? ([...answerSpec.options] as string[])
: [],
type: answerType,
},
Expand All @@ -176,7 +176,7 @@ const SurveyItemEditor: React.FC<React.PropsWithChildren<Props>> = ({
margin-top: 1rem;
margin-bottom: 1rem;
`}
value={item.answer.type}
value={item.answerSpec.type}
>
{Object.values(AnswerType).map((t) => {
if (t === AnswerType.None) {
Expand All @@ -202,13 +202,12 @@ const SurveyItemEditor: React.FC<React.PropsWithChildren<Props>> = ({
})}
</select>
)}

{(item.answer?.type === AnswerType.MultiChoice ||
item.answer?.type === AnswerType.RadioGroup ||
item.answer?.type === AnswerType.Dropdown ||
item.answer?.type === AnswerType.AdvancedDropdown) && (
{(item.answerSpec?.type === AnswerType.MultiChoice ||
item.answerSpec?.type === AnswerType.RadioGroup ||
item.answerSpec?.type === AnswerType.Dropdown ||
item.answerSpec?.type === AnswerType.AdvancedDropdown) && (
<div>
{item.answer.options.length > 0 && (
{item.answerSpec.options.length > 0 && (
<ol
className={css`
width: 100%;
Expand All @@ -220,7 +219,7 @@ const SurveyItemEditor: React.FC<React.PropsWithChildren<Props>> = ({
border-spacing: 0;
`}
>
{item.answer.options.map((o, o_idx) => {
{item.answerSpec.options.map((o, o_idx) => {
return (
<li key={o_idx}>
<StyledInnerEditor>
Expand All @@ -229,18 +228,18 @@ const SurveyItemEditor: React.FC<React.PropsWithChildren<Props>> = ({
value={o as string}
type="text"
onChange={(e) => {
const newAnswer = item.answer
newAnswer.options[o_idx] = e.target.value
onChangeSurveyItem({ ...item, answer: newAnswer })
const newAnswerSpec = item.answerSpec
newAnswerSpec.options[o_idx] = e.target.value
onChangeSurveyItem({ ...item, answerSpec: newAnswerSpec })
}}
/>
<DeleteButton
onClick={() => {
const newAnswer = {
...item.answer,
options: (item.answer.options as string[]).filter((e) => o !== e),
...item.answerSpec,
options: (item.answerSpec.options as string[]).filter((e) => o !== e),
}
onChangeSurveyItem({ ...item, answer: newAnswer })
onChangeSurveyItem({ ...item, answerSpec: newAnswer })
}}
>
{"x"}
Expand All @@ -254,8 +253,8 @@ const SurveyItemEditor: React.FC<React.PropsWithChildren<Props>> = ({
<button
onClick={() => {
const newItem = item as SurveyItem
newItem.answer.options.push("")
onChangeSurveyItem({ ...item, answer: newItem.answer })
newItem.answerSpec.options.push("")
onChangeSurveyItem({ ...item, answerSpec: newItem.answerSpec })
}}
className={css`
flex: 1;
Expand All @@ -268,9 +267,9 @@ const SurveyItemEditor: React.FC<React.PropsWithChildren<Props>> = ({
<CsvReader
parseNoHeaders={(value) => {
const newOptions = value.flat().filter((n) => n === 0 || n)
const newAnswer = item.answer
newAnswer.options = newOptions
onChangeSurveyItem({ ...item, answer: newAnswer })
const newAnswerSpec = item.answerSpec
newAnswerSpec.options = newOptions
onChangeSurveyItem({ ...item, answerSpec: newAnswerSpec })
}}
parseUsingHeaders={() => null}
title={"or upload a csv file"}
Expand All @@ -281,35 +280,35 @@ const SurveyItemEditor: React.FC<React.PropsWithChildren<Props>> = ({
/>
</div>
)}
{item.answer.type === AnswerType.WeightedRadioGroup && (
{item.answerSpec.type === AnswerType.WeightedRadioGroup && (
<>
<ol>
{item.answer.factorialOptions?.map((fop, idx) => {
{item.answerSpec.factorialOptions?.map((fop, idx) => {
return (
<li key={idx}>
<OptionEditor
questionLabel={item.question.questionLabel}
idx={idx + 1}
item={fop}
onDelete={() => {
const newOptions = item.answer.factorialOptions?.filter(
const newOptions = item.answerSpec.factorialOptions?.filter(
(e) => e.id !== fop.id,
)
onChangeSurveyItem({
...item,
answer: { ...item.answer, factorialOptions: newOptions },
answerSpec: { ...item.answerSpec, factorialOptions: newOptions },
})
}}
onChange={(op) => {
const newOptions = item.answer.factorialOptions?.map((option) => {
const newOptions = item.answerSpec.factorialOptions?.map((option) => {
if (option.id !== fop.id) {
return option
}
return op
})
onChangeSurveyItem({
...item,
answer: { ...item.answer, factorialOptions: newOptions },
answerSpec: { ...item.answerSpec, factorialOptions: newOptions },
})
}}
/>
Expand All @@ -320,10 +319,10 @@ const SurveyItemEditor: React.FC<React.PropsWithChildren<Props>> = ({
<button
onClick={() => {
const newItem: SurveyItem = { ...item }
if (typeof newItem.answer.factorialOptions === "undefined") {
newItem.answer.factorialOptions = []
if (typeof newItem.answerSpec.factorialOptions === "undefined") {
newItem.answerSpec.factorialOptions = []
}
newItem.answer.factorialOptions.push({ name: "", value: 0, id: v4() })
newItem.answerSpec.factorialOptions.push({ name: "", value: 0, id: v4() })
onChangeSurveyItem(newItem)
}}
className={css`
Expand All @@ -336,7 +335,7 @@ const SurveyItemEditor: React.FC<React.PropsWithChildren<Props>> = ({
</button>
</>
)}
{item.answer?.type === AnswerType.ConsentCheckbox && (
{item.answerSpec?.type === AnswerType.ConsentCheckbox && (
<TextArea
label="Checkbox text editor"
placeholder={"Consent message"}
Expand All @@ -350,9 +349,9 @@ const SurveyItemEditor: React.FC<React.PropsWithChildren<Props>> = ({
}
`}
onChange={(value) => {
onChangeSurveyItem({ ...item, answer: { ...item.answer, options: [value] } })
onChangeSurveyItem({ ...item, answerSpec: { ...item.answerSpec, options: [value] } })
}}
defaultValue={item.answer.options[0]}
defaultValue={item.answerSpec.options[0]}
/>
)}
<StyledInnerEditor respondTo>
Expand Down
Loading

0 comments on commit 85e7fc4

Please sign in to comment.