Skip to content

Commit

Permalink
Updates for 0.11 (#21)
Browse files Browse the repository at this point in the history
* Updates for 0.11

* Rename things, add docs

* Add NullOrUndefined, refactor module and function names

* Update README

* Remove old docs
  • Loading branch information
paf31 authored Apr 8, 2017
1 parent 6574592 commit ad0d657
Show file tree
Hide file tree
Showing 20 changed files with 554 additions and 142 deletions.
8 changes: 1 addition & 7 deletions .travis.yml
Original file line number Diff line number Diff line change
Expand Up @@ -2,17 +2,11 @@ language: node_js
dist: trusty
sudo: required
node_js: 6
env:
- PATH=$HOME/purescript:$PATH
install:
- TAG=$(wget -q -O - https://github.com/purescript/purescript/releases/latest --server-response --max-redirect 0 2>&1 | sed -n -e 's/.*Location:.*tag\///p')
- wget -O $HOME/purescript.tar.gz https://github.com/purescript/purescript/releases/download/$TAG/linux64.tar.gz
- tar -xvf $HOME/purescript.tar.gz -C $HOME/
- chmod a+x $HOME/purescript
- npm install -g bower
- npm install
script:
- bower install --production
- npm run -s build
- bower install
- npm -s test
- npm run -s test
44 changes: 44 additions & 0 deletions LICENSE
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
The MIT License (MIT)

Copyright (c) 2017 Phil Freeman

Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
the Software, and to permit persons to whom the Software is furnished to do so,
subject to the following conditions:

The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

purescript-foreign-generic uses code taken from the purescript-foreign library,
which is used under the terms of the MIT license, below:

The MIT License (MIT)

Copyright (c) 2014 PureScript

Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
the Software, and to permit persons to whom the Software is furnished to do so,
subject to the following conditions:

The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
59 changes: 36 additions & 23 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,39 +4,52 @@

Generic deriving for `purescript-foreign`.

- [Module Documentation](docs/Data/Foreign/Generic.md)
- [Module Documentation](generated-docs/Data/Foreign/Generic.md)
- [Example](test/Main.purs)
- [Further examples in this repo](https://github.com/justinwoo/purescript-howto-foreign-generic)

## Example Usage

First, define some data type and derive `Generic`:

```purescript
import Data.Foreign.Class (class AsForeign, class IsForeign, readJSON, write)
import Data.Foreign.Generic (defaultOptions, readGeneric, toForeignGeneric)
import Data.Generic.Rep (class Generic)
import Data.Generic.Rep.Show (genericShow)
> import Prelude
> import Data.Generic.Rep (class Generic)
> import Data.Generic.Rep.Show (genericShow)
> newtype MyRecord = MyRecord { a :: Int }
> derive instance genericMyRecord :: Generic MyRecord _
> instance showMyRecord :: Show MyRecord where show = genericShow
```

newtype MyRecord = MyRecord {a :: Int}
To encode JSON, use `genericEncodeJSON`:

derive instance genericMyRecord :: Generic MyRecord _
```purescript
> import Data.Foreign.Class (class Encode, class Decode, encode, decode)
> import Data.Foreign.Generic (defaultOptions, genericDecodeJSON, genericEncodeJSON)
instance isForeignMyRecord :: IsForeign MyRecord where
read = readGeneric $ defaultOptions {unwrapSingleConstructors = true}
> opts = defaultOptions { unwrapSingleConstructors = true }
instance asForeignMyRecord :: AsForeign MyRecord where
write = toForeignGeneric $ defaultOptions {unwrapSingleConstructors = true}
> genericEncodeJSON opts (MyRecord { a: 1 })
"{\"a\":1}"
```

toJSONString = write >>> unsafeStringify
fromJSONString = readJSON >>> runExcept
And to decode JSON, use `genericDecodeJSON`:

main :: forall e. Eff (console :: CONSOLE | e) Unit
main = do
log $ toJSONString (MyRecord {a: 1})
-- {a: 1}
```purescript
> import Control.Monad.Except
log $ show eMyRecord
-- Right (MyRecord {a: 1})
where
eMyRecord :: Either _ MyRecord
eMyRecord = fromJSONString """{"a": 1}"""
```
> runExcept (genericDecodeJSON opts "{\"a\":1}" :: _ MyRecord)
(Right (MyRecord { a: 1 }))
```

Badly formed JSON will result in a useful error, which can be inspected or pretty-printed:

```purescript
> lmap (map renderForeignError) $ runExcept (genericDecodeJSON opts "{\"a\":\"abc\"}" :: _ MyRecord)
(Left
(NonEmptyList
(NonEmpty
"Error at array index 0: (ErrorAtProperty \"a\" (TypeMismatch \"Int\" \"String\"))"
Nil)))
```
21 changes: 11 additions & 10 deletions bower.json
Original file line number Diff line number Diff line change
Expand Up @@ -15,17 +15,18 @@
"url": "git://github.com/paf31/purescript-foreign-generic.git"
},
"dependencies": {
"purescript-console": "^2.0.0",
"purescript-eff": "^2.0.0",
"purescript-exceptions": "^2.0.0",
"purescript-foreign": "^3.0.0",
"purescript-generics-rep": "^4.0.0",
"purescript-globals": "^2.0.0",
"purescript-maps": "^2.0.0",
"purescript-nullable": "^2.0.0",
"purescript-symbols": "^2.0.0"
"purescript-console": "^3.0.0",
"purescript-eff": "^3.0.0",
"purescript-exceptions": "^3.0.0",
"purescript-foreign": "^4.0.0",
"purescript-generics-rep": "^5.0.0",
"purescript-globals": "^3.0.0",
"purescript-maps": "^3.0.0",
"purescript-nullable": "^3.0.0",
"purescript-proxy": "^2.0.0",
"purescript-symbols": "^3.0.0"
},
"devDependencies": {
"purescript-assert": "^2.0.0"
"purescript-assert": "^3.0.0"
}
}
41 changes: 0 additions & 41 deletions docs/Data/Foreign/Generic.md

This file was deleted.

71 changes: 71 additions & 0 deletions generated-docs/Data/Foreign/Class.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
## Module Data.Foreign.Class

#### `Decode`

``` purescript
class Decode a where
decode :: Foreign -> F a
```

The `Decode` class is used to generate decoding functions
of the form `Foreign -> F a` using `generics-rep` deriving.

First, derive `Generic` for your data:

```purescript
import Data.Generic.Rep
data MyType = MyType ...
derive instance genericMyType :: Generic MyType _
```

You can then use the `genericDecode` and `genericDecodeJSON` functions
to decode your foreign/JSON-encoded data.

##### Instances
``` purescript
Decode Foreign
Decode String
Decode Char
Decode Boolean
Decode Number
Decode Int
(Decode a) => Decode (Array a)
```

#### `Encode`

``` purescript
class Encode a where
encode :: a -> Foreign
```

The `Encode` class is used to generate encoding functions
of the form `a -> Foreign` using `generics-rep` deriving.

First, derive `Generic` for your data:

```purescript
import Data.Generic.Rep
data MyType = MyType ...
derive instance genericMyType :: Generic MyType _
```

You can then use the `genericEncode` and `genericEncodeJSON` functions
to encode your data as JSON.

##### Instances
``` purescript
Encode Foreign
Encode String
Encode Char
Encode Boolean
Encode Number
Encode Int
(Encode a) => Encode (Array a)
```


63 changes: 63 additions & 0 deletions generated-docs/Data/Foreign/Generic.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
## Module Data.Foreign.Generic

#### `defaultOptions`

``` purescript
defaultOptions :: Options
```

Default decoding/encoding options:

- Represent sum types as records with `tag` and `contents` fields
- Unwrap single arguments
- Don't unwrap single constructors

#### `genericDecode`

``` purescript
genericDecode :: forall a rep. Generic a rep => GenericDecode rep => Options -> Foreign -> F a
```

Read a value which has a `Generic` type.

#### `genericEncode`

``` purescript
genericEncode :: forall a rep. Generic a rep => GenericEncode rep => Options -> a -> Foreign
```

Generate a `Foreign` value compatible with the `readGeneric` function.

#### `decodeJSON`

``` purescript
decodeJSON :: forall a. Decode a => String -> F a
```

Decode a JSON string using a `Decode` instance.

#### `encodeJSON`

``` purescript
encodeJSON :: forall a. Encode a => a -> String
```

Decode a JSON string using a `Decode` instance.

#### `genericDecodeJSON`

``` purescript
genericDecodeJSON :: forall a rep. Generic a rep => GenericDecode rep => Options -> String -> F a
```

Read a value which has a `Generic` type from a JSON String

#### `genericEncodeJSON`

``` purescript
genericEncodeJSON :: forall a rep. Generic a rep => GenericEncode rep => Options -> a -> String
```

Write a value which has a `Generic` type as a JSON String


Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
## Module Data.Foreign.Generic.Classes
## Module Data.Foreign.Generic.Class

#### `GenericDecode`

Expand Down Expand Up @@ -38,7 +38,7 @@ class GenericDecodeArgs a where
##### Instances
``` purescript
GenericDecodeArgs NoArguments
(IsForeign a) => GenericDecodeArgs (Argument a)
(Decode a) => GenericDecodeArgs (Argument a)
(GenericDecodeArgs a, GenericDecodeArgs b) => GenericDecodeArgs (Product a b)
(GenericDecodeFields fields) => GenericDecodeArgs (Rec fields)
```
Expand All @@ -53,7 +53,7 @@ class GenericEncodeArgs a where
##### Instances
``` purescript
GenericEncodeArgs NoArguments
(AsForeign a) => GenericEncodeArgs (Argument a)
(Encode a) => GenericEncodeArgs (Argument a)
(GenericEncodeArgs a, GenericEncodeArgs b) => GenericEncodeArgs (Product a b)
(GenericEncodeFields fields) => GenericEncodeArgs (Rec fields)
```
Expand All @@ -67,7 +67,7 @@ class GenericDecodeFields a where

##### Instances
``` purescript
(IsSymbol name, IsForeign a) => GenericDecodeFields (Field name a)
(IsSymbol name, Decode a) => GenericDecodeFields (Field name a)
(GenericDecodeFields a, GenericDecodeFields b) => GenericDecodeFields (Product a b)
```

Expand All @@ -80,7 +80,7 @@ class GenericEncodeFields a where

##### Instances
``` purescript
(IsSymbol name, AsForeign a) => GenericEncodeFields (Field name a)
(IsSymbol name, Encode a) => GenericEncodeFields (Field name a)
(GenericEncodeFields a, GenericEncodeFields b) => GenericEncodeFields (Product a b)
```

Expand Down
File renamed without changes.
Loading

0 comments on commit ad0d657

Please sign in to comment.