skylot/jadx · error · JadxRuntimeException

Failed to init res container factory: ${resContainerFactory}

Error message

Failed to init res container factory: ${resContainerFactory}

What it means

Thrown during ResourcesLoader.init() when an IResContainerFactory's init(root) throws. Container factories build resource containers (e.g., for nested archives or special resource types) and are initialized once against the RootNode alongside the table providers. A failure aborts resource loading with a JadxRuntimeException naming the factory via toString(), chaining the cause.

Source

Thrown at jadx-core/src/main/java/jadx/api/ResourcesLoader.java:76

		for (File file : inputFiles) {
			loadFile(list, file);
		}
		return list;
	}

	private void init(RootNode root) {
		for (IResTableParserProvider resTableParserProvider : resTableParserProviders) {
			try {
				resTableParserProvider.init(root);
			} catch (Exception e) {
				throw new JadxRuntimeException("Failed to init res table provider: " + resTableParserProvider);
			}
		}
		for (IResContainerFactory resContainerFactory : resContainerFactories) {
			try {
				resContainerFactory.init(root);
			} catch (Exception e) {
				throw new JadxRuntimeException("Failed to init res container factory: " + resContainerFactory);
			}
		}
	}

	public interface ResourceDecoder<T> {
		T decode(long size, InputStream is) throws IOException;
	}

	@Override
	public void addResContainerFactory(IResContainerFactory resContainerFactory) {
		resContainerFactories.add(resContainerFactory);
	}

	@Override
	public void addResTableParserProvider(IResTableParserProvider resTableParserProvider) {
		resTableParserProviders.add(resTableParserProvider);
	}

View on GitHub (pinned to e738a26571)

Solutions

  1. Inspect getCause() and the factory name in the message to identify the failing factory.
  2. Remove or update the offending IResContainerFactory from the registered factories.
  3. Align the factory's version with the jadx-core API version.
  4. Make a custom factory's init defensive: catch internally and degrade gracefully instead of throwing.

Example fix

// before
@Override
public void init(RootNode root) {
    this.cache = buildContainerCache(root); // throws
}

// after
@Override
public void init(RootNode root) {
    try {
        this.cache = buildContainerCache(root);
    } catch (Exception e) {
        LOG.error("Container factory init failed, factory disabled", e);
        this.cache = Collections.emptyMap();
    }
}
Defensive patterns

Strategy: try-catch

Validate before calling

// Wrap each factory's init during your own setup so one bad factory
// does not abort all resource loading.
for (IResContainerFactory f : factories) {
    try { f.init(root); } catch (Exception e) {
        LOG.warn("Disabling failing factory {}: {}", f, e);
    }
}

Try / catch

try {
    jadx.getResources();
} catch (JadxRuntimeException e) {
    if (e.getMessage().startsWith("Failed to init res container factory")) {
        LOG.error("Resource container factory failed: {}", e.getMessage());
        // remove the named factory and retry
    } else throw e;
}

Prevention

When it happens

Trigger: Triggering resource loading (jadx.getResources()) with a registered IResContainerFactory whose init(root) raises an exception during the init loop.

Common situations: A custom IResContainerFactory plugin that throws on init (missing config, incompatible API); a version mismatch between the factory and jadx-core; a factory that depends on an external file/path that is absent; a classpath conflict loading the factory.

Related errors


AI-assisted analysis of skylot/jadx@e738a26571 (2026-08-14). Data as JSON: /api/errors/8152e8dab3948b7b. Report an issue: GitHub.