Search in sources :

Example 1 with MapCounter

use of org.apache.accumulo.core.util.MapCounter in project accumulo by apache.

the class GroupBalancer method balance.

@Override
public long balance(SortedMap<TServerInstance, TabletServerStatus> current, Set<KeyExtent> migrations, List<TabletMigration> migrationsOut) {
    if (!shouldBalance(current, migrations)) {
        return 5000;
    }
    if (System.currentTimeMillis() - lastRun < getWaitTime()) {
        return 5000;
    }
    MapCounter<String> groupCounts = new MapCounter<>();
    Map<TServerInstance, TserverGroupInfo> tservers = new HashMap<>();
    for (TServerInstance tsi : current.keySet()) {
        tservers.put(tsi, new TserverGroupInfo(tsi));
    }
    Function<KeyExtent, String> partitioner = getPartitioner();
    // collect stats about current state
    for (Pair<KeyExtent, Location> entry : getLocationProvider()) {
        String group = partitioner.apply(entry.getFirst());
        Location loc = entry.getSecond();
        if (loc.equals(Location.NONE) || !tservers.containsKey(loc.getTserverInstance())) {
            return 5000;
        }
        groupCounts.increment(group, 1);
        TserverGroupInfo tgi = tservers.get(loc.getTserverInstance());
        tgi.addGroup(group);
    }
    Map<String, Integer> expectedCounts = new HashMap<>();
    int totalExtra = 0;
    for (String group : groupCounts.keySet()) {
        long groupCount = groupCounts.get(group);
        totalExtra += groupCount % current.size();
        expectedCounts.put(group, (int) (groupCount / current.size()));
    }
    // The number of extra tablets from all groups that each tserver must have.
    int expectedExtra = totalExtra / current.size();
    int maxExtraGroups = expectedExtra + 1;
    expectedCounts = Collections.unmodifiableMap(expectedCounts);
    tservers = Collections.unmodifiableMap(tservers);
    for (TserverGroupInfo tgi : tservers.values()) {
        tgi.finishedAdding(expectedCounts);
    }
    Moves moves = new Moves();
    // The order of the following steps is important, because as ordered each step should not move any tablets moved by a previous step.
    balanceExpected(tservers, moves);
    if (moves.size() < getMaxMigrations()) {
        balanceExtraExpected(tservers, expectedExtra, moves);
        if (moves.size() < getMaxMigrations()) {
            boolean cont = balanceExtraMultiple(tservers, maxExtraGroups, moves);
            if (cont && moves.size() < getMaxMigrations()) {
                balanceExtraExtra(tservers, maxExtraGroups, moves);
            }
        }
    }
    populateMigrations(tservers.keySet(), migrationsOut, moves);
    lastRun = System.currentTimeMillis();
    return 5000;
}
Also used : HashMap(java.util.HashMap) KeyExtent(org.apache.accumulo.core.data.impl.KeyExtent) TServerInstance(org.apache.accumulo.server.master.state.TServerInstance) MapCounter(org.apache.accumulo.core.util.MapCounter)

Example 2 with MapCounter

use of org.apache.accumulo.core.util.MapCounter in project accumulo by apache.

the class TableOperationsImpl method waitForTableStateTransition.

