1
2 """
3
4 @author: Fabio Erculiani <lxnay@sabayonlinux.org>
5 @contact: lxnay@sabayonlinux.org
6 @copyright: Fabio Erculiani
7 @license: GPL-2
8
9 B{Entropy Package Manager Server Main Interfaces}.
10
11 """
12
13 from __future__ import with_statement
14 import os
15 import shutil
16 from entropy.core import Singleton
17 from entropy.exceptions import OnlineMirrorError, PermissionDenied, \
18 SystemDatabaseError
19 from entropy.const import etpConst, etpSys, const_setup_perms, \
20 const_create_working_dirs, const_extract_srv_repo_params, etpUi
21 from entropy.output import TextInterface, purple, red, darkgreen, \
22 bold, brown, blue, darkred
23 from entropy.server.interfaces.mirrors import Server as MirrorsServer
24 from entropy.i18n import _
25 from entropy.core.settings.base import SystemSettings
26 from entropy.core.settings.plugins.skel import SystemSettingsPlugin
27 from entropy.transceivers import FtpInterface
28 from entropy.db import EntropyRepository
29 from entropy.spm.plugins.factory import get_default_instance as get_spm
30
32
34
35 """
36 Parses Entropy server system configuration file.
37
38 @return dict data
39 """
40
41 data = {
42 'repositories': etpConst['server_repositories'].copy(),
43 'default_repository_id': etpConst['officialserverrepositoryid'],
44 'packages_expiration_days': etpConst['packagesexpirationdays'],
45 'database_file_format': etpConst['etpdatabasefileformat'],
46 'disabled_eapis': set(),
47 'exp_based_scope': etpConst['expiration_based_scope'],
48 'rss': {
49 'enabled': etpConst['rss-feed'],
50 'name': etpConst['rss-name'],
51 'base_url': etpConst['rss-base-url'],
52 'website_url': etpConst['rss-website-url'],
53 'editor': etpConst['rss-managing-editor'],
54 'max_entries': etpConst['rss-max-entries'],
55 'light_max_entries': etpConst['rss-light-max-entries'],
56 },
57 }
58
59 fake_instance = self._helper.fake_default_repo
60
61 if not os.access(etpConst['serverconf'], os.R_OK):
62 return data
63
64 with open(etpConst['serverconf'],"r") as server_f:
65 serverconf = [x.strip() for x in server_f.readlines() if x.strip()]
66
67 for line in serverconf:
68
69 split_line = line.split("|")
70 split_line_len = len(split_line)
71
72 if (line.find("officialserverrepositoryid|") != -1) and \
73 (not line.startswith("#")) and (split_line_len == 2):
74
75 if not fake_instance:
76 data['default_repository_id'] = split_line[1].strip()
77
78 elif line.startswith("expiration-days|") and (split_line_len == 2):
79
80 mydays = split_line[1].strip()
81 try:
82 mydays = int(mydays)
83 data['packages_expiration_days'] = mydays
84 except ValueError:
85 continue
86
87 elif line.startswith("expiration-based-scope|") and \
88 (split_line_len == 2):
89
90 exp_opt = split_line[1].strip().lower()
91 if exp_opt in ("enable", "enabled", "true", "1", "yes"):
92 data['exp_based_scope'] = True
93 else:
94 data['exp_based_scope'] = False
95
96 elif line.startswith("disabled-eapis|") and (split_line_len == 2):
97
98 mydis = split_line[1].strip().split(",")
99 try:
100 mydis = [int(x) for x in mydis]
101 mydis = set([x for x in mydis if x in (1, 2, 3,)])
102 except ValueError:
103 continue
104 if (len(mydis) < 3) and mydis:
105 data['disabled_eapis'] = mydis
106
107
108 elif line.startswith("repository|") and (split_line_len in [5, 6]) \
109 and (not fake_instance):
110
111 repoid, repodata = const_extract_srv_repo_params(line,
112 product = sys_set['repositories']['product'])
113 if repoid in data['repositories']:
114
115 data['repositories'][repoid]['mirrors'].extend(
116 repodata['mirrors'])
117 else:
118 data['repositories'][repoid] = repodata.copy()
119
120 elif line.startswith("database-format|") and (split_line_len == 2):
121
122 fmt = split_line[1]
123 if fmt in etpConst['etpdatabasesupportedcformats']:
124 data['database_file_format'] = fmt
125
126 elif line.startswith("rss-feed|") and (split_line_len == 2):
127
128 feed = split_line[1]
129 if feed in ("enable", "enabled", "true", "1"):
130 data['rss']['enabled'] = True
131 elif feed in ("disable", "disabled", "false", "0", "no",):
132 data['rss']['enabled'] = False
133
134 elif line.startswith("rss-name|") and (split_line_len == 2):
135
136 feedname = line.split("rss-name|")[1].strip()
137 data['rss']['name'] = feedname
138
139 elif line.startswith("rss-base-url|") and (split_line_len == 2):
140
141 data['rss']['base_url'] = line.split("rss-base-url|")[1].strip()
142 if not data['rss']['base_url'][-1] == "/":
143 data['rss']['base_url'] += "/"
144
145 elif line.startswith("rss-website-url|") and (split_line_len == 2):
146
147 data['rss']['website_url'] = split_line[1].strip()
148
149 elif line.startswith("managing-editor|") and (split_line_len == 2):
150
151 data['rss']['editor'] = split_line[1].strip()
152
153 elif line.startswith("max-rss-entries|") and (split_line_len == 2):
154
155 try:
156 entries = int(split_line[1].strip())
157 data['rss']['max_entries'] = entries
158 except (ValueError, IndexError,):
159 continue
160
161 elif line.startswith("max-rss-light-entries|") and \
162 (split_line_len == 2):
163
164 try:
165 entries = int(split_line[1].strip())
166 data['rss']['light_max_entries'] = entries
167 except (ValueError, IndexError,):
168 continue
169
170
171 if self._helper.community_repo:
172 data['repositories'][etpConst['clientserverrepoid']] = {}
173 mydata = {}
174 mydata['description'] = "Community Repositories System Database"
175 mydata['mirrors'] = []
176 mydata['community'] = False
177 data['repositories'][etpConst['clientserverrepoid']].update(mydata)
178
179
180 for repoid in data['repositories']:
181 data['repositories'][repoid]['packages_dir'] = \
182 os.path.join( etpConst['entropyworkdir'],
183 "server",
184 repoid,
185 "packages",
186 etpSys['arch']
187 )
188 data['repositories'][repoid]['store_dir'] = \
189 os.path.join( etpConst['entropyworkdir'],
190 "server",
191 repoid,
192 "store",
193 etpSys['arch']
194 )
195 data['repositories'][repoid]['upload_dir'] = \
196 os.path.join( etpConst['entropyworkdir'],
197 "server",
198 repoid,
199 "upload",
200 etpSys['arch']
201 )
202 data['repositories'][repoid]['database_dir'] = \
203 os.path.join( etpConst['entropyworkdir'],
204 "server",
205 repoid,
206 "database",
207 etpSys['arch']
208 )
209 data['repositories'][repoid]['packages_relative_path'] = \
210 os.path.join( sys_set['repositories']['product'],
211 repoid,
212 "packages",
213 etpSys['arch']
214 )+"/"
215 data['repositories'][repoid]['database_relative_path'] = \
216 os.path.join( sys_set['repositories']['product'],
217 repoid,
218 "database",
219 etpSys['arch']
220 )+"/"
221
222
223 shell_repoid = os.getenv('ETP_REPO')
224 if shell_repoid:
225 data['default_repository_id'] = shell_repoid
226
227 expiration_days = os.getenv('ETP_EXPIRATION_DAYS')
228 if expiration_days:
229 try:
230 expiration_days = int(expiration_days)
231 data['packages_expiration_days'] = expiration_days
232 except ValueError:
233 pass
234
235 return data
236
238
239 import entropy.tools as entropyTools
240
242
243 data = {}
244 srv_plug_id = etpConst['system_settings_plugins_ids']['server_plugin']
245
246 srv_parser_data = sys_set[srv_plug_id]['server']
247 if not srv_parser_data['exp_based_scope']:
248 return data
249
250
251 for repoid in srv_parser_data['repositories']:
252
253
254
255 if repoid == etpConst['clientserverrepoid']:
256 continue
257
258 idpackages = set()
259 exp_fp = self._helper.get_local_exp_based_pkgs_rm_whitelist_file(
260 repo = repoid)
261 dbconn = self._helper.open_server_repository(
262 just_reading = True, repo = repoid)
263
264 if os.access(exp_fp, os.R_OK | os.F_OK):
265 pkgs = self.entropyTools.generic_file_content_parser(exp_fp)
266 if '*' in pkgs:
267 idpackages.add(-1)
268 else:
269 for pkg in pkgs:
270 idpackage, rc_match = dbconn.atomMatch(pkg)
271 if rc_match:
272 continue
273 idpackages.add(idpackage)
274
275 data[repoid] = idpackages
276
277 return data
278
279
280 -class Server(Singleton, TextInterface):
281
282 - def init_singleton(self, default_repository = None, save_repository = False,
283 community_repo = False, fake_default_repo = False,
284 fake_default_repo_id = '::fake::',
285 fake_default_repo_desc = 'this is a fake repository'):
286
287 self.__instance_destroyed = False
288 if etpConst['uid'] != 0:
289 mytxt = _("Entropy Server interface must be run as root")
290 raise PermissionDenied("PermissionDenied: %s" % (mytxt,))
291
292
293 self.SystemSettings = SystemSettings()
294 self.community_repo = community_repo
295 from entropy.db import dbapi2
296 self.dbapi2 = dbapi2
297 etpSys['serverside'] = True
298 self._memory_db_instances = {}
299 self.fake_default_repo = fake_default_repo
300 self.indexing = False
301 self.xcache = False
302 self.MirrorsService = None
303 self.__server_dbcache = {}
304 self.repository_treeupdate_digests = {}
305 self.__settings_to_backup = []
306 self.__do_save_repository = save_repository
307 self.__sync_lock_cache = set()
308 self.rssMessages = {
309 'added': {},
310 'removed': {},
311 'commitmessage': "",
312 'light': {},
313 }
314
315 if fake_default_repo:
316 default_repository = fake_default_repo_id
317 etpConst['officialserverrepositoryid'] = fake_default_repo_id
318 self.init_generic_memory_server_repository(fake_default_repo_id,
319 fake_default_repo_desc)
320
321
322 self.sys_settings_plugin_id = \
323 etpConst['system_settings_plugins_ids']['server_plugin']
324 self.sys_settings_plugin = ServerSystemSettingsPlugin(
325 self.sys_settings_plugin_id, self)
326 self.SystemSettings.add_plugin(self.sys_settings_plugin)
327
328
329 self.sys_settings_fatscope_plugin_id = \
330 etpConst['system_settings_plugins_ids']['server_plugin_fatscope']
331 self.sys_settings_fatscope_plugin = ServerFatscopeSystemSettingsPlugin(
332 self.sys_settings_fatscope_plugin_id, self)
333 self.SystemSettings.add_plugin(self.sys_settings_fatscope_plugin)
334
335 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
336 self.default_repository = default_repository
337 if self.default_repository == None:
338 self.default_repository = srv_set['default_repository_id']
339
340 if self.default_repository in srv_set['repositories']:
341 self.ensure_paths(self.default_repository)
342
343
344
345
346 if self.default_repository not in srv_set['repositories']:
347 raise PermissionDenied("PermissionDenied: %s %s" % (
348 self.default_repository,
349 _("repository not configured"),
350 )
351 )
352 if etpConst['clientserverrepoid'] == self.default_repository:
353 raise PermissionDenied("PermissionDenied: %s %s" % (
354 etpConst['clientserverrepoid'],
355 _("protected repository id, can't use this, sorry dude..."),
356 )
357 )
358
359 self.switch_default_repository(self.default_repository)
360
362 self.__instance_destroyed = True
363 if hasattr(self,'ClientService'):
364 self.ClientService.destroy()
365 if hasattr(self,'sys_settings_server_plugin'):
366 try:
367 self.SystemSettings.remove_plugin(self.sys_settings_plugin_id)
368 except KeyError:
369 pass
370 if hasattr(self,'sys_settings_fatscope_plugin'):
371 try:
372 self.SystemSettings.remove_plugin(
373 self.sys_settings_fatscope_plugin)
374 except KeyError:
375 pass
376 self.close_server_databases()
377
379 return self.__instance_destroyed
380
383
392
393
395 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
396 migrated_filename = '.branch_migrated'
397 for repoid in srv_set['repositories'].keys():
398
399 if repoid == etpConst['clientserverrepoid']: continue
400 mydir = srv_set['repositories'][repoid]['database_dir']
401 if not os.path.isdir(mydir):
402 continue
403
404 migrated_filepath = os.path.join(mydir, migrated_filename)
405 if os.path.isfile(migrated_filepath):
406 continue
407
408 my_branched_dir = self.get_local_database_dir(repoid)
409 if os.path.isdir(my_branched_dir):
410 continue
411
412 self.updateProgress(
413 "[%s:%s] %s: %s, %s: %s" % (
414 brown("repo"),
415 purple(repoid),
416 _("migrating database path from"),
417 brown(mydir),
418 _('to'),
419 brown(my_branched_dir),
420 ),
421 importance = 1,
422 type = "info",
423 header = bold(" @@ ")
424 )
425
426 repo_files = [os.path.join(mydir, x) for x in os.listdir(mydir) if \
427 (os.path.isfile(os.path.join(mydir, x)) and \
428 os.access(os.path.join(mydir, x), os.W_OK))
429 ]
430 os.makedirs(my_branched_dir)
431 const_setup_perms(my_branched_dir, etpConst['entropygid'])
432
433 for repo_file in repo_files:
434 repo_filename = os.path.basename(repo_file)
435 shutil.move(repo_file,
436 os.path.join(my_branched_dir, repo_filename))
437
438 f_migrated = open(migrated_filepath,"w")
439 f_migrated.write("done\n")
440 f_migrated.flush()
441 f_migrated.close()
442
466
468 """
469 Get Source Package Manager interface instance.
470
471 @return: Source Package Manager interface instance
472 @rtype: entropy.spm.plugins.skel.SpmPlugin based instance
473 """
474 return get_spm(self)
475
477 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
478 backup_list = [
479 'etpdatabaseclientfilepath',
480 'clientdbid',
481 {'server': srv_set.copy()},
482 ]
483 for setting in backup_list:
484 if setting not in self.__settings_to_backup:
485 self.__settings_to_backup.append(setting)
486
487 if not self.community_repo:
488 etpConst['etpdatabaseclientfilepath'] = \
489 self.get_local_database_file(repo)
490 etpConst['clientdbid'] = etpConst['serverdbid']
491 const_create_working_dirs()
492
494 if hasattr(self,'serverDbCache'):
495 for item in self.__server_dbcache:
496 try:
497 self.__server_dbcache[item].closeDB()
498 except self.dbapi2.ProgrammingError:
499 pass
500 self.__server_dbcache.clear()
501
503 found = None
504 for item in self.__server_dbcache:
505 if dbinstance == self.__server_dbcache[item]:
506 found = item
507 break
508 if found:
509 instance = self.__server_dbcache.pop(found)
510 instance.closeDB()
511
513 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
514 return srv_set['repositories'].copy()
515
543
545 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
546 if self.community_repo:
547 for repoid in srv_set['repositories']:
548 srv_set['repositories'][repoid]['community'] = True
549
550
552
553 if not self.is_repository_initialized(repoid):
554 mytxt = blue("%s.") % (
555 _("Your default repository is not initialized"),)
556 self.updateProgress(
557 "[%s:%s] %s" % (
558 brown("repo"),
559 purple(repoid),
560 mytxt,
561 ),
562 importance = 1,
563 type = "warning",
564 header = darkred(" !!! ")
565 )
566 answer = self.askQuestion(
567 _("Do you want to initialize your default repository ?"))
568 if answer == "No":
569 mytxt = red("%s.") % (
570 _("Continuing with an uninitialized repository"),)
571 self.updateProgress(
572 "[%s:%s] %s" % (
573 brown("repo"),
574 purple(repoid),
575 mytxt,
576 ),
577 importance = 1,
578 type = "warning",
579 header = darkred(" !!! ")
580 )
581 else:
582
583 dbfile = self.get_local_database_file(repoid)
584 if os.path.isfile(dbfile):
585 shutil.move(dbfile, dbfile+".backup")
586 self.initialize_server_database(empty = True,
587 repo = repoid, warnings = False)
588
589
591 type_txt = _("server-side repository")
592 if self.community_repo:
593 type_txt = _("community repository")
594
595 mytxt = _("Entropy Server Interface Instance on repository")
596 self.updateProgress(
597 blue("%s: %s, %s: %s (%s: %s)" % (
598 mytxt,
599 red(self.default_repository),
600 _("current branch"),
601 darkgreen(self.SystemSettings['repositories']['branch']),
602 purple(_("type")),
603 bold(type_txt),
604 )
605 ),
606 importance = 2,
607 type = "info",
608 header = red(" @@ ")
609 )
610 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
611 repos = srv_set['repositories'].keys()
612 mytxt = blue("%s:") % (_("Currently configured repositories"),)
613 self.updateProgress(
614 mytxt,
615 importance = 1,
616 type = "info",
617 header = red(" @@ ")
618 )
619 for repo in repos:
620 self.updateProgress(
621 darkgreen(repo),
622 importance = 0,
623 type = "info",
624 header = brown(" # ")
625 )
626
627
629
630
631 if repoid == etpConst['clientserverrepoid']:
632 return
633
634 if os.path.isfile(etpConst['serverconf']):
635 f_srv = open(etpConst['serverconf'],"r")
636 content = f_srv.readlines()
637 f_srv.close()
638 content = [x.strip() for x in content]
639 found = False
640 new_content = []
641 for line in content:
642 if line.strip().startswith("officialserverrepositoryid|"):
643 line = "officialserverrepositoryid|%s" % (repoid,)
644 found = True
645 new_content.append(line)
646 if not found:
647 new_content.append("officialserverrepositoryid|%s" % (repoid,))
648 f_srv_t = open(etpConst['serverconf']+".save_default_repo_tmp","w")
649 for line in new_content:
650 f_srv_t.write(line+"\n")
651 f_srv_t.flush()
652 f_srv_t.close()
653 os.rename(etpConst['serverconf']+".save_default_repo_tmp",
654 etpConst['serverconf'])
655 else:
656 f_srv = open(etpConst['serverconf'],"w")
657 f_srv.write("officialserverrepositoryid|%s\n" % (repoid,))
658 f_srv.flush()
659 f_srv.close()
660
662
663
664 if repoid == etpConst['clientserverrepoid']:
665 return False
666
667 if not os.path.isfile(etpConst['serverconf']):
668 return None
669 f_srv = open(etpConst['serverconf'])
670 tmpfile = etpConst['serverconf']+".switch"
671 mycontent = [x.strip() for x in f_srv.readlines()]
672 f_srv.close()
673 f_tmp = open(tmpfile,"w")
674 st = "repository|%s" % (repoid,)
675 status = False
676 for line in mycontent:
677 if enable:
678 if (line.find(st) != -1) and line.startswith("#") and \
679 (len(line.split("|")) == 5):
680 line = line[1:]
681 status = True
682 else:
683 if (line.find(st) != -1) and not line.startswith("#") and \
684 (len(line.split("|")) == 5):
685 line = "#"+line
686 status = True
687 f_tmp.write(line+"\n")
688 f_tmp.flush()
689 f_tmp.close()
690 shutil.move(tmpfile, etpConst['serverconf'])
691 if status:
692 self.close_server_databases()
693 self.SystemSettings.clear()
694 self.setup_services()
695 self.show_interface_status()
696 return status
697
704
713
714 dbc = self.open_server_repository(just_reading = True, repo = repo)
715 valid = do_validate(dbc)
716 self.close_server_database(dbc)
717 if not valid:
718 dbc = self.open_server_repository(read_only = False,
719 no_upload = True, repo = repo, is_new = True)
720 valid = do_validate(dbc)
721 self.close_server_database(dbc)
722
723 return valid
724
726
727 if repo == None:
728 repo = self.default_repository
729
730
731 lock_file = self.MirrorsService.get_database_lockfile(repo)
732 if os.path.isfile(lock_file):
733 self.updateProgress(
734 red(_("Entropy database is already locked by you :-)")),
735 importance = 1,
736 type = "info",
737 header = red(" * ")
738 )
739 else:
740
741 mytxt = "%s ..." % (_("Locking and Syncing Entropy database"),)
742 self.updateProgress(
743 red(mytxt),
744 importance = 1,
745 type = "info",
746 header = red(" * "),
747 back = True
748 )
749 for uri in self.get_remote_mirrors(repo):
750 given_up = self.MirrorsService.mirror_lock_check(uri,
751 repo = repo)
752 if given_up:
753 crippled_uri = \
754 self.entropyTools.extract_ftp_host_from_uri(uri)
755 mytxt = "%s:" % (_("Mirrors status table"),)
756 self.updateProgress(
757 darkgreen(mytxt),
758 importance = 1,
759 type = "info",
760 header = brown(" * ")
761 )
762 dbstatus = self.MirrorsService.get_mirrors_lock(repo = repo)
763 for db_uri, db_st1, db_st2 in dbstatus:
764 db_st1_info = darkgreen(_("Unlocked"))
765 if db_st1:
766 db_st1_info = red(_("Locked"))
767 db_st2_info = darkgreen(_("Unlocked"))
768 if db_st2:
769 db_st2_info = red(_("Locked"))
770
771 crippled_uri = \
772 self.entropyTools.extract_ftp_host_from_uri(db_uri)
773 self.updateProgress(
774 "%s: [%s: %s] [%s: %s]" % (
775 bold(crippled_uri),
776 brown(_("database")),
777 db_st1_info,
778 brown(_("download")),
779 db_st2_info,
780 ),
781 importance = 1,
782 type = "info",
783 header = "\t"
784 )
785
786 raise OnlineMirrorError("OnlineMirrorError: %s %s" % (
787 _("cannot lock mirror"),
788 crippled_uri,
789 )
790 )
791
792
793 self.MirrorsService.lock_mirrors(True, repo = repo)
794 self.MirrorsService.sync_databases(no_upload, repo = repo)
795
796
799
800 if mirrors is None:
801 mirrors = []
802 dbc = self.open_memory_database(dbname = etpConst['serverdbid']+repoid)
803 self._memory_db_instances[repoid] = dbc
804
805 eapi3_port = int(etpConst['socket_service']['port'])
806 eapi3_ssl_port = int(etpConst['socket_service']['ssl_port'])
807
808 repodata = {
809 'repoid': repoid,
810 'description': description,
811 'mirrors': mirrors,
812 'community': community_repo,
813 'service_port': eapi3_port,
814 'ssl_service_port': eapi3_ssl_port,
815 'service_url': service_url,
816 'handler': '',
817 'in_memory': True,
818 }
819
820 etpConst['server_repositories'][repoid] = repodata
821 self.SystemSettings.clear()
822
823 return dbc
824
826 if dbname == None:
827 dbname = etpConst['genericdbid']
828 dbc = EntropyRepository(
829 readOnly = False,
830 dbFile = ':memory:',
831 clientDatabase = True,
832 dbname = dbname,
833 xcache = False,
834 indexing = False,
835 OutputInterface = self,
836 skipChecks = True
837 )
838 dbc.initializeDatabase()
839 return dbc
840
841 - def open_server_repository(
842 self,
843 read_only = True,
844 no_upload = True,
845 just_reading = False,
846 repo = None,
847 indexing = True,
848 warnings = True,
849 do_cache = True,
850 use_branch = None,
851 lock_remote = True,
852 is_new = False,
853 do_treeupdates = True
854 ):
855
856 if repo == None:
857 repo = self.default_repository
858
859 if repo == etpConst['clientserverrepoid'] and self.community_repo:
860 return self.ClientService.clientDbconn
861
862
863 if repo in self._memory_db_instances:
864 return self._memory_db_instances.get(repo)
865
866 if just_reading:
867 read_only = True
868 no_upload = True
869
870 local_dbfile = self.get_local_database_file(repo, use_branch)
871 if do_cache:
872 cached = self.__server_dbcache.get(
873 (repo, etpConst['systemroot'], local_dbfile, read_only,
874 no_upload, just_reading, use_branch, lock_remote,)
875 )
876 if cached != None:
877 return cached
878
879 local_dbfile_dir = os.path.dirname(local_dbfile)
880 if not os.path.isdir(local_dbfile_dir):
881 os.makedirs(local_dbfile_dir)
882
883 if (not read_only) and (lock_remote) and \
884 (repo not in self.__sync_lock_cache):
885 self.do_server_repository_sync_lock(repo, no_upload)
886 self.__sync_lock_cache.add(repo)
887
888 local_dbfile_exists = os.path.lexists(local_dbfile)
889 conn = EntropyRepository(
890 readOnly = read_only,
891 dbFile = local_dbfile,
892 noUpload = no_upload,
893 OutputInterface = self,
894 dbname = etpConst['serverdbid']+repo,
895 useBranch = use_branch,
896 lockRemote = lock_remote
897 )
898 if not local_dbfile_exists:
899
900 conn.readOnly = False
901 conn.initializeDatabase()
902 conn.commitChanges()
903
904 valid = True
905 try:
906 conn.validateDatabase()
907 except SystemDatabaseError:
908 valid = False
909
910
911
912 if (repo not in etpConst['server_treeupdatescalled']) and \
913 (not just_reading):
914
915
916 if valid:
917 if do_treeupdates:
918 self.repository_packages_spm_sync(conn,
919 branch = use_branch, repo = repo)
920 elif warnings and not is_new:
921 mytxt = _("Entropy database is corrupted!")
922 self.updateProgress(
923 darkred(mytxt),
924 importance = 1,
925 type = "warning",
926 header = bold(" !!! ")
927 )
928
929 if not read_only and valid and indexing:
930
931 self.updateProgress(
932 "[repo:%s|%s] %s" % (
933 blue(repo),
934 red(_("database")),
935 blue(_("indexing database")),
936 ),
937 importance = 1,
938 type = "info",
939 header = brown(" @@ "),
940 back = True
941 )
942 conn.createAllIndexes()
943
944 if do_cache:
945
946
947 self.__server_dbcache[
948 (repo, etpConst['systemroot'], local_dbfile, read_only,
949 no_upload, just_reading, use_branch, lock_remote,)] = conn
950
951
952 if (not read_only) and (not is_new):
953 cur_sets = conn.retrievePackageSets()
954 sys_sets = self.get_configured_package_sets(repo)
955 if cur_sets != sys_sets:
956 self.update_database_package_sets(repo, dbconn = conn)
957 conn.commitChanges()
958
959 return conn
960
962 """
963 Service method used to sync package names with Source Package Manager.
964 Source Package Manager can change package names, categories or slot
965 and Entropy repositories must be kept in sync.
966
967 In other words, it checks for /usr/portage/profiles/updates changes.
968 """
969
970 if branch == None:
971 branch = self.SystemSettings['repositories']['branch']
972 if repo == None:
973 repo = self.default_repository
974
975 etpConst['server_treeupdatescalled'].add(repo)
976
977 repo_updates_file = self.get_local_database_treeupdates_file(repo)
978 doRescan = False
979
980 stored_digest = repo_db.retrieveRepositoryUpdatesDigest(repo)
981 if stored_digest == -1:
982 doRescan = True
983
984
985 portage_dirs_digest = "0"
986 if not doRescan:
987
988 if self.repository_treeupdate_digests.has_key(repo):
989 portage_dirs_digest = self.repository_treeupdate_digests.get(
990 repo)
991 else:
992
993 spm = self.Spm()
994
995 updates_dir = etpConst['systemroot'] + \
996 spm.get_setting("PORTDIR") + "/profiles/updates"
997 if os.path.isdir(updates_dir):
998
999 mdigest = self.entropyTools.md5obj_directory(updates_dir)
1000
1001 if os.path.isfile(repo_updates_file):
1002 f = open(repo_updates_file)
1003 block = f.read(1024)
1004 while block:
1005 mdigest.update(block)
1006 block = f.read(1024)
1007 f.close()
1008 portage_dirs_digest = mdigest.hexdigest()
1009 self.repository_treeupdate_digests[repo] = \
1010 portage_dirs_digest
1011
1012 if doRescan or (str(stored_digest) != str(portage_dirs_digest)):
1013
1014
1015 repo_db.readOnly = False
1016 repo_db.noUpload = True
1017
1018
1019 repo_db.clearTreeupdatesEntries(repo)
1020
1021 updates_dir = etpConst['systemroot'] + \
1022 self.Spm().get_setting("PORTDIR") + "/profiles/updates"
1023 update_files = self.entropyTools.sort_update_files(
1024 os.listdir(updates_dir))
1025 update_files = [os.path.join(updates_dir, x) for x in update_files]
1026
1027 update_actions = []
1028 for update_file in update_files:
1029 f = open(update_file, "r")
1030 mycontent = f.readlines()
1031 f.close()
1032 lines = [x.strip() for x in mycontent if x.strip()]
1033 update_actions.extend(lines)
1034
1035
1036 if os.path.isfile(repo_updates_file):
1037 f = open(repo_updates_file, "r")
1038 mycontent = f.readlines()
1039 f.close()
1040 lines = [x.strip() for x in mycontent if x.strip() and \
1041 not x.strip().startswith("#")]
1042 update_actions.extend(lines)
1043
1044 update_actions = repo_db.filterTreeUpdatesActions(update_actions)
1045 if update_actions:
1046
1047 mytxt = "%s: %s. %s %s" % (
1048 bold(_("ATTENTION")),
1049 red(_("forcing package updates")),
1050 red(_("Syncing with")),
1051 blue(updates_dir),
1052 )
1053 self.updateProgress(
1054 mytxt,
1055 importance = 1,
1056 type = "info",
1057 header = brown(" * ")
1058 )
1059
1060 if repo_db.lockRemote:
1061 self.do_server_repository_sync_lock(
1062 repo, repo_db.noUpload)
1063
1064 try:
1065 quickpkg_list = repo_db.runTreeUpdatesActions(
1066 update_actions)
1067 except:
1068
1069 repo_db.setRepositoryUpdatesDigest(repo, "-1")
1070 raise
1071
1072 if quickpkg_list:
1073
1074 try:
1075 self._run_packages_spm_sync_quickpkg(
1076 quickpkg_list, repo_db, repo)
1077 except:
1078 self.entropyTools.print_traceback()
1079 mytxt = "%s: %s: %s, %s." % (
1080 bold(_("WARNING")),
1081 red(_("Cannot complete quickpkg for atoms")),
1082 blue(str(sorted(quickpkg_list))),
1083 _("do it manually"),
1084 )
1085 self.updateProgress(
1086 mytxt,
1087 importance = 1,
1088 type = "warning",
1089 header = darkred(" * ")
1090 )
1091 repo_db.commitChanges()
1092
1093
1094 repo_db.addRepositoryUpdatesActions(
1095 repo, update_actions, branch)
1096
1097
1098 repo_db.setRepositoryUpdatesDigest(
1099 repo, portage_dirs_digest)
1100 repo_db.commitChanges()
1101
1103 """
1104 Executes packages regeneration for given atoms.
1105 """
1106 package_paths = set()
1107 runatoms = set()
1108 for myatom in atoms:
1109 mymatch = repo_db.atomMatch(myatom)
1110 if mymatch[0] == -1:
1111 continue
1112 myatom = repo_db.retrieveAtom(mymatch[0])
1113 myatom = self.entropyTools.remove_tag(myatom)
1114 runatoms.add(myatom)
1115
1116 for myatom in runatoms:
1117
1118 self.updateProgress(
1119 red("%s: " % (_("repackaging"),) )+blue(myatom),
1120 importance = 1,
1121 type = "warning",
1122 header = blue(" # ")
1123 )
1124 mydest = self.get_local_store_directory(repo = repo)
1125 try:
1126 mypath = self.quickpkg(myatom, mydest)
1127 except:
1128
1129 mypath = os.path.join(mydest,
1130 os.path.basename(myatom) + etpConst['packagesext'])
1131 if os.path.isfile(mypath):
1132 os.remove(mypath)
1133 self.entropyTools.print_traceback()
1134 mytxt = "%s: %s: %s, %s." % (
1135 bold(_("WARNING")),
1136 red(_("Cannot complete quickpkg for atom")),
1137 blue(myatom),
1138 _("do it manually"),
1139 )
1140 self.updateProgress(
1141 mytxt,
1142 importance = 1,
1143 type = "warning",
1144 header = darkred(" * ")
1145 )
1146 continue
1147 package_paths.add(mypath)
1148 packages_data = [(x, False,) for x in package_paths]
1149 idpackages = self.add_packages_to_repository(
1150 packages_data, repo = repo)
1151
1152 if not idpackages:
1153
1154 mytxt = "%s: %s. %s." % (
1155 bold(_("ATTENTION")),
1156 red(_("package files rebuild did not run properly")),
1157 red(_("Please update packages manually")),
1158 )
1159 self.updateProgress(
1160 mytxt,
1161 importance = 1,
1162 type = "warning",
1163 header = darkred(" * ")
1164 )
1165
1167
1168 sys_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
1169 server_repos = sys_set['repositories'].keys()
1170 installed_packages = set()
1171
1172 if default_repo:
1173 server_repos = [default_repo]
1174
1175 for repo in server_repos:
1176 dbconn = self.open_server_repository(read_only = True,
1177 no_upload = True, repo = repo, do_treeupdates = False)
1178 installed_packages |= set([(x, repo) for x in \
1179 dbconn.listAllIdpackages()])
1180
1181
1182 deps_not_satisfied = set()
1183 length = str((len(installed_packages)))
1184 count = 0
1185 mytxt = _("Checking")
1186
1187 for idpackage, repo in installed_packages:
1188 count += 1
1189 dbconn = self.open_server_repository(read_only = True,
1190 no_upload = True, repo = repo, do_treeupdates = False)
1191
1192 if (count%150 == 0) or (count == length) or (count == 1):
1193 atom = dbconn.retrieveAtom(idpackage)
1194 self.updateProgress(
1195 darkgreen(mytxt)+" "+bold(atom),
1196 importance = 0,
1197 type = "info",
1198 back = True,
1199 count = (count, length),
1200 header = darkred(" @@ ")
1201 )
1202
1203 xdeps = dbconn.retrieveDependencies(idpackage)
1204 for xdep in xdeps:
1205 xid, xuseless = self.atom_match(xdep)
1206 if xid == -1:
1207 deps_not_satisfied.add(xdep)
1208
1209 return deps_not_satisfied
1210
1212
1213 mytxt = "%s %s" % (blue(_("Running dependencies test")), red("..."))
1214 self.updateProgress(
1215 mytxt,
1216 importance = 2,
1217 type = "info",
1218 header = red(" @@ ")
1219 )
1220
1221 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
1222 server_repos = srv_set['repositories'].keys()
1223 deps_not_matched = self.deps_tester(repo)
1224
1225 if deps_not_matched:
1226
1227 crying_atoms = {}
1228 for atom in deps_not_matched:
1229 for repo in server_repos:
1230 dbconn = self.open_server_repository(just_reading = True,
1231 repo = repo, do_treeupdates = False)
1232 riddep = dbconn.searchDependency(atom)
1233 if riddep == -1:
1234 continue
1235 ridpackages = dbconn.searchIdpackageFromIddependency(riddep)
1236 for i in ridpackages:
1237 iatom = dbconn.retrieveAtom(i)
1238 if not crying_atoms.has_key(atom):
1239 crying_atoms[atom] = set()
1240 crying_atoms[atom].add((iatom, repo))
1241
1242 mytxt = blue("%s:") % (_("These are the dependencies not found"),)
1243 self.updateProgress(
1244 mytxt,
1245 importance = 1,
1246 type = "info",
1247 header = red(" @@ ")
1248 )
1249 mytxt = "%s:" % (_("Needed by"),)
1250 for atom in deps_not_matched:
1251 self.updateProgress(
1252 red(atom),
1253 importance = 1,
1254 type = "info",
1255 header = blue(" # ")
1256 )
1257 if crying_atoms.has_key(atom):
1258 self.updateProgress(
1259 red(mytxt),
1260 importance = 0,
1261 type = "info",
1262 header = blue(" # ")
1263 )
1264 for my_dep, myrepo in crying_atoms[atom]:
1265 self.updateProgress(
1266 "[%s:%s] %s" % (
1267 blue(_("by repo")),
1268 darkred(myrepo),
1269 darkgreen(my_dep),
1270 ),
1271 importance = 0,
1272 type = "info",
1273 header = blue(" # ")
1274 )
1275 else:
1276
1277 mytxt = blue(_("Every dependency is satisfied. It's all fine."))
1278 self.updateProgress(
1279 mytxt,
1280 importance = 2,
1281 type = "info",
1282 header = red(" @@ ")
1283 )
1284
1285 return deps_not_matched
1286
1287 - def test_shared_objects(self, get_files = False, repo = None,
1288 dump_results_to_file = False):
1289
1290 pkg_list_path = None
1291 if dump_results_to_file:
1292 tmp_dir = os.path.dirname(self.entropyTools.get_random_temp_file())
1293 pkg_list_path = os.path.join(tmp_dir, "libtest_broken.txt")
1294 dmp_data = [
1295 (_("Broken and matched packages list"), pkg_list_path,),
1296 ]
1297 mytxt = "%s:" % (purple(_("Dumping results into these files")),)
1298 self.updateProgress(
1299 mytxt,
1300 importance = 1,
1301 type = "info",
1302 header = blue(" @@ ")
1303 )
1304 for txt, path in dmp_data:
1305 mytxt = "%s: %s" % (blue(txt), path,)
1306 self.updateProgress(
1307 mytxt,
1308 importance = 0,
1309 type = "info",
1310 header = darkgreen(" ## ")
1311 )
1312
1313
1314
1315 dbconn = self.open_server_repository(read_only = True,
1316 no_upload = True, repo = repo)
1317 QA = self.QA()
1318 packages_matched, brokenexecs, status = QA.test_shared_objects(dbconn,
1319 broken_symbols = True, dump_results_to_file = dump_results_to_file)
1320 if status != 0:
1321 return 1, None
1322
1323 if get_files:
1324 return 0, brokenexecs
1325
1326 if (not brokenexecs) and (not packages_matched):
1327 mytxt = "%s." % (_("System is healthy"),)
1328 self.updateProgress(
1329 blue(mytxt),
1330 importance = 2,
1331 type = "info",
1332 header = red(" @@ ")
1333 )
1334 return 0, None
1335
1336 mytxt = "%s..." % (_("Matching libraries with Spm, please wait"),)
1337 self.updateProgress(
1338 blue(mytxt),
1339 importance = 1,
1340 type = "info",
1341 header = red(" @@ ")
1342 )
1343
1344 packages = self.Spm().search_paths_owners(brokenexecs)
1345
1346 if packages:
1347 mytxt = "%s:" % (_("These are the matched packages"),)
1348 self.updateProgress(
1349 red(mytxt),
1350 importance = 1,
1351 type = "info",
1352 header = red(" @@ ")
1353 )
1354 for my_atom, my_elf_id in packages:
1355 package_slot = my_atom, my_elf_id
1356 self.updateProgress(
1357 "%s [elf:%s]" % (
1358 purple(my_atom),
1359 darkgreen(str(my_elf_id)),
1360 ),
1361 importance = 0,
1362 type = "info",
1363 header = red(" # ")
1364 )
1365 for filename in sorted(packages[package_slot]):
1366 self.updateProgress(
1367 darkgreen(filename),
1368 importance = 0,
1369 type = "info",
1370 header = brown(" => ")
1371 )
1372
1373 pkgstring_list = sorted(["%s:%s" % (
1374 self.entropyTools.dep_getkey(x[0]), x[1],) for x \
1375 in sorted(packages)])
1376 if pkg_list_path is not None:
1377 with open(pkg_list_path, "w") as pkg_f:
1378 for pkgstr in pkgstring_list:
1379 pkg_f.write(pkgstr + "\n")
1380 pkg_f.flush()
1381 pkgstring = ' '.join(pkgstring_list)
1382 mytxt = "%s: %s" % (darkgreen(_("Packages string")), pkgstring,)
1383 self.updateProgress(
1384 mytxt,
1385 importance = 1,
1386 type = "info",
1387 header = red(" @@ ")
1388 )
1389 else:
1390 self.updateProgress(
1391 red(_("No matched packages")),
1392 importance = 1,
1393 type = "info",
1394 header = red(" @@ ")
1395 )
1396
1397 return 0, packages
1398
1400
1401 mytxt = "%s %s" % (
1402 blue(_("Running orphaned SPM packages test")), red("..."),)
1403 self.updateProgress(
1404 mytxt,
1405 importance = 2,
1406 type = "info",
1407 header = red(" @@ ")
1408 )
1409 installed_packages = self.Spm().get_installed_packages()
1410 length = len(installed_packages)
1411 not_found = {}
1412 count = 0
1413 for installed_package in installed_packages:
1414 count += 1
1415 self.updateProgress(
1416 "%s: %s" % (
1417 darkgreen(_("Scanning package")),
1418 brown(installed_package),),
1419 importance = 0,
1420 type = "info",
1421 back = True,
1422 count = (count, length),
1423 header = darkred(" @@ ")
1424 )
1425 key, slot = (self.entropyTools.dep_getkey(installed_package),
1426 self.Spm().get_installed_package_metadata(installed_package,
1427 "SLOT"),)
1428 pkg_atom = "%s:%s" % (key, slot,)
1429 tree_atom = self.Spm().match_package(pkg_atom)
1430 if not tree_atom:
1431 not_found[installed_package] = pkg_atom
1432 self.updateProgress(
1433 "%s: %s" % (
1434 blue(pkg_atom),
1435 darkred(_("not found anymore")),
1436 ),
1437 importance = 0,
1438 type = "warning",
1439 count = (count, length),
1440 header = darkred(" @@ ")
1441 )
1442
1443 if not_found:
1444 not_found_list = ' '.join([not_found[x] for x in sorted(not_found)])
1445 self.updateProgress(
1446 "%s: %s" % (
1447 blue(_("Packages string")),
1448 not_found_list,
1449 ),
1450 importance = 0,
1451 type = "warning",
1452 count = (count, length),
1453 header = darkred(" @@ ")
1454 )
1455
1456 return not_found
1457
1464
1471
1473 if dbpath == None:
1474 dbpath = self.get_local_database_file(repo)
1475
1476 dbdir = os.path.dirname(dbpath)
1477 if not os.path.isdir(dbdir):
1478 os.makedirs(dbdir)
1479
1480 mytxt = red("%s ...") % (_("Initializing an empty database"),)
1481 self.updateProgress(
1482 mytxt,
1483 importance = 1,
1484 type = "info",
1485 header = darkgreen(" * "),
1486 back = True
1487 )
1488 dbconn = self.ClientService.open_generic_database(dbpath)
1489 dbconn.initializeDatabase()
1490 dbconn.commitChanges()
1491 dbconn.closeDB()
1492 mytxt = "%s %s %s." % (
1493 red(_("Entropy database file")),
1494 bold(dbpath),
1495 red(_("successfully initialized")),
1496 )
1497 self.updateProgress(
1498 mytxt,
1499 importance = 1,
1500 type = "info",
1501 header = darkgreen(" * ")
1502 )
1503
1504 - def tag_packages(self, package_tag, idpackages, repo = None, ask = True):
1505
1506
1507
1508 try:
1509 package_tag = str(package_tag)
1510 if " " in package_tag:
1511 raise ValueError
1512 except (UnicodeDecodeError, UnicodeEncodeError, ValueError,):
1513 self.updateProgress(
1514 "%s: %s" % (
1515 blue(_("Invalid tag specified")),
1516 package_tag,
1517 ),
1518 importance = 1, type = "error", header = darkred(" !! ")
1519 )
1520 return 1, package_tag
1521
1522 if repo == None:
1523 repo = self.default_repository
1524
1525
1526 invalid_atoms = []
1527 dbconn = self.open_server_repository(read_only = True,
1528 no_upload = True, repo = repo)
1529 for idpackage in idpackages:
1530 ver_tag = dbconn.retrieveVersionTag(idpackage)
1531 if ver_tag:
1532 invalid_atoms.append(dbconn.retrieveAtom(idpackage))
1533
1534 if invalid_atoms:
1535 self.updateProgress(
1536 "%s: %s" % (
1537 blue(_("Packages already tagged, action aborted")),
1538 ', '.join([darkred(unicode(x)) for x in invalid_atoms]),
1539 ),
1540 importance = 1, type = "error", header = darkred(" !! ")
1541 )
1542 return 2, invalid_atoms
1543
1544 matches = [(x, repo) for x in idpackages]
1545 status = 0
1546 data = self.move_packages(
1547 matches, to_repo = repo, from_repo = repo, ask = ask,
1548 do_copy = True, new_tag = package_tag
1549 )
1550 return status, data
1551
1553 """
1554 When creating a new branch, for space reasons, packages are not
1555 moved to a new location. This works fine until old branch is removed.
1556 To avoid inconsistences, before deciding to do that, all the packages
1557 in the old branch should be flushed back to the the currently configured
1558 branch.
1559
1560 @param from_branches -- list of branches to move packages from
1561 @type from_branches -- list
1562 @param repo -- repository to work on
1563 @type repo -- str
1564 @param ask -- user interactivity
1565 @type ask -- bool
1566
1567 @return status
1568 """
1569
1570 status = True
1571 if repo == None:
1572 repo = self.default_repository
1573 branch = self.SystemSettings['repositories']['branch']
1574
1575 if branch in from_branches:
1576 from_branches = [x for x in from_branches if x != branch]
1577
1578 self.updateProgress(
1579 "[%s=>%s|%s] %s" % (
1580 darkgreen(', '.join(from_branches)),
1581 darkred(branch),
1582 brown(repo),
1583 blue(_("flushing back selected packages from branches")),
1584 ),
1585 importance = 2,
1586 type = "info",
1587 header = red(" @@ ")
1588 )
1589
1590 dbconn = self.open_server_repository(read_only = True,
1591 no_upload = True, repo = repo)
1592
1593 idpackage_map = dict(((x, [],) for x in from_branches))
1594 idpackages = dbconn.listAllIdpackages(order_by = 'atom')
1595 for idpackage in idpackages:
1596 download_url = dbconn.retrieveDownloadURL(idpackage)
1597 url_br = self.ClientService.get_branch_from_download_relative_uri(
1598 download_url)
1599 if url_br in from_branches:
1600 idpackage_map[url_br].append(idpackage)
1601
1602 mapped_branches = [x for x in idpackage_map if idpackage_map[x]]
1603 if not mapped_branches:
1604 self.updateProgress(
1605 "[%s=>%s|%s] %s !" % (
1606 darkgreen(', '.join(from_branches)),
1607 darkred(branch),
1608 brown(repo),
1609 blue(_("nothing to do")),
1610 ),
1611 importance = 0,
1612 type = "warning",
1613 header = blue(" @@ ")
1614 )
1615 return status
1616
1617
1618 all_fine = True
1619 tmp_down_dir = self.entropyTools.get_random_temp_file()
1620 os.makedirs(tmp_down_dir)
1621
1622 download_queue = {}
1623 local_up_dir = self.get_local_upload_directory(repo)
1624 local_basedir = os.path.join(local_up_dir, branch)
1625 dbconn = self.open_server_repository(read_only = False,
1626 no_upload = True, repo = repo)
1627
1628 def generate_queue(branch, repo, from_branch, down_q, idpackage_map):
1629
1630 self.updateProgress(
1631 "[%s=>%s|%s] %s" % (
1632 darkgreen(from_branch),
1633 darkred(branch),
1634 brown(repo),
1635 brown(_("these are the packages that will be flushed")),
1636 ),
1637 importance = 1,
1638 type = "info",
1639 header = brown(" @@ ")
1640 )
1641
1642
1643 for idpackage in idpackage_map[from_branch]:
1644 atom = dbconn.retrieveAtom(idpackage)
1645 self.updateProgress(
1646 "[%s=>%s|%s] %s" % (
1647 darkgreen(from_branch),
1648 darkred(branch),
1649 brown(repo),
1650 purple(atom),
1651 ),
1652 importance = 0,
1653 type = "info",
1654 header = blue(" # ")
1655 )
1656 pkg_fp = os.path.basename(dbconn.retrieveDownloadURL(idpackage))
1657 pkg_fp = os.path.join(tmp_down_dir, pkg_fp)
1658 down_q.append((pkg_fp, idpackage,))
1659
1660
1661 for from_branch in sorted(mapped_branches):
1662
1663 download_queue[from_branch] = []
1664 all_fine = False
1665 generate_queue(branch, repo, from_branch,
1666 download_queue[from_branch], idpackage_map)
1667
1668 if ask:
1669 rc_question = self.askQuestion(
1670 _("Would you like to continue ?"))
1671 if rc_question == "No":
1672 continue
1673
1674 remote_relative_path = self.get_remote_packages_relative_path(repo)
1675
1676 for uri in self.get_remote_mirrors(repo):
1677
1678 crippled_uri = self.entropyTools.extract_ftp_host_from_uri(uri)
1679 ftp_basedir = os.path.join(remote_relative_path, from_branch)
1680
1681 downloader_queue = [x[0] for x in download_queue[from_branch]]
1682 downloader = self.MirrorsService.FtpServerHandler(
1683 FtpInterface,
1684 self,
1685 [uri],
1686 downloader_queue,
1687 critical_files = downloader_queue,
1688 use_handlers = True,
1689 ftp_basedir = ftp_basedir,
1690 local_basedir = tmp_down_dir,
1691 download = True,
1692 repo = repo
1693 )
1694
1695 errors, m_fine_uris, m_broken_uris = downloader.go()
1696
1697 if not errors:
1698 for downloaded_path, idpackage in \
1699 download_queue[from_branch]:
1700
1701 self.updateProgress(
1702 "[%s=>%s|%s|%s] %s: %s" % (
1703 darkgreen(from_branch),
1704 darkred(branch),
1705 brown(repo),
1706 dbconn.retrieveAtom(idpackage),
1707 blue(_("checking package hash")),
1708 darkgreen(os.path.basename(downloaded_path)),
1709 ),
1710 importance = 0,
1711 type = "info",
1712 header = brown(" "),
1713 back = True
1714 )
1715
1716 md5hash = self.entropyTools.md5sum(downloaded_path)
1717 db_md5hash = dbconn.retrieveDigest(idpackage)
1718 if md5hash != db_md5hash:
1719 errors = True
1720 self.updateProgress(
1721 "[%s=>%s|%s|%s] %s: %s" % (
1722 darkgreen(from_branch),
1723 darkred(branch),
1724 brown(repo),
1725 dbconn.retrieveAtom(idpackage),
1726 blue(_("hash does not match for")),
1727 darkgreen(os.path.basename(downloaded_path)),
1728 ),
1729 importance = 0,
1730 type = "error",
1731 header = brown(" ")
1732 )
1733 continue
1734
1735
1736
1737 if errors:
1738 reason = _("wrong md5")
1739 if m_broken_uris:
1740 my_broken_uris = [
1741 (self.entropyTools.extract_ftp_host_from_uri(x), y,) \
1742 for x, y in m_broken_uris]
1743 reason = my_broken_uris[0][1]
1744
1745 self.updateProgress(
1746 "[%s=>%s|%s] %s, %s: %s" % (
1747 darkgreen(from_branch),
1748 darkred(branch),
1749 brown(repo),
1750 blue(_("download errors")),
1751 blue(_("reason")),
1752 reason,
1753 ),
1754 importance = 1,
1755 type = "error",
1756 header = darkred(" !!! ")
1757 )
1758
1759 continue
1760
1761 all_fine = True
1762
1763 self.updateProgress(
1764 "[%s=>%s|%s] %s: %s" % (
1765 darkgreen(from_branch),
1766 darkred(branch),
1767 brown(repo),
1768 blue(_("download completed successfully")),
1769 darkgreen(crippled_uri),
1770 ),
1771 importance = 1,
1772 type = "info",
1773 header = darkgreen(" * ")
1774 )
1775
1776 if not all_fine:
1777 self.updateProgress(
1778 "[%s=>%s|%s] %s" % (
1779 darkgreen(', '.join(from_branches)),
1780 darkred(branch),
1781 brown(repo),
1782 blue(_("error downloading packages from mirrors")),
1783 ),
1784 importance = 2,
1785 type = "error",
1786 header = darkred(" !!! ")
1787 )
1788 return False
1789
1790 for from_branch in sorted(mapped_branches):
1791
1792 self.updateProgress(
1793 "[%s=>%s|%s] %s: %s" % (
1794 darkgreen(from_branch),
1795 darkred(branch),
1796 brown(repo),
1797 blue(_("working on branch")),
1798 darkgreen(from_branch),
1799 ),
1800 importance = 1,
1801 type = "info",
1802 header = brown(" @@ ")
1803 )
1804
1805 down_queue = download_queue[from_branch]
1806 for package_path, idpackage in down_queue:
1807
1808 self.updateProgress(
1809 "[%s=>%s|%s] %s: %s" % (
1810 darkgreen(from_branch),
1811 darkred(branch),
1812 brown(repo),
1813 blue(_("updating package")),
1814 darkgreen(os.path.basename(package_path)),
1815 ),
1816 importance = 1,
1817 type = "info",
1818 header = brown(" "),
1819 back = True
1820 )
1821
1822
1823 package_name = os.path.basename(package_path)
1824 new_package_path = os.path.join(local_basedir, package_name)
1825 try:
1826 os.rename(package_path, new_package_path)
1827 except OSError:
1828 shutil.move(package_path, new_package_path)
1829
1830
1831 self.entropyTools.create_md5_file(new_package_path)
1832
1833
1834 download_url = dbconn.retrieveDownloadURL(idpackage)
1835 download_url = \
1836 self.ClientService.swap_branch_in_download_relative_uri(
1837 branch, download_url)
1838 dbconn.setDownloadURL(idpackage, download_url)
1839 dbconn.switchBranch(idpackage, branch)
1840 dbconn.commitChanges()
1841
1842 self.updateProgress(
1843 "[%s=>%s|%s] %s: %s" % (
1844 darkgreen(from_branch),
1845 darkred(branch),
1846 brown(repo),
1847 blue(_("package flushed")),
1848 darkgreen(os.path.basename(package_path)),
1849 ),
1850 importance = 1,
1851 type = "info",
1852 header = brown(" ")
1853 )
1854
1855 try:
1856 os.rmdir(tmp_down_dir)
1857 except OSError:
1858 pass
1859
1860 return True
1861
1862 - def move_packages(self, matches, to_repo, from_repo = None, ask = True,
1863 do_copy = False, new_tag = None, pull_deps = False):
1864
1865 if from_repo == None:
1866 from_repo = self.default_repository
1867 switched = set()
1868
1869 my_matches = list(matches)
1870
1871
1872 if etpConst['clientserverrepoid'] in (to_repo, from_repo):
1873 self.updateProgress(
1874 "%s: %s" % (
1875 blue(_("Cannot touch system database")),
1876 red(etpConst['clientserverrepoid']),
1877 ),
1878 importance = 2, type = "warning", header = darkred(" @@ ")
1879 )
1880 return switched
1881
1882 if not my_matches and from_repo:
1883 dbconn = self.open_server_repository(read_only = True,
1884 no_upload = True, repo = from_repo)
1885 my_matches = set( \
1886 [(x, from_repo) for x in \
1887 dbconn.listAllIdpackages()]
1888 )
1889
1890 mytxt = _("Preparing to move selected packages to")
1891 if do_copy:
1892 mytxt = _("Preparing to copy selected packages to")
1893 self.updateProgress(
1894 "%s %s:" % (
1895 blue(mytxt),
1896 red(to_repo),
1897 ),
1898 importance = 2,
1899 type = "info",
1900 header = red(" @@ ")
1901 )
1902 self.updateProgress(
1903 "%s: %s" % (
1904 bold(_("Note")),
1905 red(_("all old packages with conflicting scope will be " \
1906 "removed from destination repo unless injected")),
1907 ),
1908 importance = 1,
1909 type = "info",
1910 header = red(" @@ ")
1911 )
1912
1913 new_tag_string = ''
1914 if new_tag != None:
1915 new_tag_string = "[%s: %s]" % (darkgreen(_("new tag")),
1916 brown(new_tag),)
1917
1918 my_qa = self.QA()
1919 branch = self.SystemSettings['repositories']['branch']
1920 pull_deps_matches = []
1921 for idpackage, repo in my_matches:
1922 dbconn = self.open_server_repository(read_only = True,
1923 no_upload = True, repo = repo)
1924 self.updateProgress(
1925 "[%s=>%s|%s] %s " % (
1926 darkgreen(repo),
1927 darkred(to_repo),
1928 brown(branch),
1929 blue(dbconn.retrieveAtom(idpackage)),
1930 ) + new_tag_string,
1931 importance = 0,
1932 type = "info",
1933 header = brown(" # ")
1934 )
1935
1936 if pull_deps:
1937 dep_idpackages = my_qa.get_deep_dependency_list(dbconn,
1938 idpackage)
1939 for dep_idpackage in dep_idpackages:
1940
1941 my_dep_match = (dep_idpackage, repo,)
1942 if my_dep_match in pull_deps_matches:
1943 continue
1944 if my_dep_match in my_matches:
1945 continue
1946
1947 pull_deps_matches.append(my_dep_match)
1948 self.updateProgress(
1949 "[%s|%s] %s" % (
1950 brown(branch),
1951 blue(_("dependency")),
1952 purple(dbconn.retrieveAtom(dep_idpackage)),
1953 ),
1954 importance = 0,
1955 type = "info",
1956 header = purple(" >> ")
1957 )
1958
1959 if pull_deps:
1960
1961 my_matches = pull_deps_matches + [x for x in my_matches if x not \
1962 in pull_deps_matches]
1963
1964 if ask:
1965 rc_question = self.askQuestion(_("Would you like to continue ?"))
1966 if rc_question == "No":
1967 return switched
1968
1969 for idpackage, repo in my_matches:
1970 dbconn = self.open_server_repository(read_only = False,
1971 no_upload = True, repo = repo)
1972 match_branch = dbconn.retrieveBranch(idpackage)
1973 match_atom = dbconn.retrieveAtom(idpackage)
1974 package_filename = os.path.basename(
1975 dbconn.retrieveDownloadURL(idpackage))
1976 self.updateProgress(
1977 "[%s=>%s|%s] %s: %s" % (
1978 darkgreen(repo),
1979 darkred(to_repo),
1980 brown(branch),
1981 blue(_("switching")),
1982 darkgreen(match_atom),
1983 ),
1984 importance = 0,
1985 type = "info",
1986 header = red(" @@ "),
1987 back = True
1988 )
1989
1990 from_file = os.path.join(self.get_local_packages_directory(repo),
1991 match_branch, package_filename)
1992 if not os.path.isfile(from_file):
1993 from_file = os.path.join(self.get_local_upload_directory(repo),
1994 match_branch, package_filename)
1995 if not os.path.isfile(from_file):
1996 self.updateProgress(
1997 "[%s=>%s|%s] %s: %s -> %s" % (
1998 darkgreen(repo),
1999 darkred(to_repo),
2000 brown(branch),
2001 bold(_("cannot switch, package not found, skipping")),
2002 darkgreen(match_atom),
2003 red(from_file),
2004 ),
2005 importance = 1,
2006 type = "warning",
2007 header = darkred(" !!! ")
2008 )
2009 continue
2010
2011 if new_tag != None:
2012 match_category = dbconn.retrieveCategory(idpackage)
2013 match_name = dbconn.retrieveName(idpackage)
2014 match_version = dbconn.retrieveVersion(idpackage)
2015 tagged_package_filename = \
2016 self.entropyTools.create_package_filename(
2017 match_category, match_name, match_version, new_tag)
2018 to_file = os.path.join(self.get_local_upload_directory(to_repo),
2019 match_branch, tagged_package_filename)
2020 else:
2021 to_file = os.path.join(self.get_local_upload_directory(to_repo),
2022 match_branch, package_filename)
2023 if not os.path.isdir(os.path.dirname(to_file)):
2024 os.makedirs(os.path.dirname(to_file))
2025
2026 copy_data = [
2027 (from_file, to_file,),
2028 (from_file + etpConst['packagesmd5fileext'],
2029 to_file + etpConst['packagesmd5fileext'],),
2030 (from_file + etpConst['packagesexpirationfileext'],
2031 to_file + etpConst['packagesexpirationfileext'],)
2032 ]
2033
2034 for from_item, to_item in copy_data:
2035 self.updateProgress(
2036 "[%s=>%s|%s] %s: %s" % (
2037 darkgreen(repo),
2038 darkred(to_repo),
2039 brown(branch),
2040 blue(_("moving file")),
2041 darkgreen(os.path.basename(from_item)),
2042 ),
2043 importance = 0,
2044 type = "info",
2045 header = red(" @@ "),
2046 back = True
2047 )
2048 if os.path.isfile(from_item):
2049 shutil.copy2(from_item, to_item)
2050
2051 self.updateProgress(
2052 "[%s=>%s|%s] %s: %s" % (
2053 darkgreen(repo),
2054 darkred(to_repo),
2055 brown(branch),
2056 blue(_("loading data from source database")),
2057 darkgreen(repo),
2058 ),
2059 importance = 0,
2060 type = "info",
2061 header = red(" @@ "),
2062 back = True
2063 )
2064
2065 data = dbconn.getPackageData(idpackage)
2066 if new_tag != None:
2067 data['versiontag'] = new_tag
2068
2069 todbconn = self.open_server_repository(read_only = False,
2070 no_upload = True, repo = to_repo)
2071
2072 self.updateProgress(
2073 "[%s=>%s|%s] %s: %s" % (
2074 darkgreen(repo),
2075 darkred(to_repo),
2076 brown(branch),
2077 blue(_("injecting data to destination database")),
2078 darkgreen(to_repo),
2079 ),
2080 importance = 0,
2081 type = "info",
2082 header = red(" @@ "),
2083 back = True
2084 )
2085 new_idpackage, new_revision, new_data = todbconn.handlePackage(data)
2086 del data
2087 todbconn.commitChanges()
2088
2089 if not do_copy:
2090 self.updateProgress(
2091 "[%s=>%s|%s] %s: %s" % (
2092 darkgreen(repo),
2093 darkred(to_repo),
2094 brown(branch),
2095 blue(_("removing entry from source database")),
2096 darkgreen(repo),
2097 ),
2098 importance = 0,
2099 type = "info",
2100 header = red(" @@ "),
2101 back = True
2102 )
2103
2104
2105 dbconn.removePackage(idpackage)
2106 dbconn.commitChanges()
2107
2108 self.updateProgress(
2109 "[%s=>%s|%s] %s: %s" % (
2110 darkgreen(repo),
2111 darkred(to_repo),
2112 brown(branch),
2113 blue(_("successfully handled atom")),
2114 darkgreen(match_atom),
2115 ),
2116 importance = 0,
2117 type = "info",
2118 header = blue(" @@ ")
2119 )
2120 switched.add((idpackage, repo,))
2121
2122
2123 self.dependencies_test(to_repo)
2124
2125 return switched
2126
2127
2129
2130 if repo == None:
2131 repo = self.default_repository
2132
2133 upload_dir = os.path.join(self.get_local_upload_directory(repo),
2134 self.SystemSettings['repositories']['branch'])
2135 if not os.path.isdir(upload_dir):
2136 os.makedirs(upload_dir)
2137
2138 dbconn = self.open_server_repository(read_only = False,
2139 no_upload = True, repo = repo)
2140 self.updateProgress(
2141 red("[repo: %s] %s: %s" % (
2142 darkgreen(repo),
2143 _("adding package"),
2144 bold(os.path.basename(package_file)),
2145 )
2146 ),
2147 importance = 1,
2148 type = "info",
2149 header = brown(" * "),
2150 back = True
2151 )
2152 mydata = self.Spm().extract_package_metadata(package_file)
2153 mydata['injected'] = inject
2154 idpackage, revision, mydata = dbconn.handlePackage(mydata)
2155
2156
2157 trashing_counters = set()
2158 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
2159 myserver_repos = srv_set['repositories'].keys()
2160 for myrepo in myserver_repos:
2161 mydbconn = self.open_server_repository(read_only = True,
2162 no_upload = True, repo = myrepo)
2163 mylist = mydbconn.retrieve_packages_to_remove(
2164 mydata['name'],
2165 mydata['category'],
2166 mydata['slot'],
2167 mydata['injected']
2168 )
2169 for myitem in mylist:
2170 trashing_counters.add(mydbconn.retrieveSpmUid(myitem))
2171
2172 for mycounter in trashing_counters:
2173 dbconn.setTrashedUid(mycounter)
2174
2175
2176 dbconn.dropInstalledPackageFromStore(idpackage)
2177 dbconn.storeInstalledPackage(idpackage, repo)
2178 atom = dbconn.retrieveAtom(idpackage)
2179
2180 self.updateProgress(
2181 "[repo:%s] %s: %s %s: %s" % (
2182 darkgreen(repo),
2183 blue(_("added package")),
2184 darkgreen(atom),
2185 blue(_("rev")),
2186 bold(str(revision)),
2187 ),
2188 importance = 1,
2189 type = "info",
2190 header = red(" @@ ")
2191 )
2192
2193 manual_deps = sorted(dbconn.retrieveManualDependencies(idpackage))
2194 if manual_deps:
2195 self.updateProgress(
2196 "[repo:%s] %s: %s" % (
2197 darkgreen(repo),
2198 blue(_("manual dependencies for")),
2199 darkgreen(atom),
2200 ),
2201 importance = 1,
2202 type = "warning",
2203 header = darkgreen(" ## ")
2204 )
2205 for m_dep in manual_deps:
2206 self.updateProgress(
2207 brown(m_dep),
2208 importance = 1,
2209 type = "warning",
2210 header = darkred(" # ")
2211 )
2212
2213 download_url = self._setup_repository_package_filename(idpackage,
2214 repo = repo)
2215 downloadfile = os.path.basename(download_url)
2216 destination_path = os.path.join(upload_dir, downloadfile)
2217 try:
2218 os.rename(package_file, destination_path)
2219 except OSError:
2220 shutil.move(package_file, destination_path)
2221
2222 dbconn.commitChanges()
2223 return idpackage, destination_path
2224
2225
2227
2228 dbconn = self.open_server_repository(read_only = False,
2229 no_upload = True, repo = repo)
2230
2231 downloadurl = dbconn.retrieveDownloadURL(idpackage)
2232 packagerev = dbconn.retrieveRevision(idpackage)
2233 downloaddir = os.path.dirname(downloadurl)
2234 downloadfile = os.path.basename(downloadurl)
2235
2236 downloadfile = downloadfile[:-5]+"~%s%s" % (packagerev,
2237 etpConst['packagesext'],)
2238 downloadurl = os.path.join(downloaddir, downloadfile)
2239
2240
2241 dbconn.setDownloadURL(idpackage, downloadurl)
2242
2243 return downloadurl
2244
2247
2248 if repo == None:
2249 repo = self.default_repository
2250
2251 mycount = 0
2252 maxcount = len(packages_data)
2253 idpackages_added = set()
2254 to_be_injected = set()
2255 my_qa = self.QA()
2256 missing_deps_taint = False
2257 for package_filepath, inject in packages_data:
2258
2259 mycount += 1
2260 self.updateProgress(
2261 "[repo:%s] %s: %s" % (
2262 darkgreen(repo),
2263 blue(_("adding package")),
2264 darkgreen(os.path.basename(package_filepath)),
2265 ),
2266 importance = 1,
2267 type = "info",
2268 header = blue(" @@ "),
2269 count = (mycount, maxcount,)
2270 )
2271
2272 try:
2273
2274 idpackage, destination_path = self.package_injector(
2275 package_filepath,
2276 inject = inject,
2277 repo = repo
2278 )
2279 idpackages_added.add(idpackage)
2280 to_be_injected.add((idpackage, destination_path))
2281 except Exception, err:
2282 self.entropyTools.print_traceback()
2283 self.updateProgress(
2284 "[repo:%s] %s: %s" % (
2285 darkgreen(repo),
2286 darkred(_("Exception caught, closing tasks")),
2287 darkgreen(unicode(err)),
2288 ),
2289 importance = 1,
2290 type = "error",
2291 header = bold(" !!! "),
2292 count = (mycount, maxcount,)
2293 )
2294
2295 self.depends_table_initialize(repo)
2296
2297 self.library_paths_table_initialize(repo)
2298 if idpackages_added:
2299 dbconn = self.open_server_repository(read_only = False,
2300 no_upload = True, repo = repo)
2301 missing_deps_taint = my_qa.test_missing_dependencies(
2302 idpackages_added,
2303 dbconn,
2304 ask = ask,
2305 repo = repo,
2306 self_check = True,
2307 black_list = \
2308 self.get_missing_dependencies_blacklist(
2309 repo = repo),
2310 black_list_adder = \
2311 self.add_missing_dependencies_blacklist_items
2312 )
2313 my_qa.test_depends_linking(idpackages_added, dbconn,
2314 repo = repo)
2315 if to_be_injected:
2316 self.inject_database_into_packages(to_be_injected,
2317 repo = repo)
2318
2319 if missing_deps_taint:
2320 self.depends_table_initialize(repo)
2321 self.close_server_databases()
2322 raise
2323
2324
2325 self.depends_table_initialize(repo)
2326
2327 self.library_paths_table_initialize(repo)
2328
2329 if idpackages_added:
2330 dbconn = self.open_server_repository(read_only = False,
2331 no_upload = True, repo = repo)
2332 missing_deps_taint = my_qa.test_missing_dependencies(
2333 idpackages_added,
2334 dbconn,
2335 ask = ask,
2336 repo = repo,
2337 self_check = True,
2338 black_list = \
2339 self.get_missing_dependencies_blacklist(repo = repo),
2340 black_list_adder = \
2341 self.add_missing_dependencies_blacklist_items
2342 )
2343 my_qa.test_depends_linking(idpackages_added, dbconn, repo = repo)
2344
2345
2346 if missing_deps_taint:
2347 self.depends_table_initialize(repo)
2348
2349
2350 self.inject_database_into_packages(to_be_injected, repo = repo)
2351
2352 return idpackages_added
2353
2354
2356
2357 if repo == None:
2358 repo = self.default_repository
2359
2360
2361 self.updateProgress(
2362 "[repo:%s] %s:" % (
2363 darkgreen(repo),
2364 blue(_("Injecting entropy metadata into built packages")),
2365 ),
2366 importance = 1,
2367 type = "info",
2368 header = red(" @@ ")
2369 )
2370
2371 dbconn = self.open_server_repository(read_only = False,
2372 no_upload = True, repo = repo)
2373 for idpackage, package_path in injection_data:
2374 self.updateProgress(
2375 "[repo:%s|%s] %s: %s" % (
2376 darkgreen(repo),
2377 brown(str(idpackage)),
2378 blue(_("injecting entropy metadata")),
2379 darkgreen(os.path.basename(package_path)),
2380 ),
2381 importance = 1,
2382 type = "info",
2383 header = blue(" @@ "),
2384 back = True
2385 )
2386 data = dbconn.getPackageData(idpackage)
2387 treeupdates_actions = dbconn.listAllTreeUpdatesActions()
2388 dbpath = self.ClientService.inject_entropy_database_into_package(
2389 package_path, data, treeupdates_actions)
2390 digest = self.entropyTools.md5sum(package_path)
2391
2392 dbconn.setDigest(idpackage, digest)
2393
2394 signatures = data['signatures'].copy()
2395 for hash_key in sorted(signatures):
2396 hash_func = getattr(self.entropyTools, hash_key)
2397 signatures[hash_key] = hash_func(package_path)
2398 dbconn.setSignatures(idpackage, signatures['sha1'],
2399 signatures['sha256'], signatures['sha512'])
2400 self.entropyTools.create_md5_file(package_path)
2401
2402 os.remove(dbpath)
2403 self.updateProgress(
2404 "[repo:%s|%s] %s: %s" % (
2405 darkgreen(repo),
2406 brown(str(idpackage)),
2407 blue(_("injection complete")),
2408 darkgreen(os.path.basename(package_path)),
2409 ),
2410 importance = 1,
2411 type = "info",
2412 header = red(" @@ ")
2413 )
2414 dbconn.commitChanges()
2415
2417 self.updateProgress(
2418 "[%s] %s" % (
2419 red(_("config files")),
2420 blue(_("checking system")),
2421 ),
2422 importance = 1,
2423 type = "info",
2424 header = blue(" @@ "),
2425 back = True
2426 )
2427
2428 scandata = self.ClientService.FileUpdates.scanfs(dcache = False)
2429 if scandata:
2430 self.updateProgress(
2431 "[%s] %s" % (
2432 red(_("config files")),
2433 blue(_("there are configuration files not updated yet")),
2434 ),
2435 importance = 1,
2436 type = "error",
2437 header = darkred(" @@ ")
2438 )
2439 for key in scandata:
2440 self.updateProgress(
2441 "%s" % (brown(etpConst['systemroot'] + \
2442 scandata[key]['destination'])),
2443 importance = 1,
2444 type = "info",
2445 header = "\t"
2446 )
2447 return True
2448 return False
2449
2452
2454
2455 if repo == None:
2456 repo = self.default_repository
2457
2458 dbconn = self.open_server_repository(read_only = False,
2459 no_upload = True, repo = repo)
2460 for idpackage in idpackages:
2461 atom = dbconn.retrieveAtom(idpackage)
2462 self.updateProgress(
2463 "[repo:%s] %s: %s" % (
2464 darkgreen(repo),
2465 blue(_("removing package")),
2466 darkgreen(atom),
2467 ),
2468 importance = 1,
2469 type = "info",
2470 header = brown(" @@ ")
2471 )
2472 dbconn.removePackage(idpackage)
2473 self.close_server_database(dbconn)
2474 self.updateProgress(
2475 "[repo:%s] %s" % (
2476 darkgreen(repo),
2477 blue(_("removal complete")),
2478 ),
2479 importance = 1,
2480 type = "info",
2481 header = brown(" @@ ")
2482 )
2483
2484
2490
2492 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
2493 if repo == None:
2494 repo = self.default_repository
2495 return srv_set['repositories'][repo]['mirrors'][:]
2496
2498 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
2499 if repo == None:
2500 repo = self.default_repository
2501 return srv_set['repositories'][repo]['packages_relative_path']
2502
2504 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
2505 if repo == None:
2506 repo = self.default_repository
2507 return srv_set['repositories'][repo]['database_relative_path']
2508
2510 if repo == None:
2511 repo = self.default_repository
2512 return os.path.join(self.get_local_database_dir(repo, branch),
2513 etpConst['etpdatabasefile'])
2514
2516 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
2517 if repo == None:
2518 repo = self.default_repository
2519 return srv_set['repositories'][repo]['store_dir']
2520
2522 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
2523 if repo == None:
2524 repo = self.default_repository
2525 return srv_set['repositories'][repo]['upload_dir']
2526
2528 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
2529 if repo == None:
2530 repo = self.default_repository
2531 return srv_set['repositories'][repo]['packages_dir']
2532
2534 if repo == None:
2535 repo = self.default_repository
2536 return os.path.join(self.get_local_database_dir(repo, branch),
2537 etpConst['etpdatabasetaintfile'])
2538
2540 if repo == None:
2541 repo = self.default_repository
2542 return os.path.join(self.get_local_database_dir(repo, branch),
2543 etpConst['etpdatabaserevisionfile'])
2544
2546 if repo == None:
2547 repo = self.default_repository
2548 return os.path.join(self.get_local_database_dir(repo, branch),
2549 etpConst['etpdatabasetimestampfile'])
2550
2552 if repo == None:
2553 repo = self.default_repository
2554 return os.path.join(self.get_local_database_dir(repo, branch),
2555 etpConst['etpdatabasecacertfile'])
2556
2558 if repo == None:
2559 repo = self.default_repository
2560 return os.path.join(self.get_local_database_dir(repo, branch),
2561 etpConst['etpdatabaseservercertfile'])
2562
2564 if repo == None:
2565 repo = self.default_repository
2566 return os.path.join(self.get_local_database_dir(repo, branch),
2567 etpConst['etpdatabasemaskfile'])
2568
2570 if repo == None:
2571 repo = self.default_repository
2572 return os.path.join(self.get_local_database_dir(repo, branch),
2573 etpConst['etpdatabasesytemmaskfile'])
2574
2576 if repo == None:
2577 repo = self.default_repository
2578 return os.path.join(self.get_local_database_dir(repo, branch),
2579 etpConst['etpdatabaseconflictingtaggedfile'])
2580
2583
2584 if repo == None:
2585 repo = self.default_repository
2586 return os.path.join(self.get_local_database_dir(repo, branch),
2587 etpConst['etpdatabaselicwhitelistfile'])
2588
2590 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
2591 if repo == None:
2592 repo = self.default_repository
2593 return os.path.join(self.get_local_database_dir(repo, branch),
2594 srv_set['rss']['name'])
2595
2597 if repo == None:
2598 repo = self.default_repository
2599 return os.path.join(self.get_local_database_dir(repo, branch),
2600 etpConst['rss-light-name'])
2601
2603 if repo == None:
2604 repo = self.default_repository
2605 return os.path.join(self.get_local_database_dir(repo, branch),
2606 etpConst['rss-notice-board'])
2607
2609 if repo == None:
2610 repo = self.default_repository
2611 return os.path.join(self.get_local_database_dir(repo, branch),
2612 etpConst['etpdatabaseupdatefile'])
2613
2621
2629
2632 if repo == None:
2633 repo = self.default_repository
2634 return os.path.join(self.get_local_database_dir(repo, branch),
2635 etpConst['etpdatabaseexpbasedpkgsrm'])
2636
2638 if repo == None:
2639 repo = self.default_repository
2640 return os.path.join(self.get_local_database_dir(repo, branch),
2641 etpConst['etpdatabasepkglist'])
2642
2644 if repo == None:
2645 repo = self.default_repository
2646 return os.path.join(self.get_local_database_dir(repo, branch),
2647 etpConst['confsetsdirname'])
2648
2649 - def get_local_post_branch_mig_script(self, repo = None, branch = None):
2650 if repo == None:
2651 repo = self.default_repository
2652 return os.path.join(self.get_local_database_dir(repo, branch),
2653 etpConst['etp_post_branch_hop_script'])
2654
2655 - def get_local_post_branch_upg_script(self, repo = None, branch = None):
2656 if repo == None:
2657 repo = self.default_repository
2658 return os.path.join(self.get_local_database_dir(repo, branch),
2659 etpConst['etp_post_branch_upgrade_script'])
2660
2662 if repo == None:
2663 repo = self.default_repository
2664 return os.path.join(self.get_local_database_dir(repo, branch),
2665 etpConst['etpdatabasecriticalfile'])
2666
2668 if repo == None:
2669 repo = self.default_repository
2670 return os.path.join(self.get_local_database_dir(repo, branch),
2671 etpConst['etpdatabasekeywordsfile'])
2672
2674 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
2675 if repo == None:
2676 repo = self.default_repository
2677 if branch == None:
2678 branch = self.SystemSettings['repositories']['branch']
2679 return os.path.join(srv_set['repositories'][repo]['database_dir'],
2680 branch)
2681
2684 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
2685 if repo == None:
2686 repo = self.default_repository
2687 if branch == None:
2688 branch = self.SystemSettings['repositories']['branch']
2689 return os.path.join(srv_set['repositories'][repo]['database_dir'],
2690 branch, etpConst['etpdatabasemissingdepsblfile'])
2691
2693 if repo == None:
2694 repo = self.default_repository
2695 if branch == None:
2696 branch = self.SystemSettings['repositories']['branch']
2697 wl_file = self.get_missing_dependencies_blacklist_file(repo, branch)
2698 wl_data = []
2699 if os.path.isfile(wl_file) and os.access(wl_file, os.R_OK):
2700 f_wl = open(wl_file,"r")
2701 wl_data = [x.strip() for x in f_wl.readlines() if x.strip() and \
2702 not x.strip().startswith("#")]
2703 f_wl.close()
2704 return set(wl_data)
2705
2708
2709 if repo == None:
2710 repo = self.default_repository
2711 if branch == None:
2712 branch = self.SystemSettings['repositories']['branch']
2713 wl_file = self.get_missing_dependencies_blacklist_file(repo, branch)
2714 wl_dir = os.path.dirname(wl_file)
2715 if not (os.path.isdir(wl_dir) and os.access(wl_dir, os.W_OK)):
2716 return
2717 if os.path.isfile(wl_file) and not os.access(wl_file, os.W_OK):
2718 return
2719 f_wl = open(wl_file,"a+")
2720 f_wl.write('\n'.join(items)+'\n')
2721 f_wl.flush()
2722 f_wl.close()
2723
2725
2726 if repo == None:
2727 repo = self.default_repository
2728
2729 dbrev_file = self.get_local_database_revision_file(repo)
2730 if os.path.isfile(dbrev_file):
2731 f_rev = open(dbrev_file)
2732 rev = f_rev.readline().strip()
2733 f_rev.close()
2734 try:
2735 rev = int(rev)
2736 except ValueError:
2737 self.updateProgress(
2738 "[repo:%s] %s: %s - %s" % (
2739 darkgreen(repo),
2740 blue(_("invalid database revision")),
2741 bold(rev),
2742 blue(_("defaulting to 0")),
2743 ),
2744 importance = 2,
2745 type = "error",
2746 header = darkred(" !!! ")
2747 )
2748 rev = 0
2749 return rev
2750 else:
2751 return 0
2752
2754
2755 if repo == None:
2756 repo = self.default_repository
2757
2758 remote_status = self.MirrorsService.get_remote_databases_status(repo)
2759 if not [x for x in remote_status if x[1]]:
2760 remote_revision = 0
2761 else:
2762 remote_revision = max([x[1] for x in remote_status])
2763
2764 return remote_revision
2765
2768
2770 from datetime import datetime
2771 import time
2772 return "%s" % (datetime.fromtimestamp(time.time()),)
2773
2775 pkglist_file = self.get_local_pkglist_file(repo = repo, branch = branch)
2776
2777 tmp_pkglist_file = pkglist_file + ".tmp"
2778 dbconn = self.open_server_repository(repo = repo, just_reading = True,
2779 do_treeupdates = False)
2780 pkglist = dbconn.listAllDownloads(do_sort = True, full_path = True)
2781
2782 with open(tmp_pkglist_file, "w") as pkg_f:
2783 for pkg in pkglist:
2784 pkg_f.write(pkg + "\n")
2785 pkg_f.flush()
2786
2787 os.rename(tmp_pkglist_file, pkglist_file)
2788
2790 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
2791 repos = srv_set['repositories'].keys()
2792 kwargs['server_repos'] = repos
2793 kwargs['serverInstance'] = self
2794 return self.ClientService.package_set_list(*args, **kwargs)
2795
2797 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
2798 repos = srv_set['repositories'].keys()
2799 kwargs['server_repos'] = repos
2800 kwargs['serverInstance'] = self
2801 return self.ClientService.package_set_search(*args, **kwargs)
2802
2804 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
2805 repos = srv_set['repositories'].keys()
2806 kwargs['server_repos'] = repos
2807 kwargs['serverInstance'] = self
2808 return self.ClientService.package_set_match(*args, **kwargs)
2809
2811 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
2812 repos = srv_set['repositories'].keys()
2813 kwargs['server_repos'] = repos
2814 kwargs['serverInstance'] = self
2815 return self.ClientService.atom_match(*args, **kwargs)
2816
2818
2819 spm = self.Spm()
2820
2821 spm_packages = spm.get_installed_packages()
2822 installed_packages = []
2823 for spm_package in spm_packages:
2824 pkg_counter = spm.get_installed_package_metadata(spm_package,
2825 "COUNTER")
2826 try:
2827 pkg_counter = int(pkg_counter)
2828 except ValueError:
2829 continue
2830 installed_packages.append((spm_package, pkg_counter,))
2831
2832 installed_counters = set()
2833 to_be_added = set()
2834 to_be_removed = set()
2835 to_be_injected = set()
2836 my_settings = self.SystemSettings[self.sys_settings_plugin_id]['server']
2837 exp_based_scope = my_settings['exp_based_scope']
2838
2839 server_repos = my_settings['repositories'].keys()
2840
2841
2842 for spm_atom, spm_counter in installed_packages:
2843 found = False
2844 for server_repo in server_repos:
2845 installed_counters.add(spm_counter)
2846 server_dbconn = self.open_server_repository(read_only = True,
2847 no_upload = True, repo = server_repo)
2848 counter = server_dbconn.isSpmUidAvailable(spm_counter)
2849 if counter:
2850 found = True
2851 break
2852 if not found:
2853 to_be_added.add((spm_atom, spm_counter,))
2854
2855
2856 database_counters = {}
2857 for server_repo in server_repos:
2858 server_dbconn = self.open_server_repository(read_only = True,
2859 no_upload = True, repo = server_repo)
2860 database_counters[server_repo] = server_dbconn.listAllSpmUids()
2861
2862 ordered_counters = set()
2863 for server_repo in database_counters:
2864 for data in database_counters[server_repo]:
2865 ordered_counters.add((data, server_repo))
2866 database_counters = ordered_counters
2867
2868 for (counter, idpackage,), xrepo in database_counters:
2869
2870 if counter < 0:
2871 continue
2872
2873 if counter in installed_counters:
2874 continue
2875
2876 dbconn = self.open_server_repository(read_only = True,
2877 no_upload = True, repo = xrepo)
2878
2879 dorm = True
2880
2881 if to_be_added:
2882
2883 dorm = False
2884 atom = dbconn.retrieveAtom(idpackage)
2885 atomkey = self.entropyTools.dep_getkey(atom)
2886 atomtag = self.entropyTools.dep_gettag(atom)
2887 atomslot = dbconn.retrieveSlot(idpackage)
2888
2889 add = True
2890 for spm_atom, spm_counter in to_be_added:
2891 addslot = self.Spm().get_installed_package_metadata(
2892 spm_atom, "SLOT")
2893 addkey = self.entropyTools.dep_getkey(spm_atom)
2894
2895 if addslot == None:
2896 addslot = '0'
2897
2898 if (atomkey == addkey) and \
2899 ((str(atomslot) == str(addslot)) or (atomtag != None)):
2900
2901 add = False
2902 break
2903
2904 if not add:
2905 continue
2906 dorm = True
2907
2908
2909
2910
2911 if dorm and (xrepo == self.default_repository):
2912 trashed = self.is_counter_trashed(counter)
2913 if trashed:
2914
2915 try:
2916 key, slot = dbconn.retrieveKeySlot(idpackage)
2917 trashed = self.Spm().match_installed_package(
2918 key+":"+slot)
2919 except TypeError:
2920 trashed = True
2921 if not trashed:
2922
2923 dbtag = dbconn.retrieveVersionTag(idpackage)
2924 if dbtag:
2925 is_injected = dbconn.isInjected(idpackage)
2926 if not is_injected:
2927 to_be_injected.add((idpackage, xrepo))
2928
2929 elif exp_based_scope:
2930
2931
2932 plg_id = self.sys_settings_fatscope_plugin_id
2933 exp_data = self.SystemSettings[plg_id]['repos'].get(
2934 xrepo, set())
2935
2936
2937
2938 if (idpackage not in exp_data) and (-1 not in exp_data):
2939 to_be_removed.add((idpackage, xrepo))
2940 continue
2941
2942 idpackage_expired = self.is_match_expired((idpackage,
2943 xrepo,))
2944
2945 if idpackage_expired:
2946
2947
2948 to_be_removed.add((idpackage, xrepo))
2949 for my_id in dbconn.retrieveReverseDependencies(
2950 idpackage):
2951 to_be_removed.add((my_id, xrepo))
2952
2953 else:
2954 to_be_removed.add((idpackage, xrepo))
2955
2956 return to_be_added, to_be_removed, to_be_injected
2957
2959
2960 idpackage, repoid = match
2961 dbconn = self.open_server_repository(repo = repoid, just_reading = True)
2962
2963 my_settings = self.SystemSettings[self.sys_settings_plugin_id]['server']
2964 pkg_exp_secs = my_settings['packages_expiration_days'] * 86400
2965 cur_unix_time = self.entropyTools.get_current_unix_time()
2966
2967
2968
2969 mydate = dbconn.retrieveCreationDate(idpackage)
2970
2971 mydelta = cur_unix_time - float(mydate)
2972 if mydelta > pkg_exp_secs:
2973 return True
2974 return False
2975
2977 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
2978 server_repos = srv_set['repositories'].keys()
2979 for repo in server_repos:
2980 dbconn = self.open_server_repository(read_only = True,
2981 no_upload = True, repo = repo)
2982 if dbconn.isSpmUidTrashed(counter):
2983 return True
2984 return False
2985
2992
2995
2996 if repo == None:
2997 repo = self.default_repository
2998
2999 self.close_server_databases()
3000 revisions_match = {}
3001 treeupdates_actions = []
3002 injected_packages = set()
3003 idpackages = set()
3004 idpackages_added = set()
3005
3006 mytxt = red("%s ...") % (_("Initializing Entropy database"),)
3007 self.updateProgress(
3008 mytxt, importance = 1,
3009 type = "info", header = darkgreen(" * "),
3010 back = True
3011 )
3012
3013 if os.path.isfile(self.get_local_database_file(repo)):
3014
3015 dbconn = self.open_server_repository(read_only = True,
3016 no_upload = True, repo = repo, warnings = warnings)
3017
3018 try:
3019 dbconn.validateDatabase()
3020 idpackages = dbconn.listAllIdpackages()
3021 except SystemDatabaseError:
3022 pass
3023
3024 try:
3025 treeupdates_actions = dbconn.listAllTreeUpdatesActions()
3026 except dbconn.dbapi2.Error:
3027 pass
3028
3029
3030 try:
3031 injected_packages = dbconn.listAllInjectedPackages(
3032 just_files = True)
3033 injected_packages = set([os.path.basename(x) for x \
3034 in injected_packages])
3035 except dbconn.dbapi2.Error:
3036 pass
3037
3038 for idpackage in idpackages:
3039 url = dbconn.retrieveDownloadURL(idpackage)
3040 package = os.path.basename(url)
3041 branch = dbconn.retrieveBranch(idpackage)
3042 revision = dbconn.retrieveRevision(idpackage)
3043 revisions_match[package] = (branch, revision,)
3044
3045 self.close_server_database(dbconn)
3046
3047 mytxt = "%s: %s: %s" % (
3048 bold(_("WARNING")),
3049 red(_("database already exists")),
3050 self.get_local_database_file(repo),
3051 )
3052 self.updateProgress(
3053 mytxt,
3054 importance = 1,
3055 type = "warning",
3056 header = darkred(" !!! ")
3057 )
3058
3059 rc_question = self.askQuestion(_("Do you want to continue ?"))
3060 if rc_question == "No":
3061 return
3062 try:
3063 os.remove(self.get_local_database_file(repo))
3064 except OSError:
3065 pass
3066
3067
3068
3069 dbconn = self.open_server_repository(read_only = False,
3070 no_upload = True, repo = repo, is_new = True)
3071 dbconn.initializeDatabase()
3072
3073 if not empty:
3074
3075 revisions_file = "/entropy-revisions-dump.txt"
3076
3077 if revisions_match:
3078 self.updateProgress(
3079 "%s: %s" % (
3080 red(_("Dumping current revisions to file")),
3081 darkgreen(revisions_file),
3082 ),
3083 importance = 1,
3084 type = "info",
3085 header = darkgreen(" * ")
3086 )
3087 f_rev = open(revisions_file,"w")
3088 f_rev.write(str(revisions_match))
3089 f_rev.flush()
3090 f_rev.close()
3091
3092
3093 treeupdates_file = "/entropy-treeupdates-dump.txt"
3094 if treeupdates_actions:
3095 self.updateProgress(
3096 "%s: %s" % (
3097
3098 red(_("Dumping current 'treeupdates' actions to file")),
3099 bold(treeupdates_file),
3100 ),
3101 importance = 1,
3102 type = "info",
3103 header = darkgreen(" * ")
3104 )
3105 f_tree = open(treeupdates_file,"w")
3106 f_tree.write(str(treeupdates_actions))
3107 f_tree.flush()
3108 f_tree.close()
3109
3110 rc_question = self.askQuestion(
3111 _("Would you like to sync packages first (important!) ?"))
3112 if rc_question == "Yes":
3113 self.MirrorsService.sync_packages(repo = repo)
3114
3115
3116 if treeupdates_actions:
3117 dbconn.bumpTreeUpdatesActions(treeupdates_actions)
3118
3119
3120 pkg_branch_dir = os.path.join(
3121 self.get_local_packages_directory(repo),
3122 self.SystemSettings['repositories']['branch'])
3123 pkglist = os.listdir(pkg_branch_dir)
3124
3125 pkg_ext_len = len(etpConst['packagesext'])
3126 pkglist = [x for x in pkglist if (x[(pkg_ext_len*-1):] == \
3127 etpConst['packagesext']) and not \
3128 os.path.isfile(os.path.join(pkg_branch_dir,
3129 x + etpConst['packagesexpirationfileext']))]
3130
3131 if pkglist:
3132 self.updateProgress(
3133 "%s '%s' %s %s" % (
3134 red(_("Reinitializing Entropy database for branch")),
3135 bold(self.SystemSettings['repositories']['branch']),
3136 red(_("using Packages in the repository")),
3137 red("..."),
3138 ),
3139 importance = 1,
3140 type = "info",
3141 header = darkgreen(" * ")
3142 )
3143
3144 counter = 0
3145 maxcount = len(pkglist)
3146 branch = self.SystemSettings['repositories']['branch']
3147 for pkg in pkglist:
3148 counter += 1
3149
3150 self.updateProgress(
3151 "[repo:%s|%s] %s: %s" % (
3152 darkgreen(repo),
3153 brown(branch),
3154 blue(_("analyzing")),
3155 bold(pkg),
3156 ),
3157 importance = 1,
3158 type = "info",
3159 header = " ",
3160 back = True,
3161 count = (counter, maxcount,)
3162 )
3163
3164 doinject = False
3165 if pkg in injected_packages:
3166 doinject = True
3167
3168 pkg_path = os.path.join(self.get_local_packages_directory(repo),
3169 branch, pkg)
3170 mydata = self.Spm().extract_package_metadata(pkg_path)
3171 mydata['injected'] = doinject
3172
3173
3174 revision_avail = revisions_match.get(pkg)
3175 add_revision = 0
3176 if (revision_avail != None):
3177 if branch == revision_avail[0]:
3178 add_revision = revision_avail[1]
3179
3180 idpackage, revision, mydata_upd = dbconn.addPackage(mydata,
3181 revision = add_revision)
3182 idpackages_added.add(idpackage)
3183
3184 self.updateProgress(
3185 "[repo:%s] [%s:%s/%s] %s: %s, %s: %s" % (
3186 repo,
3187 brown(branch),
3188 darkgreen(str(counter)),
3189 blue(str(maxcount)),
3190 red(_("added package")),
3191 darkgreen(pkg),
3192 red(_("revision")),
3193 brown(str(revision)),
3194 ),
3195 importance = 1,
3196 type = "info",
3197 header = " ",
3198 back = True
3199 )
3200
3201 self.depends_table_initialize(repo)
3202 self.library_paths_table_initialize(repo)
3203
3204 my_qa = self.QA()
3205
3206 if idpackages_added:
3207 dbconn = self.open_server_repository(read_only = False,
3208 no_upload = True, repo = repo)
3209 my_qa.test_missing_dependencies(
3210 idpackages_added, dbconn, ask = True,
3211 repo = repo, self_check = True,
3212 black_list = \
3213 self.get_missing_dependencies_blacklist(repo = repo),
3214 black_list_adder = \
3215 self.add_missing_dependencies_blacklist_items
3216 )
3217
3218 dbconn.commitChanges()
3219 self.close_server_databases()
3220
3221 return 0
3222
3224
3225 dbconn = self.open_server_repository(read_only = True,
3226 no_upload = True, repo = repo)
3227 if ("world" in packages) or not packages:
3228 return dbconn.listAllIdpackages(), True
3229 else:
3230 idpackages = set()
3231 for package in packages:
3232 matches = dbconn.atomMatch(package, multiMatch = True)
3233 if matches[1] == 0:
3234 idpackages |= matches[0]
3235 else:
3236 mytxt = "%s: %s: %s" % (
3237 red(_("Attention")),
3238 blue(_("cannot match")),
3239 bold(package),
3240 )
3241 self.updateProgress(
3242 mytxt,
3243 importance = 1,
3244 type = "warning",
3245 header = darkred(" !!! ")
3246 )
3247 return idpackages, False
3248
3250
3251 import urllib2
3252 srv_set = self.SystemSettings[self.sys_settings_plugin_id]['server']
3253 if not srv_set['repositories'][repo].has_key('handler'):
3254 return None
3255 url = srv_set['repositories'][repo]['handler']
3256
3257
3258 filename = filename.replace("#","%23")
3259
3260 filename = filename.replace("+","%2b")
3261 request = os.path.join(url, etpConst['handlers']['md5sum'])
3262 request += filename+"&branch="+branch
3263
3264 proxy_settings = self.SystemSettings['system']['proxy']
3265 try:
3266 mydict = {}
3267 if proxy_settings['ftp']:
3268 mydict['ftp'] = proxy_settings['ftp']
3269 if proxy_settings['http']:
3270 mydict['http'] = proxy_settings['http']
3271 if mydict:
3272 mydict['username'] = proxy_settings['username']
3273 mydict['password'] = proxy_settings['password']
3274 self.entropyTools.add_proxy_opener(urllib2, mydict)
3275 else:
3276
3277 urllib2._opener = None
3278 item = urllib2.urlopen(request)
3279 result = item.readline().strip()
3280 item.close()
3281 del item
3282 return result
3283 except (urllib2.URLError, urllib2.HTTPError,):
3284 return None
3285
3287
3288 if repo == None:
3289 repo = self.default_repository
3290
3291 self.updateProgress(
3292 "[%s] %s:" % (
3293 red("remote"),
3294 blue(_("Integrity verification of the selected packages")),
3295 ),
3296 importance = 1,
3297 type = "info",
3298 header = blue(" @@ ")
3299 )
3300
3301 idpackages, world = self.match_packages(packages)
3302 dbconn = self.open_server_repository(read_only = True, no_upload = True,
3303 repo = repo)
3304 branch = self.SystemSettings['repositories']['branch']
3305
3306 if world:
3307 self.updateProgress(
3308 blue(
3309 _("All the packages in repository will be checked.")),
3310 importance = 1,
3311 type = "info",
3312 header = " "
3313 )
3314 else:
3315 mytxt = red("%s:") % (
3316 _("This is the list of the packages that would be checked"),)
3317 self.updateProgress(
3318 mytxt,
3319 importance = 1,
3320 type = "info",
3321 header = " "
3322 )
3323 for idpackage in idpackages:
3324 pkgatom = dbconn.retrieveAtom(idpackage)
3325 down_url = dbconn.retrieveDownloadURL(idpackage)
3326 pkgfile = os.path.basename(down_url)
3327 self.updateProgress(
3328 red(pkgatom) + " -> " + bold(os.path.join(branch, pkgfile)),
3329 importance = 1,
3330 type = "info",
3331 header = darkgreen(" - ")
3332 )
3333
3334 if ask:
3335 rc_question = self.askQuestion(
3336 _("Would you like to continue ?"))
3337 if rc_question == "No":
3338 return set(), set(), {}
3339
3340 match = set()
3341 not_match = set()
3342 broken_packages = {}
3343
3344 for uri in self.get_remote_mirrors(repo):
3345
3346 crippled_uri = self.entropyTools.extract_ftp_host_from_uri(uri)
3347 self.updateProgress(
3348 "[repo:%s] %s: %s" % (
3349 darkgreen(repo),
3350 blue(_("Working on mirror")),
3351 brown(crippled_uri),
3352 ),
3353 importance = 1,
3354 type = "info",
3355 header = red(" @@ ")
3356 )
3357
3358
3359 totalcounter = len(idpackages)
3360 currentcounter = 0
3361 for idpackage in idpackages:
3362
3363 currentcounter += 1
3364 pkgfile = dbconn.retrieveDownloadURL(idpackage)
3365 orig_branch = self.get_branch_from_download_relative_uri(
3366 pkgfile)
3367
3368 self.updateProgress(
3369 "[%s] %s: %s" % (
3370 brown(crippled_uri),
3371 blue(_("checking hash")),
3372 darkgreen(pkgfile),
3373 ),
3374 importance = 1,
3375 type = "info",
3376 header = blue(" @@ "),
3377 back = True,
3378 count = (currentcounter, totalcounter,)
3379 )
3380
3381 checksum_ok = False
3382 ck_remote = self.get_remote_package_checksum(repo,
3383 os.path.basename(pkgfile), orig_branch)
3384 if ck_remote == None:
3385 self.updateProgress(
3386 "[%s] %s: %s %s" % (
3387 brown(crippled_uri),
3388 blue(_("digest verification of")),
3389 bold(pkgfile),
3390 blue(_("not supported")),
3391 ),
3392 importance = 1,
3393 type = "info",
3394 header = blue(" @@ "),
3395 count = (currentcounter, totalcounter,)
3396 )
3397 elif len(ck_remote) == 32:
3398 pkghash = dbconn.retrieveDigest(idpackage)
3399 if ck_remote == pkghash:
3400 checksum_ok = True
3401 else:
3402 self.updateProgress(
3403 "[%s] %s: %s %s" % (
3404 brown(crippled_uri),
3405 blue(_("digest verification of")),
3406 bold(pkgfile),
3407 blue(_("failed for unknown reasons")),
3408 ),
3409 importance = 1,
3410 type = "info",
3411 header = blue(" @@ "),
3412 count = (currentcounter, totalcounter,)
3413 )
3414
3415 if checksum_ok:
3416 match.add(idpackage)
3417 else:
3418 not_match.add(idpackage)
3419 self.updateProgress(
3420 "[%s] %s: %s %s" % (
3421 brown(crippled_uri),
3422 blue(_("package")),
3423 bold(pkgfile),
3424 red(_("NOT healthy")),
3425 ),
3426 importance = 1,
3427 type = "warning",
3428 header = darkred(" !!! "),
3429 count = (currentcounter, totalcounter,)
3430 )
3431 if not broken_packages.has_key(crippled_uri):
3432 broken_packages[crippled_uri] = []
3433 broken_packages[crippled_uri].append(pkgfile)
3434
3435 if broken_packages:
3436 mytxt = blue("%s:") % (
3437 _("This is the list of broken packages"),)
3438 self.updateProgress(
3439 mytxt,
3440 importance = 1,
3441 type = "info",
3442 header = red(" * ")
3443 )
3444 for mirror in broken_packages.keys():
3445 mytxt = "%s: %s" % (
3446 brown(_("Mirror")),
3447 bold(mirror),
3448 )
3449 self.updateProgress(
3450 mytxt,
3451 importance = 1,
3452 type = "info",
3453 header = red(" <> ")
3454 )
3455 for broken_package in broken_packages[mirror]:
3456 self.updateProgress(
3457 blue(broken_package),
3458 importance = 1,
3459 type = "info",
3460 header = red(" - ")
3461 )
3462
3463 self.updateProgress(
3464 "%s:" % (
3465 blue(_("Statistics")),
3466 ),
3467 importance = 1,
3468 type = "info",
3469 header = red(" @@ ")
3470 )
3471 self.updateProgress(
3472 "[%s] %s:\t%s" % (
3473 red(crippled_uri),
3474 brown(_("Number of checked packages")),
3475 brown(str(len(match) + len(not_match))),
3476 ),
3477 importance = 1,
3478 type = "info",
3479 header = brown(" # ")
3480 )
3481 self.updateProgress(
3482 "[%s] %s:\t%s" % (
3483 red(crippled_uri),
3484 darkgreen(_("Number of healthy packages")),
3485 darkgreen(str(len(match))),
3486 ),
3487 importance = 1,
3488 type = "info",
3489 header = brown(" # ")
3490 )
3491 self.updateProgress(
3492 "[%s] %s:\t%s" % (
3493 red(crippled_uri),
3494 darkred(_("Number of broken packages")),
3495 darkred(str(len(not_match))),
3496 ),
3497 importance = 1,
3498 type = "info",
3499 header = brown(" # ")
3500 )
3501
3502 return match, not_match, broken_packages
3503
3504
3506
3507 if repo == None:
3508 repo = self.default_repository
3509
3510 self.updateProgress(
3511 "[%s] %s:" % (
3512 red(_("local")),
3513 blue(_("Integrity verification of the selected packages")),
3514 ),
3515 importance = 1,
3516 type = "info",
3517 header = darkgreen(" * ")
3518 )
3519
3520 idpackages, world = self.match_packages(packages)
3521 dbconn = self.open_server_repository(read_only = True,
3522 no_upload = True, repo = repo)
3523
3524 if world:
3525 self.updateProgress(
3526 blue(_("All the packages in repository will be checked.")),
3527 importance = 1,
3528 type = "info",
3529 header = " "
3530 )
3531
3532 to_download = set()
3533 available = set()
3534 for idpackage in idpackages:
3535
3536 pkgatom = dbconn.retrieveAtom(idpackage)
3537 pkg_path = dbconn.retrieveDownloadURL(idpackage)
3538 pkg_rel_path = '/'.join(pkg_path.split("/")[2:])
3539
3540 bindir_path = os.path.join(self.get_local_packages_directory(repo),
3541 pkg_rel_path)
3542 uploaddir_path = os.path.join(self.get_local_upload_directory(repo),
3543 pkg_rel_path)
3544
3545 if os.path.isfile(bindir_path):
3546 if not world:
3547 self.updateProgress(
3548 "[%s] %s :: %s" % (
3549 darkgreen(_("available")),
3550 blue(pkgatom),
3551 darkgreen(pkg_rel_path),
3552 ),
3553 importance = 0,
3554 type = "info",
3555 header = darkgreen(" # ")
3556 )
3557 available.add(idpackage)
3558 elif os.path.isfile(uploaddir_path):
3559 if not world:
3560 self.updateProgress(
3561 "[%s] %s :: %s" % (
3562 darkred(_("upload/ignored")),
3563 blue(pkgatom),
3564 darkgreen(pkg_rel_path),
3565 ),
3566 importance = 0,
3567 type = "info",
3568 header = darkgreen(" # ")
3569 )
3570 else:
3571 self.updateProgress(
3572 "[%s] %s :: %s" % (
3573 brown(_("download")),
3574 blue(pkgatom),
3575 darkgreen(pkg_rel_path),
3576 ),
3577 importance = 0,
3578 type = "info",
3579 header = darkgreen(" # ")
3580 )
3581 to_download.add((idpackage, pkg_path,))
3582
3583 if ask:
3584 rc_question = self.askQuestion(_("Would you like to continue ?"))
3585 if rc_question == "No":
3586 return set(), set(), set(), set()
3587
3588
3589 fine = set()
3590 failed = set()
3591 downloaded_fine = set()
3592 downloaded_errors = set()
3593
3594 if to_download:
3595
3596 not_downloaded = set()
3597 mytxt = blue("%s ...") % (_("Starting to download missing files"),)
3598 self.updateProgress(
3599 mytxt,
3600 importance = 1,
3601 type = "info",
3602 header = " "
3603 )
3604 for uri in self.get_remote_mirrors(repo):
3605
3606 if not_downloaded:
3607 mytxt = blue("%s ...") % (
3608 _("Searching missing/broken files on another mirror"),)
3609 self.updateProgress(
3610 mytxt,
3611 importance = 1,
3612 type = "info",
3613 header = " "
3614 )
3615 to_download = not_downloaded.copy()
3616 not_downloaded = set()
3617
3618 for idpackage, pkg_path in to_download:
3619 rc_down = self.MirrorsService.download_package(uri,
3620 pkg_path, repo = repo)
3621 if rc_down:
3622 downloaded_fine.add(idpackage)
3623 available.add(idpackage)
3624 else:
3625 not_downloaded.add(pkg_path)
3626
3627 if not not_downloaded:
3628 self.updateProgress(
3629 red(_("Binary packages downloaded successfully.")),
3630 importance = 1,
3631 type = "info",
3632 header = " "
3633 )
3634 break
3635
3636 if not_downloaded:
3637 mytxt = blue("%s:") % (
3638 _("These are the packages that cannot be found online"),)
3639 self.updateProgress(
3640 mytxt,
3641 importance = 1,
3642 type = "info",
3643 header = " "
3644 )
3645 for pkg_path in not_downloaded:
3646 downloaded_errors.add(pkg_path)
3647 self.updateProgress(
3648 brown(pkg_path),
3649 importance = 1,
3650 type = "warning",
3651 header = red(" * ")
3652 )
3653 downloaded_errors |= not_downloaded
3654 mytxt = "%s." % (_("They won't be checked"),)
3655 self.updateProgress(
3656 mytxt,
3657 importance = 1,
3658 type = "warning",
3659 header = " "
3660 )
3661
3662 my_qa = self.QA()
3663
3664 totalcounter = str(len(available))
3665 currentcounter = 0
3666 for idpackage in available:
3667 currentcounter += 1
3668 pkg_path = dbconn.retrieveDownloadURL(idpackage)
3669 orig_branch = self.get_branch_from_download_relative_uri(pkg_path)
3670 pkgfile = os.path.basename(pkg_path)
3671
3672 self.updateProgress(
3673 "[branch:%s] %s %s" % (
3674 brown(orig_branch),
3675 blue(_("checking status of")),
3676 darkgreen(pkgfile),
3677 ),
3678 importance = 1,
3679 type = "info",
3680 header = " ",
3681 back = True,
3682 count = (currentcounter, totalcounter,)
3683 )
3684
3685 storedmd5 = dbconn.retrieveDigest(idpackage)
3686 pkgpath = os.path.join(self.get_local_packages_directory(repo),
3687 orig_branch, pkgfile)
3688 result = self.entropyTools.compare_md5(pkgpath, storedmd5)
3689 qa_fine = my_qa.entropy_package_checks(pkgpath)
3690 if result and qa_fine:
3691 fine.add(idpackage)
3692 else:
3693 failed.add(idpackage)
3694 self.updateProgress(
3695 "[branch:%s] %s %s %s: %s" % (
3696 brown(orig_branch),
3697 blue(_("package")),
3698 darkgreen(pkg_path),
3699 blue(_("is corrupted, stored checksum")),
3700 brown(storedmd5),
3701 ),
3702 importance = 1,
3703 type = "info",
3704 header = " ",
3705 count = (currentcounter, totalcounter,)
3706 )
3707
3708 if failed:
3709 mytxt = blue("%s:") % (_("This is the list of broken packages"),)
3710 self.updateProgress(
3711 mytxt,
3712 importance = 1,
3713 type = "warning",
3714 header = darkred(" # ")
3715 )
3716 for idpackage in failed:
3717 atom = dbconn.retrieveAtom(idpackage)
3718 down_p = dbconn.retrieveDownloadURL(idpackage)
3719 self.updateProgress(
3720 blue("[atom:%s] %s" % (atom, down_p,)),
3721 importance = 0,
3722 type = "warning",
3723 header = brown(" # ")
3724 )
3725
3726
3727 self.updateProgress(
3728 red("Statistics:"),
3729 importance = 1,
3730 type = "info",
3731 header = blue(" * ")
3732 )
3733 self.updateProgress(
3734 brown("%s => %s" % (
3735 len(fine) + len(failed),
3736 _("checked packages"),
3737 )
3738 ),
3739 importance = 0,
3740 type = "info",
3741 header = brown(" # ")
3742 )
3743 self.updateProgress(
3744 darkgreen("%s => %s" % (
3745 len(fine),
3746 _("healthy packages"),
3747 )
3748 ),
3749 importance = 0,
3750 type = "info",
3751 header = brown(" # ")
3752 )
3753 self.updateProgress(
3754 darkred("%s => %s" % (
3755 len(failed),
3756 _("broken packages"),
3757 )
3758 ),
3759 importance = 0,
3760 type = "info",
3761 header = brown(" # ")
3762 )
3763 self.updateProgress(
3764 blue("%s => %s" % (
3765 len(downloaded_fine),
3766 _("downloaded packages"),
3767 )
3768 ),
3769 importance = 0,
3770 type = "info",
3771 header = brown(" # ")
3772 )
3773 self.updateProgress(
3774 bold("%s => %s" % (
3775 len(downloaded_errors),
3776 _("failed downloads"),
3777 )
3778 ),
3779 importance = 0,
3780 type = "info",
3781 header = brown(" # ")
3782 )
3783
3784 self.close_server_database(dbconn)
3785 return fine, failed, downloaded_fine, downloaded_errors
3786
3787
3789
3790 if repo == None:
3791 repo = self.default_repository
3792
3793 if to_branch != self.SystemSettings['repositories']['branch']:
3794 mytxt = "%s: %s %s" % (
3795 blue(_("Please setup your branch to")),
3796 bold(to_branch),
3797 blue(_("and retry")),
3798 )
3799 self.updateProgress(
3800 mytxt,
3801 importance = 1,
3802 type = "error",
3803 header = darkred(" !! ")
3804 )
3805 return None
3806
3807 mytxt = red("%s ...") % (_("Copying database (if not exists)"),)
3808 self.updateProgress(
3809 mytxt,
3810 importance = 1,
3811 type = "info",
3812 header = darkgreen(" @@ ")
3813 )
3814 branch_dbdir = self.get_local_database_dir(repo)
3815 old_branch_dbdir = self.get_local_database_dir(repo, from_branch)
3816
3817
3818 self.close_server_databases()
3819
3820
3821
3822 branch_dbfile = self.get_local_database_file(repo)
3823 if os.path.isfile(branch_dbfile):
3824 if self.entropyTools.get_file_size(branch_dbfile) == 0:
3825 shutil.rmtree(branch_dbdir, True)
3826
3827 if os.path.isdir(branch_dbdir):
3828
3829 while 1:
3830 rnd_num = self.entropyTools.get_random_number()
3831 backup_dbdir = branch_dbdir + str(rnd_num)
3832 if not os.path.isdir(backup_dbdir):
3833 break
3834 os.rename(branch_dbdir, backup_dbdir)
3835
3836 if os.path.isdir(old_branch_dbdir):
3837 shutil.copytree(old_branch_dbdir, branch_dbdir)
3838
3839 mytxt = red("%s ...") % (_("Switching packages"),)
3840 self.updateProgress(
3841 mytxt,
3842 importance = 1,
3843 type = "info",
3844 header = darkgreen(" @@ ")
3845 )
3846
3847 dbconn = self.open_server_repository(read_only = False,
3848 no_upload = True, repo = repo, lock_remote = False)
3849 try:
3850 dbconn.validateDatabase()
3851 except SystemDatabaseError:
3852 self.handle_uninitialized_repository(repo)
3853 dbconn = self.open_server_repository(read_only = False,
3854 no_upload = True, repo = repo, lock_remote = False)
3855
3856 idpackages = dbconn.listAllIdpackages()
3857 already_switched = set()
3858 not_found = set()
3859 switched = set()
3860 ignored = set()
3861 no_checksum = set()
3862
3863 maxcount = len(idpackages)
3864 count = 0
3865 for idpackage in idpackages:
3866 count += 1
3867
3868 cur_branch = dbconn.retrieveBranch(idpackage)
3869 atom = dbconn.retrieveAtom(idpackage)
3870 if cur_branch == to_branch:
3871 already_switched.add(idpackage)
3872 self.updateProgress(
3873 red("%s %s, %s %s" % (
3874 _("Ignoring"),
3875 bold(atom),
3876 _("already in branch"),
3877 cur_branch,
3878 )
3879 ),
3880 importance = 0,
3881 type = "info",
3882 header = darkgreen(" @@ "),
3883 count = (count, maxcount,)
3884 )
3885 ignored.add(idpackage)
3886 continue
3887
3888 self.updateProgress(
3889 "[%s=>%s] %s" % (
3890 brown(cur_branch),
3891 bold(to_branch),
3892 darkgreen(atom),
3893 ),
3894 importance = 0,
3895 type = "info",
3896 header = darkgreen(" @@ "),
3897 back = True,
3898 count = (count, maxcount,)
3899 )
3900 dbconn.switchBranch(idpackage, to_branch)
3901 dbconn.commitChanges()
3902 switched.add(idpackage)
3903
3904 dbconn.commitChanges()
3905
3906
3907 dbconn.moveSpmUidsToBranch(to_branch, from_branch = from_branch)
3908
3909 self.close_server_database(dbconn)
3910 mytxt = blue("%s.") % (_("migration loop completed"),)
3911 self.updateProgress(
3912 "[%s=>%s] %s" % (
3913 brown(from_branch),
3914 bold(to_branch),
3915 mytxt,
3916 ),
3917 importance = 1,
3918 type = "info",
3919 header = darkgreen(" * ")
3920 )
3921
3922 return switched, already_switched, ignored, not_found, no_checksum
3923
3925
3926 if branch == None:
3927 branch = self.SystemSettings['repositories']['branch']
3928 if repo == None:
3929 repo = self.default_repository
3930
3931 sets_dir = self.get_local_database_sets_dir(repo, branch)
3932 if not (os.path.isdir(sets_dir) and os.access(sets_dir, os.R_OK)):
3933 return {}
3934
3935 mydata = {}
3936 items = os.listdir(sets_dir)
3937 for item in items:
3938
3939 try:
3940 item_clean = str(item)
3941 except (UnicodeEncodeError, UnicodeDecodeError,):
3942 continue
3943 item_path = os.path.join(sets_dir, item)
3944 if not (os.path.isfile(item_path) and \
3945 os.access(item_path, os.R_OK)):
3946 continue
3947 item_elements = self.entropyTools.extract_packages_from_set_file(
3948 item_path)
3949 if item_elements:
3950 mydata[item_clean] = item_elements.copy()
3951
3952 return mydata
3953
3984
3998