Skip to content

Commit

Permalink
📖 docs: copy rationale in README
Browse files Browse the repository at this point in the history
  • Loading branch information
prayerslayer committed Nov 29, 2016
1 parent 2ceda9e commit d565b52
Showing 1 changed file with 11 additions and 1 deletion.
12 changes: 11 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
@@ -1,10 +1,20 @@
# js.spec

clojure.spec for Javascript

[![Latest build](https://travis-ci.org/prayerslayer/js.spec.svg)](https://travis-ci.org/prayerslayer/js.spec)
[![Coverage Status](https://coveralls.io/repos/github/prayerslayer/js.spec/badge.svg?branch=master)](https://coveralls.io/github/prayerslayer/js.spec?branch=master)
[![npm version](https://badge.fury.io/js/js.spec.svg)](https://badge.fury.io/js/js.spec)

clojure.spec for Javascript
There is [`clojure.spec`](http://clojure.org/about/spec), a part of Clojure's core library that is intended to help with specification, testing and error messages. I recommend you to read the linked rationale, you will get the gist even without knowledge of Clojure. In any case here's my best attempt of a summary:

In a dynamic language like Javascript or Clojure it is common to represent information with data. For instance, you could encode the score of a soccer match with a list of two integers `[0, 1]`. (In a statically typed language like Java the idiomatic way would be an instance of a `SoccerScore` class.) This data is passed around between modules of your code or sent to external systems, yet the knowledge about what this list of integers stands for is not available anywhere. Maybe you described it in the project's documentation, which is likely outdated. Most probably it is implicitly assumed in your code (`var goals_scored = score[0] + score[1];`). If the semantics change (e.g. list contains also teams), your code breaks.

One way to mitigate this is by static analysis tools ([Flow](https://github.com/facebook/flow)) or typed languages ([Typescript](https://www.typescriptlang.org/)), but they only get you so far. For instance they don't work at runtime (duh!) and offer limited expressiveness. (They also need more tooling, but that's another story.) So what you're left with is manual parsing and checking, which is repetitive and half-assed at worst (`if (!Array.isArray(score)) ...`), and non-standard at best, ie. there is no way for users of your function to know where exactly their provided input failed your specification.

Another issue is that schemas get more popular in the Javascript community (JSON Schema, React.PropTypes...), yet there is no uniform way to define them. Error messages differ from system to system. You can't port your schemas, but need to define them multiple times in different syntax.

`js.spec` tries to solve those problems.

# Usage

Expand Down

0 comments on commit d565b52

Please sign in to comment.