web/ldt/ldt_utils/views.py
changeset 1 eb9188f2ee4f
child 5 5044dbe8745f
equal deleted inserted replaced
0:85b071fb75b2 1:eb9188f2ee4f
       
     1 from contentindexer import *
       
     2 from django.conf import settings
       
     3 from django.contrib.auth.decorators import login_required
       
     4 from django.core import serializers
       
     5 from django.core.urlresolvers import reverse
       
     6 from django.db.models import Q
       
     7 from django.forms.forms import get_declared_fields
       
     8 from django.forms.models import model_to_dict
       
     9 from django.forms.util import ErrorList
       
    10 from django.http import HttpResponse, HttpResponseRedirect, \
       
    11     HttpResponseForbidden, HttpResponseServerError
       
    12 from django.shortcuts import render_to_response, get_object_or_404, \
       
    13     get_list_or_404
       
    14 from django.template import RequestContext
       
    15 from django.template.loader import render_to_string
       
    16 from django.utils import simplejson
       
    17 from django.utils.html import escape
       
    18 from django.utils.translation import ugettext as _, ungettext
       
    19 from fileimport import *
       
    20 from forms import LdtImportForm, LdtAddForm, SearchForm, AddProjectForm, \
       
    21     CopyProjectForm, ContentForm, MediaForm
       
    22 from ldt.core.models import Owner
       
    23 from ldt.ldt_utils.models import Content, Project, Owner
       
    24 from ldt.ldt_utils.projectserializer import ProjectSerializer
       
    25 from ldt.ldt_utils.utils import boolean_convert
       
    26 from lxml import etree
       
    27 from lxml.html import fromstring, fragment_fromstring
       
    28 from models import *
       
    29 from projectserializer import *
       
    30 from string import Template
       
    31 from urllib2 import urlparse
       
    32 from utils import *
       
    33 import StringIO
       
    34 import base64
       
    35 import cgi
       
    36 import django.core.urlresolvers
       
    37 import ldt.auth as ldt_auth
       
    38 import ldt.utils.path as ldt_utils_path
       
    39 import logging
       
    40 import lucene
       
    41 import lxml.etree
       
    42 import tempfile
       
    43 import urllib2
       
    44 import uuid
       
    45 
       
    46 
       
    47 @login_required
       
    48 def workspace(request):
       
    49 
       
    50     # list of contents
       
    51     content_list = Content.objects.all()
       
    52 
       
    53     # get list of projects
       
    54     project_list = Project.objects.all()
       
    55 
       
    56     # render list
       
    57     return render_to_response("ldt/ldt_utils/workspace.html",
       
    58                               {'contents': content_list, 'projects': project_list},
       
    59                               context_instance=RequestContext(request))
       
    60 
       
    61 
       
    62 def popup_embed(request):
       
    63 
       
    64     json_url = request.GET.get("json_url")
       
    65     player_id = request.GET.get("player_id")
       
    66     ldt_id = request.GET.get("ldt_id")
       
    67 
       
    68 
       
    69     project = Project.objects.get(ldt_id=ldt_id);
       
    70 
       
    71     if not ldt_auth.checkAccess(request.user, project):
       
    72         return HttpResponseForbidden(_("You can not access this project"))
       
    73 
       
    74     ps = ProjectSerializer(project, from_contents=False, from_display=True)
       
    75     annotations = ps.getAnnotations(first_cutting=True)
       
    76 
       
    77     embed_rendered = dict((typestr,
       
    78                            (lambda s:escape(lxml.etree.tostring(fragment_fromstring(render_to_string("ldt/ldt_utils/partial/embed_%s.html"%(s), {'json_url':json_url,'player_id':player_id, 'annotations':annotations, 'ldt_id': ldt_id}, context_instance=RequestContext(request))),pretty_print=True)))(typestr))
       
    79                            for typestr in ('player','seo_body', 'seo_meta', 'links')  )
       
    80 
       
    81     return render_to_response("ldt/ldt_utils/embed_popup.html",
       
    82                               {'json_url':json_url,'player_id':player_id, 'embed_rendered':embed_rendered, 'annotations':annotations},
       
    83                               context_instance=RequestContext(request))
       
    84 
       
    85 
       
    86 
       
    87 @login_required
       
    88 def projectsfilter(request, filter, is_owner=False, status=0):
       
    89 
       
    90     project_list = None
       
    91     is_owner = boolean_convert(is_owner)
       
    92     status = int(status)
       
    93     query = Q()
       
    94 
       
    95     if is_owner:
       
    96         owner = None
       
    97         try:
       
    98             owner = Owner.objects.get(user=request.user)
       
    99         except:
       
   100             return HttpResponseServerError("<h1>User not found</h1>")
       
   101         query &= Q(owner=owner)
       
   102 
       
   103     if status > 0:
       
   104         query &= Q(state=status)
       
   105 
       
   106     if filter:
       
   107         if len(filter) > 0 and filter[0] == '_':
       
   108             filter = filter[1:]
       
   109         query &= Q(title__icontains=filter)
       
   110 
       
   111     project_list =  Project.objects.filter(query)
       
   112 
       
   113     return render_to_response("ldt/ldt_utils/partial/projectslist.html",
       
   114                               {'projects': project_list},
       
   115                               context_instance=RequestContext(request))
       
   116 
       
   117 
       
   118 
       
   119 
       
   120 
       
   121 @login_required
       
   122 def contentsfilter(request, filter):
       
   123     if filter and len(filter) > 0 and filter[0] == '_':
       
   124         filter = filter[1:]
       
   125 
       
   126     if filter:
       
   127         content_list = Content.objects.filter(title__icontains=filter)
       
   128     else:
       
   129         content_list = Content.objects.all()
       
   130 
       
   131     return render_to_response("ldt/ldt_utils/partial/contentslist.html",
       
   132                               {'contents': content_list},
       
   133                               context_instance=RequestContext(request))
       
   134 
       
   135 
       
   136 def searchForm(request):
       
   137     form = SearchForm()
       
   138     return render_to_response('ldt/ldt_utils/search_form.html',{'form': form} , context_instance=RequestContext(request))    
       
   139 
       
   140 def searchIndex(request):
       
   141     
       
   142     sform = SearchForm(request.POST)
       
   143     if sform.is_valid():
       
   144         search = sform.cleaned_data["search"]
       
   145     
       
   146     
       
   147         queryStr = base64.urlsafe_b64encode(search.encode('utf8'))
       
   148         field = request.POST["field"]
       
   149         language_code = request.LANGUAGE_CODE[:2]
       
   150     
       
   151         url = settings.WEB_URL + django.core.urlresolvers.reverse("ldt.ldt_utils.views.searchInit", args=[field, queryStr])
       
   152         return render_to_response('ldt/ldt_utils/init_ldt.html', {'LDT_MEDIA_PREFIX': settings.LDT_MEDIA_PREFIX, 'colorurl': settings.LDT_MEDIA_PREFIX+'swf/ldt/pkg/color.xml', 'i18nurl': settings.LDT_MEDIA_PREFIX+'swf/ldt/pkg/i18n', 'language': language_code, 'baseurl': settings.LDT_MEDIA_PREFIX+'swf/ldt/', 'url': url}, context_instance=RequestContext(request))
       
   153     else:
       
   154         resp = HttpResponse()
       
   155         resp.write("<html><head></head><body>Error : No result</body></html>");
       
   156 
       
   157 def searchIndexGet(request, field, query):
       
   158 
       
   159     language_code = request.LANGUAGE_CODE[:2]
       
   160     url = settings.WEB_URL + django.core.urlresolvers.reverse("ldt.ldt_utils.views.searchInit", args=[field, query])
       
   161     return render_to_response('ldt/ldt_utils/init_ldt.html', {'LDT_MEDIA_PREFIX': settings.LDT_MEDIA_PREFIX, 'colorurl': settings.LDT_MEDIA_PREFIX+'swf/ldt/pkg/color.xml', 'i18nurl': settings.LDT_MEDIA_PREFIX+'swf/ldt/pkg/i18n', 'language': language_code, 'baseurl': settings.LDT_MEDIA_PREFIX+'swf/ldt/', 'url': url}, context_instance=RequestContext(request))
       
   162 
       
   163 def searchInit(request, field, query):
       
   164     
       
   165     ldtgen = LdtUtils()
       
   166     
       
   167     doc = ldtgen.generateInit([field,query], 'ldt.ldt_utils.views.searchLdt', 'ldt.ldt_utils.views.searchSegments')
       
   168     
       
   169     resp = HttpResponse(mimetype="text/xml;charset=utf-8")
       
   170     doc.write(resp, pretty_print=True)
       
   171     return resp
       
   172 
       
   173 def searchLdt(request, field, query, edition=None):
       
   174     
       
   175     contentList = []
       
   176     resp = HttpResponse(mimetype="text/xml")
       
   177     queryStr = ""
       
   178 
       
   179     if query and len(query)>0:        
       
   180         queryStr = base64.urlsafe_b64decode(query.encode("ascii")).decode("utf8")
       
   181         searcher = LdtSearch()
       
   182         ids = {}
       
   183         
       
   184         for result in searcher.query(field, queryStr):
       
   185             ids[result["iri_id"]] = ""            
       
   186 
       
   187         id_list = ids.keys()
       
   188         
       
   189         if edition is not None:
       
   190             ids_editions = map(lambda t:t[0], filter(lambda id: id[0] is not None, Speak.objects.filter(session__day__edition=edition).order_by("session__start_ts", "order").values_list("content__iri_id")))            
       
   191             id_list = filter(lambda id: id in id_list, ids_editions)
       
   192             
       
   193         contentList = Content.objects.filter(iri_id__in=id_list)        
       
   194 
       
   195             
       
   196     ldtgen = LdtUtils()
       
   197     ldtgen.generateLdt(contentList, file=resp, title = u"Recherche : " + queryStr)
       
   198     
       
   199     return resp
       
   200 
       
   201 
       
   202 def searchSegments(request, field, query, edition=None):
       
   203     
       
   204     if query and len(query)>0:
       
   205         searcher = LdtSearch()
       
   206         
       
   207         queryStr = base64.urlsafe_b64decode(query.encode("ascii")).decode("utf8")
       
   208         res = searcher.query(field, queryStr)
       
   209     else:
       
   210         res = []
       
   211         
       
   212     iri_ids = None
       
   213     
       
   214     if edition is not None:
       
   215         iri_ids = map(lambda t:t[0], filter(lambda id: id[0] is not None, Speak.objects.filter(session__day__edition=edition).order_by("session__start_ts", "order").values_list("content__iri_id")))
       
   216 
       
   217     iri = lxml.etree.Element('iri')
       
   218     doc = lxml.etree.ElementTree(iri)	
       
   219 
       
   220     for resultMap in res:
       
   221         if iri_ids is None or resultMap['iri_id'] in iri_ids:
       
   222 	    seg = etree.SubElement(iri, 'seg')
       
   223 	    seg.set('idctt', resultMap['iri_id'])
       
   224             seg.set('idens', resultMap['ensemble_id'])
       
   225             seg.set('iddec', resultMap['decoupage_id'])
       
   226             seg.set('idseg', resultMap['element_id'])
       
   227             seg.set('idvue', "")
       
   228 	    seg.set('crit', "")
       
   229 
       
   230     return doc  
       
   231   
       
   232     return HttpResponse(lxml.etree.tostring(doc, pretty_print=True), mimetype="text/xml;charset=utf-8") 
       
   233 
       
   234 
       
   235 
       
   236 @login_required         
       
   237 def list_ldt(request):
       
   238     contents = Content.objects.all()
       
   239     try:
       
   240         owner = Owner.objects.get(user=request.user)
       
   241     except:
       
   242         return HttpResponseRedirect(settings.LOGIN_URL)
       
   243     ldtProjects = Project.objects.filter(owner=owner)
       
   244     context={
       
   245     'contents': contents,
       
   246     'projects': ldtProjects.reverse(),
       
   247     }
       
   248     return render_to_response('ldt/ldt_utils/ldt_list.html', context, context_instance=RequestContext(request))
       
   249 
       
   250 @login_required         
       
   251 def list_content(request):
       
   252     contents = Content.objects.all()
       
   253     context={
       
   254         'contents': contents,
       
   255     }
       
   256     return render_to_response('ldt/ldt_utils/content_list.html', context, context_instance=RequestContext(request))
       
   257 
       
   258 @login_required
       
   259 def create_ldt_view(request):
       
   260     if request.method == "POST" :
       
   261         form = LdtAddForm(request.POST)
       
   262         if form.is_valid():
       
   263             user = request.user
       
   264             Project.create_project(title=form.cleaned_data['title'], user=user, contents=form.cleaned_data['contents'])
       
   265             form_status = "saved"
       
   266             contents=[]
       
   267             #return HttpResponseRedirect(reverse("ldt.ldt_utils.views.list_ldt"))
       
   268     else:
       
   269         form = LdtAddForm()
       
   270         contents = Content.objects.all()
       
   271         form_status = "none"
       
   272             
       
   273     return render_to_response('ldt/ldt_utils/create_ldt.html', {'contents': contents, 'form': form, 'form_status':form_status,'create_project_action':reverse(create_ldt_view)}, context_instance=RequestContext(request))
       
   274      
       
   275 def created_ldt(request):
       
   276     return render_to_response('ldt/ldt_utils/save_done.html', context_instance=RequestContext(request))
       
   277     
       
   278 def indexProject(request, id):
       
   279 
       
   280     urlStr = settings.WEB_URL + reverse("space_ldt_init", args=['ldtProject', id])
       
   281     posturl= settings.WEB_URL + reverse("ldt.ldt_utils.views.save_ldtProject")
       
   282     language_code = request.LANGUAGE_CODE[:2]
       
   283     
       
   284     ldt = get_object_or_404(Project, ldt_id=id)
       
   285     if ldt.state ==2: #published
       
   286         readonly = 'true'
       
   287     else:
       
   288         readonly = 'false'
       
   289     
       
   290     return render_to_response('ldt/ldt_utils/init_ldt.html', {'LDT_MEDIA_PREFIX': settings.LDT_MEDIA_PREFIX, 'colorurl': settings.LDT_MEDIA_PREFIX+'swf/ldt/pkg/color.xml', 'i18nurl': settings.LDT_MEDIA_PREFIX+'swf/ldt/pkg/i18n', 'language': language_code, 'baseurl': settings.LDT_MEDIA_PREFIX+'swf/ldt/', 'url': urlStr, 'posturl': posturl, 'id': id, 'readonly': readonly}, context_instance=RequestContext(request))
       
   291     
       
   292 def init(request, method, url):
       
   293     ldtgen = LdtUtils()
       
   294 
       
   295     doc = ldtgen.generateInit([url], 'ldt.ldt_utils.views.'+method, None)
       
   296 
       
   297     resp = HttpResponse(mimetype="text/xml")
       
   298     resp['Cache-Control']='no-cache, must-revalidate'
       
   299     resp['Pragma']='no-cache'
       
   300 
       
   301     resp.write( etree.tostring(doc, pretty_print=True, xml_declaration=True, encoding="utf-8")) 
       
   302     return resp
       
   303        
       
   304 def ldtProject(request, id):
       
   305     resp = HttpResponse(mimetype="text/xml")
       
   306     resp['Cache-Control']='no-cache, must-revalidate'
       
   307     resp['Pragma']='no-cache'
       
   308     
       
   309     project = Project.objects.get(ldt_id=id)
       
   310     resp.write(project.ldt)
       
   311     return resp
       
   312 
       
   313 
       
   314 def project_json_id(request, id):
       
   315     
       
   316     project = get_object_or_404(Project,ldt_id=id)
       
   317 
       
   318     return project_json(request, project, False)
       
   319 
       
   320 
       
   321 def project_json_externalid(request, id):
       
   322         
       
   323     res_proj = get_list_or_404(Project.objects.order_by('-modification_date'),contents__external_id = id)
       
   324     
       
   325     return project_json(request, res_proj[0], False)
       
   326 
       
   327 
       
   328 
       
   329 def project_json(request, project, serialize_contents = True):
       
   330     
       
   331     if not ldt_auth.checkAccess(request.user, project):
       
   332         return HttpResponseForbidden(_("You can not access this project"))
       
   333         
       
   334     mimetype = request.REQUEST.get("mimetype")
       
   335     if mimetype is None:
       
   336         mimetype = "application/json; charset=utf-8"
       
   337     else:
       
   338         mimetype = mimetype.encode("utf-8")
       
   339     if "charset" not in mimetype:
       
   340         mimetype += "; charset=utf-8" 
       
   341     resp = HttpResponse(mimetype=mimetype)
       
   342     resp['Cache-Control']='no-cache, must-revalidate'
       
   343     resp['Pragma']='no-cache'
       
   344     
       
   345     indent = request.REQUEST.get("indent")
       
   346     if indent is None:
       
   347         indent = settings.LDT_JSON_DEFAULT_INDENT
       
   348     else:
       
   349         indent = int(indent)
       
   350     
       
   351     callback = request.REQUEST.get("callback")
       
   352     escape_str = request.REQUEST.get("escape")
       
   353     escape_bool = False
       
   354     if escape_str:
       
   355         escape_bool = {'true': True, 'false': False, "0": False, "1": True}.get(escape_str.lower())
       
   356         
       
   357         
       
   358     ps = ProjectSerializer(project, serialize_contents)
       
   359     project_dict = ps.serialize_to_cinelab()
       
   360     
       
   361     json_str = simplejson.dumps(project_dict, ensure_ascii=False, indent=indent)
       
   362     
       
   363     if callback is not None:
       
   364         json_str = "%s(%s)" % (callback,json_str)
       
   365     
       
   366     if escape_bool:
       
   367         json_str = escape(json_str)
       
   368     
       
   369     resp.write(json_str)
       
   370 
       
   371     return resp
       
   372 
       
   373 def project_annotations_rdf(request, ldt_id):
       
   374 
       
   375     project = Project.objects.get(ldt_id=ldt_id);
       
   376     
       
   377     if not ldt_auth.checkAccess(request.user, project):
       
   378         return HttpResponseForbidden(_("You can not access this project"))
       
   379 
       
   380     mimetype = request.REQUEST.get("mimetype")
       
   381     if mimetype is None:
       
   382         mimetype = "application/rdf+xml; charset=utf-8"
       
   383     else:
       
   384         mimetype = mimetype.encode("utf-8")
       
   385     if "charset" not in mimetype:
       
   386         mimetype += "; charset=utf-8" 
       
   387     resp = HttpResponse(mimetype=mimetype)
       
   388     resp['Cache-Control']='no-cache, must-revalidate'
       
   389     resp['Pragma']='no-cache'
       
   390 
       
   391     ps = ProjectSerializer(project, from_contents=False, from_display=True) 
       
   392     annotations = ps.getAnnotations(first_cutting=True)
       
   393     
       
   394     rdf_ns = u"http://www.w3.org/1999/02/22-rdf-syntax-ns#"
       
   395     dc_ns = u"http://purl.org/dc/elements/1.1/"
       
   396     rdf = u"{%s}" % rdf_ns
       
   397     dc = u"{%s}" % dc_ns
       
   398     nsmap = {u'rdf' : rdf_ns, u'dc':dc_ns}
       
   399     
       
   400     rdf_root = etree.Element(rdf+u"RDF", nsmap=nsmap)
       
   401     
       
   402     logging.debug("RDF annotations : " + repr(annotations))
       
   403     
       
   404     for annotation in annotations:
       
   405         uri = u""
       
   406         if 'uri' in annotation and annotation['uri']:
       
   407             uri = unicode(annotation['uri'])
       
   408         annot_desc = etree.SubElement(rdf_root, rdf+u"Description")
       
   409         annot_desc.set(rdf+u'about',uri)
       
   410         if annotation['title']:
       
   411             etree.SubElement(annot_desc, dc+'title').text = etree.CDATA(unicode(annotation['title']))
       
   412         if annotation['desc']:
       
   413             etree.SubElement(annot_desc, dc+'description').text = etree.CDATA(unicode(annotation['desc']))
       
   414         if annotation['tags']:
       
   415             for tag in annotation['tags']:
       
   416                 etree.SubElement(annot_desc, dc+'subject').text = etree.CDATA(unicode(tag))
       
   417         etree.SubElement(annot_desc,dc+'coverage').text = u"start=%s, duration=%s" % (annotation['begin'], annotation['duration'])
       
   418         
       
   419     resp.write(u"<?xml version=\"1.0\" encoding=\"utf-8\"?>\n")
       
   420     resp.write(u"<!DOCTYPE rdf:RDF PUBLIC \"-//DUBLIN CORE//DCMES DTD 2002/07/31//EN\" \"http://dublincore.org/documents/2002/07/31/dcmes-xml/dcmes-xml-dtd.dtd\">\n")
       
   421     
       
   422     resp.write(etree.tostring(rdf_root, xml_declaration=False, encoding="utf-8", pretty_print=True))
       
   423 
       
   424     return resp
       
   425 
       
   426 def save_ldtProject(request):
       
   427     if request.method=="POST":
       
   428         ldt = request.POST['ldt']
       
   429         id = request.POST['id']
       
   430         ldtproject=Project.objects.get(ldt_id=id)
       
   431 
       
   432 	    #save xml ldt
       
   433         ldtproject.ldt=ldt
       
   434 
       
   435 
       
   436         doc = lxml.etree.fromstring(ldtproject.ldt.encode( "utf-8" ))
       
   437         result = doc.xpath("/iri/project")
       
   438         
       
   439         #set new title
       
   440         ldtproject.title = result[0].get("title")
       
   441         
       
   442         #get new content list
       
   443         new_contents=[]
       
   444         result = doc.xpath("/iri/medias/media")
       
   445         for medianode in result:
       
   446             id = medianode.get("id")
       
   447             new_contents.append(id)
       
   448     
       
   449         #set new content list
       
   450         for c in ldtproject.contents.all():
       
   451             if not c.iri_id in new_contents:
       
   452                 ldtproject.contents.remove(c)
       
   453     
       
   454         ldtproject.save()
       
   455     else:
       
   456         ldt = ''
       
   457         new_contents=[]
       
   458     
       
   459     return render_to_response('ldt/ldt_utils/save_done.html', {'ldt': ldt, 'id':id, 'title':ldtproject.title, 'contents': new_contents}, context_instance=RequestContext(request))
       
   460 
       
   461 
       
   462 
       
   463 @login_required    
       
   464 def publish(request, id, redirect=True):
       
   465     ldt = get_object_or_404(Project, ldt_id=id)
       
   466     ldt.state = 2 #published
       
   467     ldt.save()
       
   468     redirect = boolean_convert(redirect)
       
   469     if redirect:
       
   470         return HttpResponseRedirect(reverse("ldt.ldt_utils.views.list_ldt"))
       
   471     else:
       
   472         return HttpResponse(simplejson.dumps({'res':True, 'ldt': {'id': ldt.id, 'state':ldt.state,'ldt_id': ldt.ldt_id}}, ensure_ascii=False),mimetype='application/json')
       
   473     
       
   474 @login_required    
       
   475 def unpublish(request, id, redirect=True):
       
   476     ldt = get_object_or_404(Project, ldt_id=id)
       
   477     ldt.state = 1 #edition
       
   478     ldt.save()
       
   479     redirect = boolean_convert(redirect)
       
   480     if redirect:
       
   481         return HttpResponseRedirect(reverse("ldt.ldt_utils.views.list_ldt"))
       
   482     else:
       
   483         return HttpResponse(simplejson.dumps({'res':True, 'ldt': {'id': ldt.id, 'state':ldt.state,'ldt_id': ldt.ldt_id}}, ensure_ascii=False),mimetype='application/json')
       
   484     
       
   485 
       
   486 def index(request, url):
       
   487     
       
   488     urlStr = settings.WEB_URL + reverse("ldt_init", args=['ldt',url])
       
   489     language_code = request.LANGUAGE_CODE[:2]
       
   490     
       
   491     return render_to_response('ldt/ldt_utils/init_ldt.html', {'LDT_MEDIA_PREFIX': settings.LDT_MEDIA_PREFIX, 'colorurl': settings.LDT_MEDIA_PREFIX+'swf/ldt/pkg/color.xml', 'i18nurl': settings.LDT_MEDIA_PREFIX+'swf/ldt/pkg/i18n', 'language': language_code, 'baseurl': settings.LDT_MEDIA_PREFIX+'swf/ldt/', 'url': urlStr, 'weburl':settings.WEB_URL+settings.BASE_URL}, context_instance=RequestContext(request))
       
   492 
       
   493 
       
   494 def ldt(request, url, startSegment = None):
       
   495     
       
   496     resp = HttpResponse(mimetype="text/xml; charset=utf-8")
       
   497     resp['Cache-Control'] = 'no-cache'
       
   498 
       
   499     contentList = Content.objects.filter(iri_id=url)
       
   500 
       
   501     ldtgen = LdtUtils()
       
   502     ldtgen.generateLdt(contentList, file=resp, title = contentList[0].title, startSegment=startSegment)
       
   503 
       
   504     return resp
       
   505 
       
   506 
       
   507 def loading(request):
       
   508      return render_to_response('ldt/ldt_utils/loading.html', context_instance=RequestContext(request))
       
   509 
       
   510 
       
   511 @login_required
       
   512 def create_project(request, iri_id):
       
   513 
       
   514     content = get_object_or_404(Content, iri_id=iri_id)
       
   515     contents = [ content, ]
       
   516     if request.method == "POST" :
       
   517         form = AddProjectForm(request.POST)
       
   518         if form.is_valid():
       
   519             user=request.user
       
   520             project = Project.create_project(title=form.cleaned_data['title'], user=user, contents=contents)
       
   521             return HttpResponseRedirect(reverse('ldt.ldt_utils.views.indexProject', args=[project.ldt_id]))
       
   522     else:
       
   523         form = AddProjectForm()
       
   524     return render_to_response('ldt/ldt_utils/create_ldt.html', {'form':form, 'contents':contents, 'create_project_action':reverse("ldt.ldt_utils.views.create_project",args=[iri_id])}, context_instance=RequestContext(request))
       
   525 
       
   526 @login_required
       
   527 def update_project(request, ldt_id):
       
   528 
       
   529     project = get_object_or_404(Project, ldt_id=ldt_id)
       
   530     contents = project.contents.all()
       
   531     if request.method == "POST" :
       
   532         submit_action = request.REQUEST.get("submit_button",False)
       
   533         if submit_action == "prepare_delete":
       
   534             errors = []
       
   535             if project.state == 2:
       
   536                 errors.append(_("the project %(title)s is published. please unpublish before deleting.")%{'title':project.title})
       
   537                 message = _("can not delete the project. Please correct the following error")
       
   538                 title =  _('title error deleting project')
       
   539             else:
       
   540                 message = _("please confirm deleting project %(title)s")%{'title':project.title}
       
   541                 title = _("confirm deletion")
       
   542             return render_to_response('ldt/ldt_utils/error_confirm.html', {'errors':errors, 'message':message, 'title': title}, context_instance=RequestContext(request))
       
   543         elif submit_action == "delete":
       
   544             if project.state != 2:
       
   545                 project.delete()
       
   546             form_status= 'deleted'
       
   547             form = AddProjectForm()
       
   548         else:
       
   549             form_status= 'saved'
       
   550             form = AddProjectForm(request.POST)
       
   551             if form.is_valid():
       
   552                 if project.title != form.cleaned_data['title']:
       
   553                     project.title=form.cleaned_data['title']
       
   554                     ldt = lxml.etree.fromstring(project.ldt.encode("utf-8"))
       
   555                     res = ldt.xpath("/iri/project")
       
   556                     res[0].set("title",project.title)
       
   557                     project.ldt = lxml.etree.tostring(ldt,pretty_print=True)
       
   558                     project.save()
       
   559     else:
       
   560         form = AddProjectForm({'title':unicode(project.title)})
       
   561         form_status= 'none'
       
   562         
       
   563     return render_to_response('ldt/ldt_utils/create_ldt.html', {'form':form, 'form_status':form_status, 'ldt_id': ldt_id, 'contents':contents, 'create_project_action':reverse("ldt.ldt_utils.views.update_project",args=[ldt_id])}, context_instance=RequestContext(request))
       
   564 
       
   565 
       
   566 @login_required
       
   567 def copy_project(request, ldt_id):
       
   568 
       
   569     project = get_object_or_404(Project, ldt_id=ldt_id)
       
   570     if request.method == "POST" :
       
   571         form = CopyProjectForm(request.POST)
       
   572         if form.is_valid():
       
   573             user=request.user
       
   574             project = project.copy_project(title=request.POST['title'], user=user)
       
   575             return HttpResponseRedirect(reverse('ldt.ldt_utils.views.indexProject', args=[project.ldt_id]))
       
   576     else:
       
   577         form = CopyProjectForm
       
   578     return render_to_response('ldt/ldt_utils/copy_ldt.html', {'form':form, 'project':project}, context_instance=RequestContext(request))
       
   579 
       
   580 
       
   581 def write_content_base(request, iri_id=None):
       
   582 
       
   583     if iri_id:        
       
   584         instance_content = Content.objects.get(iri_id=iri_id)
       
   585         instance_media = instance_content.media_obj
       
   586         logging.debug("write_content_base : valid form: for instance : media -> " + repr(instance_media) + " content : for instance : " + repr(instance_content) ) 
       
   587     else:
       
   588         logging.debug("No iri_id")
       
   589         instance_content = None
       
   590         instance_media = None
       
   591     
       
   592     form_status= 'none'        
       
   593     if request.method =="POST":
       
   594         
       
   595         content_instance_val = model_to_dict(instance_content,exclude=ContentForm.Meta.exclude)
       
   596         media_instance_val = model_to_dict(instance_media, exclude=MediaForm.Meta.exclude)
       
   597         #add prefix
       
   598         
       
   599         def add_prefix(dict, prefix):
       
   600             for key,value in dict.items():
       
   601                 dict['%s-%s' % (prefix, key)] = value
       
   602                 del(dict[key])
       
   603         
       
   604         add_prefix(content_instance_val, "content")
       
   605         add_prefix(media_instance_val, "media")        
       
   606         
       
   607         for k in request.POST.keys():
       
   608             value = request.POST.get(k)
       
   609             content_instance_val[k] = value
       
   610             media_instance_val[k] = value
       
   611         
       
   612         content_form = ContentForm(content_instance_val, prefix="content", instance=instance_content)
       
   613         media_form = MediaForm(media_instance_val, request.FILES, prefix="media", instance=instance_media)
       
   614         
       
   615         media_valid = media_form.is_valid()
       
   616         content_valid = content_form.is_valid()
       
   617         
       
   618         logging.debug("write_content_base : valid form: for instance : " + repr(instance_media) + " -> media " + str(media_valid) +" content : for instance : " + repr(instance_content) + " : " + str(content_valid) )
       
   619         
       
   620         if media_valid and content_valid :
       
   621             
       
   622             # see if media must be created
       
   623             cleaned_data = {}
       
   624             cleaned_data.update(media_form.cleaned_data)
       
   625 
       
   626             media_input_type = content_form.cleaned_data["media_input_type"]
       
   627             
       
   628             if media_input_type == "none":
       
   629                 media = None
       
   630             elif media_input_type == "link":
       
   631                 media = content_form.cleaned_data["media_obj"]
       
   632                 created = False
       
   633             elif media_input_type == "create":
       
   634                 del cleaned_data["media_file"]
       
   635                 if not cleaned_data['videopath']:
       
   636                     cleaned_data['videopath'] = settings.STREAM_URL
       
   637                 media, created = Media.objects.get_or_create(src=cleaned_data['src'], defaults=cleaned_data)
       
   638             elif media_input_type == "url" or  media_input_type == "upload" :                
       
   639                 # copy file
       
   640                 #complet src
       
   641                 destination_file = None
       
   642                 source_file = None
       
   643                 destination_file_path = None
       
   644                 try:
       
   645                     if media_input_type == "url":
       
   646                         url = cleaned_data["external_src_url"]
       
   647                         source_file = urllib2.urlopen(url)
       
   648                         source_filename = source_file.info().get('Content-Disposition', None)
       
   649                         if not source_filename:
       
   650                             source_filename = urlparse.urlparse(url).path.rstrip("/").split('/')[-1]
       
   651                     elif media_input_type == "upload":
       
   652                         source_file = request.FILES['media-media_file']
       
   653                         source_filename = source_file.name
       
   654                     
       
   655                     source_filename = ldt_utils_path.sanitize_filename(source_filename)
       
   656                     destination_filepath = os.path.join(settings.STREAM_PATH, source_filename)
       
   657                     base_source_filename = source_filename
       
   658                     extension = base_source_filename.split(".")[-1]
       
   659                     if extension == base_source_filename:
       
   660                         extension = ""
       
   661                         base_basename_filename = base_source_filename
       
   662                     else:
       
   663                         base_basename_filename  =  base_source_filename[:-1 *(len(extension)+1)]
       
   664                     i = 0
       
   665                     while os.path.exists(destination_filepath):
       
   666                         base_source_filename = "%s.%d.%s" % (base_basename_filename,i,extension)
       
   667                         destination_filepath = os.path.join(settings.STREAM_PATH, base_source_filename)
       
   668                         i += 1
       
   669                         
       
   670                     destination_file = open(destination_filepath, "w")
       
   671                     src_prefix = settings.STREAM_SRC_PREFIX.rstrip("/")
       
   672                     if len(src_prefix) > 0:
       
   673                         cleaned_data["src"] = src_prefix + "/" + base_source_filename
       
   674                     else:
       
   675                         cleaned_data["src"] =  base_source_filename
       
   676                     
       
   677                     chunck = source_file.read(2048)
       
   678                     while chunck:
       
   679                         destination_file.write(chunck)
       
   680                         chunck = source_file.read(2048)
       
   681         
       
   682                 except Exception as inst:
       
   683                     logging.debug("write_content_base : POST error when processing file:" + str(inst))
       
   684                     form_status = "error"
       
   685                     #set error for form
       
   686                     if media_input_type == "url":
       
   687                         errors = media_form._errors.setdefault("external_src_url", ErrorList())
       
   688                         errors.append(_("Problem when downloading file from url : ")+str(inst))
       
   689                     elif media_input_type == "upload":
       
   690                         errors = media_form._errors.setdefault("media_file", ErrorList())
       
   691                         errors.append(_("Problem when uploading file : ") + str(inst))
       
   692                 finally:
       
   693                     if destination_file:
       
   694                         destination_file.close()
       
   695                     if source_file:
       
   696                         source_file.close()
       
   697                         
       
   698                 if form_status != "error":
       
   699                     #try:
       
   700                     del cleaned_data["media_file"]
       
   701                     if not cleaned_data['videopath']:
       
   702                         cleaned_data['videopath'] = settings.STREAM_URL
       
   703                     media, created = Media.objects.get_or_create(src=cleaned_data['src'], defaults=cleaned_data)
       
   704                 else:
       
   705                     media = None
       
   706 
       
   707             if media and not created:                        
       
   708                 for attribute in ('external_id', 'external_permalink', 'external_publication_url', 'external_src_url', 'media_creation_date', 'videopath', 'duration', 'description', 'title'):
       
   709                     setattr(media, attribute, cleaned_data.get(attribute))
       
   710                 media.save()
       
   711                     #except Exception as inst:
       
   712 #                        logging.debug("write_content_base : POST error when saving media:" + str(inst))
       
   713  #                       form_status = "error"
       
   714                         #TODO: set error message
       
   715                         #media_form.errors = _("Error when saving the media : " + e.message)
       
   716 
       
   717             #if needed preparetemp file and copy temp file to destination
       
   718             
       
   719             
       
   720             if form_status != "error":
       
   721                 #try:
       
   722                 content_defaults = {}
       
   723                 content_defaults.update(content_form.cleaned_data)
       
   724                 content_defaults['media_obj'] = media
       
   725                 del content_defaults["media_input_type"]
       
   726                 content, created = Content.objects.get_or_create(iri_id = content_form.cleaned_data['iri_id'], defaults = content_defaults)
       
   727                 if not created:
       
   728                     
       
   729                     for attribute in ('iriurl', 'title', 'description', 'duration', 'content_creation_date', 'tags', 'media_obj'):
       
   730                         setattr(content, attribute, content_defaults[attribute])
       
   731                 content.save()
       
   732                 form_status = 'saved'
       
   733                 media_form = MediaForm(instance=media, prefix="media")
       
   734                 content_form = ContentForm(instance=content, prefix="content")
       
   735                 #except:
       
   736                     #logging.debug("write_content_base : POST error when saving content:" + str(inst))
       
   737                     #form_status = "error"
       
   738                     #TODO : set error on content form
       
   739         else:
       
   740             form_status = 'error'
       
   741     else:
       
   742         form_status = 'empty'
       
   743         initial = { 'media_input_type':"link"}
       
   744         
       
   745         content_form = ContentForm(prefix="content", instance=instance_content, initial = initial )
       
   746         media_form = MediaForm(prefix="media", instance=instance_media)
       
   747         
       
   748         if instance_content is not None:
       
   749             content_form.media_input_type = "link"
       
   750     
       
   751     return content_form, media_form, form_status
       
   752 
       
   753 @login_required
       
   754 def write_content(request, iri_id=None):
       
   755     
       
   756     submit_action = request.REQUEST.get("submit_button",False) 
       
   757 
       
   758     if submit_action == "prepare_delete": 
       
   759         errors, titles = prepare_delete_content(request, iri_id)
       
   760         if errors and len(errors) > 0:
       
   761             message = ungettext("There is %(count)d error when deleting content", "There are %(count)d errors when deleting content", len(errors)) % { 'count': len(errors)}
       
   762             title_msg = _('title error deleting content')
       
   763         else:
       
   764             message = _("Confirm delete content %(titles)s") % { 'titles' : ",".join(titles) }
       
   765             title_msg = _("confirm delete content")
       
   766         return render_to_response('ldt/ldt_utils/error_confirm.html', {'errors':errors, 'message':message, 'title': title_msg}, context_instance=RequestContext(request))  
       
   767     elif submit_action == "delete":
       
   768         delete_content(request, iri_id)
       
   769         form_status = "deleted"
       
   770         content_form = ContentForm()
       
   771         media_form = MediaForm()
       
   772     else:
       
   773         content_form, media_form, form_status = write_content_base(request, iri_id)
       
   774 
       
   775     if iri_id:
       
   776         create_content_action =  reverse('ldt.ldt_utils.views.write_content', kwargs={'iri_id':iri_id})
       
   777     else:
       
   778         create_content_action =  reverse('ldt.ldt_utils.views.write_content')
       
   779     
       
   780     return render_to_response('ldt/ldt_utils/create_content.html', {'content_form': content_form, 'media_form': media_form,'form_status': form_status,'create_content_action': create_content_action, 'iri_id': iri_id}, context_instance=RequestContext(request))
       
   781 
       
   782 @login_required
       
   783 def prepare_delete_content(request, iri_id=None):
       
   784     errors = []
       
   785     titles = []
       
   786     if not iri_id:
       
   787         iri_id = request.REQUEST.get("iri_id", None)
       
   788         
       
   789     if iri_id:
       
   790         for content in Content.objects.filter(iri_id=iri_id):
       
   791             titles.append(unicode(content.title))
       
   792             projects = content.project_set.all()
       
   793             projects_nb = len(projects)
       
   794             if projects_nb > 0:
       
   795                 project_titles = map(lambda p: unicode(p.title), projects)
       
   796                 errors.append(ungettext("Content '%(title)s' is referenced by this project : %(project_titles)s. Please delete it beforehand.", "Content '%(title)s' is referenced by %(count)d projects: %(project_titles)s. Please delete them beforehand.", projects_nb)%{'title':unicode(content.title),'count':projects_nb, 'project_titles': ",".join(project_titles)})
       
   797  
       
   798         
       
   799     return errors, titles
       
   800 
       
   801 
       
   802 @login_required
       
   803 def delete_content(request, iri_id=None):
       
   804     if not iri_id:
       
   805         iri_id = request.REQUEST.get("iri_id", None)
       
   806         
       
   807     if iri_id:
       
   808         Content.objects.filter(iri_id=iri_id).delete()
       
   809