Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Generate JSON Survey Schema - Bugs found #6227

Closed
BinoDino opened this issue May 19, 2023 · 13 comments
Closed

Generate JSON Survey Schema - Bugs found #6227

BinoDino opened this issue May 19, 2023 · 13 comments
Assignees
Labels
bug user issue An issue or bug reported by users
Milestone

Comments

@BinoDino
Copy link

Generate JSON Survey Schema - Bugs found

Hi,
I am currently working with the surveyjs form library. I used the Survey.Serializer.generateSchema() method in order to create the JSON schema for the survey. That is when I encountered some bugs in the schema + got error message "schema is invalid" using Ajv library.

Would be great if you could take a look at it 🙂 Sorry for the long message and thank you!

current schema

property visible

{
  "properties": {
     "visible": {
         "type": "string"
      }
   }
}

properties title and description

{
  "properties": {
     "title": {
         "type": "string"
      },
     "description": {
         "type": "string"
      }
   }
}

empty enum properties in schema

{
  "properties": {
    "questionTitlePattern": {
          "type": "string",
          "enum": []
      }
   },
  "definitions": {
    "question": {
       "properties": {
         "page": {
             "type": "string",
             "enum": []
         }
       }
     },
    "panel": {
     "allOf": [
        {},
        {
         "properties": {
            "page": {
             "type": "string",
             "enum": []
            }
          }
        }
     ]
   }
  }
}

properties questions (and others)

{
  "properties": {
     "questions": {
         "type": "array",
         "items": [ { }, { }, { } ]
      }
   }
}

references

$id:

{
   "htmlconditionitem": {
        "$id": "#htmlconditionitem"
   }
}

in properties:

{
  "properties": {
     "completedHtmlOnCondition": {
          "type": "array",
          "items": {
              "$ref": "#htmlconditionitem"
          }
      }
   }
}

in definitions:

