Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
C
cpython
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
Kirill Smelkov
cpython
Commits
80e57fb2
Commit
80e57fb2
authored
Dec 21, 1997
by
Guido van Rossum
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Converted to use re instead of regex; version 0.9.0.
parent
9897f0f8
Changes
3
Hide whitespace changes
Inline
Side-by-side
Showing
3 changed files
with
52 additions
and
55 deletions
+52
-55
Tools/faqwiz/README
Tools/faqwiz/README
+14
-2
Tools/faqwiz/faqconf.py
Tools/faqwiz/faqconf.py
+6
-6
Tools/faqwiz/faqwiz.py
Tools/faqwiz/faqwiz.py
+32
-47
No files found.
Tools/faqwiz/README
View file @
80e57fb2
...
@@ -2,8 +2,8 @@ FAQ Wizard
...
@@ -2,8 +2,8 @@ FAQ Wizard
----------
----------
Author: Guido van Rossum <guido@python.org>
Author: Guido van Rossum <guido@python.org>
Version: 0.
8.4
Version: 0.
9.0
Date:
16
December 1997
Date:
21
December 1997
This is a CGI program that maintains a user-editable FAQ. It uses RCS
This is a CGI program that maintains a user-editable FAQ. It uses RCS
...
@@ -22,6 +22,17 @@ faqwiz.py main module, lives in same directory as FAQ entry files
...
@@ -22,6 +22,17 @@ faqwiz.py main module, lives in same directory as FAQ entry files
faqconf.py main configuration module
faqconf.py main configuration module
faqcust.py additional local customization module (optional)
faqcust.py additional local customization module (optional)
What's New?
-----------
Version 0.9.0 uses the re module (Perl style regular expressions) for
all its regular expression needs, instead of the regex and regsub
modules (Emacs style). This affects the syntax for regular
expressions entered by the user as search strings (with "regular
expression" checked), hence the version number jump.
Setup Information
Setup Information
-----------------
-----------------
...
@@ -76,6 +87,7 @@ file faq01.001.htp,v in the RCS subdirectory. You can now exercise
...
@@ -76,6 +87,7 @@ file faq01.001.htp,v in the RCS subdirectory. You can now exercise
the other FAQ wizard features (search, index, whole FAQ, what's new,
the other FAQ wizard features (search, index, whole FAQ, what's new,
roulette, and so on).
roulette, and so on).
Maintaining Multiple FAQs
Maintaining Multiple FAQs
-------------------------
-------------------------
...
...
Tools/faqwiz/faqconf.py
View file @
80e57fb2
...
@@ -49,7 +49,7 @@ entries marked with * were changed within the last 7 days.)
...
@@ -49,7 +49,7 @@ entries marked with * were changed within the last 7 days.)
# Version -- don't change unless you edit faqwiz.py
# Version -- don't change unless you edit faqwiz.py
WIZVERSION
=
"0.
8.4
"
# FAQ Wizard version
WIZVERSION
=
"0.
9.0
"
# FAQ Wizard version
# This parameter is normally overwritten with a dynamic value
# This parameter is normally overwritten with a dynamic value
...
@@ -58,12 +58,12 @@ import os, sys
...
@@ -58,12 +58,12 @@ import os, sys
FAQCGI
=
os
.
path
.
basename
(
sys
.
argv
[
0
])
or
FAQCGI
FAQCGI
=
os
.
path
.
basename
(
sys
.
argv
[
0
])
or
FAQCGI
del
os
,
sys
del
os
,
sys
#
Regular expression to recognize FAQ entry files: group(1) should be
#
Perl (re module) style regular expression to recognize FAQ entry
#
the section number, group(2) should be the question number. Both
#
files: group(1) should be the section number, group(2) should be the
#
should be fixed width so simple-minded sorting yields the right
#
question number. Both should be fixed width so simple-minded
# order.
#
sorting yields the right
order.
OKFILENAME
=
"^faq
\
([
0
-9][0-9]
\
)
\
.
\
([
0
-9][0-9][0-9]
\
)
\
.htp$"
OKFILENAME
=
r"^faq(\
d
\d)\
.(
\d\
d
\d
)\
.h
tp$"
# Format to construct a FAQ entry file name
# Format to construct a FAQ entry file name
...
...
Tools/faqwiz/faqwiz.py
View file @
80e57fb2
...
@@ -11,7 +11,7 @@ The actual script to place in cgi-bin is faqw.py.
...
@@ -11,7 +11,7 @@ The actual script to place in cgi-bin is faqw.py.
"""
"""
import
sys
,
string
,
time
,
os
,
stat
,
re
gex
,
cgi
,
faqconf
import
sys
,
string
,
time
,
os
,
stat
,
re
,
cgi
,
faqconf
from
faqconf
import
*
# This imports all uppercase names
from
faqconf
import
*
# This imports all uppercase names
now
=
time
.
time
()
now
=
time
.
time
()
...
@@ -32,21 +32,15 @@ class NoSuchFile(FileError):
...
@@ -32,21 +32,15 @@ class NoSuchFile(FileError):
FileError
.
__init__
(
self
,
file
)
FileError
.
__init__
(
self
,
file
)
self
.
why
=
why
self
.
why
=
why
def
replace
(
s
,
old
,
new
):
try
:
return
string
.
replace
(
s
,
old
,
new
)
except
AttributeError
:
return
string
.
join
(
string
.
split
(
s
,
old
),
new
)
def
escape
(
s
):
def
escape
(
s
):
s
=
replace
(
s
,
'&'
,
'&'
)
s
=
string
.
replace
(
s
,
'&'
,
'&'
)
s
=
replace
(
s
,
'<'
,
'<'
)
s
=
string
.
replace
(
s
,
'<'
,
'<'
)
s
=
replace
(
s
,
'>'
,
'>'
)
s
=
string
.
replace
(
s
,
'>'
,
'>'
)
return
s
return
s
def
escapeq
(
s
):
def
escapeq
(
s
):
s
=
escape
(
s
)
s
=
escape
(
s
)
s
=
replace
(
s
,
'"'
,
'"'
)
s
=
string
.
replace
(
s
,
'"'
,
'"'
)
return
s
return
s
def
_interpolate
(
format
,
args
,
kw
):
def
_interpolate
(
format
,
args
,
kw
):
...
@@ -73,20 +67,20 @@ translate_prog = None
...
@@ -73,20 +67,20 @@ translate_prog = None
def
translate
(
text
,
pre
=
0
):
def
translate
(
text
,
pre
=
0
):
global
translate_prog
global
translate_prog
if
not
translate_prog
:
if
not
translate_prog
:
url
=
'
\
(h
t
tp
\
|
f
tp
\
|h
t
tps
\
)://[^
\
t
\
r
\
n
]*'
translate_prog
=
prog
=
re
.
compile
(
email
=
'
\
<[-
a
-zA-Z0-9._]+@[-a-zA-Z0-9._]+'
r'\b(http|ftp|https)://\
S+(
\b|/)|\b[-.\
w]+@[-.
\w]+'
)
translate_prog
=
prog
=
regex
.
compile
(
url
+
'
\
|
'
+ email)
else
:
else
:
prog
=
translate_prog
prog
=
translate_prog
i
=
0
i
=
0
list
=
[]
list
=
[]
while
1
:
while
1
:
j
= prog.search(text, i)
m
=
prog
.
search
(
text
,
i
)
if
j < 0
:
if
not
m
:
break
break
j
=
m
.
start
()
list
.
append
(
escape
(
text
[
i
:
j
]))
list
.
append
(
escape
(
text
[
i
:
j
]))
i
=
j
i
=
j
url =
prog
.group(0)
url
=
m
.
group
(
0
)
while
url
[
-
1
]
in
'();:,.?
\
'
"<>'
:
while
url
[
-
1
]
in
'();:,.?
\
'
"<>'
:
url
=
url
[:
-
1
]
url
=
url
[:
-
1
]
i
=
i
+
len
(
url
)
i
=
i
+
len
(
url
)
...
@@ -103,26 +97,19 @@ def translate(text, pre=0):
...
@@ -103,26 +97,19 @@ def translate(text, pre=0):
list
.
append
(
escape
(
text
[
i
:
j
]))
list
.
append
(
escape
(
text
[
i
:
j
]))
return
string
.
join
(
list
,
''
)
return
string
.
join
(
list
,
''
)
emphasize_prog
=
None
def
emphasize
(
line
):
def
emphasize
(
line
):
global
emphasize_prog
return
re
.
sub
(
r'\
*([
a-zA-Z]+)\
*
', r'
<
I
>
\
1
</
I
>
', line)
import
regsub
if
not
emphasize_prog
:
pat
=
'
\
*
\
([a-zA-Z]+
\
)
\
*'
emphasize_prog
=
regex
.
compile
(
pat
)
return
regsub
.
gsub
(
emphasize_prog
,
'<I>
\
\
1</I>'
,
line
)
revparse_prog = None
revparse_prog = None
def revparse(rev):
def revparse(rev):
global revparse_prog
global revparse_prog
if not revparse_prog:
if not revparse_prog:
revparse_prog
=
re
gex
.
compile
(
revparse_prog = re
.compile(r'
^
(
\
d
{
1
,
3
})
\
.(
\
d
{
1
-
4
})
$
')
'^
\
([
1
-9][0-9]?[0-9]?
\
)
\
.
\
([
1
-9][0-9]?[0-9]?[0-9]?
\
)$
'
)
m = revparse_prog.match(rev
)
if
revparse_prog.match(rev) < 0
:
if
not m
:
return None
return None
[major, minor] = map(string.atoi,
revparse_prog
.group(1, 2))
[major, minor] = map(string.atoi,
m
.group(1, 2))
return major, minor
return major, minor
def load_cookies():
def load_cookies():
...
@@ -315,7 +302,7 @@ class FaqDir:
...
@@ -315,7 +302,7 @@ class FaqDir:
entryclass = FaqEntry
entryclass = FaqEntry
__okprog = re
gex
.compile(OKFILENAME)
__okprog = re.compile(OKFILENAME)
def __init__(self, dir=os.curdir):
def __init__(self, dir=os.curdir):
self.__dir = dir
self.__dir = dir
...
@@ -327,17 +314,18 @@ class FaqDir:
...
@@ -327,17 +314,18 @@ class FaqDir:
self.__files = files = []
self.__files = files = []
okprog = self.__okprog
okprog = self.__okprog
for file in os.listdir(self.__dir):
for file in os.listdir(self.__dir):
if
okprog.match(file) >= 0
:
if
self.__okprog.match(file)
:
files.append(file)
files.append(file)
files.sort()
files.sort()
def good(self, file):
def good(self, file):
return self.__okprog.match(file)
>= 0
return self.__okprog.match(file)
def parse(self, file):
def parse(self, file):
if not self.good(file):
m = self.good(file)
if not m:
return None
return None
sec, num =
self.__okprog
.group(1, 2)
sec, num =
m
.group(1, 2)
return string.atoi(sec), string.atoi(num)
return string.atoi(sec), string.atoi(num)
def list(self):
def list(self):
...
@@ -426,31 +414,29 @@ class FaqWizard:
...
@@ -426,31 +414,29 @@ class FaqWizard:
self
.
error
(
"Empty query string!"
)
self
.
error
(
"Empty query string!"
)
return
return
if
self
.
ui
.
querytype
==
'simple'
:
if
self
.
ui
.
querytype
==
'simple'
:
for
c
in
'
\
\
.[]?+^$*'
:
query
=
re
.
escape
(
query
)
if
c
in
query
:
query
=
replace
(
query
,
c
,
'
\
\
'
+
c
)
queries
=
[
query
]
queries
=
[
query
]
elif
self
.
ui
.
querytype
in
(
'anykeywords'
,
'allkeywords'
):
elif
self
.
ui
.
querytype
in
(
'anykeywords'
,
'allkeywords'
):
import
regsub
words
=
filter
(
None
,
re
.
split
(
'
\
W+
'
, query))
words
=
string
.
split
(
regsub
.
gsub
(
'[^a-zA-Z0-9]+'
,
' '
,
query
))
if not words:
if not words:
self.error("No keywords specified!")
self.error("No keywords specified!")
return
return
words
=
map
(
lambda
w
:
'
\
<%s
\
>
'
%
w
,
words
)
words = map(lambda w:
r'
\
b
%
s
\
b
' % w, words)
if self.ui.querytype[:3] == '
any
':
if self.ui.querytype[:3] == '
any
':
queries
=
[
string
.
join
(
words
,
'
\
|
'
)]
queries = [string.join(words, '
|
')]
else:
else:
# Each of the individual queries must match
queries = words
queries = words
else:
else:
# Default to reg
ex
# Default to reg
ular expression
queries = [query]
queries = [query]
self.prologue(T_SEARCH)
self.prologue(T_SEARCH)
progs = []
progs = []
for query in queries:
for query in queries:
if self.ui.casefold == '
no
':
if self.ui.casefold == '
no
':
p = re
gex
.compile(query)
p = re.compile(query)
else:
else:
p = re
gex.compile(query, regex.casefold
)
p = re
.compile(query, re.IGNORECASE
)
progs.append(p)
progs.append(p)
hits = []
hits = []
for file in self.dir.list():
for file in self.dir.list():
...
@@ -459,7 +445,7 @@ class FaqWizard:
...
@@ -459,7 +445,7 @@ class FaqWizard:
except FileError:
except FileError:
constants
constants
for p in progs:
for p in progs:
if
p.search(entry.title) < 0 and p.search(entry.body) < 0
:
if
not p.search(entry.title) and not p.search(entry.body)
:
break
break
else:
else:
hits.append(file)
hits.append(file)
...
@@ -777,8 +763,7 @@ class FaqWizard:
...
@@ -777,8 +763,7 @@ class FaqWizard:
file
=
entry
.
file
file
=
entry
.
file
# Normalize line endings in body
# Normalize line endings in body
if
'
\
r
'
in
self
.
ui
.
body
:
if
'
\
r
'
in
self
.
ui
.
body
:
import
regsub
self
.
ui
.
body
=
re
.
sub
(
'
\
r
\
n
?'
,
'
\
n
'
,
self
.
ui
.
body
)
self
.
ui
.
body
=
regsub
.
gsub
(
'
\
r
\
n
?'
,
'
\
n
'
,
self
.
ui
.
body
)
# Normalize whitespace in title
# Normalize whitespace in title
self
.
ui
.
title
=
string
.
join
(
string
.
split
(
self
.
ui
.
title
))
self
.
ui
.
title
=
string
.
join
(
string
.
split
(
self
.
ui
.
title
))
# Check that there were any changes
# Check that there were any changes
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment