github.com/jdgcs/sqlite3@v1.12.1-0.20210908114423-bc5f96e4dd51/cgo_test.go (about)

     1  // Copyright 2017 The Sqlite Authors. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  //go:build cgo && cgobench
     6  // +build cgo,cgobench
     7  
     8  package sqlite // import "modernc.org/sqlite"
     9  
    10  import (
    11  	"database/sql"
    12  	"fmt"
    13  	"os"
    14  	"path/filepath"
    15  	"testing"
    16  
    17  	_ "github.com/mattn/go-sqlite3"
    18  )
    19  
    20  const gcoDriver = "sqlite3"
    21  
    22  var drivers = []string{
    23  	driverName,
    24  	gcoDriver,
    25  }
    26  
    27  var inMemory = []bool{
    28  	true,
    29  	false,
    30  }
    31  
    32  func makename(inMemory bool, driver string, e int) string {
    33  	name := driver
    34  	if inMemory {
    35  		name += "InMemory"
    36  	} else {
    37  		name += "OnDisk"
    38  	}
    39  	return fmt.Sprintf("%s1e%d", name, e)
    40  }
    41  
    42  func benchmarkRead(b *testing.B, drivername, file string, n int) {
    43  	os.Remove(file)
    44  	db, err := sql.Open(drivername, file)
    45  	if err != nil {
    46  		b.Fatal(err)
    47  	}
    48  
    49  	defer func() {
    50  		db.Close()
    51  	}()
    52  
    53  	if _, err := db.Exec(`
    54  	create table t(i int);
    55  	begin;
    56  	`); err != nil {
    57  		b.Fatal(err)
    58  	}
    59  
    60  	s, err := db.Prepare("insert into t values(?)")
    61  	if err != nil {
    62  		b.Fatal(err)
    63  	}
    64  
    65  	defer s.Close()
    66  
    67  	for i := 0; i < n; i++ {
    68  		if _, err := s.Exec(int64(i)); err != nil {
    69  			b.Fatal(err)
    70  		}
    71  	}
    72  	if _, err := db.Exec("commit"); err != nil {
    73  		b.Fatal(err)
    74  	}
    75  
    76  	dst := 0
    77  	b.ReportAllocs()
    78  	b.ResetTimer()
    79  	for i := 0; i < b.N; i++ {
    80  		b.StopTimer()
    81  		r, err := db.Query("select * from t")
    82  		if err != nil {
    83  			b.Fatal(err)
    84  		}
    85  
    86  		b.StartTimer()
    87  		for i := 0; i < n; i++ {
    88  			if !r.Next() {
    89  				b.Fatal(r.Err())
    90  			}
    91  
    92  			err = r.Scan(&dst)
    93  			if err != nil {
    94  				b.Fatal(err)
    95  			}
    96  		}
    97  		b.StopTimer()
    98  		r.Close()
    99  	}
   100  	b.StopTimer()
   101  	if *oRecsPerSec {
   102  		b.SetBytes(1e6 * int64(n))
   103  	}
   104  }
   105  
   106  func BenchmarkReading1(b *testing.B) {
   107  	dir := b.TempDir()
   108  	for _, memory := range inMemory {
   109  		filename := "file::memory:"
   110  		if !memory {
   111  			filename = filepath.Join(dir, "test.db")
   112  		}
   113  		for _, driver := range drivers {
   114  			for i, n := range []int{1e1, 1e2, 1e3, 1e4, 1e5, 1e6} {
   115  				b.Run(makename(memory, driver, i+1), func(b *testing.B) {
   116  					benchmarkRead(b, driver, filename, n)
   117  					if !memory {
   118  						err := os.Remove(filename)
   119  						if err != nil {
   120  							b.Fatal(err)
   121  						}
   122  					}
   123  				})
   124  			}
   125  		}
   126  	}
   127  }
   128  
   129  func benchmarkInsertComparative(b *testing.B, drivername, file string, n int) {
   130  	os.Remove(file)
   131  	db, err := sql.Open(drivername, file)
   132  	if err != nil {
   133  		b.Fatal(err)
   134  	}
   135  
   136  	defer func() {
   137  		db.Close()
   138  	}()
   139  
   140  	if _, err := db.Exec(`
   141  	create table t(i int);
   142  	`); err != nil {
   143  		b.Fatal(err)
   144  	}
   145  
   146  	s, err := db.Prepare("insert into t values(?)")
   147  	if err != nil {
   148  		b.Fatal(err)
   149  	}
   150  
   151  	defer s.Close()
   152  
   153  	b.ReportAllocs()
   154  	b.ResetTimer()
   155  	for i := 0; i < b.N; i++ {
   156  		b.StopTimer()
   157  		if _, err := db.Exec("begin"); err != nil {
   158  			b.Fatal(err)
   159  		}
   160  		if err, _ := db.Exec("delete * from t"); err != nil {
   161  			b.Fatal(err)
   162  		}
   163  
   164  		b.StartTimer()
   165  		for i := 0; i < n; i++ {
   166  			if _, err := s.Exec(int64(i)); err != nil {
   167  				b.Fatal(err)
   168  			}
   169  		}
   170  		if _, err := db.Exec("commit"); err != nil {
   171  			b.Fatal(err)
   172  		}
   173  		b.StopTimer()
   174  	}
   175  	b.StopTimer()
   176  	if *oRecsPerSec {
   177  		b.SetBytes(1e6 * int64(n))
   178  	}
   179  }
   180  
   181  // https://gitlab.com/cznic/sqlite/-/issues/39
   182  func BenchmarkInsertComparative(b *testing.B) {
   183  	dir := b.TempDir()
   184  	for _, memory := range inMemory {
   185  		filename := "file::memory:"
   186  		if !memory {
   187  			filename = filepath.Join(dir, "test.db")
   188  		}
   189  		for _, driver := range drivers {
   190  			for i, n := range []int{1e1, 1e2, 1e3, 1e4, 1e5, 1e6} {
   191  				b.Run(makename(memory, driver, i+1), func(b *testing.B) {
   192  					benchmarkInsertComparative(b, driver, filename, n)
   193  					if !memory {
   194  						err := os.Remove(filename)
   195  						if err != nil {
   196  							b.Fatal(err)
   197  						}
   198  					}
   199  				})
   200  			}
   201  		}
   202  	}
   203  }