Skip to content

Commit

Permalink
Change parseJson to perform type validation
Browse files Browse the repository at this point in the history
Adds a second argument to the `parseJson` function:
A TypeRep which the result from parsing the JSON is
validated against. This closes #150.
  • Loading branch information
Avaq committed Apr 12, 2016
1 parent a6b73d2 commit 30b3b7a
Show file tree
Hide file tree
Showing 2 changed files with 35 additions and 16 deletions.
20 changes: 12 additions & 8 deletions index.js
Original file line number Diff line number Diff line change
Expand Up @@ -2760,24 +2760,28 @@
)(s);
});

//# parseJson :: String -> Maybe Any
//# parseJson :: TypeRep a -> String -> Maybe a
//.
//. Takes a string which may or may not be valid JSON, and returns Just
//. the result of applying `JSON.parse` to the string if valid; Nothing
//. otherwise.
//. Takes a [type representative](#type-representatives) and a string which
//. may or may not be valid JSON, and returns Just the result of applying
//. `JSON.parse` to the string *if* the result is of the specified type
//. (according to [`is`](#is)); Nothing otherwise.
//.
//. ```javascript
//. > S.parseJson('["foo","bar","baz"]')
//. > S.parseJson(Array, '["foo","bar","baz"]')
//. Just(['foo', 'bar', 'baz'])
//.
//. > S.parseJson('[')
//. > S.parseJson(Array, '[')
//. Nothing()
//.
//. > S.parseJson(Object, '["foo","bar","baz"]')
//. Nothing()
//. ```
S.parseJson =
def('parseJson',
{},
[$.String, $Maybe($.Any)],
encase(JSON.parse));
[TypeRep, $.String, $Maybe(a)],
function(type, s) { return filter(is(type), encase(JSON.parse, s)); });

//. ### RegExp

Expand Down
31 changes: 23 additions & 8 deletions test/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -5125,31 +5125,46 @@ describe('parse', function() {

describe('parseJson', function() {

it('is a unary function', function() {
it('is a binary function', function() {
eq(typeof S.parseJson, 'function');
eq(S.parseJson.length, 1);
eq(S.parseJson.length, 2);
});

it('type checks its arguments', function() {
throws(function() { S.parseJson([1, 2, 3]); },
throws(function() { S.parseJson('String'); },
errorEq(TypeError,
'Invalid value\n' +
'\n' +
'parseJson :: String -> Maybe Any\n' +
' ^^^^^^\n' +
' 1\n' +
'parseJson :: TypeRep -> String -> Maybe a\n' +
' ^^^^^^^\n' +
' 1\n' +
'\n' +
'1) "String" :: String\n' +
'\n' +
'The value at position 1 is not a member of ‘TypeRep’.\n'));
throws(function() { S.parseJson(Array, [1, 2, 3]); },
errorEq(TypeError,
'Invalid value\n' +
'\n' +
'parseJson :: TypeRep -> String -> Maybe a\n' +
' ^^^^^^\n' +
' 1\n' +
'\n' +
'1) [1, 2, 3] :: Array Number, Array FiniteNumber, Array NonZeroFiniteNumber, Array Integer, Array ValidNumber\n' +
'\n' +
'The value at position 1 is not a member of ‘String’.\n'));
});

it('returns a Just when applied to a valid JSON string', function() {
eq(S.parseJson('["foo","bar"]'), S.Just(['foo', 'bar']));
eq(S.parseJson(Array, '["foo","bar"]'), S.Just(['foo', 'bar']));
});

it('returns a Nothing when applied to an invalid JSON string', function() {
eq(S.parseJson('[Invalid JSON]'), S.Nothing());
eq(S.parseJson(Object, '[Invalid JSON]'), S.Nothing());
});

it('returns a Nothing when the parsed result is not a member of the given type', function() {
eq(S.parseJson(Array, '{"foo":"bar"}'), S.Nothing());
});

});
Expand Down

0 comments on commit 30b3b7a

Please sign in to comment.