C++ client library for PostgreSQL

Overview

Welcome to taoPQ

Windows CI macOS CI Linux CI
clang-analyze clang-tidy Sanitizer Code Coverage

taoPQ is a lightweight C++ client library for accessing a PostgreSQL➚ database. It has no dependencies beyond libpq, the C application programmer's interface to PostgreSQL.

Introduction

The library provides support for database connections, transactions, nested transactions, prepared statements, large objects, connection pools, high-speed bulk data transfer, and more. An extensible traits mechanism is used to convert C++ types into SQL statement parameters, and conversely to convert query results into arbitrary C++ types. The following example shows the basic look and feel of the library.

#include <iostream>
#include <tao/pq.hpp>

int main()
{
   // open a connection to the database
   const auto conn = tao::pq::connection::create( "dbname=template1" );

   // execute statements
   conn->execute( "DROP TABLE IF EXISTS users" );
   conn->execute( "CREATE TABLE users ( name TEXT PRIMARY KEY, age INTEGER NOT NULL )" );

   // prepare statements
   conn->prepare( "insert_user", "INSERT INTO users ( name, age ) VALUES ( $1, $2 )" );

   {
      // begin transaction
      const auto tr = conn->transaction();

      // execute previously prepared statements
      tr->execute( "insert_user", "Daniel", 42 );
      tr->execute( "insert_user", "Tom", 41 );
      tr->execute( "insert_user", "Jerry", 29 );

      // commit transaction
      tr->commit();
   }

   // query data
   const auto users = conn->execute( "SELECT name, age FROM users WHERE age >= $1", 40 );

   // iterate and convert results
   for( const auto& row : users ) {
      std::cout << row[ "name" ].as< std::string >() << " is "
                << row[ "age" ].as< unsigned >() << " years old.\n";
   }
}

Documentation

Contact

Join us on Discord

For questions and suggestions regarding taoPQ, success or failure stories, and any other kind of feedback, please feel free to join our Discord➚ server, open a discussion, an issue or a pull request on GitHub or contact the authors at taocpp(at)icemx.net.

The Art of C++

taoPQ is part of The Art of C++.

colinh d-frey uilianries

License

Open Source Initiative

Copyright (c) 2016-2021 Daniel Frey and Dr. Colin Hirsch

taoPQ is certified Open Source➚ software. It is licensed➚ under the terms of the Boost Software License, Version 1.0➚ reproduced here.

Boost Software License - Version 1.0 - August 17th, 2003

Permission is hereby granted, free of charge, to any person or organization obtaining a copy of the software and accompanying documentation covered by this license (the "Software") to use, reproduce, display, distribute, execute, and transmit the Software, and to prepare derivative works of the Software, and to permit third-parties to whom the Software is furnished to do so, all subject to the following:

The copyright notices in the Software and this entire statement, including the above license grant, this restriction and the following disclaimer, must be included in all copies of the Software, in whole or in part, and all derivative works of the Software, unless such copies or derivative works are solely in the form of machine-executable object code generated by a source language processor.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, TITLE AND NON-INFRINGEMENT. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR ANYONE DISTRIBUTING THE SOFTWARE BE LIABLE FOR ANY DAMAGES OR OTHER LIABILITY, WHETHER IN CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

