Revision 58b9c196

b/cloudcms/forms.py
5 5
import os
6 6
import glob
7 7
import logging
8
import StringIO
8 9

  
9 10
from django import forms
10 11
from django.conf import settings
......
63 64
    return MediaCategory.objects.get(slug=slug)
64 65

  
65 66

  
66
CATEGORIES_CHOICES = (('faqs', 'FAQs'), ('guide', 'User guide'))
67
CATEGORIES_CHOICES = (('faq', 'FAQs'), ('user-guide', 'User guide'))
67 68

  
68 69
class RstZipImportForm(forms.Form):
69 70

  
......
102 103
        return data
103 104

  
104 105
    def clean_existing_data(self):
106
        logger.warning("Removing all FAQ questions")
105 107
        Question.objects.all().delete()
108
        logger.warning("Removing all User Guide entries")
106 109
        UserGuideEntry.objects.all().delete()
110
        logger.warning("Removing all media files in categories %s", [self.FAQ_MEDIA_CATEGORY,
111
            self.GUIDE_MEDIA_CATEGORY])
107 112
        MediaFile.objects.filter(categories__slug__in=[self.FAQ_MEDIA_CATEGORY, \
108 113
            self.GUIDE_MEDIA_CATEGORY]).delete()
109 114

  
110 115
    def save(self, user, use_dir=None):
116
        stream = StringIO.StringIO()
117
        stream_handler = logging.StreamHandler(stream)
118
        stream_handler.setFormatter(logging.Formatter('<div class="log-entry %(levelname)s"><em>%(levelname)s</em>'
119
            '<pre>%(message)s</pre></div>'))
120
        logger.addHandler(stream_handler)
121
        old_level = logger.level
122
        logger.setLevel(logging.DEBUG)
123

  
111 124
        dry_run = self.cleaned_data.get('dry_run')
112 125
        clean_data = self.cleaned_data.get('clean_data')
113 126
        import_file = self.cleaned_data.get('import_file')
......
125 138
                subdirs[0])) and subdirs[0] != 'source':
126 139
            zipdir = os.path.join(zipdir, subdirs[0])
127 140

  
128
        #sid = transaction.savepoint()
141
        sid = transaction.savepoint()
129 142

  
130 143
        if clean_data:
131 144
            try:
145
                logger.warning("Removing exising entries")
132 146
                self.clean_existing_data()
133 147
            except Exception, e:
134
                return False
148
                transaction.savepoint_rollback(sid)
149
                logger.exception("Failed to clean existing data")
150
                logger.removeHandler(stream_handler)
151
                logger.setLevel(old_level)
152
                return False, stream.getvalue()
135 153

  
136 154
        ret = ""
137 155
        try:
156
            logger.warning("Parsing contents of '%s'", zipdir)
138 157
            for data_type, rst, category, slug, title, html_content, \
139 158
                    images, stderr in generate_rst_contents_from_dir(zipdir):
140 159

  
141
                ret += stderr
142
                #logger.info("Parsed %s" % (rst, ))
143 160
                if stderr:
144
                    pass
145
                    #logger.info("Error output: %s" % (stderr, ))
161
                    logger.error("Docutils error output for '%s'\n: %s" % (rst, stderr, ))
146 162

  
147 163
                service = service_from_filename(rst)
148 164
                if not service:
149 165
                    logger.info("Skipping entry for file '%s'. No category found" % rst)
150 166
                    continue
151 167

  
168
                logger.info("Processing, '%s'" % (rst, ))
169

  
152 170

  
153 171
                # first save media files
172
                cat = False
154 173
                newimages = []
155 174
                if data_type == 'userguide':
156 175
                    cat = get_media_category(self.GUIDE_MEDIA_CATEGORY)
......
158 177
                    cat = get_media_category(self.FAQ_MEDIA_CATEGORY)
159 178

  
160 179
                if not cat:
180
                    logger.info("Skipping %s, no media category found for '%s'",
181
                            rst, data_type)
161 182
                    continue
162 183

  
163 184
                for imgname, imgpath, imgabspath in images:
185
                    logger.debug("Checking image (%s, %s, %s)", imgname, imgpath, imgabspath)
