/*
* Copyright (c) 2002-2009 "Neo Technology,"
* Network Engine for Objects in Lund AB [http://neotechnology.com]
*
* This file is part of Neo4j.
*
* Neo4j is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License as
* published by the Free Software Foundation, either version 3 of the
* License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* You should have received a copy of the GNU Affero General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.neo4j.index.lucene;
import java.io.File;
import java.io.IOException;
import java.io.RandomAccessFile;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;
import java.util.Random;
class LuceneIndexStore
{
private long creationTime;
private long randomIdentifier;
private long version;
private final FileChannel fileChannel;
private final ByteBuffer buf = ByteBuffer.allocate( 24 );
public LuceneIndexStore( String store )
{
if ( !new File( store ).exists() )
{
create( store );
}
try
{
fileChannel = new RandomAccessFile( store, "rw" ).getChannel();
if ( fileChannel.read( buf ) != 24 )
{
throw new RuntimeException( "Expected to read 24 bytes" );
}
buf.flip();
creationTime = buf.getLong();
randomIdentifier = buf.getLong();
version = buf.getLong();
}
catch ( IOException e )
{
throw new RuntimeException( e );
}
}
static void create( String store )
{
if ( new File( store ).exists() )
{
throw new IllegalArgumentException( store + " already exist" );
}
try
{
FileChannel fileChannel =
new RandomAccessFile( store, "rw" ).getChannel();
ByteBuffer buf = ByteBuffer.allocate( 24 );
long time = System.currentTimeMillis();
long identifier = new Random( time ).nextLong();
buf.putLong( time ).putLong( identifier ).putLong( 0 );
buf.flip();
if ( fileChannel.write( buf ) != 24 )
{
throw new RuntimeException( "Expected to write 24 bytes" );
}
fileChannel.close();
}
catch ( IOException e )
{
throw new RuntimeException( e );
}
}
public long getCreationTime()
{
return creationTime;
}
public long getRandomNumber()
{
return randomIdentifier;
}
public long getVersion()
{
return version;
}
public synchronized long incrementVersion()
{
long current = getVersion();
version++;
writeOut();
return current;
}
public synchronized void setVersion( long version )
{
this.version = version;
writeOut();
}
private void writeOut()
{
buf.clear();
buf.putLong( creationTime ).putLong( randomIdentifier ).putLong(
version );
buf.flip();
try
{
if ( fileChannel.write( buf, 0 ) != 24 )
{
throw new RuntimeException( "Expected to write 24 bytes" );
}
}
catch ( IOException e )
{
throw new RuntimeException( e );
}
}
public void close()
{
if ( !fileChannel.isOpen() )
{
return;
}
try
{
fileChannel.close();
}
catch ( IOException e )
{
throw new RuntimeException( e );
}
}
}