Syntax tree now stores map of require names -> full paths
This commit is contained in:
parent
596deaf0c3
commit
7e972e2132
@ -15,6 +15,14 @@ func (tree SyntaxTree) Sections () (iterator types.Iterator[Section]) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ResolveRequire returns the full path, from the filesystem root, of an import.
|
||||||
|
// This method will return false for exists if the module has not been
|
||||||
|
// imported.
|
||||||
|
func (tree SyntaxTree) ResolveRequire (name string) (path string, exists bool) {
|
||||||
|
path, exists = tree.requires[name]
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
// Kind returns the section's kind (SectionKindType).
|
// Kind returns the section's kind (SectionKindType).
|
||||||
func (section TypeSection) Kind () (kind SectionKind) {
|
func (section TypeSection) Kind () (kind SectionKind) {
|
||||||
kind = SectionKindType
|
kind = SectionKindType
|
||||||
|
@ -1,10 +1,14 @@
|
|||||||
package parser
|
package parser
|
||||||
|
|
||||||
|
import "os"
|
||||||
|
import "path/filepath"
|
||||||
import "git.tebibyte.media/arf/arf/lexer"
|
import "git.tebibyte.media/arf/arf/lexer"
|
||||||
import "git.tebibyte.media/arf/arf/infoerr"
|
import "git.tebibyte.media/arf/arf/infoerr"
|
||||||
|
|
||||||
// parseMeta parsese the metadata header at the top of an arf file.
|
// parseMeta parsese the metadata header at the top of an arf file.
|
||||||
func (parser *ParsingOperation) parseMeta () (err error) {
|
func (parser *ParsingOperation) parseMeta () (err error) {
|
||||||
|
cwd, _ := os.Getwd()
|
||||||
|
|
||||||
for {
|
for {
|
||||||
err = parser.expect (
|
err = parser.expect (
|
||||||
lexer.TokenKindName,
|
lexer.TokenKindName,
|
||||||
@ -31,7 +35,30 @@ func (parser *ParsingOperation) parseMeta () (err error) {
|
|||||||
case "license":
|
case "license":
|
||||||
parser.tree.license = value
|
parser.tree.license = value
|
||||||
case "require":
|
case "require":
|
||||||
parser.tree.requires = append(parser.tree.requires, value)
|
// if import path is relative, get absolute path.
|
||||||
|
if value[0] == '.' {
|
||||||
|
value = filepath.Join(cwd, value)
|
||||||
|
} else if value[0] != '/' {
|
||||||
|
// TODO: get arf import path from an env
|
||||||
|
// variable, and default to this if not found.
|
||||||
|
// then, search all paths.
|
||||||
|
value = filepath.Join (
|
||||||
|
"/usr/local/include/arf/",
|
||||||
|
value)
|
||||||
|
}
|
||||||
|
|
||||||
|
basename := filepath.Base(value)
|
||||||
|
_, exists := parser.tree.requires[basename]
|
||||||
|
|
||||||
|
if exists {
|
||||||
|
err = parser.token.NewError (
|
||||||
|
"cannot require \"" + basename +
|
||||||
|
"\" multiple times",
|
||||||
|
infoerr.ErrorKindError)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
parser.tree.requires[basename] = value
|
||||||
default:
|
default:
|
||||||
parser.token.NewError (
|
parser.token.NewError (
|
||||||
"unrecognized metadata field: " + field,
|
"unrecognized metadata field: " + field,
|
||||||
|
@ -1,14 +1,18 @@
|
|||||||
package parser
|
package parser
|
||||||
|
|
||||||
|
import "os"
|
||||||
import "testing"
|
import "testing"
|
||||||
|
import "path/filepath"
|
||||||
|
|
||||||
func TestMeta (test *testing.T) {
|
func TestMeta (test *testing.T) {
|
||||||
|
cwd, _ := os.Getwd()
|
||||||
checkTree ("../tests/parser/meta", false,
|
checkTree ("../tests/parser/meta", false,
|
||||||
`:arf
|
`:arf
|
||||||
author "Sasha Koshka"
|
author "Sasha Koshka"
|
||||||
license "GPLv3"
|
license "GPLv3"
|
||||||
require "someModule"
|
require "` + filepath.Join(cwd, "./some/local/module") + `"
|
||||||
require "otherModule"
|
require "/some/absolute/path/to/someModule"
|
||||||
|
require "/usr/include/arf/someLibraryInstalledInStandardLocation"
|
||||||
---
|
---
|
||||||
`, test)
|
`, test)
|
||||||
}
|
}
|
||||||
|
@ -38,6 +38,7 @@ func Fetch (modulePath string, skim bool) (tree SyntaxTree, err error) {
|
|||||||
modulePath: modulePath,
|
modulePath: modulePath,
|
||||||
skimming: skim,
|
skimming: skim,
|
||||||
tree: SyntaxTree {
|
tree: SyntaxTree {
|
||||||
|
requires: make(map[string] string),
|
||||||
sections: make(map[string] Section),
|
sections: make(map[string] Section),
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
@ -4,8 +4,6 @@ import "git.tebibyte.media/arf/arf/file"
|
|||||||
import "git.tebibyte.media/arf/arf/types"
|
import "git.tebibyte.media/arf/arf/types"
|
||||||
import "git.tebibyte.media/arf/arf/infoerr"
|
import "git.tebibyte.media/arf/arf/infoerr"
|
||||||
|
|
||||||
// TODO: implement table of import names -> full paths from /. perhaps replace
|
|
||||||
// requires[] with this, and build it when parsing the meta section.
|
|
||||||
// SyntaxTree represents an abstract syntax tree. It covers an entire module. It
|
// SyntaxTree represents an abstract syntax tree. It covers an entire module. It
|
||||||
// can be expected to be syntactically correct, but it might not be semantically
|
// can be expected to be syntactically correct, but it might not be semantically
|
||||||
// correct (because it has not been analyzed yet.)
|
// correct (because it has not been analyzed yet.)
|
||||||
@ -13,7 +11,7 @@ type SyntaxTree struct {
|
|||||||
license string
|
license string
|
||||||
author string
|
author string
|
||||||
|
|
||||||
requires []string
|
requires map[string] string
|
||||||
sections map[string] Section
|
sections map[string] Section
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
:arf
|
:arf
|
||||||
author "Sasha Koshka"
|
author "Sasha Koshka"
|
||||||
license "GPLv3"
|
license "GPLv3"
|
||||||
require "someModule"
|
require "./some/local/module"
|
||||||
require "otherModule"
|
require "/some/absolute/path/to/someModule"
|
||||||
|
require "someLibraryInstalledInStandardLocation"
|
||||||
---
|
---
|
||||||
|
Reference in New Issue
Block a user