mirror of
https://github.com/gohugoio/hugo.git
synced 2024-11-07 20:30:36 -05:00
Speed up GetPage
``` name old time/op new time/op delta GetPage-10 413ns ± 0% 287ns ± 1% -30.47% (p=0.029 n=4+4) GetPageRegular/From_root-10 757ns ± 1% 706ns ± 1% -6.75% (p=0.029 n=4+4) GetPageRegular/Page_relative-10 838ns ± 1% 786ns ± 1% -6.16% (p=0.029 n=4+4) name old alloc/op new alloc/op delta GetPage-10 312B ± 0% 24B ± 0% -92.31% (p=0.029 n=4+4) GetPageRegular/From_root-10 328B ± 0% 200B ± 0% -39.02% (p=0.029 n=4+4) GetPageRegular/Page_relative-10 360B ± 0% 232B ± 0% -35.56% (p=0.029 n=4+4) name old allocs/op new allocs/op delta GetPage-10 8.00 ± 0% 2.00 ± 0% -75.00% (p=0.029 n=4+4) GetPageRegular/From_root-10 7.00 ± 0% 5.00 ± 0% -28.57% (p=0.029 n=4+4) GetPageRegular/Page_relative-10 9.00 ± 0% 7.00 ± 0% -22.22% (p=0.029 n=4+4) ```
This commit is contained in:
parent
f521336c81
commit
bf14d0cb26
2 changed files with 37 additions and 22 deletions
|
@ -54,15 +54,27 @@ func NormalizePathStringBasic(s string) string {
|
||||||
|
|
||||||
// ParseIdentity parses component c with path s into a StringIdentity.
|
// ParseIdentity parses component c with path s into a StringIdentity.
|
||||||
func (pp *PathParser) ParseIdentity(c, s string) identity.StringIdentity {
|
func (pp *PathParser) ParseIdentity(c, s string) identity.StringIdentity {
|
||||||
|
p := pp.parsePooled(c, s)
|
||||||
|
defer putPath(p)
|
||||||
|
return identity.StringIdentity(p.IdentifierBase())
|
||||||
|
}
|
||||||
|
|
||||||
|
// ParseBaseAndBaseNameNoIdentifier parses component c with path s into a base and a base name without any identifier.
|
||||||
|
func (pp *PathParser) ParseBaseAndBaseNameNoIdentifier(c, s string) (string, string) {
|
||||||
|
p := pp.parsePooled(c, s)
|
||||||
|
defer putPath(p)
|
||||||
|
return p.Base(), p.BaseNameNoIdentifier()
|
||||||
|
}
|
||||||
|
|
||||||
|
func (pp *PathParser) parsePooled(c, s string) *Path {
|
||||||
s = NormalizePathStringBasic(s)
|
s = NormalizePathStringBasic(s)
|
||||||
p := getPath()
|
p := getPath()
|
||||||
p.component = c
|
p.component = c
|
||||||
defer putPath(p)
|
|
||||||
p, err := pp.doParse(c, s, p)
|
p, err := pp.doParse(c, s, p)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
panic(err)
|
panic(err)
|
||||||
}
|
}
|
||||||
return identity.StringIdentity(p.IdentifierBase())
|
return p
|
||||||
}
|
}
|
||||||
|
|
||||||
// Parse parses component c with path s into Path using Hugo's content path rules.
|
// Parse parses component c with path s into Path using Hugo's content path rules.
|
||||||
|
@ -259,7 +271,9 @@ type Path struct {
|
||||||
|
|
||||||
var pathPool = &sync.Pool{
|
var pathPool = &sync.Pool{
|
||||||
New: func() any {
|
New: func() any {
|
||||||
return &Path{}
|
p := &Path{}
|
||||||
|
p.reset()
|
||||||
|
return p
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -268,6 +282,11 @@ func getPath() *Path {
|
||||||
}
|
}
|
||||||
|
|
||||||
func putPath(p *Path) {
|
func putPath(p *Path) {
|
||||||
|
p.reset()
|
||||||
|
pathPool.Put(p)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (p *Path) reset() {
|
||||||
p.s = ""
|
p.s = ""
|
||||||
p.posContainerLow = -1
|
p.posContainerLow = -1
|
||||||
p.posContainerHigh = -1
|
p.posContainerHigh = -1
|
||||||
|
@ -279,7 +298,6 @@ func putPath(p *Path) {
|
||||||
p.disabled = false
|
p.disabled = false
|
||||||
p.trimLeadingSlash = false
|
p.trimLeadingSlash = false
|
||||||
p.unnormalized = nil
|
p.unnormalized = nil
|
||||||
pathPool.Put(p)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// TrimLeadingSlash returns a copy of the Path with the leading slash removed.
|
// TrimLeadingSlash returns a copy of the Path with the leading slash removed.
|
||||||
|
|
|
@ -131,22 +131,21 @@ func (c *pageFinder) getContentNode(context page.Page, isReflink bool, ref strin
|
||||||
return c.getContentNodeForRef(context, isReflink, true, inRef, ref)
|
return c.getContentNodeForRef(context, isReflink, true, inRef, ref)
|
||||||
}
|
}
|
||||||
|
|
||||||
var refs []string
|
|
||||||
|
|
||||||
// We are always looking for a content file and having an extension greatly simplifies the code that follows,
|
// We are always looking for a content file and having an extension greatly simplifies the code that follows,
|
||||||
// even in the case where the extension does not match this one.
|
// even in the case where the extension does not match this one.
|
||||||
if ref == "/" {
|
if ref == "/" {
|
||||||
refs = append(refs, "/_index"+defaultContentExt)
|
if n, err := c.getContentNodeForRef(context, isReflink, false, inRef, "/_index"+defaultContentExt); n != nil || err != nil {
|
||||||
} else if strings.HasSuffix(ref, "/index") {
|
return n, err
|
||||||
refs = append(refs, ref+"/index"+defaultContentExt)
|
|
||||||
refs = append(refs, ref+defaultContentExt)
|
|
||||||
} else {
|
|
||||||
refs = append(refs, ref+defaultContentExt)
|
|
||||||
}
|
}
|
||||||
|
} else if strings.HasSuffix(ref, "/index") {
|
||||||
for _, ref := range refs {
|
if n, err := c.getContentNodeForRef(context, isReflink, false, inRef, ref+"/index"+defaultContentExt); n != nil || err != nil {
|
||||||
n, err := c.getContentNodeForRef(context, isReflink, false, inRef, ref)
|
return n, err
|
||||||
if n != nil || err != nil {
|
}
|
||||||
|
if n, err := c.getContentNodeForRef(context, isReflink, false, inRef, ref+defaultContentExt); n != nil || err != nil {
|
||||||
|
return n, err
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if n, err := c.getContentNodeForRef(context, isReflink, false, inRef, ref+defaultContentExt); n != nil || err != nil {
|
||||||
return n, err
|
return n, err
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -175,7 +174,7 @@ func (c *pageFinder) getContentNodeForRef(context page.Page, isReflink, hadExten
|
||||||
|
|
||||||
rel := path.Join(baseDir, ref)
|
rel := path.Join(baseDir, ref)
|
||||||
|
|
||||||
relPath := contentPathParser.Parse(files.ComponentFolderContent, rel)
|
relPath, _ := contentPathParser.ParseBaseAndBaseNameNoIdentifier(files.ComponentFolderContent, rel)
|
||||||
|
|
||||||
n, err := c.getContentNodeFromPath(relPath, ref)
|
n, err := c.getContentNodeFromPath(relPath, ref)
|
||||||
if n != nil || err != nil {
|
if n != nil || err != nil {
|
||||||
|
@ -195,9 +194,9 @@ func (c *pageFinder) getContentNodeForRef(context page.Page, isReflink, hadExten
|
||||||
return nil, nil
|
return nil, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
refPath := contentPathParser.Parse(files.ComponentFolderContent, ref)
|
relPath, nameNoIdentifier := contentPathParser.ParseBaseAndBaseNameNoIdentifier(files.ComponentFolderContent, ref)
|
||||||
|
|
||||||
n, err := c.getContentNodeFromPath(refPath, ref)
|
n, err := c.getContentNodeFromPath(relPath, ref)
|
||||||
|
|
||||||
if n != nil || err != nil {
|
if n != nil || err != nil {
|
||||||
return n, err
|
return n, err
|
||||||
|
@ -221,7 +220,7 @@ func (c *pageFinder) getContentNodeForRef(context page.Page, isReflink, hadExten
|
||||||
return nil, nil
|
return nil, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
n = c.pageMap.pageReverseIndex.Get(refPath.BaseNameNoIdentifier())
|
n = c.pageMap.pageReverseIndex.Get(nameNoIdentifier)
|
||||||
if n == ambiguousContentNode {
|
if n == ambiguousContentNode {
|
||||||
return nil, fmt.Errorf("page reference %q is ambiguous", inRef)
|
return nil, fmt.Errorf("page reference %q is ambiguous", inRef)
|
||||||
}
|
}
|
||||||
|
@ -254,9 +253,7 @@ func (c *pageFinder) getContentNodeFromRefReverseLookup(ref string, fi hugofs.Fi
|
||||||
return nil, nil
|
return nil, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *pageFinder) getContentNodeFromPath(refPath *paths.Path, ref string) (contentNodeI, error) {
|
func (c *pageFinder) getContentNodeFromPath(s string, ref string) (contentNodeI, error) {
|
||||||
s := refPath.Base()
|
|
||||||
|
|
||||||
n := c.pageMap.treePages.Get(s)
|
n := c.pageMap.treePages.Get(s)
|
||||||
if n != nil {
|
if n != nil {
|
||||||
return n, nil
|
return n, nil
|
||||||
|
|
Loading…
Reference in a new issue