Skip to content

Commit 4402a5c

Browse files
Upload new plugin source
0 parents  commit 4402a5c

File tree

18 files changed

+1981
-0
lines changed

18 files changed

+1981
-0
lines changed

.babelrc

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
{
2+
"presets": ["es2015"]
3+
}

.gitignore

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
# Logs
2+
logs
3+
*.log
4+
npm-debug.log*
5+
yarn-debug.log*
6+
yarn-error.log*
7+
8+
# Runtime data
9+
pids
10+
*.pid
11+
*.seed
12+
*.pid.lock
13+
14+
# Directory for instrumented libs generated by jscoverage/JSCover
15+
lib-cov
16+
17+
# Coverage directory used by tools like istanbul
18+
coverage
19+
20+
# nyc test coverage
21+
.nyc_output
22+
23+
# Grunt intermediate storage (http://gruntjs.com/creating-plugins#storing-task-files)
24+
.grunt
25+
26+
# Bower dependency directory (https://bower.io/)
27+
bower_components
28+
29+
# node-waf configuration
30+
.lock-wscript
31+
32+
# Compiled binary addons (http://nodejs.org/api/addons.html)
33+
build/Release
34+
35+
# Dependency directories
36+
node_modules/
37+
jspm_packages/
38+
39+
# Typescript v1 declaration files
40+
typings/
41+
42+
# Optional npm cache directory
43+
.npm
44+
45+
# Optional eslint cache
46+
.eslintcache
47+
48+
# Optional REPL history
49+
.node_repl_history
50+
51+
# Output of 'npm pack'
52+
*.tgz
53+
54+
# Yarn Integrity file
55+
.yarn-integrity
56+
57+
# dotenv environment variables file
58+
.env
59+

.npmignore

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
node_modules
2+
src
3+
test

LICENSE

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

README.md

Lines changed: 90 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,90 @@
1+
# babel-plugin-implicit-function
2+
3+
This plugin is made to make JS syntax easier to work with functional programming by creating
4+
quoted expressions that may be lazily evaluated and work together with functional libraries,
5+
like Ramda. I've overloaded the `~` prefix unary operator for that.
6+
7+
## Examples
8+
9+
```javascript
10+
import { cond } from 'ramda';
11+
12+
const precomputedResult = ~(10 === 20);
13+
const otherwise = ~true;
14+
const matches = cond([
15+
[precomputedResult, ~'Something is reeeeally wrong!'],
16+
[otherwise, ~'Nice! Math still works!']
17+
]);
18+
```
19+
20+
Turn into
21+
22+
```javascript
23+
import { cond } from 'ramda';
24+
25+
const precomputedResult = () => 10 === 20;
26+
const otherwise = () => true;
27+
const matches = cond([
28+
[precomputedResult, () => 'Something is reeeeally wrong!'],
29+
[otherwise, () => 'Nice! Math still works!']
30+
]);
31+
```
32+
33+
This is a good replacement for `always` function, because this is really lazy, and the value
34+
only gets computed when you need it. Using `always` can cause problems by premature evaluation:
35+
36+
```javascript
37+
getUsers()
38+
.then(always(doSomethingImportantAndReturn());
39+
```
40+
41+
Note that `doSomethingImportantAndReturn` needs `getUsers` to be computed before, but that's
42+
not what happen, and this is a source of error and code smell. We could easily fix that with
43+
`~` operator. Remember: **never** use `always`!
44+
45+
```javascript
46+
getUsers()
47+
.then(~doSomethingImportantAndReturn());
48+
```
49+
50+
51+
## Disabling in current scope
52+
53+
If you want to use the original bitwise negation operator, you can disable this plugin in
54+
current scope (and it children scopes) using `'no implicit function` directive.
55+
56+
## Installation
57+
58+
```sh
59+
$ npm install --save-dev babel-plugin-implicit-function
60+
```
61+
62+
## Usage
63+
64+
### Via `.babelrc` (Recommended)
65+
66+
**.babelrc**
67+
68+
```json
69+
{
70+
"plugins": ["implicit-function"]
71+
}
72+
```
73+
74+
### Via CLI
75+
76+
```sh
77+
$ babel --plugins implicit-function script.js
78+
```
79+
80+
### Via Node API
81+
82+
```javascript
83+
require('babel-core').transform('code', {
84+
plugins: ['implicit-function']
85+
});
86+
```
87+
88+
# License
89+
90+
MIT

