alibaba/spring-ai-alibaba · error · IllegalArgumentException

SkillRegistry cannot be null

Error message

SkillRegistry cannot be null

What it means

SearchSkillsTool's constructor rejects a null SkillRegistry. Searching skills is entirely registry-backed, so the library validates the dependency at construction and fails fast rather than throwing NPEs on first use.

Source

Thrown at spring-ai-alibaba-agent-framework/src/main/java/com/alibaba/cloud/ai/graph/agent/hook/skills/SearchSkillsTool.java:51

 */
public class SearchSkillsTool implements BiFunction<SearchSkillsTool.SearchSkillsRequest, ToolContext, String> {

	public static final String SEARCH_SKILLS = "search_skills";

	public static final String DESCRIPTION = """
			Searches the current SkillRegistry by skill name, description, or skill path.
			
			Usage:
			- Provide a query to search the locally registered skills
			- Matching is performed against name, description, and path
			- Returns matching skills with their descriptions and paths
			""";

	private final SkillRegistry skillRegistry;

	public SearchSkillsTool(SkillRegistry skillRegistry) {
		if (skillRegistry == null) {
			throw new IllegalArgumentException("SkillRegistry cannot be null");
		}
		this.skillRegistry = skillRegistry;
	}

	public static ToolCallback createSearchSkillsToolCallback(SkillRegistry skillRegistry, String description) {
		return FunctionToolCallback.builder(SEARCH_SKILLS, new SearchSkillsTool(skillRegistry))
				.description(description != null ? description : DESCRIPTION)
				.inputType(SearchSkillsRequest.class)
				.build();
	}

	@Override
	public String apply(SearchSkillsRequest request, ToolContext toolContext) {
		String query = request != null ? request.query : null;
		List<SkillMetadata> skills = skillRegistry.search(query);
		if (skills.isEmpty()) {
			return "No skills found.";
		}

View on GitHub (pinned to f82da0b50f)

Solutions

  1. Build the registry before the tool: SkillRegistry registry = FileSystemSkillRegistry.builder().build();
  2. Conditionally register the search-skills tool only when a non-null registry exists.
  3. Check the call site of createSearchSkillsToolCallback and ensure it forwards a real registry.

Example fix

// before
ToolCallback cb = SearchSkillsTool.createSearchSkillsToolCallback(null, "Search skills");
// after
SkillRegistry registry = FileSystemSkillRegistry.builder().build();
ToolCallback cb = SearchSkillsTool.createSearchSkillsToolCallback(registry, "Search skills");
Defensive patterns

Strategy: validation

Validate before calling

if (registry == null) { throw new IllegalStateException("Create SkillRegistry before SearchSkillsTool"); }
SearchSkillsTool tool = new SearchSkillsTool(registry);

Type guard

boolean registryPresent(SkillRegistry r) { return r != null; }

Try / catch

try { tool = new SearchSkillsTool(registry); } catch (IllegalArgumentException e) { log.error("Registry required: {}", e.getMessage()); }

Prevention

When it happens

Trigger: Calling new SearchSkillsTool(null) or createSearchSkillsToolCallback(skillRegistry, description) with a null registry.

Common situations: Optional skill-directory loading skipped, yielding null; refactored wiring that dropped registry initialization; DI container returning null because the registry bean was not configured.

Related errors


AI-assisted analysis of alibaba/spring-ai-alibaba@f82da0b50f (2026-09-09). Data as JSON: /api/errors/1517703e0c061556. Report an issue: GitHub.