1#! /usr/bin/env python3 

2 

3"""Initial setup of an archive.""" 

4# Copyright (C) 2002, 2004, 2006 James Troup <james@nocrew.org> 

5 

6# This program is free software; you can redistribute it and/or modify 

7# it under the terms of the GNU General Public License as published by 

8# the Free Software Foundation; either version 2 of the License, or 

9# (at your option) any later version. 

10 

11# This program is distributed in the hope that it will be useful, 

12# but WITHOUT ANY WARRANTY; without even the implied warranty of 

13# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 

14# GNU General Public License for more details. 

15 

16# You should have received a copy of the GNU General Public License 

17# along with this program; if not, write to the Free Software 

18# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 

19 

20################################################################################ 

21 

22import os 

23import sys 

24import apt_pkg 

25from daklib import utils 

26from daklib.dbconn import * 

27 

28################################################################################ 

29 

30Cnf = None 

31 

32################################################################################ 

33 

34 

35def usage(exit_code=0): 

36 """Print a usage message and exit with 'exit_code'.""" 

37 

38 print("""Usage: dak init-dirs 

39Creates directories for an archive based on dak.conf configuration file. 

40 

41 -h, --help show this help and exit.""") 

42 sys.exit(exit_code) 

43 

44################################################################################ 

45 

46 

47def do_dir(target, config_name): 

48 """If 'target' exists, make sure it is a directory. If it doesn't, create 

49it.""" 

50 

51 if os.path.exists(target): 

52 if not os.path.isdir(target): 52 ↛ 53line 52 didn't jump to line 53, because the condition on line 52 was never true

53 utils.fubar("%s (%s) is not a directory." 

54 % (target, config_name)) 

55 else: 

56 print("Creating {} ...".format(target)) 

57 os.makedirs(target) 

58 

59 

60def process_file(config, config_name): 

61 """Create directories for a config entry that's a filename.""" 

62 

63 if config_name in config: 

64 target = os.path.dirname(config[config_name]) 

65 do_dir(target, config_name) 

66 

67 

68def process_tree(config, tree): 

69 """Create directories for a config tree.""" 

70 

71 for entry in config.subtree(tree).list(): 

72 entry = entry.lower() 

73 config_name = "%s::%s" % (tree, entry) 

74 target = config[config_name] 

75 do_dir(target, config_name) 

76 

77 

78def process_morguesubdir(subdir): 

79 """Create directories for morgue sub directories.""" 

80 

81 config_name = "%s::MorgueSubDir" % (subdir) 

82 if config_name in Cnf: 82 ↛ 83line 82 didn't jump to line 83, because the condition on line 82 was never true

83 target = os.path.join(Cnf["Dir::Morgue"], Cnf[config_name]) 

84 do_dir(target, config_name) 

85 

86 

87def process_keyring(fullpath, secret=False): 

88 """Create empty keyring if necessary.""" 

89 

90 if os.path.exists(fullpath): 90 ↛ 91line 90 didn't jump to line 91, because the condition on line 90 was never true

91 return 

92 

93 keydir = os.path.dirname(fullpath) 

94 

95 if not os.path.isdir(keydir): 95 ↛ 96line 95 didn't jump to line 96, because the condition on line 95 was never true

96 print("Creating {} ...".format(keydir)) 

97 os.makedirs(keydir) 

98 if secret: 

99 # Make sure secret keyring directories are 0700 

100 os.chmod(keydir, 0o700) 

101 

102 # Touch the file 

103 print("Creating {} ...".format(fullpath)) 

104 with open(fullpath, 'w') as fh: 

105 if secret: 105 ↛ 106line 105 didn't jump to line 106, because the condition on line 105 was never true

106 os.fchmod(fh.fileno(), 0o600) 

107 else: 

108 os.fchmod(fh.fileno(), 0o644) 

109 

110###################################################################### 

111 

112 

113def create_directories(): 

114 """Create directories referenced in dak.conf.""" 

115 

116 session = DBConn().session() 

117 