164 186
                    newalt, newpath = create_or_update_media_file(cat, \
165 187
                            imgname, imgabspath)
166 188

  
......
169 191
                # now html contains correct image links, we are ready to save
170 192
                # the faq/guide content
171 193
                if data_type == 'faq':
194
                    logger.info('Processing FAQ entry, %s, %s, %s', service, slug, title)
172 195
                    cat = add_or_update_faq_category(category[0], category[1])
173 196
                    question = add_or_update_faq_question(user, service, cat, slug, \
174 197
                            title, html_content)
175 198

  
176 199
                if data_type == 'userguide':
200
                    logger.info('Processing USER GUIDE entry, %s, %s, %s', service, slug, title)
177 201
                    guide_entry = add_or_update_guide_entry(user, service, slug, \
178 202
                            title, html_content)
179 203

  
180 204

  
181 205
        except Exception, e:
182 206
            logger.exception("RST import failed")
183
            #transaction.savepoint_rollback(sid)
184
            return False
207
            logger.removeHandler(stream_handler)
208
            logger.setLevel(old_level)
209
            transaction.savepoint_rollback(sid)
210
            return False, stream.getvalue()
185 211

  
186 212
        if dry_run:
187
            pass
188
            #transaction.savepoint_rollback(sid)
213
            transaction.savepoint_rollback(sid)
189 214
        else:
190
            pass
191
            #transaction.savepoint_commit(sid)
215
            transaction.savepoint_commit(sid)
216

  
217
        return True, stream.getvalue()
192 218

  
193 219

  
194 220
def create_or_update_media_file(category, name, path):
221
    logger.info("Create or update media file, %s, %s, [category: %s]", name,
222
            path, category)
195 223
    name = category.title + " " + name
196 224

  
197 225
    try:
198 226
        # TODO: Check language ?????
199
        mf = MediaFile.objects.get(categories=category, translations__caption=name)
227
        mf = MediaFile.objects.get(categories__in=[category], translations__caption=name)
228
        logger.info("Media file found")
200 229
    except MediaFile.DoesNotExist:
230
        logger.info("Media file not found, creating...")
201 231
        mf = MediaFile()
202
        mf.category = category
203 232
        mf.file = File(open(path))
204 233
        mf.save()
205 234
        mf.translations.create(caption=name)
235
        mf.categories.clear()
236
        mf.categories = [category]
237
        mf.save()
206 238

  
207 239
    # TODO: Check language ?????
208 240
    return mf.translations.all()[0].caption, mf.get_absolute_url()
209 241

  
210 242

  
211 243
def add_or_update_faq_category(slug, name):
244
    logger.info("Create or update faq subcategory, %s, %s", slug,
245
            name)
212 246
    try:
213 247
        category = FaqCategory.objects.get(translations__slug=slug)
248
        logger.info("FAQ category found")
214 249
    except FaqCategory.DoesNotExist:
250
        logger.info("FAQ category not found, creating...")
215 251
        category = FaqCategory()
216 252
        category.save()
217 253
        category.translations.create(slug=slug, title=name)
218 254

  
219 255
    return category
220 256

  
257

  
221 258
def add_or_update_faq_question(author, service, category, slug,\
222 259
        title, html_content):
260
    logger.info("Create or update faq question, %s, %s, %s, %s", service,
261
            category, slug, title)
223 262

  
224 263
    try:
225 264
        q = Question.objects.get(slug=slug)
265
        logger.info("Question found, updating...")
226 266
    except:
267
        logger.info("Question not found, creating...")
227 268
        q = Question()
228 269

  
229 270
    q.author = author
......
248 289
    return q
249 290

  
250 291
def add_or_update_guide_entry(author, service, slug, title, html_content):
292
    logger.info("Create or update user guide entry, %s, %s, %s", service,
293
            slug, title)
251 294
    try:
295
        logger.info("Guide entry found, updating...")
252 296
        guide = UserGuideEntry.objects.get(slug=slug)
253 297
    except:
298
        logger.info("Guide entry not found, creating...")
254 299
        guide = UserGuideEntry()
255 300

  
256 301
    guide.author = author
......
271 316

  
272 317
    return guide
273 318

  
319

  

Also available in: Unified diff