Skip to content

Commit

Permalink
fix panic concurrent parse
Browse files Browse the repository at this point in the history
  • Loading branch information
YousefHagag committed Feb 10, 2025
1 parent 3041b3b commit e426c77
Show file tree
Hide file tree
Showing 3 changed files with 20 additions and 12 deletions.
2 changes: 1 addition & 1 deletion concurrent_parse_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ import (
func TestConcurrentParse(t *testing.T) {
var wg sync.WaitGroup

for i := 0; i < 10; i++ {
for i := 0; i < 100; i++ {
wg.Add(1)
go func() {
defer wg.Done()
Expand Down
11 changes: 11 additions & 0 deletions schema.go
Original file line number Diff line number Diff line change
Expand Up @@ -131,6 +131,17 @@ func (c *SchemaCache) Get(name string) Schema {
return nil
}

// AddAll adds all schemas from the given cache to the current cache.
func (c *SchemaCache) AddAll(cache *SchemaCache) {
if cache == nil {
return
}
cache.cache.Range(func(key, value interface{}) bool {
c.cache.Store(key, value)
return true
})
}

// Schemas is a slice of Schemas.
type Schemas []Schema

Expand Down
19 changes: 8 additions & 11 deletions schema_parse.go
Original file line number Diff line number Diff line change
Expand Up @@ -64,16 +64,7 @@ func ParseFiles(paths ...string) (Schema, error) {

// ParseBytes parses a schema byte slice.
func ParseBytes(schema []byte) (Schema, error) {
var internalCache = &SchemaCache{}
DefaultSchemaCache.cache.Range(func(key, value any) bool {
internalCache.Add(key.(string), value.(Schema))
return true
})
s, err := ParseBytesWithCache(schema, "", internalCache)
internalCache.cache.Range(func(key, value any) bool {
DefaultSchemaCache.Add(key.(string), value.(Schema))
return true
})
s, err := ParseBytesWithCache(schema, "", DefaultSchemaCache)
return s, err
}

Expand All @@ -84,11 +75,17 @@ func ParseBytesWithCache(schema []byte, namespace string, cache *SchemaCache) (S
json = string(schema)
}

internalCache := &SchemaCache{}
internalCache.AddAll(DefaultSchemaCache)

seen := seenCache{}
s, err := parseType(namespace, json, seen, cache)
s, err := parseType(namespace, json, seen, internalCache)
if err != nil {
return nil, err
}

DefaultSchemaCache.AddAll(internalCache)

return derefSchema(s), nil
}

Expand Down

0 comments on commit e426c77

Please sign in to comment.