lib/index.js

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
'use strict';
2+
3+
Object.defineProperty(exports, "__esModule", {
4+
value: true
5+
});
6+
var hasNoImplicitFunction = function hasNoImplicitFunction(path) {
7+
return !!path.findParent(function (_ref) {
8+
var node = _ref.node;
9+
return node.directives && node.directives.some(function (_ref2) {
10+
var value = _ref2.value;
11+
return value.value === 'no implicit function';
12+
});
13+
});
14+
};
15+
16+
exports.default = function (_ref3) {
17+
var t = _ref3.types;
18+
return {
19+
visitor: {
20+
UnaryExpression: function UnaryExpression(path) {
21+
if (!path.isUnaryExpression({ operator: '~' }) || hasNoImplicitFunction(path)) {
22+
return;
23+
}
24+
25+
var wrapper = t.arrowFunctionExpression([], path.node.argument);
26+
path.replaceWith(wrapper);
27+
}
28+
}
29+
};
30+
};

package.json

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
{
2+
"name": "babel-plugin-implicit-function",
3+
"version": "0.1.1",
4+
"description": "Babel plugin to allow lazy expressions by implicit arrow functions via ~ operator",
5+
"main": "lib/index.js",
6+
"repository": "https://github.com/haskellcamargo/babel-plugin-implicit-function.git",
7+
"author": "Marcelo Camargo <marcelocamargo@linuxmail.org>",
8+
"license": "MIT",
9+
"scripts": {
10+
"build": "babel src/index.js -o lib/index.js",
11+
"watch-build": "npm run build -- -w",
12+
"test": "mocha --compilers js:babel-register",
13+
"watch-test": "npm test -- -w"
14+
},
15+
"keywords": [
16+
"babel",
17+
"babel-plugin",
18+
"function",
19+
"arrow function",
20+
"implicit function",
21+
"functional programming"
22+
],
23+
"bugs": {
24+
"url": "https://github.com/haskellcamargo/babel-plugin-implicit-function/issues"
25+
},
26+
"devDependencies": {
27+
"babel-cli": "6.26.0",
28+
"babel-core": "6.26.0",
29+
"babel-preset-es2015": "6.24.1",
30+
"babel-register": "6.26.0",
31+
"chai": "4.1.1",
32+
"mocha": "3.5.0"
33+
}
34+
}

src/index.js

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
const hasNoImplicitFunction = path =>
2+
!!path.findParent(({ node }) =>
3+
node.directives && node.directives.some(({ value }) => value.value === 'no implicit function'));
4+
5+
export default ({ types: t }) => ({
6+
visitor: {
7+
UnaryExpression(path) {
8+
if (!path.isUnaryExpression({ operator: '~' }) || hasNoImplicitFunction(path)) {
9+
return;
10+
}
11+
12+
const wrapper = t.arrowFunctionExpression([], path.node.argument);
13+
path.replaceWith(wrapper);
14+
}
15+
}
16+
});
17+

test/fixtures/disable/actual.js

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
() => {
2+
const One = ~1;
3+
4+
void function () {
5+
'no implicit function';
6+
7+
const one = ~1;
8+
};
9+
};
10+

test/fixtures/disable/expected.js

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
() => {
2+
const One = () => 1;
3+
4+
void function () {
5+
'no implicit function';
6+
7+
const one = ~1;
8+
};
9+
};
10+

0 commit comments

Comments
 (0)