OSDN Git Service

Move ThreadInvoker and FileWrap to misc.py
[fukui-no-namari/fukui-no-namari.git] / src / FukuiNoNamari / misc.py
1 # Copyright (C) 2006 by Aiwota Programmer
2 # aiwotaprog@tetteke.tk
3 #
4 # This program is free software; you can redistribute it and/or modify
5 # it under the terms of the GNU General Public License as published by
6 # the Free Software Foundation; either version 2 of the License, or
7 # (at your option) any later version.
8 #
9 # This program is distributed in the hope that it will be useful,
10 # but WITHOUT ANY WARRANTY; without even the implied warranty of
11 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12 # GNU General Public License for more details.
13 #
14 # You should have received a copy of the GNU General Public License
15 # along with this program; if not, write to the Free Software
16 # Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
17
18 import os.path
19 import re
20 import time
21 import threading
22
23 import config
24
25 REG_EXPR_HTTPDATE = re.compile("((?:Mon)|(?:Tue)|(?:Wed)|(?:Thu)|(?:Fri)|(?:Sat)|(?:Sun)), (\d{2}) ((?:Jan)|(?:Feb)|(?:Mar)|(?:Apr)|(?:May)|(?:Jun)|(?:Jul)|(?:Aug)|(?:Sep)|(?:Oct)|(?:Nov)|(?:Dec)) (\d{4}) (\d{2}):(\d{2}):(\d{2}) GMT")
26 WDAY_DICT = {"Mon":0, "Tue":1, "Wed":2, "Thu":3, "Fri":4, "Sat":5, "Sun":6}
27 MON_DICT = {"Jan":1, "Feb":2, "Mar":3, "Apr":4, "May":5, "Jun":6, "Jul":7,
28             "Aug":8, "Sep":9, "Oct":10, "Nov":11, "Dec":12}
29
30 def get_logs_dir_path():
31     return os.path.join(config.get_config_dir_path(), "logs")
32
33 def get_thread_dat_dir_path(bbs, board):
34     """Returns dir path for saving thread dat file"""
35
36     # if parameter is empty, raise ValueError
37     if not bbs or not board:
38         raise ValueError, "parameter must not be empty"
39
40     return os.path.join(get_board_dir_path(bbs, board), "dat")
41
42 def get_thread_idx_dir_path(bbs, board):
43     """Returns dir path for saving thread index file"""
44
45     # if parameter is empty, raise ValueError
46     if not bbs or not board:
47         raise ValueError, "parameter must not be empty"
48
49     return os.path.join(get_board_dir_path(bbs, board), "idx")
50
51 def get_thread_states_dir_path(bbs, board):
52     if not bbs or not board:
53         raise ValueError, "parameter must not be empty"
54
55     return os.path.join(get_board_dir_path(bbs, board), "states")
56
57 def get_thread_dat_path(bbs, board, thread):
58     """Returns thread dat file path
59
60     bbs: bbs id
61
62     board: board id
63
64     thread: thread id
65     """
66
67     # if parameter is empty, raise ValueError
68     if not bbs or not board or not thread:
69         raise ValueError, "parameter must not be empty"
70
71     return os.path.join(get_thread_dat_dir_path(bbs, board), thread + ".dat")
72
73 def get_board_subjecttxt_url(bbs, board):
74     """Returns subject.txt file url
75
76     bbs: bbs id
77
78     board: board id
79     """
80
81     # if parameter is empty, raise ValueError
82     if not bbs or not board:
83         raise ValueError, "parameter must not be empty"
84
85     return get_board_base_url(bbs, board) + "subject.txt"
86
87 def get_board_subjecttxt_path(bbs, board):
88     """Returns subject.txt file path
89
90     bbs: bbs id
91
92     board: board id
93     """
94
95     # if parameter is empty, raise ValueError
96     if not bbs or not board:
97         raise ValueError, "parameter must not be empty"
98
99     return os.path.join(get_logs_dir_path(), bbs, board, "subject.txt")
100
101 def get_thread_states_path(bbs, board, thread):
102     # if parameter is empty, raise ValueError
103     if not bbs or not board or not thread:
104         raise ValueError, "parameter must not be empty"
105
106     return os.path.join(get_thread_states_dir_path(bbs, board),
107                         thread + ".states")
108
109 def get_board_states_path(bbs, board):
110     # if parameter is empty, raise ValueError
111     if not bbs or not board:
112         raise ValueError, "parameter must not be empty"
113
114     return os.path.join(get_board_dir_path(bbs, board), "board.states")
115
116 def get_board_idx_path(bbs, board):
117     """Returns board idx file path
118
119     bbs: bbs id
120
121     board: board id
122     """
123
124     # if parameter is empty, raise ValueError
125     if not bbs or not board:
126         raise ValueError, "parameter must not be empty"
127
128     return os.path.join(get_logs_dir_path(), bbs, board, "subject.idx")
129
130 def get_board_dir_path(bbs, board):
131     """Returns board dir path
132
133     bbs: bbs ID
134
135     board: board ID
136     """
137
138     # if parameter is empty, raise ValueError
139     if not bbs or not board:
140         raise ValueError, "parameter must not be empty"
141
142     return os.path.join(get_logs_dir_path(), bbs, board)
143
144 def get_thread_idx_path(bbs, board, thread):
145     """Returns idx file path of thread
146
147     bbs: bbs ID
148
149     board: board ID
150
151     thread: thread ID
152
153     Note: if parameter is empty, raise ValueError
154     """
155
156     # if parameter is empty, raise ValueError
157     if not bbs or not board or not thread:
158         raise ValueError, "parameter must not be empty"
159
160     return os.path.join(get_thread_idx_dir_path(bbs, board), thread + ".idx")
161
162 def get_board_cache_path(bbs, board):
163     """ Returns .cache file path of board
164
165     bbs: bbs ID
166
167     board: board ID
168
169     Note: if parameter is empty, raise ValueError
170     """
171
172     # if parameter is empty, raise ValueError
173     if not bbs or not board:
174         raise ValueError, "parameter must not be empty"
175
176     return os.path.join(get_thread_idx_dir_path(bbs, board), ".cache")
177
178 def httpdate_to_secs(httpdate):
179     """Returns the seconds since the epoch"""
180
181     m = REG_EXPR_HTTPDATE.match(httpdate)
182     if m:
183         tm_wday = WDAY_DICT[m.group(1)]
184         tm_mday = int(m.group(2))
185         tm_mon = MON_DICT[m.group(3)]
186         tm_year = int(m.group(4))
187         tm_hour = int(m.group(5))
188         tm_min = int(m.group(6))
189         tm_sec = int(m.group(7))
190
191         return int(time.mktime(
192             (tm_year,tm_mon,tm_mday,tm_hour,tm_min,tm_sec,tm_wday,0,-1)) \
193             - time.timezone)
194     else:
195         raise ValueError
196
197
198 class ThreadInvoker(threading.Thread):
199     def __init__(self, on_end, *methods):
200         super(ThreadInvoker, self).__init__()
201         self.on_end = on_end
202         self.methods = methods
203     def run(self):
204         try:
205             for m in self.methods:
206                 m()
207         finally:
208             self.on_end()
209
210
211 class FileWrap:
212     def __init__(self, path):
213         self._file = None
214         self._path = path
215     def __del__(self):
216         self.close()
217     def seek(self, size):
218         self.file().seek(size)
219     def write(self, data):
220         self.file().write(data)
221     def close(self):
222         if self._file:
223             self._file.close()
224             self._file = None
225     def file(self):
226         if not self._file:
227             basedir = os.path.dirname(self._path)
228             if not os.path.isdir(basedir):
229                 os.makedirs(basedir)
230             self._file = file(self._path, "a+")
231         return self._file