Skip to content

Race Condition Issue : Protect union registry with sync.Map to prevent concurrent write panics (race condition) #4326

@DARSHANR007

Description

@DARSHANR007

Confirm this is a Go library issue and not an underlying Cloudflare API issue

  • This is an issue with the Go library

Describe the Bug

Problem

The union registry (unionRegistry and unionVariants global maps in internal/apijson/registry.go) are unprotected and not thread-safe.

When multiple goroutines call RegisterUnion() simultaneously, the Go runtime panics with:

fatal error: concurrent map writes

The issue occurs because both global maps are written concurrently without synchronization.


Vulnerable Code

File: internal/apijson/registry.go

// Lines 15-16: Unprotected maps
var unionRegistry = map[reflect.Type]unionEntry{}
var unionVariants = map[reflect.Type]interface{}{}

// Lines 24-30: Concurrent writes cause panic
func RegisterUnion(typ reflect.Type, discriminator string, variants ...UnionVariant) {
    unionRegistry[typ] = unionEntry{...} // concurrent write
    for _, variant := range variants {
        unionVariants[variant.Type] = typ // concurrent write
    }
}

Multiple goroutines calling RegisterUnion() simultaneously can trigger a runtime panic.


Steps To Reproduce

  1. Create multiple goroutines that call RegisterUnion() concurrently.
  2. Run the race demo test repeatedly.
  3. The runtime eventually panics with concurrent map writes.

Command

go test ./internal/apijson -run TestBareMapConcurrency -v -count=50

Expected Behavior

The registry should support concurrent registration safely without panicking.

Expected approaches could include:

  • protecting the maps with sync.RWMutex
  • using sync.Map
  • or ensuring registration only happens during initialization

Actual Output

=== RUN   TestBareMapConcurrency
fatal error: concurrent map writes

goroutine 12 [running]:
runtime/maps.go:1046 +0x18
github.com/cloudflare/cloudflare-go/v7/internal/apijson.TestBareMapConcurrency.func1(0x5)
    internal/apijson/registry_race_demo_test.go:138 +0x128

Process exit code: 2

Error

fatal error: concurrent map writes

Environment

OS

Windows/amd64

Go Version

Go 1.22.0

Library Version

github.com/cloudflare/cloudflare-go/v7

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions