Package com.foundationdb.server.test.it.keyupdate

Source Code of com.foundationdb.server.test.it.keyupdate.GIUpdateITBase$StringsIndexScanner

/**
* Copyright (C) 2009-2013 FoundationDB, LLC
*
* This program 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 com.foundationdb.server.test.it.keyupdate;

import com.foundationdb.ais.model.AkibanInformationSchema;
import com.foundationdb.ais.model.Group;
import com.foundationdb.ais.model.GroupIndex;
import com.foundationdb.ais.model.Index;
import com.foundationdb.ais.model.Table;
import com.foundationdb.ais.model.TableName;
import com.foundationdb.qp.row.Row;
import com.foundationdb.server.api.dml.scan.NewRow;
import com.foundationdb.server.service.transaction.TransactionService.CloseableTransaction;
import com.foundationdb.server.store.IndexRecordVisitor;
import com.foundationdb.server.test.it.ITBase;
import com.foundationdb.util.Exceptions;
import com.foundationdb.util.Strings;
import org.junit.After;
import org.junit.Before;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

import static org.junit.Assert.assertEquals;

public abstract class GIUpdateITBase extends ITBase {

    @Before
    public final void createTables() {
        c = createTable(SCHEMA, "c", "cid int not null primary key, name varchar(32)");
        o = createTable(SCHEMA, "o", "oid int not null primary key, c_id int, when varchar(32)", akibanFK("c_id", "c", "cid") );
        i = createTable(SCHEMA, "i", "iid int not null primary key, o_id int, sku int", akibanFK("o_id", "o", "oid") );
        h = createTable(SCHEMA, "h", "sid int not null primary key, i_id int, handling_instructions varchar(32)", akibanFK("i_id", "i", "iid") );
        a = createTable(SCHEMA, "a", "oid int not null primary key, c_id int, street varchar(56)", akibanFK("c_id", "c", "cid") );
        groupName = getTable(c).getGroup().getName();
    }

    @After
    public final void forgetTables() {
        int[] ids = { a, h, i, o, c};
        int idIndex = 0;
        for(int i = 5; i >= 0; --i) {
            try {
                while(idIndex < ids.length) {
                    dml().truncateTable(session(), ids[idIndex]);
                    ++idIndex;
                }
                break;
            } catch(Exception e) {
                if(!Exceptions.isRollbackException(e) || i == 0) {
                    throw e;
                }
            }
        }

        Group group = getTable(c).getGroup();
        for (GroupIndex groupIndex : group.getIndexes()) {
            checkIndex(groupIndex);
        }

        c = null;
        o = null;
        i = null;
        h = null;
        a = null;
        groupName = null;
    }

    void writeAndCheck(Row row, String... expectedGiEntries) {
        writeRows(row);
        checkIndex(groupIndexName, expectedGiEntries);
    }

    void deleteAndCheck(Row row, String... expectedGiEntries) {
        deleteRow(row);
        checkIndex(groupIndexName, expectedGiEntries);
    }

    void deleteCascadeAndCheck(Row row, String... expectedGiEntries) {
        deleteRow(row, true);
        checkIndex(groupIndexName, expectedGiEntries);
    }

    void updateAndCheck(Row oldRow, Row newRow, String... expectedGiEntries) {
        updateRow(oldRow, newRow);
        checkIndex(groupIndexName, expectedGiEntries);
    }

    void checkIndex(String indexName, String... expected) {
        GroupIndex groupIndex = ddl().getAIS(session()).getGroup(groupName).getIndex(indexName);
        checkIndex(groupIndex, expected);
    }

    private void checkIndex(GroupIndex groupIndex, String... expected) {
        try(CloseableTransaction txn = txnService().beginCloseableTransaction(session())) {
            checkIndexInternal(groupIndex, expected);
            txn.commit();
        }
    }

    private void checkIndexInternal(GroupIndex groupIndex, String... expected) {
        StringsIndexScanner scanner = store().traverse(session(), groupIndex, new StringsIndexScanner(), -1, 0);
        // convert "a, b, c => d" to "[a, b, c] => d"
        for (int i = 0; i < expected.length; ++i) {
            String original = expected[i];
            int arrow = original.indexOf(" => ");
            String keys = original.substring(0, arrow);
            String value = original.substring(arrow + " => ".length());
            expected[i] = String.format("[%s] => %s", keys, value);
        }

        List<String> expectedList = Arrays.asList(expected);
        if (!expectedList.equals(scanner.strings())) {
            assertEquals("scan of " + groupIndex, Strings.join(expectedList), Strings.join(scanner.strings()));
            // just in case
            assertEquals("scan of " + groupIndex, expectedList, scanner.strings());
        }
    }

    String containing(String indexName, int firstTableId, int... tableIds) {
        Set<Table> containingTables = new HashSet<>();
        AkibanInformationSchema ais = ddl().getAIS(session());
        containingTables.add(ais.getTable(firstTableId));
        for (int tableId : tableIds) {
            containingTables.add(ais.getTable(tableId));
        }
        GroupIndex groupIndex = ais.getGroup(groupName).getIndex(indexName);
        if (groupIndex == null)
            throw new RuntimeException("group index undefined: " + indexName);
        long result = 0;
        for(Table table = groupIndex.leafMostTable();
            table != groupIndex.rootMostTable().getParentTable();
            table = table.getParentTable())
        {
            if (containingTables.remove(table)) {
                result |= 1 << table.getDepth();
            }
        }
        if (!containingTables.isEmpty())
            throw new RuntimeException("tables specified not in the branch: " + containingTables);
        assert Long.bitCount(result) == tableIds.length + 1;
        return Long.toBinaryString(result) + " (Long)";
    }

    String containing( int firstTableId, int... tableIds) {
        return containing(groupIndexName, firstTableId, tableIds);
    }

    String groupIndexNamed(String indexName, String... columnNames) {
        createGroupIndex(groupName, indexName, joinType, columnNames);
        return indexName;
    }

    String groupIndex(String... columnNames) {
        return groupIndexNamed(groupIndexName, columnNames);
    }

    GIUpdateITBase(Index.JoinType joinType) {
        this.joinType = joinType;
    }

    private final Index.JoinType joinType;
    private final String groupIndexName = "test_gi";

    TableName groupName;
    Integer c;
    Integer o;
    Integer i;
    Integer h;
    Integer a;

    // consts

    private static final String SCHEMA = "coia";

    // nested class

    private static class StringsIndexScanner extends IndexRecordVisitor {

        // IndexVisitor interface

        @Override
        public boolean groupIndex()
        {
            return true;
        }

        // IndexRecordVisitor interface

        @Override
        public void visit(List<?> key, Object value) {
            final String asString;
            if (value == null) {
                asString = String.format("%s => null", key);
            }
            else {
                final String className;
                if (value instanceof Long) {
                    value = Long.toBinaryString((Long)value);
                    className = "Long";
                }
                else {
                    className = value.getClass().getSimpleName();
                }
                asString = String.format("%s => %s (%s)", key, value, className);
            }
            _strings.add(asString);
        }

        // StringsIndexScanner interface

        public List<String> strings() {
            return _strings;
        }

        // object state

        private final List<String> _strings = new ArrayList<>();
    }
}
TOP

Related Classes of com.foundationdb.server.test.it.keyupdate.GIUpdateITBase$StringsIndexScanner

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.