Skip to content

Make ServiceKeys, ServiceTypes, ServiceLifetimes internal to prevent external mutation #28

Description

@AGiorgetti

Description

ServiceKeys, ServiceTypes, ServiceLifetimes, and ServiceKeys<T> in ServiceProviderFactory.cs are declared as public classes that inherit from HashSet<>. This exposes mutable collection APIs (.Add(), .Remove(), .Clear()) to all consumers of the library.

public class ServiceKeys<T> : HashSet<object> { ... }
public class ServiceKeys : HashSet<object>;
public class ServiceTypes : HashSet<Type>;
public class ServiceLifetimes { ... }  // has public Add() method

Impact

Library consumers can mutate these tracking collections after the service provider is built, potentially corrupting the IsServiceRegistered / IsKeyedServiceRegistered / lifetime-check infrastructure.

Suggested Fix

These types are only used internally by ServiceProviderExtensions. Consider:

  1. Making them internal (they're registered as singletons and resolved by type, so internal visibility is sufficient)
  2. Or wrapping them in read-only interfaces for the public API

Note: ServiceKeys<T> needs to remain resolvable by the generic GetAllServices method, but that can work with internal visibility since both are in the same assembly.

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions