manyfest 1.0.1 → 1.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.config/configstore/update-notifier-npm.json +1 -1
- package/README.md +336 -10
- package/examples/chocula/Chocula.js +8 -0
- package/examples/chocula/Data-Archive-org-Frankenberry.json +246 -0
- package/examples/chocula/Schema-Archive-org-Item.json +47 -0
- package/package.json +2 -2
- package/source/Manyfest.js +145 -2
- package/test/Data-Archive-org-Frankenberry.json +246 -0
- package/test/Data-Yahoo-Weather.json +115 -0
- package/test/Manyfest_AdvancedObjectAccess_tests.js +80 -0
- package/test/Manyfest_ObjectAccess_tests.js +144 -0
- package/test/Manyfest_tests.js +2 -116
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
{
|
|
2
|
+
"Scope": "Archive.org",
|
|
3
|
+
"Descriptors": {
|
|
4
|
+
"d1": {
|
|
5
|
+
"Hash": "Server",
|
|
6
|
+
"Name": "Server",
|
|
7
|
+
"Description": "The primary server to download these files from.",
|
|
8
|
+
"DataType": "String"
|
|
9
|
+
},
|
|
10
|
+
"d2": {
|
|
11
|
+
"Hash": "ServerAlternate",
|
|
12
|
+
"Name": "Alternate Server",
|
|
13
|
+
"Description": "The alternate server to download these files from.",
|
|
14
|
+
"DataType": "String"
|
|
15
|
+
},
|
|
16
|
+
"dir": {
|
|
17
|
+
"Hash": "Path",
|
|
18
|
+
"Name": "Server URL Path",
|
|
19
|
+
"NameShort": "Path",
|
|
20
|
+
"Description": "The path on the server where these files are located."
|
|
21
|
+
},
|
|
22
|
+
"metadata.identifier": {
|
|
23
|
+
"Hash": "GUID",
|
|
24
|
+
"Name": "Globally Unique Identifier",
|
|
25
|
+
"NameShort": "GUID",
|
|
26
|
+
"Description": "Archive.org unique identifier string."
|
|
27
|
+
},
|
|
28
|
+
"metadata.title": {
|
|
29
|
+
"Hash": "Title",
|
|
30
|
+
"Name": "Title",
|
|
31
|
+
"NameShort": "Title",
|
|
32
|
+
"Description": "The title of the media item."
|
|
33
|
+
},
|
|
34
|
+
"metadata.creator": {
|
|
35
|
+
"Hash": "Creator",
|
|
36
|
+
"Name": "Creator",
|
|
37
|
+
"NameShort": "Creator",
|
|
38
|
+
"Description": "The creator of the media item."
|
|
39
|
+
},
|
|
40
|
+
"metadata.mediatype": {
|
|
41
|
+
"Hash": "Type",
|
|
42
|
+
"Name": "Media Type",
|
|
43
|
+
"NameShort": "Type",
|
|
44
|
+
"Description": "The type of media item."
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
}
|
package/package.json
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "manyfest",
|
|
3
|
-
"version": "1.0.
|
|
3
|
+
"version": "1.0.2",
|
|
4
4
|
"description": "JSON Object Manifest for Data Description and Parsing",
|
|
5
|
-
"main": "
|
|
5
|
+
"main": "source/Manyfest.js",
|
|
6
6
|
"scripts": {
|
|
7
7
|
"docker-dev-build-image": "docker build ./ -f Dockerfile_LUXURYCode -t retold/manyfest:local",
|
|
8
8
|
"docker-dev-run": "docker run -it -d --name manyfest -p 12340:8080 -v \"$PWD/.config:/home/coder/.config\" -v \"$PWD:/home/coder/manyfest\" -u \"$(id -u):$(id -g)\" -e \"DOCKER_USER=$USER\" retold/manyfest:local",
|
package/source/Manyfest.js
CHANGED
|
@@ -189,6 +189,19 @@ class Manyfest
|
|
|
189
189
|
}
|
|
190
190
|
}
|
|
191
191
|
|
|
192
|
+
|
|
193
|
+
cleanWrapCharacters (pCharacter, pString)
|
|
194
|
+
{
|
|
195
|
+
if (pString.startsWith(pCharacter) && pString.endsWith(pCharacter))
|
|
196
|
+
{
|
|
197
|
+
return pString.substring(1, pString.length - 1);
|
|
198
|
+
}
|
|
199
|
+
else
|
|
200
|
+
{
|
|
201
|
+
return pString;
|
|
202
|
+
}
|
|
203
|
+
}
|
|
204
|
+
|
|
192
205
|
// Get the value of an element at an address
|
|
193
206
|
getValueAtAddress (pObject, pAddress)
|
|
194
207
|
{
|
|
@@ -197,18 +210,148 @@ class Manyfest
|
|
|
197
210
|
// Make sure pAddress is a string
|
|
198
211
|
if (!typeof(pAddress) === 'string') return undefined;
|
|
199
212
|
|
|
213
|
+
// TODO: Make this work for things like SomeRootObject.Metadata["Some.People.Use.Bad.Object.Property.Names"]
|
|
200
214
|
let tmpSeparatorIndex = pAddress.indexOf('.');
|
|
201
215
|
|
|
216
|
+
// This is the terminal address string (no more dots so the RECUSION ENDS IN HERE somehow)
|
|
202
217
|
if (tmpSeparatorIndex === -1)
|
|
203
218
|
{
|
|
204
|
-
//
|
|
205
|
-
|
|
219
|
+
// Check if it's a boxed property
|
|
220
|
+
let tmpBracketStartIndex = pAddress.indexOf('[');
|
|
221
|
+
let tmpBracketStopIndex = pAddress.indexOf(']');
|
|
222
|
+
// Boxed elements look like this:
|
|
223
|
+
// MyValues[10]
|
|
224
|
+
// MyValues['Name']
|
|
225
|
+
// MyValues["Age"]
|
|
226
|
+
// MyValues[`Cost`]
|
|
227
|
+
//
|
|
228
|
+
// When we are passed SomeObject["Name"] this code below recurses as if it were SomeObject.Name
|
|
229
|
+
// The requirements to detect a boxed element are:
|
|
230
|
+
// 1) The start bracket is after character 0
|
|
231
|
+
if ((tmpBracketStartIndex > 0)
|
|
232
|
+
// 2) The end bracket has something between them
|
|
233
|
+
&& (tmpBracketStopIndex > tmpBracketStartIndex)
|
|
234
|
+
// 3) There is data
|
|
235
|
+
&& (tmpBracketStopIndex - tmpBracketStartIndex > 0))
|
|
236
|
+
{
|
|
237
|
+
// The "Name" of the Object contained too the left of the bracket
|
|
238
|
+
let tmpBoxedPropertyName = pAddress.substring(0, tmpBracketStartIndex).trim();
|
|
239
|
+
|
|
240
|
+
// If the subproperty doesn't test as a proper Object, none of the rest of this is possible.
|
|
241
|
+
// This is a rare case where Arrays testing as Objects is useful
|
|
242
|
+
if (typeof(pObject[tmpBoxedPropertyName]) !== 'object')
|
|
243
|
+
{
|
|
244
|
+
return undefined;
|
|
245
|
+
}
|
|
246
|
+
|
|
247
|
+
// The "Reference" to the property within it, either an array element or object property
|
|
248
|
+
let tmpBoxedPropertyReference = pAddress.substring(tmpBracketStartIndex+1, tmpBracketStopIndex).trim();
|
|
249
|
+
// Attempt to parse the reference as a number, which will be used as an array element
|
|
250
|
+
let tmpBoxedPropertyNumber = parseInt(tmpBoxedPropertyReference, 10);
|
|
251
|
+
|
|
252
|
+
// Guard: If the referrant is a number and the boxed property is not an array, or vice versa, return undefined.
|
|
253
|
+
// This seems confusing to me at first read, so explaination:
|
|
254
|
+
// Is the Boxed Object an Array? TRUE
|
|
255
|
+
// And is the Reference inside the boxed Object not a number? TRUE
|
|
256
|
+
// --> So when these are in agreement, it's an impossible access state
|
|
257
|
+
if (Array.isArray(pObject[tmpBoxedPropertyName]) == isNaN(tmpBoxedPropertyNumber))
|
|
258
|
+
{
|
|
259
|
+
return undefined;
|
|
260
|
+
}
|
|
261
|
+
|
|
262
|
+
// 4) If the middle part is *only* a number (no single, double or backtick quotes) it is an array element,
|
|
263
|
+
// otherwise we will try to treat it as a dynamic object property.
|
|
264
|
+
if (isNaN(tmpBoxedPropertyNumber))
|
|
265
|
+
{
|
|
266
|
+
// This isn't a number ... let's treat it as a dynamic object property.
|
|
267
|
+
// We would expect the property to be wrapped in some kind of quotes so strip them
|
|
268
|
+
tmpBoxedPropertyReference = this.cleanWrapCharacters('"', tmpBoxedPropertyReference);
|
|
269
|
+
tmpBoxedPropertyReference = this.cleanWrapCharacters('`', tmpBoxedPropertyReference);
|
|
270
|
+
tmpBoxedPropertyReference = this.cleanWrapCharacters("'", tmpBoxedPropertyReference);
|
|
271
|
+
|
|
272
|
+
// Return the value in the property
|
|
273
|
+
return pObject[tmpBoxedPropertyName][tmpBoxedPropertyReference];
|
|
274
|
+
}
|
|
275
|
+
else
|
|
276
|
+
{
|
|
277
|
+
return pObject[tmpBoxedPropertyName][tmpBoxedPropertyNumber];
|
|
278
|
+
}
|
|
279
|
+
}
|
|
280
|
+
else
|
|
281
|
+
{
|
|
282
|
+
// Now is the point in recursion to return the value in the address
|
|
283
|
+
return pObject[pAddress];
|
|
284
|
+
}
|
|
206
285
|
}
|
|
207
286
|
else
|
|
208
287
|
{
|
|
209
288
|
let tmpSubObjectName = pAddress.substring(0, tmpSeparatorIndex);
|
|
210
289
|
let tmpNewAddress = pAddress.substring(tmpSeparatorIndex+1);
|
|
211
290
|
|
|
291
|
+
// Test if the tmpNewAddress is an array or object
|
|
292
|
+
// Check if it's a boxed property
|
|
293
|
+
let tmpBracketStartIndex = tmpSubObjectName.indexOf('[');
|
|
294
|
+
let tmpBracketStopIndex = tmpSubObjectName.indexOf(']');
|
|
295
|
+
// Boxed elements look like this:
|
|
296
|
+
// MyValues[42]
|
|
297
|
+
// MyValues['Color']
|
|
298
|
+
// MyValues["Weight"]
|
|
299
|
+
// MyValues[`Diameter`]
|
|
300
|
+
//
|
|
301
|
+
// When we are passed SomeObject["Name"] this code below recurses as if it were SomeObject.Name
|
|
302
|
+
// The requirements to detect a boxed element are:
|
|
303
|
+
// 1) The start bracket is after character 0
|
|
304
|
+
if ((tmpBracketStartIndex > 0)
|
|
305
|
+
// 2) The end bracket has something between them
|
|
306
|
+
&& (tmpBracketStopIndex > tmpBracketStartIndex)
|
|
307
|
+
// 3) There is data
|
|
308
|
+
&& (tmpBracketStopIndex - tmpBracketStartIndex > 0))
|
|
309
|
+
{
|
|
310
|
+
let tmpBoxedPropertyName = tmpSubObjectName.substring(0, tmpBracketStartIndex).trim();
|
|
311
|
+
|
|
312
|
+
let tmpBoxedPropertyReference = tmpSubObjectName.substring(tmpBracketStartIndex+1, tmpBracketStopIndex).trim();
|
|
313
|
+
|
|
314
|
+
let tmpBoxedPropertyNumber = parseInt(tmpBoxedPropertyReference, 10);
|
|
315
|
+
|
|
316
|
+
// Guard: If the referrant is a number and the boxed property is not an array, or vice versa, return undefined.
|
|
317
|
+
// This seems confusing to me at first read, so explaination:
|
|
318
|
+
// Is the Boxed Object an Array? TRUE
|
|
319
|
+
// And is the Reference inside the boxed Object not a number? TRUE
|
|
320
|
+
// --> So when these are in agreement, it's an impossible access state
|
|
321
|
+
// This could be a failure in the recursion chain because they passed something like this in:
|
|
322
|
+
// StudentData.Sections.Algebra.Students[1].Tardy
|
|
323
|
+
// BUT
|
|
324
|
+
// StudentData.Sections.Algebra.Students[1] is an object, so the .Tardy is not possible to access
|
|
325
|
+
// This could be a failure in the recursion chain because they passed something like this in:
|
|
326
|
+
// StudentData.Sections.Algebra.Students["JaneDoe"].Grade
|
|
327
|
+
// BUT
|
|
328
|
+
// StudentData.Sections.Algebra.Students["JaneDoe"] is an array, so the .Grade is not possible to access
|
|
329
|
+
// TODO: Should this be an error or something? Should we keep a log of failures like this?
|
|
330
|
+
if (Array.isArray(pObject[tmpBoxedPropertyName]) == isNaN(tmpBoxedPropertyNumber))
|
|
331
|
+
{
|
|
332
|
+
return undefined;
|
|
333
|
+
}
|
|
334
|
+
|
|
335
|
+
//This is a bracketed value
|
|
336
|
+
// 4) If the middle part is *only* a number (no single, double or backtick quotes) it is an array element,
|
|
337
|
+
// otherwise we will try to reat it as a dynamic object property.
|
|
338
|
+
if (isNaN(tmpBoxedPropertyNumber))
|
|
339
|
+
{
|
|
340
|
+
// This isn't a number ... let's treat it as a dynanmic object property.
|
|
341
|
+
tmpBoxedPropertyReference = this.cleanWrapCharacters('"', tmpBoxedPropertyReference);
|
|
342
|
+
tmpBoxedPropertyReference = this.cleanWrapCharacters('`', tmpBoxedPropertyReference);
|
|
343
|
+
tmpBoxedPropertyReference = this.cleanWrapCharacters("'", tmpBoxedPropertyReference);
|
|
344
|
+
|
|
345
|
+
// Recurse directly into the subobject
|
|
346
|
+
return this.getValueAtAddress(pObject[tmpBoxedPropertyName][tmpBoxedPropertyReference], tmpNewAddress);
|
|
347
|
+
}
|
|
348
|
+
else
|
|
349
|
+
{
|
|
350
|
+
// We parsed a valid number out of the boxed property name, so recurse into the array
|
|
351
|
+
return this.getValueAtAddress(pObject[tmpBoxedPropertyName][tmpBoxedPropertyNumber], tmpNewAddress);
|
|
352
|
+
}
|
|
353
|
+
}
|
|
354
|
+
|
|
212
355
|
// If there is an object property already named for the sub object, but it isn't an object
|
|
213
356
|
// then the system can't set the value in there. Error and abort!
|
|
214
357
|
if (pObject.hasOwnProperty(tmpSubObjectName) && typeof(pObject[tmpSubObjectName]) !== 'object')
|
|
@@ -0,0 +1,246 @@
|
|
|
1
|
+
{
|
|
2
|
+
"created": 1664830085,
|
|
3
|
+
"d1": "ia600202.us.archive.org",
|
|
4
|
+
"d2": "ia800202.us.archive.org",
|
|
5
|
+
"dir": "/7/items/FrankenberryCountChoculaTevevisionCommercial1971",
|
|
6
|
+
"files": [
|
|
7
|
+
{
|
|
8
|
+
"name": "FrankenberryCountChoculaTevevisionCommercial1971.thumbs/frankerberry_countchockula_1971.0001_000001.jpg",
|
|
9
|
+
"source": "derivative",
|
|
10
|
+
"format": "Thumbnail",
|
|
11
|
+
"original": "frankerberry_countchockula_1971.0001.mpg",
|
|
12
|
+
"mtime": "1296336956",
|
|
13
|
+
"size": "838",
|
|
14
|
+
"md5": "e47269cd5a82db9594f265a65785ec12",
|
|
15
|
+
"crc32": "165c668b",
|
|
16
|
+
"sha1": "383303d9546c381267569ad4e33aff691f0bb8c7"
|
|
17
|
+
},
|
|
18
|
+
{
|
|
19
|
+
"name": "FrankenberryCountChoculaTevevisionCommercial1971.thumbs/frankerberry_countchockula_1971.0001_000004.jpg",
|
|
20
|
+
"source": "derivative",
|
|
21
|
+
"format": "Thumbnail",
|
|
22
|
+
"original": "frankerberry_countchockula_1971.0001.mpg",
|
|
23
|
+
"mtime": "1296336957",
|
|
24
|
+
"size": "6843",
|
|
25
|
+
"md5": "c93fa52000ab4665e69b25c403e11aff",
|
|
26
|
+
"crc32": "9444e6f6",
|
|
27
|
+
"sha1": "716b4f9950b8147f51d3265f9c62ff86451308d5"
|
|
28
|
+
},
|
|
29
|
+
{
|
|
30
|
+
"name": "FrankenberryCountChoculaTevevisionCommercial1971.thumbs/frankerberry_countchockula_1971.0001_000009.jpg",
|
|
31
|
+
"source": "derivative",
|
|
32
|
+
"format": "Thumbnail",
|
|
33
|
+
"original": "frankerberry_countchockula_1971.0001.mpg",
|
|
34
|
+
"mtime": "1296336957",
|
|
35
|
+
"size": "8388",
|
|
36
|
+
"md5": "30eb3eb4cbbdfa08d531a0a74da7c000",
|
|
37
|
+
"crc32": "be874a9e",
|
|
38
|
+
"sha1": "0c392d777609e967b6022be27edad678c5ae74e2"
|
|
39
|
+
},
|
|
40
|
+
{
|
|
41
|
+
"name": "FrankenberryCountChoculaTevevisionCommercial1971.thumbs/frankerberry_countchockula_1971.0001_000014.jpg",
|
|
42
|
+
"source": "derivative",
|
|
43
|
+
"format": "Thumbnail",
|
|
44
|
+
"original": "frankerberry_countchockula_1971.0001.mpg",
|
|
45
|
+
"mtime": "1296336958",
|
|
46
|
+
"size": "5993",
|
|
47
|
+
"md5": "4e9ebc3d076bec8cf7dfe76795f8c769",
|
|
48
|
+
"crc32": "912ec98c",
|
|
49
|
+
"sha1": "01dc49c852e1bbb421199450dd902935c62b06de"
|
|
50
|
+
},
|
|
51
|
+
{
|
|
52
|
+
"name": "FrankenberryCountChoculaTevevisionCommercial1971.thumbs/frankerberry_countchockula_1971.0001_000019.jpg",
|
|
53
|
+
"source": "derivative",
|
|
54
|
+
"format": "Thumbnail",
|
|
55
|
+
"original": "frankerberry_countchockula_1971.0001.mpg",
|
|
56
|
+
"mtime": "1296336958",
|
|
57
|
+
"size": "4951",
|
|
58
|
+
"md5": "59f190f0c5b0a048415b26412860b6dd",
|
|
59
|
+
"crc32": "a70a30b1",
|
|
60
|
+
"sha1": "a284af9757cb24d28f96ec88ec1b1c23a8cea9fe"
|
|
61
|
+
},
|
|
62
|
+
{
|
|
63
|
+
"name": "FrankenberryCountChoculaTevevisionCommercial1971.thumbs/frankerberry_countchockula_1971.0001_000024.jpg",
|
|
64
|
+
"source": "derivative",
|
|
65
|
+
"format": "Thumbnail",
|
|
66
|
+
"original": "frankerberry_countchockula_1971.0001.mpg",
|
|
67
|
+
"mtime": "1296336959",
|
|
68
|
+
"size": "3383",
|
|
69
|
+
"md5": "be2a908acd563b896e7758b598295148",
|
|
70
|
+
"crc32": "ed467831",
|
|
71
|
+
"sha1": "94c001e72ebc86d837a78c61a004db9ab9d597bd"
|
|
72
|
+
},
|
|
73
|
+
{
|
|
74
|
+
"name": "FrankenberryCountChoculaTevevisionCommercial1971.thumbs/frankerberry_countchockula_1971.0001_000029.jpg",
|
|
75
|
+
"source": "derivative",
|
|
76
|
+
"format": "Thumbnail",
|
|
77
|
+
"original": "frankerberry_countchockula_1971.0001.mpg",
|
|
78
|
+
"mtime": "1296336960",
|
|
79
|
+
"size": "3503",
|
|
80
|
+
"md5": "c82199d09be07633000fd07b363dd8a3",
|
|
81
|
+
"crc32": "a1fd79cb",
|
|
82
|
+
"sha1": "2bc8e761edb24a441fa5906dda1c424e1f98a47a"
|
|
83
|
+
},
|
|
84
|
+
{
|
|
85
|
+
"name": "FrankenberryCountChoculaTevevisionCommercial1971_archive.torrent",
|
|
86
|
+
"source": "metadata",
|
|
87
|
+
"btih": "de6b371e7cc3c83db1cc08150500753eae533409",
|
|
88
|
+
"mtime": "1542761794",
|
|
89
|
+
"size": "4093",
|
|
90
|
+
"md5": "a275d3b4028cccb5bea8b47a88c838af",
|
|
91
|
+
"crc32": "5ffa7334",
|
|
92
|
+
"sha1": "af8222637b574cba1360d0ea77e231640ffd43c4",
|
|
93
|
+
"format": "Archive BitTorrent"
|
|
94
|
+
},
|
|
95
|
+
{
|
|
96
|
+
"name": "FrankenberryCountChoculaTevevisionCommercial1971_files.xml",
|
|
97
|
+
"source": "metadata",
|
|
98
|
+
"format": "Metadata",
|
|
99
|
+
"md5": "3a7e87b08bed1e203a5858b31352c110"
|
|
100
|
+
},
|
|
101
|
+
{
|
|
102
|
+
"name": "FrankenberryCountChoculaTevevisionCommercial1971_meta.xml",
|
|
103
|
+
"source": "metadata",
|
|
104
|
+
"format": "Metadata",
|
|
105
|
+
"mtime": "1542761793",
|
|
106
|
+
"size": "1371",
|
|
107
|
+
"md5": "0b9c9bf21b9a26aea43a2f735b404624",
|
|
108
|
+
"crc32": "41077288",
|
|
109
|
+
"sha1": "22e6f2c73bf63072f671d846355da2785db51dbd"
|
|
110
|
+
},
|
|
111
|
+
{
|
|
112
|
+
"name": "FrankenberryCountChoculaTevevisionCommercial1971_reviews.xml",
|
|
113
|
+
"source": "original",
|
|
114
|
+
"mtime": "1466898697",
|
|
115
|
+
"size": "620",
|
|
116
|
+
"md5": "260bfba5d696772445dcc7ff6e6d5bdb",
|
|
117
|
+
"crc32": "25ea3229",
|
|
118
|
+
"sha1": "7d541f18fcd5ad9c6e593afe5a80f18771f23b32",
|
|
119
|
+
"format": "Metadata"
|
|
120
|
+
},
|
|
121
|
+
{
|
|
122
|
+
"name": "__ia_thumb.jpg",
|
|
123
|
+
"source": "original",
|
|
124
|
+
"mtime": "1539115881",
|
|
125
|
+
"size": "7481",
|
|
126
|
+
"md5": "8cec324fa0016fd77cc04e6a4b2ebb00",
|
|
127
|
+
"crc32": "d9e1b316",
|
|
128
|
+
"sha1": "4dab42952fe0405a3b7f80146636b33d7b1bd01e",
|
|
129
|
+
"format": "Item Tile",
|
|
130
|
+
"rotation": "0"
|
|
131
|
+
},
|
|
132
|
+
{
|
|
133
|
+
"name": "frankerberry_countchockula_1971.0001.gif",
|
|
134
|
+
"source": "derivative",
|
|
135
|
+
"format": "Animated GIF",
|
|
136
|
+
"original": "frankerberry_countchockula_1971.0001.mpg",
|
|
137
|
+
"mtime": "1296336965",
|
|
138
|
+
"size": "101114",
|
|
139
|
+
"md5": "b78a13094030f104900eb996bafe2b7d",
|
|
140
|
+
"crc32": "6650cd8",
|
|
141
|
+
"sha1": "669798c037205cac14f70592deef6f7831b3d4a1"
|
|
142
|
+
},
|
|
143
|
+
{
|
|
144
|
+
"name": "frankerberry_countchockula_1971.0001.mpg",
|
|
145
|
+
"source": "original",
|
|
146
|
+
"format": "MPEG2",
|
|
147
|
+
"mtime": "1296335803",
|
|
148
|
+
"size": "31625216",
|
|
149
|
+
"md5": "762ba18b026b85b3f074523e7fcb4db0",
|
|
150
|
+
"crc32": "42347f78",
|
|
151
|
+
"sha1": "41162dc2d1a91b618124c84628d0c231544a02be",
|
|
152
|
+
"length": "31.14",
|
|
153
|
+
"height": "480",
|
|
154
|
+
"width": "640"
|
|
155
|
+
},
|
|
156
|
+
{
|
|
157
|
+
"name": "frankerberry_countchockula_1971.0001.mpg.idx",
|
|
158
|
+
"source": "derivative",
|
|
159
|
+
"format": "Video Index",
|
|
160
|
+
"original": "frankerberry_countchockula_1971.0001.mpg",
|
|
161
|
+
"mtime": "1296336956",
|
|
162
|
+
"size": "31141",
|
|
163
|
+
"md5": "49423e072726e4ea3cdd8ebdd26c7dfc",
|
|
164
|
+
"crc32": "ae969a68",
|
|
165
|
+
"sha1": "805782cd2d0f9002555816daadf3b8607e621f79"
|
|
166
|
+
},
|
|
167
|
+
{
|
|
168
|
+
"name": "frankerberry_countchockula_1971.0001.ogv",
|
|
169
|
+
"source": "derivative",
|
|
170
|
+
"format": "Ogg Video",
|
|
171
|
+
"original": "frankerberry_countchockula_1971.0001.mpg",
|
|
172
|
+
"mtime": "1296336994",
|
|
173
|
+
"size": "2248166",
|
|
174
|
+
"md5": "f1b933e97ce63594fb28a0a019ff3436",
|
|
175
|
+
"crc32": "a2a0e5e9",
|
|
176
|
+
"sha1": "a6bf0aec9f006baeca37c03f586686ebe685d59b",
|
|
177
|
+
"length": "31.15",
|
|
178
|
+
"height": "300",
|
|
179
|
+
"width": "400"
|
|
180
|
+
},
|
|
181
|
+
{
|
|
182
|
+
"name": "frankerberry_countchockula_1971.0001_512kb.mp4",
|
|
183
|
+
"source": "derivative",
|
|
184
|
+
"format": "512Kb MPEG4",
|
|
185
|
+
"original": "frankerberry_countchockula_1971.0001.mpg",
|
|
186
|
+
"mtime": "1296336977",
|
|
187
|
+
"size": "2378677",
|
|
188
|
+
"md5": "a7750839519c61ba3bb99fc66b32011d",
|
|
189
|
+
"crc32": "4dbd37c8",
|
|
190
|
+
"sha1": "3929314c192dec006fac2739bcb4730788e8c068",
|
|
191
|
+
"length": "31.13",
|
|
192
|
+
"height": "240",
|
|
193
|
+
"width": "320"
|
|
194
|
+
}
|
|
195
|
+
],
|
|
196
|
+
"files_count": 17,
|
|
197
|
+
"item_last_updated": 1542761794,
|
|
198
|
+
"item_size": 36431778,
|
|
199
|
+
"metadata": {
|
|
200
|
+
"identifier": "FrankenberryCountChoculaTevevisionCommercial1971",
|
|
201
|
+
"title": "Franken Berry / Count Chocula : Tevevision Commercial 1971",
|
|
202
|
+
"creator": "General Mills",
|
|
203
|
+
"mediatype": "movies",
|
|
204
|
+
"collection": [
|
|
205
|
+
"classic_tv_commercials",
|
|
206
|
+
"television"
|
|
207
|
+
],
|
|
208
|
+
"description": "Count Chocula and Franken Berry were both introduced in 1971. Boo Berry Cereal appeared in 1973 followed by Fruit Brute in 1974. Yummy Mummy appeared more than a decade later in 1988 - completing the the group known as the General Mills Monster Cereals.",
|
|
209
|
+
"subject": "Third Eye Cinema; Classic Television Commercials; animation; cartoons;General Mills",
|
|
210
|
+
"licenseurl": "http://creativecommons.org/publicdomain/mark/1.0/",
|
|
211
|
+
"publicdate": "2011-01-29 21:36:42",
|
|
212
|
+
"addeddate": "2011-01-29 21:35:38",
|
|
213
|
+
"uploader": "bolexman@msn.com",
|
|
214
|
+
"updater": [
|
|
215
|
+
"Bolexman",
|
|
216
|
+
"Bolexman",
|
|
217
|
+
"Jeff Kaplan"
|
|
218
|
+
],
|
|
219
|
+
"updatedate": [
|
|
220
|
+
"2011-01-29 21:45:38",
|
|
221
|
+
"2011-01-29 21:55:46",
|
|
222
|
+
"2011-01-29 23:04:55"
|
|
223
|
+
],
|
|
224
|
+
"sound": "sound",
|
|
225
|
+
"color": "color",
|
|
226
|
+
"runtime": "0:31",
|
|
227
|
+
"backup_location": "ia903608_22",
|
|
228
|
+
"ia_orig__runtime": "31 seconds"
|
|
229
|
+
},
|
|
230
|
+
"reviews": [
|
|
231
|
+
{
|
|
232
|
+
"reviewbody": "Sugar cereal cartoon Karloff and Lugosi argue self-importance pre Lorre ghost. Interesting how kids still know the voices without any idea of the origins.",
|
|
233
|
+
"reviewtitle": "pre booberry",
|
|
234
|
+
"reviewer": "outofthebox",
|
|
235
|
+
"reviewdate": "2016-06-25 23:51:36",
|
|
236
|
+
"createdate": "2016-06-25 23:51:36",
|
|
237
|
+
"stars": "4"
|
|
238
|
+
}
|
|
239
|
+
],
|
|
240
|
+
"server": "ia800202.us.archive.org",
|
|
241
|
+
"uniq": 1957612749,
|
|
242
|
+
"workable_servers": [
|
|
243
|
+
"ia800202.us.archive.org",
|
|
244
|
+
"ia600202.us.archive.org"
|
|
245
|
+
]
|
|
246
|
+
}
|
|
@@ -0,0 +1,115 @@
|
|
|
1
|
+
{
|
|
2
|
+
"location": {
|
|
3
|
+
"woeid": 2502265,
|
|
4
|
+
"city": "Sunnyvale",
|
|
5
|
+
"region": " CA",
|
|
6
|
+
"country": "United States",
|
|
7
|
+
"lat": 37.371609,
|
|
8
|
+
"long": -122.038254,
|
|
9
|
+
"timezone_id": "America/Los_Angeles"
|
|
10
|
+
},
|
|
11
|
+
"current_observation": {
|
|
12
|
+
"wind": {
|
|
13
|
+
"chill": 59,
|
|
14
|
+
"direction": 165,
|
|
15
|
+
"speed": 8.7
|
|
16
|
+
},
|
|
17
|
+
"atmosphere": {
|
|
18
|
+
"humidity": 76,
|
|
19
|
+
"visibility": 10,
|
|
20
|
+
"pressure": 29.68
|
|
21
|
+
},
|
|
22
|
+
"astronomy": {
|
|
23
|
+
"sunrise": "7:23 am",
|
|
24
|
+
"sunset": "5:7 pm"
|
|
25
|
+
},
|
|
26
|
+
"condition": {
|
|
27
|
+
"text": "Scattered Showers",
|
|
28
|
+
"code": 39,
|
|
29
|
+
"temperature": 60
|
|
30
|
+
},
|
|
31
|
+
"pubDate": 1546992000
|
|
32
|
+
},
|
|
33
|
+
"forecasts": [
|
|
34
|
+
{
|
|
35
|
+
"day": "Tue",
|
|
36
|
+
"date": 1546934400,
|
|
37
|
+
"low": 52,
|
|
38
|
+
"high": 61,
|
|
39
|
+
"text": "Rain",
|
|
40
|
+
"code": 12
|
|
41
|
+
},
|
|
42
|
+
{
|
|
43
|
+
"day": "Wed",
|
|
44
|
+
"date": 1547020800,
|
|
45
|
+
"low": 51,
|
|
46
|
+
"high": 62,
|
|
47
|
+
"text": "Scattered Showers",
|
|
48
|
+
"code": 39
|
|
49
|
+
},
|
|
50
|
+
{
|
|
51
|
+
"day": "Thu",
|
|
52
|
+
"date": 1547107200,
|
|
53
|
+
"low": 46,
|
|
54
|
+
"high": 60,
|
|
55
|
+
"text": "Mostly Cloudy",
|
|
56
|
+
"code": 28
|
|
57
|
+
},
|
|
58
|
+
{
|
|
59
|
+
"day": "Fri",
|
|
60
|
+
"date": 1547193600,
|
|
61
|
+
"low": 48,
|
|
62
|
+
"high": 61,
|
|
63
|
+
"text": "Showers",
|
|
64
|
+
"code": 11
|
|
65
|
+
},
|
|
66
|
+
{
|
|
67
|
+
"day": "Sat",
|
|
68
|
+
"date": 1547280000,
|
|
69
|
+
"low": 47,
|
|
70
|
+
"high": 62,
|
|
71
|
+
"text": "Rain",
|
|
72
|
+
"code": 12
|
|
73
|
+
},
|
|
74
|
+
{
|
|
75
|
+
"day": "Sun",
|
|
76
|
+
"date": 1547366400,
|
|
77
|
+
"low": 48,
|
|
78
|
+
"high": 58,
|
|
79
|
+
"text": "Rain",
|
|
80
|
+
"code": 12
|
|
81
|
+
},
|
|
82
|
+
{
|
|
83
|
+
"day": "Mon",
|
|
84
|
+
"date": 1547452800,
|
|
85
|
+
"low": 47,
|
|
86
|
+
"high": 58,
|
|
87
|
+
"text": "Rain",
|
|
88
|
+
"code": 12
|
|
89
|
+
},
|
|
90
|
+
{
|
|
91
|
+
"day": "Tue",
|
|
92
|
+
"date": 1547539200,
|
|
93
|
+
"low": 46,
|
|
94
|
+
"high": 59,
|
|
95
|
+
"text": "Scattered Showers",
|
|
96
|
+
"code": 39
|
|
97
|
+
},
|
|
98
|
+
{
|
|
99
|
+
"day": "Wed",
|
|
100
|
+
"date": 1547625600,
|
|
101
|
+
"low": 49,
|
|
102
|
+
"high": 56,
|
|
103
|
+
"text": "Rain",
|
|
104
|
+
"code": 12
|
|
105
|
+
},
|
|
106
|
+
{
|
|
107
|
+
"day": "Thu",
|
|
108
|
+
"date": 1547712000,
|
|
109
|
+
"low": 49,
|
|
110
|
+
"high": 59,
|
|
111
|
+
"text": "Scattered Showers",
|
|
112
|
+
"code": 39
|
|
113
|
+
}
|
|
114
|
+
]
|
|
115
|
+
}
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Unit tests for Meadow
|
|
3
|
+
*
|
|
4
|
+
* @license MIT
|
|
5
|
+
*
|
|
6
|
+
* @author Steven Velozo <steven@velozo.com>
|
|
7
|
+
*/
|
|
8
|
+
|
|
9
|
+
var Chai = require("chai");
|
|
10
|
+
var Expect = Chai.expect;
|
|
11
|
+
|
|
12
|
+
let libManyfest = require('../source/Manyfest.js');
|
|
13
|
+
|
|
14
|
+
let _SampleDataArchiveOrgFrankenberry = require('./Data-Archive-org-Frankenberry.json');
|
|
15
|
+
let _SampleDataWeather = require('./Data-Yahoo-Weather.json');
|
|
16
|
+
|
|
17
|
+
suite
|
|
18
|
+
(
|
|
19
|
+
'Advanced Object Access',
|
|
20
|
+
function()
|
|
21
|
+
{
|
|
22
|
+
setup (()=> {} );
|
|
23
|
+
|
|
24
|
+
suite
|
|
25
|
+
(
|
|
26
|
+
'Advanced Object Reading (with Arrays and Boxed Property addresses)',
|
|
27
|
+
()=>
|
|
28
|
+
{
|
|
29
|
+
test
|
|
30
|
+
(
|
|
31
|
+
'Access specific array elements',
|
|
32
|
+
(fTestComplete)=>
|
|
33
|
+
{
|
|
34
|
+
let _Manyfest = new libManyfest();
|
|
35
|
+
let tmpDog = _Manyfest.getValueAtAddress({Dogs:['Fido','Spot','Trinity']}, 'Dogs[1]');
|
|
36
|
+
Expect(tmpDog)
|
|
37
|
+
.to.equal('Spot');
|
|
38
|
+
fTestComplete();
|
|
39
|
+
}
|
|
40
|
+
);
|
|
41
|
+
test
|
|
42
|
+
(
|
|
43
|
+
'Access specific boxed properties',
|
|
44
|
+
(fTestComplete)=>
|
|
45
|
+
{
|
|
46
|
+
let _Manyfest = new libManyfest();
|
|
47
|
+
let tmpDog = _Manyfest.getValueAtAddress({Dogs:{RunnerUp:'Fido',Loser:'Spot',Winner:'Trinity'}}, 'Dogs["Winner"]');
|
|
48
|
+
Expect(tmpDog)
|
|
49
|
+
.to.equal('Trinity');
|
|
50
|
+
fTestComplete();
|
|
51
|
+
}
|
|
52
|
+
);
|
|
53
|
+
test
|
|
54
|
+
(
|
|
55
|
+
'Attempt to access specific boxed properties that do not exist',
|
|
56
|
+
(fTestComplete)=>
|
|
57
|
+
{
|
|
58
|
+
let _Manyfest = new libManyfest();
|
|
59
|
+
let tmpDog = _Manyfest.getValueAtAddress({Dogs:{RunnerUp:'Fido',Loser:'Spot',Winner:'Trinity'}}, 'Dogs["Disqualified"]');
|
|
60
|
+
Expect(tmpDog)
|
|
61
|
+
.to.be.an('undefined');
|
|
62
|
+
fTestComplete();
|
|
63
|
+
}
|
|
64
|
+
);
|
|
65
|
+
test
|
|
66
|
+
(
|
|
67
|
+
'Access nested box properties',
|
|
68
|
+
(fTestComplete)=>
|
|
69
|
+
{
|
|
70
|
+
let _Manyfest = new libManyfest();
|
|
71
|
+
let tmpDog = _Manyfest.getValueAtAddress({Dogs:{RunnerUp:{Name:'Fido',Speed:100},Loser:{Name:'Spot'},Winner:{Name:'Trinity'}}}, 'Dogs["RunnerUp"].Name');
|
|
72
|
+
Expect(tmpDog)
|
|
73
|
+
.to.equal('Fido');
|
|
74
|
+
fTestComplete();
|
|
75
|
+
}
|
|
76
|
+
);
|
|
77
|
+
}
|
|
78
|
+
)
|
|
79
|
+
}
|
|
80
|
+
);
|