drogonframework / drogon

Drogon: A C++14/17/20 based HTTP web application framework running on Linux/macOS/Unix/Windows
MIT License
11.58k stars 1.12k forks source link

drogon_ctl create model hangs #1188

Closed bradleysmith closed 6 months ago

bradleysmith commented 2 years ago

Using postrgresql version 12, and latest drogon version as of 14:22 on 7th march 2022.

My model.json looks like this:

{
    "rdbms": "postgresql",
    "host": "localhost",
    "port": 5432,
    "dbname": "XXXX",
    "schema": "public",
    "user": "XXX",
    "password": "XXX",
    "tables": ["phrases", "sentences", "sentence_phrase"],
    "relationships": {
        "enabled": true,
        "items": [
            {
                "type": "has many",
                "original_table_name": "sentences",
                "original_table_alias": "sentence",
                "original_key": "id",
                "target_table_name": "phrases",
                "target_table_alias": "phrase",
                "target_key": "id",
                "enable_reverse": true
            }
        ]
    }
}

Issuing command: drogon_ctl create model models from the root of my project folder I get:

XXX@XXX:~/my-project$ drogon_ctl create model models
Create model
postgresql
Connect to server...
Source files in the models folder will be overwritten, continue(y/n)?
y
table name:phrases

and it just hangs there. No files are written.

Credentials are 100% correct. I can successfully connect and browse the tables using psql, PGAdmin and DBeaver using those same credentials and server details.

Removing the relationships section has no impact.

an-tao commented 2 years ago

@bradleysmith thanks for your feedback, what OS are you using? and how did you install drogon into your system?

bradleysmith commented 2 years ago

Hi,

I can repeat the problem on two systems:

Ubuntu 20.04 and MX Linux.

Installed drogon by doing a git clone, mkdir build, cd build, cmake .., make, sudo make install.

One thing I have just remembered, on both machines I installed drogon BEFORE installing postgresql. Then I did a cmake, make, make install on drogonagain afterwards.

an-tao commented 2 years ago

Hi,

I can repeat the problem on two systems:

Ubuntu 20.04 and MX Linux.

Installed drogon by doing a git clone, mkdir build, cd build, cmake .., make, sudo make install.

One thing I have just remembered, on both machines I installed drogon BEFORE installing postgresql. Then I did a cmake, make, make install on drogonagain afterwards.

Did you clean the cmake cache before rebuilding drogon? the simplest way to do that is to remove the build directory. please run drogon ctrl -v to confirm that the postgresql is supported by drogon.

bradleysmith commented 2 years ago

Hi,

Yes, I cleared out the whole of build. Here's my drogon_ctl -v output:

A utility for drogon
Version: 1.7.5
Git commit: b9bbe45642a137d5b3a15a8e68fd955e59c36745
Compilation: 
  Compiler: /usr/bin/c++
  Compiler ID: GNU
  Compilation flags: -std=c++17 -I/usr/local/include
Libraries: 
  postgresql: yes  (batch mode: no)
  mariadb: no
  sqlite3: no
  openssl: yes
  brotli: no
  boost: no
  hiredis: no
  c-ares: no
bradleysmith commented 2 years ago

I started to debug it. It's locking at line 178 of create_model.cc

EDIT: Line 717 of "future"

Here are the call stacks:

