func init() { playEnabled = true log.Println("initializing godoc ...") log.Printf(".zip file = %s", zipFilename) log.Printf(".zip GOROOT = %s", zipGoroot) log.Printf("index files = %s", indexFilenames) // Determine file system to use. local.Init(zipGoroot, zipFilename, "", "") fs.Bind("/", local.RootFS(), "/", vfs.BindReplace) fs.Bind("/lib/godoc", local.StaticFS(*lang), "/", vfs.BindReplace) fs.Bind("/doc", local.DocumentFS(*lang), "/", vfs.BindReplace) corpus := godoc.NewCorpus(fs) corpus.Verbose = false corpus.MaxResults = 10000 // matches flag default in main.go corpus.IndexEnabled = true corpus.IndexFiles = indexFilenames // translate hook corpus.SummarizePackage = func(importPath string) (summary string, showList, ok bool) { if pkg := local.Package(*lang, importPath); pkg != nil { summary = doc.Synopsis(pkg.Doc) } ok = (summary != "") return } corpus.TranslateDocPackage = func(pkg *doc.Package) *doc.Package { return local.Package(*lang, pkg.ImportPath, pkg) } if err := corpus.Init(); err != nil { log.Fatal(err) } if corpus.IndexEnabled && corpus.IndexFiles != "" { go corpus.RunIndexer() } pres = godoc.NewPresentation(corpus) pres.TabWidth = 8 pres.ShowPlayground = true pres.ShowExamples = true pres.DeclLinks = true pres.NotesRx = regexp.MustCompile("BUG") readTemplates(pres, true) registerHandlers(pres) log.Println("godoc initialization complete") }
func ParsePackageInfo(name, lang string) (pkg *PackageInfo, err error) { type PkgInfo struct { Dir string // directory containing package sources Name string // package name ImportPath string // import path of package in dir } var pkgInfo PkgInfo listOut, err := exec.Command(`go`, `list`, `-json`, name).Output() if err != nil { return } err = json.Unmarshal(listOut, &pkgInfo) if err != nil { return } fset := token.NewFileSet() past, err := parser.ParseDir(fset, pkgInfo.Dir, func(fi os.FileInfo) bool { if strings.HasSuffix(fi.Name(), "_test.go") { return false } return true }, parser.ParseComments, ) if err != nil { return } var mode doc.Mode if pkgInfo.ImportPath == "builtin" { mode = doc.AllDecls } pdoc := doc.New(past[pkgInfo.Name], pkgInfo.ImportPath, mode) pdocLocal := local.Package(lang, pkgInfo.ImportPath) pkg = &PackageInfo{ Lang: lang, FSet: fset, PAst: past[pkgInfo.Name], PDoc: pdoc, PDocLocal: pdocLocal, PDocMap: make(map[string]string), } pkg.initDocTable("", pkg.PDoc) if pkg.PDocLocal != nil { pkg.initDocTable(lang, pkg.PDocLocal) } return }
func runGodoc() { // Determine file system to use. local.Init(*goroot, *zipfile, *templateDir, build.Default.GOPATH) fs.Bind("/", local.RootFS(), "/", vfs.BindReplace) fs.Bind("/lib/godoc", local.StaticFS(*lang), "/", vfs.BindReplace) fs.Bind("/doc", local.DocumentFS(*lang), "/", vfs.BindReplace) httpMode := *httpAddr != "" var typeAnalysis, pointerAnalysis bool if *analysisFlag != "" { for _, a := range strings.Split(*analysisFlag, ",") { switch a { case "type": typeAnalysis = true case "pointer": pointerAnalysis = true default: log.Fatalf("unknown analysis: %s", a) } } } corpus := godoc.NewCorpus(fs) // translate hook corpus.SummarizePackage = func(importPath string) (summary string, showList, ok bool) { if pkg := local.Package(*lang, importPath); pkg != nil { summary = doc.Synopsis(pkg.Doc) } ok = (summary != "") return } corpus.TranslateDocPackage = func(pkg *doc.Package) *doc.Package { return local.Package(*lang, pkg.ImportPath, pkg) } corpus.Verbose = *verbose corpus.MaxResults = *maxResults corpus.IndexEnabled = *indexEnabled && httpMode if *maxResults == 0 { corpus.IndexFullText = false } corpus.IndexFiles = *indexFiles corpus.IndexThrottle = *indexThrottle if *writeIndex { corpus.IndexThrottle = 1.0 corpus.IndexEnabled = true } if *writeIndex || httpMode || *urlFlag != "" { if err := corpus.Init(); err != nil { log.Fatal(err) } } pres = godoc.NewPresentation(corpus) pres.TabWidth = *tabWidth pres.ShowTimestamps = *showTimestamps pres.ShowPlayground = *showPlayground pres.ShowExamples = *showExamples pres.DeclLinks = *declLinks pres.SrcMode = *srcMode pres.HTMLMode = *html if *notesRx != "" { pres.NotesRx = regexp.MustCompile(*notesRx) } readTemplates(pres, httpMode || *urlFlag != "") registerHandlers(pres) if *writeIndex { // Write search index and exit. if *indexFiles == "" { log.Fatal("no index file specified") } log.Println("initialize file systems") *verbose = true // want to see what happens corpus.UpdateIndex() log.Println("writing index file", *indexFiles) f, err := os.Create(*indexFiles) if err != nil { log.Fatal(err) } index, _ := corpus.CurrentIndex() _, err = index.WriteTo(f) if err != nil { log.Fatal(err) } log.Println("done") return } // Print content that would be served at the URL *urlFlag. if *urlFlag != "" { handleURLFlag() return } if httpMode { // HTTP server mode. var handler http.Handler = http.DefaultServeMux if *verbose { log.Printf("Go Documentation Server") log.Printf("version = %s", runtime.Version()) log.Printf("address = %s", *httpAddr) log.Printf("goroot = %s", *goroot) log.Printf("tabwidth = %d", *tabWidth) switch { case !*indexEnabled: log.Print("search index disabled") case *maxResults > 0: log.Printf("full text index enabled (maxresults = %d)", *maxResults) default: log.Print("identifier search index enabled") } handler = loggingHandler(handler) } // Initialize search index. if *indexEnabled { go corpus.RunIndexer() } // Start type/pointer analysis. if typeAnalysis || pointerAnalysis { go analysis.Run(pointerAnalysis, &corpus.Analysis) } // Start http server. if err := http.ListenAndServe(*httpAddr, handler); err != nil { log.Fatalf("ListenAndServe %s: %v", *httpAddr, err) } return } if *query { handleRemoteSearch() return } if err := godoc.CommandLine(os.Stdout, fs, pres, flag.Args()); err != nil { log.Print(err) } }