Erlang 无法连接到 mysql/mariadb

dat*_*ose 1 mysql erlang mariadb erlang-shell

我无法使用 erlang 连接到 mysql/mariadb。

根据这个github-page的要求:https : //github.com/mysql-otp/mysql-otp

要求:

Erlang/OTP version R16B or later
MySQL database version 4.1 or later or MariaDB
GNU Make or Rebar or any other tool for building Erlang/OTP applications
Run Code Online (Sandbox Code Playgroud)

版本:

14> erlang:system_info(otp_release).
"22"
Run Code Online (Sandbox Code Playgroud)

我不确定是否不再需要此要求,但我添加了以下内容:

[mysqld] default_authentication_plugin=mysql_native_password

到我的 /etc/my.cnf。但这可能无关紧要,因为错误是一个未定义的函数。我可以编译代码,但我不能运行它。非常感谢任何帮助使其正常工作。

编码:

-module(mydatabase).
-compile(export_all).

connect_to_database() -> 
Conn = mysql:start_link([{host, "localhost"}, {user, "user"},
                       {password, "password"}, {database, "MyDatabase"}]) ,
           
  case Conn of
      {ok, Pid} -> io:fwrite("~w~w~n", [ok,Pid]);
      {error, ConnErr}  -> io:fwrite("error : ~p ~n", [ConnErr])
    end.
              
 start() -> connect_to_database().
Run Code Online (Sandbox Code Playgroud)

mariadb 正在运行:

sudo systemctl status mariadb
[sudo] password for user: 
? mariadb.service - MariaDB 10.4.13 database server
   Loaded: loaded (/usr/lib/systemd/system/mariadb.service; disabled; vendor >
   Active: active (running) since Sun 2020-06-28 15:33:50 CEST; 1h 4min ago
Run Code Online (Sandbox Code Playgroud)

错误信息:

12> c(mydatabase).     
mydatabase.erl:2: Warning: export_all flag enabled - all functions will be exported
{ok,mydatabase}
13> mydatabase:start().
** exception error: undefined function mysql:start_link/1
 in function  mydatabase:connect_to_database/0 (mydatabase.erl, line 1
Run Code Online (Sandbox Code Playgroud)

7st*_*tud 7

你忘记了这个要求:

GNU Make 或 Rebar 或任何其他用于构建 Erlang/OTP 应用程序的工具

根据mysql-otp 文档

MySQL/OTP 是将 Erlang/OTP 应用程序连接到 MySQL 和 MariaDB 数据库的驱动程序。

AnOTP application需要一定的架构,并且需要在应用程序中将mysql驱动列为依赖项。您的错误是由于mysql:start_link/1Erlang 中没有命名的函数。相反,这是您的代码必须以某种方式访问​​的第三方函数,因此文档中的使用作为依赖项部分。

以下步骤可用于创建OTP application使用 mysql/mariaDB 作为依赖项的一个:

  1. 安装 rebar3

  2. 创建一个 rebar3 app

    ~/erlang_programs/mysql1$ rebar3 new app myapp
    ===> Writing myapp/src/myapp_app.erl
    ===> Writing myapp/src/myapp_sup.erl
    ===> Writing myapp/src/myapp.app.src
    ===> Writing myapp/rebar.config
    ===> Writing myapp/.gitignore
    ===> Writing myapp/LICENSE
    ===> Writing myapp/README.md
    
    Run Code Online (Sandbox Code Playgroud)
  3. 在 rebar.config 文件中添加 mysql-otp 作为依赖项:

      ~/erlang_programs/mysql1$ cd myapp
      ~/erlang_programs/mysql1/myapp$ ls
      LICENSE       rebar.config
      README.md src
    
    Run Code Online (Sandbox Code Playgroud)

像这样:

    {erl_opts, [debug_info]}.
    {deps, [

      {mysql, ".*", {
                      git, "https://github.com/mysql-otp/mysql-otp",
                      {tag, "1.6.0"}
                    }
      }

    ]}.

    {shell, [
      % {config, "config/sys.config"},
        {apps, [myapp]}
    ]}.
Run Code Online (Sandbox Code Playgroud)
  1. 将您的源代码放在src目录中:

     ~/erlang_programs/mysql1/myapp$ cd src
     ~/erlang_programs/mysql1/myapp/src$ ls
     my_mysql.erl    myapp_app.erl
     myapp.app.src   myapp_sup.erl
    
    Run Code Online (Sandbox Code Playgroud)

my_mysql.erl:

-module(my_mysql).
-compile(export_all).

do_mysql(Name, Info) ->
    {ok, MysqlPid} = mysql:start_link(
                  [{host, "localhost"}, 
                   {user, "root"},
                   {password, ""}, 
                   {database, "mydb"}
                  ]
                ),

     ok = mysql:query(
           MysqlPid, 
           "INSERT INTO people (name, info) VALUES (?, ?)", [Name, Info]
        ),

     {ok, ColumnNames, Rows} = mysql:query(
                MysqlPid, 
                <<"SELECT * FROM people">>),

     io:format("ColumnNames: ~p~nRows: ~p~n", [ColumnNames, Rows]).
Run Code Online (Sandbox Code Playgroud)
  1. 获取依赖项并编译所有源代码:

     ~/erlang_programs/mysql1/myapp$ rebar3 compile
     ===> Verifying dependencies...
     ===> Fetching mysql ({git,"https://github.com/mysql-otp/mysql-otp",
                                      {tag,"1.6.0"}})
     ===> Compiling mysql
     ===> Compiling myapp
     src/my_mysql.erl:2: Warning: export_all flag enabled - all functions will be exported
    
    Run Code Online (Sandbox Code Playgroud)
  2. 启动 shell 并自动构建所有 .beam 文件的路径(在 rebar3 放置它们的深层嵌套目录中):

     ~/erlang_programs/mysql1/myapp$ rebar3 shell
     ===> Verifying dependencies...
     ===> Compiling myapp
     Erlang/OTP 20 [erts-9.3] [source] [64-bit] [smp:4:4] [ds:4:4:10] [async-threads:1] [hipe] [kernel-poll:false]
    
     ===> The rebar3 shell is a development tool; to deploy applications in production, consider using releases (http://www.rebar3.org/docs/releases)
     ===> Booted myapp
     Eshell V9.3  (abort with ^G)
    
    Run Code Online (Sandbox Code Playgroud)
  3. 执行你的功能:

     1> my_mysql:do_mysql("Jeffsy", "2.0").
     ColumnNames: [<<"id">>,<<"name">>,<<"info">>]
     Rows: [[1,<<"7stud">>,<<"abc">>],
            [2,<<"Beth">>,<<"xxx">>],
            [3,<<"Diane">>,<<"xyz">>],
            [4,<<"Kathy">>,<<"xyz">>],
            [5,<<"Kathy">>,<<"xyz">>],
            [6,<<"Dave">>,<<"efg">>],
            [7,<<"Tom">>,<<"zzz">>],
            [8,<<"David">>,<<"abc">>],
            [9,<<"Eloise">>,<<"abc">>],
            [10,<<"Jess">>,<<"xyz">>],
            [11,<<"Jeffsy">>,<<"2.0">>]]
     ok
    
    Run Code Online (Sandbox Code Playgroud)