web2py 1.99.7中无法通过DAL连接MySQL数据库的问题

问题描述

根据在Ubuntu 10.04下配置MySQL数据库(完整版)一文的介绍,完成了MySQL数据库的配置,在客户端访问正常。

然后在web2py应用中通过DAL访问这个MySQL数据库时却碰到了问题:

Traceback (most recent call last): File “/home/www-data/web2py/gluon/restricted.py”, line 205, in restricted exec ccode in environment File “/home/www-data/web2py/applications/mianshi/models/db.py”, line 11, in db = DAL(‘mysql://chinakr:temp_pwd@localhost:3366/saedb’) File “/home/www-data/web2py/gluon/dal.py”, line 5968, in init raise RuntimeError, “Failure to connect, tried %d times:\n%s” % (attempts, tb) RuntimeError: Failure to connect, tried 5 times: Traceback (most recent call last): File “/home/www-data/web2py/gluon/dal.py”, line 5955, in init self._adapter = ADAPTERSself._dbname File “/home/www-data/web2py/gluon/dal.py”, line 1886, in initself.pool_connection(connect) File “/home/www-data/web2py/gluon/dal.py”, line 465, in pool_connection self.connection = f() File “/home/www-data/web2py/gluon/dal.py”, line 1885, in connect return self.driver.connect(**driver_args) File “/home/www-data/web2py/gluon/contrib/pymysql/init.py”, line 93, in Connect return Connection(*args, **kwargs) File “/home/www-data/web2py/gluon/contrib/pymysql/connections.py”, line 513, ininit self._connect() File “/home/www-data/web2py/gluon/contrib/pymysql/connections.py”, line 669, in _connect raise OperationalError(2003, “Can’t connect to MySQL server on %r (%d)” % (self.host, e.args[0])) OperationalError: (2003, “Can’t connect to MySQL server on ‘localhost’ (111)”)

也就是在web2py中通过DAL连接MySQL数据库失败。

问题分析

直接Google错误提示没有发现相关资料。

跟踪报错的web2py源代码:

$ vim /home/www-data/web2py/gluon/contrib/pymysql/connetctions.py 

第668和669行:

 except socket.error, e: raise OperationalError(2003, "Can't connect to MySQL server on %r (%d)" % (self.host, e.args[0])) 

也就是说,这个数据库无法连接的错误实际上是MySQL的Socket错误引起的。

解决问题

第一次尝试失败

在MySQL数据库服务器上:

$ sudo vim /etc/mysql/my.cnf [mysqld] socket = /tmp/mysql.sock 

重启MySQL服务器:

$ sudo service mysql restart 

注:根据后文叙述,这一步应该不是必须的。

问题终于解决了

根据Can’t connect to MySQL server on ‘localhost’中Kevin Ivarsen的描述:

MySQL can communicate over either TCP or a named pipe. It’s possible that your MySQL server is only listening on the named pipe. I could imagine that the mysql command line client would connect successfully over this channel, but Python would try to connect to the TCP socket and fail.

Try telnetting to the local mysql port and see what happens:

telnet localhost 3306

If you get an error like “connection refused”, then this is almost certainly the problem. Take a look at your mysql config file (/etc/mysql/my.cnf or similar) and look for the bind-address or skip-networking settings.

修改MySQL的端口绑定:

$ sudo vim /etc/mysql/my.cnf 

有两种修改方式:

  1. 只允许本地访问

“`

[mysqld] bind-address = 127.0.0.1 #bind-address = 211.147.217.171 

“`

  1. 允许本地和远程访问

“`

[mysqld] #bind-address = 127.0.0.1 #bind-address = 211.147.217.171 

“`

重启MySQL服务器:

$ sudo service mysql restart 

问题解决!

参考资料

在Ubuntu 10.04下配置MySQL数据库(完整版)

目标设定

在服务器上创建指定端口和用户权限的MySQL数据库。

这里,我们设定:

  • 数据库服务器IP:211.147.217.171
  • 数据库访问端口:3366
  • 数据库名称:saedb
  • 用户名:chinakr
  • 密码:temp_pwd
  • 权限:saedb数据库的全部权限,不限制IP

安装MySQL数据库

$ sudo aptitude install mysql-server mysql-client phpmyadmin 

注:安装过程中会提示输入MySQL数据库的root用户的密码。

如果需要重新设置root用户的密码:

$ sudo dpkg-reconfigure mysql-server-5.1 

注:重设密码后会重启MySQL数据库,重启的时间可能会比较长。

测试MySQL数据库连接

$ mysql -u root -p mysql> exit 

注:这里会提示数据MySQL数据库的root用户的密码。

修改MySQL数据库的默认端口

把端口由默认的3306改为3366:

$ sudo vim /etc/mysql/my.cnf [mysqld] port = 3366 

重启MySQL数据库:

$ sudo service mysql restart 

注:数据库重启的时间可能会比较长。

创建数据库、用户,配置权限

创建数据库saedb:

$ mysql -u root -p mysql> CREATE DATABASE saedb; 

创建用户chinakr:

mysql> CREATE USER 'chinakr'@'%' IDENTIFIED BY 'temp_pwd'; 

赋予用户数据库的全部权限:

mysql> GRANT ALL PRIVILEGES ON saedb.* TO 'chinakr'@'%'; mysql> exit 

测试刚才创建的数据库和用户:

mysql> mysql -u chinakr -p mysql> USE saedb; mysql> CREATE TABLE helloword (id INT NOT NULL AUTO_INCREMENT PRIMARY KEY, name VARCHAR(20), content TEXT); mysql> INSERT INTO helloword (name, content) VALUE ('chinakr', 'Hi, everyone!'); mysql> SELECT * FROM helloword; 

在客户端访问远程MySQL数据库

现在我们从MySQL数据库所在的服务器退出,返回本地桌面。

$ mysql -u chinakr -p -h 211.147.217.171 -P 3366 saedb 

到这里,整个配置工作就完成了。 接下来,我们可以在Web应用中访问MySQL数据库了!

参考资料

Discuz X2论坛SEO指南

后台设置

全局 > SEO设置

  • URL静态化:URL规则。一旦设置不能轻易修改。
  • 门户:设置门户页面的title、keywords和description。
    • 这个是下一步的重点。
  • 论坛:设置论坛页面的title、keywords和description。
    • 这个是重点。
  • 家园:设置个人空间页面的title、keywords和description。
    • 目前不是重点。
  • 群组:设置群组页面的title、keywords和description。
    • 目前不是重点。
  • 其他:不清楚有什么用。

门户的SEO设置

  • 完成用户注册和激活的整理后,可以把论坛的列表页和内容页都单独生成门户页面,这样SEO就变得非常重要。
  • 可以为首页、列表页、内容页设置不同的title、keywords和description。
  • 可以为不同版块的列表页设置不同的title、keywords和description。

论坛的SEO设置

  • 可以为首页、列表页、内容页设置不同的title、keywords和description。
  • 可以为不同版块的列表页设置不同的title、keywords和description。

Discuz! X2 SEO存在的问题

主要问题是重复的Meta信息。

其次是URL静态化不完全。

注:这里的Meta信息指description和keywords。

重复的Meta信息

  1. 同一个版块的列表页,第一页、第二页、第三页…的Meta信息完全一样。(www.discuz.net也是这样)
  2. 一个帖子的第二页、第三页、第四页…的Meta信息完全一样,都是帖子的标题+网站标题。(www.discuz.net也是这样)

对策: 在description中加入页码(分页数{page})。

URL静态化不完全

  1. 一级版块的URL仍然是动态的。(www.discuz.net也是这样)
  2. “最后发表”的URL仍然是动态的。(www.discuz.net也是这样)

对策: 通过robots.txt屏蔽动态URL。

优化技巧

避免Archiver分散权重

例子:

从上面的例子我们可以看到,www.discuz.net有意把Archiver的URL改为动态的, 降低了Archiver页面的权重,减少了搜索引擎的收录, 最大程度避免了网站页面的权重因为Archiver而下降。

诀窍就在文件名前面的那一个小小的问号上,是不是很神奇?

为Archiver设置动态URL的方法

Discuz! X2后台 > 全局 > SEO设置 > URL静态化:

论坛Archiver页,格式由“{action}-{value}.html”改为“?{action}-{value}.html”。

为帖子设置标签和相关帖子

打开了标签和相关帖子后,和当前帖子标签相同的其他帖子会显示在当前帖子的下方。

这样做的好处是用户有可能点击相关帖子,从而增加PV,同时也有效增加了内链。

允许用户设置标签的方法

Discuz! X2后台 > 用户 > 用户组 > 选择某个用户组 > 基本设置:

允许使用标签,把“否”改为“是”。

自动生成标签

参考资料“X2优化分析三—自动标签!自动获取标签SEO优化”提供了一种自动生成标签的方法,需要简单修改Discuz! X2的源代码。

显示相关帖子的方法

Discuz! X2后台 > 界面 > 界面设置 > 帖子内容页:

相关帖子条目数,默认为10条。

参考资料

[分享]源代码&开发手记:SAE应用“车百科” (Python + SAE + Bottle + Bootstrap)

车百科”是一个基于SAE Python的简单应用,提供了汽车标图片志大全,并提供了到厂商主页、相关新闻和评论的快速入口。

“车百科”是用Python Web开发框架Bottle开发的,涉及到了控制器、视图和数据库访问。前端使用了Twitter开发的Bootstrap框架,简洁、高效、强大。

汽车标志图片使用SAE Storage存储,管理方便,上传、访问速度都很快。

开发过程中,没有使用SAE默认的SVN版本控制系统,而是使用了Git来管理代码,用saecloud来部署代码。

为了帮助更多的朋友快速掌握基于SAE的Python开发,我把“车百科”的开发手记源代码公开,一方面希望加强和大家的交流、分享,另一方面希望能帮助一些刚接触SAE开发的朋友。

欢迎访问我的微博博客,交流、分享、沟通提高。