github.com/willyham/dosa@v2.3.1-0.20171024181418-1e446d37ee71+incompatible/schema/uql/uql_test.go (about)

     1  // Copyright (c) 2017 Uber Technologies, Inc.
     2  //
     3  // Permission is hereby granted, free of charge, to any person obtaining a copy
     4  // of this software and associated documentation files (the "Software"), to deal
     5  // in the Software without restriction, including without limitation the rights
     6  // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
     7  // copies of the Software, and to permit persons to whom the Software is
     8  // furnished to do so, subject to the following conditions:
     9  //
    10  // The above copyright notice and this permission notice shall be included in
    11  // all copies or substantial portions of the Software.
    12  //
    13  // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
    14  // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
    15  // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
    16  // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
    17  // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
    18  // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
    19  // THE SOFTWARE.
    20  
    21  package uql_test
    22  
    23  import (
    24  	"fmt"
    25  	"strings"
    26  	"testing"
    27  
    28  	"github.com/stretchr/testify/assert"
    29  	"github.com/uber-go/dosa"
    30  	"github.com/uber-go/dosa/schema/uql"
    31  )
    32  
    33  func TestToUql(t *testing.T) {
    34  	allColumnTypes := []*dosa.ColumnDefinition{
    35  		{
    36  			Name: "foo",
    37  			Type: dosa.Int32,
    38  		},
    39  		{
    40  			Name: "bar",
    41  			Type: dosa.TUUID,
    42  		},
    43  		{
    44  			Name: "qux",
    45  			Type: dosa.Blob,
    46  		},
    47  		{
    48  			Name: "fox",
    49  			Type: dosa.String,
    50  		},
    51  		{
    52  			Name: "dog",
    53  			Type: dosa.Int64,
    54  		},
    55  		{
    56  			Name: "cat",
    57  			Type: dosa.Timestamp,
    58  		},
    59  		{
    60  			Name: "tap",
    61  			Type: dosa.Double,
    62  		},
    63  		{
    64  			Name: "pop",
    65  			Type: dosa.Bool,
    66  		},
    67  	}
    68  
    69  	singleKeyEntity := &dosa.EntityDefinition{
    70  		Name: "singlekey",
    71  		Key: &dosa.PrimaryKey{
    72  			PartitionKeys: []string{"foo"},
    73  		},
    74  		Columns: allColumnTypes,
    75  	}
    76  
    77  	compoundKeyEntity := &dosa.EntityDefinition{
    78  		Name: "compoundkey",
    79  		Key: &dosa.PrimaryKey{
    80  			PartitionKeys: []string{"foo"},
    81  			ClusteringKeys: []*dosa.ClusteringKey{
    82  				{"qux", true},
    83  			},
    84  		},
    85  		Columns: allColumnTypes,
    86  	}
    87  
    88  	twoParitionKeyEntity := &dosa.EntityDefinition{
    89  		Name: "twopartitionkey",
    90  		Key: &dosa.PrimaryKey{
    91  			PartitionKeys: []string{"foo", "bar"},
    92  		},
    93  		Columns: allColumnTypes,
    94  	}
    95  
    96  	compositeKeyEntity := &dosa.EntityDefinition{
    97  		Name: "compositekey",
    98  		Key: &dosa.PrimaryKey{
    99  			PartitionKeys: []string{"foo", "bar"},
   100  			ClusteringKeys: []*dosa.ClusteringKey{
   101  				{"qux", true},
   102  				{"fox", false},
   103  			},
   104  		},
   105  		Columns: allColumnTypes,
   106  	}
   107  
   108  	invalidEntity := &dosa.EntityDefinition{
   109  		Name:    "twopartitionkey",
   110  		Key:     nil,
   111  		Columns: allColumnTypes,
   112  	}
   113  
   114  	expectedTmpl := `CREATE TABLE %s (
   115  	  foo int32;
   116  	  bar uuid;
   117  	  qux blob;
   118  	  fox string;
   119  	  dog int64;
   120  	  cat timestamp;
   121  	  tap double;
   122  	  pop bool;
   123  	) PRIMARY KEY %s;
   124  	`
   125  
   126  	dataProvider := []struct {
   127  		e         *dosa.EntityDefinition
   128  		expected  string
   129  		shouldErr bool
   130  	}{
   131  		{
   132  			e:        singleKeyEntity,
   133  			expected: fmt.Sprintf(expectedTmpl, singleKeyEntity.Name, "(foo)"),
   134  		},
   135  		{
   136  			e:        compoundKeyEntity,
   137  			expected: fmt.Sprintf(expectedTmpl, compoundKeyEntity.Name, "(foo, qux DESC)"),
   138  		},
   139  		{
   140  			e:        twoParitionKeyEntity,
   141  			expected: fmt.Sprintf(expectedTmpl, twoParitionKeyEntity.Name, "((foo, bar))"),
   142  		},
   143  		{
   144  			e:        compositeKeyEntity,
   145  			expected: fmt.Sprintf(expectedTmpl, compositeKeyEntity.Name, "((foo, bar), qux DESC, fox ASC)"),
   146  		},
   147  		{
   148  			e:         nil,
   149  			expected:  "",
   150  			shouldErr: true,
   151  		},
   152  		{
   153  			e:         invalidEntity,
   154  			expected:  "",
   155  			shouldErr: true,
   156  		},
   157  	}
   158  
   159  	for _, testdata := range dataProvider {
   160  		actual, err := uql.ToUQL(testdata.e)
   161  		if testdata.shouldErr {
   162  			assert.Error(t, err)
   163  			continue
   164  		}
   165  
   166  		caseName := testdata.e.Name
   167  		// compare line by line ignore leading and trailing whitespaces
   168  		actualLines := strings.Split(actual, "\n")
   169  		expectedLines := strings.Split(testdata.expected, "\n")
   170  		assert.Equal(t, len(expectedLines), len(actualLines), caseName, "number of lines does not match expected")
   171  		for i, actualLine := range actualLines {
   172  			assert.Equal(t, strings.TrimSpace(expectedLines[i]), strings.TrimSpace(actualLine), caseName,
   173  				fmt.Sprintf("output line %d does not match expected", i))
   174  		}
   175  	}
   176  }