func TestPGWireDBName(t *testing.T) { defer leaktest.AfterTest(t)() s, _, _ := serverutils.StartServer(t, base.TestServerArgs{}) defer s.Stopper().Stop() pgURL, cleanupFn := sqlutils.PGUrl(t, s.ServingAddr(), "TestPGWireDBName", url.User(security.RootUser)) pgURL.Path = "foo" defer cleanupFn() { db, err := gosql.Open("postgres", pgURL.String()) if err != nil { t.Fatal(err) } defer db.Close() if _, err := db.Exec(`CREATE DATABASE foo`); err != nil { t.Fatal(err) } if _, err := db.Exec(`CREATE TABLE bar (i INT PRIMARY KEY)`); err != nil { t.Fatal(err) } } db, err := gosql.Open("postgres", pgURL.String()) if err != nil { t.Fatal(err) } defer db.Close() if _, err := db.Exec(`INSERT INTO bar VALUES ($1)`, 1); err != nil { t.Fatal(err) } }
// Test that rando commands while in COMMIT_WAIT return a particular error. func TestCommitWaitState(t *testing.T) { defer leaktest.AfterTest(t)() params, _ := createTestServerParams() s, sqlDB, _ := serverutils.StartServer(t, params) defer s.Stopper().Stop() if _, err := sqlDB.Exec(` CREATE DATABASE t; CREATE TABLE t.test (k INT PRIMARY KEY, v TEXT); `); err != nil { t.Fatal(err) } tx, err := sqlDB.Begin() if err != nil { t.Fatal(err) } if _, err := tx.Exec( "SAVEPOINT cockroach_restart; RELEASE cockroach_restart"); err != nil { t.Fatal(err) } if _, err := tx.Exec("INSERT INTO t.test(k, v) VALUES (0, 'sentinel')"); !testutils.IsError(err, "current transaction is committed") { t.Fatalf("unexpected error: %v", err) } // Rollback should respond with a COMMIT command tag. if err := tx.Rollback(); !testutils.IsError(err, "unexpected command tag COMMIT") { t.Fatalf("unexpected error: %v", err) } }
// TestRollbackToSavepointStatement tests that issuing a RESTART outside of a // txn produces the proper error. func TestRollbackToSavepointStatement(t *testing.T) { defer leaktest.AfterTest(t)() params, _ := createTestServerParams() s, sqlDB, _ := serverutils.StartServer(t, params) defer s.Stopper().Stop() // ROLLBACK TO SAVEPOINT without a transaction _, err := sqlDB.Exec("ROLLBACK TO SAVEPOINT cockroach_restart") if !testutils.IsError(err, "the transaction is not in a retriable state") { t.Fatalf("unexpected error: %v", err) } // ROLLBACK TO SAVEPOINT with a wrong name _, err = sqlDB.Exec("ROLLBACK TO SAVEPOINT foo") if !testutils.IsError(err, "SAVEPOINT not supported except for COCKROACH_RESTART") { t.Fatalf("unexpected error: %v", err) } // ROLLBACK TO SAVEPOINT in a non-retriable transaction tx, err := sqlDB.Begin() if err != nil { t.Fatal(err) } if _, err := tx.Exec("SAVEPOINT cockroach_restart"); err != nil { t.Fatal(err) } if _, err := tx.Exec("BOGUS SQL STATEMENT"); !testutils.IsError(err, `syntax error at or near "BOGUS"`) { t.Fatalf("unexpected error: %v", err) } if _, err := tx.Exec("ROLLBACK TO SAVEPOINT cockroach_restart"); !testutils.IsError( err, "SAVEPOINT COCKROACH_RESTART has not been used or a non-retriable error was encountered", ) { t.Fatalf("unexpected error: %v", err) } }
// TestClientEmptyValues verifies that empty values are preserved // for both empty []byte and integer=0. This used to fail when we // allowed the protobufs to be gob-encoded using the default go rpc // gob codec because gob treats pointer values and non-pointer values // as equivalent and elides zero-valued defaults on decode. func TestClientEmptyValues(t *testing.T) { defer leaktest.AfterTest(t)() s, _, _ := serverutils.StartServer(t, base.TestServerArgs{}) defer s.Stopper().Stop() db := createTestClient(t, s) if err := db.Put(context.TODO(), testUser+"/a", []byte{}); err != nil { t.Error(err) } if gr, err := db.Get(context.TODO(), testUser+"/a"); err != nil { t.Error(err) } else if bytes := gr.ValueBytes(); bytes == nil || len(bytes) != 0 { t.Errorf("expected non-nil empty byte slice; got %q", bytes) } if _, err := db.Inc(context.TODO(), testUser+"/b", 0); err != nil { t.Error(err) } if gr, err := db.Get(context.TODO(), testUser+"/b"); err != nil { t.Error(err) } else if gr.Value == nil { t.Errorf("expected non-nil integer") } else if gr.ValueInt() != 0 { t.Errorf("expected 0-valued integer, but got %d", gr.ValueInt()) } }
// TestNonRetryableErrorOnCommit verifies that a non-retryable error from the // execution of EndTransactionRequests is propagated to the client. func TestNonRetryableErrorOnCommit(t *testing.T) { defer leaktest.AfterTest(t)() params, cmdFilters := createTestServerParams() s, sqlDB, _ := serverutils.StartServer(t, params) defer s.Stopper().Stop() hitError := false cleanupFilter := cmdFilters.AppendFilter( func(args storagebase.FilterArgs) *roachpb.Error { if req, ok := args.Req.(*roachpb.EndTransactionRequest); ok { if bytes.Contains(req.Key, []byte(keys.DescIDGenerator)) { hitError = true return roachpb.NewErrorWithTxn(fmt.Errorf("testError"), args.Hdr.Txn) } } return nil }, false) defer cleanupFilter() if _, err := sqlDB.Exec("CREATE DATABASE t"); !testutils.IsError(err, "pq: testError") { t.Errorf("unexpected error %v", err) } if !hitError { t.Errorf("expected to hit error, but it didn't happen") } }
// TestClientGetAndPutProto verifies gets and puts of protobufs using the // client's convenience methods. func TestClientGetAndPutProto(t *testing.T) { defer leaktest.AfterTest(t)() s, _, _ := serverutils.StartServer(t, base.TestServerArgs{}) defer s.Stopper().Stop() db := createTestClient(t, s) zoneConfig := config.ZoneConfig{ NumReplicas: 2, Constraints: config.Constraints{Constraints: []config.Constraint{{Value: "mem"}}}, RangeMinBytes: 1 << 10, // 1k RangeMaxBytes: 1 << 18, // 256k } key := roachpb.Key(testUser + "/zone-config") if err := db.Put(context.TODO(), key, &zoneConfig); err != nil { t.Fatalf("unable to put proto: %s", err) } var readZoneConfig config.ZoneConfig if err := db.GetProto(context.TODO(), key, &readZoneConfig); err != nil { t.Fatalf("unable to get proto: %s", err) } if !proto.Equal(&zoneConfig, &readZoneConfig) { t.Errorf("expected %+v, but found %+v", zoneConfig, readZoneConfig) } }
func TestHealthAPI(t *testing.T) { defer leaktest.AfterTest(t)() s, _, _ := serverutils.StartServer(t, base.TestServerArgs{}) defer s.Stopper().Stop() // We need to retry because the node ID isn't set until after // bootstrapping. testutils.SucceedsSoon(t, func() error { var resp serverpb.HealthResponse return getAdminJSONProto(s, "health", &resp) }) // Expire this node's liveness record by pausing heartbeats and advancing the // server's clock. ts := s.(*TestServer) ts.nodeLiveness.PauseHeartbeat(true) self, err := ts.nodeLiveness.Self() if err != nil { t.Fatal(err) } s.Clock().Update(self.Expiration.Add(1, 0)) expected := "node is not live" var resp serverpb.HealthResponse if err := getAdminJSONProto(s, "health", &resp); !testutils.IsError(err, expected) { t.Errorf("expected %q error, got %v", expected, err) } }
func TestOrderByRandom(t *testing.T) { defer leaktest.AfterTest(t)() params, _ := createTestServerParams() s, sqlDB, _ := serverutils.StartServer(t, params) defer s.Stopper().Stop() seenOne := false seenTwo := false for { row := sqlDB.QueryRow("SELECT * FROM (VALUES (1),(2)) ORDER BY RANDOM() LIMIT 1") var val int if err := row.Scan(&val); err != nil { t.Fatal(err) } switch val { case 1: seenOne = true case 2: seenTwo = true } if seenOne && seenTwo { break } } }
// TestAuthentication tests authentication for the KV endpoint. func TestAuthentication(t *testing.T) { defer leaktest.AfterTest(t)() s, _, _ := serverutils.StartServer(t, base.TestServerArgs{}) defer s.Stopper().Stop() b1 := &client.Batch{} b1.Put("a", "b") // Create a node user client and call Run() on it which lets us build our own // request, specifying the user. db1 := createTestClientForUser(t, s, security.NodeUser) if err := db1.Run(context.TODO(), b1); err != nil { t.Fatal(err) } b2 := &client.Batch{} b2.Put("c", "d") // Try again, but this time with certs for a non-node user (even the root // user has no KV permissions). db2 := createTestClientForUser(t, s, security.RootUser) if err := db2.Run(context.TODO(), b2); !testutils.IsError(err, "is not allowed") { t.Fatal(err) } }
// TestNoSequenceCachePutOnRangeMismatchError verifies that the // sequence cache is not updated with RangeKeyMismatchError. This is a // higher-level version of TestSequenceCacheShouldCache. func TestNoSequenceCachePutOnRangeMismatchError(t *testing.T) { defer leaktest.AfterTest(t)() s, _, _ := serverutils.StartServer(t, base.TestServerArgs{}) defer s.Stopper().Stop() db := setupMultipleRanges(t, s, "b", "c") // The requests in the transaction below will be chunked and // sent to replicas in the following way: // 1) A batch request containing a BeginTransaction and a // put on "a" are sent to a replica owning range ["a","b"). // 2) A next batch request containing a put on "b" and a put // on "c" are sent to a replica owning range ["b","c"). // (The range cache has a stale range descriptor.) // 3) The put request on "c" causes a RangeKeyMismatchError. // 4) The dist sender re-sends a request to the same replica. // This time the request contains only the put on "b" to the // same replica. // 5) The command succeeds since the sequence cache has not yet been updated. epoch := 0 if err := db.Txn(context.TODO(), func(txn *client.Txn) error { epoch++ b := txn.NewBatch() b.Put("a", "val") b.Put("b", "val") b.Put("c", "val") return txn.CommitInBatch(b) }); err != nil { t.Errorf("unexpected error on transactional Puts: %s", err) } if epoch != 1 { t.Errorf("unexpected epoch; the txn must not be retried, but got %d retries", epoch) } }
func TestDropTableInTxn(t *testing.T) { defer leaktest.AfterTest(t)() params, _ := createTestServerParams() s, sqlDB, _ := serverutils.StartServer(t, params) defer s.Stopper().Stop() if _, err := sqlDB.Exec(` CREATE DATABASE t; CREATE TABLE t.kv (k CHAR PRIMARY KEY, v CHAR); `); err != nil { t.Fatal(err) } tx, err := sqlDB.Begin() if err != nil { t.Fatal(err) } if _, err := tx.Exec(`DROP TABLE t.kv`); err != nil { t.Fatal(err) } // We might still be able to read/write in the table inside this transaction // until the schema changer runs, but we shouldn't be able to ALTER it. if _, err := tx.Exec(`ALTER TABLE t.kv ADD COLUMN w CHAR`); !testutils.IsError(err, `table "kv" is being dropped`) { t.Fatalf("different error than expected: %v", err) } // Can't commit after ALTER errored, so we ROLLBACK. if err := tx.Rollback(); err != nil { t.Fatal(err) } }
// startServer will start a server with a short scan interval, wait for // the scan to complete, and return the server. The caller is // responsible for stopping the server. func startServer(t *testing.T) *TestServer { tsI, _, kvDB := serverutils.StartServer(t, base.TestServerArgs{ StoreSpecs: []base.StoreSpec{ base.DefaultTestStoreSpec, base.DefaultTestStoreSpec, base.DefaultTestStoreSpec, }, }) ts := tsI.(*TestServer) // Make sure the range is spun up with an arbitrary read command. We do not // expect a specific response. if _, err := kvDB.Get(context.TODO(), "a"); err != nil { t.Fatal(err) } // Make sure the node status is available. This is done by forcing stores to // publish their status, synchronizing to the event feed with a canary // event, and then forcing the server to write summaries immediately. if err := ts.node.computePeriodicMetrics(0); err != nil { t.Fatalf("error publishing store statuses: %s", err) } if err := ts.WriteSummaries(); err != nil { t.Fatalf("error writing summaries: %s", err) } return ts }
// TestMetricsRecording verifies that Node statistics are periodically recorded // as time series data. func TestMetricsRecording(t *testing.T) { defer leaktest.AfterTest(t)() s, _, kvDB := serverutils.StartServer(t, base.TestServerArgs{ MetricsSampleInterval: 5 * time.Millisecond}) defer s.Stopper().Stop() checkTimeSeriesKey := func(now int64, keyName string) error { key := ts.MakeDataKey(keyName, "", ts.Resolution10s, now) data := roachpb.InternalTimeSeriesData{} return kvDB.GetProto(context.TODO(), key, &data) } // Verify that metrics for the current timestamp are recorded. This should // be true very quickly. util.SucceedsSoon(t, func() error { now := s.Clock().PhysicalNow() if err := checkTimeSeriesKey(now, "cr.store.livebytes.1"); err != nil { return err } if err := checkTimeSeriesKey(now, "cr.node.sys.go.allocbytes.1"); err != nil { return err } return nil }) }
func TestMixedDirections(t *testing.T) { defer leaktest.AfterTest(t)() s, db, cdb := serverutils.StartServer(t, base.TestServerArgs{ UseDatabase: "t", }) defer s.Stopper().Stop() rowRanges, tableDesc := setupRanges(db, s.(*server.TestServer), cdb, t) lr := distsqlplan.NewSpanResolver( s.DistSender(), s.Gossip(), s.(*server.TestServer).GetNode().Descriptor, distsqlplan.BinPackingLeaseHolderChoice) ctx := context.Background() it := lr.NewSpanResolverIterator() spans := []spanWithDir{ orient(kv.Ascending, makeSpan(tableDesc, 11, 15))[0], orient(kv.Descending, makeSpan(tableDesc, 1, 14))[0], } replicas, err := resolveSpans(ctx, it, spans...) if err != nil { t.Fatal(err) } expected := [][]rngInfo{ {onlyReplica(rowRanges[1])}, {onlyReplica(rowRanges[1]), onlyReplica(rowRanges[0])}, } if err = expectResolved(replicas, expected...); err != nil { t.Fatal(err) } }
// Test that table names are not treated as case sensitive by the name cache. func TestTableNameNotCaseSensitive(t *testing.T) { defer leaktest.AfterTest(t)() s, db, kvDB := serverutils.StartServer(t, base.TestServerArgs{}) defer s.Stopper().Stop() leaseManager := s.LeaseManager().(*LeaseManager) if _, err := db.Exec(` CREATE DATABASE t; CREATE TABLE t.test (k CHAR PRIMARY KEY, v CHAR); `); err != nil { t.Fatal(err) } // Populate the name cache. if _, err := db.Exec("SELECT * FROM t.test;"); err != nil { t.Fatal(err) } tableDesc := sqlbase.GetTableDescriptor(kvDB, "t", "test") // Check that we can get the table by a different name. lease := leaseManager.tableNames.get(tableDesc.ParentID, "tEsT", s.Clock()) if lease == nil { t.Fatalf("no name cache entry") } if err := leaseManager.Release(lease); err != nil { t.Fatal(err) } }
func TestExplainTrace(t *testing.T) { defer leaktest.AfterTest(t)() params, _ := createTestServerParams() s, sqlDB, _ := serverutils.StartServer(t, params) defer s.Stopper().Stop() if _, err := sqlDB.Exec(`CREATE DATABASE test; CREATE TABLE test.foo (id INT PRIMARY KEY)`); err != nil { t.Fatal(err) } rows, err := sqlDB.Query(`EXPLAIN (TRACE) INSERT INTO test.foo VALUES (1)`) if err != nil { t.Fatal(err) } expParts := []string{"coordinator", "node.Batch"} var parts []string pretty := rowsToStrings(rows) for _, row := range pretty[1:] { part := row[3] // Operation if ind := sort.SearchStrings(parts, part); ind == len(parts) || parts[ind] != part { parts = append(parts, part) sort.Strings(parts) } } sort.Strings(expParts) if err := rows.Err(); err != nil { t.Fatal(err) } if !reflect.DeepEqual(expParts, parts) { t.Fatalf("expected %v, got %v\n\nResults:\n%v", expParts, parts, prettyPrint(pretty)) } }
func TestBadRequest(t *testing.T) { defer leaktest.AfterTest(t)() s, _, _ := serverutils.StartServer(t, base.TestServerArgs{}) defer s.Stopper().Stop() db := createTestClient(t, s.Stopper(), s.ServingAddr()) ctx := context.TODO() // Write key "a". if err := db.Put(ctx, "a", "value"); err != nil { t.Fatal(err) } if _, err := db.Scan(ctx, "a", "a", 0); !testutils.IsError(err, "truncation resulted in empty batch") { t.Fatalf("unexpected error on scan with startkey == endkey: %v", err) } if _, err := db.ReverseScan(ctx, "a", "a", 0); !testutils.IsError(err, "truncation resulted in empty batch") { t.Fatalf("unexpected error on reverse scan with startkey == endkey: %v", err) } if err := db.DelRange(ctx, "x", "a"); !testutils.IsError(err, "truncation resulted in empty batch") { t.Fatalf("unexpected error on deletion on [x, a): %v", err) } if err := db.DelRange(ctx, "", "z"); !testutils.IsError(err, "must be greater than LocalMax") { t.Fatalf("unexpected error on deletion on [KeyMin, z): %v", err) } }
// TestRangeLookupWithOpenTransaction verifies that range lookups are // done in such a way (e.g. using inconsistent reads) that they // proceed in the event that a write intent is extant at the meta // index record being read. func TestRangeLookupWithOpenTransaction(t *testing.T) { defer leaktest.AfterTest(t)() s, _, _ := serverutils.StartServer(t, base.TestServerArgs{}) defer s.Stopper().Stop() db := createTestClient(t, s.Stopper(), s.ServingAddr()) // Create an intent on the meta1 record by writing directly to the // engine. key := testutils.MakeKey(keys.Meta1Prefix, roachpb.KeyMax) now := s.Clock().Now() txn := roachpb.NewTransaction("txn", roachpb.Key("foobar"), 0, enginepb.SERIALIZABLE, now, 0) if err := engine.MVCCPutProto( context.Background(), s.(*server.TestServer).Engines()[0], nil, key, now, txn, &roachpb.RangeDescriptor{}); err != nil { t.Fatal(err) } // Now, with an intent pending, attempt (asynchronously) to read // from an arbitrary key. This will cause the distributed sender to // do a range lookup, which will encounter the intent. We're // verifying here that the range lookup doesn't fail with a write // intent error. If it did, it would go into a deadloop attempting // to push the transaction, which in turn requires another range // lookup, etc, ad nauseam. if _, err := db.Get(context.TODO(), "a"); err != nil { t.Fatal(err) } }
// TestDropTableInterleaved tests dropping a table that is interleaved within // another table. func TestDropTableInterleaved(t *testing.T) { defer leaktest.AfterTest(t)() params, _ := createTestServerParams() s, sqlDB, kvDB := serverutils.StartServer(t, params) defer s.Stopper().Stop() numRows := 2*sql.TableTruncateChunkSize + 1 createKVInterleavedTable(t, sqlDB, numRows) tableDesc := sqlbase.GetTableDescriptor(kvDB, "t", "kv") tablePrefix := roachpb.Key(keys.MakeTablePrefix(uint32(tableDesc.ID))) checkKeyCount(t, kvDB, tablePrefix, 3*numRows) if _, err := sqlDB.Exec(`DROP TABLE t.intlv`); err != nil { t.Fatal(err) } checkKeyCount(t, kvDB, tablePrefix, numRows) // Test that deleted table cannot be used. This prevents regressions where // name -> descriptor ID caches might make this statement erronously work. if _, err := sqlDB.Exec(`SELECT * FROM t.intlv`); !testutils.IsError( err, `table "t.intlv" does not exist`, ) { t.Fatalf("different error than expected: %v", err) } }
// TestMultiRangeBoundedBatchScanSortedOverlapping runs two overlapping // ordered (by start key) scan requests, and shows how the batch response can // contain two partial responses. func TestMultiRangeBoundedBatchScanSortedOverlapping(t *testing.T) { defer leaktest.AfterTest(t)() s, _, _ := serverutils.StartServer(t, base.TestServerArgs{}) defer s.Stopper().Stop() db := setupMultipleRanges(t, s, "a", "b", "c", "d", "e", "f") for _, key := range []string{"a1", "a2", "a3", "b1", "b2", "c1", "c2", "d1", "f1", "f2", "f3"} { if err := db.Put(context.TODO(), key, "value"); err != nil { t.Fatal(err) } } bound := 6 b := &client.Batch{} b.Header.MaxSpanRequestKeys = int64(bound) // Two ordered overlapping requests. spans := [][]string{{"a", "d"}, {"b", "g"}} for _, span := range spans { b.Scan(span[0], span[1]) } if err := db.Run(context.TODO(), b); err != nil { t.Fatal(err) } // See incomplete results for the two requests. expResults := [][]string{ {"a1", "a2", "a3", "b1", "b2"}, {"b1"}, } checkScanResults(t, spans, b.Results, expResults, bound) }
// Tests a batch of bounded DelRange() requests. func TestMultiRangeBoundedBatchDelRange(t *testing.T) { defer leaktest.AfterTest(t)() s, _, _ := serverutils.StartServer(t, base.TestServerArgs{}) defer s.Stopper().Stop() db := setupMultipleRanges(t, s, "a", "b", "c", "d", "e", "f", "g", "h") // These are the expected results if there is no bound. expResults := [][]string{ {"a1", "a2", "a3", "b1", "b2"}, {"c1", "c2", "d1"}, {"g1", "g2"}, } maxExpCount := 0 for _, res := range expResults { maxExpCount += len(res) } for bound := 1; bound <= 20; bound++ { // Initialize all keys. for _, key := range []string{"a1", "a2", "a3", "b1", "b2", "c1", "c2", "d1", "f1", "f2", "f3", "g1", "g2", "h1"} { if err := db.Put(context.TODO(), key, "value"); err != nil { t.Fatal(err) } } b := &client.Batch{} b.Header.MaxSpanRequestKeys = int64(bound) spans := [][]string{{"a", "c"}, {"c", "f"}, {"g", "h"}} for _, span := range spans { b.DelRange(span[0], span[1], true) } if err := db.Run(context.TODO(), b); err != nil { t.Fatal(err) } if len(expResults) != len(b.Results) { t.Fatalf("bound: %d, only got %d results, wanted %d", bound, len(expResults), len(b.Results)) } expCount := maxExpCount if bound < maxExpCount { expCount = bound } rem := expCount for i, res := range b.Results { // Verify that the KeyValue slice contains the given keys. rem -= len(res.Keys) for j, key := range res.Keys { if expKey := expResults[i][j]; string(key) != expKey { t.Errorf("%s: expected scan key %d, %d to be %q; got %q", errInfo(), i, j, expKey, key) } } } if rem != 0 { t.Errorf("expected %d keys, got %d", bound, expCount-rem) } checkResumeSpanDelRangeResults(t, spans, b.Results, expResults, expCount) } }
func newKVNative(b *testing.B) kvInterface { enableTracing := tracing.Disable() s, _, _ := serverutils.StartServer(b, base.TestServerArgs{}) // TestServer.DB() returns the TxnCoordSender wrapped client. But that isn't // a fair comparison with SQL as we want these client requests to be sent // over the network. sender, err := client.NewSender( rpc.NewContext(log.AmbientContext{}, &base.Config{ User: security.NodeUser, SSLCA: filepath.Join(security.EmbeddedCertsDir, security.EmbeddedCACert), SSLCert: filepath.Join(security.EmbeddedCertsDir, "node.crt"), SSLCertKey: filepath.Join(security.EmbeddedCertsDir, "node.key"), }, nil, s.Stopper()), s.ServingAddr()) if err != nil { b.Fatal(err) } return &kvNative{ db: client.NewDB(sender), doneFn: func() { s.Stopper().Stop() enableTracing() }, } }
// TestCopyInProgress verifies that after a COPY has started another statement // cannot run. func TestCopyInProgress(t *testing.T) { defer leaktest.AfterTest(t)() t.Skip("https://github.com/lib/pq/issues/494") params, _ := createTestServerParams() s, db, _ := serverutils.StartServer(t, params) defer s.Stopper().Stop() if _, err := db.Exec(` CREATE DATABASE d; SET DATABASE = d; CREATE TABLE t ( i INT PRIMARY KEY ); `); err != nil { t.Fatal(err) } txn, err := db.Begin() if err != nil { t.Fatal(err) } if _, err := txn.Prepare(pq.CopyIn("t", "i")); err != nil { t.Fatal(err) } if _, err := txn.Query("SELECT 1"); err == nil { t.Fatal("expected error") } }
// TestServerQueryStarvation tests a very specific scenario, wherein a single // query request has more queries than the server's MaxWorkers count. func TestServerQueryStarvation(t *testing.T) { defer leaktest.AfterTest(t)() workerCount := 20 s, _, _ := serverutils.StartServer(t, base.TestServerArgs{ TimeSeriesQueryWorkerMax: workerCount, }) defer s.Stopper().Stop() tsrv := s.(*server.TestServer) seriesCount := workerCount * 2 if err := populateSeries(seriesCount, 10, tsrv.TsDB()); err != nil { t.Fatal(err) } conn, err := tsrv.RPCContext().GRPCDial(tsrv.Cfg.Addr) if err != nil { t.Fatal(err) } client := tspb.NewTimeSeriesClient(conn) queries := make([]tspb.Query, 0, seriesCount) for i := 0; i < seriesCount; i++ { queries = append(queries, tspb.Query{ Name: seriesName(i), }) } if _, err := client.Query(context.Background(), &tspb.TimeSeriesQueryRequest{ StartNanos: 0 * 1e9, EndNanos: 500 * 1e9, Queries: queries, }); err != nil { t.Fatal(err) } }
// TestErrorDuringTransaction tests that the transaction abort count goes up when a query // results in an error during a txn. func TestAbortCountErrorDuringTransaction(t *testing.T) { defer leaktest.AfterTest(t)() params, _ := createTestServerParams() s, sqlDB, _ := serverutils.StartServer(t, params) defer s.Stopper().Stop() txn, err := sqlDB.Begin() if err != nil { t.Fatal(err) } if _, err := txn.Query("SELECT * FROM i_do.not_exist"); err == nil { t.Fatal("Expected an error but didn't get one") } if err := checkCounterEQ(s, sql.MetaTxnAbort, 1); err != nil { t.Error(err) } if err := checkCounterEQ(s, sql.MetaTxnBegin, 1); err != nil { t.Error(err) } if err := checkCounterEQ(s, sql.MetaSelect, 1); err != nil { t.Error(err) } }
// TestMultiRangeReverseScan verifies that ReverseScan gets the right results // across multiple ranges. func TestMultiRangeReverseScan(t *testing.T) { defer leaktest.AfterTest(t)() s, _, _ := serverutils.StartServer(t, base.TestServerArgs{}) defer s.Stopper().Stop() db := initReverseScanTestEnv(s, t) ctx := context.TODO() // Case 1: Request.EndKey is in the middle of the range. if rows, pErr := db.ReverseScan(ctx, "a", "d", 0); pErr != nil { t.Fatalf("unexpected error on ReverseScan: %s", pErr) } else if l := len(rows); l != 3 { t.Errorf("expected 3 rows; got %d", l) } if rows, pErr := db.ReverseScan(ctx, "a", "d", 2); pErr != nil { t.Fatalf("unexpected error on ReverseScan: %s", pErr) } else if l := len(rows); l != 2 { t.Errorf("expected 2 rows; got %d", l) } // Case 2: Request.EndKey is equal to the EndKey of the range. if rows, pErr := db.ReverseScan(ctx, "d", "g", 0); pErr != nil { t.Fatalf("unexpected error on ReverseScan: %s", pErr) } else if l := len(rows); l != 3 { t.Errorf("expected 3 rows; got %d", l) } }
func TestDropIndexInterleaved(t *testing.T) { defer leaktest.AfterTest(t)() const chunkSize = 200 params, _ := createTestServerParams() params.Knobs = base.TestingKnobs{ SQLSchemaChanger: &sql.SchemaChangerTestingKnobs{ BackfillChunkSize: chunkSize, }, } s, sqlDB, kvDB := serverutils.StartServer(t, params) defer s.Stopper().Stop() numRows := 2*chunkSize + 1 createKVInterleavedTable(t, sqlDB, numRows) tableDesc := sqlbase.GetTableDescriptor(kvDB, "t", "kv") tablePrefix := roachpb.Key(keys.MakeTablePrefix(uint32(tableDesc.ID))) checkKeyCount(t, kvDB, tablePrefix, 3*numRows) if _, err := sqlDB.Exec(`DROP INDEX t.intlv@intlv_idx`); err != nil { t.Fatal(err) } checkKeyCount(t, kvDB, tablePrefix, 2*numRows) // Ensure that index is not active. tableDesc = sqlbase.GetTableDescriptor(kvDB, "t", "intlv") if _, _, err := tableDesc.FindIndexByName("intlv_idx"); err == nil { t.Fatalf("table descriptor still contains index after index is dropped") } }
// TestReverseScanWithSplitAndMerge verifies that ReverseScan gets the right results // across multiple ranges while range splits and merges happen. func TestReverseScanWithSplitAndMerge(t *testing.T) { defer leaktest.AfterTest(t)() s, _, _ := serverutils.StartServer(t, base.TestServerArgs{}) defer s.Stopper().Stop() db := initReverseScanTestEnv(s, t) // Case 1: An encounter with a range split. // Split the range ["b", "e") at "c". if err := db.AdminSplit(context.TODO(), "c"); err != nil { t.Fatal(err) } // The ReverseScan will run into a stale descriptor. if rows, err := db.ReverseScan(context.TODO(), "a", "d", 0); err != nil { t.Fatalf("unexpected error on ReverseScan: %s", err) } else if l := len(rows); l != 3 { t.Errorf("expected 3 rows; got %d", l) } // Case 2: encounter with range merge . // Merge the range ["e", "g") and ["g", "\xff\xff") . if err := db.AdminMerge(context.TODO(), "e"); err != nil { t.Fatal(err) } if rows, err := db.ReverseScan(context.TODO(), "d", "g", 0); err != nil { t.Fatalf("unexpected error on ReverseScan: %s", err) } else if l := len(rows); l != 3 { t.Errorf("expected 3 rows; got %d", l) } }
// TestTxnObeysLeaseExpiration tests that a transaction is aborted when it tries // to use a table descriptor with an expired lease. func TestTxnObeysLeaseExpiration(t *testing.T) { defer leaktest.AfterTest(t)() t.Skip("TODO(vivek): #7031") // Set the lease duration such that it expires quickly. savedLeaseDuration, savedMinLeaseDuration := csql.LeaseDuration, csql.MinLeaseDuration defer func() { csql.LeaseDuration, csql.MinLeaseDuration = savedLeaseDuration, savedMinLeaseDuration }() csql.MinLeaseDuration = 100 * time.Millisecond csql.LeaseDuration = 2 * csql.MinLeaseDuration params, _ := createTestServerParams() s, sqlDB, _ := serverutils.StartServer(t, params) defer s.Stopper().Stop() leaseManager := s.LeaseManager().(*csql.LeaseManager) if _, err := sqlDB.Exec(` CREATE DATABASE t; CREATE TABLE t.kv (k CHAR PRIMARY KEY, v CHAR); INSERT INTO t.kv VALUES ('a', 'b'); `); err != nil { t.Fatal(err) } // Run a number of sql operations and expire the lease they acquire. runCommandAndExpireLease(t, leaseManager, s.Clock(), sqlDB, `INSERT INTO t.kv VALUES ('c', 'd')`) runCommandAndExpireLease(t, leaseManager, s.Clock(), sqlDB, `UPDATE t.kv SET v = 'd' WHERE k = 'a'`) runCommandAndExpireLease(t, leaseManager, s.Clock(), sqlDB, `DELETE FROM t.kv WHERE k = 'a'`) runCommandAndExpireLease(t, leaseManager, s.Clock(), sqlDB, `TRUNCATE TABLE t.kv`) }
// TestRenameTable tests the table descriptor changes during // a rename operation. func TestRenameTable(t *testing.T) { defer leaktest.AfterTest(t)() s, db, kvDB := serverutils.StartServer(t, base.TestServerArgs{}) defer s.Stopper().Stop() counter := int64(keys.MaxReservedDescID) counter++ oldDBID := sqlbase.ID(counter) if _, err := db.Exec(`CREATE DATABASE test`); err != nil { t.Fatal(err) } // Create table in 'test'. counter++ oldName := "foo" if _, err := db.Exec(`CREATE TABLE test.foo (k INT PRIMARY KEY, v int)`); err != nil { t.Fatal(err) } // Check the table descriptor. desc := &sqlbase.Descriptor{} tableDescKey := sqlbase.MakeDescMetadataKey(sqlbase.ID(counter)) if err := kvDB.GetProto(context.TODO(), tableDescKey, desc); err != nil { t.Fatal(err) } tableDesc := desc.GetTable() if tableDesc.Name != oldName { t.Fatalf("Wrong table name, expected %s, got: %+v", oldName, tableDesc) } if tableDesc.ParentID != oldDBID { t.Fatalf("Wrong parent ID on table, expected %d, got: %+v", oldDBID, tableDesc) } // Create database test2. counter++ newDBID := sqlbase.ID(counter) if _, err := db.Exec(`CREATE DATABASE test2`); err != nil { t.Fatal(err) } // Move table to test2 and change its name as well. newName := "bar" if _, err := db.Exec(`ALTER TABLE test.foo RENAME TO test2.bar`); err != nil { t.Fatal(err) } // Check the table descriptor again. if err := kvDB.GetProto(context.TODO(), tableDescKey, desc); err != nil { t.Fatal(err) } tableDesc = desc.GetTable() if tableDesc.Name != newName { t.Fatalf("Wrong table name, expected %s, got: %+v", newName, tableDesc) } if tableDesc.ParentID != newDBID { t.Fatalf("Wrong parent ID on table, expected %d, got: %+v", newDBID, tableDesc) } }