rust/src/rustdoc/markdown_index_pass.rs

231 lines
5.5 KiB
Rust
Raw Normal View History

2012-03-02 17:17:13 -06:00
#[doc = "Build indexes as appropriate for the markdown pass"];
export mk_pass;
fn mk_pass(config: config::config) -> pass {
2012-03-02 17:17:13 -06:00
{
name: "markdown_index",
f: fn~(srv: astsrv::srv, doc: doc::doc) -> doc::doc {
run(srv, doc, config)
}
2012-03-02 17:17:13 -06:00
}
}
fn run(
_srv: astsrv::srv,
doc: doc::doc,
config: config::config
) -> doc::doc {
2012-03-02 17:17:13 -06:00
let fold = fold::fold({
fold_mod: fold_mod,
fold_nmod: fold_nmod
with *fold::default_any_fold(config)
2012-03-02 17:17:13 -06:00
});
fold.fold_doc(fold, doc)
2012-03-02 17:17:13 -06:00
}
fn fold_mod(
fold: fold::fold<config::config>,
doc: doc::moddoc
) -> doc::moddoc {
2012-03-02 17:17:13 -06:00
let doc = fold::default_any_fold_mod(fold, doc);
{
index: some(build_mod_index(doc, fold.ctxt))
2012-03-02 17:17:13 -06:00
with doc
}
}
fn fold_nmod(
fold: fold::fold<config::config>,
doc: doc::nmoddoc
) -> doc::nmoddoc {
let doc = fold::default_any_fold_nmod(fold, doc);
{
index: some(build_nmod_index(doc, fold.ctxt))
with doc
}
}
fn build_mod_index(
doc: doc::moddoc,
config: config::config
) -> doc::index {
2012-03-02 17:17:13 -06:00
{
2012-06-30 18:19:07 -05:00
entries: par::anymap(doc.items, |doc| {
item_to_entry(doc, config)
})
}
}
fn build_nmod_index(
doc: doc::nmoddoc,
config: config::config
) -> doc::index {
{
2012-06-30 18:19:07 -05:00
entries: par::anymap(doc.fns, |doc| {
item_to_entry(doc::fntag(doc), config)
})
2012-03-02 17:17:13 -06:00
}
}
fn item_to_entry(
doc: doc::itemtag,
config: config::config
) -> doc::index_entry {
let link = alt doc {
doc::modtag(_) | doc::nmodtag(_)
if config.output_style == config::doc_per_mod {
markdown_writer::make_filename(config, doc::itempage(doc))
}
_ {
"#" + pandoc_header_id(markdown_pass::header_text(doc))
}
};
2012-03-02 17:17:13 -06:00
{
kind: markdown_pass::header_kind(doc),
name: markdown_pass::header_name(doc),
brief: doc.brief(),
link: link
2012-03-02 17:17:13 -06:00
}
}
fn pandoc_header_id(header: str) -> str {
// http://johnmacfarlane.net/pandoc/README.html#headers
let header = remove_formatting(header);
let header = remove_punctuation(header);
let header = replace_with_hyphens(header);
let header = convert_to_lowercase(header);
let header = remove_up_to_first_letter(header);
let header = maybe_use_section_id(header);
ret header;
fn remove_formatting(s: str) -> str {
2012-03-02 17:17:13 -06:00
str::replace(s, "`", "")
}
fn remove_punctuation(s: str) -> str {
let s = str::replace(s, "<", "");
let s = str::replace(s, ">", "");
let s = str::replace(s, "[", "");
let s = str::replace(s, "]", "");
let s = str::replace(s, "(", "");
let s = str::replace(s, ")", "");
let s = str::replace(s, "@", "");
let s = str::replace(s, "~", "");
let s = str::replace(s, "/", "");
ret s;
}
2012-03-02 17:17:13 -06:00
fn replace_with_hyphens(s: str) -> str {
str::replace(s, " ", "-")
}
fn convert_to_lowercase(s: str) -> str { str::to_lower(s) }
fn remove_up_to_first_letter(s: str) -> str { s }
fn maybe_use_section_id(s: str) -> str { s }
}
#[test]
fn should_remove_punctuation_from_headers() {
assert pandoc_header_id("impl foo of bar<A>") == "impl-foo-of-bara";
assert pandoc_header_id("fn@(~[~A])") == "fna";
}
2012-03-02 17:17:13 -06:00
#[test]
fn should_index_mod_contents() {
let doc = test::mk_doc(
config::doc_per_crate,
"mod a { } fn b() { }"
);
assert option::get(doc.cratemod().index).entries[0] == {
kind: "Module",
name: "a",
brief: none,
link: "#module-a"
};
assert option::get(doc.cratemod().index).entries[1] == {
kind: "Function",
name: "b",
brief: none,
link: "#function-b"
};
}
#[test]
fn should_index_mod_contents_multi_page() {
let doc = test::mk_doc(
config::doc_per_mod,
"mod a { } fn b() { }"
);
assert option::get(doc.cratemod().index).entries[0] == {
2012-03-02 17:17:13 -06:00
kind: "Module",
name: "a",
brief: none,
link: "a.html"
2012-03-02 17:17:13 -06:00
};
assert option::get(doc.cratemod().index).entries[1] == {
2012-03-02 17:17:13 -06:00
kind: "Function",
name: "b",
brief: none,
link: "#function-b"
2012-03-02 17:17:13 -06:00
};
}
#[test]
fn should_index_foreign_mod_pages() {
let doc = test::mk_doc(
config::doc_per_mod,
"extern mod a { }"
);
assert option::get(doc.cratemod().index).entries[0] == {
kind: "Foreign module",
name: "a",
brief: none,
link: "a.html"
};
}
#[test]
fn should_add_brief_desc_to_index() {
let doc = test::mk_doc(
config::doc_per_mod,
2012-03-09 20:12:15 -06:00
"#[doc = \"test\"] mod a { }"
);
assert option::get(doc.cratemod().index).entries[0].brief == some("test");
}
#[test]
fn should_index_foreign_mod_contents() {
let doc = test::mk_doc(
config::doc_per_crate,
"extern mod a { fn b(); }"
);
assert option::get(doc.cratemod().nmods()[0].index).entries[0] == {
kind: "Function",
name: "b",
brief: none,
link: "#function-b"
};
}
2012-03-02 17:17:13 -06:00
#[cfg(test)]
mod test {
fn mk_doc(output_style: config::output_style, source: str) -> doc::doc {
2012-06-30 18:19:07 -05:00
do astsrv::from_str(source) |srv| {
let config = {
output_style: output_style
with config::default_config("whatever")
};
2012-03-02 17:17:13 -06:00
let doc = extract::from_srv(srv, "");
let doc = attr_pass::mk_pass().f(srv, doc);
2012-03-09 20:12:15 -06:00
let doc = desc_to_brief_pass::mk_pass().f(srv, doc);
2012-03-02 17:17:13 -06:00
let doc = path_pass::mk_pass().f(srv, doc);
run(srv, doc, config)
2012-03-02 17:17:13 -06:00
}
}
}