private void waitForTableStateTransition(Table.ID tableId, TableState expectedState) throws AccumuloException, TableNotFoundException, AccumuloSecurityException {
    Text startRow = null;
    Text lastRow = null;
    while (true) {
        if (Tables.getTableState(context.getInstance(), tableId) != expectedState) {
            Tables.clearCache(context.getInstance());
            TableState currentState = Tables.getTableState(context.getInstance(), tableId);
            if (currentState != expectedState) {
                if (!Tables.exists(context.getInstance(), tableId))
                    throw new TableDeletedException(tableId.canonicalID());
                if (currentState == TableState.DELETING)
                    throw new TableNotFoundException(tableId.canonicalID(), "", "Table is being deleted.");
                throw new AccumuloException("Unexpected table state " + tableId + " " + Tables.getTableState(context.getInstance(), tableId) + " != " + expectedState);
            }
        }
        Range range;
        if (startRow == null || lastRow == null)
            range = new KeyExtent(tableId, null, null).toMetadataRange();
        else
            range = new Range(startRow, lastRow);
        String metaTable = MetadataTable.NAME;
        if (tableId.equals(MetadataTable.ID))
            metaTable = RootTable.NAME;
        Scanner scanner = createMetadataScanner(metaTable, range);
        RowIterator rowIter = new RowIterator(scanner);
        KeyExtent lastExtent = null;
        int total = 0;
        int waitFor = 0;
        int holes = 0;
        Text continueRow = null;
        MapCounter<String> serverCounts = new MapCounter<>();
        while (rowIter.hasNext()) {
            Iterator<Entry<Key, Value>> row = rowIter.next();
            total++;
            KeyExtent extent = null;
            String future = null;
            String current = null;
            while (row.hasNext()) {
                Entry<Key, Value> entry = row.next();
                Key key = entry.getKey();
                if (key.getColumnFamily().equals(TabletsSection.FutureLocationColumnFamily.NAME))
                    future = entry.getValue().toString();
                if (key.getColumnFamily().equals(TabletsSection.CurrentLocationColumnFamily.NAME))
                    current = entry.getValue().toString();
                if (TabletsSection.TabletColumnFamily.PREV_ROW_COLUMN.hasColumns(key))
                    extent = new KeyExtent(key.getRow(), entry.getValue());
            }
            if ((expectedState == TableState.ONLINE && current == null) || (expectedState == TableState.OFFLINE && (future != null || current != null))) {
                if (continueRow == null)
                    continueRow = extent.getMetadataEntry();
                waitFor++;
                lastRow = extent.getMetadataEntry();
                if (current != null)
                    serverCounts.increment(current, 1);
                if (future != null)
                    serverCounts.increment(future, 1);
            }
            if (!extent.getTableId().equals(tableId)) {
                throw new AccumuloException("Saw unexpected table Id " + tableId + " " + extent);
            }
            if (lastExtent != null && !extent.isPreviousExtent(lastExtent)) {
                holes++;
            }
            lastExtent = extent;
        }
        if (continueRow != null) {
            startRow = continueRow;
        }
        if (holes > 0 || total == 0) {
            startRow = null;
            lastRow = null;
        }
        if (waitFor > 0 || holes > 0 || total == 0) {
            long waitTime;
            long maxPerServer = 0;
            if (serverCounts.size() > 0) {
                maxPerServer = Collections.max(serverCounts.values());
                waitTime = maxPerServer * 10;
            } else
                waitTime = waitFor * 10;
            waitTime = Math.max(100, waitTime);
            waitTime = Math.min(5000, waitTime);
            log.trace("Waiting for {}({}) tablets, startRow = {} lastRow = {}, holes={} sleeping:{}ms", waitFor, maxPerServer, startRow, lastRow, holes, waitTime);
            sleepUninterruptibly(waitTime, TimeUnit.MILLISECONDS);
        } else {
            break;
        }
    }
}
Also used : AccumuloException(org.apache.accumulo.core.client.AccumuloException) IsolatedScanner(org.apache.accumulo.core.client.IsolatedScanner) Scanner(org.apache.accumulo.core.client.Scanner) Text(org.apache.hadoop.io.Text) TRowRange(org.apache.accumulo.core.data.thrift.TRowRange) Range(org.apache.accumulo.core.data.Range) KeyExtent(org.apache.accumulo.core.data.impl.KeyExtent) TableDeletedException(org.apache.accumulo.core.client.TableDeletedException) Constraint(org.apache.accumulo.core.constraints.Constraint) TableNotFoundException(org.apache.accumulo.core.client.TableNotFoundException) ZipEntry(java.util.zip.ZipEntry) Entry(java.util.Map.Entry) RowIterator(org.apache.accumulo.core.client.RowIterator) MapCounter(org.apache.accumulo.core.util.MapCounter) Value(org.apache.accumulo.core.data.Value) Key(org.apache.accumulo.core.data.Key) TableState(org.apache.accumulo.core.master.state.tables.TableState)

Example 3 with MapCounter

use of org.apache.accumulo.core.util.MapCounter in project accumulo by apache.

the class SessionManager method getActiveScansPerTable.

