1
/*******************************************************************************
2
*Copyright (c) 2009 Eucalyptus Systems, Inc.
4
* This program is free software: you can redistribute it and/or modify
5
* it under the terms of the GNU General Public License as published by
6
* the Free Software Foundation, only version 3 of the License.
9
* This file is distributed in the hope that it will be useful, but WITHOUT
10
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14
* You should have received a copy of the GNU General Public License along
15
* with this program. If not, see <http://www.gnu.org/licenses/>.
17
* Please contact Eucalyptus Systems, Inc., 130 Castilian
18
* Dr., Goleta, CA 93101 USA or visit <http://www.eucalyptus.com/licenses/>
19
* if you need additional information or have any questions.
21
* This file may incorporate work covered under the following copyright and
24
* Software License Agreement (BSD License)
26
* Copyright (c) 2008, Regents of the University of California
27
* All rights reserved.
29
* Redistribution and use of this software in source and binary forms, with
30
* or without modification, are permitted provided that the following
33
* Redistributions of source code must retain the above copyright notice,
34
* this list of conditions and the following disclaimer.
36
* Redistributions in binary form must reproduce the above copyright
37
* notice, this list of conditions and the following disclaimer in the
38
* documentation and/or other materials provided with the distribution.
40
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
41
* IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
42
* TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
43
* PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
44
* OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
45
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
46
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
47
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
48
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
49
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
50
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. USERS OF
51
* THIS SOFTWARE ACKNOWLEDGE THE POSSIBLE PRESENCE OF OTHER OPEN SOURCE
52
* LICENSED MATERIAL, COPYRIGHTED MATERIAL OR PATENTED MATERIAL IN THIS
53
* SOFTWARE, AND IF ANY SUCH MATERIAL IS DISCOVERED THE PARTY DISCOVERING
54
* IT MAY INFORM DR. RICH WOLSKI AT THE UNIVERSITY OF CALIFORNIA, SANTA
55
* BARBARA WHO WILL THEN ASCERTAIN THE MOST APPROPRIATE REMEDY, WHICH IN
56
* THE REGENTS’ DISCRETION MAY INCLUDE, WITHOUT LIMITATION, REPLACEMENT
57
* OF THE CODE SO IDENTIFIED, LICENSING OF THE CODE SO IDENTIFIED, OR
58
* WITHDRAWAL OF THE CODE CAPABILITY TO THE EXTENT NEEDED TO COMPLY WITH
59
* ANY SUCH LICENSES OR RIGHTS.
60
*******************************************************************************/
62
* Author: chris grzegorczyk <grze@eucalyptus.com>
64
package com.eucalyptus.bootstrap;
66
import java.util.concurrent.atomic.AtomicBoolean;
68
import org.apache.log4j.Logger;
69
import org.hsqldb.DatabaseURL;
70
import org.hsqldb.Server;
71
import org.hsqldb.ServerConstants;
72
import org.hsqldb.persist.HsqlProperties;
74
import com.eucalyptus.auth.util.SslSetup;
75
import com.eucalyptus.event.ClockTick;
76
import com.eucalyptus.event.Event;
77
import com.eucalyptus.event.EventListener;
78
import com.eucalyptus.event.ListenerRegistry;
79
import com.eucalyptus.util.DatabaseUtil;
80
import com.eucalyptus.util.DebugUtil;
81
import com.eucalyptus.util.GroovyUtil;
82
import com.eucalyptus.util.LogUtil;
84
@Provides( resource = Resource.Database )
85
@Depends( resources = Resource.SystemCredentials, local = Component.eucalyptus )
86
public class LocalDatabaseBootstrapper extends Bootstrapper implements EventListener, Runnable, DatabaseBootstrapper {
87
private static Logger LOG = Logger.getLogger( LocalDatabaseBootstrapper.class );
88
private static DatabaseBootstrapper singleton;
90
public static DatabaseBootstrapper getInstance( ) {
91
synchronized ( LocalDatabaseBootstrapper.class ) {
92
if ( singleton == null ) {
93
for( DatabaseUtil.PoolConfig p : DatabaseUtil.PoolConfig.values( ) ) {
94
LOG.debug( String.format( "Default pool config: %s=%s", p.getKey( ), p.getValue( ) ) );
96
singleton = new LocalDatabaseBootstrapper( );
97
SystemBootstrapper.setDatabaseBootstrapper( singleton );
103
private static void setDefault( String key, Object value ) {
104
if( System.getProperties( ).containsKey( key ) ) System.setProperty( key, value.toString() );
108
private String fileName;
110
private LocalDatabaseBootstrapper( ) {
111
ListenerRegistry.getInstance( ).register( ClockTick.class, this );
115
public boolean check( ) {
120
public boolean destroy( ) throws Exception {
125
public boolean load( Resource current ) throws Exception {
126
LOG.debug( "Initializing SSL just in case: " + SslSetup.class );
128
DatabaseConfig.initialize( );
129
} catch ( Exception e ) {
136
public boolean isRunning( ) {
138
if ( this.db != null ) this.db.checkRunning( true );
140
} catch ( RuntimeException e ) {
145
private static AtomicBoolean hup = new AtomicBoolean( false );
147
if( hup.compareAndSet( false, true ) ) {
148
DebugUtil.printDebugDetails( );
150
if ( this.db != null ) {
151
this.db.checkRunning( true );
154
} catch ( RuntimeException e ) {
156
this.createDatabase( );
157
this.waitForDatabase( );
160
LOG.info("Already scheduled a database restart.");
164
private void createDatabase( ) {
165
this.db = new Server( );
166
this.db.setProperties( new HsqlProperties( DatabaseConfig.getProperties( ) ) );
167
SystemBootstrapper.makeSystemThread( this ).start( );
171
public boolean start( ) throws Exception {
172
this.waitForDatabase( );
174
GroovyUtil.evaluateScript( "startup.groovy" );
175
} catch ( Exception e ) {
182
private void waitForDatabase( ) {
183
while ( this.db.getState( ) != 1 ) {
184
Throwable t = this.db.getServerError( );
187
throw new RuntimeException( t );
190
Thread.sleep( 1000 );
191
} catch ( InterruptedException e ) {
192
Thread.currentThread( ).interrupt( );
194
LOG.info( "Waiting for database to start..." );
203
public boolean stop( ) {
207
public String getFileName( ) {
211
public void setFileName( String fileName ) {
212
LOG.info( "Setting hsqldb filename=" + fileName );
213
this.fileName = fileName;
217
public void advertiseEvent( Event event ) {}
220
public void fireEvent( Event event ) {
221
if( event instanceof ClockTick && Component.eucalyptus.isLocal( ) ) {
223
LOG.trace( "-> Ping database." );
225
} catch ( RuntimeException e ) {