LINUXQQ

八月 29, 2011

django 全局变量

Filed under: python — admin @ 10:07 上午

首先,request对象并不是自动作为可用的 Context 变量的。在 global_settings.py 中有一段 Context 处理器的定义:

# List of processors used by RequestContext to populate the context.
# Each one should be a callable that takes the request object as its
# only parameter and returns a dictionary to add to the context.
TEMPLATE_CONTEXT_PROCESSORS = (
    ‘django.core.context_processors.auth’,
    ‘django.core.context_processors.debug’,
    ‘django.core.context_processors.i18n’,
#    ‘django.core.context_processors.request’,
)

注意,这个Context处理器的配置只对RequestContext生效。request并不是缺省可用的。那么我现在就是需要增加一个自定义的SiteInfo处理器即可。

这个SiteInfo处理器很简单:

from apps.site.models import BlogSite

def siteinfo(request):
    sites = BlogSite.objects.all()
    if len(sites) > 0:
        site = sites[0]
    else:
        site = None
    return {’site’: site}

然后在 settings.py 中定义:

TEMPLATE_CONTEXT_PROCESSORS = (
    ‘django.core.context_processors.auth’,
    ‘django.core.context_processors.debug’,
    ‘django.core.context_processors.i18n’,
    ‘django.core.context_processors.request’,
    ‘utils.sitecontext.siteinfo’,
)

同时因为为了处理user,我的View中的Context基本上都是使用的 RequestContext,所以这块工作就省了。然后再在几个基础模板中增加 {{ site.othercode }} 这样就完成了。

整个处理还是比较简单。

八月 22, 2011

Django数据库模型的字段类型

Filed under: python — admin @ 1:38 下午

V=models.CharField(max_length=None[, **options])    #varchar

V=models.EmailField([max_length=75, **options])    #varchar
V=models.URLField([verify_exists=True, max_length=200, **options])    #varchar
V=models.FileField(upload_to=None[, max_length=100, **options])    #varchar
#upload_to指定保存目录可带格式,
V=models.ImageField(upload_to=None[, height_field=None, width_field=None, max_length=100, **options])
V=models.IPAddressField([**options])    #varchar
V=models.FilePathField(path=None[, match=None, recursive=False, max_length=100, **options]) #varchar
V=models.SlugField([max_length=50, **options])    #varchar,标签,内含索引
V=models.CommaSeparatedIntegerField(max_length=None[, **options])    #varchar

V=models.IntegerField([**options])    #int
V=models.PositiveIntegerField([**options])    #int 正整数
V=models.SmallIntegerField([**options])    #smallint
V=models.PositiveSmallIntegerField([**options])    #smallint 正整数
V=models.AutoField(**options)    #int;在Django代码内是自增
V=models.DecimalField(max_digits=None, decimal_places=None[, **options])    #decimal
V=models.FloatField([**options])    #real

V=models.BooleanField(**options)    #boolean或bit

V=models.NullBooleanField([**options])    #bit字段上可以设置上null值

V=models.DateField([auto_now=False, auto_now_add=False, **options])    #date
#auto_now最后修改记录的日期;auto_now_add添加记录的日期
V=models.DateTimeField([auto_now=False, auto_now_add=False, **options])    #datetime
V=models.TimeField([auto_now=False, auto_now_add=False, **options])    #time

V=models.TextField([**options])    #text
V=models.XMLField(schema_path=None[, **options])    #text

——————————————————————————–
V=models.ForeignKey(othermodel[, **options])    #外键,关联其它模型,创建关联索引
V=models.ManyToManyField(othermodel[, **options])    #多对多,关联其它模型,创建关联表
V=models.OneToOneField(othermodel[, parent_link=False, **options])    #一对一,字段关联表属性

