hibernate/hibernate-orm · error · SchemaManagementException
Illegal state : writer null - not prepared
Error message
Illegal state : writer null - not prepared
What it means
ScriptTargetOutputToFile creates its FileWriter lazily in prepare() and nulls it in release(); writer() throws this SchemaManagementException when a write is attempted while the writer is null — i.e. before prepare() or after release(). It is a lifecycle-contract violation inside the script-target plumbing; stock hbm2ddl calls prepare/write/release in order, so users normally hit it only through custom schema tooling.
Source
Thrown at hibernate-core/src/main/java/org/hibernate/tool/schema/internal/exec/ScriptTargetOutputToFile.java:59
this.append = append;
}
/**
* Constructs a ScriptTargetOutputToFile instance,
* the bytes will be written to the end of the file rather than the beginning
*
* @param file The file to read from
* @param charsetName The charset name
*
*/
public ScriptTargetOutputToFile(File file, String charsetName ) {
this(file, charsetName, true);
}
@Override
protected Writer writer() {
if ( writer == null ) {
throw new SchemaManagementException( "Illegal state : writer null - not prepared" );
}
return writer;
}
@Override
public void prepare() {
super.prepare();
this.writer = toFileWriter( this.file, this.charsetName, append );
}
@Override
public void release() {
if ( writer != null ) {
try {
writer.close();
}
catch (IOException e) {
throw new SchemaManagementException( "Unable to close file writer : " + e );View on GitHub (pinned to fad1729dce)
Solutions
- Call prepare() before any write and release() exactly once at the end — mirror SchemaExport's ordering.
- Never reuse a ScriptTargetOutputToFile after release(); construct a fresh instance for each export run.
- If this surfaces during plain hbm2ddl with no custom code, upgrade hibernate-core — lifecycle sequencing bugs were fixed in patches.
Example fix
// before: writing before/outside the lifecycle ScriptTargetOutput out = new ScriptTargetOutputToFile( file, null ); out.write( "create table ..." ); // IllegalStateException-style failure // after: explicit lifecycle out.prepare(); out.write( "create table ..." ); out.release();
Defensive patterns
Strategy: try-catch
Try / catch
try {
target.prepare();
target.write( ddl );
}
finally {
target.release(); // release() must run even if write fails, so state is clean for a fresh instance
} Prevention
- Treat ScriptTargetOutput as single-use: one prepare/write/release cycle per export run.
- Never call write() before prepare() returns; assert the lifecycle in custom integrations.
- Create a fresh ScriptTargetOutputToFile for retries instead of reusing the released instance.
When it happens
Trigger: Calling write() on a ScriptTargetOutputToFile without calling prepare() first; reusing the same target for a second export after release() has run (release() sets writer=null); custom SchemaManagementTool/GenerationTarget code orchestrating the target lifecycle out of order.
Common situations: Custom integrations that build their own GenerationTargets; interrupted schema generation where release() already executed and a later phase tries to write again; copies of Hibernate examples that skip prepare().
Related errors
- Writing to script was requested, but no script file was spec
- The ClassLoaderService cannot be reused (this instance was s
- No child ServiceRegistry registrations found
- Can't reactivate an active registry
- Should not register strategies during shutdown
AI-assisted analysis of hibernate/hibernate-orm@fad1729dce (2026-08-22).
Data as JSON: /api/errors/d2e3cf670ec32201.
Report an issue: GitHub.