theonedev/onedev · error · ExplicitException

Attribute '%s' should start and end with alphanumeric or und

Error message

Attribute '%s' should start and end with alphanumeric or underscore. Only alphanumeric, underscore, dash, space and dot are allowed in the middle.

What it means

When an agent connects, agentConnected validates every attribute name reported in AgentData against AttributeNameValidator.PATTERN (must be alphanumeric/underscore at the ends, only alphanumerics, underscore, dash, space, dot inside) and rejects reserved agent field names separately. Invalid names throw ExplicitException to keep agent metadata keys well-formed.

Source

Thrown at server-core/src/main/java/io/onedev/server/service/impl/DefaultAgentService.java:172

		}
	}
	
	@Override
	public String getAgentVersion() {
		return agentVersion;
	}

	@Override
	public Collection<String> getAgentLibs() {
		return agentLibs;
	}

	@Transactional
	@Override
	public Long agentConnected(AgentData data, Session session) {
		for (String attributeName: data.getAttributes().keySet()) {
			if (!AttributeNameValidator.PATTERN.matcher(attributeName).matches()) {
				throw new ExplicitException("Attribute '" + attributeName + "' should start and end with "
						+ "alphanumeric or underscore. Only alphanumeric, underscore, dash, space and "
						+ "dot are allowed in the middle.");
			} else if (Agent.ALL_FIELDS.contains(attributeName)) { 
				throw new ExplicitException("Attribute '" + attributeName + "' is reserved");
			}
		}
		
		AgentToken token = Preconditions.checkNotNull(tokenService.find(data.getToken()));
		Agent agent = findByToken(token);
		if (agent == null) {
			agent = new Agent();
			agent.setToken(token);
			agent.setOsName(data.getOsInfo().getOsName());
			agent.setOsVersion(data.getOsInfo().getOsVersion());
			agent.setOsArch(data.getOsInfo().getOsArch());
			agent.setName(data.getName());
			agent.setCpuCount(data.getCpus());
			agent.setIpAddress(data.getIpAddress());

View on GitHub (pinned to d44925c47c)

Solutions

  1. Rename the attribute in the agent's data to match the pattern: start/end with alphanumeric or underscore, middle limited to alphanumerics, underscore, dash, space, dot.
  2. Trim leading/trailing spaces from attribute keys before sending.
  3. Replace reserved agent field names with a non-reserved custom key.
  4. Sanitize keys programmatically on the agent side before reporting them to the server.

Example fix

// before
attributes.put("cpu/cores", "8");
// after
attributes.put("cpu.cores", "8");
Defensive patterns

Strategy: validation

Validate before calling

const PATTERN = /^[A-Za-z0-9_]([A-Za-z0-9_ .-]*[A-Za-z0-9_])?$/;
Object.keys(attributes).forEach(k => {
  if (!PATTERN.test(k)) throw new Error(`Invalid attribute name: ${k}`);
});

Type guard

function isValidAttributeName(k) {
  return /^[A-Za-z0-9_]([A-Za-z0-9_ .-]*[A-Za-z0-9_])?$/.test(k);
}

Try / catch

try {
  agentNode.connect(data);
} catch (ExplicitException e) {
  if (e.getMessage().includes("should start and end with alphanumeric")) {
    sanitizeAndReconnect();
  }
}

Prevention

When it happens

Trigger: An agent registers via agentConnected(data, session) with data.getAttributes() containing a key that fails the pattern (e.g. starts with a digit, contains '/', '@', '-', special chars) or equals a reserved Agent.ALL_FIELDS name.

Common situations: Custom agent scripts exporting environment-derived attribute keys like 'os.version!' or '123node'; keys with spaces at edges or non-ASCII characters; accidentally using reserved names like 'Name' or 'Version'.

Understand the failure class

Background: "invalid id" errors: invalid identifier format — why libraries reject IDs before lookup, and how to fix them — this error's family across 37 libraries.

Related errors


AI-assisted analysis of theonedev/onedev@d44925c47c (2026-09-06). Data as JSON: /api/errors/88296db7a8d25c60. Report an issue: GitHub.