1.   from django.db.backends.creation import BaseDatabaseCreation
2.
3.   class DatabaseCreation(BaseDatabaseCreation):
4.       # This dictionary maps Field objects to their associated MySQL column
5.       # types, as strings. Column-type strings can contain format strings; they’ll
6.       # be interpolated against the values of Field.__dict__ before being output.
7.       # If a column type is set to None, it won’t be included in the output.
8.       data_types = {
9.           ’AutoField’:         ’integer AUTO_INCREMENT’,
10.           ’BooleanField’:      ’bool’,
11.           ’CharField’:         ’varchar(%(max_length)s)’,
12.           ’CommaSeparatedIntegerField’: ’varchar(%(max_length)s)’,
13.           ’DateField’:         ’date’,
14.           ’DateTimeField’:     ’datetime’,
15.           ’DecimalField’:      ’numeric(%(max_digits)s, %(decimal_places)s)’,
16.           ’FileField’:         ’varchar(%(max_length)s)’,
17.           ’FilePathField’:     ’varchar(%(max_length)s)’,
18.           ’FloatField’:        ’double precision’,
19.           ’IntegerField’:      ’integer’,
20.           ’BigIntegerField’:   ’bigint’,
21.           ’IPAddressField’:    ’char(15)’,
22.           ’NullBooleanField’:  ’bool’,
23.           ’OneToOneField’:     ’integer’,
24.           ’PositiveIntegerField’: ’integer UNSIGNED’,
25.           ’PositiveSmallIntegerField’: ’smallint UNSIGNED’,
26.           ’SlugField’:         ’varchar(%(max_length)s)’,
27.           ’SmallIntegerField’: ’smallint’,
28.           ’TextField’:         ’longtext’,

29.           ’TimeField’:         ’time’,
30.       }
31.
32.       def sql_table_creation_suffix(self):
33.           suffix = []
34.           if self.connection.settings_dict['TEST_CHARSET']:
35.               suffix.append(‘CHARACTER SET %s’ % self.connection.settings_dict['TEST_CHARSET'])
36.           if self.connection.settings_dict['TEST_COLLATION']:
37.               suffix.append(‘COLLATE %s’ % self.connection.settings_dict['TEST_COLLATION'])
38.           return ’ ’.join(suffix)
39.
40.       def sql_for_inline_foreign_key_references(self, field, known_models, style):
41.           ”All inline references are pending under MySQL”
42.           return [], True
43.
44.       def sql_for_inline_many_to_many_references(self, model, field, style):
45.           from django.db import models
46.           opts = model._meta
47.           qn = self.connection.ops.quote_name
48.
49.           table_output = [
50.               '    %s %s %s,' %
51.                   (style.SQL_FIELD(qn(field.m2m_column_name())),
52.                   style.SQL_COLTYPE(models.ForeignKey(model).db_type(connection=self.connection)),
53.                   style.SQL_KEYWORD('NOT NULL')),
54.               '    %s %s %s,' %
55.               (style.SQL_FIELD(qn(field.m2m_reverse_name())),
56.               style.SQL_COLTYPE(models.ForeignKey(field.rel.to).db_type(connection=self.connection)),
57.               style.SQL_KEYWORD('NOT NULL'))
58.           ]
59.           deferred = [
60.               (field.m2m_db_table(), field.m2m_column_name(), opts.db_table,
61.                   opts.pk.column),
62.               (field.m2m_db_table(), field.m2m_reverse_name(),
63.                   field.rel.to._meta.db_table, field.rel.to._meta.pk.column)
64.               ]
65.           return table_output, deferred
objects.values_list 查询列的数据

八月 12, 2011

apache django admin 配置

Filed under: python — admin @ 11:58 上午

我把我的配置直接COPY进来,下面是APACHE里面的配置

<VirtualHost 192.168.1.2>
    ServerAdmin linuxqq@linuxqq.net
    DocumentRoot “/var/mysite”
    ServerName py.linuxqq.net
ErrorLog “logs/py.linuxqq.net-error_log”
    CustomLog “logs/py.linuxqq.net_log” common
    <Directory “/var/mysite”>
            Options Indexes FollowSymLinks
            AllowOverride None
            Order allow,deny
            Allow from all
    </Directory>
    Alias /media /var/mysite/html/media/
    <Location “/”>
            SetHandler python-program
            PythonHandler django.core.handlers.modpython
            PythonPath “['/var/mysite','/usr/lib/python2.4/site-packages/django/']+sys.path”
            SetEnv DJANGO_SETTINGS_MODULE settings
            SetEnv PYTHON_EGG_CACHE /tmp/mysite
            PythonDebug On
    </Location>
    <Location “/media/”>
       SetHandler None
    </Location>
    <LocationMatch “(?i)\.(jpg|gif|png|txt|ico|pdf|css|jpeg)$”>
       SetHandler None
    </LocationMatch>
</VirtualHost>

下面是DJANGO的SETTING的配置

DEBUG = False
TEMPLATE_DEBUG = DEBUG

ADMINS = (
    # (‘Your Name’, ‘your_email@example.com’),
)

MANAGERS = ADMINS

DATABASES = {
    ‘default’: {
        ‘ENGINE’: ‘django.db.backends.mysql’, # Add ‘postgresql_psycopg2′, ‘postgresql’, ‘mysql’, ‘sqlite3′ or ‘oracle’.
        ‘NAME’: ‘python’,                      # Or path to database file if using sqlite3.
        ‘USER’: ‘root’,                      # Not used with sqlite3.
        ‘PASSWORD’: ’123456789′,                  # Not used with sqlite3.
        ‘HOST’: ‘localhost’,                      # Set to empty string for localhost. Not used with sqlite3.
        ‘PORT’: ’3306′,                      # Set to empty string for default. Not used with sqlite3.
    }
}

TIME_ZONE = ‘America/Chicago’

LANGUAGE_CODE = ‘zh-CN’

SITE_ID = 1

USE_I18N = True

USE_L10N = True

MEDIA_ROOT = ‘/var/mysite/html’

MEDIA_URL = ‘http://py.linuxqq.net/media/’

STATIC_ROOT = ‘/var/mysite/html/media/’

STATIC_URL = ‘http://py.linuxqq.net/media/’

ADMIN_MEDIA_PREFIX = ‘http://py.linuxqq.net/media/’

STATICFILES_DIRS = (
    # Put strings here, like “/home/html/static” or “C:/www/django/static”.
    # Always use forward slashes, even on Windows.
    # Don’t forget to use absolute paths, not relative paths.
)

STATICFILES_FINDERS = (
    ‘django.contrib.staticfiles.finders.FileSystemFinder’,
    ‘django.contrib.staticfiles.finders.AppDirectoriesFinder’,

)

SECRET_KEY = ’8*v*#(wuh)g%#5ms-ytp%)apkadu508_9&8n2$b8&xdm^hn7xx’

TEMPLATE_LOADERS = (
    ‘django.template.loaders.filesystem.Loader’,
    ‘django.template.loaders.app_directories.Loader’,
)

MIDDLEWARE_CLASSES = (
    ‘django.middleware.common.CommonMiddleware’,
    ‘django.contrib.sessions.middleware.SessionMiddleware’,
    ‘django.middleware.csrf.CsrfViewMiddleware’,
    ‘django.contrib.auth.middleware.AuthenticationMiddleware’,
    ‘django.contrib.messages.middleware.MessageMiddleware’,
)

ROOT_URLCONF = ‘urls’

TEMPLATE_DIRS = (
           ‘/var/mysite/html’,
)

INSTALLED_APPS = (
    ‘django.contrib.auth’,
    ‘django.contrib.contenttypes’,
   ‘django.contrib.sessions’,
     ‘django.contrib.admin’,
     ‘books’,
)