public Map<Table.ID, MapCounter<ScanRunState>> getActiveScansPerTable() {
    Map<Table.ID, MapCounter<ScanRunState>> counts = new HashMap<>();
    Set<Entry<Long, Session>> copiedIdleSessions = new HashSet<>();
    synchronized (idleSessions) {
        /**
         * Add sessions so that get the list returned in the active scans call
         */
        for (Session session : idleSessions) {
            copiedIdleSessions.add(Maps.immutableEntry(expiredSessionMarker, session));
        }
    }
    for (Entry<Long, Session> entry : Iterables.concat(sessions.entrySet(), copiedIdleSessions)) {
        Session session = entry.getValue();
        @SuppressWarnings("rawtypes") ScanTask nbt = null;
        Table.ID tableID = null;
        if (session instanceof ScanSession) {
            ScanSession ss = (ScanSession) session;
            nbt = ss.nextBatchTask;
            tableID = ss.extent.getTableId();
        } else if (session instanceof MultiScanSession) {
            MultiScanSession mss = (MultiScanSession) session;
            nbt = mss.lookupTask;
            tableID = mss.threadPoolExtent.getTableId();
        }
        if (nbt == null)
            continue;
        ScanRunState srs = nbt.getScanRunState();
        if (srs == ScanRunState.FINISHED)
            continue;
        MapCounter<ScanRunState> stateCounts = counts.get(tableID);
        if (stateCounts == null) {
            stateCounts = new MapCounter<>();
            counts.put(tableID, stateCounts);
        }
        stateCounts.increment(srs, 1);
    }
    return counts;
}
Also used : Table(org.apache.accumulo.core.client.impl.Table) ScanTask(org.apache.accumulo.tserver.scan.ScanTask) HashMap(java.util.HashMap) ConcurrentHashMap(java.util.concurrent.ConcurrentHashMap) Entry(java.util.Map.Entry) MapCounter(org.apache.accumulo.core.util.MapCounter) ScanRunState(org.apache.accumulo.tserver.scan.ScanRunState) HashSet(java.util.HashSet)

Example 4 with MapCounter

use of org.apache.accumulo.core.util.MapCounter in project accumulo by apache.

the class CompactionDriver method isReady.

