默认情况下,lftp mirror 命令不会下载 .file 这样的隐藏文件,需要打开相应的选项才行:
sh$ lftp $hostname
lftp> cd pub
lftp> set ftp:list-options -a
lftp> mirror src
星期五, 四月 27, 2007
星期一, 四月 16, 2007
df 和 du 输出不符 -- lsof +L1
在删除了大日志文件后,使用 df 发现分区快用尽了,但用 du 统计的结果却发现没有使用多少分区。这是因为文件虽然被删除了,但运行中的进程却仍然 link 到它们,所以磁盘空间实际上并没有释放。
可以使用 lsof +L1 来查看所有这样的文件。类似下面的输出:
如果重启服务不行,那就 kill 掉这些进程:
参考:
http://www.prefetch.net/blog/index.php/2006/01/10/where-is-my-space/
可以使用 lsof +L1 来查看所有这样的文件。类似下面的输出:
COMMAND PID USER FD TYPE DEVICE SIZE NLINK NODE NAME这里只是一个小文件,实际可能是一个很大的文件。+L1 标识 link counts 的上限为 1,所以就是 0。
httpd 10944 root 42u REG 253,0 0 0 491543 /tmp/ZCUD6duOXq (deleted)
httpd 11381 httpd 42u REG 253,0 0 0 491543 /tmp/ZCUD6duOXq (deleted)
httpd 11382 httpd 42u REG 253,0 0 0 491543 /tmp/ZCUD6duOXq (deleted)
httpd 11383 httpd 42u REG 253,0 0 0 491543 /tmp/ZCUD6duOXq (deleted)
httpd 11384 httpd 42u REG 253,0 0 0 491543 /tmp/ZCUD6duOXq (deleted)
...
如果重启服务不行,那就 kill 掉这些进程:
sh# lsof +L1 | awk '{print $2}' | sed -n '2,$p' | uniq | xargs kill所以最好还是先更改 httpd.conf 的 log 配置,重启 Apache 之后再移除旧日志。参考:
http://www.prefetch.net/blog/index.php/2006/01/10/where-is-my-space/
tar cfz onefile simultaneously by 2 processes
先看看同时打包同一个文件:
也说明两个包相同。
再看看对不同目录打包的情况:
#!/usr/bin/python这样做似乎还没有什么问题,两个进程都结束后用 tar tfz 看不出有问题。再这样看看:
import os,sys
dirname = os.path.dirname(os.path.abspath(sys.argv[0]))
os.chdir(dirname)
pid1 = os.fork()
if pid1 == 0:
os.system("tar cfz /tmp/sametar.tgz src")
sys.exit(0)
pid2 = os.fork()
if pid2 == 0:
os.system("tar cfz /tmp/sametar.tgz src")
sys.exit(0)
os.wait()
sh$ tar cfz /tmp/sametar1.tgz src
sh$ diff /tmp/sametar.tgz /tmp/sametar.tgz --brief
也说明两个包相同。
再看看对不同目录打包的情况:
#!/usr/bin/python这时候就暴露除问题了。这应该是一个进程资源互斥的问题。而且每次报告的出错情况可能还不一样:
import os,sys
dirname = os.path.dirname(os.path.abspath(sys.argv[0]))
os.chdir(dirname)
pid1 = os.fork()
if pid1 == 0:
os.system("tar cfz /tmp/sametar.tgz src")
sys.exit(0)
pid2 = os.fork()
if pid2 == 0:
os.system("tar cfz /tmp/sametar.tgz src_archive")
sys.exit(0)
os.wait()
sh$ tar tfz sametar.py
gzip: stdin: not in gzip format
tar: Child returned status 1
tar: Error exit delayed from previous errors
tar tfz /tmp/sametar.tgz
src_archive/
src_archive/file1
gzip: stdin: invalid compressed data--crc error
gzip: stdin: invalid compressed data--length error
tar: Unexpected EOF in archive
tar: Error is not recoverable: exiting now
星期一, 四月 02, 2007
sourceforge svn
现在需要使用 sourceforge 的 subversion,并将以前的版本库导入到里面。这涉及几个方面的问题,可以参考 sourceforge 的文档。
http://sourceforge.net/docs/E09
首先是需要启用 subversion。我的项目创建时默认使用的是 CVS,可以进入 "Admin"->"CVS" 禁止掉,在进入 "Admin"->"subversion" enable。
sourceforge svn 的 repos URL 是:
http://PROJECTNAME.svn.sourceforge.net/svnroot/PROJECTNAME
所以我的项目将是:
http://crablfs.svn.sourceforge.net/svnroot/crablfs
但是如果要写入,则需要使用 https。
先试试检出:
换用 subversion-1.4.3,neon 和 apr 都不再包括在源代码中了,只能自己编译。但似乎这次必须使用 apache(必须指定 apxs),即使使用 --disable-mod-activative,否则连 http scheme 都没有了。
不想为了一个 svn client 装一个 apache server,结果找了一个 1.3.2 解决这个问题,也是包含 neon 和 apr 的,
然后需要将以前的版本库导入。不可能直接使用 svn import 导入,因为需要保留以前的所有信息。可以参考:
http://sourceforge.net/docs/E09#import
的指导。大体上,就是先使用 svnadmin dump 得到当前版本库的备份,再利用 sourceforge 的机制导入。
然后进入 "Admin"->"Subversion"->"Migration Instructions"->"migrate"进入:
http://sourceforge.net/project/admin/svn_migration.php?group_id=180695
填写刚才的 .gz 文件并提交即可。
最后还有一个问题,就是备份。虽然 svn 版本库保存在网络上了,但是还是需要以防万一,且不说如果 sourceforge 本身出问题如何,如果出现象地震或 GFW 等问题导致不能连接,至少还可以使用本地拷贝,如果可能还可以使用前面的 migrate 方法重新导入。用如下方法备份:
其他一些问题:
如何查询某个特定版本与另一个特定版本相比修改了哪些文件?
目前不知道如何直接利用 svn 的命令来做到,但是可以使用 --diff-cmd -x 来调用 diff,从而可以得到一个简要清单:
http://sourceforge.net/docs/E09
首先是需要启用 subversion。我的项目创建时默认使用的是 CVS,可以进入 "Admin"->"CVS" 禁止掉,在进入 "Admin"->"subversion" enable。
sourceforge svn 的 repos URL 是:
http://PROJECTNAME.svn.sourceforge.net/svnroot/PROJECTNAME
所以我的项目将是:
http://crablfs.svn.sourceforge.net/svnroot/crablfs
但是如果要写入,则需要使用 https。
先试试检出:
sh$ svn co https://crablfs.svn.sourceforge.net/svnroot/crablfs要检查 svn 支持哪些 scheme,使用 svn --version 命令:
svn: Unrecognized URL scheme https
sh$ svn --version从 google search 的情况来看,必须添加 ssl 支持,而这个支持是由 neon 库来完成的。另外还需要 apr/apr-util。我之前使用的是 1.1.4 版,neon 和 apr 都包含在 source 里了,但编译添加 --with-ssl,或单独编译 neon-0.26.3 再在 svn ./configure 时添加参数 --with-neon 都无效。
...
he following repository access (RA) modules are available:
* ra_dav : Module for accessing a repository via WebDAV (DeltaV) protocol.
- handles 'http' scheme
* ra_svn : Module for accessing a repository using the svn network protocol.
- handles 'svn' scheme
* ra_local : Module for accessing a repository on local disk.
- handles 'file' scheme
换用 subversion-1.4.3,neon 和 apr 都不再包括在源代码中了,只能自己编译。但似乎这次必须使用 apache(必须指定 apxs),即使使用 --disable-mod-activative,否则连 http scheme 都没有了。
不想为了一个 svn client 装一个 apache server,结果找了一个 1.3.2 解决这个问题,也是包含 neon 和 apr 的,
The following repository access (RA) modules are available:添加 --with-ssl 编译。
* ra_dav : Module for accessing a repository via WebDAV (DeltaV) protocol.
- handles 'http' scheme
- handles 'https' scheme
* ra_svn : Module for accessing a repository using the svn network protocol.
- handles 'svn' scheme
* ra_local : Module for accessing a repository on local disk.
- handles 'file' scheme
然后需要将以前的版本库导入。不可能直接使用 svn import 导入,因为需要保留以前的所有信息。可以参考:
http://sourceforge.net/docs/E09#import
的指导。大体上,就是先使用 svnadmin dump 得到当前版本库的备份,再利用 sourceforge 的机制导入。
sh$ svnadmin dump /mnt/file/data/gears | gzip >/tmp/gears.gz这里 /home/groups/p/pr/project 就是相关文档的 DocumentRoot。
sh$ cp /tmp/gears.gz chowroc@crablfs.sourceforge.net:/home/groups/c/cr/crablfs/
然后进入 "Admin"->"Subversion"->"Migration Instructions"->"migrate"进入:
http://sourceforge.net/project/admin/svn_migration.php?group_id=180695
填写刚才的 .gz 文件并提交即可。
最后还有一个问题,就是备份。虽然 svn 版本库保存在网络上了,但是还是需要以防万一,且不说如果 sourceforge 本身出问题如何,如果出现象地震或 GFW 等问题导致不能连接,至少还可以使用本地拷贝,如果可能还可以使用前面的 migrate 方法重新导入。用如下方法备份:
sh$ mkdir gears注意需要使用 svn/crablfs/* 而不是 svn/crablfs,因为 svn/crablfs 实际上是到 /home/groups/c/cr/crablfs/svnroot 的一个符号链接。
sh$ cd gears
sh$ rsync -av crablfs.svn.sourceforge.net::svn/crablfs/* .
其他一些问题:
如何查询某个特定版本与另一个特定版本相比修改了哪些文件?
目前不知道如何直接利用 svn 的命令来做到,但是可以使用 --diff-cmd -x 来调用 diff,从而可以得到一个简要清单:
sh$ svn diff --diff-cmd -x --breif因此也可以利用这一点做一些其他形式的比较,比如我比较喜欢使用 diff 的 -y --suppress-common-lines:
sh$ svn diff --diff-cmd diff -x '-y --suppress-common-lines' utilsea/trunk/fs_backup | less
python try/except variable scope?
>>> try:所以在 try 中定义的变量在 except 中仍有效!
... testr = "still be effective in the except?"
... raise "exception"
... except:
... print testr
...
still be effective in the except?
然后看看下面这种情况:
>>> try:注意这里的 item,在 excpet 中仍然有效,只不过只是最后一个值。
... for item in ['A', 'B', 'C']:
... print item
... raise "exception"
... except:
... print item
...
A
B
C
C
再改成 finally:
>>> try:
... testr = "still be effective in the except?"
... raise "exception"
... finally:
... print testr
...
still be effective in the finally
Traceback (most recent call last):
File "", line 3, in ?
exception
python script suid
在较新的内核中,已经禁止了对 script 的 suid,只有二进制程序拥有 suid 权限:
因此在编写 cgi 脚本时需要考虑这一点,mailman 的 cgi 程序就都是二进制的程序(C 编译)。
#!/usr/bin/python可以看到,起作用的并不是 s 位,而仅仅是 x 位。其他 script 如 perl/php 亦同。
import os
print os.geteuid(), os.getegid()
-bash-3.00$ ls /usr/bin/passwd -l
-r-s--x--x 1 root root 21200 2005-06-17 /usr/bin/passwd
-bash-3.00$ ls test.py -l
-r-sr-xr-x 1 root root 62 Mar 26 17:43 test.py
-bash-3.00$ ./test.py
10001 10001
-rwsr--r-- 1 root root 66 Mar 30 17:59 test.py
-bash-3.00$ ./test.py
-bash: ./test.py: Permission denied
因此在编写 cgi 脚本时需要考虑这一点,mailman 的 cgi 程序就都是二进制的程序(C 编译)。
python unzip
先,企图利用 os.popen3("unzip ...") 直接来完成,但遇到问题:
改进:
http://aspn.activestate.com/ASPN/Cookbook/Python/Recipe/252508
http://www.thescripts.com/forum/thread25297.html
fin, fout, ferr = os.popen3("unzip -o -d %s %s" % (dest, zipfile))
strerr = ferr.read()
# 这一步挂起!
if strerr:
print >> sys.stderr, strerr
outlog.error(strerr)估计是 unzip 命令没有在 stderr 输出文件结束符 EOF。于是只能自己编写相关函数。如下:import zipfile但是这里没有是否覆盖的选项,所以改进方案如下。
def _extract_all(self, destdir):
namelist = self.namelist()
namelist.sort()
for name in namelist:
print "extracting... %s" % name
if name.endswith('/'):
print name
os.mkdir(os.path.join(destdir, name))
else:
outfile = open(os.path.join(destdir, name), 'wb')
outfile.write(self.read(name))
outfile.close()
zipfile.ZipFile.extract_all = _extract_all
def unzip(...):
zipo = zipfile.ZipFile(zipfn, 'r')
zipo.extract_all(dest)
改进:
import zipfile参考:
def _extract_all(self, destdir, overwrite=0):
namelist = self.namelist()
namelist.sort()
for name in namelist:
if os.path.exists(name) and not overwrite:
strerr = "destination %s exists" % name
print strerr
outlog.error(strerr)
break
print "extracting... %s" % name
if name.endswith('/'):
try:
os.mkdir(os.path.join(destdir, name))
except OSError:
pass
else:
outfile = open(os.path.join(destdir, name), 'wb')
outfile.write(self.read(name))
outfile.close()
zipfile.ZipFile.extract_all = _extract_all
def unzip(...overwrite=0):
zipo = zipfile.ZipFile(zipfn, 'r')
zipo.extract_all(dest, overwrite)
http://aspn.activestate.com/ASPN/Cookbook/Python/Recipe/252508
http://www.thescripts.com/forum/thread25297.html
星期四, 三月 29, 2007
bash redirect only stderr to pipe
sh$ cat test
#!/bin/sh
echo "testing 1"
echo "testing 2" >&2
sh$ bash test >/dev/null 2>&1
sh$ bash test 2>&1 >/dev/null
testing 2
星期二, 三月 27, 2007
从 txt2tags 进一步认识标记语句
最开始使用标记语句是从王垠介绍的 TeX/LaTeX 开始的,有很长一段时间我都在努力将文档转变成 TeX/LaTeX,但实际上还是比较麻烦的。从 TeX/LaTeX 的学习中,最大的收获是对标记语言的一个重要特性的认识:内容和形式分离。
感觉上,TeX/LaTeX 的标记设计得不是非常清楚,所以为了达到形式与内容分离,需要花费大量的精力,自己定义模板,而效果也不是十分理想;为了实现各种功能,可能需要选择大量新的标记和新的模块包(\usepackage),使本身已经陡峭的学习曲线更加让人生畏;而且为了使 TeX/LaTeX 适应中文也相当麻烦(基本上没有什么软件的中文化不麻烦的,我想现在的编码方式还是有问题)。
后来决定转移到 xml docbook。xml 的标记设计相当的标准,而且 docbook 在一开始就实现了形式与内容的分离。通过样式文件 XSL 来改变目标文档(html/PDF 等)的外观,而作者集中精力于编写的内容。
不过我现在却在使用 txt2tags(.t2t 文件),最主要的一个原因是:简单(KISS)。它的标记非常的简单和直观,从人的感观来说,和编辑普通的 txt 文件没有太大区别,因此具有很强的可读性。使用 XML 的好处的确很多,但其学习曲线也颇为陡峭,在企业当中的现实往往是,让人们去花费精力学习 XML,他们可能会宁可选择 Micro$oft Word。使用 .doc 的弊端是很明显的,那就是你没办法版本化,或者说版本化的意义不大(无法比较,无法查知在什么时候、谁做了哪些改动),因而你无法获得集中管理的优势,在多人协作中将造成巨大的重复成本,因为你没办法同步文档。而使用 t2t,最多只需要半个小时的学习就可以开始使用了(看看 sample,实际上几分钟就可以了,倒是设置编辑器的语法高亮花的时间还多一点)——当然,有问题的时候你还是需要去查查手册,一些比较高级的功能也是需要深入学习才能了解(不需要深入太多)。
当然 t2t 的简单也有其局限性,虽然它的确基本上实现了内容与形式分离(因为实在是很简单),但它的标记太少,不适合比较复杂的文档,另外它缺乏 footnote 和 xref(文档应用)以及索引等功能。而且,它也没有明确的部分、章、节的划分,只是一个层次结构而已。
所以,实际上我心里还是比较倾向于 XML,不过考虑到现在公司的实际情况,而且我还需要能够对 xml 的编辑和使用加深一些学习,比如设置 vim 编辑器等,所以 txt2tags 还是一个不错的选择。
目前来看,我只能是在将来再将现在用 t2t 编写的文档转变为 xml docbook(还得找或者写程序,t2t 默认只支持 SGML),而不可能同时使用这两套系统,并且一旦我转变为 XML,就不大有希望再试听 t2t 了。最主要的原因是 txt2tags <=> xml docbook 的标记之间是一个一对多的关系,即一个 txt2tags 标记在 xml docbook 可以多个标记来表示。如果编写 xml docbook 的人使用了 docbook 才有的特性,这些特性要么不能显示,要么干脆会丢失,因为使用 t2t 的人在提交和转换的时候会导致这些信息丢失。
除非我改变 t2t 的标记,在其中保留一些诸如"<"screen">""<"/screen">"的 XML 标记,而扩充的 txt2tags 在处理的时候能够自动忽略这些标记,或通过一个映射表将其转换为某种它能够处理的标记。不过重点还是在 XML,即后台时间实现自动化处理以转换其他文档的还是 XML 文档,即增加了一层,由
这样做的目的是一方面在最大程度上保持了 t2t 的简单性,同时在 t2t 无法达到要求的时候采用 xml。
关于映射表,参考 txt2tags 源代码(python),可以发现它实际上做了一个标记的映射,将 txt2tags 的标记和其他格式文档的标记进行 dict map。不过它这个映射表是写在代码里面的,这使我考虑是否能将其写在外部,作为一种 schema 而存在。这样不仅能实现上面的转换要求,而且可以实现一些比如自定义标签的功能。
自定义标签?比如假设我已经编写了一个脚本可以处理这些 schema,并且可以做转换,那么我可能会使用如下的命令:
那么一个 schema 可能的形式如下:
感觉上,TeX/LaTeX 的标记设计得不是非常清楚,所以为了达到形式与内容分离,需要花费大量的精力,自己定义模板,而效果也不是十分理想;为了实现各种功能,可能需要选择大量新的标记和新的模块包(\usepackage),使本身已经陡峭的学习曲线更加让人生畏;而且为了使 TeX/LaTeX 适应中文也相当麻烦(基本上没有什么软件的中文化不麻烦的,我想现在的编码方式还是有问题)。
后来决定转移到 xml docbook。xml 的标记设计相当的标准,而且 docbook 在一开始就实现了形式与内容的分离。通过样式文件 XSL 来改变目标文档(html/PDF 等)的外观,而作者集中精力于编写的内容。
不过我现在却在使用 txt2tags(.t2t 文件),最主要的一个原因是:简单(KISS)。它的标记非常的简单和直观,从人的感观来说,和编辑普通的 txt 文件没有太大区别,因此具有很强的可读性。使用 XML 的好处的确很多,但其学习曲线也颇为陡峭,在企业当中的现实往往是,让人们去花费精力学习 XML,他们可能会宁可选择 Micro$oft Word。使用 .doc 的弊端是很明显的,那就是你没办法版本化,或者说版本化的意义不大(无法比较,无法查知在什么时候、谁做了哪些改动),因而你无法获得集中管理的优势,在多人协作中将造成巨大的重复成本,因为你没办法同步文档。而使用 t2t,最多只需要半个小时的学习就可以开始使用了(看看 sample,实际上几分钟就可以了,倒是设置编辑器的语法高亮花的时间还多一点)——当然,有问题的时候你还是需要去查查手册,一些比较高级的功能也是需要深入学习才能了解(不需要深入太多)。
当然 t2t 的简单也有其局限性,虽然它的确基本上实现了内容与形式分离(因为实在是很简单),但它的标记太少,不适合比较复杂的文档,另外它缺乏 footnote 和 xref(文档应用)以及索引等功能。而且,它也没有明确的部分、章、节的划分,只是一个层次结构而已。
所以,实际上我心里还是比较倾向于 XML,不过考虑到现在公司的实际情况,而且我还需要能够对 xml 的编辑和使用加深一些学习,比如设置 vim 编辑器等,所以 txt2tags 还是一个不错的选择。
目前来看,我只能是在将来再将现在用 t2t 编写的文档转变为 xml docbook(还得找或者写程序,t2t 默认只支持 SGML),而不可能同时使用这两套系统,并且一旦我转变为 XML,就不大有希望再试听 t2t 了。最主要的原因是 txt2tags <=> xml docbook 的标记之间是一个一对多的关系,即一个 txt2tags 标记在 xml docbook 可以多个标记来表示。如果编写 xml docbook 的人使用了 docbook 才有的特性,这些特性要么不能显示,要么干脆会丢失,因为使用 t2t 的人在提交和转换的时候会导致这些信息丢失。
除非我改变 t2t 的标记,在其中保留一些诸如"<"screen">""<"/screen">"的 XML 标记,而扩充的 txt2tags 在处理的时候能够自动忽略这些标记,或通过一个映射表将其转换为某种它能够处理的标记。不过重点还是在 XML,即后台时间实现自动化处理以转换其他文档的还是 XML 文档,即增加了一层,由
txt2tags --> html/pdf/tex变为
txt2tags --> xml docbook --> html/pdf/tex。但是所有人仍然必须编辑 t2t 文件而不是同时编辑 t2t 和 xml 文件,否则是无法同步的。
这样做的目的是一方面在最大程度上保持了 t2t 的简单性,同时在 t2t 无法达到要求的时候采用 xml。
关于映射表,参考 txt2tags 源代码(python),可以发现它实际上做了一个标记的映射,将 txt2tags 的标记和其他格式文档的标记进行 dict map。不过它这个映射表是写在代码里面的,这使我考虑是否能将其写在外部,作为一种 schema 而存在。这样不仅能实现上面的转换要求,而且可以实现一些比如自定义标签的功能。
自定义标签?比如假设我已经编写了一个脚本可以处理这些 schema,并且可以做转换,那么我可能会使用如下的命令:
sh$ ctags schema text.t2t >text...当然还可以使用 html 等,不过我觉得不太好,因为既然 xml 最标准,那么为什么还要其他的呢?直接利用 xml 的威力就好了。并且对同一个 xml 文档,我还可以通过使用不同的映射关系来实现一些差别化的功能...
例如 xml 文件:
sh$ ctags xml.schema text.t2t >text.xml
那么一个 schema 可能的形式如下:
xml_tag_name, src_tag_start, src_tag_end, dst_tag_start, dst_tag_end如
verbatim, ``, ``, "<"verbatim">", "<"/verbatim">"
星期五, 三月 23, 2007
txt2tags and its vim highlight
安装很简单,将解压包里的 txt2tags 拷贝到 /usr/local/bin 即可。
为了在编辑器中实现语法高亮,必须做一些调整。对 vim,需要将 syntax highlighting file 拷贝到系统中,如果是 root 用户,可以将 extras/txt2tags.vim 拷贝到诸如 /usr/share/vim/vim63/syntax/,普通用户可以拷贝到 ~/.vim/syntax。在编辑时使用 :set syntax=txt2tags 即可实现 txt2tags 语法高亮。
但为了自动实现,可以在 /usr/share/vim/vim63/filetype.vim 中
普通用户可以直接在 ~/.vimrc 中加入:
关于 filetype 的说明也可以在 extras/txt2tags.vim 的 INSTALL 一节找到。
关于其他编辑器,目前没有研究的结果。
为了在编辑器中实现语法高亮,必须做一些调整。对 vim,需要将 syntax highlighting file 拷贝到系统中,如果是 root 用户,可以将 extras/txt2tags.vim 拷贝到诸如 /usr/share/vim/vim63/syntax/,普通用户可以拷贝到 ~/.vim/syntax。在编辑时使用 :set syntax=txt2tags 即可实现 txt2tags 语法高亮。
但为了自动实现,可以在 /usr/share/vim/vim63/filetype.vim 中
" Z-Shell script后面加上两行:
au BufNewFile,BufRead zsh*,zlog* setf zsh
" txt2tags file注意在 .vim 文件中 " 表示注释。
au BufNewFile,BufRead *.t2t setf txt2tags
普通用户可以直接在 ~/.vimrc 中加入:
au BufNewFile,BufRead *.t2t set ft=txt2tags
关于 filetype 的说明也可以在 extras/txt2tags.vim 的 INSTALL 一节找到。
~/.vim/syntax
~/.vimrc(normal user)
au BufNewFile,BufRead *.t2t set ft=txt2tags
" INSTALL: (as superuser)
"
" If you have access to the system configuration, edit the
" /usr/share/vim/vim*/filetype.vim file, adding the following
" lines after the 'Z-Shell script' entry (near the end):
"
" " txt2tags file
" au BufNewFile,BufRead *.t2t setf txt2tags
"
" And copy this file (txt2tags.vim) to the Vim syntax dir:
"
" /usr/share/vim/vim*/syntax/
关于其他编辑器,目前没有研究的结果。
AA Center (2), openldap for centrialized login
在前面说明 Kerberos 的时候,已经说明的使用 openldap 的必要性,也就是要集中用户信息,来实现集中登录。这样我不需要在每一个主机上单独维护用户信息了。
openldap 标准的文档在:
http://www.openldap.org/doc/admin23/
应该先阅读这个文档,我这里只说明一些比较特殊不好理解的地方,特别是这个文档中没有说清楚的问题。以及利用基本的知识建立集中用户信息的方法。
有一个中文版:
http://www.infosecurity.org.cn/article/pki/ldap/23484.html
首先来看看 LDAP 的基本原理。LDAP(Lightweight Directory Access Protocol),轻型目录访问协议,从用户的角度来说,可以看成是对一个树形结构的数据库的访问协议,也就是目录服务。
数据模型:
在这个树形结构中,每一个节点是以条目(Entry)来表示的,这相当于 XML 中的 Element。每一个 Entry 最基本的信息就是 DN(Distinguished Name)和RDN(Relative Distinguished Name),用来表示这个节点,类似于相对路径和绝对路径的概念。
每一个 Entry 是一组属性(Attribute)的集合,每一个 Attribute 包含 Value 以及相应的 Type 和 ObjectClass 说明。
ObjectClass 是面向对象的概念,因此每一个 Entry 可以看作一个 Class 的实例(Instance)。而这个 Class 的定义会说明这种类型的 Entry 必须(MUST)包含哪些属性,可能(MAY)包含哪些属性等。Type 的定义与之类似。
RFC2551
每一个 Entry 必须包含至少一个 ObjectClass 声明。
那么这些 ObjectClass 和 AttributeType 的声明在什么地方呢?一般都放在 Schema 中。Schema 一般都以文件的形式而存在,例如 /usr/local/etc/openldap/schema,因此与 DocBook 的 DTD 就有些相似了。
可以看一个 Entry 的例子:
事实上,这些东西都是 AttributeType,在 RFC2253 中,你可以看到如下的说明:
前面已经说过,ObjectClass 和 AttributeType 都是有定义的,定义在 schema 中。那么对这些 AttributeType 的定义就在 /usr/local/etc/openldap/schema/core.shema 中。所以,可以看到,虽然 O,OU,C,CN,DC,UID 这些是很基础的属性类型,也仍然是由外部来定义的。注意:dn 不是由 schema 定义的。
所以在上面那个 Entry 的例子中,除了 objectClass 声明之外,其他都是 Attribute Type 声明,其实质是相同的,所以 cn, uid 与 uidNumber, userPassword 是一样的,只不过那些属性类型的声明不再 core.schema 中,而在 /usr/local/etc/openldap/schema/nis.schema。
上面的 Entry 是有格式的。按照这个格式编写的文件就称之为 LDIF(LDAP Data Interchange Format)文件。那么 ldif 又如何知道要用哪个 schema 的呢?
这在 slapd.conf 中定义。slapd 是 ldap 的服务守护进程。
用 LDAP 集中登录(Kerberos):
就目 前我所知之,利用 LDAP 集中用户信息以实现登录有两种方案,一是利用 pam_ldap 来实现认证,另一种是利用 Kerberos 替代 pam_ldap 来做认证,而用户信息存放在 LDAP 数据库中。无论采取那种形式,都必须用到 nss_ldap 库,从而可以在 /etc/nsswitch.conf 中增加对 ldap 的使用选项。
配置服务器,修改 slapd.conf,将 suffix 和 rootdn 都改成你自己的域,如下:
然后启动服务:
可以在 http://www.padl.com/download/MigrationTools.tgz 下载最新的版本。然后来看看怎么做:
如果要迁移 root 用户,还有其他一些重要的问题需要考虑。
如果没有问题,那么应该是如下的输出:
从 PuTTY 登录的情况来看:
而
尝试先从 Kerberos 取得票据:
再看看以其他用户的身份会是什么情况:
注意上面的 FILE:/tmp/krb5cc_501, 可以发现是以用户的 UID 来命名的。
然后看看增加一个 Kerberos 用户 roc,并从这个用户登录到 rocky 是否可行:
方案比较,以及为什么选择 Kerberos:
前面说过,除了使用 Kerberos 的 pam_krb5 来进行 Authentication(这也是上一篇中使用的方法)之外,另一种选择是使用 pam_ldap。看起来,如果使用 pam_ldap 似乎要简单的多,因为只使用一套软件就解决问题了。其实不然。因为这是在做身份验证,所以安全性是非常重要的问题,那么加密就必不可少,而 openldap 默认是使用明文加密的。可以看下面这个例子:
Kerberos 默认是加密的,而 openldap 要实现加密则必须使用 SSL/TLS,这也就意味着你必须为每一台客户系统维护一对私钥/证书,在这里也可以看到 Kerberos 的一个好处,那就是票据的加密是由 Kerberos 自动维护的。这并不是说就不再需要 SSL/TLS 了,不过在认证这一块,Kerberos 确实更方便。
而且,你不再需要频繁的输入密码了!
所以这里最终的效果就是,openldap 充当了 /etc/passwd 的角色,而 Kerberos 相当于 /etc/shadow。
openldap 标准的文档在:
http://www.openldap.org/doc/admin23/
应该先阅读这个文档,我这里只说明一些比较特殊不好理解的地方,特别是这个文档中没有说清楚的问题。以及利用基本的知识建立集中用户信息的方法。
有一个中文版:
http://www.infosecurity.org.cn/article/pki/ldap/23484.html
首先来看看 LDAP 的基本原理。LDAP(Lightweight Directory Access Protocol),轻型目录访问协议,从用户的角度来说,可以看成是对一个树形结构的数据库的访问协议,也就是目录服务。
数据模型:
在这个树形结构中,每一个节点是以条目(Entry)来表示的,这相当于 XML 中的 Element。每一个 Entry 最基本的信息就是 DN(Distinguished Name)和RDN(Relative Distinguished Name),用来表示这个节点,类似于相对路径和绝对路径的概念。
每一个 Entry 是一组属性(Attribute)的集合,每一个 Attribute 包含 Value 以及相应的 Type 和 ObjectClass 说明。
ObjectClass 是面向对象的概念,因此每一个 Entry 可以看作一个 Class 的实例(Instance)。而这个 Class 的定义会说明这种类型的 Entry 必须(MUST)包含哪些属性,可能(MAY)包含哪些属性等。Type 的定义与之类似。
RFC2551
Each entry MUST have an objectClass attribute. The objectClass
attribute specifies the object classes of an entry, which along with
the system and user schema determine the permitted attributes of an
entry. Values of this attribute may be modified by clients, but the
objectClass attribute cannot be removed. Servers may restrict the
modifications of this attribute to prevent the basic structural class
of the entry from being changed (e.g. one cannot change a person into
a country).
每一个 Entry 必须包含至少一个 ObjectClass 声明。
那么这些 ObjectClass 和 AttributeType 的声明在什么地方呢?一般都放在 Schema 中。Schema 一般都以文件的形式而存在,例如 /usr/local/etc/openldap/schema,因此与 DocBook 的 DTD 就有些相似了。
可以看一个 Entry 的例子:
dn: uid=rocky,ou=People,dc=shopex,dc=cndn 就是前面说的 DN,那么其他那些 uid,o,ou,dc,cn,st,... 等又是表示什么含义呢?随便找一些 LDAP 的技术资料,都会给你一些如上的例子,其中有很多 o,ou,dc,cn 之类的东西,但几乎从来没有什么通俗点的文档解释过这些东西的来历。我怎么知道什么时候要使用那一个呢?
uid: rocky
cn: rocky
objectClass: account
objectClass: posixAccount
objectClass: top
objectClass: shadowAccount
userPassword: {crypt}$1$Kk00o2L8$fKM7c./FLiobXS4I.ktHU1
shadowLastChange: 13524
shadowMax: 99999
shadowWarning: 7
loginShell: /bin/bash
uidNumber: 1000
gidNumber: 1000
homeDirectory: /home/rocky
gecos: rocky
事实上,这些东西都是 AttributeType,在 RFC2253 中,你可以看到如下的说明:
String X.500 AttributeType
------------------------------
CN commonName
L localityName
ST stateOrProvinceName
O organizationName
OU organizationalUnitName
C countryName
STREET streetAddress
DC domainComponent
UID userid
前面已经说过,ObjectClass 和 AttributeType 都是有定义的,定义在 schema 中。那么对这些 AttributeType 的定义就在 /usr/local/etc/openldap/schema/core.shema 中。所以,可以看到,虽然 O,OU,C,CN,DC,UID 这些是很基础的属性类型,也仍然是由外部来定义的。注意:dn 不是由 schema 定义的。
所以在上面那个 Entry 的例子中,除了 objectClass 声明之外,其他都是 Attribute Type 声明,其实质是相同的,所以 cn, uid 与 uidNumber, userPassword 是一样的,只不过那些属性类型的声明不再 core.schema 中,而在 /usr/local/etc/openldap/schema/nis.schema。
上面的 Entry 是有格式的。按照这个格式编写的文件就称之为 LDIF(LDAP Data Interchange Format)文件。那么 ldif 又如何知道要用哪个 schema 的呢?
这在 slapd.conf 中定义。slapd 是 ldap 的服务守护进程。
sh# vi /usr/local/etc/openldap/slapd.conf
include /Opt/LDAP/etc/openldap/schema/nis.schema
用 LDAP 集中登录(Kerberos):
就目 前我所知之,利用 LDAP 集中用户信息以实现登录有两种方案,一是利用 pam_ldap 来实现认证,另一种是利用 Kerberos 替代 pam_ldap 来做认证,而用户信息存放在 LDAP 数据库中。无论采取那种形式,都必须用到 nss_ldap 库,从而可以在 /etc/nsswitch.conf 中增加对 ldap 的使用选项。
配置服务器,修改 slapd.conf,将 suffix 和 rootdn 都改成你自己的域,如下:
sh# slappasswd这样,openldap 将以 cn=ldampadmin,dc=shopex,dc=cn 作为你实际的顶级域。rootpw 是服务器密码,是可以通过网络来访问的,默认是明文,所以上面使用 slappasswd 来生成加密串,一旦完成配置,应该注释禁用该条目。openldap 默认使用明文传送密码,除非在 slapd.conf 中配置使用了 SSL/TSL(Transaction Layer Security)。
{SSHA}ck65VXczIGUsE/EOCYdF8qxwBCf73di7
sh# vi /usr/local/etc/openldap/slapd.conf
# suffix "dc=my-domain,dc=com"
suffix "dc=shopex,dc=cn"
# rootdn "cn=Manager,dc=my-domain,dc=com"
rootdn "cn=ldapadmin,dc=shopex,dc=org"
# rootpw secret
rootpw {SSHA}ck65VXczIGUsE/EOCYdF8qxwBCf73di7
然后启动服务:
sh# /usr/local/libexec/slapd在继续之前,先看看有没有问题,运行如下命令:
或
sh# /usr/local/libexec/slapd -f /usr/local/etc/openldap/slapd.conf
sh# ldapsearch -x -b '' -s base '(objectclass=*)' namingContexts然后我需要在 LDAP 的数据库中添加用户信息,这可以通过编写 LDIF 文件,然后用 ldapadd 工具来导入。前面的 Entry 例子即是这样一个包含完整用户信息的一个 LDIF 文件。但如果要将现有的用户信息迁移到 LDAP,那么可以使用一个称之为 MigrationTools 的工具;可能你不太属性这个 LDIF 应该怎么手工编写,那么也可以利用这个工具先生成一个模板,再在那个基础上进行修改。
# extended LDIF
#
# LDAPv3
# base <> with scope baseObject
# filter: (objectclass=*)
# requesting: namingContexts
#
#
dn:
namingContexts: dc=shopex,dc=org
# search result
search: 2
result: 0 Success
# numResponses: 2
# numEntries: 1
可以在 http://www.padl.com/download/MigrationTools.tgz 下载最新的版本。然后来看看怎么做:
sh# cd MigrationTools-47/然后修改这几个文件,特别是 passwd.ldif 和 group.ldif,因为这里我们之做实验,不做实际的迁移,所以我们将上面 Entry 例子中的内容照搬过来,其 他的条目删除——注意,在做实际迁移的时候,因为迁移后很多用户比如 root 不再使用本地 /etc/passwd 中的信息,所以如果中间出错,有可能导致无法登录,所以如果要迁移 root 等重要用户,应该保证有一个 root 登录会话,并且在测试成功之前不要注销!
sh# vi migrate_common.ph
$DEFAULT_BASE = "dc=shopex,dc=cn"
sh# ./migrate_base.pl >/tmp/base.ldif
sh# ./migrate_group.pl /etc/group /tmp/group.ldif
sh# ./migrate_hosts.pl /etc/hosts /tmp/hosts.ldif
sh# ./migrate_passwd.pl /etc/passwd /tmp/passwd.ldif
如果要迁移 root 用户,还有其他一些重要的问题需要考虑。
sh# ldapadd -x -h localhost -D "cn=ldapadmin,dc=shopex,dc=org" -w "secret" -f passwd.ldif出现这个错误就是和上面说的那样,应该将 nis.schema 包含进来。
adding new entry "uid=rocky,ou=People,dc=shopex,dc=cn"
ldap_add: Invalid syntax (21)
additional info: objectClass: value #0 invalid per syntax
sh# vi /usr/local/etc/openldap/slapd.conf这是因为还 nis.schema 还依赖于另一个 schema,consine.schema
include /usr/local/etc/openldap/schema/core.schema
include /usr/local/etc/openldap/schema/nis.schema
sh# killall -HUP slapd
# /usr/local/libexec/slapd -f /usr/local/etc/openldap/slapd.conf
/usr/local/etc/openldap/schema/nis.schema: line 203: AttributeType not found: "manager"
sh# vi /usr/local/etc/openldap/slapd.conf我不太清楚为什么使用加密后的密码不行,所以还是只好先使用了默认的那个密码。
include /usr/local/etc/openldap/schema/core.schema
include /usr/local/etc/openldap/schema/cosine.schema
include /usr/local/etc/openldap/schema/nis.schema
sh# ldapadd -x -h localhost -D "cn=ldapadmin,dc=shoepx,dc=org" -f passwd.ldif -w "{SSHA}ck65VXczIGUsE/EOCYdF8qxwBCf73di7"
ldap_bind: Invalid credentials (49)如果你在导入时发现如下错误:sh# /usr/local/libexec/slapd -f /usr/local/etc/openldap/slapd.conf那么你应该首先检查 slapd.conf 文件的配置是使用了正确的域,和 migrate_common.ph 中应该是一样的。这里是
sh# ldapadd -x -h localhost -D "cn=ldapadmin,dc=shopex,dc=org" -w "secret" -f passwd.ldif
adding new entry "uid=rocky,ou=People,dc=shopex,dc=cn"
ldap_add: Server is unwilling to perform (53)
additional info: no global superior knowledge
rootdn "cn=ldapadmin,dc=shopex,dc=org"写错了!如果没有问题,那么应该是如下的输出:
adding new entry "uid=rocky,ou=People,dc=shopex,dc=cn"接着配置各个客户端。你应该已经安装 Kerberos 的方法配置了 PAM 认证,所以不需要再做改动,唯一需要更改的就是 /etc/nsswitch.conf 了:
adding new entry "cn=rocky,ou=Group,dc=shopex,dc=cn"
passwd: files ldap注意,和前面配置 Kerberos 认证时一样,rocky 这个帐户并不存在与本地的 /etc/passwd 文件中,现在只有在 LDAP 数据库中有他的信息,并且 Kerberos 中有其相应的 Client principal。
shadow: files ldap
group: files ldap
从 PuTTY 登录的情况来看:
login as: rocky那是不是说我实际上不需要 Kerberos 呢?因为几乎所有的信息都在 LDAP 数据库中。
rocky@192.168.0.98's password:
Last login: Tue Mar 20 13:23:46 2007 from 192.168.0.64
Could not chdir to home directory /home/rocky: No such file or directory
-bash-3.00$
sh# tail -f /var/log/message
Mar 21 09:37:53 docs sshd(pam_unix)[3913]: authentication failure; logname= uid=0 euid=0 tty=ssh ruser= rhost=192.168.0.64 user=rocky
Mar 21 09:37:53 docs sshd[3913]: pam_krb5[3913]: The "hosts" configuration directive is not supported with your release of Kerberos. Please check if your release supports an `extra_addresses' directive instead.
Mar 21 09:37:53 docs sshd[3913]: pam_krb5[3913]: authentication succeeds for 'rocky' (rocky@SHOPEX.CN)
Mar 21 09:37:53 docs sshd(pam_unix)[3915]: session opened for user rocky by (uid=0)
sh# tail -f /var/log/krb5kdc.log
Mar 21 09:37:53 docs.shopex.cn krb5kdc[23244](info): AS_REQ (7 etypes {18 17 16 23 1 3 2}) 192.168.0.98: ISSUE: authtime 1174484273, etypes {rep=16 tkt=23 ses=16}, rocky@SHOPEX.CN for krbtgt/SHOPEX.CN@SHOPEX.CN
Mar 21 09:37:53 docs.shopex.cn krb5kdc[23244](info): AS_REQ (7 etypes {18 17 16 23 1 3 2}) 192.168.0.98: ISSUE: authtime 1174484273, etypes {rep=16 tkt=23 ses=16}, rocky@SHOPEX.CN for krbtgt/SHOPEX.CN@SHOPEX.CN
而
sh# /etc/init.d/krb5kdc stop后再尝试登录,则 /var/log/messages 输出如下:
这说明 Kerberos 的验证确实在起作用。而且 LDAP 中的 userPassword 和 Kerberos 的 rocky 用户的 Password 实际上是不一样的。
Mar 21 09:42:05 docs sshd(pam_unix)[3972]: authentication failure; logname= uid=0 euid=0 tty=ssh ruser= rhost=192.168.0.64 user=rocky
Mar 21 09:42:05 docs sshd[3972]: pam_krb5[3972]: The "hosts" configuration directive is not supported with your release of Kerberos. Please check if your release supports an `extra_addresses' directive instead.
Mar 21 09:42:05 docs sshd[3972]: pam_krb5[3972]: authentication fails for 'rocky' (rocky@SHOPEX.CN): Authentication service cannot retrieve authentication info. (Cannot contact any KDC for requested realm)
尝试先从 Kerberos 取得票据:
sh# kinit rocky可见,使用 kinit 取得票据之后,登录就不会再有密码提示了。
sh# ssh rocky@docs.shopex.cn
Last login: Wed Mar 21 09:56:11 2007 from docs.shopex.cn
Could not chdir to home directory /home/rocky: No such file or directory
-bash-3.00$ id
uid=1000(rocky) gid=1000(rocky) groups=1000(rocky)
sh# tail -f /var/log/messages
Mar 21 09:56:57 docs sshd(pam_unix)[4129]: session opened for user rocky by (uid=0)
[root@docs ~]# su - rocky也没有问题。
su: warning: cannot change directory to /home/rocky: No such file or directory
-bash-3.00$
再看看以其他用户的身份会是什么情况:
sh# su - sysadm
sh$ ssh rocky@docs.shopex.cn
The authenticity of host 'docs.shopex.cn (192.168.0.98)' can't be established.
RSA key fingerprint is 82:25:6e:1f:8e:70:dc:66:62:3e:7b:4c:f0:40:3e:4c.
Are you sure you want to continue connecting (yes/no)? yes
Warning: Permanently added 'docs.shopex.cn,192.168.0.98' (RSA) to the list of known hosts.
rocky@docs.shopex.cn's password:
Last login: Wed Mar 21 09:56:57 2007 from docs.shopex.cn
Could not chdir to home directory /home/rocky: No such file or directory
-bash-3.00$
/var/log/messages
Mar 21 09:57:33 docs su(pam_unix)[4148]: session opened for user sysadm by root(uid=0)
Mar 21 09:57:44 docs sshd(pam_unix)[4174]: authentication failure; logname= uid=0 euid=0 tty=ssh ruser= rhost=docs.shopex.cn user=rocky
Mar 21 09:57:44 docs sshd[4174]: pam_krb5[4174]: The "hosts" configuration directive is not supported with your release of Kerberos. Please check if your release supports an `extra_addresses' directive instead.
Mar 21 09:57:44 docs sshd[4174]: pam_krb5[4174]: authentication succeeds for 'rocky' (rocky@SHOPEX.CN)
Mar 21 09:57:44 docs sshd(pam_unix)[4176]: session opened for user rocky by (uid=0)
sh# su - sysadm
sh$ kinit rocky
Password for rocky@SHOPEX.CN:
sh$ klist
Ticket cache: FILE:/tmp/krb5cc_501
Default principal: rocky@SHOPEX.CN
Valid starting Expires Service principal
03/21/07 09:59:52 03/22/07 09:59:52 krbtgt/SHOPEX.CN@SHOPEX.CN
Kerberos 4 ticket cache: /tmp/tkt501
klist: You have no tickets cached
sh$ ssh rocky@docs.shopex.cn
Last login: Wed Mar 21 09:57:44 2007 from docs.shopex.cn
Could not chdir to home directory /home/rocky: No such file or directory
-bash-3.00$
/var/log/messages
Mar 21 10:00:32 docs sshd(pam_unix)[4234]: session opened for user rocky by (uid=0)
Mar 21 10:18:44 docs su[4629]: nss_ldap: reconnecting to LDAP server...
Mar 21 10:18:44 docs su[4629]: nss_ldap: reconnected to LDAP server after 1 attempt(s)
注意上面的 FILE:/tmp/krb5cc_501, 可以发现是以用户的 UID 来命名的。
然后看看增加一个 Kerberos 用户 roc,并从这个用户登录到 rocky 是否可行:
sh# kadmin -p rocky/admin@SHOPEX.CN这说明 Kerberos 的 User principal 也还是必须和 LDAP 的 User infomation 互相匹配,否则仍然是不能登录的。
Authenticating as principal rocky/admin@SHOPEX.CN with password.
Password for rocky/admin@SHOPEX.CN:
kadmin: addprinc roc
WARNING: no policy specified for roc@SHOPEX.CN; defaulting to no policy
Enter password for principal "roc@SHOPEX.CN":
Re-enter password for principal "roc@SHOPEX.CN":
Principal "roc@SHOPEX.CN" created.
kadmin: quit
sh# kinit roc
Password for roc@SHOPEX.CN:
sh# klist
Ticket cache: FILE:/tmp/krb5cc_0
Default principal: roc@SHOPEX.CN
Valid starting Expires Service principal
03/21/07 10:16:05 03/22/07 10:16:05 krbtgt/SHOPEX.CN@SHOPEX.CN
Kerberos 4 ticket cache: /tmp/tkt0
klist: You have no tickets cached
sh# ssh rocky@docs.shopex.cn
rocky@docs.shopex.cn's password:
Last login: Wed Mar 21 10:19:32 2007 from docs.shopex.cn
Could not chdir to home directory /home/rocky: No such file or directory
-bash-3.00$
Mar 21 10:20:46 docs sshd(pam_unix)[4745]: authentication failure; logname= uid=0 euid=0 tty=ssh ruser= rhost=docs.shopex.cn user=rocky
Mar 21 10:20:46 docs sshd[4745]: pam_krb5[4745]: The "hosts" configuration directive is not supported with your release of Kerberos. Please check if your release supports an `extra_addresses' directive instead.
Mar 21 10:20:46 docs sshd[4745]: pam_krb5[4745]: authentication succeeds for 'rocky' (rocky@SHOPEX.CN)
Mar 21 10:20:46 docs sshd(pam_unix)[4747]: session opened for user rocky by (uid=0)
方案比较,以及为什么选择 Kerberos:
前面说过,除了使用 Kerberos 的 pam_krb5 来进行 Authentication(这也是上一篇中使用的方法)之外,另一种选择是使用 pam_ldap。看起来,如果使用 pam_ldap 似乎要简单的多,因为只使用一套软件就解决问题了。其实不然。因为这是在做身份验证,所以安全性是非常重要的问题,那么加密就必不可少,而 openldap 默认是使用明文加密的。可以看下面这个例子:
sh# ldapsearch -x -b 'uid=rocky,ou=People,dc=shopex,dc=cn'这里可以看到,其他的用户信息无所谓,但 userPassword 是可以毫无障碍的被任何人查询的,如果密码确实存放在 LDAP 中,那就危险了。
# extended LDIF
#
# LDAPv3
# basewith scope subtree
# filter: (objectclass=*)
# requesting: ALL
#
# rocky, People, shopex.cn
dn: uid=rocky,ou=People,dc=shopex,dc=cn
uid: rocky
cn: rocky
objectClass: account
objectClass: posixAccount
objectClass: top
objectClass: shadowAccount
userPassword:: e2NyeXB0fSQxJEtrMDBvMkw4JGZLTTdjLi9GTGlvYlhTNEkua3RIVTE=
shadowLastChange: 13524
shadowMax: 99999
shadowWarning: 7
loginShell: /bin/bash
uidNumber: 1000
gidNumber: 1000
homeDirectory: /home/rocky
gecos: rocky
# search result
search: 2
result: 0 Success
# numResponses: 2
# numEntries: 1
Kerberos 默认是加密的,而 openldap 要实现加密则必须使用 SSL/TLS,这也就意味着你必须为每一台客户系统维护一对私钥/证书,在这里也可以看到 Kerberos 的一个好处,那就是票据的加密是由 Kerberos 自动维护的。这并不是说就不再需要 SSL/TLS 了,不过在认证这一块,Kerberos 确实更方便。
而且,你不再需要频繁的输入密码了!
所以这里最终的效果就是,openldap 充当了 /etc/passwd 的角色,而 Kerberos 相当于 /etc/shadow。
/---------->KDC
| /------KDC
(1) |
| (2)
| |
| V
Client------(3)------>Server(4)------(5)------>LDAP
(4) Lookup /etc/passwd and /etc/nsswitch.conf
(5) Lookup LDAP Database for account information(NOT Password)
订阅:
博文 (Atom)