LOGGING = {
    ‘version’: 1,
    ‘disable_existing_loggers’: False,
    ‘handlers’: {
        ‘mail_admins’: {
            ‘level’: ‘ERROR’,
            ‘class’: ‘django.utils.log.AdminEmailHandler’
        }
    },
    ‘loggers’: {
        ‘django.request’: {
            ‘handlers’: ['mail_admins'],
            ‘level’: ‘ERROR’,
            ‘propagate’: True,
        },
    }
}

下面是模型的步骤的步骤

首先在修改MODEL.PY 建立模型

from django.db import models
class BlogPost(models.Model):
    title = models.CharField(max_length=150)
    body = models.TextField()
    timestamp = models.DateTimeField()

然后去admin.py里面注册下

rom django.contrib import admin
from books.models import BlogPost

admin.site.register(BlogPost)

八月 11, 2011

apache加载python

Filed under: python — admin @ 11:15 上午

前一篇文章写的在APACHE安装MOD_PYTHON的经过,其实挺简单,就是版本不兼容的问题.这次我大概说下部署DJANGO的过程.

先修改APACHE配置文件,使其加载mod_python模块

LoadModule python_module libexec/mod_python.so

运行命令查看

bin/httpd -M可以看到

 python_module (shared)
Syntax OK

说明apache已经成功加载mod_python.

下面我说下我的实际的环境和项目情况:

/infoware/xx/web是django程序目录

/infoware/_conf/xx/是控制django的程序还有一些配置(有些配置变量没有写在settings),这一步可以不需要,因为大多数人会直接配置settings文件的.我是在虚拟主机上操作.

–CENTOS5.2+APACHE2.2.11+PYTHON 2.4.3+MOD_PYTHON3.3.1+DJANGO 0.96

下面是apache配置文件

—————————————————-

