DIARIO DE CHINOS 华侨快报(国际刊号 ISSN 2530-1349) 新手帮助

西班牙华人网-华侨快报

电脑爱好电脑爱好
关注: 0贴子:195 排名: 56 
0 回复贴,1706 次查看
<返回列表

Discuz! 从 GBK 转换 UTF-8 编码全过程

网友
网友  发表于 2017-7-27 19:57:51
在 Discuz! 诞生之时,国内网站清一色以 GBK 编码为主流,很多老站长都选择了以在当时很成熟的 GBK 编码来建站。如今过了十几个年头,Unicode 已经成功统治了世界,如何把 Discuz! 从 GBK 转换到 UTF-8 成了困扰很多老论坛的难题。1 y% A2 Y  C, i: O) z, s

( H  u4 S/ e8 G2 VSteamCN 论坛如今已经拥有十三年的历史,经历了 dvbbs、Discuz!、Discuz! X 三个阶段,是国内为数不多能完好保存十多年前附件和图片的论坛。今天在短短两小时的维护时间内,SteamCN 论坛成功从 GBK 编码完美转换到了 UTF-8(utf8mb4,支持 emoji &#128536;)。本文将记录转换所用的工具、脚本以及常见的坑,以供广大 Discuz! 站长参考。
% K% T+ Q' J* o% V
7 Q' Q) n0 @: h
本次转换工作得到了 DxGit Forker 群内 Coxxsgreenrock[微凡] 的帮助,非常感谢二位的指导!

$ M$ j* l) i& L8 j
% M2 }# h1 B& C! Q9 Z7 q3 d) {5 J1. 准备工作1 `- R  H" G* W* M% N/ }6 C4 p: ~

$ O) D/ n9 Y( A% j, y! z不同的网站都有自己的不同之处,请务必先在测试环境内演练转换过程,然后再应用到线上正式服务器。
- j# s6 [1 X  G: |1 ]" h# N6 @: o( Y9 Q
1. 下载与自己当前 Discuz! 版本号相同的 UTF-8 安装包。本站为经过浅度定制的 Discuz! X3.3,以下教程以 Discuz! X3.3 为例来进行。如果你的网站经过深度定制,请人工将代码转换为 UTF-8 编码。0 Y! f4 C" E1 S2 c  i. w
2. 准备测试数据库。将当前线上版本数据库完整拷贝一份作为测试数据库,我们将先以该数据库进行一次演练。
* a7 z" M5 C. L  L7 k3. 准备测试用 Web 服务器。将网站文件夹拷贝一份到测试 Web 服务器上。由于 data、uc_client/data、uc_server/data/avatar 这几个目录体积会比较大,可以忽略它们。$ I" w* V2 l( f* _
4. 编辑测试环境中的 config/config_global.php、config/config_ucenter.php、uc_server/data/config.inc.php,将数据库配置为测试数据库,并关闭 Discuz! 的一切内存缓存功能。
' i8 z- P. [3 g; y1 Y) d$ D: ?5. 确认测试环境的网站可以正常运行。9 r$ O$ Q* e( `& m/ ]4 N

0 X6 a' k# N# u7 o8 e, e5 E, o2. 转换数据库
  l- u0 q) c- e1 x$ Z8 J/ S. U% o$ H- X% g/ `& X1 Z) i$ a
我们需要人工手动使用这条语句对数据库中的每一个表进行转换:# a9 g, I& _$ G) o9 [. T' p; P
  • ALTER TABLE `表名` CONVERT TO CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;
    # _/ H6 H5 Q; J3 Q: ]. T

: ]8 V6 M; {: j3 `% o) W[color=rgb(87, 186, 232) !important]复制代码
; g3 N  \7 i& \. x) h& m9 L

