Skip to content
This repository was archived by the owner on Oct 1, 2024. It is now read-only.

Commit

Permalink
Upgraded to remark-html 5.x.
Browse files Browse the repository at this point in the history
Closes #24.
  • Loading branch information
ben-eb committed Jul 23, 2016
1 parent 53ed9a3 commit d89bcfc
Show file tree
Hide file tree
Showing 6 changed files with 83 additions and 47 deletions.
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,2 +1,4 @@
.nyc_output
coverage
node_modules
dist
12 changes: 12 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,15 @@
# 4.0.0

* Upgraded to remark-html 5.x.

## Breaking changes

* `opts.attributes` is now named `opts.linkProperties`.
* `opts.template` has been replaced with `opts.content`; instead of supplying
a HTML string here, you can specify either a single HAST node or an array
of them. This makes the module more suitable for working with virtual node
consumers, such as React.

# 3.0.1

* Upgraded to remark 5.x, this module will work the same using either version.
Expand Down
29 changes: 15 additions & 14 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -40,29 +40,30 @@ console.log(result);

#### options

##### attributes

Type: `object`

By default, when using the `append` or `prepend` behaviour, this will add
`aria-hidden="false"` to the anchor. When using the `wrap` behaviour, this is
left empty for you to add any extra HTML attributes.

##### behaviour

Type: `string`
Default: `prepend`

Set this to `prepend` to inject the link before the heading text; `append` after
it, and `wrap` to wrap the whole heading text with the link. Note that the
`wrap` option doesn't apply any value set by the `template` option.
it, and `wrap` to wrap the whole heading text with the link. Note that supplying
`wrap` will ignore any value defined by the `template` option.

##### template
##### content

Type: `string`
Default: `<span class="icon icon-link"></span>`
Type: `Object|Array`
Default: `{type: 'element', tagName: 'span', properties: {className: [icon, `${icon}-${link}`]} }`

The template used by the `append` & `prepend` behaviours.
Supply a list of HAST nodes or a single node here. For further details, please
refer to the specification at https://github.com/wooorm/hast.

##### linkProperties

Type: `object`

By default, when using the `append` or `prepend` behaviour, this will add
`aria-hidden="false"` to the anchor. When using the `wrap` behaviour, this is
left empty for you to add any extra HTML attributes.


## Contributing
Expand Down
13 changes: 7 additions & 6 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,9 @@
"scripts": {
"pretest": "eslint src",
"prepublish": "del-cli dist && babel src --out-dir dist --ignore /__tests__/",
"test": "ava src/__tests__",
"test-012": "ava src/__tests__"
"report": "nyc report --reporter=html",
"test": "nyc ava",
"test-012": "nyc ava"
},
"keywords": [
"headings",
Expand All @@ -36,18 +37,18 @@
"eslint-plugin-babel": "^3.3.0",
"eslint-plugin-import": "^1.10.2",
"remark": "^5.0.1",
"remark-html": "^3.0.0",
"remark-slug": "^4.1.0"
"remark-html": "^5.0.0",
"remark-slug": "^4.1.0",
"nyc": "^7.0.0"
},
"homepage": "https://github.com/ben-eb/mdast-autolink-headings",
"homepage": "https://github.com/ben-eb/remark-autolink-headings",
"author": {
"name": "Ben Briggs",
"email": "beneb.info@gmail.com",
"url": "http://beneb.info"
},
"repository": "ben-eb/remark-autolink-headings",
"dependencies": {
"object-assign": "^4.0.1",
"unist-util-visit": "^1.0.1"
},
"eslintConfig": {
Expand Down
6 changes: 6 additions & 0 deletions src/__tests__/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,12 @@ test('should autolink headings', t => {
});
});

test('should accept custom content', t => {
const md = '# method';
const {contents} = remark().use(slug).use(html).use(headings, {content: {type: 'text', value: '#'}}).process(md);
t.deepEqual(contents, '<h1 id="method"><a href="#method" aria-hidden="true">#</a>method</h1>\n');
});

test('should do nothing if slugs are not used', t => {
let {contents} = remark().use(headings).use(html).process(base('input.md'));
t.deepEqual(contents, base('output.html'));
Expand Down
68 changes: 41 additions & 27 deletions src/index.js
Original file line number Diff line number Diff line change
@@ -1,58 +1,72 @@
import assign from 'object-assign';
import visit from 'unist-util-visit';

let base = (node, callback) => {
let data = node.data || {};
const icon = 'icon';
const link = 'link';
const wrap = 'wrap';

const methodMap = {
prepend: 'unshift',
append: 'push',
};

const base = (node, callback) => {
const {data} = node;
if (!data || !data.htmlAttributes || !data.htmlAttributes.id) {
return;
}

return callback('#' + data.htmlAttributes.id);
};

const contentDefaults = {
type: 'element',
tagName: 'span',
properties: {className: [icon, `${icon}-${link}`]},
};

export default function attacher (remark, opts = {}) {
opts = assign({
let {linkProperties, behaviour, content} = {
behaviour: 'prepend',
template: '<span class="icon icon-link"></span>',
}, opts);

let behaviour = opts.behaviour;

let methodMap = {
prepend: 'unshift',
append: 'push',
content: contentDefaults,
...opts,
};

function inject (node) {
return base(node, id => {
if (behaviour !== wrap && !linkProperties) {
linkProperties = {'aria-hidden': true};
}

function injectNode (node) {
return base(node, url => {
if (!Array.isArray(content)) {
content = [content];
}
node.children[methodMap[behaviour]]({
type: 'link',
url: id,
type: link,
url,
title: null,
children: [],
data: {
htmlContent: opts.template,
htmlAttributes: opts.attributes || {'aria-hidden': true},
hProperties: linkProperties,
hChildren: content,
},
});
});
}

function wrap (node) {
return base(node, id => {
let children = node.children;
function wrapNode (node) {
return base(node, url => {
const {children} = node;

node.children = [{
type: 'link',
url: id,
type: link,
url,
title: null,
children: children,
children,
data: {
htmlAttributes: opts.attributes,
hProperties: linkProperties,
},
}];
});
}

return ast => visit(ast, 'heading', behaviour === 'wrap' ? wrap : inject);
return ast => visit(ast, 'heading', behaviour === wrap ? wrapNode : injectNode);
}

0 comments on commit d89bcfc

Please sign in to comment.