<VirtualHost *:80>
        ServerAdmin webmaster@xxcom
        DocumentRoot “/infoware/xx/web”
        ServerName www1.xx.com
        ServerAlias www1.xx.com
        ErrorLog “/var/log/apache/xx/xx_error_log”
        CustomLog “/var/log/apache/xx/xx_access_log” common
        <Directory “/infoware/xx/web”>
            Options Indexes FollowSymLinks
            AllowOverride None
            Order allow,deny
            Allow from all

        </Directory>
        <Location “/”>
            SetHandler python-program
            PythonHandler django.core.handlers.modpython
            PythonPath “['/infoware/xx/web']+['/infoware/_conf/xx] + sys.path”
            SetEnv DJANGO_SETTINGS_MODULE settings
            SetEnv PYTHON_EGG_CACHE /tmp/cucrm//这儿是加个变量,会在下面说明
            PythonDebug On
        </Location>
</VirtualHost>

——————————————————————

以上配置一定要注意环境变量的配置,否则会出错!

我在配置前出现了以下错误,##################################################################
Can’t extract file(s) to egg cache The following error occurred while trying to extract file(s) to the Python egg cache: [Errno 13] Permission denied: ‘/root/.python-eggs’ The Python egg cache directory is currently set to: /root/.python-eggs Perhaps your account does not have write access to this directory? You can change the cache directory by setting the PYTHON_EGG_CACHE environment variable to point to an accessible directory.
#################################################################

解决方法就是加环境变量

SetEnv PYTHON_EGG_CACHE /tmp/cucrm//这个目录的权限属主一定要设为APACHE指定的用户,要不就777

大概就这样,仅供参考,如果觉得麻烦的话建议FASTCGI,这个简单点.

七月 20, 2011

django admin 设置

Filed under: python — admin @ 2:18 下午

# Include these import statements…
from django.contrib import admin
from django.conf.urls.defaults import *
admin.autodiscover()

# And include this URLpattern…
urlpatterns = patterns(”,
    # …
    (r’^admin/’, include(admin.site.urls)),
    # …
)

顺便理清下自己最近学习PYTHON的思路

 先是URLS  在是VIEWS 然后是模版template

如果新做项目

python manage.py startapp books
接下来编辑books/model.py 里面的文件
添加需要做的数据库
python manage.py validate  这个命令验证模型的有效性
 
python manage.py sqlall books   这个命令查看转换出来的SQL语句
 
python manage.py syncdb      这个命令将SQL 添加到库里
 

模版系统

修改setting.py 将里面TEMPLATE_DIRS = (
           '/var/mysite/html',
)
修改views.py
from django.http import HttpResponse
from django.shortcuts import render_to_response
from django.template import Template, Context
def ua_display_bad(request):
        ua=request.META['HTTP_USER_AGENT']
        return HttpResponse("Your browser is %s" % ua)

def ua_display_good1(request):
        try:
            ua=request.META['HTTP_USER_AGENT']
        except KeyError:
            ua='unknown'
        return HttpResponse("Your browser is %s" % ua)

def ua_display_good2(request):
        ua=request.META.get('HTTP_USER_AGENT','unknown')
        return HttpResponse("Ypur brow is %s" % ua)

def search_form(request):
    return render_to_response('search_form.html')

 

 

URLS里面的设置

 

# Include these import statements...
from django.contrib import admin
from django.conf.urls.defaults import *
from views import *
admin.autodiscover()

# And include this URLpattern...
urlpatterns = patterns('',
    (r'^admin/', include(admin.site.urls)),
    (r'^good1/',ua_display_good1),
    (r'^good2/',ua_display_good2),
    (r'^display/',ua_display_bad),
    (r'^search-form/$',search_form),
)

 

没办法啊 我新手刚学PYTHON。所以记录下来 免的老忘掉 理清思路

七月 19, 2011

/usr/bin/ld: cannot find -lmysqlclient_r

Filed under: python — admin @ 1:08 下午

我的环境 centos 5.2,mysql 5.0.89 版(源码安装的),配置为:

./configure –prefix=/usr/local/mysql –with-charset=utf8 –with-extra-charsets=all

python 是自带的 2.4.3,按照 官方 web.py 0.3 写例子。安装 MySQL-python 想从源码安装,但后来报错

gcc -pthread -shared build/temp.linux-x86_64-2.4/_mysql.o -L/usr/local/mysql/lib/mysql -lmysqlclient_r -lz -lpthread -lcrypt -lnsl -lm -lpthread -o build/lib.linux-x86_64-2.4/_mysql.so
/usr/bin/ld: cannot find -lmysqlclient_r
collect2: ld returned 1 exit status
error: command ‘gcc’ failed with exit status 1

说没有 mysqlclient_r 后 google 到答案:把 mysql-python/site.cfg 的 threadsafe = True 改为 False。就可以安装,的确如此。再看看 mysql 源码里的 ./configure –help 就知道有个 –enable-thread-safe-client 选项,如果安装的时候指定就可以了(就还是用 threadsfe = True)。

安装时又说没有 setuptools 模块,这个可以直接运动 mysql-python/ez_setup.py 即可。 然后 python setup.py install 就可以了。

按照 web.py 0.3 的例子:

import web  
render = web.template.render(‘templates/’)  
db = web.database(dbn=’mysql’, user=’test’, pw=’test’, db=’test’)  
urls = (  
        ‘/’, ‘index’ 
)  
 
class index:  
        def GET(self):  
                todos = db.select(‘todo’)  
                return render.index(todos)  
 
app = web.application(urls, globals())  
 
if __name__ == “__main__”: app.run() 

import web
render = web.template.render(‘templates/’)
db = web.database(dbn=’mysql’, user=’test’, pw=’test’, db=’test’)
urls = (
        ‘/’, ‘index’
)

class index:
        def GET(self):
                todos = db.select(‘todo’)
                return render.index(todos)

app = web.application(urls, globals())

if __name__ == “__main__”: app.run()
然后运行它,打开浏览器访问,N多错误信息。后台错误:

  File “/usr/lib/python2.4/site-packages/web/db.py”, line 641, in select
    return self.query(qout, processed=True)
  File “/usr/lib/python2.4/site-packages/web/db.py”, line 602, in query
    db_cursor = self._db_cursor()
  File “/usr/lib/python2.4/site-packages/web/db.py”, line 533, in _db_cursor
    return self.ctx.db.cursor()
  File “/usr/lib/python2.4/site-packages/web/db.py”, line 474, in _getctx
    self._load_context(self._ctx)
  File “/usr/lib/python2.4/site-packages/web/db.py”, line 485, in _load_context
    ctx.db = self._connect(self.keywords)
  File “/usr/lib/python2.4/site-packages/web/db.py”, line 513, in _connect
    return self.db_module.connect(**keywords)
  File “build/bdist.linux-x86_64/egg/MySQLdb/__init__.py”, line 81, in Connect
  File “build/bdist.linux-x86_64/egg/MySQLdb/connections.py”, line 188, in __init__
OperationalError: (2002, “Can’t connect to local MySQL server through socket ‘/var/lib/mysql/mysql.sock’ (2)”)用 /var/lib/mysql/mysql.sock 肯定链接不上,因为 mysql.sock 在 /tmp/mysql.sock 里。如果你还没安装 mysql,安装 mysql 时可以用 –with-unix-socket-path=/var/lib/mysql/mysql.sock 指定,这就不会报错的。

网上文章已经记录过此问题,没给出解决方案:MySQLdb connect 问题

然后看了 django 连接 mysql 是可以设置 mysql.sock 的。恩那应该 web.py 也可以的。

想找 connections.py 源码又没发现在哪里,原来在 mysql-python/MySQLdb 目录下,看了 __init__,里面有个 unix_socket 变量,恩有救了,于是在 web.py 的例子里加入 unix_socket 参数值。就可以了连接 mysql 了:

db = web.database(dbn=’mysql’, user=’test’, pw=’test’, db=’test’, unix_socket=’/tmp/mysql.sock’) 

db = web.database(dbn=’mysql’, user=’test’, pw=’test’, db=’test’, unix_socket=’/tmp/mysql.sock’)
浏览器终于显示 Learn web.py 了。

比较诡异的是,有时即使安装完成,在python中执行
import MySQLdb
仍然可能出错:
libmysqlclient.so.12: cannot open shared object file: No such file or directory

遇到这种问题,需要在/usr/lib/下为libmysqlclient.so.15设置一个符号链接(这里假设mysql安装在/usr/local/mysql下)
ln -s /usr/lib/mysql/lib/libmysqlclient.so /usr/lib/libmysqlclient.so.15
再次执行
import MySQLdb

五月 26, 2011

python 分析日志一例 完善中

Filed under: python — admin @ 12:59 下午

#!/usr/bin/python
import re
import glob
def openfile(openfile):
    f=open(openfile,’r')   
    for line in f.readlines():
        recompile(line)
    f.close

def recompile(recompile):
    text=recompile
    dist={}
    p=0
    list_lines=[(r'[a-zA-Z]{3}\s\d+\s\d+:\d+:\d+’),(r’[a-zA-Z]{9}\s[a-zA-Z]{4}\[\d+\]‘)]
    for i in list_lines:
        dist[p]=re.compile(i).findall(text)
        if dist[p]!=”:
             p+=1
             if p==2:
                print dist[0],dist[1]
def main():
    flog=sorted(glob.glob(r’c:\*.txt’))
    for txt in flog:
        openfile(txt)

       
if __name__==”__main__”:
    main()

五月 10, 2011

TypeError: __init__() got an unexpected keyword argument ‘maxlength

Filed under: python — admin @ 1:47 下午

TypeError: __init__() got an unexpected keyword argument ‘maxlength

然后在执行manage.py syncdb的时候又开始报错:
TypeError: __init__() got an unexpected keyword argument ‘maxlength’
查看了一下源码Python25\Lib\site-packages\django\forms\fields.py    的CharField类,发现__init__里面那个参数原来是max_length
而不是maxlength,limodou大范了次笔误呵呵。
以上便是学习Django途中的一点小小的经验,希望对碰到类似问题的朋友有所帮助

转载注明(LINUXQQ)

五月 6, 2011

DeprecationWarning: Short names for ENGINE in database configurations are deprecated. Prepend default.ENGINE with ‘django.db.backends

Filed under: python — admin @ 1:01 下午

DeprecationWarning: Short names for ENGINE in database configurations are deprecated. Prepend default.ENGINE with ‘django.db.backend 出错

解决办法是

在settings.py中DATABASE的配置中,有一个叫ENGINE的,在1.2以前的版本中,用的是短名称,比如 “mysql”、”sqlite”、“oracle”等等,1.3版本以后,需要写一个全名,这个东东在官网上可以查到,比如mysql应该写成 “django.db.backends.mysql”

转载注明(LINUXQQ)

四月 22, 2011

python AbstractFormatter

Filed under: python — admin @ 4:29 下午

模糊的搞懂了什么意思

HTMLParser(AbstractFormatter(DumbWriter(StringIO)))  ”’ 使用HTMLParser的方法进行处理,StringIO是从内存中读取数据,DumbWriter将事件流转换为存文本文档”’
主要是AbstractFormatter 查了下相关资料

formatter 模块
formatter 模块提供了一些可用于 htmllib 的格式类( formatter classes ).
这些类有两种, formatter 和 writer . formatter 将 HTML 解析器的标签和数据流转换为适合输出设备的事件流( event stream ), 而 writer 将事件流输出到设备上.
大多情况下, 你可以使用 AbstractFormatter 类进行格式化. 它会根据不同的格式化事件调用 writer 对象的方法. AbstractWriter 类在每次方法调用时打印一条信息.

 

HTMLParser是python用来解析html的模块。它可以分析出html里面的标签、数据等等,是一种处理html的简便途径。HTMLParser采用的是一种事件驱动的模式,当HTMLParser找到一个特定的标记时,它会去调用一个用户定义的函数,以此来通知程序处理。它主要的用户回调函数的命名都是以handler_开头的,都是HTMLParser的成员函数。当我们使用时,就从HTMLParser派生出新的类,然后重新定义这几个以handler_开头的函数即可。这几个函数包括:
handle_startendtag  处理开始标签和结束标签
handle_starttag     处理开始标签,比如<xx>
handle_endtag       处理结束标签,比如</xx>
handle_charref      处理特殊字符串,就是以&#开头的,一般是内码表示的字符
handle_entityref    处理一些特殊字符,以&开头的,比如 &nbsp;
handle_data         处理数据,就是<xx>data</xx>中间的那些数据
handle_comment      处理注释
handle_decl         处理<!开头的,比如<!DOCTYPE html PUBLIC “-//W3C//DTD HTML 4.01 Transitional//EN”
handle_pi           处理形如<?instruction>的东西
    这里我以从网页中获取到url为例,介绍一下。要想获取到url,肯定是要分析<a>标签,然后取到它的href属性的值。下面是代码:

#-*- encoding: gb2312 -*-
import HTMLParser

class MyParser(HTMLParser.HTMLParser):
    def __init__(self):
        HTMLParser.HTMLParser.__init__(self)        
        
    def handle_starttag(self, tag, attrs):
        # 这里重新定义了处理开始标签的函数
        if tag == ’a':
            # 判断标签<a>的属性
            for name,value in attrs:
                if name == ’href’:
                    print value
        

if __name__ == ’__main__’:
    a = ’<html><head><title>test</title><body><a href=”http://www.163.com”>链接到163</a></body></html>’
    
    my = MyParser()
    # 传入要分析的数据,是html的。
    my.feed(a)

class HTMLParser.HTMLParser:使用HTMLParser 的实例,填充HTML数据,并在开始和结束标记间调用函数.HTMLParser类意味着重载.和 htmllib 的分析器不同,this parser并不检测和开始标记对应的结束标记

HTMLParser 实例有如下的方法:
HTMLParser.reset()  #重置实例.所有未处理的数据都会丢失.在初始化时自动调用.
HTMLParser.feed(data) #给分析器喂食.在由完整元素构成的情况下工作;不完整数据情况下,会进行缓冲知道更多数据加进来或者 close() 被调用.
HTMLParser.close()  #处理所有缓冲数据.这个方法可以被派生类重定义,以便在输入结束后处理额外的事情,重定义的版本也要调用 HTMLParser 基类的 close() 方法.
HTMLParser.getpos() #返回当前行数和列数
HTMLParser.get_starttag_text() #返回最近打开过得开始标记处的文本.通常不会用到
HTMLParser.handle_starttag(tag, attrs) #该方法用来处理一个标记的开始.tag参数是tag的名字的小写化.attrs参数是一个list,由(name,value)组成,反映了<>里面的属性. name会被翻译成小写字母,在value中的引号也被移除了,字符实体引用也会被替换.例如,有个 tag<A HREF=”http://www.cwi.nl/”> ,那么使用该方法就该这么做: handle_starttag(‘a’, [('href','http://www.cwi.nl/')])
HTMLParser.handle_startendtag(tag, attrs) #和handle_starttag()类似,用来处理XHTML风格的空标签(<a …/>).可能被子类重载
HTMLParser.handle_endtag(tag) #该方法用来处理元素结束标记.可以被派生类重载;基类什么也不做. tag参数是tag的name转化来的小写字母.
HTMLParser.handle_data(data) #该方法用来处理随机的数据.
HTMLParser.handle_charref(name) #处理 &#ref 格式的字符引用.
HTMLParser.handle_entityref(name)  #处理一般的 &name 格式的实体引用. name 是一个一般的实体引用.
HTMLParser.handle_comment(data) #处理遇到注释的情况.注释参数为在——和——之间的字符串文本,而不是分隔符自身.例如 <!–text–> ,该方法将调用’text’.
HTMLParser.handle_decl(decl) #当分析器遇到SGML声明时调用此方法. decl 参数是 <!…> 标记里的整个内容.
HTMLParser.handle_pi(data) #处理命令, data 参数包含整个的处理命令.例如 <?proc color=’red’> ,该方法应写成 handle_pi(“proc color=’red’”).

使用实例:

#!/usr/bin/python
#-*- encoding: utf-8 -*-

import HTMLParser
class MyParser(HTMLParser.HTMLParser):
    def __init__(self):
        HTMLParser.HTMLParser.__init__(self)               
    def handle_starttag(self, tag, attrs):
       
# 这里重新定义了处理开始标签的函数
        if tag == ‘a’:
            # 判断标签<a>的属性
            for name,value in attrs:
                if name == ‘href’:
                    print value
       
if __name__ == ‘__main__’:
    a = ‘<html><head><title>test</title><body><a href=”http: //www.163.com”>链接到163</a><a href=”
http://www.linuxqq.net“>焦点</a></body></html>’
    my = MyParser()
    # 传入要分析的数据,是html的。
    my.feed(a)

运行结果:

www.163.com www.linuxqq.net

http: //www.163.com
http://www.linuxqq.net
handle_startendtag 处理开始标签和结束标签
handle_starttag     处理开始标签,比如<xx>
handle_endtag       处理结束标签,比如</xx>
handle_charref      处理特殊字符串,就是以&#开头的,一般是内码表示的字符
handle_entityref    处理一些特殊字符,以&开头的,比如 &nbsp;
handle_data         处理数据,就是<xx>data</xx>中间的那些数据
handle_comment      处理注释
handle_decl         处理<!开头的,比如<!DOCTYPE html PUBLIC “-//W3C//DTD HTML 4.01 Transitional//EN”
handle_pi           处理形如<?instruction>的东西
« Newer PostsOlder Posts »

Powered by LINUXQQ   ICP 10203065