/
main.go
124 lines (105 loc) · 3.31 KB
/
main.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
// SPDX-FileCopyrightText: 2020 SAP SE
// SPDX-FileCopyrightText: 2021 SAP SE
// SPDX-FileCopyrightText: 2022 SAP SE
// SPDX-FileCopyrightText: 2023 SAP SE
//
// SPDX-License-Identifier: Apache-2.0
// This example shows a simple interaction with a TDS server using the
// database/sql interface and the pure go driver.
//
// Other examples will use helper functions to ease the setup and
// teardown and to shift attention entirely to their focus.
package main
import (
"database/sql"
"fmt"
"log"
"math"
"github.com/SAP/go-ase"
"github.com/SAP/go-dblib/dsn"
"github.com/SAP/go-dblib/integration"
)
const (
exampleName = "simple"
databaseName = exampleName + "DB"
tableName = databaseName + ".." + exampleName + "Table"
)
func main() {
if err := DoMain(); err != nil {
log.Fatalf("%s failed: %v", exampleName, err)
}
}
func DoMain() error {
// Retrieve connection information from the environment.
// It is also possible to retrieve the information from e.g. a k/v
// storage or from a file.
//
// Assuming the functions `GetUsername()` and `GetPassword()` are
// implemented and read the authentication information from a file:
//
// func main() {
// info, err := ase.NewInfo()
// if err != nil {
// log.Fatal(err)
// }
// info.Username = GetUsername()
// info.Password = GetPassword()
// info.Host = "ase.internal.net"
//
// db, rer := sql.Open("ase", dsn.FormatSimple(info)
// if err != nil {
// log.Fatal(err)
// }
// defer db.Close()
// }
info, err := ase.NewInfoWithEnv()
if err != nil {
return fmt.Errorf("error reading DSN info from env: %w", err)
}
fmt.Println("Opening database")
db, err := sql.Open("ase", dsn.FormatSimple(info))
if err != nil {
return fmt.Errorf("failed to open connection to database: %w", err)
}
defer db.Close()
// This is used to synchronize the examples and integration tests as
// ASE doesn't handle creating multiple databases concurrently well.
integration.DBCreateLock.Lock()
defer integration.DBCreateLock.Unlock()
if _, err = db.Exec("if object_id('simple_tab') is not null drop table simple_tab"); err != nil {
return fmt.Errorf("failed to drop table 'simple_tab': %w", err)
}
fmt.Println("Creating table 'simple_tab'")
if _, err = db.Exec("create table simple_tab (a bigint, b char(30))"); err != nil {
return fmt.Errorf("failed to create table: %w", err)
}
fmt.Printf("Writing a=%d, b='a string' to table\n", math.MaxInt32)
if _, err = db.Exec("insert into simple_tab (a, b) values (?, ?)", math.MaxInt32, "a string"); err != nil {
return fmt.Errorf("failed to insert values: %w", err)
}
fmt.Println("Querying values from table")
rows, err := db.Query("select * from simple_tab")
if err != nil {
return fmt.Errorf("querying failed: %w", err)
}
defer rows.Close()
fmt.Println("Displaying results of query")
colNames, err := rows.Columns()
if err != nil {
return fmt.Errorf("failed to retrieve column names: %w", err)
}
fmt.Printf("| %-10s | %-30s |\n", colNames[0], colNames[1])
format := "| %-10d | %-30s |\n"
var a int
var b string
for rows.Next() {
if err = rows.Scan(&a, &b); err != nil {
return fmt.Errorf("failed to scan row: %w", err)
}
fmt.Printf(format, a, b)
}
if err := rows.Err(); err != nil {
return fmt.Errorf("error reading rows: %w", err)
}
return nil
}