|
|
|
package wikilink
|
|
|
|
|
|
|
|
import (
|
|
|
|
"strings"
|
|
|
|
|
|
|
|
"go.uber.org/zap"
|
|
|
|
)
|
|
|
|
|
|
|
|
func isOpenLink(s string) bool {
|
|
|
|
return strings.HasPrefix(s, OpenLink)
|
|
|
|
}
|
|
|
|
|
|
|
|
func isCloseLink(s string) bool {
|
|
|
|
return strings.HasPrefix(s, CloseLink)
|
|
|
|
}
|
|
|
|
|
|
|
|
func isAlias(s string) bool {
|
|
|
|
return strings.HasPrefix(s, Alias)
|
|
|
|
}
|
|
|
|
|
|
|
|
func isHeading(s string) bool {
|
|
|
|
return strings.HasPrefix(s, Heading)
|
|
|
|
}
|
|
|
|
|
|
|
|
func isBlockRef(s string) bool {
|
|
|
|
return strings.HasPrefix(s, BlockRef)
|
|
|
|
}
|
|
|
|
|
|
|
|
func lexIdent(l *Lexer) stateFn {
|
|
|
|
for {
|
|
|
|
r := l.next()
|
|
|
|
l.L.Named("lexIdent").Debug("stepping through lexIdent",
|
|
|
|
zap.String("r", string(r)),
|
|
|
|
)
|
|
|
|
s := l.input[l.GetPos():]
|
|
|
|
if r == '\\' { // i think this will handle escape characters?
|
|
|
|
break
|
|
|
|
}
|
|
|
|
switch {
|
|
|
|
case isBlockRef(s):
|
|
|
|
l.emit(ItemIdent)
|
|
|
|
return lexBlockRef
|
|
|
|
case isAlias(s):
|
|
|
|
l.emit(ItemIdent)
|
|
|
|
return lexAlias
|
|
|
|
case isCloseLink(s):
|
|
|
|
l.emit(ItemIdent)
|
|
|
|
return lexCloseLink
|
|
|
|
case isHeading(s):
|
|
|
|
l.emit(ItemIdent)
|
|
|
|
return lexHeading
|
|
|
|
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return l.errorf("malformed link")
|
|
|
|
}
|
|
|
|
|
|
|
|
func lexHeading(l *Lexer) stateFn {
|
|
|
|
l.SetPos(l.GetPos() + len(Heading))
|
|
|
|
l.emit(ItemHeading)
|
|
|
|
|
|
|
|
return lexIdent
|
|
|
|
}
|
|
|
|
|
|
|
|
func lexBlockRef(l *Lexer) stateFn {
|
|
|
|
l.SetPos(l.GetPos() + len(BlockRef))
|
|
|
|
l.emit(ItemBlockRef)
|
|
|
|
|
|
|
|
return lexIdent
|
|
|
|
}
|
|
|
|
|
|
|
|
func lexAlias(l *Lexer) stateFn {
|
|
|
|
l.SetPos(l.GetPos() + len(Alias))
|
|
|
|
l.emit(ItemAlias)
|
|
|
|
|
|
|
|
return lexIdent
|
|
|
|
}
|
|
|
|
|
|
|
|
func lexText(l *Lexer) stateFn {
|
|
|
|
for {
|
|
|
|
if isOpenLink(l.input[l.GetPos():]) {
|
|
|
|
return lexOpenLink
|
|
|
|
}
|
|
|
|
r := l.next()
|
|
|
|
switch {
|
|
|
|
case r == EOF || r == '\n':
|
|
|
|
l.emit(ItemText)
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func lexOpenLink(l *Lexer) stateFn {
|
|
|
|
l.SetPos(l.GetPos() + len(OpenLink))
|
|
|
|
l.emit(ItemOpenLink)
|
|
|
|
|
|
|
|
return lexIdent
|
|
|
|
}
|
|
|
|
|
|
|
|
func lexCloseLink(l *Lexer) stateFn {
|
|
|
|
l.SetPos(l.GetPos() + len(CloseLink))
|
|
|
|
l.emit(ItemCloseLink)
|
|
|
|
|
|
|
|
return lexText
|
|
|
|
}
|