分享
 
 
 

PostgreSQL数据库学习手册之libpq-C库---数据库联接函数

王朝mssql·作者佚名  2008-05-18
窄屏简体版  字體: |||超大  

1.2. 数据库联接函数

下面的过程处理与 PostgreSQL 后端服务器联接的事情. 一个应用程序一次可以与多个后端建立联接. (这么做的原因之一是访问多于一个数据库.) 每个连接都是用一个从PQconnectdb()或 PQsetdbLogin() 获得的PGconn对象表示. 注意,这些函数总是返回一个非空的对象指针, 除非存储器少得连个PGconn对象都分配不出来. 在把查询发送给联接对象之前,可以调用PQstatus 函数来检查一下联接是否成功.

*

PQconnectdb 与后端数据库服务器建立一个新的联接.

PGconn *PQconnectdb(const char *conninfo)

这个过程用从一个字符串 conninfo 来的参数与数据库打开一个新的联接. 与下面的PQsetdbLogin()不同的是, 我们可以不必更换函数签名(名字)就可以扩展参数集, 所以我们建议应用程序中使用这个函数或者是它的非阻塞的相似函数 PQconnectStart 和 PQconnectPoll. 传入的参数可以为空,表明使用所有缺省的参数, 或者可以包含一个或更多个用空白间隔的参数设置.

每个参数以 关键字 = 数值的形式设置. (要写一个空值或者一个包含空白的值, 你可以用一对单引号包围它们,例如, keyword = 'a value' . 数值内部的单引号和反斜扛必须用一个反斜扛逃逸, 也就是说, '或\\.) 等号周围的空白是可选的.目前可识别的参数键字是:

host

要联接的主机(host ). 如果主机名以斜扛开头, 则它声明使用 Unix 域套接字通讯而不是 TCP/IP 通讯; 该值就是套接字文件所存储的目录. 缺省时是与位于 /tmp 里面的 Unix-域套接字联接.

hostaddr

与之联接的主机的 IP 地址。这个可以是标准的数字-点的形式, 象在 BSD 函数inet_aton等里面用的那样。 如果声明了一个非零长的字符串,那么使用 TCP/IP 通讯机制。

使用hostaddr取代 host 可以让应用避免一次主机名查找, 这一点对于那些有时间约束的应用来说可能是非常重要的。 不过,Kerberos 认证系统要求主机(host)名。因此,应用下面的规则。 如果声明了不带hostaddr的 host 那么就强制进行主机名查找。 如果声明中没有 host,hostaddr 的值给出远端的地址; 如果使用了 Kerberos, 将导致一次反向名字查询。如果同时声明了 host 和hostaddr, 除非使用了 Kerberos,否则将使用hostaddr的值作为远端地址; host 的值将被忽略,如果使用了 Kerberos,host 的值用于 Kerberos 认证。 要注意如果传递给libpq的主机名(host) 不是地址hostaddr处的机器名,那么认证很有可能失败。

如果主机名(host)和主机地址都没有, 那么libpq将使用一个本地的 Unix 域套接字进行通讯。

port

主机服务器的端口号,或者在 Unix 域套接字联接时的套接字扩展文件名.

dbname

数据库名.

user

要联接的用户名。

password

如果后端要求口令认证,所用的口令.

connect_timeout

给连接过程设置的时间范围,以秒计。零或者不设置表示无穷。

options

发给后端的跟踪/调试选项.

tty

文件或控制台(tty),用于从后端的可选调试输出.

requiressl

设为 '1' 要求与后端进行 SSL 联接.如果服务器不支持 SSL, 那么Libpq将马上拒绝联接. 设置为 '0' (缺省)与服务器进行协商.

如果有任何没有声明的参数,那么将检查对应的环境变量(参阅Section 1.10 小节)。 如果环境变量也没有设置,那么使用编译时的硬代码。 返回的值是一个指向代表与后端联接的抽象 struct指针。

*

PQsetdbLogin 与后端数据库服务器建立一个新的联接.

PGconn *PQsetdbLogin(const char *pghost,

const char *pgport,

const char *pgoptions,

const char *pgtty,

const char *dbName,

const char *login,

const char *pwd)

这个函数是 PQconnectdb 前身, 它有固定个数的参数,但是有相同的功能。

*

PQsetdb 与后端数据库服务器建立一个新的联接.

PGconn *PQsetdb(char *pghost,

char *pgport,

char *pgoptions,

char *pgtty,

char *dbName)

这是一个调用 PQsetdbLogin() 的宏,只是login和pwd参数用空(null )代替. 提供这个函数主要是为了与老版本的程序兼容.

*

PQconnectStart, PQconnectPoll 与数据库服务器建立一次非阻塞的联接。

PGconn *PQconnectStart(const char *conninfo)

PostgreSQLPollingStatusType PQconnectPoll(PGconn *conn)

这两个过程用于打开一个与数据库服务器之间的非阻塞的联接: 你的应用的执行线索在执行它的时候不会因远端的 I/O 而阻塞。

数据库联接是用从 conninfo字符串里取得的参数传递给 PQconnectStart进行的。 这个字符串的格式与上面PQconnectdb里描述的一样。

PQconnectStart 和PQconnectPoll 都不会阻塞(进程),不过有一些条件:

o

必须正确提供hostaddr和host 参数以确保不会发生正向或者反向的名字查找。 参阅上面PQconnectdb里的这些参数的文档获取细节。

o

如果你调用了PQtrace, 确保你跟踪进入的流对象不会阻塞。

o

你必须在调用PQconnectPoll之前确保 socket 处于正确的状态,象下面描述的那样。

要开始(联接),调用 conn=PQconnectStart("connection_info_string") . 如果conn是NULL, 表明libpq无法分配一个新的 PGconn 结构。 否则,返回一个有效的PGconn指针 (尽管还不一定代表一个与数据库有效联接)。 PQconnectStart 一返回,调用 status=PQstatus(conn)。 如果 status 等于CONNECTION_BAD, PQconnectStart 失败。

如果PQconnectStart成功了,下一个阶段是轮询 libpq, 这样它就可以继续进行后继的联接动作。 象这样循环:认为一个联接缺省时是"不活跃"的。 如果PQconnectPoll的最后一个返回是 PGRES_POLLING_ACTIVE,则认为它是"活跃的"。 如果PQconnectPoll(conn)的最后一个返回是 PGRES_POLLING_READING,执行一个对 PQsocket(conn)的读select()。 如果最后一个返回是PGRES_POLLING_WRITING, 执行一个对PQsocket(conn)的写select()。 如果还要调用PQconnectPoll, 也就是调用完PQconnectStart之后, 把它当作最后返回PGRES_POLLING_WRITING那样对待。 如果select()显示 socket 已经准备好, 那么认为它是"活跃的"。如果认为一个联接是 "活跃的", 再次调用PQconnectPoll(conn)。 如果这次调用返回PGRES_POLLING_FAILED, 联接过程失败,如果这次调用 返回PGRES_POLLING_OK,联接成功。

要注意上面用select()来确保一个 socket 准备好只是一个(近似)的例子; 还可以用其他方法,比如一个poll()调用,来代替 select。

在联接的任意时刻,我们都可以通过调用PQstatus 来检查联接的状态。 如果这是CONNECTION_BAD, 那么联接过程失败;如果是CONNECTION_OK, 那么联接已经做好。 这两种状态同样也可以从上面的PQconnectPoll 的返回值里检测到。 其他状态可能(也只能)在一次异步联接过程中看到。 这些标识联接过程 的当前状态,因而可能对给用户提供反馈有帮助。这些状态可能包括:

CONNECTION_STARTED

等待进行联接。

CONNECTION_MADE

联接成功;等待发送。

CONNECTION_AWAITING_RESPONSE

等待来自服务器的响应。

CONNECTION_AUTH_OK

已收到认证;等待联接启动继续进行。

CONNECTION_SETENV

协商环境(联接启动的一部分)。

注意,尽管这些常量将保持下去(为了维持兼容性), 应用决不应该依赖于这些常量的某种特定顺序, 或者是根本不应依赖于这些常量, 或者是不应该依赖于这些状态总是某个文档声明的值。 一个应用可能象象下面这样:

switch(PQstatus(conn))

{

case CONNECTION_STARTED:

feedback = "Connecting...";

break;

case CONNECTION_MADE:

feedback = "Connected to server...";

break;

.

.

.

default:

feedback = "Connecting...";

}

要注意如果PQconnectStart返回一个非空的指针, 你必须在使用完它(指针)之后调用PQfinish, 以处理那些结构和所有相关的存储块。 甚至调用PQconnectStart或者 PQconnectPoll失败时也要这样处理。

如果编译libpq时定义了USE_SSL 那么目前的PQconnectPoll将阻塞住。 这个限制可能在将来的版本移除。

这些函数把 socket 置于一个非阻塞的状态,就好象调用了 PQsetnonblocking 一样。

*

PQconndefaults 返回缺省的联接选项。

PQconninfoOption *PQconndefaults(void)

struct PQconninfoOption

{

char *keyword; /* The keyword of the option */

char *envvar; /* Fallback environment variable name */

char *compiled; /* Fallback compiled in default value */

char *val; /* Option's current value, or NULL */

char *label; /* Label for field in connect dialog */

char *dispchar; /* Character to display for this field

in a connect dialog. Values are:

"" Display entered value as is

"*" Password field - hide value

"D" Debug option - don't show by default */

int dispsize; /* Field size in characters for dialog */

}

返回联接选项结构的地址. 可以用于获取所有可能的PQconnectdb选项和它们的当前缺省值. 返回值指向一个PQconninfoOption struct 的数组, 该数组以一个有 NULL 关键字指针的条目结束.注意缺省值(val 域)将 依赖于环境变量和其他上下文.调用者必须把联接选项当作只读对待.

在处理完选项数组后,把数组交给PQconninfoFree()释放. 如果没有这么做,每次调用PQconndefaults() 都会有一小部分内存泄漏.

在PostgreSQL7.0 以前的版本, PQconndefaults() 返回一个指向静态数组的指针, 而不是一个动态分配的数组.这样做是线程不安全的,因此这个特点被修改了.

*

PQfinish 关闭与后端的联接.同时释放被PGconn 对象使用的存储器.

void PQfinish(PGconn *conn)

注意,即使与后端的联接尝试失败(可由PQstatus判断), 应用也要调用PQfinish释放被PGconn 对象使用的存储器.不应该在调用 PQfinish后再使用PGconn 指针.

*

PQreset 重置与后端的通讯端口.

void PQreset(PGconn *conn)

此函数将关闭与后端的联接并且试图与同一个服务器重建新的联接, 使用所有前面使用过的参数.这在 失去工作联接后进行故障恢复时很有用.

*

PQresetStart PQresetPoll 以非阻塞模式重置与后端的通讯端口。

int PQresetStart(PGconn *conn);

PostgreSQLPollingStatusType PQresetPoll(PGconn *conn);

此函数将关闭与后端的联接并且试图与同一个服务器重建新的联接, 使用所有前面使用过的参数.这在 失去工作联接后进行故障恢复时很有用. 它们和上面的PQreset的区别是它们工作在非阻塞模式。 这些函数的使用有与上面PQconnectStart和 PQconnectPoll一样的限制。

调用PQresetStart。如果它返回 0,那么重置失败。 如果返回 1,用与使用PQconnectPoll 建立联接的同样的 方法使用PQresetPoll重置联接。

libpq应用程序员应该仔细维护PGconn结构.使用下面的访问函数来获取PGconn的内容.避免直接引用PGconn结构里的字段,因为这些字段在今后可能被改变.(从 PostgreSQL 版本 6.4 开始, struct PGconn的定义甚至没有放在 libpq-fe.h里.如果你有一些直接访问PGconn数据域的旧代码,你可以通过包含 libpq-int.h 来访问它们,但我们鼓励你赶快修改那些代码.)

*

PQdb 返回联接的数据库名.

char *PQdb(const PGconn *conn)

PQdb 和下面几个函数返回联接时建立起来的几个值.这些值在PGconn对象的生存期内是固定的.

*

PQuser 返回联接的用户名.

char *PQuser(const PGconn *conn)

*

PQpass 返回联接的口令.

char *PQpass(const PGconn *conn)

*

PQhost 返回联接的服务器主机名.

char *PQhost(const PGconn *conn)

*

PQport 返回联接的端口号.

char *PQport(const PGconn *conn)

*

PQtty 返回联接的调试控制台( tty ).

char *PQtty(const PGconn *conn)

*

PQoptions 返回联接中使用的后端选项.

char *PQoptions(const PGconn *conn)

*

PQstatus 返回联接的状态.

ConnStatusType PQstatus(const PGconn *conn)

这个状态可以是一些值之一。 不过,如果不是一次异步联接过程的话,我们只能看到其中的两个 - CONNECTION_OK 或 CONNECTION_BAD。一个与数据库的成功的联接返回状态 CONNECTION_OK。 一次失败的企图用状态 CONNECTION_BAD 标识。 通常,一个 OK 状态保持到 PQfinish,但是一个通讯失败可能会导致状态过早地改变为 CONNECTION_BAD 。这时应用可以试着调用 PQreset 来恢复.

参阅PQconnectStart和PQconnectPoll 条目看看可能出现的其他的状态码。

*

PQerrorMessage 返回联接中操作产生的最近的错误信息.

char *PQerrorMessage(const PGconn* conn);

几乎所有libpq函数在失败时都会设置 PQerrorMessage.注意libpq的传统是, 一个非空的 PQerrorMessage 将在结尾包含一个新行.

*

PQbackendPID 返回控制此联接的后端服务器的进程号ID。

int PQbackendPID(const PGconn *conn);

这个后端PID 在调试和对比 NOTIFY 信息( 包含发出通知的后端的 PID )时很有用. 注意该 PID 属于运行数据库服务器的主机的进程, 而不是本地主机!

*

PQgetssl 返回联接使用的 SSL 结构,或者如果 SSL 没有使用的话返回 NULL.

SSL *PQgetssl(const PGconn *conn);

这个结构可以用于核实加密级别,检查服务器认证等信息.参考 SSL 文档获取关于这个结构的更多信息.

为了获取这个函数的原形,你必须定义 USE_SSL. 这样做会自动包含来自OpenSSL的 ssl.h.

 
 
 
免责声明:本文为网络用户发布,其观点仅代表作者个人观点,与本站无关,本站仅提供信息存储服务。文中陈述内容未经本站证实,其真实性、完整性、及时性本站不作任何保证或承诺,请读者仅作参考,并请自行核实相关内容。
2023年上半年GDP全球前十五强
 百态   2023-10-24
美众议院议长启动对拜登的弹劾调查
 百态   2023-09-13
上海、济南、武汉等多地出现不明坠落物
 探索   2023-09-06
印度或要将国名改为“巴拉特”
 百态   2023-09-06
男子为女友送行,买票不登机被捕
 百态   2023-08-20
手机地震预警功能怎么开?
 干货   2023-08-06
女子4年卖2套房花700多万做美容:不但没变美脸,面部还出现变形
 百态   2023-08-04
住户一楼被水淹 还冲来8头猪
 百态   2023-07-31
女子体内爬出大量瓜子状活虫
 百态   2023-07-25
地球连续35年收到神秘规律性信号,网友:不要回答!
 探索   2023-07-21
全球镓价格本周大涨27%
 探索   2023-07-09
钱都流向了那些不缺钱的人,苦都留给了能吃苦的人
 探索   2023-07-02
倩女手游刀客魅者强控制(强混乱强眩晕强睡眠)和对应控制抗性的关系
 百态   2020-08-20
美国5月9日最新疫情:美国确诊人数突破131万
 百态   2020-05-09
荷兰政府宣布将集体辞职
 干货   2020-04-30
倩女幽魂手游师徒任务情义春秋猜成语答案逍遥观:鹏程万里
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案神机营:射石饮羽
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案昆仑山:拔刀相助
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案天工阁:鬼斧神工
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案丝路古道:单枪匹马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:与虎谋皮
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:李代桃僵
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:指鹿为马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:小鸟依人
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:千金买邻
 干货   2019-11-12
 
推荐阅读
 
 
 
>>返回首頁<<
 
靜靜地坐在廢墟上,四周的荒凉一望無際,忽然覺得,淒涼也很美
© 2005- 王朝網路 版權所有