1 e" g* V) W  n. Y/ Q! y: ]" _" y& j% f5 t* `5 l# w) X, t! b
务必将运行过的每一个语句记录下来中,方便最后在线上服务器部署。
) q0 a$ t1 Y/ m! L' d) O9 H3 _9 ?- `
可能会遇到的问题:! H& n1 g6 V* [; n2 U2 R

: p& w; k( z2 k: K6 |/ wQ: 为什么这里不提供预先编写好的 SQL 呢?0 B& I2 Q- L. A4 \/ U/ d( G
A: 因为每个网站的数据库差异很大,我们使用的 SQL 脚本(文末附件压缩包内 gbk-to-utf8mb4.sql)未必适合你的网站。这里需要人工对每一个数据表运行这个语句。) J( r) g0 r& |
9 U% F. E7 B+ ?2 m/ s9 p4 V, p
Q: 提示索引最大长度为 xxx,转换失败
4 w% `) I! |7 M% B+ j2 }! {A: 调整索引涉及到的字段长度,保证不超过 xxx / 4。例如 pre_common_addon 这个表报错索引长度最大不能超过 1000,那么需要将 key 字段的类型从 varchar(255) 改为 varchar(200)。3 y5 V9 N) Y* s# @3 x

/ ?. H6 j* M4 W; `& X2 AQ: 提示用户名重复,转换失败0 Z. \. @3 }$ J6 P+ @! D
A: 这是由于一些字符在 gbk_chinese_ci 排序规则下认为是不同的,但是在 utf8mb4_unicode_ci 排序规则下认为是相等的。例如全角英文字母与半角英文字母,在 gbk_chinene_ci 下认为 A != A,但是在 utf8mb4_unicode_ci 下认为 A == A。这时需要编辑 unique 索引,改为普通索引,然后重新转换,再将索引改回 unique 类型,此时会具体指出哪个用户名重复,请记录其 UID。如果数据量比较大,可以自行编写 SQL 寻找重复项。+ c9 }! h8 h+ I6 t$ J
对于重复的用户名,我们可以使用这个语句将该用户的用户名重置为 email:
7 K8 s7 O6 s4 Y  s1 o0 u5 N
  • UPDATE `表名` SET `username` = email WHERE `表名`.`uid` = 上面记录的用户UID;. r# o& R/ ^+ `) Q

  O1 i6 B& r6 Y" V$ r, i[color=rgb(87, 186, 232) !important]复制代码

' \1 c- H8 p' r3 Z
* f3 k2 x. W; c8 x! C8 T- b. j7 P' n5 w# P! Z$ o
3. 上传 UTF-8 版本代码( h3 l9 e+ Q! N5 O9 m5 M% B
0 a  u1 R2 w# S1 e
将准备阶段取得的 UTF-8 版本代码覆盖到测试服务器中(注意不要覆盖掉 config 文件)。
& @8 M" _6 ^5 z2 q" |" O7 u编辑 config/config_global.php、config/config_ucenter.php、uc_server/data/config.inc.php,将其中 DBCHARSET 改为 utf8mb4,输出 CHARSET 改为 utf-8。
$ L  v4 e/ a& T- I到此先不要打开网站测试效果!' a- q2 r8 V  W# z; w! \

) G4 k; Z4 D3 ~3 U$ ]. b/ \, |4. 修复数据库' R% s! t+ m6 T. _) Z