libc.so.6!syscall() (\build\glibc-sMfBJT\glibc-2.31\sysdeps\unix\sysv\linux\x86_64\syscall.S:38)
libstdc++.so.6!std::__atomic_futex_unsigned_base::_M_futex_wait_until(unsigned int*, unsigned int, bool, std::chrono::duration<long, std::ratio<1l, 1l> >, std::chrono::duration<long, std::ratio<1l, 1000000000l> >) (Unknown Source:0)
std::__atomic_futex_unsigned<2147483648u>::_M_load_and_test_until(std::__atomic_futex_unsigned<2147483648> * this, unsigned int __assumed, unsigned int __operand, bool __equal, std::memory_order __mo, bool __has_timeout, std::chrono::seconds __s, std::chrono::nanoseconds __ns) (\usr\include\c++\9\bits\atomic_futex.h:102)
std::__atomic_futex_unsigned<2147483648u>::_M_load_and_test(std::__atomic_futex_unsigned<2147483648> * this, unsigned int __assumed, unsigned int __operand, bool __equal, std::memory_order __mo) (\usr\include\c++\9\bits\atomic_futex.h:121)
std::__atomic_futex_unsigned<2147483648u>::_M_load_when_equal(std::__atomic_futex_unsigned<2147483648> * this, unsigned int __val, std::memory_order __mo) (\usr\include\c++\9\bits\atomic_futex.h:162)
std::__future_base::_State_baseV2::wait(std::__future_base::_State_baseV2 * this) (\usr\include\c++\9\future:337)
std::__basic_future<drogon::orm::Result>::_M_get_result(const std::__basic_future<drogon::orm::Result> * this) (\usr\include\c++\9\future:717)
std::future<drogon::orm::Result>::get(std::future<drogon::orm::Result> * this) (\usr\include\c++\9\future:796)
drogon::orm::internal::SqlBinder::exec(drogon::orm::internal::SqlBinder * this) (\home\dev\drogon\orm_lib\src\SqlBinder.cc:104)
drogon::orm::internal::SqlBinder::~SqlBinder(drogon::orm::internal::SqlBinder * this) (\home\dev\drogon\orm_lib\src\SqlBinder.cc:132)
drogon_ctl::create_model::createModelClassFromPG(drogon_ctl::create_model * this, const std::string & path, const drogon::orm::DbClientPtr & client, const std::string & tableName, const std::string & schema, const Json::Value & restfulApiConfig, const std::vector<drogon_ctl::Relationship, std::allocator<drogon_ctl::Relationship> > & relationships, const std::vector<drogon_ctl::ConvertMethod, std::allocator<drogon_ctl::ConvertMethod> > & convertMethods) (\home\dev\drogon\drogon_ctl\create_model.cc:178)
drogon_ctl::create_model::createModel(drogon_ctl::create_model * this, const std::string & path, const Json::Value & config, const std::string & singleModelName) (\home\dev\drogon\drogon_ctl\create_model.cc:874)
drogon_ctl::create_model::createModel(drogon_ctl::create_model * this, const std::string & path, const std::string & singleModelName) (\home\dev\drogon\drogon_ctl\create_model.cc:1135)
drogon_ctl::create_model::handleCommand(drogon_ctl::create_model * this, std::vector<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >, std::allocator<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > > > & parameters) (\home\dev\drogon\drogon_ctl\create_model.cc:1175)
exeCommand(std::vector<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >, std::allocator<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > > > & parameters) (\home\dev\drogon\drogon_ctl\cmd.cc:43)
drogon_ctl::create::handleCommand(drogon_ctl::create * this, std::vector<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >, std::allocator<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > > > & parameters) (\home\dev\drogon\drogon_ctl\create.cc:54)
exeCommand(std::vector<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >, std::allocator<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > > > & parameters) (\home\dev\drogon\drogon_ctl\cmd.cc:43)
main(int argc, char ** argv) (\home\dev\drogon\drogon_ctl\main.cc:46)

and

libc.so.6!epoll_wait(int epfd, struct epoll_event * events, int maxevents, int timeout) (\build\glibc-sMfBJT\glibc-2.31\sysdeps\unix\sysv\linux\epoll_wait.c:30)
trantor::EpollPoller::poll(trantor::EpollPoller * this, int timeoutMs, trantor::ChannelList * activeChannels) (\home\dev\drogon\trantor\trantor\net\inner\poller\EpollPoller.cc:80)
trantor::EventLoop::loop(trantor::EventLoop * this) (\home\dev\drogon\trantor\trantor\net\EventLoop.cc:193)
trantor::EventLoopThread::loopFuncs(trantor::EventLoopThread * this) (\home\dev\drogon\trantor\trantor\net\EventLoopThread.cc:60)
trantor::EventLoopThread::EventLoopThread(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)::$_0::operator()() const(const class {...} * this) (\home\dev\drogon\trantor\trantor\net\EventLoopThread.cc:25)
std::__invoke_impl<void, trantor::EventLoopThread::EventLoopThread(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)::$_0>(std::__invoke_other, trantor::EventLoopThread::EventLoopThread(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)::$_0&&)(class {...} && __f) (\usr\include\c++\9\bits\invoke.h:60)
std::__invoke<trantor::EventLoopThread::EventLoopThread(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)::$_0>(trantor::EventLoopThread::EventLoopThread(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)::$_0&&)(class {...} && __fn) (\usr\include\c++\9\bits\invoke.h:95)
std::thread::_Invoker<std::tuple<trantor::EventLoopThread::EventLoopThread(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)::$_0> >::_M_invoke<0ul>(std::_Index_tuple<0ul>)(std::thread::_Invoker<std::tuple<(lambda at /home/dev/drogon/trantor/trantor/net/EventLoopThread.cc:25:15)> > * this) (\usr\include\c++\9\thread:244)
std::thread::_Invoker<std::tuple<trantor::EventLoopThread::EventLoopThread(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)::$_0> >::operator()()(std::thread::_Invoker<std::tuple<(lambda at /home/dev/drogon/trantor/trantor/net/EventLoopThread.cc:25:15)> > * this) (\usr\include\c++\9\thread:251)
std::thread::_State_impl<std::thread::_Invoker<std::tuple<trantor::EventLoopThread::EventLoopThread(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)::$_0> > >::_M_run()(std::thread::_State_impl<std::thread::_Invoker<std::tuple<(lambda at /home/dev/drogon/trantor/trantor/net/EventLoopThread.cc:25:15)> > > * this) (\usr\include\c++\9\thread:195)
libstdc++.so.6![Unknown/Just-In-Time compiled code] (Unknown Source:0)
libpthread.so.0!start_thread(void * arg) (\build\glibc-sMfBJT\glibc-2.31\nptl\pthread_create.c:477)
libc.so.6!clone() (\build\glibc-sMfBJT\glibc-2.31\sysdeps\unix\sysv\linux\x86_64\clone.S:95)
bradleysmith commented 2 years ago

OK problem solved by changing host from localhost to 127.0.0.1 in the model.json file.

And it looks like the real issue is down to my configuration of postgres in pg_hba.conf.