@Override
public long isReady(long tid, Master master) throws Exception {
    String zCancelID = Constants.ZROOT + "/" + master.getInstance().getInstanceID() + Constants.ZTABLES + "/" + tableId + Constants.ZTABLE_COMPACT_CANCEL_ID;
    IZooReaderWriter zoo = ZooReaderWriter.getInstance();
    if (Long.parseLong(new String(zoo.getData(zCancelID, null))) >= compactId) {
        // compaction was canceled
        throw new AcceptableThriftTableOperationException(tableId.canonicalID(), null, TableOperation.COMPACT, TableOperationExceptionType.OTHER, "Compaction canceled");
    }
    MapCounter<TServerInstance> serversToFlush = new MapCounter<>();
    Connector conn = master.getConnector();
    Scanner scanner;
    if (tableId.equals(MetadataTable.ID)) {
        scanner = new IsolatedScanner(conn.createScanner(RootTable.NAME, Authorizations.EMPTY));
        scanner.setRange(MetadataSchema.TabletsSection.getRange());
    } else {
        scanner = new IsolatedScanner(conn.createScanner(MetadataTable.NAME, Authorizations.EMPTY));
        Range range = new KeyExtent(tableId, null, startRow == null ? null : new Text(startRow)).toMetadataRange();
        scanner.setRange(range);
    }
    TabletsSection.ServerColumnFamily.COMPACT_COLUMN.fetch(scanner);
    TabletsSection.ServerColumnFamily.DIRECTORY_COLUMN.fetch(scanner);
    scanner.fetchColumnFamily(TabletsSection.CurrentLocationColumnFamily.NAME);
    long t1 = System.currentTimeMillis();
    RowIterator ri = new RowIterator(scanner);
    int tabletsToWaitFor = 0;
    int tabletCount = 0;
    while (ri.hasNext()) {
        Iterator<Entry<Key, Value>> row = ri.next();
        long tabletCompactID = -1;
        TServerInstance server = null;
        Entry<Key, Value> entry = null;
        while (row.hasNext()) {
            entry = row.next();
            Key key = entry.getKey();
            if (TabletsSection.ServerColumnFamily.COMPACT_COLUMN.equals(key.getColumnFamily(), key.getColumnQualifier()))
                tabletCompactID = Long.parseLong(entry.getValue().toString());
            if (TabletsSection.CurrentLocationColumnFamily.NAME.equals(key.getColumnFamily()))
                server = new TServerInstance(entry.getValue(), key.getColumnQualifier());
        }
        if (tabletCompactID < compactId) {
            tabletsToWaitFor++;
            if (server != null)
                serversToFlush.increment(server, 1);
        }
        tabletCount++;
        Text tabletEndRow = new KeyExtent(entry.getKey().getRow(), (Text) null).getEndRow();
        if (tabletEndRow == null || (endRow != null && tabletEndRow.compareTo(new Text(endRow)) >= 0))
            break;
    }
    long scanTime = System.currentTimeMillis() - t1;
    Instance instance = master.getInstance();
    Tables.clearCache(instance);
    if (tabletCount == 0 && !Tables.exists(instance, tableId))
        throw new AcceptableThriftTableOperationException(tableId.canonicalID(), null, TableOperation.COMPACT, TableOperationExceptionType.NOTFOUND, null);
    if (serversToFlush.size() == 0 && Tables.getTableState(instance, tableId) == TableState.OFFLINE)
        throw new AcceptableThriftTableOperationException(tableId.canonicalID(), null, TableOperation.COMPACT, TableOperationExceptionType.OFFLINE, null);
    if (tabletsToWaitFor == 0)
        return 0;
    for (TServerInstance tsi : serversToFlush.keySet()) {
        try {
            final TServerConnection server = master.getConnection(tsi);
            if (server != null)
                server.compact(master.getMasterLock(), tableId.canonicalID(), startRow, endRow);
        } catch (TException ex) {
            LoggerFactory.getLogger(CompactionDriver.class).error(ex.toString());
        }
    }
    long sleepTime = 500;
    if (serversToFlush.size() > 0)
        // make wait time depend on the server with the most to
        sleepTime = Collections.max(serversToFlush.values()) * sleepTime;
    // compact
    sleepTime = Math.max(2 * scanTime, sleepTime);
    sleepTime = Math.min(sleepTime, 30000);
    return sleepTime;
}
Also used : TException(org.apache.thrift.TException) Connector(org.apache.accumulo.core.client.Connector) IsolatedScanner(org.apache.accumulo.core.client.IsolatedScanner) Scanner(org.apache.accumulo.core.client.Scanner) Instance(org.apache.accumulo.core.client.Instance) TServerInstance(org.apache.accumulo.server.master.state.TServerInstance) Text(org.apache.hadoop.io.Text) Range(org.apache.accumulo.core.data.Range) KeyExtent(org.apache.accumulo.core.data.impl.KeyExtent) TServerInstance(org.apache.accumulo.server.master.state.TServerInstance) AcceptableThriftTableOperationException(org.apache.accumulo.core.client.impl.AcceptableThriftTableOperationException) TServerConnection(org.apache.accumulo.server.master.LiveTServerSet.TServerConnection) Entry(java.util.Map.Entry) IZooReaderWriter(org.apache.accumulo.fate.zookeeper.IZooReaderWriter) RowIterator(org.apache.accumulo.core.client.RowIterator) MapCounter(org.apache.accumulo.core.util.MapCounter) Value(org.apache.accumulo.core.data.Value) IsolatedScanner(org.apache.accumulo.core.client.IsolatedScanner) Key(org.apache.accumulo.core.data.Key)

Example 5 with MapCounter

use of org.apache.accumulo.core.util.MapCounter in project accumulo by apache.

the class TabletServer method getStats.

