def upload_package(distro, comp, files, changes, skipUpdateMeta=False, forceUpdateMeta=False): # files is array of files of .deb, .dsc, .tar.gz and .changes # these files are belongs to single package meta = {} affected_arches = set() for file in files: filename = os.path.basename(file) base_key = "{0}/pool/{1}".format(distro, filename) with open(file) as f: hashes = common.get_hashes(f) log.info("Uploading %s to distro '%s' component '%s'", base_key, distro, comp) storage_key = plugin_loader.get_plugin('storage').put(base_key, filename=file) #storage_key = os.path.join(common.config['repo_daemon']['storage_subdir'], storage_key) if file.endswith('.deb') or file.endswith('.udeb'): if 'debs' not in meta: meta['debs'] = [] deb = _process_deb_file(file, storage_key) meta['debs'].append(deb) else: if 'sources' not in meta: meta['sources'] = [] source,dsc = _process_source_file(file, storage_key) meta['sources'].append(source) if dsc: meta['dsc'] = dsc if changes: meta['Source'] = changes['source'] meta['Version'] = changes['version'] else: # if changes file is not present (i.e. we are uploading single deb file in non-strict repo), # take package name and version from 1st (which also should be last) deb file meta['Source'] = meta['debs'][0]['Package'] meta['Version'] = meta['debs'][0]['Version'] affected_arches.update(x['Architecture'] for x in meta['debs']) if affected_arches: # critical section. updating meta DB try: with common.RepoLock(distro, comp): common.db_packages.packages.find_one_and_update( {'Source': meta['Source'], 'Version': meta['Version']}, {'$set': meta, '$addToSet': {'repos': {'distro': distro, 'component': comp}}}, upsert=True) if not skipUpdateMeta: log.info("Updating '%s/%s' distro metadata for arches: %s", distro, comp, ', '.join(affected_arches)) update_distro_metadata(distro, [comp], affected_arches, force=forceUpdateMeta) except common.RepoLockTimeout as e: log.error("Error updating distro: %s", e) raise common.TemporaryError("Cannot lock distro: {0}".format(e)) else: log.info("No changes made on distro %s/%s, skipping metadata update", distro, comp)
def _process_deb_file(file, storage_key): with open(file) as f: hashes = common.get_hashes(f) doc = { 'size': os.stat(file)[stat.ST_SIZE], 'sha512': binary.Binary(hashes['sha512']), 'sha256': binary.Binary(hashes['sha256']), 'sha1': binary.Binary(hashes['sha1']), 'md5': binary.Binary(hashes['md5']), 'storage_key': storage_key } try: deb = debfile.DebFile(file) except debfile.DebError as e: log.critical("Cannot load debfile %s: %s", file, e) raise common.FatalError("Cannot load debfile {0}: {1}".format(file, e)) doc.update(deb.debcontrol()) return doc
def _process_source_file(file, storage_key): with open(file) as f: hashes = common.get_hashes(f) filename = os.path.basename(file) dsc = None doc = { 'name': filename, 'size': os.stat(file)[stat.ST_SIZE], 'sha512': binary.Binary(hashes['sha512']), 'sha256': binary.Binary(hashes['sha256']), 'sha1': binary.Binary(hashes['sha1']), 'md5': binary.Binary(hashes['md5']), 'storage_key': storage_key } if file.endswith('.dsc'): with open(file) as f: dsc = deb822.Dsc(f) dsc = dict((k,v) for k,v in dsc.items() if not k.startswith('Checksums-') and k != 'Files') return doc, dsc