summaryrefslogtreecommitdiff
blob: 30afc8a5ee6ec92b301319a8f913d4d39a8b38bb (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
import re, os
from ebuild import *
from filetricks import *
from settings import *

def pmsify_package_version(version_str):
    return version_str.replace('-','.') #some CRAN-style versions have the form 0.1-1, which we transform into 0.1.1

def pmsify_package_list(package_list):
    #note: the following returns a list of tuples
    matches=re.findall(r'\s*(([^,]+\([^()]+?\))|([^,]+))\s*',package_list) #split into packages + versions
    packages=[]
    for package_part in matches: #process each package match
        if len(package_part[1])>len(package_part[2]): #versioned package identifier
            parse=re.match(r'([^,]+)\(([^()]+?)\)',package_part[1])
            pkg_name=parse.group(1).strip()
            versions=parse.group(2)
            #fixme version specifiers
            if pkg_name=='R':
                category='dev-lang'
            else:
                category='dev-R'
            packages.append(category+'/'+pkg_name)
        else:
            pkg_name=package_part[2].strip()
            if pkg_name=='R':
                category='dev-lang'
            else:
                category='dev-R' #assume it's a CRAN package
            packages.append(category+'/'+pkg_name)
    return packages

#Parse package options into values we can work with in accordance with PMS
def pmsify_package_data(data,remote_repository):
    pms_pkg=Ebuild()
    pms_pkg.cran_data=data
    e_vars=pms_pkg.ebuild_vars
    #fix settings:
    if 'package' not in data:
        e_vars['pn']='test'
    else:
        e_vars['pn']=data['package']
    if not re.match('[a-zA-Z0-9+_].*',e_vars['pn']): #package name may not be valid according to PMS
        e_vars['pn']='_'+e_vars.pn
    if re.match('.*-[0-9]+',e_vars['pn']):
        e_vars['pn']=e_vars.pn+'_'
    if 'version' not in data: #set a version even if we have none
        e_vars['pv']='0'
    else:
        e_vars['pv']=pmsify_package_version(data['version'])
    if 'depends' in data:
        deps=pmsify_package_list(data['depends'])
    else: #some packages don't set dependencies, so force dependency on R
        deps=['dev-lang/R',]
    e_vars['depend']=deps
    e_vars['pdepend']=deps
    e_vars['rdepend']=deps
    
    e_vars['iuse']="doc"
    e_vars['keywords']="~x86 ~amd64"
    if 'description' in data:
        e_vars['description']=data['description'].strip().replace('\n',' ')
    else:
        e_vars['description']=e_vars['pn']
    if 'license' in data: #fixme parse license data
        e_vars['license']=data['license'].strip()

    e_vars['src_uri']=remote_repository+'/src/contrib/'+data['package']+'_'+data['version']+'.tar.gz'
    return pms_pkg

def read_packages(package_filename,local_repository):
    packages_file=open(package_filename,"r")
    file_parts=EmptyLinesFile(packages_file) #this is where we split the PACKAGES file into several file parts
    packages=[]
    import rfc822
    repository_file=open(os.path.join(local_repository,REPO_MYDIR,'remote_uri'),'r')
    remote_uri=repository_file.read().strip()
    while not file_parts.eof:
        cran_package=dict(rfc822.Message(file_parts).items()) #read part of PACKAGES file
        pms_package=pmsify_package_data(cran_package,remote_uri) #fix values
        packages.append(pms_package) #store in dict
    return packages

def find_package(repo_location,package_name):
    packages=read_packages(os.path.join(repo_location,REPO_MYDIR,'PACKAGES'),repo_location)
    for package in packages:
        if package.ebuild_vars['pn']==package_name:
	    return package
    raise ValueError("Package not found")