118 # Process directories from dak.conf 

119 process_tree(Cnf, "Dir") 

120 

121 # Hardcode creation of the unchecked directory 

122 if "Dir::Base" in Cnf: 122 ↛ 126line 122 didn't jump to line 126, because the condition on line 122 was never false

123 do_dir(os.path.join(Cnf["Dir::Base"], "queue", "unchecked"), 'unchecked directory') 

124 

125 # Process queue directories 

126 for queue in session.query(PolicyQueue): 

127 do_dir(queue.path, '%s queue' % queue.queue_name) 

128 # If we're doing the NEW queue, make sure it has a COMMENTS directory 

129 if queue.queue_name == 'new': 

130 do_dir(os.path.join(queue.path, "COMMENTS"), '%s queue comments' % queue.queue_name) 

131 

132 for config_name in ["Rm::LogFile", 

133 "Import-Archive::ExportDir"]: 

134 process_file(Cnf, config_name) 

135 

136 for subdir in ["Clean-Queues", "Clean-Suites"]: 

137 process_morguesubdir(subdir) 

138 

139 suite_suffix = "%s" % (Cnf.find("Dinstall::SuiteSuffix")) 

140 

141 # Process secret keyrings 

142 if 'Dinstall::SigningKeyring' in Cnf: 142 ↛ 143line 142 didn't jump to line 143, because the condition on line 142 was never true

143 process_keyring(Cnf['Dinstall::SigningKeyring'], secret=True) 

144 

145 if 'Dinstall::SigningPubKeyring' in Cnf: 145 ↛ 146line 145 didn't jump to line 146, because the condition on line 145 was never true

146 process_keyring(Cnf['Dinstall::SigningPubKeyring'], secret=True) 

147 

148 # Process public keyrings 

149 for keyring in session.query(Keyring).filter_by(active=True): 

150 process_keyring(keyring.keyring_name) 

151 

152 # Process dists directories 

153 # TODO: Store location of each suite in database 

154 for suite in session.query(Suite): 

155 suite_dir = os.path.join(suite.archive.path, 'dists', suite.suite_name, suite_suffix) 

156 

157 # TODO: Store valid suite/component mappings in database 

158 for component in session.query(Component): 

159 component_name = component.component_name 

160 

161 sc_dir = os.path.join(suite_dir, component_name) 

162 

163 do_dir(sc_dir, "%s/%s" % (suite.suite_name, component_name)) 

164 

165 for arch in suite.architectures: 165 ↛ 166line 165 didn't jump to line 166, because the loop on line 165 never started

166 if arch.arch_string == 'source': 

167 arch_string = 'source' 

168 else: 

169 arch_string = 'binary-%s' % arch.arch_string 

170 

171 suite_arch_dir = os.path.join(sc_dir, arch_string) 

172 

173 do_dir(suite_arch_dir, "%s/%s/%s" % (suite.suite_name, component_name, arch_string)) 

174 

175################################################################################ 

176 

177 

178def main(): 

179 """Initial setup of an archive.""" 

180 

181 global Cnf 

182 

183 Cnf = utils.get_conf() 

184 arguments = [('h', "help", "Init-Dirs::Options::Help")] 

185 for i in ["help"]: 

186 key = "Init-Dirs::Options::%s" % i 

187 if key not in Cnf: 187 ↛ 185line 187 didn't jump to line 185, because the condition on line 187 was never false

188 Cnf[key] = "" 

189 

190 d = DBConn() 

191 

192 arguments = apt_pkg.parse_commandline(Cnf, arguments, sys.argv) 

193 

194 options = Cnf.subtree("Init-Dirs::Options") 

195 if options["Help"]: 

196 usage() 

197 elif arguments: 197 ↛ 198line 197 didn't jump to line 198, because the condition on line 197 was never true

198 utils.warn("dak init-dirs takes no arguments.") 

199 usage(exit_code=1) 

200 

201 create_directories() 

202 

203################################################################################ 

204 

205 

206if __name__ == '__main__': 

207 main()