source: products/quintagroup.themetemplate/trunk/quintagroup/themetemplate/localcommands/templates/importing/utils.py_tmpl @ 1005

Last change on this file since 1005 was 1005, checked in by mylan, 15 years ago

Import package: Copied http://svn.quintagroup.com/products/qtheme.template/trunk@2041 + modifications concerning changed package name, namespace

File size: 11.0 KB
Line 
1#
2import transaction
3import os, sys, re, string
4from sets import Set
5from StringIO import StringIO
6from time import gmtime, strftime
7from zLOG import LOG, INFO
8from zExceptions import BadRequest
9from App.config import getConfiguration
10from Products.CMFCore.utils import getToolByName
11from Products.CMFCore.DirectoryView import addDirectoryViews
12from Globals import package_home
13
14from fixes import fix
15from ${namespace_package}.${namespace_package2}.${package} import GLOBALS
16
17IMPORT_POLICY = "backup"
18
19######################################################################
20##                      IMPORTING UTILS                             ##
21######################################################################
22osp = os.path
23ALLOWED_IMPORT_POLICY = ["only_new", "backup", "overwrite"]
24INTRO_TO_INSTANCE = "< Started copying object files from Product import directory to Instance one."
25SUMMARY_TO_INSTANCE = "> Finished copying."
26INTRO_TO_ROOT = "< Started import %s file[s] with '%s' policy."
27SUMMARY_TO_ROOT = "> Finished importing."
28INTRO_CLEAN = "< Started cleaning Instance import directory."
29SUMMARY_CLEAN = "> Finished cleaning."
30CREXP_INVALID_ID = re.compile('^The id \"(.*?)\" is invalid - it is already in use.$', re.DOTALL|re.IGNORECASE|re.MULTILINE)
31CSS_BASE_IDS_QPSD053 = ['id','expression','enabled','cookable','media','rel','title','rendering']   # supporting qPSD-0.5.3 version
32################    CHECK IMPORTING    ################
33def checkIfImport():
34    """ Return if perform importing, based on checking
35        *zexp files in <SkinProduct>/import directory.
36    """
37    instance_ipath, product_ipath = getImportedPathes()
38    product_ilist = [i for i in os.listdir(product_ipath) \
39                     if osp.isfile(osp.join(product_ipath,i)) and i.endswith('.zexp')]
40    if product_ilist:
41        return 1
42    return 0
43
44################    IMPORTING TO PLONE'S IMPORT DIR   ################
45def getImportedPathes():
46    """ Return Plone instance and Skin product import pathes."""
47    # Based on instance path, construct import pathes
48    cfg = getConfiguration()
49    instance_ipath = osp.join(cfg.instancehome, "import")
50    product_ipath = osp.join(package_home(GLOBALS), "import")
51    # Check presence of Product import directory
52    if not osp.isdir(product_ipath):       
53        raise BadRequest, "Skin Product's import directory '%s' - does not exist or is'nt direcory" % product_ipath
54    # Check presence of Instance import directory
55    if not osp.isdir(instance_ipath):
56        raise BadRequest, "Instance import directory '%s' - does not exist or isn't direcory" % instance_ipath
57    return [instance_ipath, product_ipath]
58
59def copyFile(src_dir, dst_dir, f_name):
60    """ Copy file from src_dir to dst_dir under original name."""
61    try:
62        src_file = open(osp.join(src_dir, f_name),"rb")
63        dst_file = open(osp.join(dst_dir, f_name),"wb")
64        dst_file.write(src_file.read())
65        dst_file.close()
66        src_file.close()
67    except Exception, e:
68        msg = "!!! In copying files from < %s > dir to < %s > dir exception occur. Details: %s." % (src_dir,dst_dir, str(e))
69        print >> import_out, msg
70        LOG('performImportToPortal',INFO,'copyFile', msg)
71
72def moveToTemp(same_instance_files, instance_ipath, temp_dir_path):
73    """ Move samenamed files from Instanse's dir to temp dir."""
74    os.mkdir(temp_dir_path) # Create temp back_[date] dir
75    try:
76        [copyFile(instance_ipath, temp_dir_path, f_name) for f_name in same_instance_files]
77        [os.remove(osp.join(instance_ipath, f_name)) for f_name in same_instance_files]
78    except Exception, e:
79        msg = "!!! Exception occur during moving files from Instance's dir to temp dir. Detaile:%s." % str(e)
80        print >> import_out, msg
81        LOG('performImportToPortal',INFO,'moveToTemp', msg)
82   
83def copyToInstanceImport():
84    """ Perform copying imported files from <SkinProduct>/import dir
85        to Plone's instance import dir.
86    """
87    print >> import_out, INTRO_TO_INSTANCE
88    instance_ipath, product_ipath = getImportedPathes()
89    # Compose temp dir back_[date] dir path in Instance import directory
90    temp_dir_id = "back_%s" % strftime("%Y%m%d%H%M%S", gmtime())
91    temp_dir_path = osp.join(instance_ipath, temp_dir_id)
92    # Get *.zexp files from Skin Product's import dir and Plone's instance import dir files
93    product_ilist = [i for i in os.listdir(product_ipath) \
94                     if osp.isfile(osp.join(product_ipath,i)) and i.endswith('.zexp')]
95    instance_ilist = [i for i in os.listdir(instance_ipath) \
96                      if osp.isfile(osp.join(instance_ipath,i)) and i.endswith('.zexp')]
97    # Check for presence samenamed files in Instance and Product import directories.
98    same_instance_files = [f_name for f_name in instance_ilist if f_name in product_ilist]
99    if same_instance_files:
100        moveToTemp(same_instance_files, instance_ipath, temp_dir_path)
101    # Copy all *zexp files from Product's import dir to Instance's import dir
102    [copyFile(product_ipath, instance_ipath, f_name) for f_name in product_ilist]
103    print >> import_out, SUMMARY_TO_INSTANCE
104    return [instance_ipath, product_ipath, temp_dir_path, product_ilist]
105
106################    IMPORTING TO PORTAL   ################
107def importObject(portal, file_name):
108    """ Work around old Zope bug in importing."""
109    try:
110        portal.manage_importObject(file_name)
111    except:
112        portal._p_jar = portal.Destination()._p_jar
113        portal.manage_importObject(file_name)
114
115def makeBackUp(portal, portal_objects, temp_dir_path, obj_id):
116    """ Perfom backup same named portal objects in temp folder."""
117    # Get id of temp folder-object
118    durty_path,temp_id = osp.split(temp_dir_path)
119    if not temp_id:
120        durty_path,temp_id = osp.split(durty_path)
121    # Get temp folder-object
122    if temp_id not in portal_objects:
123        portal.invokeFactory('Large Plone Folder', id=temp_id)
124        print >> import_out, "! Created '%s' backup directory with same-ids " \
125                             "objects from portal root." % temp_id
126    temp_dir = getattr(portal, temp_id)
127    # Move object with same id to temp folder-object
128    #get_transaction().commit(1)
129    transaction.savepoint()
130    obj = portal.manage_cutObjects(ids=[obj_id])
131    temp_dir.manage_pasteObjects(obj)
132    print >> import_out, "! '%s' Object moved from portal root to '%s' backup directory." % (obj_id, temp_id)
133
134def performImport(portal, temp_dir_path, file_name):
135    """ Importing an object to portal."""
136    portal_objects = portal.objectIds()
137    try:
138        portal.manage_importObject(file_name)
139    except Exception, e:
140        msg = str(e)
141        is_invalid_id = CREXP_INVALID_ID.match(msg)
142        if is_invalid_id:
143            obj_id = is_invalid_id.group(1)
144            if IMPORT_POLICY == "only_new":
145                msg = "! Object with '%s' id was not importing because it's already exist " \
146                      "in portal root." % obj_id
147                print >> import_out, msg
148            elif IMPORT_POLICY == "backup":
149                makeBackUp(portal, portal_objects, temp_dir_path, obj_id)
150                importObject(portal, file_name)
151            elif IMPORT_POLICY == "overwrite":
152                portal.manage_delObjects(ids=[obj_id])
153                importObject(portal, file_name)
154        else:
155            # work around old Zope bug in importing
156            portal._p_jar = portal.Destination()._p_jar
157            portal.manage_importObject(file_name)
158
159def importToPortalRoot(portal, product_file_names, temp_dir_path):
160    """ Import all objects from *zexp files to portal root (based on IMPORT_POLICY)."""
161    if not IMPORT_POLICY in ALLOWED_IMPORT_POLICY:
162        raise Exception("%s - wrong import policy, must be one of the %s" \
163                        % (IMPORT_POLICY, ALLOWED_IMPORT_POLICY) )
164    print >> import_out, INTRO_TO_ROOT % (product_file_names, IMPORT_POLICY)
165    for file_name in product_file_names:
166        try:
167            # Temporary allow implicitly adding Large Plone Folder
168            types_tool = getToolByName(portal, 'portal_types')
169            lpf_fti = types_tool['Large Plone Folder']
170            lpf_global_setting = lpf_fti.global_allow
171            lpf_fti.global_allow = 1
172            try:
173                performImport(portal, temp_dir_path, file_name)
174            finally:
175                lpf_fti.global_allow = lpf_global_setting
176        except Exception, error:
177            msg = '!!! Under "%s" policy importing exception occur: %s.' % (IMPORT_POLICY, str(error))
178            print >> import_out, msg
179            LOG('performImportToPortal',INFO,'importToPortalRoot', msg)
180    print >> import_out, SUMMARY_TO_ROOT
181
182################    CLEANING PLONE'S IMPORT DIR   ################
183def cleanInstanceImport(instance_ipath, product_file_names, temp_dir_path):
184    """ Cleaning Plone's import dir."""
185    print >> import_out, INTRO_CLEAN
186    # Erase all copied *zexp files from Instance's import dir
187    for f_name in product_file_names:
188        f_path = osp.join(instance_ipath, f_name)
189        if osp.exists(f_path) and osp.isfile(f_path):
190            os.remove(f_path)
191        else:
192            msg = '! "%s" file was not deleted from "%s" import directory.' %\
193                   (f_name, osp.join(instance_ipath))
194            print >> import_out, msg
195            LOG('performImportToPortal',INFO,'cleanInstanceImport', msg)
196    # Move all files from temp back_[date] dir to Instance's import dir
197    if osp.exists(temp_dir_path) and osp.isdir(temp_dir_path):
198        f_names = os.listdir(temp_dir_path)
199        try:
200            [copyFile(temp_dir_path, instance_ipath, f_name) for f_name in f_names]
201            [os.remove(osp.join(temp_dir_path, f_name)) for f_name in f_names]
202            # Erase temp back_[date] dir
203            os.rmdir(temp_dir_path)
204        except Exception, e:
205            msg = "!!! In moving files from temp dir to Instance's import dir exception occur."
206            print >> import_out, msg
207            LOG('performImportToPortal',INFO,'moveFromTempToImport', msg)
208    print >> import_out, SUMMARY_CLEAN
209
210def fixImportingIssues(portal, beforeimporting_objects):
211    ''' Fix defects of importing process: reindexing, other'''
212    afterimporting_objects = portal.objectItems()
213    diff_objects = list(Set(afterimporting_objects)-Set(beforeimporting_objects))
214    for id, ob in diff_objects:
215        if id.startswith('back_'):
216            continue
217        fix(ob)
218
219################    MAIN    ################
220def performImportToPortal(portal):
221    """ Import objects from Skin Product to Portal root."""
222    globals()['import_out'] = StringIO()
223    instance_ipath, product_ipath, temp_dir_path, product_file_names = copyToInstanceImport()
224    if product_file_names:
225        beforeimporting_objects = portal.objectItems()
226        importToPortalRoot(portal, product_file_names, temp_dir_path)
227        fixImportingIssues(portal, beforeimporting_objects)
228        cleanInstanceImport(instance_ipath, product_file_names, temp_dir_path)
229    else:
230        print >> import_out, "!!! Failure importing: there is no file for importing to be found."
231    result = import_out.getvalue()
232    del globals()['import_out']
233    return result
234
235#
Note: See TracBrowser for help on using the repository browser.