From 2415f508808bc0d29ed74e3e816f59bfc8aac895 Mon Sep 17 00:00:00 2001 From: Sven Van Caekenberghe Date: Wed, 25 Oct 2023 13:27:33 +0200 Subject: [PATCH] More example, more documentation --- lepiter/81brlbrknhsro4cxzdl06l22t.bak | 695 ++++++++++++++++- lepiter/81brlbrknhsro4cxzdl06l22t.lepiter | 728 +++++++++++++++++- .../Neo-JSON-Core/NeoJSONObject.class.st | 23 + .../Neo-JSON-Core/NeoJSONReader.class.st | 23 + .../Neo-JSON-Core/NeoJSONWriter.class.st | 28 + 5 files changed, 1491 insertions(+), 6 deletions(-) diff --git a/lepiter/81brlbrknhsro4cxzdl06l22t.bak b/lepiter/81brlbrknhsro4cxzdl06l22t.bak index eef434e..5a641c9 100644 --- a/lepiter/81brlbrknhsro4cxzdl06l22t.bak +++ b/lepiter/81brlbrknhsro4cxzdl06l22t.bak @@ -78,6 +78,576 @@ }, "string" : "NeoJSON is an elegant and efficient standalone Smalltalk framework to read and write JSON converting to or from Smalltalk objects." }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T11:58:50.079586+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T11:59:38.00409+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "7dQtPenEDQCwkkjwCLMSBQ==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "# Arrays & Dictionaries" + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T11:59:44.369072+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:06:19.904615+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "BEJqQOnEDQCxjPmCCLMSBQ==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "JSON is defined using a number of primitive types (numbers, strings, booleans and null) and two composite types (lists and maps). Maps consist of unordered key value pairs and are sometimes called objects. Lists contain an ordered collection of JSON values. The natural or generic mapping of these two concepts is to {{gtClass:Array}} and {{gtClass:Dictionary}}. This is what {{gtClass:NeoJSONReader}} does out of the box." + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:04:56.100214+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:06:41.24643+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "cOT+UunEDQC6HlPJCLMSBQ==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "Let's consider some JSON input." + }, + { + "__type" : "exampleSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:06:49.982516+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:06:49.982516+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "1JnIWenEDQC8L1vZCLMSBQ==" + }, + "exampleSelector" : "exampleCoordinatesJSON", + "previewHeight" : 200, + "previewShowSelector" : "gtStringFor:", + "exampleBehaviorName" : "NeoJSONReader class", + "codeExpanded" : true, + "previewExpanded" : false, + "noCode" : false + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:08:10.942323+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:08:49.896313+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "W7XlXenEDQC8h3syCLMSBQ==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "Here is how to use {{gtClass:NeoJSONReader}} to parse this JSON input." + }, + { + "__type" : "exampleSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:08:58.808255+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:08:58.808255+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "1VN2YenEDQC+SF0qCLMSBQ==" + }, + "exampleSelector" : "exampleCoordinatesGenericParsing", + "previewHeight" : 200, + "previewShowSelector" : "gtViewsFor:", + "exampleBehaviorName" : "NeoJSONReader class", + "codeExpanded" : true, + "previewExpanded" : false, + "noCode" : false + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:09:56.333014+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:10:36.168612+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "3BTkZOnEDQC+rIHICLMSBQ==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "The resulting data structure is an array of dictionaries." + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:11:20.602757+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:23:52.709532+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "I+/paenEDQCAHWklCLMSBQ==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "Generating JSON is done using {{gtClass:NeoJSONWriter}} with this data structure as input. Actually, many collections are considered as lists except those that are explicitly seen as maps because they contain key value pairs. " + }, + { + "__type" : "exampleSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:13:27.745059+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:13:27.745059+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "afp9cenEDQCFexvvCLMSBQ==" + }, + "exampleSelector" : "exampleCoordinatesGenericWriting", + "previewHeight" : 200, + "previewShowSelector" : "gtStringFor:", + "exampleBehaviorName" : "NeoJSONWriter class", + "codeExpanded" : true, + "previewExpanded" : false, + "noCode" : false + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:16:38.934273+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:16:45.257142+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "5kjjfOnEDQCFy427CLMSBQ==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "# Mapping" + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:16:47.512544+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:03:04.233496+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "ADJmfenEDQCF9BZpCLMSBQ==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "JSON is fully dynamic and does not contain any type or class information. However, users do place meaning on certain JSON constructs. In our coordinates example we can all see that this is a list of x y coordinates, although this is not explicitly defined. So we might be inclined to use {{gtClass:Point}} here. Mapping allows you to make some use of the implicit schema present in JSON, either during parsing or during writing." + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:03:13.264218+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:04:58.868156+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "kWFxI+rEDQCvbdhdBdJ9wA==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "For parsing we need to tell the reader about the domain object that we want to use. And although we could have used {{gtMethod:NeoJSONReader>>#nextListAs:}} we defined and used a virtual type, ArrayOfPoints. " + }, + { + "__type" : "exampleSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:01:50.942757+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:01:50.942757+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "jUGJHurEDQCu8xlxBdJ9wA==" + }, + "exampleSelector" : "exampleCoordinatesCustomParsing", + "previewHeight" : 200, + "previewShowSelector" : "gtViewsFor:", + "exampleBehaviorName" : "NeoJSONReader class", + "codeExpanded" : true, + "previewExpanded" : false, + "noCode" : false + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:05:40.597846+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:09:44.12187+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "04M5LOrEDQCz5dG4BdJ9wA==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "For writing, we only need to map Point. Without a mapping, the writer would fail on Point since it does not know how to turn points into JSON." + }, + { + "__type" : "exampleSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:06:22.54966+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:06:22.54966+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "Dai5LurEDQC1aiNMBdJ9wA==" + }, + "exampleSelector" : "exampleCoordinatesCustomWriting", + "previewHeight" : 200, + "previewShowSelector" : "gtViewsFor:", + "exampleBehaviorName" : "NeoJSONWriter class", + "codeExpanded" : true, + "previewExpanded" : false, + "noCode" : false + }, { "__type" : "textSnippet", "children" : { @@ -103,7 +673,7 @@ "__type" : "time", "time" : { "__type" : "dateAndTime", - "dateAndTimeString" : "2023-10-23T15:00:55.457512+02:00" + "dateAndTimeString" : "2023-10-25T12:16:52.770243+02:00" } }, "uid" : { @@ -140,7 +710,7 @@ "__type" : "time", "time" : { "__type" : "dateAndTime", - "dateAndTimeString" : "2023-10-23T14:53:01.507768+02:00" + "dateAndTimeString" : "2023-10-25T13:26:15.191477+02:00" } }, "uid" : { @@ -150,7 +720,7 @@ "paragraphStyle" : { "__type" : "textStyle" }, - "string" : "Here is a small and simple example of JSON, a map with 2 key-value pairs." + "string" : "Another option is to use {{gtClass:NeoJSONObject}} and {{gtClass:NeoJSONArray}}. These are then used as mapClHere is a small and simple example of JSON, a map with 2 key-value pairs." }, { "__type" : "exampleSnippet", @@ -186,7 +756,7 @@ }, "exampleSelector" : "exampleSimpleJSON", "previewHeight" : 200, - "previewShowSelector" : "gtViewsFor:", + "previewShowSelector" : "gtStringFor:", "exampleBehaviorName" : "NeoJSONObject class", "codeExpanded" : true, "previewExpanded" : false, @@ -499,6 +1069,123 @@ "codeExpanded" : true, "previewExpanded" : false, "noCode" : false + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:15:58.018722+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:16:34.590223+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "upYGUerEDQC3uiMoBdJ9wA==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "The next two examples show how to work with the coordinates example." + }, + { + "__type" : "exampleSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:16:55.662258+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:16:55.662258+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "Yy52VOrEDQC5snhFBdJ9wA==" + }, + "exampleSelector" : "exampleCoordinatesWriting", + "previewHeight" : 200, + "previewShowSelector" : "gtViewsFor:", + "exampleBehaviorName" : "NeoJSONObject class", + "codeExpanded" : true, + "previewExpanded" : false, + "noCode" : false + }, + { + "__type" : "exampleSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:17:12.624073+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:17:12.624073+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "wv94VerEDQC5uU/RBdJ9wA==" + }, + "exampleSelector" : "exampleCoordinatesParsing", + "previewHeight" : 200, + "previewShowSelector" : "gtViewsFor:", + "exampleBehaviorName" : "NeoJSONObject class", + "codeExpanded" : true, + "previewExpanded" : false, + "noCode" : false } ] }, diff --git a/lepiter/81brlbrknhsro4cxzdl06l22t.lepiter b/lepiter/81brlbrknhsro4cxzdl06l22t.lepiter index 3d76944..0ed6103 100644 --- a/lepiter/81brlbrknhsro4cxzdl06l22t.lepiter +++ b/lepiter/81brlbrknhsro4cxzdl06l22t.lepiter @@ -78,6 +78,576 @@ }, "string" : "NeoJSON is an elegant and efficient standalone Smalltalk framework to read and write JSON converting to or from Smalltalk objects." }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T11:58:50.079586+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T11:59:38.00409+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "7dQtPenEDQCwkkjwCLMSBQ==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "# Arrays & Dictionaries" + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T11:59:44.369072+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:06:19.904615+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "BEJqQOnEDQCxjPmCCLMSBQ==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "JSON is defined using a number of primitive types (numbers, strings, booleans and null) and two composite types (lists and maps). Maps consist of unordered key value pairs and are sometimes called objects. Lists contain an ordered collection of JSON values. The natural or generic mapping of these two concepts is to {{gtClass:Array}} and {{gtClass:Dictionary}}. This is what {{gtClass:NeoJSONReader}} does out of the box." + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:04:56.100214+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:06:41.24643+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "cOT+UunEDQC6HlPJCLMSBQ==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "Let's consider some JSON input." + }, + { + "__type" : "exampleSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:06:49.982516+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:06:49.982516+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "1JnIWenEDQC8L1vZCLMSBQ==" + }, + "exampleSelector" : "exampleCoordinatesJSON", + "previewHeight" : 200, + "previewShowSelector" : "gtStringFor:", + "exampleBehaviorName" : "NeoJSONReader class", + "codeExpanded" : true, + "previewExpanded" : false, + "noCode" : false + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:08:10.942323+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:08:49.896313+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "W7XlXenEDQC8h3syCLMSBQ==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "Here is how to use {{gtClass:NeoJSONReader}} to parse this JSON input." + }, + { + "__type" : "exampleSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:08:58.808255+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:08:58.808255+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "1VN2YenEDQC+SF0qCLMSBQ==" + }, + "exampleSelector" : "exampleCoordinatesGenericParsing", + "previewHeight" : 200, + "previewShowSelector" : "gtViewsFor:", + "exampleBehaviorName" : "NeoJSONReader class", + "codeExpanded" : true, + "previewExpanded" : false, + "noCode" : false + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:09:56.333014+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:10:36.168612+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "3BTkZOnEDQC+rIHICLMSBQ==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "The resulting data structure is an array of dictionaries." + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:11:20.602757+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:23:52.709532+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "I+/paenEDQCAHWklCLMSBQ==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "Generating JSON is done using {{gtClass:NeoJSONWriter}} with this data structure as input. Actually, many collections are considered as lists except those that are explicitly seen as maps because they contain key value pairs. " + }, + { + "__type" : "exampleSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:13:27.745059+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:13:27.745059+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "afp9cenEDQCFexvvCLMSBQ==" + }, + "exampleSelector" : "exampleCoordinatesGenericWriting", + "previewHeight" : 200, + "previewShowSelector" : "gtStringFor:", + "exampleBehaviorName" : "NeoJSONWriter class", + "codeExpanded" : true, + "previewExpanded" : false, + "noCode" : false + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:16:38.934273+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:16:45.257142+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "5kjjfOnEDQCFy427CLMSBQ==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "# Mapping" + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T12:16:47.512544+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:03:04.233496+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "ADJmfenEDQCF9BZpCLMSBQ==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "JSON is fully dynamic and does not contain any type or class information. However, users do place meaning on certain JSON constructs. In our coordinates example we can all see that this is a list of x y coordinates, although this is not explicitly defined. So we might be inclined to use {{gtClass:Point}} here. Mapping allows you to make some use of the implicit schema present in JSON, either during parsing or during writing." + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:03:13.264218+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:04:58.868156+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "kWFxI+rEDQCvbdhdBdJ9wA==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "For parsing we need to tell the reader about the domain object that we want to use. And although we could have used {{gtMethod:NeoJSONReader>>#nextListAs:}} we defined and used a virtual type, ArrayOfPoints. " + }, + { + "__type" : "exampleSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:01:50.942757+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:01:50.942757+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "jUGJHurEDQCu8xlxBdJ9wA==" + }, + "exampleSelector" : "exampleCoordinatesCustomParsing", + "previewHeight" : 200, + "previewShowSelector" : "gtViewsFor:", + "exampleBehaviorName" : "NeoJSONReader class", + "codeExpanded" : true, + "previewExpanded" : false, + "noCode" : false + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:05:40.597846+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:09:44.12187+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "04M5LOrEDQCz5dG4BdJ9wA==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "For writing, we only need to map Point. Without a mapping, the writer would fail on Point since it does not know how to turn points into JSON." + }, + { + "__type" : "exampleSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:06:22.54966+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:06:22.54966+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "Dai5LurEDQC1aiNMBdJ9wA==" + }, + "exampleSelector" : "exampleCoordinatesCustomWriting", + "previewHeight" : 200, + "previewShowSelector" : "gtViewsFor:", + "exampleBehaviorName" : "NeoJSONWriter class", + "codeExpanded" : true, + "previewExpanded" : false, + "noCode" : false + }, { "__type" : "textSnippet", "children" : { @@ -103,7 +673,7 @@ "__type" : "time", "time" : { "__type" : "dateAndTime", - "dateAndTimeString" : "2023-10-23T15:00:55.457512+02:00" + "dateAndTimeString" : "2023-10-25T12:16:52.770243+02:00" } }, "uid" : { @@ -115,6 +685,43 @@ }, "string" : "# NeoJSONObject" }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:26:33.484917+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:26:33.484917+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "aA/ndurEDQC7ZHW+BdJ9wA==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "Another option is to use {{gtClass:NeoJSONObject}} and {{gtClass:NeoJSONArray}}. These are then used as mapClass and listClass instead of Dictionary and Array. " + }, { "__type" : "textSnippet", "children" : { @@ -140,7 +747,7 @@ "__type" : "time", "time" : { "__type" : "dateAndTime", - "dateAndTimeString" : "2023-10-23T14:53:01.507768+02:00" + "dateAndTimeString" : "2023-10-25T13:26:33.48926+02:00" } }, "uid" : { @@ -499,6 +1106,123 @@ "codeExpanded" : true, "previewExpanded" : false, "noCode" : false + }, + { + "__type" : "textSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:15:58.018722+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:16:34.590223+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "upYGUerEDQC3uiMoBdJ9wA==" + }, + "paragraphStyle" : { + "__type" : "textStyle" + }, + "string" : "The next two examples show how to work with the coordinates example." + }, + { + "__type" : "exampleSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:16:55.662258+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:16:55.662258+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "Yy52VOrEDQC5snhFBdJ9wA==" + }, + "exampleSelector" : "exampleCoordinatesWriting", + "previewHeight" : 200, + "previewShowSelector" : "gtViewsFor:", + "exampleBehaviorName" : "NeoJSONObject class", + "codeExpanded" : true, + "previewExpanded" : false, + "noCode" : false + }, + { + "__type" : "exampleSnippet", + "children" : { + "__type" : "snippets", + "items" : [ ] + }, + "createEmail" : { + "__type" : "email", + "emailString" : "" + }, + "createTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:17:12.624073+02:00" + } + }, + "editEmail" : { + "__type" : "email", + "emailString" : "" + }, + "editTime" : { + "__type" : "time", + "time" : { + "__type" : "dateAndTime", + "dateAndTimeString" : "2023-10-25T13:17:12.624073+02:00" + } + }, + "uid" : { + "__type" : "uid", + "uidString" : "wv94VerEDQC5uU/RBdJ9wA==" + }, + "exampleSelector" : "exampleCoordinatesParsing", + "previewHeight" : 200, + "previewShowSelector" : "gtViewsFor:", + "exampleBehaviorName" : "NeoJSONObject class", + "codeExpanded" : true, + "previewExpanded" : false, + "noCode" : false } ] }, diff --git a/repository/Neo-JSON-Core/NeoJSONObject.class.st b/repository/Neo-JSON-Core/NeoJSONObject.class.st index d5da387..99254fe 100644 --- a/repository/Neo-JSON-Core/NeoJSONObject.class.st +++ b/repository/Neo-JSON-Core/NeoJSONObject.class.st @@ -45,6 +45,29 @@ Class { #category : #'Neo-JSON-Core' } +{ #category : #example } +NeoJSONObject class >> exampleCoordinates [ + + ^ (0 to: 4) + collect: [ :each | self new x: each; y: each * 2 ] + as: NeoJSONArray +] + +{ #category : #example } +NeoJSONObject class >> exampleCoordinatesParsing [ + + | result | + result := self fromString: NeoJSONReader exampleCoordinatesJSON. + self assert: result equals: self exampleCoordinates. + ^ result +] + +{ #category : #example } +NeoJSONObject class >> exampleCoordinatesWriting [ + + ^ self exampleCoordinates printString +] + { #category : #example } NeoJSONObject class >> exampleMagnitudeClassHierarchy [ diff --git a/repository/Neo-JSON-Core/NeoJSONReader.class.st b/repository/Neo-JSON-Core/NeoJSONReader.class.st index 5666cf2..24c83ff 100644 --- a/repository/Neo-JSON-Core/NeoJSONReader.class.st +++ b/repository/Neo-JSON-Core/NeoJSONReader.class.st @@ -42,6 +42,29 @@ Class { #category : #'Neo-JSON-Core' } +{ #category : #example } +NeoJSONReader class >> exampleCoordinatesCustomParsing [ + + | reader | + reader := self on: self exampleCoordinatesJSON readStream. + reader mapAllInstVarsFor: Point. + reader for: #ArrayOfPoints customDo: [ :mapping | + mapping listOfElementSchema: Point ]. + ^ reader nextAs: #ArrayOfPoints +] + +{ #category : #example } +NeoJSONReader class >> exampleCoordinatesGenericParsing [ + + ^ self fromString: self exampleCoordinatesJSON +] + +{ #category : #example } +NeoJSONReader class >> exampleCoordinatesJSON [ + + ^ '[{"x":0,"y":0},{"x":1,"y":2},{"x":2,"y":4},{"x":3,"y":6},{"x":4,"y":8}]' +] + { #category : #convenience } NeoJSONReader class >> fromString: string [ ^ (self on: string readStream) next diff --git a/repository/Neo-JSON-Core/NeoJSONWriter.class.st b/repository/Neo-JSON-Core/NeoJSONWriter.class.st index cbf6aa3..eb1c4c7 100644 --- a/repository/Neo-JSON-Core/NeoJSONWriter.class.st +++ b/repository/Neo-JSON-Core/NeoJSONWriter.class.st @@ -37,6 +37,34 @@ Class { #category : #'Neo-JSON-Core' } +{ #category : #example } +NeoJSONWriter class >> exampleCoordinates [ + + ^ { 0@0 . 1@2. 2@4. 3@6 . 4@8} +] + +{ #category : #example } +NeoJSONWriter class >> exampleCoordinatesCustomWriting [ + + ^ String streamContents: [ :out | + | writer | + writer := self on: out. + writer mapAllInstVarsFor: Point. + writer nextPut: self exampleCoordinates ] +] + +{ #category : #example } +NeoJSONWriter class >> exampleCoordinatesGeneric [ + + ^ (0 to: 4) collect: [ :each | { 'x' -> each . 'y' -> (each * 2) } asDictionary ] +] + +{ #category : #example } +NeoJSONWriter class >> exampleCoordinatesGenericWriting [ + + ^ self toString: self exampleCoordinatesGeneric +] + { #category : #'instance creation' } NeoJSONWriter class >> on: writeStream [ "Initialize on writeStream, which should be a character stream that