Skip to content

Commit

Permalink
[new] Add wiki content to main repo
Browse files Browse the repository at this point in the history
  • Loading branch information
ptaoussanis committed Aug 3, 2023
1 parent 18b6c7e commit f53ba6e
Show file tree
Hide file tree
Showing 4 changed files with 443 additions and 0 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -10,3 +10,4 @@ pom.xml*
/target/
/checkouts/
/logs/
/wiki/.git
153 changes: 153 additions & 0 deletions wiki/1 Getting-started.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,153 @@
# Setup

Add the [relevant dependency](../#latest-releases) to your project:

```clojure
Leiningen: [com.taoensso/nippy "x-y-z"] ; or
deps.edn: com.taoensso/nippy {:mvn/version "x-y-z"}
```

And setup your namespace imports:

```clojure
(ns my-app (:require [taoensso.nippy :as nippy]))
```

# De/serializing

As an example of what it can do, let's take a look at Nippy's own reference stress data:

```clojure
nippy/stress-data
=>
{:nil nil
:true true
:false false
:boxed-false (Boolean. false)

:char \ಬ
:str-short "ಬಾ ಇಲ್ಲಿ ಸಂಭವಿಸ"
:str-long (apply str (range 1000))
:kw :keyword
:kw-ns ::keyword
:kw-long (keyword
(apply str "kw" (range 1000))
(apply str "kw" (range 1000)))

:sym 'foo
:sym-ns 'foo/bar
:sym-long (symbol
(apply str "sym" (range 1000))
(apply str "sym" (range 1000)))

:regex #"^(https?:)?//(www\?|\?)?"

;;; Try reflect real-world data:
:many-small-numbers (vec (range 200))
:many-small-keywords (->> (java.util.Locale/getISOLanguages)
(mapv keyword))
:many-small-strings (->> (java.util.Locale/getISOCountries)
(mapv #(.getDisplayCountry (java.util.Locale. "en" %))))

:queue (enc/queue [:a :b :c :d :e :f :g])
:queue-empty (enc/queue)
:sorted-set (sorted-set 1 2 3 4 5)
:sorted-map (sorted-map :b 2 :a 1 :d 4 :c 3)

:list (list 1 2 3 4 5 (list 6 7 8 (list 9 10 '(()))))
:vector [1 2 3 4 5 [6 7 8 [9 10 [[]]]]]
:map {:a 1 :b 2 :c 3 :d {:e 4 :f {:g 5 :h 6 :i 7 :j {{} {}}}}}
:set #{1 2 3 4 5 #{6 7 8 #{9 10 #{#{}}}}}
:meta (with-meta {:a :A} {:metakey :metaval})
:nested [#{{1 [:a :b] 2 [:c :d] 3 [:e :f]} [#{{}}] #{:a :b}}
#{{1 [:a :b] 2 [:c :d] 3 [:e :f]} [#{{}}] #{:a :b}}
[1 [1 2 [1 2 3 [1 2 3 4 [1 2 3 4 5]]]]]]

:lazy-seq (repeatedly 1000 rand)
:lazy-seq-empty (map identity '())

:byte (byte 16)
:short (short 42)
:integer (int 3)
:long (long 3)
:bigint (bigint 31415926535897932384626433832795)

:float (float 3.14)
:double (double 3.14)
:bigdec (bigdec 3.1415926535897932384626433832795)

:ratio 22/7
:uri (java.net.URI. "https://clojure.org/reference/data_structures")
:uuid (java.util.UUID/randomUUID)
:util-date (java.util.Date.)
:sql-date (java.sql.Date/valueOf "2023-06-21")

;;; JVM 8+
:time-instant (enc/compile-if java.time.Instant (java.time.Instant/now) nil)
:time-duration (enc/compile-if java.time.Duration (java.time.Duration/ofSeconds 100 100) nil)
:time-period (enc/compile-if java.time.Period (java.time.Period/of 1 1 1) nil)

:bytes (byte-array [(byte 1) (byte 2) (byte 3)])
:objects (object-array [1 "two" {:data "data"}])

:stress-record (StressRecord. "data")
:stress-type (StressType. "data")

;; Serializable
:throwable (Throwable. "Yolo")
:exception (try (/ 1 0) (catch Exception e e))
:ex-info (ex-info "ExInfo" {:data "data"})}
```

Serialize it:

```clojure
(def frozen-stress-data (nippy/freeze nippy/stress-data))
=> #<byte[] [B@3253bcf3>
```

Deserialize it:

```clojure
(nippy/thaw frozen-stress-data)
=> {:bytes (byte-array [(byte 1) (byte 2) (byte 3)])
:nil nil
:boolean true
<...> }
```

Couldn't be simpler!

See also the lower-level [`freeze-to-out!`](https://taoensso.github.io/nippy/taoensso.nippy.html#var-freeze-to-out.21) and [`thaw-from-in!`](https://taoensso.github.io/nippy/taoensso.nippy.html#var-thaw-from-in.21) fns for operating on `DataOutput` and `DataInput` types directly.

# Encryption

> You may want to consider using Nippy with [Tempel](https://github.com/taoensso/tempel) for more comprehensive encryption options.

Nippy also gives you **dead simple data encryption**.
Add a single option to your usual freeze/thaw calls like so:

```clojure
(nippy/freeze nippy/stress-data {:password [:salted "my-password"]}) ; Encrypt
(nippy/thaw <encrypted-data> {:password [:salted "my-password"]}) ; Decrypt
```

There's two default forms of encryption on offer: `:salted` and `:cached`. Each of these makes carefully-chosen trade-offs and is suited to one of two common use cases. See [`aes128-encryptor`](https://taoensso.github.io/nippy/taoensso.nippy.html#var-aes128-encryptor) for a detailed explanation of why/when you'd want one or the other.

# Custom types

It's easy to extend Nippy to your own data types:

```clojure
(defrecord MyType [data])

(nippy/extend-freeze MyType :my-type/foo ; A unique (namespaced) type identifier
[x data-output]
(.writeUTF data-output (:data x)))

(nippy/extend-thaw :my-type/foo ; Same type id
[data-input]
(MyType. (.readUTF data-input)))

(nippy/thaw (nippy/freeze (MyType. "Joe"))) => #taoensso.nippy.MyType{:data "Joe"}
```
Loading

0 comments on commit f53ba6e

Please sign in to comment.