Skip to content

Commit 76650c6

Browse files
committed
Initial commit
0 parents  commit 76650c6

File tree

6 files changed

+623
-0
lines changed

6 files changed

+623
-0
lines changed

.gitignore

Whitespace-only changes.

LICENSE

+20
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
Copyright (C) 2014 Luca Antiga http://lantiga.github.io
2+
3+
Permission is hereby granted, free of charge, to any person obtaining
4+
a copy of this software and associated documentation files (the
5+
"Software"), to deal in the Software without restriction, including
6+
without limitation the rights to use, copy, modify, merge, publish,
7+
distribute, sublicense, and/or sell copies of the Software, and to
8+
permit persons to whom the Software is furnished to do so, subject to
9+
the following conditions:
10+
11+
The above copyright notice and this permission notice shall be
12+
included in all copies or substantial portions of the Software.
13+
14+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

README.md

+87
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,87 @@
1+
2+
# kin
3+
4+
** mori + lisp + sweet.js **
5+
6+
kin is a lisp with Clojure data structures and semantics that can be intermixed with Javascript code at any level.
7+
8+
kin is a thin macro layer on top of [mori](https://github.com/swannodette/mori) plus a few constructs.
9+
10+
kin is in flux, feel free to test it out but expect glitches.
11+
12+
13+
## Examples
14+
15+
Require mori
16+
```
17+
var mori = require('mori');
18+
```
19+
20+
Mori's persistent data structures and Clojure(Script)-like api at your fingertips
21+
```js
22+
var foo = kin (vector 1 2 3)
23+
kin (conj foo 4)
24+
// => [1 2 3 4]
25+
```
26+
27+
Plus lambdas
28+
```js
29+
kin (map (fn [a] (inc a)) (range 5))
30+
// => (1 2 3 4 5)
31+
```
32+
33+
Interoperability: write js in a kin form
34+
```js
35+
var fn1 = kin (js function (a,b) { return a + b + 2; })
36+
```
37+
at any level - e.g. you can use infix where it makes sense
38+
```js
39+
var fn2 = kin (fn [a b] (js a + b + 2))
40+
```
41+
42+
and you can use kin wherever in js code
43+
```js
44+
function somefunc (a) {
45+
kin (clj_to_js (filter (fn [el] (is_even el)) (range a))).forEach(function(el) {
46+
console.log(el);
47+
});
48+
return [0, 1, 2, 3, 4].filter(kin (fn [el] (is_even el)));
49+
}
50+
console.log(somefunc(5));
51+
52+
// Like a pro
53+
kin (take 6 (map (fn [x] (js x * 2)) (range 1000)))
54+
// => (0 2 4 6 8 10)
55+
```
56+
57+
58+
## Get it
59+
60+
First install [sweet.js](http://sweetjs.org) if you don't have it already
61+
62+
$ npm install -g sweet.js
63+
64+
If you do have it, update it (0.4.0 is required)
65+
66+
$ npm update -g sweet.js
67+
68+
Then
69+
70+
$ npm install kin
71+
72+
All set. Now to compile a kin js file into a plain js file do
73+
74+
$ sjs -m kin/macros -o foo_build.js foo.js
75+
76+
To watch the file and have it automatically compiled whenever the file changes on disk
77+
78+
$ sjs -m kin/macros -o foo_build.js -w foo.js
79+
80+
81+
## License
82+
83+
MIT license http://www.opensource.org/licenses/mit-license.php/
84+
85+
Copyright (C) 2014 Luca Antiga http://lantiga.github.io
86+
87+

macros/index.js

+246
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,246 @@
1+
/**
2+
* kin: mori + lisp + sweet.js
3+
* MIT license http://www.opensource.org/licenses/mit-license.php/
4+
* Copyright (C) 2014 Luca Antiga http://lantiga.github.io
5+
*/
6+
7+
macro _args {
8+
rule { ($arg) } => {
9+
_sexpr $arg
10+
}
11+
rule { ($arg $args ...) } => {
12+
_sexpr $arg, _args ($args ...)
13+
}
14+
}
15+
16+
macro _fun {
17+
case { _ ($f) } => {
18+
var fun = unwrapSyntax(#{$f});
19+
var mori_funs = {
20+
// Fundamentals
21+
equals: true,
22+
hash: true,
23+
// Type predicates
24+
is_list: true,
25+
is_seq: true,
26+
is_vector: true,
27+
is_map: true,
28+
is_set: true,
29+
is_collection: true,
30+
is_sequential: true,
31+
is_associative: true,
32+
is_counted: true,
33+
is_indexed: true,
34+
is_reduceable: true,
35+
is_seqable: true,
36+
is_reversible: true,
37+
// Collections
38+
list: true,
39+
vector: true,
40+
hash_map: true,
41+
set: true,
42+
sorted_set: true,
43+
range: true,
44+
// Collection operations
45+
conj: true,
46+
into: true,
47+
assoc: true,
48+
dissoc: true,
49+
empty: true,
50+
get: true,
51+
get_in: true,
52+
has_key: true,
53+
find: true,
54+
nth: true,
55+
last: true,
56+
assoc_in: true,
57+
update_in: true,
58+
count: true,
59+
is_empty: true,
60+
peek: true,
61+
pop: true,
62+
zipmap: true,
63+
reverse: true,
64+
// Vector operations
65+
subvec: true,
66+
// Hash map operations
67+
keys: true,
68+
vals: true,
69+
// Set operations
70+
disj: true,
71+
union: true,
72+
intersection: true,
73+
difference: true,
74+
is_subset: true,
75+
is_superset: true,
76+
// Sequences
77+
first: true,
78+
rest: true,
79+
seq: true,
80+
cons: true,
81+
concat: true,
82+
flatten: true,
83+
into_array: true,
84+
each: true,
85+
map: true,
86+
mapcat: true,
87+
filter: true,
88+
remove: true,
89+
reduce: true,
90+
reduce_kv: true,
91+
take: true,
92+
take_while: true,
93+
drop: true,
94+
drop_while: true,
95+
some: true,
96+
every: true,
97+
sort: true,
98+
sort_by: true,
99+
interpose: true,
100+
interleave: true,
101+
iterate: true,
102+
repeat: true,
103+
repeatedly: true,
104+
partition: true,
105+
partition_by: true,
106+
group_by: true,
107+
// Helpers
108+
prim_seq: true,
109+
identity: true,
110+
constantly: true,
111+
inc: true,
112+
dec: true,
113+
sum: true,
114+
is_even: true,
115+
is_odd: true,
116+
comp: true,
117+
juxt: true,
118+
knit: true,
119+
pipeline: true,
120+
partial: true,
121+
curry: true,
122+
fnil: true,
123+
js_to_clj: true,
124+
clj_to_js: true
125+
}
126+
if (mori_funs[fun]) {
127+
return #{mori.$f}
128+
}
129+
return #{$f}
130+
}
131+
}
132+
133+
macro _keys {
134+
rule { ($($k $v)) } => {
135+
$k
136+
}
137+
rule { ($($k $v) $($ks $vs) ...) } => {
138+
$k, _keys ($($ks $vs) ...)
139+
}
140+
}
141+
142+
macro _vals {
143+
rule { ($($k $v)) } => {
144+
$v
145+
}
146+
rule { ($($k $v) $($ks $vs) ...) } => {
147+
$v, _vals ($($ks $vs) ...)
148+
}
149+
}
150+
151+
macro _sexpr {
152+
rule { () } => {
153+
}
154+
rule { (fn [$args ...] $sexprs ...) } => {
155+
function ($args(,)...) {
156+
_return_sexprs ($sexprs ...)
157+
}
158+
}
159+
//rule { (letv [$($k $v) ...] $sexprs ...) } => {
160+
// function ( _keys($($k $v) ...) ) {
161+
// _return_sexprs ($sexprs ...)
162+
// }(_vals ($($k $v) ...))
163+
//}
164+
rule { (prn $args ...) } => {
165+
console.log(_sexprs($args ...))
166+
}
167+
rule { (js $body ...) } => {
168+
$body ...
169+
}
170+
rule { ($f) } => {
171+
_fun($f)()
172+
}
173+
rule { ($f $arg) } => {
174+
_fun($f)(_args($arg))
175+
}
176+
rule { ($f $arg $args ...) } => {
177+
_fun($f)( _args($arg) , _args($args ...))
178+
}
179+
rule { $x } => { $x }
180+
}
181+
182+
macro _return_sexprs {
183+
rule { ($sexpr) } => {
184+
return _sexpr $sexpr
185+
}
186+
rule { ($sexpr $sexprs ...) } => {
187+
_sexpr $sexpr _return_sexprs ($sexprs ...)
188+
}
189+
}
190+
191+
macro _sexprs {
192+
rule { ($sexpr) } => {
193+
_sexpr $sexpr
194+
}
195+
rule { ($sexpr $sexprs ...) } => {
196+
_sexpr $sexpr _sexprs ($sexprs ...)
197+
}
198+
}
199+
200+
macro kin {
201+
rule { ($x ...) } => {
202+
_sexpr ($x ...)
203+
}
204+
}
205+
206+
// EXAMPLES
207+
208+
var mori = require('mori');
209+
210+
// Mori at your fingertips
211+
var foo = kin (vector 1 2 3)
212+
kin (conj foo 4)
213+
// => [1 2 3 4]
214+
215+
// Plus lambdas
216+
kin (map (fn [a] (inc a)) (range 5))
217+
// => (1 2 3 4 5)
218+
219+
// Interoperability: write js in a kin form
220+
var fn1 = kin (js function (a,b) { return a + b + 2; })
221+
222+
// at any level - e.g. you can use infix where it makes sense
223+
var fn2 = kin (fn [a b] (js a + b + 2))
224+
225+
// and you can use kin wherever in js code
226+
function somefunc (a) {
227+
kin (clj_to_js (filter (fn [el] (is_even el)) (range a))).forEach(function(el) {
228+
console.log(el);
229+
});
230+
return [0, 1, 2, 3, 4].filter(kin (fn [el] (is_even el)));
231+
}
232+
console.log(somefunc(5));
233+
234+
// Like a pro
235+
kin (take 6 (map (fn [x] (js x * 2)) (range 1000)))
236+
// => (0 2 4 6 8 10)
237+
238+
239+
// TODO:
240+
// * letv (impl. above doesn't work due to parsing quirks)
241+
// * literals
242+
// * math expressions -> use infix (SOLVED)
243+
// * destructuring
244+
// * threading macros
245+
246+

package.json

+24
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
{
2+
"name": "kin",
3+
"version": "0.1.0",
4+
"description": "mori + lisp + sweet.js",
5+
"repository": {
6+
"type": "git",
7+
"url": "https://github.com/lantiga/kin.git"
8+
},
9+
"keywords": [
10+
"lisp",
11+
"data",
12+
"persistent",
13+
"clojure",
14+
"clojurescript",
15+
"macros",
16+
"macro"
17+
],
18+
"author": "Luca Antiga http://lantiga.github.io",
19+
"license": "MIT",
20+
"readmeFilename": "README.md",
21+
"devDependencies": {
22+
"sweet.js": "~0.4.0"
23+
}
24+
}

0 commit comments

Comments
 (0)