
/*
 * weinre is available under *either* the terms of the modified BSD license *or* the
 * MIT License (2008). See http://opensource.org/licenses/alphabetical for full text.
 * 
 * Copyright (c) 2011 IBM Corporation
 */

//-----------------------------------------------------------------------------
class WeinreExtraTargetEventsImpl

//-----------------------------------------------------------------------------
method databaseOpened(databaseRecord)
    WeinreExtraTargetEventsImpl.addDatabaseRecords([databaseRecord])
    
//-----------------------------------------------------------------------------
static method addDatabaseRecords(databaseRecords)
    // databaseRecord.id
    // databaseRecord.domain
    // databaseRecord.name
    // databaseRecord.version
    
    if (!WebInspector.panels) return
    if (!WebInspector.panels.resources) return
    if (!WebInspector.panels.resources._databases) return
    
    var existingDbs = WebInspector.panels.resources._databases
    var existingDbNames = {}
    
    for (var i=0; i<existingDbs.length; i++) {
        existingDbNames[existingDbs[i].name] = existingDbs[i]
    }
    
    for (var i=0; i<databaseRecords.length; i++) {
        if (existingDbNames[databaseRecords[i].name]) continue
        
        var databaseRecord = databaseRecords[i]
        var database = new WebInspector.Database(
            databaseRecord.id,
            databaseRecord.domain,
            databaseRecord.name,
            databaseRecord.version
            )
        
        WebInspector.panels.resources.addDatabase(database)
    }
    
    
