why can I use IAssetRegistry Functions withou adding AssetRegistry to dependency in Build.cs

I can use IAssetRegistry like below in my own module:

FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked<FAssetRegistryModule>("AssetRegistry");
TArray<FAssetData> AssetData;
const UClass* Class = UStaticMesh::StaticClass();
AssetRegistryModule.Get().GetAssetsByClass(Class->GetFName(), AssetData);

but IAssetRegistry does not use ASSETREGISTRY_API to expose its functions to other modules:

UINTERFACE(MinimalApi, BlueprintType, meta = (CannotImplementInterfaceInBlueprint))
class UAssetRegistry : public UInterface
{
	GENERATED_UINTERFACE_BODY()
};

class IAssetRegistry
{
	GENERATED_IINTERFACE_BODY()
public:
	static IAssetRegistry* Get()
	{
		return UE::AssetRegistry::Private::IAssetRegistrySingleton::Get();
	}
	static IAssetRegistry& GetChecked()
	{
		IAssetRegistry* Singleton = UE::AssetRegistry::Private::IAssetRegistrySingleton::Get();
		check(Singleton);
		return *Singleton;
	}
        // other functions
}

refer to this slide: UE4 Modules - Google Slides

why can I use functions in IAsserRegistry without adding “AssetRegistry” to my module’s dependency?

Under the hood it calls UE::AssetRegistry::Private::IAssetRegistrySingleton::Get which lives in Engine\Source\Runtime\CoreUObject\Public\Misc\AssetRegistryInterface.h. The underlying singleton is exported via COREUOBJECT_API. These CoreUObject/AssetRegistry functions are all defined in headers, thus inline, which is why only the singleton storage needs to be marked for export.

For further context, refer to this comment on IAssetRegistrySingleton

/**
	* Storage for the singleton IAssetRegistry*
	* TODO: this storage should be a class static variable on IAssetRegistry, but that type is defined in the AssetRegistry module, and many modules try to access the singleton (and call virtual functions on it) without linking against
	* the AssetRegistry module, so the storage for the singleton needs to be defined in a lower-level module that all of those modules do include
	*/

Specifically:

so the storage for the singleton needs to be defined in a lower-level module that all of those modules do include