libgo: update to final Go 1.8 release
[official-gcc.git] / libgo / go / database / sql / ctxutil.go
blobbd652b54625337b211fe1b9466239acfa104b190
1 // Copyright 2016 The Go 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.
5 package sql
7 import (
8 "context"
9 "database/sql/driver"
10 "errors"
13 func ctxDriverPrepare(ctx context.Context, ci driver.Conn, query string) (driver.Stmt, error) {
14 if ciCtx, is := ci.(driver.ConnPrepareContext); is {
15 return ciCtx.PrepareContext(ctx, query)
17 si, err := ci.Prepare(query)
18 if err == nil {
19 select {
20 default:
21 case <-ctx.Done():
22 si.Close()
23 return nil, ctx.Err()
26 return si, err
29 func ctxDriverExec(ctx context.Context, execer driver.Execer, query string, nvdargs []driver.NamedValue) (driver.Result, error) {
30 if execerCtx, is := execer.(driver.ExecerContext); is {
31 return execerCtx.ExecContext(ctx, query, nvdargs)
33 dargs, err := namedValueToValue(nvdargs)
34 if err != nil {
35 return nil, err
38 select {
39 default:
40 case <-ctx.Done():
41 return nil, ctx.Err()
43 return execer.Exec(query, dargs)
46 func ctxDriverQuery(ctx context.Context, queryer driver.Queryer, query string, nvdargs []driver.NamedValue) (driver.Rows, error) {
47 if queryerCtx, is := queryer.(driver.QueryerContext); is {
48 ret, err := queryerCtx.QueryContext(ctx, query, nvdargs)
49 return ret, err
51 dargs, err := namedValueToValue(nvdargs)
52 if err != nil {
53 return nil, err
56 select {
57 default:
58 case <-ctx.Done():
59 return nil, ctx.Err()
61 return queryer.Query(query, dargs)
64 func ctxDriverStmtExec(ctx context.Context, si driver.Stmt, nvdargs []driver.NamedValue) (driver.Result, error) {
65 if siCtx, is := si.(driver.StmtExecContext); is {
66 return siCtx.ExecContext(ctx, nvdargs)
68 dargs, err := namedValueToValue(nvdargs)
69 if err != nil {
70 return nil, err
73 select {
74 default:
75 case <-ctx.Done():
76 return nil, ctx.Err()
78 return si.Exec(dargs)
81 func ctxDriverStmtQuery(ctx context.Context, si driver.Stmt, nvdargs []driver.NamedValue) (driver.Rows, error) {
82 if siCtx, is := si.(driver.StmtQueryContext); is {
83 return siCtx.QueryContext(ctx, nvdargs)
85 dargs, err := namedValueToValue(nvdargs)
86 if err != nil {
87 return nil, err
90 select {
91 default:
92 case <-ctx.Done():
93 return nil, ctx.Err()
95 return si.Query(dargs)
98 var errLevelNotSupported = errors.New("sql: selected isolation level is not supported")
100 func ctxDriverBegin(ctx context.Context, opts *TxOptions, ci driver.Conn) (driver.Tx, error) {
101 if ciCtx, is := ci.(driver.ConnBeginTx); is {
102 dopts := driver.TxOptions{}
103 if opts != nil {
104 dopts.Isolation = driver.IsolationLevel(opts.Isolation)
105 dopts.ReadOnly = opts.ReadOnly
107 return ciCtx.BeginTx(ctx, dopts)
110 if ctx.Done() == context.Background().Done() {
111 return ci.Begin()
114 if opts != nil {
115 // Check the transaction level. If the transaction level is non-default
116 // then return an error here as the BeginTx driver value is not supported.
117 if opts.Isolation != LevelDefault {
118 return nil, errors.New("sql: driver does not support non-default isolation level")
121 // If a read-only transaction is requested return an error as the
122 // BeginTx driver value is not supported.
123 if opts.ReadOnly {
124 return nil, errors.New("sql: driver does not support read-only transactions")
128 txi, err := ci.Begin()
129 if err == nil {
130 select {
131 default:
132 case <-ctx.Done():
133 txi.Rollback()
134 return nil, ctx.Err()
137 return txi, err
140 func namedValueToValue(named []driver.NamedValue) ([]driver.Value, error) {
141 dargs := make([]driver.Value, len(named))
142 for n, param := range named {
143 if len(param.Name) > 0 {
144 return nil, errors.New("sql: driver does not support the use of Named Parameters")
146 dargs[n] = param.Value
148 return dargs, nil