apache/iceberg · error · AlreadyExistsException
Cannot rename %s to %s. View already exists
Error message
Cannot rename %s to %s. View already exists
What it means
InMemoryCatalog.renameTable throws AlreadyExistsException when a view already exists at the destination identifier. The catalog keeps tables and views in separate maps but both occupy the same identifier space, so a rename cannot target an identifier held by a view.
Source
Thrown at core/src/main/java/org/apache/iceberg/inmemory/InMemoryCatalog.java:186
}
synchronized (this) {
if (!namespaceExists(to.namespace())) {
throw new NoSuchNamespaceException(
"Cannot rename %s to %s. Namespace does not exist: %s", from, to, to.namespace());
}
String fromLocation = tables.get(from);
if (null == fromLocation) {
throw new NoSuchTableException("Cannot rename %s to %s. Table does not exist", from, to);
}
if (tables.containsKey(to)) {
throw new AlreadyExistsException("Cannot rename %s to %s. Table already exists", from, to);
}
if (views.containsKey(to)) {
throw new AlreadyExistsException("Cannot rename %s to %s. View already exists", from, to);
}
tables.put(to, fromLocation);
tables.remove(from);
}
}
@Override
public void createNamespace(Namespace namespace) {
createNamespace(namespace, Collections.emptyMap());
}
@Override
public void createNamespace(Namespace namespace, Map<String, String> metadata) {
synchronized (this) {
if (namespaceExists(namespace)) {
throw new AlreadyExistsException(
"Cannot create namespace %s. Namespace already exists", namespace);View on GitHub (pinned to 86d9c8fc54)
Solutions
- Drop the existing view at the destination before renaming
- Pick a destination identifier not used by any view
- Check for view existence (e.g. via view catalog APIs) before the rename
- Catch AlreadyExistsException and resolve the collision explicitly
Example fix
// before
catalog.renameTable(from, to); // to is a view name
// after
if (catalog.viewExists(to)) {
catalog.dropView(to);
}
catalog.renameTable(from, to); Defensive patterns
Strategy: validation
Validate before calling
if (catalog.tableExists(to) || catalog.viewExists(to)) { throw new IllegalStateException("Destination occupied: " + to); } Try / catch
try { catalog.renameTable(from, to); } catch (AlreadyExistsException e) { if (catalog.viewExists(to)) { catalog.dropView(to); catalog.renameTable(from, to); } } Prevention
- Treat tables and views as sharing one identifier namespace
- Check both table and view existence before renaming
- Enforce naming conventions separating tables and views
- Audit target namespaces for views before migrations
When it happens
Trigger: Calling catalog.renameTable(from, to) where views contains 'to'. E.g. renaming a table to a name that a view already occupies in the same namespace.
Common situations: Environments where views and tables share naming conventions; scripts unaware a view was created at the target name; migrating tables into namespaces occupied by reporting views.
Understand the failure class
Background: "already exists" / EEXIST / FileAlreadyExistsException: what the 'file already exists' error means and how to fix it — this error's family across 37 libraries.
Related errors
- Cannot rename %s to %s. Namespace does not exist: %s
- Cannot rename %s to %s. Table does not exist
- Cannot rename %s to %s. Table already exists
- Cannot rename table %s to %s: %s does not exist
- Cannot rename table %s to %s: %s already exists
AI-assisted analysis of apache/iceberg@86d9c8fc54 (2026-09-12).
Data as JSON: /api/errors/1b3ff99233ba2190.
Report an issue: GitHub.