{
  "definitions": {
     "htmlconditionitem": {
          "type": "object",
          "$id": "#htmlconditionitem",
          "allOf": [
              {
                  "$ref": "#expressionitem"
              },
              {
                  "properties": {
                      "html": {
                          "type": "string"
                      }
                  }
              }
          ]
      }
}

missing schemas

in definitions/selectbase/allOf/{1}/properties/choicesByUrl:

"choicesByUrl": {
    "type": "array",
    "items": {
        "$ref": "#ChoicesRestful"
    }
}

in definitions/text/allOf/{1}/properties/dataList:

"dataList": {
    "type": "array",
    "items": {
        "$ref": "#string"
    }
}

expected schema

property visible

visible is of type boolean.

{
  "properties": {
     "visible": {
         "type": "boolean"
      }
   }
}

properties title and description

title and description (and others?) are either a string or a translation object.

{
  "properties": {
     "title": {
         "oneOf": [
              { "type": "string"},
              { "$ref": "path/to/some/translation/object"}
          ]
      },
     "description": {
          "oneOf": [
              { "type": "string"},
              { "$ref": "path/to/some/translation/object"}
          ]
      }
   }
}

empty enum properties in schema

empty enum properties are not allowed

properties questions (and others)

Syntax error. Must be anyOf:

{
  "properties": {
     "questions": {
         "type": "array",
         "items": {
            "anyOf": [ { }, { }, { } ]
      }
   }
}

Also affected:

  • triggers
  • defintions/panelbase/properties/elements
  • defintions/question/properties/validators
  • defintions/matrixdropdowncolumn/properties/validators
  • defintions/multipletextitem/properties/validators
  • definitions/nonvalue/allOf/{1}/properties/validators
  • definitions/paneldynamic/allOf/{1}/properties/templateElements

references

$id - no hash symbol #

{
   "htmlconditionitem": {
        "$id": "htmlconditionitem"
   }
}

in properties - path is #/definitions/id:

{
  "properties": {
     "completedHtmlOnCondition": {
          "type": "array",
          "items": {
              "$ref": "#/definitions/htmlconditionitem"
          }
      }
   }
}

in definitions - hash symbol # after id name:

{
  "definitions": {
     "htmlconditionitem": {
          "type": "object",
          "$id": "#htmlconditionitem",
          "allOf": [
              {
                  "$ref": "expressionitem#"
              },
              {
                  "properties": {
                      "html": {
                          "type": "string"
                      }
                  }
              }
          ]
      }
}

missing schemas

provide missing schemas choicesRestful and string

Specifications

  • surveyjs platform (angular or react or jquery or knockout or vue): Angular
  • surveyjs version:
    • survey-angular-ui: 1.9.86
    • survey-core: 1.9.86
@andrewtelnov andrewtelnov self-assigned this May 19, 2023
@andrewtelnov andrewtelnov added bug user issue An issue or bug reported by users labels May 19, 2023
@andrewtelnov
Copy link
Member

@BinoDino I believe I have fixed everything, except localization string class.
I could not figure out how to define it.
It is an object that can have limited number of pairs: { {locName1: locValue1}, {locName2: locValue2} }.
Where locName is an enum ["default", "en", "fr", ...] and locValue is a string.

Thank you,
Andrew

@BinoDino
Copy link
Author

BinoDino commented May 22, 2023

@andrewtelnov Thank you very much for your fast feedback. I really appreciate that.

I think the only way to define the localization string class would be like this:

{
  "definitions": {
     "localization": {
        "type": "object",
         "$id": "localization",
         "properties": {
             "default": {
               "type": "string"
              },
              "ca": {
               "type": "string"
              },
              "cy": {
                "type": "string"
              },
              "da": {
                "type": "string"
              },
              "de": {
                 "type": "string"
              },
             (and so on)
         }
      }
   }
}

and then reference it like this (properties and definitions):

{
  "properties": {
     "title": {
          "oneOf": [
              { "type": "string"},
              { "$ref": "#/definitions/localization"}
          ]
      }
   },
 "definitions": {
    "itemvalue": {
        "type": "object",
        "properties": {
          "text": {
            "oneOf": [
              { "type": "string" },
              { "$ref": "localization#" }
            ]
          }
      }
    }
  }
}

@BinoDino
Copy link
Author

BinoDino commented May 22, 2023

@andrewtelnov sorry to write again, but I have found more bugs on the JSON schema.

The issues are the following:

1. Wrong data types

  • showCommentArea, isRequired, readOnly should be of type boolean
{
  "description":{
     "question": {
         "properties": {
           "showCommentArea": {
              "type": "string"
           },
           "isRequired": {
              "type": "string"
           },
           "readOnly": {
               "type": "string"
          }
       }
     }
  }
}
  • See also in definitions/panel/allOf/{1}/properties/isRequired

2. Double listing of properties

Example 1 (showCommentArea already listed in question):

{
   "definitions": {
       "selectbase": {
          "allOf": [
              {"$ref": "question#"},
              { "properties": {
                  "showCommentArea": {
                    "type": "string"
                   }
                }
             }
          ]
      }
   }
}

See also in

  • definitions/matrixbase/allOf/{1}/properties/showCommentArea

Example 2 (isRequired, readOnly already listed in question):

{
   "definitions": {
       "expression": {
          "allOf": [
              {"$ref": "question#"},
              { "properties": {
                  "isRequired": {
                    "type": "string"
                   },
                   "readOnly": {
                    "type": "string"
                   }
                }
             }
          ]
      }
   }
}

See also in

  • defintions/nonvalue/allOf/{1}/properties/isRequired
  • defintions/nonvalue/allOf/{1}/properties/readOnly
  • defintions/nonvalue/allOf/{1}/properties/showCommentArea
  • defintions/panel/allOf/{1}/properties/isRequired
  • defintions/panel/allOf/{1}/properties/readOnly
  • defintions/file/allOf/{1}/properties/showCommentArea
  • defintions/rating/allOf/{1}/properties/showCommentArea
  • defintions/boolean/allOf/{1}/properties/showCommentArea
  • defintions/panelDynamic/allOf/{1}/properties/showCommentArea
  • defintions/nonvalue/propertiesin general

3. Double listing and wrong data type on second listing

Initially separateSpecialChoices is boolean

{
   "definitions": {
       "selectbase": {
          "allOf": [
              {"$ref": "question#"},
              { "properties": {
                  "separateSpecialChoices": {
                      "type": "boolean"
                    }
                }
             }
          ]
      },
    "checkboxbase": {
          "type": "object",
          "$id": "checkboxbase",
          "allOf": [
            {
              "$ref": "selectbase#"
            }
         ]
     }
   }
}

Here it is a string now:

{
   "definitions": {
      "radiogroup": {
          "allOf": [
            {
              "$ref": "checkboxbase#"
            },
            {
              "properties": {
                "separateSpecialChoices": {
                  "type": "string"
                }
              }
            }
          ]
        },
      "checkbox": {
          "allOf": [
            {
              "$ref": "checkboxbase#"
            },
            {
              "properties": {
                "separateSpecialChoices": {
                  "type": "string"
                }
              }
            }
          ]
        }
    }
}

@andrewtelnov
Copy link
Member

@BinoDino I beleived I have fixed issues. You can check this PR.
Hopefully it will be merged before we relase next version tomorrow/after tomorrow.

Thank you,
Andrew

@BinoDino
Copy link
Author

@andrewtelnov Thank you very much for your efforts! 🙂 Will notify you if I come across anything else.

@BinoDino
Copy link
Author

@andrewtelnov Sorry, I have something else - it's rather a question (or maybe a bug?):

I noticed that in the JSON schema there is no property type for the elements/questions. But when I use the Survey Creator a type property is even required (to identify the question type for rendering I suppose).

Moreover, I noticed that there are no required Schema fields at all. But isn't it for example like this:

  • a page requires a name as unique identifier
  • a question requires a name as unique identifier and a type to define what kind of question it is

@andrewtelnov
Copy link
Member

@BinoDino I have added "type" property into "#question" and "#panel". It supports "required" array attribute as well.

Thank you,
Andrew

@OlgaLarina OlgaLarina added this to the v1.9.89 milestone May 23, 2023
@BinoDino
Copy link
Author

@andrewtelnov Thank you very much for the latest version of the surveyjs schema. I really appreciate your fast reply and fixes. I tested it today. Unfortunately I found two issues that were not fixed yet.

The issues are the following

1. Error message: invalid schema: data/properties/questions/items must be object,boolean

current schema

items attribute is an array

{
  "properties": {
     "questions": {
         "type": "array",
         "items": [...]
      }
   }
}

expected schema

items attribute is an object with anyOf, which is an array

{
  "properties": {
     "questions": {
         "type": "array",
         "items": {
            "anyOf": [...]
      }
   }
}

Affected:

  • properties/questions/items
  • properties/triggers/items
  • definitions/panelbase/properties/elements/items
  • definitions/question/properties/validators/items
  • definitions/matrixdropdowncolumn/properties/validators/items
  • definitions/multipletextitem/properties/validators/items
  • definitions/paneldynamic/allOf/{1}/properties/templateElements/items

2. Error message: invalid schema: data/definitions/expressionitem/$id must match pattern "^[^#]*#?$"

current schema

Every attribute $id starts with "#".

{
   "htmlconditionitem": {
        "$id": "#htmlconditionitem"
   }
}

expected schema

Remove "#" from $id, else it's invalid.

{
   "htmlconditionitem": {
        "$id": "htmlconditionitem"
   }
}

@andrewtelnov andrewtelnov reopened this May 25, 2023
@andrewtelnov andrewtelnov modified the milestones: v1.9.89, v1.9.90 May 25, 2023
@andrewtelnov
Copy link
Member

@BinoDino Regarding the second issue. Do you mean that all "$id" for all defintions should not have "#" symbol?

Thank you,
Andrew

@BinoDino
Copy link
Author

@andrewtelnov To your question: yes, that is correct.

@andrewtelnov
Copy link
Member

@BinoDino Please review my commits in this PR.

Thank you,
Andrew

tsv2013 pushed a commit that referenced this issue May 29, 2023
* Fix $id property, remove # symbol #6227

* Fix items with baseClassName => items.anyOf[] #6227
@BinoDino
Copy link
Author

@andrewtelnov sorry for my late answer. Your commits look good as far as I can evaluate 👍 Thank you so so much!

@andrewtelnov
Copy link
Member

@BinoDino Super, we are going to release v1.9.90 today.

Thank you,
Andrw

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug user issue An issue or bug reported by users
Projects
None yet
Development

No branches or pull requests

3 participants