egg2wheel.py 2.6 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273
  1. #!/usr/bin/env python
  2. import os.path
  3. import re
  4. import sys
  5. import tempfile
  6. import zipfile
  7. import wheel.bdist_wheel
  8. import shutil
  9. import distutils.dist
  10. from distutils.archive_util import make_archive
  11. from argparse import ArgumentParser
  12. from glob import iglob
  13. egg_info_re = re.compile(r'''(?P<name>.+?)-(?P<ver>.+?)
  14. (-(?P<pyver>.+?))?(-(?P<arch>.+?))?.egg''', re.VERBOSE)
  15. def egg2wheel(egg_path, dest_dir):
  16. egg_info = egg_info_re.match(os.path.basename(egg_path)).groupdict()
  17. dir = tempfile.mkdtemp(suffix="_e2w")
  18. if os.path.isfile(egg_path):
  19. # assume we have a bdist_egg otherwise
  20. egg = zipfile.ZipFile(egg_path)
  21. egg.extractall(dir)
  22. else:
  23. # support buildout-style installed eggs directories
  24. for pth in os.listdir(egg_path):
  25. src = os.path.join(egg_path, pth)
  26. if os.path.isfile(src):
  27. shutil.copy2(src, dir)
  28. else:
  29. shutil.copytree(src, os.path.join(dir, pth))
  30. dist_info = "%s-%s" % (egg_info['name'], egg_info['ver'])
  31. abi = 'none'
  32. pyver = egg_info['pyver'].replace('.', '')
  33. arch = (egg_info['arch'] or 'any').replace('.', '_').replace('-', '_')
  34. if arch != 'any':
  35. # assume all binary eggs are for CPython
  36. pyver = 'cp' + pyver[2:]
  37. wheel_name = '-'.join((
  38. dist_info,
  39. pyver,
  40. abi,
  41. arch
  42. ))
  43. bw = wheel.bdist_wheel.bdist_wheel(distutils.dist.Distribution())
  44. bw.root_is_purelib = egg_info['arch'] is None
  45. dist_info_dir = os.path.join(dir, '%s.dist-info' % dist_info)
  46. bw.egg2dist(os.path.join(dir, 'EGG-INFO'),
  47. dist_info_dir)
  48. bw.write_wheelfile(dist_info_dir, generator='egg2wheel')
  49. bw.write_record(dir, dist_info_dir)
  50. filename = make_archive(os.path.join(dest_dir, wheel_name), 'zip', root_dir=dir)
  51. os.rename(filename, filename[:-3] + 'whl')
  52. shutil.rmtree(dir)
  53. def main():
  54. parser = ArgumentParser()
  55. parser.add_argument('eggs', nargs='*', help="Eggs to convert")
  56. parser.add_argument('--dest-dir', '-d', default=os.path.curdir,
  57. help="Directory to store wheels (default %(default)s)")
  58. parser.add_argument('--verbose', '-v', action='store_true')
  59. args = parser.parse_args()
  60. for pat in args.eggs:
  61. for egg in iglob(pat):
  62. if args.verbose:
  63. sys.stdout.write("{0}... ".format(egg))
  64. egg2wheel(egg, args.dest_dir)
  65. if args.verbose:
  66. sys.stdout.write("OK\n")
  67. if __name__ == "__main__":
  68. main()