Skip to content
This repository was archived by the owner on Jan 8, 2021. It is now read-only.

Getting started

Austin Seipp edited this page Dec 10, 2013 · 3 revisions

Before we get down to anything, we need to discuss some of the underlying ideas behind the library and how it is to be used.

The NaCl Philosophy

In [1] Bernstein, Lange, and Schwabe argue that simplified, opinionated cryptographic libraries avoid "cryptographic disasters" which occur with more flexible libraries like OpenSSL. The argument is solid, but NaCl is still a somewhat difficult sell since Bernstein uses somewhat less industry selected cryptographic primitives and then happily restricts you to use them. This is a somewhat scary value proposition---tie your hands and trust in NaCl because you almost certainly can't do it better and it'll simplify your life---that should be approached directly.

This library adheres to the core spirit of nacl, and provides and recommends using the provided setup below, matching the C library. Nevertheless, as a cryptography library we also bring along some extras for convenience, keeping in line with nacl generally being cutting-edge cryptographic work. There are a few design principles here in accordance with these ideas:

  • We expose the names of primitives in modules by default, rather than hiding behind more innocuous names, and we do provide some choice between primitives in some APIs. We always recommend the default primitive selection, however.

  • We attempt to make the API reasonably typesafe to avoid programming error, without difficult to think about or use.

  • The module structure and API is intentionally simple with some overlap, and specifically not overloaded. In general overloading makes APIs harder to understand at a glance and sometimes doesn't mesh well with the idea of being simple to use and understand in the authors opinion.

    You're encouraged to just use qualified imports to resolve naming ambiguities, like we see below.

Getting started

First, import the core primitives of the nacl library. The following import specification will bring the entire library into scope:

import qualified Crypto.NaCl              as NaCl

This is (basically) the same as saying:

import qualified Crypto.DH.Curve25519     as Curve25519
import qualified Crypto.Encrypt.Box       as Box
import qualified Crypto.Encrypt.SecretBox as SecretBox
import qualified Crypto.Encrypt.Stream    as Stream
import qualified Crypto.HMAC.SHA512       as HMACSHA512
import qualified Crypto.Hash.SHA          as SHA
import qualified Crypto.MAC.Poly1305      as Poly1305
import qualified Crypto.Sign.Ed25519      as Ed25519

import qualified Crypto.Nonce             as Nonce
import qualified System.Crypto.Random     as Random

The above imports reflect the default primitives available in the nacl C library. You should always use these as your defaults.

NB: The APIs are intended to be imported in a qualified manner.

Mapping modules to APIs

The above APIs may be a bit confusing. The mapping between the above modules and their equivalents in the C API is very simple:

C API Crypto.NaCl functions Haskell module
crypto_box box/boxOpen Crypto.Encrypt.Box
crypto_scalarmult curve25519 Crypto.DH.Curve25519
crypto_sign sign/verify Crypto.Sign.Ed25519*
crypto_secretbox secretBox/secretBoxOpen Crypto.Encrypt.SecretBox
crypto_stream streamEncrypt/streamDecrypt Crypto.Encrypt.Stream
crypto_auth auth/authVerify Crypto.HMAC.SHA512
crypto_onetimeauth oneTimeAuth/oneTimeAuthVerify Crypto.MAC.Poly1305
crypto_hash hash Crypto.Hash.SHA

Again: these Haskell APIs all reflect the default nacl C primitives.

* Note that the released version of nacl-20110221 does not use ed25519 but an older Edwards curve. See "Signing gotchas" in the Field Guide

The Nonce API

Lorem ipsum...

Bibliography

[1] Bernstein D, Lange T, Schwabe P. The security impact of a new cryptographic library (2012).

Clone this wiki locally