public TabletServerStatus getStats(Map<Table.ID, MapCounter<ScanRunState>> scanCounts) {
    long start = System.currentTimeMillis();
    TabletServerStatus result = new TabletServerStatus();
    Map<KeyExtent, Tablet> onlineTabletsCopy;
    synchronized (this.onlineTablets) {
        onlineTabletsCopy = new HashMap<>(this.onlineTablets);
    }
    Map<String, TableInfo> tables = new HashMap<>();
    for (Entry<KeyExtent, Tablet> entry : onlineTabletsCopy.entrySet()) {
        String tableId = entry.getKey().getTableId().canonicalID();
        TableInfo table = tables.get(tableId);
        if (table == null) {
            table = new TableInfo();
            table.minors = new Compacting();
            table.majors = new Compacting();
            tables.put(tableId, table);
        }
        Tablet tablet = entry.getValue();
        long recs = tablet.getNumEntries();
        table.tablets++;
        table.onlineTablets++;
        table.recs += recs;
        table.queryRate += tablet.queryRate();
        table.queryByteRate += tablet.queryByteRate();
        table.ingestRate += tablet.ingestRate();
        table.ingestByteRate += tablet.ingestByteRate();
        table.scanRate += tablet.scanRate();
        long recsInMemory = tablet.getNumEntriesInMemory();
        table.recsInMemory += recsInMemory;
        if (tablet.isMinorCompactionRunning())
            table.minors.running++;
        if (tablet.isMinorCompactionQueued())
            table.minors.queued++;
        if (tablet.isMajorCompactionRunning())
            table.majors.running++;
        if (tablet.isMajorCompactionQueued())
            table.majors.queued++;
    }
    for (Entry<Table.ID, MapCounter<ScanRunState>> entry : scanCounts.entrySet()) {
        TableInfo table = tables.get(entry.getKey().canonicalID());
        if (table == null) {
            table = new TableInfo();
            tables.put(entry.getKey().canonicalID(), table);
        }
        if (table.scans == null)
            table.scans = new Compacting();
        table.scans.queued += entry.getValue().get(ScanRunState.QUEUED);
        table.scans.running += entry.getValue().get(ScanRunState.RUNNING);
    }
    ArrayList<KeyExtent> offlineTabletsCopy = new ArrayList<>();
    synchronized (this.unopenedTablets) {
        synchronized (this.openingTablets) {
            offlineTabletsCopy.addAll(this.unopenedTablets);
            offlineTabletsCopy.addAll(this.openingTablets);
        }
    }
    for (KeyExtent extent : offlineTabletsCopy) {
        String tableId = extent.getTableId().canonicalID();
        TableInfo table = tables.get(tableId);
        if (table == null) {
            table = new TableInfo();
            tables.put(tableId, table);
        }
        table.tablets++;
    }
    result.lastContact = RelativeTime.currentTimeMillis();
    result.tableMap = tables;
    result.osLoad = ManagementFactory.getOperatingSystemMXBean().getSystemLoadAverage();
    result.name = getClientAddressString();
    result.holdTime = resourceManager.holdTime();
    result.lookups = seekCount.get();
    result.indexCacheHits = resourceManager.getIndexCache().getStats().hitCount();
    result.indexCacheRequest = resourceManager.getIndexCache().getStats().requestCount();
    result.dataCacheHits = resourceManager.getDataCache().getStats().hitCount();
    result.dataCacheRequest = resourceManager.getDataCache().getStats().requestCount();
    result.logSorts = logSorter.getLogSorts();
    result.flushs = flushCounter.get();
    result.syncs = syncCounter.get();
    result.bulkImports = new ArrayList<>();
    result.bulkImports.addAll(clientHandler.getBulkLoadStatus());
    result.bulkImports.addAll(bulkImportStatus.getBulkLoadStatus());
    result.version = getVersion();
    result.responseTime = System.currentTimeMillis() - start;
    return result;
}
Also used : ConcurrentHashMap(java.util.concurrent.ConcurrentHashMap) HashMap(java.util.HashMap) ArrayList(java.util.ArrayList) TKeyExtent(org.apache.accumulo.core.data.thrift.TKeyExtent) KeyExtent(org.apache.accumulo.core.data.impl.KeyExtent) Compacting(org.apache.accumulo.core.master.thrift.Compacting) MapCounter(org.apache.accumulo.core.util.MapCounter) Tablet(org.apache.accumulo.tserver.tablet.Tablet) TableInfo(org.apache.accumulo.core.master.thrift.TableInfo) TabletServerStatus(org.apache.accumulo.core.master.thrift.TabletServerStatus)

Aggregations

MapCounter (org.apache.accumulo.core.util.MapCounter)5 KeyExtent (org.apache.accumulo.core.data.impl.KeyExtent)4 HashMap (java.util.HashMap)3 Entry (java.util.Map.Entry)3 ConcurrentHashMap (java.util.concurrent.ConcurrentHashMap)2 IsolatedScanner (org.apache.accumulo.core.client.IsolatedScanner)2 RowIterator (org.apache.accumulo.core.client.RowIterator)2 Scanner (org.apache.accumulo.core.client.Scanner)2 Key (org.apache.accumulo.core.data.Key)2 Range (org.apache.accumulo.core.data.Range)2 Value (org.apache.accumulo.core.data.Value)2 TServerInstance (org.apache.accumulo.server.master.state.TServerInstance)2 Text (org.apache.hadoop.io.Text)2 ArrayList (java.util.ArrayList)1 HashSet (java.util.HashSet)1 ZipEntry (java.util.zip.ZipEntry)1 AccumuloException (org.apache.accumulo.core.client.AccumuloException)1 Connector (org.apache.accumulo.core.client.Connector)1 Instance (org.apache.accumulo.core.client.Instance)1 TableDeletedException (org.apache.accumulo.core.client.TableDeletedException)1