Issues
  • Support for binary storage of numerical values?

    Support for binary storage of numerical values?

    I'm under the impression that taopq does currently not support binary storage of numerical values, is that correct? This less commonly known mode of libpq allows to store and retrieve numerical values directly as a series of bytes (albeit in network storage order). So for example, an int2 can be stored as the two bytes (low byte, high byte) of the short value. The main benefits are:

    • a higher numerical precision due to the lack of limited string representation of floating point values,
    • faster storage due to the lack of string conversion, and
    • lower storage and bandwidth requirement due to the lack of string representation.

    Could this be a possible extension for taopq?

    enhancement 
    opened by emmenlau 21
  • Allow compilation with `-fno-rtti`

    Allow compilation with `-fno-rtti`

    Using typeid doesn't seem to work even if the result can (and is) evaluated at compile-time. Specifically, typeid(int) or similar results in a compilation error.

    Since this data is only used to make better error messages, and therefore is not crucial, replace the type string with "(no rtti)" when RTTI is disabled.

    enhancement 
    opened by mattfbacon 15
  • Batch Insert values

    Batch Insert values

    Is it possible to make a statement that will insert N values into a table?

    I would like to be able to do something like

    https://github.com/taocpp/taopq/blob/e1e5cc016b8f7f1bb0d4e61f8f79a6bc448e5cad/src/test/pq/traits.cpp#L56

    but with multiple values at once?

    For two rows the sql statement would look like

    INSERT INTO tao_parameter_test VALUES 
                                   ( $1, $2, $3, $4 ),
                                   ( $5, $6, $7, $8 );
    

    I know I can type it manually but for performance reasonse i would like to insert ~500 values at once which would be a lot of typing :)

    Thanks for putting up the library. I find it very easy to use.

    best Søren

    enhancement question 
    opened by skaae 15
  • Building with Visual Studio?

    Building with Visual Studio?

    Dear developers, I very much cherish the moderns C++ postgreSQL interface. However it seems currently a bit hard to user with MSVC. Are you interested in supporting this platform? From my experience it can be slightly tedious work, but often it improves the overall code quality. If this is relevant for you I could try to make an Azure DevOps CI setup that provides continuous builds for your Github repository?

    question 
    opened by emmenlau 12
  • CMake - ExternalProject usage as an example

    CMake - ExternalProject usage as an example

    Hi,

    I like your library, but it's problematic to get it installed. I am playing a lot with getting cmakes ExternalProject_Add to download it,compile it and link/include it.

    DO you have any such setup? Could you share it as an example of how to "install" this?

    question 
    opened by koniarik 11
  • can't get optional string

    can't get optional string

    auto res = db->execute("...").at(0);
    auto opt = res.optional<std::string>(3);
    
    /usr/local/include/tao/pq/result_traits.hpp:23:7: error: static_assert failed due to requirement 'internal::dependent_false<std::__1::optional<std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char>>>>' "data type T not registered as taopq result type"
          static_assert( internal::dependent_false< T >, "data type T not registered as taopq result type" );
          ^              ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    /usr/local/include/tao/pq/result_traits.hpp:32:66: note: in instantiation of template class 'tao::pq::result_traits<std::__1::optional<std::__1::basic_string<char>>>' requested here
       inline constexpr std::size_t result_traits_size< T, decltype( result_traits< T >::size ) > = result_traits< T >::size;
                                                                     ^
    /usr/local/include/tao/pq/row.hpp:206:24: note: during template argument deduction for variable template partial specialization 'result_traits_size<T, decltype(result_traits<T>::size)>' [with T = std::__1::optional<std::__1::basic_string<char>>]
             if constexpr( result_traits_size< T > == 0 ) {
                           ^
    /usr/local/include/tao/pq/row.hpp:229:17: note: in instantiation of function template specialization 'tao::pq::row::get<std::__1::optional<std::__1::basic_string<char>>>' requested here
             return get< std::optional< T > >( column );
                    ^
    /usr/local/include/tao/pq/row.hpp:219:40: error: no member named 'from' in 'tao::pq::result_traits<std::__1::optional<std::__1::basic_string<char>>>'
                return result_traits< T >::from( get( column ) );
                                           ^
    /usr/local/include/tao/pq/row.hpp:229:17: note: in instantiation of function template specialization 'tao::pq::row::get<std::__1::optional<std::__1::basic_string<char>>>' requested here
             return get< std::optional< T > >( column );
    
    bug 
    opened by own2pwn 7
  • Better ways to detect constraint violations, etc

    Better ways to detect constraint violations, etc

    Currently you just get a runtime error. Compare this to the exceptions provided by libpqxx: https://libpqxx.readthedocs.io/en/7.6.0/a00247.html.

    I will try to do this myself, but I don't know much about PostgreSQL so it may be difficult.

    opened by mattfbacon 6
  • fatal error: unresolved external symbol during connection create

    fatal error: unresolved external symbol during connection create

    I am new to c++ recently downloaded taopq for database connection to an existing cpp code I am using windows and vs2019 so, I have built taopq using cmakelist in vs2019 then included the tao/pq.hpp in my code from the introduction part of github page (https://github.com/taocpp/taopq), I tried to make a connection in my code const auto conn = tao::pq::connection::create("host=, port=, dbname=, user:"); whenever I try to build this, get the following error error LNK2001: unresolved external symbol "public: static class std::shared_ptr __cdecl tao::pq::connection::create(class std::basic_string<char,struct std::char_traits,class std::allocator > const &)" ([email protected]@[email protected]@@[email protected]@[email protected]@@@[email protected]@[email protected][email protected]@[email protected]@[email protected]@[email protected]@[email protected]@Z) 1>D:\Lahari\work\EQ\EQ C++ db\x64\Release\EQ.exe : fatal error LNK1120: 1 unresolved externals 1>Done building project "EQ.vcxproj" -- FAILED. ========== Rebuild All: 0 succeeded, 1 failed, 0 skipped ========== any help??

    opened by LSG8 5
  • Specializing Parameter traits

    Specializing Parameter traits

    Hi, Im trying to specialize paramter_traits for an absl::CivilDay type because I want to try out the new struct to row magi :)

    So far i more or less copied the string specialization an specialized it for absl::CivilDay

    template<>
       struct tao::pq::parameter_traits< absl::CivilDay >
          : parameter_traits< std::string_view >
       {
           explicit parameter_traits( const absl::CivilDay v ) noexcept
             : parameter_traits<std::string_view>( absl::FormatCivilTime(v) ){}
          
    };
    
    

    FormatCivilTime will return a string. I think this works if the postgres column type is TEXT. My problem is that I'm using a DATE column type and get an error:

    C++ exception with description "ERROR:  column "local_date" is of type date but expression is of type bytea
    LINE 1: INSERT INTO settings VALUES ($1, $2, $3, $4, $5, $6, $7, $8,...
    

    I tried with all the types defined in oid.hpp but none of them work. Do i need to find the oid for DATE type?

    question 
    opened by skaae 5
  • error: ‘null’ is not a member of ‘tao::pq::result_traits<int>’

    error: ‘null’ is not a member of ‘tao::pq::result_traits

    I am getting these errors when I build! I have done a fresh clone. -- Thanks Kevin!

    include/tao/pq/row.hpp: In instantiation of ‘T tao::pq::row::get(std::size_t) const [with T = int; std::size_t = long unsigned int]’: include/tao/pq/row.hpp:299:40: required from ‘T tao::pq::field::as() const [with T = int]’ src/test/pq/result.cpp:156:10: required from here include/tao/pq/row.hpp:224:50: error: ‘null’ is not a member of ‘tao::pq::result_traits’ return result_traits< T >::null();

    include/tao/pq/row.hpp:224:50: required from ‘T tao::pq::row::get(std::size_t) const [with T = std::tuple; std::size_t = long unsigned int]’ include/tao/pq/row.hpp:247:29: required from ‘T tao::pq::row::as() const [with T = std::tuple]’ include/tao/pq/result.hpp:242:40: required from ‘T tao::pq::result::as() const [with T = std::tuple]’ include/tao/pq/result.hpp:263:43: required from ‘auto tao::pq::result::tuple() const [with Ts = {int}]’ src/test/pq/result.cpp:52:4: required from here include/tao/pq/result_traits_tuple.hpp:24:55: error: ‘null’ is not a member of ‘tao::pq::result_traits’ return std::tuple< T >( result_traits< T >::null() );

    opened by kevin143carr 5
  • Building without Postgres installed?

    Building without Postgres installed?

    Hi,

    Pardon my noobness, I'm trying to write a C++ postgres pipeline using taopq (the Python one is way too slow).

    I saw that PostgreSQL itself is a dependency in CMakeLists.txt. However, it seems that libpq itself is much smaller - https://github.com/postgres/postgres/tree/master/src/backend/libpq

    I built it by the instructions here, to receive a lipq.so.5.12

    I also saw in the makefile a line that includes pg_config. Does this mean I still need postgres installed on the machine on which I'm using taopq? Is it somehow possible to avoid it, if I already have libpq.so?

    Thanks, Eli

    opened by EliYk 5
  • Stable releases?

    Stable releases?

    Thank you for your work on this project!

    It would be very helpful for us if you had releases, release branches, or some kind of versioning so we aren't all pulling directly from main which right now looks like the active development branch.

    https://semver.org/

    enhancement 
    opened by gamedev8 1
Owner
The Art of C++
A collection of high-quality C++ libraries
The Art of C++
The official C++ client API for PostgreSQL.

libpqxx Welcome to libpqxx, the C++ API to the PostgreSQL database management system. Home page: http://pqxx.org/development/libpqxx/ Find libpqxx on

Jeroen Vermeulen 643 Jun 25, 2022
The PostgreSQL client API in modern C++

C++ client API to PostgreSQL {#mainpage} Dmitigr Pgfe (PostGres FrontEnd, hereinafter referred to as Pgfe) - is a C++ client API to PostgreSQL servers

Dmitry Igrishin 134 Jun 3, 2022
A friendly and lightweight C++ database library for MySQL, PostgreSQL, SQLite and ODBC.

QTL QTL is a C ++ library for accessing SQL databases and currently supports MySQL, SQLite, PostgreSQL and ODBC. QTL is a lightweight library that con

null 155 Jun 26, 2022
YugabyteDB is a high-performance, cloud-native distributed SQL database that aims to support all PostgreSQL features

YugabyteDB is a high-performance, cloud-native distributed SQL database that aims to support all PostgreSQL features. It is best to fit for cloud-native OLTP (i.e. real-time, business-critical) applications that need absolute data correctness and require at least one of the following: scalability, high tolerance to failures, or globally-distributed deployments.

yugabyte 6.6k Jul 1, 2022
A PostgreSQL extension providing an async networking interface accessible via SQL using a background worker and curl.

pg_net is a PostgreSQL extension exposing a SQL interface for async networking with a focus on scalability and UX.

Supabase 41 Jun 19, 2022
A framework to monitor and improve the performance of PostgreSQL using Machine Learning methods.

pg_plan_inspector pg_plan_inspector is being developed as a framework to monitor and improve the performance of PostgreSQL using Machine Learning meth

suzuki hironobu 168 Jul 1, 2022
Prometheus exporter for PostgreSQL

pgexporter pgexporter is a Prometheus exporter for PostgreSQL. pgexporter will connect to one or more PostgreSQL instances and let you monitor their o

null 15 Apr 17, 2022
PostgreSQL extension for pgexporter

pgexporter_ext pgexporter_ext is an extension for PostgreSQL to provide additional Prometheus metrics for pgexporter. Features Disk space metrics See

null 4 Apr 13, 2022
Backup / restore solution for PostgreSQL

pgmoneta pgmoneta is a backup / restore solution for PostgreSQL. pgmoneta is named after the Roman Goddess of Memory. Features Full backup Restore Sym

null 35 Jun 22, 2022
recovery postgresql table data by update/delete/rollback/dropcolumn command

recovery postgresql table data by update/delete/rollback/dropcolumn command

RadonDB 4 Mar 30, 2022
pgagroal is a high-performance protocol-native connection pool for PostgreSQL.

pgagroal is a high-performance protocol-native connection pool for PostgreSQL.

Agroal 524 Jun 15, 2022
xxhash functions for PostgreSQL

pg_xxhash PostgreSQL ❤️ xxhash Tested with xxhash 0.8.1 and PostgreSQL 14.1 on Linux and macOS. Think twice before even considering to use it in any s

Igor Hatarist 5 Mar 11, 2022
Distributed PostgreSQL as an extension

What is Citus? Citus is a PostgreSQL extension that transforms Postgres into a distributed database—so you can achieve high performance at any scale.

Citus Data 6.8k Jun 28, 2022
High-performance time-series aggregation for PostgreSQL

PipelineDB has joined Confluent, read the blog post here. PipelineDB will not have new releases beyond 1.0.0, although critical bugs will still be fix

PipelineDB 2.5k Jun 24, 2022
Reliable PostgreSQL Backup & Restore

pgBackRest Reliable PostgreSQL Backup & Restore Introduction pgBackRest aims to be a reliable, easy-to-use backup and restore solution that can seamle

pgBackRest 1.2k Jun 25, 2022
upstream module that allows nginx to communicate directly with PostgreSQL database.

About ngx_postgres is an upstream module that allows nginx to communicate directly with PostgreSQL database. Configuration directives postgres_server

RekGRpth 1 Apr 29, 2022
Modern cryptography for PostgreSQL using libsodium.

pgsodium pgsodium is an encryption library extension for PostgreSQL using the libsodium library for high level cryptographic algorithms. pgsodium can

Michel Pelletier 252 May 17, 2022
Open Source Oracle Compatible PostgreSQL.

IvorySQL is advanced, fully featured, open source Oracle compatible PostgreSQL with a firm commitment to always remain 100% compatible and a Drop-in r

null 86 Jun 20, 2022
Trilogy is a client library for MySQL-compatible database servers, designed for performance, flexibility, and ease of embedding.

Trilogy is a client library for MySQL-compatible database servers, designed for performance, flexibility, and ease of embedding.

GitHub 248 Jun 11, 2022