, V5 g* W0 ?/ `: ^6 K& [由于 Discuz! 大量使用了 PHP 的 serialize 方法来序列化对象存入数据库,而 serialize 方法序列化出来的结果和编码是相关的,因此需要修复数据库中以前使用 GBK 编码序列化的结果,使其能在 UTF-8 编码下反序列化出来。4 R1 L4 l1 E9 ^, C

" {  X- m: G" ?扩展阅读( a7 [0 _" m: k: I

9 O# ~1 T. o* N9 t. K9 b下载文末附件“脚本与工具.zip”,解压出来得到 migrate_db.php(出处,略做修改),编辑该文件结尾的数据表列表,确认这些表和字段都是在你数据库存在的。这个列表未必完善,建议手动检查一遍所有数据表,补充可能漏掉的数据表和字段。第 29 行指定了单次处理的数据条数,如果你的数据库性能比较差,建议降低该值。  |: v3 U7 }0 r8 X) u! ~

' I; e; m8 C2 c3 ?将 migrate_db.php 上传到网站根目录,浏览器访问它,点击“Discuz! 序列化整理”开始修复。
' C) B5 i) O' r9 p
$ }. ^2 H$ q% W8 D8 C9 s5. 转换模板、插件编码
9 o  n' K0 i& e2 [
  e1 v7 Q$ f% v人工将你所有使用的模板、插件的编码转换为 UTF-8。注意不要漏掉 XML 文件。; u1 K+ d# t1 F4 R& B- B
如果你的模板、插件是从应用商店下载的,没有经过改动,建议登录后台进行卸载,在应用中心重新安装一遍。6 E  `& k1 P+ n% v( K# x

  B: ]1 v( X$ o1 h' _' j6. 转换日志编码
2 V* L  P# L; x5 Q( ^4 L; ]5 X; h
Discuz! 将运行日志记录在了 data/logs 目录下,如果你在准备阶段没有将这个目录复制到测试环境,可以在最终部署时再进行。' `9 _! H- n! i3 k& c1 Q5 B
将该目录下的每个文件的编码转换为 UTF-8,重新上传覆盖原文件即可。
! g9 c7 U/ ~8 |% D) [, M2 {
: v7 S/ W7 F) ?/ e; P" B& r% O2 c4 t3 E7. 更新缓存5 J6 V. g; I% c* k2 `; R

+ c4 u3 ?* D0 K# Z# W7 n) t- p登录后台,更新所有缓存(数据缓存、模板缓存、DIY模块分类缓存)。6 k( F6 y+ j# U6 x' r$ g0 d; P! B7 |
( ~9 T( V, t, g3 y7 G
8. 检查问题3 _$ q3 N; f' g: H* M% v

( C. S8 V9 k# A; P至此基本转换完成,需要仔细检查有无其他问题,重点检查插件、模板等是否工作正常。
! l- d: N5 p% C  C9 {; ^5 U3 \. n% O5 y1 y; j9 T, R: K
9. 在正式环境部署上线7 J6 j1 Z( G% V* @- {
5 L8 U  w, L9 [; q1 J( R
一定要先阅读下面的 FAQ 再决定开始部署。
3 A3 B; I, s$ \1 U9 M/ a" F, X5 c. W, ?$ Y6 \* M1 ^
将以上步骤在正式服务器上重新操作一遍。需要注意将 config 中的数据库改为正式数据库,内存缓存无需关闭,在第 7 步更新缓存时要把内存缓存清空。
. _0 p5 Z2 J* o  q" x4 t4 F  M9 y* Z; j* I6 l
F.A.Q.
3 w, t! \( O! r% C7 `. L9 X# _- o1 z2 ]( G  d
Q: 转换数据库后,登录验证问答无法通过4 ^5 `3 y4 G& Z5 ~# Y" i5 S2 ^5 ?
A: Discuz! 登录验证问答的加密算法为“substr(md5($answer.md5($questionid))”,结果与所用编码相关。可以参考这里修改代码,强制使用 GBK 来编码答案。4 H# A: d, P: _+ I
4 h* l' P0 Z. v' Y. v( H- h
Q: 转换模板后打开网站依旧乱码( ~2 h0 p, ^4 l& ]; O7 }) b  U8 C
A: 请确认已经在后台更新缓存,如果依旧乱码,请 SSH 到服务器,运行 sync 命令。如果还不行,可以尝试修改乱码的模板(比如随便改一个字符),上传服务器,Discuz! 检测到文件变动后会重新刷新模板缓存,然后再将模板还原后上传。
! U7 l) O6 g! g) v" O/ `  `% S
9 d1 d  I8 n2 t/ M% y. u: UQ: 站点统计内部分数据乱码! G7 g# R- s% c) w! O, E
A: 等到下一个更新时间数据刷新后就正常了
/ M2 w/ O' b8 s' S$ D5 d
! i6 p3 O% s3 H' _3 I" EQ: 上传模板后 DIY 模块消失  [# a1 n3 z3 a; m6 z7 ?: m
A: 到 data/diy/template/模板名 下面寻找 .bak 文件,重新 diy,选择恢复这个文件即可。" K  d' D; n& h7 P) T/ S

2 ?/ L) N3 w- u( J! DQ: 部分论坛设置、插件设置行为诡异或设置丢失
* l  a: @. i. ]8 V% PA: 很大可能是第 4 步修复数据库时,migrate_db.php 没有处理到相关数据表的字段。请仔细检查有无漏掉的数据表字段。; X7 V* c/ s; ?2 K
; q1 U6 E0 |& _+ t% o/ z
Q: 如何方便地批量转换编码?
5 Q  G6 ^, R9 l0 B: E+ jA: 在 Linux 环境可以使用 iconv 命令(请稍微学习一下这条命令,使用很方便)。在 Windows 下可以使用 Codepage Converter 这个工具(已在附件提供)。
: o, A9 {( C7 O; F) |  X

快速回帖 使用高级回帖 (可批量传图、还有插入视频等功能哦!)

您需要登录后才可以回帖 登录 | 注册

  • 发布信息免费
  • 发贴彩色标题
  • 签到额外经验值

如何快速提升等级,查看[积分规则]

活动中心

查看更多>>
最新热版
会员排行
©2009-2016 西班牙华人网 http://www.laicw.eu西班牙文化部注册管理西中文化传媒促进会主办Powered byDiscuz!X3"世界华文媒体合作联盟"成员 ||
发帖 客服 微信 手机版 举报