MyCATApache/Mycat-Server · critical · RuntimeException

can't find class resource file

Error message

can't find class resource file {mapFile}

What it means

PartitionByPattern.initialize() loads the pattern-to-node mapping file from the classpath via ClassLoader.getResourceAsStream(mapFile). If the resource cannot be found on the classpath, it throws this RuntimeException immediately during rule initialization. Mycat throws it eagerly so a broken partition rule fails at startup instead of at query time.

Solutions

  1. Place the map file (e.g. partition-pattern.txt) on the classpath, typically in Mycat's conf directory or src/main/resources, and rebuild/redeploy.
  2. Verify the <mapFile> value in the partition rule config exactly matches the classpath resource name (case-sensitive, no leading '/', no absolute filesystem path).
  3. If the file lives on the filesystem instead, either move it into the classpath or modify the rule to fall back to FileInputStream(fileMapPath) as the commented-out code suggests.
  4. Confirm the artifact actually packages the file: unzip the jar/war and check the resource path.

Example fix

// before (rule config)
<function name="pat" class="io.mycat.route.function.PartitionByPattern">
  <property name="mapFile">/data/conf/partition-pattern.txt</property>
</function>
// after: put partition-pattern.txt on the classpath and reference it relatively
<function name="pat" class="io.mycat.route.function.PartitionByPattern">
  <property name="mapFile">partition-pattern.txt</property>
</function>
Defensive patterns

Strategy: validation

Validate before calling

boolean mapFileOnClasspath = PartitionByPattern.class.getClassLoader().getResource(mapFile) != null;
if (!mapFileOnClasspath) throw new IllegalStateException("mapFile not on classpath: " + mapFile);

Try / catch

try { rule.init(); } catch (RuntimeException e) { if (e.getMessage().contains("can't find class resource file")) { /* fail fast: fix mapFile/classpath before startup */ } throw e; }

Prevention

When it happens

Trigger: Calling init() on a PartitionByPattern rule whose <mapFile> points to a resource name that is not present on the classpath, e.g. mapFile=partition-pattern.txt when no such file exists in src/main/resources or the conf directory on the classpath.

Common situations: The map file was never added to the classpath (only placed on disk next to the config); the mapFile value contains a leading slash or wrong path casing; the file was renamed or omitted when packaging a jar/war; running from an IDE where the resources directory is not marked as a resource root.

Understand the failure class

Background: 'Could not be found', 'does not exist', 'not found in database': the resource-not-found family when an ID, slug, key, or URI lookup comes back empty — this error's family across 20 libraries.

Related errors


AI-assisted analysis of MyCATApache/Mycat-Server@65f8d8beb7 (2026-09-11). Data as JSON: /api/errors/d7467e0047857ea7. Report an issue: GitHub.

Appendix: source

Thrown at src/main/java/io/mycat/route/function/PartitionByPattern.java:109

		for(LongRange range : longRongs) {
			distNodeIdxSet.add(range.nodeIndx);
		}
		int nPartition = distNodeIdxSet.size();
		return nPartition;
	}

	public static boolean isNumeric(String str) {
		return pattern.matcher(str).matches();
	}

	private void initialize() {
		BufferedReader in = null;
		try {
			// FileInputStream fin = new FileInputStream(new File(fileMapPath));
			InputStream fin = this.getClass().getClassLoader()
					.getResourceAsStream(mapFile);
			if (fin == null) {
				throw new RuntimeException("can't find class resource file "
						+ mapFile);
			}
			in = new BufferedReader(new InputStreamReader(fin));
			LinkedList<LongRange> longRangeList = new LinkedList<LongRange>();

			for (String line = null; (line = in.readLine()) != null;) {
				line = line.trim();
				if (line.startsWith("#") || line.startsWith("//")) {
					continue;
				}
				int ind = line.indexOf('=');
				if (ind < 0) {
					System.out.println(" warn: bad line int " + mapFile + " :"
							+ line);
					continue;
				}
					String pairs[] = line.substring(0, ind).trim().split("-");
					long longStart = Long.parseLong(pairs[0].trim());

View on GitHub (pinned to 65f8d8beb7)