vdoc: move local scope-based doc generation to its own function (#6565)
parent
7a29240b00
commit
2b1a5d7a56
129
vlib/v/doc/doc.v
129
vlib/v/doc/doc.v
|
@ -30,6 +30,7 @@ pub mut:
|
||||||
fmt fmt.Fmt
|
fmt fmt.Fmt
|
||||||
time_generated time.Time
|
time_generated time.Time
|
||||||
with_pos bool
|
with_pos bool
|
||||||
|
with_head bool = true
|
||||||
filename string
|
filename string
|
||||||
pos int
|
pos int
|
||||||
is_vlib bool
|
is_vlib bool
|
||||||
|
@ -295,8 +296,9 @@ fn get_parent_mod(dir string) ?string {
|
||||||
return file_ast.mod.name
|
return file_ast.mod.name
|
||||||
}
|
}
|
||||||
|
|
||||||
fn (mut d Doc) generate_from_ast(file_ast ast.File, orig_mod_name string) {
|
pub fn (mut d Doc) generate_from_ast(file_ast ast.File, orig_mod_name string) []DocNode {
|
||||||
mut const_idx := -1
|
mut const_idx := -1
|
||||||
|
mut contents := []DocNode{}
|
||||||
stmts := file_ast.stmts
|
stmts := file_ast.stmts
|
||||||
d.fmt.file = file_ast
|
d.fmt.file = file_ast
|
||||||
d.fmt.set_current_module_name(orig_mod_name)
|
d.fmt.set_current_module_name(orig_mod_name)
|
||||||
|
@ -319,6 +321,9 @@ fn (mut d Doc) generate_from_ast(file_ast ast.File, orig_mod_name string) {
|
||||||
}
|
}
|
||||||
// TODO: Fetch head comment once
|
// TODO: Fetch head comment once
|
||||||
if stmt is ast.Module {
|
if stmt is ast.Module {
|
||||||
|
if !d.with_head {
|
||||||
|
continue
|
||||||
|
}
|
||||||
// the previous comments were probably a copyright/license one
|
// the previous comments were probably a copyright/license one
|
||||||
module_comment := get_comment_block_right_before(prev_comments)
|
module_comment := get_comment_block_right_before(prev_comments)
|
||||||
prev_comments = []
|
prev_comments = []
|
||||||
|
@ -336,46 +341,58 @@ fn (mut d Doc) generate_from_ast(file_ast ast.File, orig_mod_name string) {
|
||||||
if last_import_stmt_idx > 0 && sidx == last_import_stmt_idx {
|
if last_import_stmt_idx > 0 && sidx == last_import_stmt_idx {
|
||||||
// the accumulated comments were interspersed before/between the imports;
|
// the accumulated comments were interspersed before/between the imports;
|
||||||
// just add them all to the module comment:
|
// just add them all to the module comment:
|
||||||
|
if d.with_head {
|
||||||
import_comments := merge_comments(prev_comments)
|
import_comments := merge_comments(prev_comments)
|
||||||
if d.head.comment != '' {
|
if d.head.comment != '' {
|
||||||
d.head.comment += '\n'
|
d.head.comment += '\n'
|
||||||
}
|
}
|
||||||
d.head.comment += import_comments
|
d.head.comment += import_comments
|
||||||
|
}
|
||||||
prev_comments = []
|
prev_comments = []
|
||||||
imports_section = false
|
imports_section = false
|
||||||
}
|
}
|
||||||
if stmt is ast.Import {
|
if stmt is ast.Import {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
signature := d.get_signature(stmt, file_ast)
|
mut node := DocNode{
|
||||||
pos := d.get_pos(stmt)
|
name: d.get_name(stmt)
|
||||||
mut name := d.get_name(stmt)
|
content: d.get_signature(stmt, file_ast)
|
||||||
if (!signature.starts_with('pub') && d.pub_only) || stmt is ast.GlobalDecl {
|
comment: ''
|
||||||
|
pos: convert_pos(file_ast.path, d.get_pos(stmt))
|
||||||
|
file_path: file_ast.path
|
||||||
|
}
|
||||||
|
if (!node.content.starts_with('pub') && d.pub_only) || stmt is ast.GlobalDecl {
|
||||||
prev_comments = []
|
prev_comments = []
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
if name.starts_with(orig_mod_name + '.') {
|
if node.name.starts_with(orig_mod_name + '.') {
|
||||||
name = name.all_after(orig_mod_name + '.')
|
node.name = node.name.all_after(orig_mod_name + '.')
|
||||||
}
|
|
||||||
mut node := DocNode{
|
|
||||||
name: name
|
|
||||||
content: signature
|
|
||||||
comment: ''
|
|
||||||
pos: convert_pos(file_ast.path, pos)
|
|
||||||
file_path: file_ast.path
|
|
||||||
}
|
}
|
||||||
if node.name.len == 0 && node.comment.len == 0 && node.content.len == 0 {
|
if node.name.len == 0 && node.comment.len == 0 && node.content.len == 0 {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
if stmt is ast.FnDecl {
|
match stmt {
|
||||||
|
ast.ConstDecl {
|
||||||
|
if const_idx == -1 {
|
||||||
|
const_idx = sidx
|
||||||
|
} else {
|
||||||
|
node.attrs['parent'] = 'Constants'
|
||||||
|
}
|
||||||
|
node.attrs['category'] = 'Constants'
|
||||||
|
}
|
||||||
|
ast.EnumDecl { node.attrs['category'] = 'Enums' }
|
||||||
|
ast.InterfaceDecl { node.attrs['category'] = 'Interfaces' }
|
||||||
|
ast.StructDecl { node.attrs['category'] = 'Structs' }
|
||||||
|
ast.TypeDecl { node.attrs['category'] = 'Typedefs' }
|
||||||
|
ast.FnDecl {
|
||||||
if stmt.is_deprecated {
|
if stmt.is_deprecated {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
if stmt.receiver.typ != 0 {
|
if stmt.receiver.typ != 0 {
|
||||||
node.attrs['parent'] = d.fmt.type_to_str(stmt.receiver.typ).trim_left('&')
|
node.attrs['parent'] = d.fmt.type_to_str(stmt.receiver.typ).trim_left('&')
|
||||||
p_idx := d.contents.index_by_name(node.attrs['parent'])
|
p_idx := contents.index_by_name(node.attrs['parent'])
|
||||||
if p_idx == -1 && node.attrs['parent'] != 'void' {
|
if p_idx == -1 && node.attrs['parent'] != 'void' {
|
||||||
d.contents << DocNode{
|
contents << DocNode{
|
||||||
name: node.attrs['parent']
|
name: node.attrs['parent']
|
||||||
content: ''
|
content: ''
|
||||||
comment: ''
|
comment: ''
|
||||||
|
@ -385,32 +402,48 @@ fn (mut d Doc) generate_from_ast(file_ast ast.File, orig_mod_name string) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
node.attrs['category'] = if node.attrs['parent'] in ['void', ''] ||
|
||||||
|
!node.attrs.exists('parent') { 'Functions' } else { 'Methods' }
|
||||||
}
|
}
|
||||||
if stmt is ast.ConstDecl {
|
|
||||||
if const_idx == -1 {
|
|
||||||
const_idx = sidx
|
|
||||||
} else {
|
|
||||||
node.attrs['parent'] = 'Constants'
|
|
||||||
}
|
|
||||||
}
|
|
||||||
match stmt {
|
|
||||||
ast.ConstDecl { node.attrs['category'] = 'Constants' }
|
|
||||||
ast.EnumDecl { node.attrs['category'] = 'Enums' }
|
|
||||||
ast.InterfaceDecl { node.attrs['category'] = 'Interfaces' }
|
|
||||||
ast.StructDecl { node.attrs['category'] = 'Structs' }
|
|
||||||
ast.TypeDecl { node.attrs['category'] = 'Typedefs' }
|
|
||||||
ast.FnDecl { node.attrs['category'] = if node.attrs['parent'] in ['void', ''] ||
|
|
||||||
!node.attrs.exists('parent') { 'Functions' } else { 'Methods' } }
|
|
||||||
else {}
|
else {}
|
||||||
}
|
}
|
||||||
d.contents << node
|
contents << node
|
||||||
if d.with_comments && (prev_comments.len > 0) {
|
if d.with_comments && (prev_comments.len > 0) {
|
||||||
last_comment := d.contents[d.contents.len - 1].comment
|
last_comment := contents[contents.len - 1].comment
|
||||||
cmt := last_comment + '\n' + get_comment_block_right_before(prev_comments)
|
cmt := last_comment + '\n' + get_comment_block_right_before(prev_comments)
|
||||||
d.contents[d.contents.len - 1].comment = cmt
|
contents[contents.len - 1].comment = cmt
|
||||||
}
|
}
|
||||||
prev_comments = []
|
prev_comments = []
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return contents
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn (mut d Doc) generate_from_ast_with_pos(file_ast ast.File, pos int) []DocNode {
|
||||||
|
lscope := file_ast.scope.innermost(pos)
|
||||||
|
mut contents := []DocNode{}
|
||||||
|
for name, val in lscope.objects {
|
||||||
|
if val !is ast.Var {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
vr_data := val as ast.Var
|
||||||
|
vr_expr := vr_data.expr
|
||||||
|
l_node := DocNode{
|
||||||
|
name: name
|
||||||
|
content: ''
|
||||||
|
comment: ''
|
||||||
|
pos: convert_pos(file_ast.path, vr_data.pos)
|
||||||
|
file_path: file_ast.path
|
||||||
|
attrs: {
|
||||||
|
'category': 'Variable'
|
||||||
|
'return_type': d.expr_typ_to_string(vr_expr)
|
||||||
|
'local': 'true'
|
||||||
|
}
|
||||||
|
}
|
||||||
|
contents << l_node
|
||||||
|
}
|
||||||
|
|
||||||
|
return contents
|
||||||
}
|
}
|
||||||
|
|
||||||
fn (mut d Doc) expr_typ_to_string(ex ast.Expr) string {
|
fn (mut d Doc) expr_typ_to_string(ex ast.Expr) string {
|
||||||
|
@ -458,37 +491,19 @@ fn (mut d Doc) generate() ?Doc {
|
||||||
if module_name != 'main' && parent_mod_name.len > 0 {
|
if module_name != 'main' && parent_mod_name.len > 0 {
|
||||||
module_name = parent_mod_name + '.' + module_name
|
module_name = parent_mod_name + '.' + module_name
|
||||||
}
|
}
|
||||||
|
if d.with_head {
|
||||||
d.head = DocNode{
|
d.head = DocNode{
|
||||||
name: module_name
|
name: module_name
|
||||||
content: 'module $module_name'
|
content: 'module $module_name'
|
||||||
comment: ''
|
comment: ''
|
||||||
}
|
}
|
||||||
|
}
|
||||||
} else if file_ast.mod.name != orig_mod_name {
|
} else if file_ast.mod.name != orig_mod_name {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
d.generate_from_ast(file_ast, orig_mod_name)
|
d.contents << d.generate_from_ast(file_ast, orig_mod_name)
|
||||||
if file_ast.path == d.filename {
|
if file_ast.path == d.filename {
|
||||||
lscope := file_ast.scope.innermost(d.pos)
|
d.contents << d.generate_from_ast_with_pos(file_ast, d.pos)
|
||||||
for name, val in lscope.objects {
|
|
||||||
if val !is ast.Var {
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
vr_data := val as ast.Var
|
|
||||||
vr_expr := vr_data.expr
|
|
||||||
l_node := DocNode{
|
|
||||||
name: name
|
|
||||||
content: ''
|
|
||||||
comment: ''
|
|
||||||
pos: convert_pos(file_ast.path, vr_data.pos)
|
|
||||||
file_path: file_ast.path
|
|
||||||
attrs: {
|
|
||||||
'category': 'Variable'
|
|
||||||
'return_type': d.expr_typ_to_string(vr_expr)
|
|
||||||
'local': 'true'
|
|
||||||
}
|
|
||||||
}
|
|
||||||
d.contents << l_node
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
d.fmt.mod2alias = map[string]string{}
|
d.fmt.mod2alias = map[string]string{}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue