我的Python工具-Pythn脚本引擎在C++中的应用(实现Sql语句构造工具)

项目背景:
      最近使用C++写服务器端的代码,通过Socket监听客户端请求,解析客户端请求中的参数,并根据解析后的结果,在服务端拼接SQL传递给数据库执行。
一想到C++中字符串解析以及字符串类型转换,以及字符串的拼接...过来人都知道有多么痛苦,头疼啊,腰也疼...
    这不,我的Python工具-SqlBuilder也就应需求而生了,将Python嵌入到C++中,用Python代码实现字符串的解析及加工,拼接等操作交给嵌入到C++中的Python引擎去执行,嗨,这下省力多了,头不疼了,腰也不疼了,吃嘛嘛香...
    ok,进入正题,这一次的实现主要有两个目的:
       一.如何将Python嵌入到C++代码中

       二.用Python实现一个简单的SqlBuilder工具

 

    先简要说明一下我的本机环境:xp + vs2008 + python26

    一.如何将Python嵌入到C++

      1)安装python,如果您问具体怎么安装,请您老google一下,我使用的python26的版本,默认安装在c:\python26

      2)设定vs2008 引入python头文件: tools->options->projects and solutions->vc++ directiories->add includes, add lib 

       

         

        3) 引入python头文件,这里注意,可能你会遇到编译时的错误,找不到python26_d.lib,或者遇到链接错误,如无法解析的外部符号 __imp___Py_RefTotal等错误,请按下列的步骤进行处理

         对于错误1,请复制python26.lib,然后改名为python26_d.lib

         对于错误2,请在引入python头文件前,加

         #undef _DEBUG

         #include <python.h>

       4)  编写c++接口函数,函数内部实现python解析器的初始化,调用python代码,以及python解析器的卸载工作

        具体代码如下: 

 1 #undef _DEBUG /* Link with python26.lib and not python26_d.lib */
 2 #include <Python.h>
 3 
 4 ///<Surmary>
 5 /// 引入Python引擎构建Sql工具
 6 /// 参数说明:
 7 ///     pTemplateName:对应Sql名称
 8 ///     pValues:客户端请求的Json字符串
 9 ///</Surmary>
10 void SqlBuilder(const char* pTemplateName,const char* pValues, char* &sql)
11 {
12     PyObject *pArgs, *pName, *pModule, *pDict, *pFunc;
13     PyObject *pValue;
14     
15     // 初始化python解析器引擎
16     Py_Initialize();
17 
18     pName = PyString_FromString("SqlBuilder");
19     /* Error checking of pName left out */
20 
21     pModule = PyImport_Import(pName);
22     Py_DECREF(pName);
23 
24     if (pModule != NULL) {
25         pFunc = PyObject_GetAttrString(pModule, "BuildSql");
26         /* pFunc is a new reference */
27 
28         if (pFunc && PyCallable_Check(pFunc)) {
29             pArgs = PyTuple_New(2);
30             pValue = PyString_FromString(pTemplateName);
31             if (!pValue) {
32                 Py_DECREF(pArgs);
33                 Py_DECREF(pModule);
34                 fprintf(stderr, "Cannot convert argument pTempateName \n");
35                 return;
36             }
37             /* pValue reference stolen here: */
38             PyTuple_SetItem(pArgs,0, pValue);
39 
40             pValue = PyString_FromString(pValues);
41             if (!pValue) {
42                 Py_DECREF(pArgs);
43                 Py_DECREF(pModule);
44                 fprintf(stderr, "Cannot convert argument pValue\n");
45                 return;
46             }
47             PyTuple_SetItem(pArgs,1, pValue);
48             pValue = PyObject_CallObject(pFunc, pArgs);
49             Py_DECREF(pArgs);
50             if (pValue != NULL) {
51                 sql = PyString_AsString(pValue);
52                 printf("Result of call: %s\n", sql);
53                 Py_DECREF(pValue);
54             }
55             else {
56                 Py_DECREF(pFunc);
57                 Py_DECREF(pModule);
58                 PyErr_Print();
59                 fprintf(stderr,"Call failed\n");
60                 return;
61             }
62         }
63         else {
64             if (PyErr_Occurred())
65                 PyErr_Print();
66             fprintf(stderr, "Cannot find function\"%s\"\n""BuildSql");
67         }
68         Py_XDECREF(pFunc);
69         Py_DECREF(pModule);
70     }
71     else {
72         PyErr_Print();
73         fprintf(stderr, "Failed to load \"%s\" model\n""SqlBuilder");
74         return;
75     }
76 
77     // 卸载Python解析器引擎
78     Py_Finalize();
79 
80     return;
81 }

       ok,第一步工作完成后,已经实现了一个c++调用python代码的接口函数,现在再来实现第二部分,如何调用python代码,这里顺便实现一个sql构建工具

      

我的python工具-SqlBuilder
#-*-coding:utf-8-*-
#
SqlBuilder.py

from string import Template

dicSqlTemplate
= {
    
"A_UpdateT_Table":"""update t_table set tablename = '${tablename}' where tableid= '${tableid}' """
}

def BuildSql(template,values):
    
return Template(dicSqlTemplate[template]).safe_substitute(eval(values))

if __name__ == "__main__":
    
print BuildSql("A_UpdateT_Table""""{"tablename":'t_table', 'tableid':12}""")

    这个就是python的sqlbuilder工具,代码说明:
  包含两个部分:
    1.SQL语句模板
    2.构造SQL函数
     参数说明:pTemplate 对应SQL模板中的SQL语句
                   pValues: 通过客户端请求参数(json格式),参考上述代码中的测试代码中给定的字符串格式

     ok,我的python工具-sqlbuilder,至此完工。如果上述代码在实验的过程中遇到问题,非常欢迎与我沟通交流,email:wdong0472@gmail.com,        QQ:28358358(wdong)

       

posted @ 2010-11-08 01:03 追求、品味、境界 阅读(1731) 评论(8) 编辑 收藏

 回复 引用 查看   
#1楼 2010-11-08 08:37 Jerry Qian      
用合适的工具构建合适的方案,牛。
 回复 引用 查看   
#2楼[楼主] 2010-11-08 08:54 追求、品味、境界      
@Jerry Qian
呵呵,完全是照搬别人的东西,没有什么可牛的啊
多多交流吧

 回复 引用 查看   
#3楼 2010-11-08 11:47 Likwo      
不错,提高工作效率啊。
 回复 引用 查看   
#4楼 2010-11-08 12:42 BAsil      
不错,请问构建的c++服务器端会部署到apache上吧
 回复 引用 查看   
#5楼[楼主] 2010-11-08 20:03 追求、品味、境界      
@BAsil
没有部署apache,只是一般的socket通信(客户端不多),没有用到apache

 回复 引用 查看   
#6楼 2010-11-10 09:41 Dreampuf      
可以跑在没有安装python runtime 的机器上么?
 回复 引用 查看   
#7楼[楼主] 2010-11-12 00:34 追求、品味、境界      
@Dreampuf
不一定非要装runtime啊,只要提供python C api的 .h和lib文件就可以了

 回复 引用 查看   
#8楼 2011-06-09 16:26 左心房C      
#include <stdio.h>
EXEC SQL BEGIN DECLARE SECTION;
char deptname[20];
char hsno[9];
char hsname[20];
char hssex[2];
int hsage;
int newage;
EXEC SQL END DECLARE SECTION;
long SQLCODE;
EXEC SQL INCLUDE sqlca;
int main(void)
{
int count=0;
char yn;
printf("请输入系别:");
scanf("%s",&deptname);
EXEC SQL CONNECT TO k53@ localhost:54321 USER
"system"/"MANAGER";
EXEC SQL DECLARE SX CURSOR FOR
SELECT sno,sname,ssex,sage
from student
where sdept=:deptname;
EXEC SQL OPEN SX;
for( ; ;)
{
EXECSQL FETCH SX INTO:hsno,:hname,:hssex,:hsage;
if(sqlca.sqlcode!=0)
break;
if(count++==0)
printf("\n%-10s%-20s%-10s%-10s%\n","sno","sname","ssex","sage");
peintf("%-10s%-20s%-10s%-10d\n",hsno,hsname,hssex,hsage);
printf("是否要更新学生的年龄(y/n)");
do{
scanf("%c",&yn);
}
while(yn!='N'&&yn!='n'&&yn!='Y'&&yn!='y');
if(yn=='y'||yn=='Y')
{
printf("请输入新年龄:");
scanf("%d",&newage);
EXEC SQL UPDATE student
SET sage =:newage
WHERE CURRENT OF SX;
}
}
EXEC SQL CLOSE SX;
EXEC SQL COMMIT WORK;
EXEC SQL DISCONNECT TEST;

}



: error C2061: syntax error : identifier 'SQL'
: error C2059: syntax error : ';'
为什么会这样呀?谢谢了

发表评论

昵称: [登录] [注册]

主页:

邮箱:(仅博主可见)

评论内容:

  登录  注册

[使用Ctrl+Enter键快速提交评论]

0 1871407 7dtCLqsdBG8=