编写一个可以使用 2 个数据库的应用程序?

我正在尝试用 Go 编写一个应用程序,能够根据配置连接到 oracle 和 MySQL。我现在遇到的问题是当我使用准备好的语句时。例如,考虑下面的查询

Select * from data_table where id = 1

下面给出MySQL和oracle中对应的prepared语句

MySQL -> Select * from data_table where id = ?
ORACLE -> Select * from data_table where id = :val1

如果是这样,我维护 2 组查询并根据配置选择查询。有一个更好的方法吗?

我想避免保留两组查询的麻烦


胡说叔叔
浏览 72回答 1
1回答

小怪兽爱吃肉

这很大程度上是通过使用接口来实现的。假设您创建一个 Web 应用程序并且想要显示用户。首先,您需要定义一个接口,例如type Creator interface{  Create(u User)(User,error)}type Reader interface{  Read(k PrimaryKey)(User, error)  ListAll()([]User,error)  ListPaginated(page, offset int)([]User,error)}type Updater interface{  Update(u User)(User, error)  UpdateByKey(k PrimaryKey, u User)(User, error)  UpdateMany(...User)error}type Deleter interface{  Delete(u User)error  DeleteMany(u ...User)error  DeleteByKey(keys ...PrimaryKey)error}type CRUD interface {  Creator  Reader  Updater  Deleter}接下来,为您想要支持的每种数据库类型实现 CRUD 接口。现在,您可以创建一个处理程序:// ListHandler uses an interface instead of a concrete type to// retrieve the data from the databases.// Not only does this approach make it possible to provide different// implementations, but it makes unit testing way easier.//// "Thou Shalt Write Tests"func ListHandler(rdr Reader) http.Handler {    return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {        // Pagination ommited for brevity        // Note that the handler is agnostic of the underlying implementation.        u, err := rdr.ListAll()        if err != nil {            log.Printf("ListHandler: error retrieving user list: %s", err)            // Do not do this in production! It might give an attacker information            // Use a static error message instead!            http.Error(w, err.Error(), http.StatusInternalServerError)            return        }        if err := json.NewEncoder(w).Encode(u); err != nil {            log.Printf("ListHandler: error encoding user list to JSON: %s", err)            // See above            http.Error(w, err.Error(), http.StatusInternalServerError)        }    })}并设置如下:func main() {    // Get your config    // Then simply use an implementation of CRUD    var dbConn CRUD    switch cfg.DbType {    case "myql":        // returns your implementation of CRUD using MySQL        dbConn = createMySQLConnector(cfg)    case "oracle":        // returns your implementation of CRUD using Oracle        dbConn = createOracleConnector(cfg)    }    http.Handle("/users/", ListHandler(dbConn))    log.Fatal(http.ListenAndServe("0.0.0.0:8080", nil))}哈
打开App,查看更多内容
随时随地看视频慕课网APP