github.com/ydb-platform/ydb-go-sdk/v3@v3.57.0/tests/integration/database_sql_get_tables_test.go (about)

     1  //go:build integration
     2  // +build integration
     3  
     4  package integration
     5  
     6  import (
     7  	"context"
     8  	"database/sql"
     9  	"errors"
    10  	"path"
    11  	"sort"
    12  	"testing"
    13  
    14  	"github.com/stretchr/testify/require"
    15  
    16  	"github.com/ydb-platform/ydb-go-sdk/v3"
    17  	"github.com/ydb-platform/ydb-go-sdk/v3/retry"
    18  	"github.com/ydb-platform/ydb-go-sdk/v3/sugar"
    19  )
    20  
    21  func TestDatabaseSqlGetTables(t *testing.T) {
    22  	var (
    23  		scope  = newScope(t)
    24  		db     = scope.SQLDriverWithFolder()
    25  		folder = t.Name()
    26  	)
    27  
    28  	defer func() {
    29  		_ = db.Close()
    30  	}()
    31  
    32  	t.Run("prepare-sub-folder", func(t *testing.T) {
    33  		cc, err := ydb.Unwrap(db)
    34  		require.NoError(t, err)
    35  
    36  		err = sugar.MakeRecursive(scope.Ctx, cc, path.Join(folder, "subdir"))
    37  		require.NoError(t, err)
    38  	})
    39  
    40  	t.Run("create-tables", func(t *testing.T) {
    41  		err := retry.Do(scope.Ctx, db, func(ctx context.Context, cc *sql.Conn) (err error) {
    42  			_, err = cc.ExecContext(
    43  				ydb.WithQueryMode(ctx, ydb.SchemeQueryMode),
    44  				`CREATE TABLE episodes (
    45  				series_id Uint64,
    46  				season_id Uint64,
    47  				episode_id Uint64,
    48  				title UTF8,
    49  				air_date Date,
    50  				views Uint64,
    51  				PRIMARY KEY (
    52  					series_id,
    53  					season_id,
    54  					episode_id
    55  				)
    56  			)`,
    57  			)
    58  
    59  			if err != nil {
    60  				return err
    61  			}
    62  
    63  			_, err = cc.ExecContext(
    64  				ydb.WithQueryMode(ctx, ydb.SchemeQueryMode),
    65  				`
    66  			CREATE TABLE series (
    67  				series_id Uint64,
    68  				title UTF8,
    69  				series_info UTF8,
    70  				release_date Date,
    71  				comment UTF8,
    72  				PRIMARY KEY (
    73  					series_id
    74  				)
    75  			);`,
    76  			)
    77  
    78  			if err != nil {
    79  				return err
    80  			}
    81  
    82  			_, err = cc.ExecContext(
    83  				ydb.WithQueryMode(ctx, ydb.SchemeQueryMode),
    84  				`CREATE TABLE `+"`./subdir/seasons`"+` (
    85  				series_id Uint64,
    86  				season_id Uint64,
    87  				title UTF8,
    88  				first_aired Date,
    89  				last_aired Date,
    90  				PRIMARY KEY (
    91  					series_id,
    92  					season_id
    93  				)
    94  			)`,
    95  			)
    96  
    97  			if err != nil {
    98  				return err
    99  			}
   100  
   101  			return nil
   102  		}, retry.WithIdempotent(true))
   103  
   104  		require.NoError(t, err)
   105  	})
   106  
   107  	t.Run("get-tables-at-current-folder", func(t *testing.T) {
   108  		err := retry.Do(scope.Ctx, db, func(ctx context.Context, cc *sql.Conn) (err error) {
   109  			tables := make([]string, 0)
   110  			err = cc.Raw(func(drvConn interface{}) (err error) {
   111  				q, ok := drvConn.(interface {
   112  					GetTables(ctx context.Context, folder string, recursive bool, excludeSysDirs bool) ([]string, error)
   113  				})
   114  
   115  				if !ok {
   116  					return errors.New("drvConn does not implement extended API")
   117  				}
   118  
   119  				tables, err = q.GetTables(ctx, ".", false, true)
   120  				return err
   121  			})
   122  
   123  			if err != nil {
   124  				return err
   125  			}
   126  
   127  			require.Equal(t,
   128  				[]string{"episodes", "series"},
   129  				tables)
   130  			return nil
   131  		}, retry.WithIdempotent(true))
   132  
   133  		require.NoError(t, err)
   134  	})
   135  
   136  	t.Run("get-tables-at-relative-sub-folder", func(t *testing.T) {
   137  		err := retry.Do(scope.Ctx, db, func(ctx context.Context, cc *sql.Conn) (err error) {
   138  			tables := make([]string, 0)
   139  			err = cc.Raw(func(drvConn interface{}) (err error) {
   140  				q, ok := drvConn.(interface {
   141  					GetTables(ctx context.Context, folder string, recursive bool, excludeSysDirs bool) ([]string, error)
   142  				})
   143  
   144  				if !ok {
   145  					return errors.New("drvConn does not implement extended API")
   146  				}
   147  
   148  				tables, err = q.GetTables(ctx, "./subdir", false, true)
   149  				return err
   150  			})
   151  
   152  			if err != nil {
   153  				return err
   154  			}
   155  
   156  			require.Equal(t,
   157  				[]string{"seasons"},
   158  				tables)
   159  			return nil
   160  		}, retry.WithIdempotent(true))
   161  
   162  		require.NoError(t, err)
   163  	})
   164  
   165  	t.Run("get-tables-at-path-represent-a-table", func(t *testing.T) {
   166  		err := retry.Do(scope.Ctx, db, func(ctx context.Context, cc *sql.Conn) (err error) {
   167  			tables := make([]string, 0)
   168  			err = cc.Raw(func(drvConn interface{}) (err error) {
   169  				q, ok := drvConn.(interface {
   170  					GetTables(ctx context.Context, folder string, recursive bool, excludeSysDirs bool) ([]string, error)
   171  				})
   172  
   173  				if !ok {
   174  					return errors.New("drvConn does not implement extended API")
   175  				}
   176  
   177  				tables, err = q.GetTables(ctx, "./subdir/seasons", false, true)
   178  				return err
   179  			})
   180  
   181  			if err != nil {
   182  				return err
   183  			}
   184  
   185  			require.Equal(t,
   186  				[]string{"seasons"},
   187  				tables)
   188  			return nil
   189  		}, retry.WithIdempotent(true))
   190  
   191  		require.NoError(t, err)
   192  	})
   193  }
   194  
   195  func TestDatabaseSqlGetTablesRecursive(t *testing.T) {
   196  	var (
   197  		scope  = newScope(t)
   198  		db     = scope.SQLDriverWithFolder()
   199  		folder = t.Name()
   200  	)
   201  
   202  	defer func() {
   203  		_ = db.Close()
   204  	}()
   205  
   206  	t.Run("prepare-sub-folder", func(t *testing.T) {
   207  		cc, err := ydb.Unwrap(db)
   208  		require.NoError(t, err)
   209  
   210  		err = sugar.MakeRecursive(scope.Ctx, cc, path.Join(folder, "subdir"))
   211  		require.NoError(t, err)
   212  	})
   213  
   214  	t.Run("create-tables", func(t *testing.T) {
   215  		err := retry.Do(scope.Ctx, db, func(ctx context.Context, cc *sql.Conn) (err error) {
   216  			_, err = cc.ExecContext(
   217  				ydb.WithQueryMode(ctx, ydb.SchemeQueryMode),
   218  				`CREATE TABLE episodes (
   219  				series_id Uint64,
   220  				season_id Uint64,
   221  				episode_id Uint64,
   222  				title UTF8,
   223  				air_date Date,
   224  				views Uint64,
   225  				PRIMARY KEY (
   226  					series_id,
   227  					season_id,
   228  					episode_id
   229  				)
   230  			)`,
   231  			)
   232  
   233  			if err != nil {
   234  				return err
   235  			}
   236  
   237  			_, err = cc.ExecContext(
   238  				ydb.WithQueryMode(ctx, ydb.SchemeQueryMode),
   239  				`
   240  			CREATE TABLE series (
   241  				series_id Uint64,
   242  				title UTF8,
   243  				series_info UTF8,
   244  				release_date Date,
   245  				comment UTF8,
   246  				PRIMARY KEY (
   247  					series_id
   248  				)
   249  			);`,
   250  			)
   251  
   252  			if err != nil {
   253  				return err
   254  			}
   255  
   256  			_, err = cc.ExecContext(
   257  				ydb.WithQueryMode(ctx, ydb.SchemeQueryMode),
   258  				`CREATE TABLE `+"`./subdir/seasons`"+` (
   259  				series_id Uint64,
   260  				season_id Uint64,
   261  				title UTF8,
   262  				first_aired Date,
   263  				last_aired Date,
   264  				PRIMARY KEY (
   265  					series_id,
   266  					season_id
   267  				)
   268  			)`,
   269  			)
   270  
   271  			if err != nil {
   272  				return err
   273  			}
   274  
   275  			return nil
   276  		}, retry.WithIdempotent(true))
   277  
   278  		require.NoError(t, err)
   279  	})
   280  
   281  	t.Run("get-all-tables-at-current-folder", func(t *testing.T) {
   282  		err := retry.Do(scope.Ctx, db, func(ctx context.Context, cc *sql.Conn) (err error) {
   283  			tables := make([]string, 0)
   284  			err = cc.Raw(func(drvConn interface{}) (err error) {
   285  				q, ok := drvConn.(interface {
   286  					GetTables(ctx context.Context, folder string, recursive bool, excludeSysDirs bool) ([]string, error)
   287  				})
   288  
   289  				if !ok {
   290  					return errors.New("drvConn does not implement extended API")
   291  				}
   292  
   293  				tables, err = q.GetTables(ctx, ".", true, true)
   294  				return err
   295  			})
   296  
   297  			if err != nil {
   298  				return err
   299  			}
   300  
   301  			sort.Strings(tables)
   302  
   303  			require.Equal(t,
   304  				[]string{"episodes", "series", "subdir/seasons"},
   305  				tables)
   306  			return nil
   307  		}, retry.WithIdempotent(true))
   308  
   309  		require.NoError(t, err)
   310  	})
   311  
   312  	t.Run("get-all-tables-at-relative-sub-folder", func(t *testing.T) {
   313  		err := retry.Do(scope.Ctx, db, func(ctx context.Context, cc *sql.Conn) (err error) {
   314  			tables := make([]string, 0)
   315  			err = cc.Raw(func(drvConn interface{}) (err error) {
   316  				q, ok := drvConn.(interface {
   317  					GetTables(ctx context.Context, folder string, recursive bool, excludeSysDirs bool) ([]string, error)
   318  				})
   319  
   320  				if !ok {
   321  					return errors.New("drvConn does not implement extended API")
   322  				}
   323  
   324  				tables, err = q.GetTables(ctx, "./subdir", true, true)
   325  				return err
   326  			})
   327  
   328  			if err != nil {
   329  				return err
   330  			}
   331  
   332  			sort.Strings(tables)
   333  
   334  			require.Equal(t,
   335  				[]string{"seasons"},
   336  				tables)
   337  			return nil
   338  		}, retry.WithIdempotent(true))
   339  
   340  		require.NoError(t, err)
   341  	})
   342  
   343  	t.Run("get-all-tables-at-path-represent-a-table", func(t *testing.T) {
   344  		err := retry.Do(scope.Ctx, db, func(ctx context.Context, cc *sql.Conn) (err error) {
   345  			tables := make([]string, 0)
   346  			err = cc.Raw(func(drvConn interface{}) (err error) {
   347  				q, ok := drvConn.(interface {
   348  					GetTables(ctx context.Context, folder string, recursive bool, excludeSysDirs bool) ([]string, error)
   349  				})
   350  
   351  				if !ok {
   352  					return errors.New("drvConn does not implement extended API")
   353  				}
   354  
   355  				tables, err = q.GetTables(ctx, "./subdir/seasons", true, true)
   356  				return err
   357  			})
   358  
   359  			if err != nil {
   360  				return err
   361  			}
   362  
   363  			sort.Strings(tables)
   364  
   365  			require.Equal(t,
   366  				[]string{"seasons"},
   367  				tables)
   368  			return nil
   369  		}, retry.WithIdempotent(true))
   370  
   371  		require.NoError(t, err)
   372  	})
   373  }