def get_obj(obj_type, obj_ref, obj_revi, user): """ Get type, reference and revision of an object and return the related controller :param obj_type: :attr:`.PLMObject.type` :type obj_type: str :param obj_ref: :attr:`.PLMObject.reference` :type obj_ref: str :param obj_revi: :attr:`.PLMObject.revision` :type obj_revi: str :return: a :class:`PLMObjectController` or a :class:`UserController` """ if obj_type == 'User': obj = get_object_or_404(User, username=obj_ref) controller_cls = UserController elif obj_type == 'Group': obj = get_object_or_404(Group, name=obj_ref) controller_cls = GroupController else: obj = get_object_or_404(models.PLMObject, type=obj_type, reference=obj_ref, revision=obj_revi) # guess what kind of PLMObject (Part, Document) obj is cls = models.PLMObject find = True while find: find = False for c in cls.__subclasses__(): if hasattr(obj, c.__name__.lower()): cls = c obj = getattr(obj, c.__name__.lower()) find = True controller_cls = get_controller(obj_type) return controller_cls(obj, user)
def clone(self,form, user, block_mails=False, no_index=False): """ .. versionadded:: 1.1 Clone this object and return the related controller. :param form: the form sent from clone view :param user: the user who is cloning the object """ self.check_clone() type_= self.object.type ctrl_cls = get_controller(type_) if form.is_valid(): creation_fields = self.get_creation_fields() data = {} for field in form.cleaned_data : if field in creation_fields: data[field]=form.cleaned_data[field] ref = form.cleaned_data["reference"] rev = form.cleaned_data["revision"] new_ctrl = ctrl_cls.create(ref, type_ , rev, user, data, block_mails, no_index) return new_ctrl else: raise ValueError("form is invalid")
def clone(self, form, user, block_mails=False, no_index=False): """ .. versionadded:: 1.1 Clone this object and return the related controller. :param form: the form sent from clone view :param user: the user who is cloning the object """ self.check_clone() type_ = self.object.type ctrl_cls = get_controller(type_) if form.is_valid(): creation_fields = self.get_creation_fields() data = {} for field in form.cleaned_data: if field in creation_fields: data[field] = form.cleaned_data[field] ref = form.cleaned_data["reference"] rev = form.cleaned_data["revision"] new_ctrl = ctrl_cls.create(ref, type_, rev, user, data, block_mails, no_index) return new_ctrl else: raise ValueError("form is invalid")
def _save_comment_history(sender, comment, request, **kwargs): """ Save an history line when a comment is posted. """ from openPLM.plmapp.controllers import get_controller obj = comment.content_object ctrl_cls = get_controller(obj.__class__.__name__) ctrl = ctrl_cls(comment.content_object, request.user, no_index=True) ctrl._save_histo("New comment", comment.comment)
def get_obj_by_id(obj_id, user): u""" Returns an adequate controller for the object identify by *obj_id*. The returned controller is instanciate with *user* as the user who modify the object. :param obj_id: id of a :class:`.PLMObject` :param user: a :class:`.django.contrib.auth.models.User` :return: a subinstance of a :class:`.PLMObjectController` """ obj = get_object_or_404(models.PLMObject, id=obj_id) obj = models.get_all_plmobjects()[obj.type].objects.get(id=obj_id) return get_controller(obj.type)(obj, user)
def get_obj(obj_type, obj_ref, obj_revi, user): """ Get type, reference and revision of an object and return the related controller :param obj_type: :attr:`.PLMObject.type` :type obj_type: str :param obj_ref: :attr:`.PLMObject.reference` :type obj_ref: str :param obj_revi: :attr:`.PLMObject.revision` :type obj_revi: str :return: a :class:`PLMObjectController` or a :class:`UserController` """ controller_cls = get_controller(obj_type) return controller_cls.load(obj_type, obj_ref, obj_revi, user)
def create(request): """ Creates a :class:`.PLMObject` and returns it :implements: :func:`http_api.create` """ try: type_name = request.POST["type"] cls = models.get_all_plmobjects()[type_name] except KeyError: return {"result" : "error", 'error' : 'bad type'} form = forms.get_creation_form(request.user, cls, request.POST) if form.is_valid(): controller_cls = get_controller(type_name) controller = controller_cls.create_from_form(form, request.user) ret = {"object" : object_to_dict(controller)} return ret else: return {"result" : "error", "error" : form.errors.as_text()}
def create(request): """ Creates a :class:`.PLMObject` and returns it :implements: :func:`http_api.create` """ try: type_name = request.POST["type"] cls = models.get_all_plmobjects()[type_name] except KeyError: return {"result": "error", 'error': 'bad type'} form = forms.get_creation_form(request.user, cls, request.POST) if form.is_valid(): controller_cls = get_controller(type_name) controller = controller_cls.create_from_form(form, request.user) ret = {"object": object_to_dict(controller)} return ret else: return {"result": "error", "error": form.errors.as_text()}
def update_child_files_BD(product, user, old_product): """ :param product: :class:`.Product` that represents a sub-arborescense of the file **.stp** that was decomposed UPDATE whit the news doc_id and doc_path generating in the bomb-child :param old_product: :class:`.Product` that represents a sub-arborescense ORIGINAL of the file **.stp** that was decomposed Updates a :class:`.DocumentFile` STEP that WAS NOT root in a decomposition, to know which :class:`.DocumentFile` to update we use the attribute **product**.doc_id of the arborescense(**product**) This update consists in: Generate a new :class:`.ArbreFile` for each :class:`.DocumentFile` STEP present in the arborescense(**product**) Generate news :class:`.GeometryFile` for the :class:`.DocumentFile` STEP (Copies of the GeometryFiles of the root :class:`.DocumentFile` (Identified for **old_product**.doc_id)) """ for link, old_link in zip(product.links, old_product.links): if not link.product.visited: link.product.visited = True product_copy = copy.copy(link.product) old_product_copy = copy.copy(old_link.product) product_copy.links = [] #when we decompose we delete the links old_product_copy.links = [] doc_file = pmodels.DocumentFile.objects.get(id=product_copy.doc_id) doc_file.filename = product_copy.name + ".stp".encode("utf-8") doc_file.no_index = False doc_file.size = os.path.getsize(doc_file.file.path) doc_file.locked = False doc_file.locker = None doc_file.save() os.chmod(doc_file.file.path, 0400) copy_geometry(old_product_copy, doc_file) #we utilise old_product ArbreFile.create_from_product(product_copy, doc_file) doc_file.document.no_index = False # to reverse no_index=True make in document3D.views.generate_part_doc_links doc_file.document.save() ctrl = get_controller(doc_file.document.type) ctrl = ctrl(doc_file.document, user, True) ctrl._save_histo("File generated by decomposition", "file : %s" % doc_file.filename) update_child_files_BD(link.product, user, old_link.product)
def update_child_files_BD(product,user,old_product): """ :param product: :class:`.Product` that represents a sub-arborescense of the file **.stp** that was decomposed UPDATE whit the news doc_id and doc_path generating in the bomb-child :param old_product: :class:`.Product` that represents a sub-arborescense ORIGINAL of the file **.stp** that was decomposed Updates a :class:`.DocumentFile` STEP that WAS NOT root in a decomposition, to know which :class:`.DocumentFile` to update we use the attribute **product**.doc_id of the arborescense(**product**) This update consists in: Generate a new :class:`.ArbreFile` for each :class:`.DocumentFile` STEP present in the arborescense(**product**) Generate news :class:`.GeometryFile` for the :class:`.DocumentFile` STEP (Copies of the GeometryFiles of the root :class:`.DocumentFile` (Identified for **old_product**.doc_id)) """ for link, old_link in zip(product.links,old_product.links): if not link.product.visited: link.product.visited=True product_copy=copy.copy(link.product) old_product_copy=copy.copy(old_link.product) product_copy.links=[] #when we decompose we delete the links old_product_copy.links=[] doc_file=pmodels.DocumentFile.objects.get(id=product_copy.doc_id) doc_file.filename=product_copy.name+".stp".encode("utf-8") doc_file.no_index=False doc_file.size=os.path.getsize(doc_file.file.path) doc_file.locked = False doc_file.locker = None doc_file.save() os.chmod(doc_file.file.path, 0400) copy_geometry(old_product_copy,doc_file) #we utilise old_product ArbreFile.create_from_product(product_copy,doc_file) doc_file.document.no_index=False # to reverse no_index=True make in document3D.views.generate_part_doc_links doc_file.document.save() ctrl=get_controller(doc_file.document.type) ctrl=ctrl(doc_file.document,user,True) ctrl._save_histo("File generated by decomposition", "file : %s" % doc_file.filename) update_child_files_BD(link.product,user,old_link.product)
def select_pdf_part(request, ctx, obj): """ View helper to select pdf files to download. :type obj: :class:`.PartController` """ data = request.GET if request.GET.get("Download") else None # retrieve all pdf files (from documents attached to children parts) children = obj.get_children(-1) formsets = [] self_link = FakeLink("self", child=obj.object) for level, link in [(0, self_link)] + list(children): link.formsets = [] for l in link.child.documentpartlink_part.now(): doc = l.document ctrl = get_controller(doc.type)(doc, request.user) if ctrl.check_readable(raise_=False): formset = get_pdf_formset(doc, data, prefix="pdf_%s_%d" % (link.id, doc.id)) link.formsets.append(formset) formsets.append((level, link)) if data: # returns a pdf file if all formsets are valid valid = True files = [] for level, link in formsets: for formset in link.formsets: if formset.is_valid(): for form in formset.forms: selected = form.cleaned_data["selected"] if selected: df = form.cleaned_data["id"] files.append(df) else: valid = False if valid: return download_merged_pdf(obj, files) ctx["children"] = formsets return r2r("select_pdf_part.html", ctx, request)
def create_object(request): """ Manage html page for the creation of an instance of `models.PLMObject` subclass. It computes a context dictionnary based on :param request: :class:`django.http.QueryDict` :return: a :class:`django.http.HttpResponse` """ obj, ctx = get_generic_data(request) if request.method == 'GET': type_form = TypeFormWithoutUser(request.GET) if type_form.is_valid(): type_ = type_form.cleaned_data["type"] cls = models.get_all_plmobjects()[type_] if cls in _creation_views: return _creation_views[cls](request) creation_form = get_creation_form(request.user, cls) elif request.method == 'POST': type_form = TypeFormWithoutUser(request.POST) if type_form.is_valid(): type_name = type_form.cleaned_data["type"] cls = models.get_all_plmobjects()[type_name] if cls in _creation_views: return _creation_views[cls](request) creation_form = get_creation_form(request.user, cls, request.POST) if creation_form.is_valid(): user = request.user controller_cls = get_controller(type_name) controller = controller_cls.create_from_form(creation_form, user) return HttpResponseRedirect(controller.plmobject_url) ctx.update({ 'creation_form': creation_form, 'object_type': type_form.cleaned_data["type"], }) return r2r('DisplayObject4creation.htm', ctx, request)
def create_object(request, from_registered_view=False, creation_form=None): """ View to create a :class:`.PLMObject` or a :class:`.GroupInfo`. :url: ``/object/create/`` Requests (POST and GET) must contain a ``type`` variable that validates a :class:`.TypeForm`. POST requests must validate the creation form, fields depend on the given type. If the creation form is valid, an object is created and in case of success, this view redirects to the created object. Requests may contain a ``__next__`` variable. A successful creation will redirect to this URL. Some special strings are replaced: * ``##type##`` with the created object's type * ``##ref##`` with the created object's reference * ``##rev##`` with the created object's reference Requests may also contain other special variables (at most one of them): ``related_doc`` Id of a document. The created part will be attached to this document. Object's type is restricted to part types. Two context variables (``related_doc`` and ``related``) are set to the document controller. ``related_part`` Id of a part. The created document will be attached to this part. Object's type is restricted to document types. Two context variables (``related_part`` and ``related``) are set to the part controller. ``related_parent`` Id of a part. Object's type is restricted to part types. Two context variables (``related_parent`` and ``related``) are set to the part controller. .. note:: If *from_registered_view* is False, this view delegates its treatment to a registered view that handles creation of objects of the given type. (see :func:`.get_creation_view` and :func:`.register_creation_view`) :param from_registered_view: True if this function is called by another creation view :param creation_form: a creation form that will be used instead of the default one **Template:** :file:`create.html` **Context:** ``RequestContext`` ``creation_form`` ``creation_type_form`` :class:`.TypeForm` to select the type of the created object ``object_type`` type of the created object ``next`` value of the ``__next__`` request variable if given """ obj, ctx = get_generic_data(request) Form = forms.TypeForm # it is possible that the created object must be attached to a part # or a document # related_doc and related_part should be a plmobject id # If the related_doc/part is not a doc/part, we let python raise # an AttributeError, since a user should not play with the URL # and openPLM must be smart enough to produce valid URLs attach = related = None if "related_doc" in request.REQUEST: Form = forms.PartTypeForm doc = get_obj_by_id(int(request.REQUEST["related_doc"]), request.user) attach = doc.attach_to_part ctx["related_doc"] = request.REQUEST["related_doc"] related = ctx["related"] = doc elif "related_part" in request.REQUEST: Form = forms.DocumentTypeForm part = get_obj_by_id(int(request.REQUEST["related_part"]), request.user) attach = part.attach_to_document ctx["related_part"] = request.REQUEST["related_part"] related = ctx["related"] = part elif "related_parent" in request.REQUEST: Form = forms.PartTypeForm parent = get_obj_by_id(int(request.REQUEST["related_parent"]), request.user) ctx["related_parent"] = request.REQUEST["related_parent"] related = ctx["related"] = parent if "pfiles" in request.REQUEST: Form = forms.Document2TypeForm if "__next__" in request.REQUEST: redirect_to = request.REQUEST["__next__"] ctx["next"] = redirect_to else: # will redirect to the created object redirect_to = None type_form = Form(request.REQUEST) if type_form.is_valid(): type_ = type_form.cleaned_data["type"] cls = models.get_all_users_and_plmobjects()[type_] if not from_registered_view: view = get_creation_view(cls) if view is not None: # view has been registered to create an object of type 'cls' return view(request) else: ctx["creation_type_form"] = type_form return r2r('create.html', ctx, request) if request.method == 'GET' and creation_form is None: creation_form = forms.get_creation_form(request.user, cls, template="pfiles" not in request.GET) if related is not None: creation_form.fields["group"].initial = related.group creation_form.initial["lifecycle"] = related.lifecycle if "pfiles" in request.GET: pfiles = request.GET.getlist("pfiles") creation_form.initial["pfiles"] = pfiles try: name = filename_to_name( obj.files.get(id=int(pfiles[0])).filename) creation_form.initial["name"] = name except Exception: pass elif request.method == 'POST': if creation_form is None: creation_form = forms.get_creation_form(request.user, cls, request.POST) if creation_form.is_valid(): ctrl_cls = get_controller(type_) ctrl = ctrl_cls.create_from_form(creation_form, request.user) message = _(u"The %(Object_type)s has been created") % dict( Object_type=type_) messages.info(request, message) if attach is not None: try: attach(ctrl) message = _(u"The %(Object_type)s has been attached" ) % dict(Object_type=type_) messages.info(request, message) except (ControllerError, ValueError) as e: # crtl cannot be attached (maybe the state of the # related object as changed) # alerting the user using the messages framework since # the response is redirected message = _(u"Error: %(details)s") % dict( details=unicode(e)) messages.error(request, message) # redirecting to the ctrl page that lists its attached # objects if ctrl.is_document: return HttpResponseRedirect(ctrl.plmobject_url + "parts/") else: return HttpResponseRedirect(ctrl.plmobject_url + "doc-cad/") if redirect_to: redirect_to = redirect_to.replace("##ref##", ctrl.reference) redirect_to = redirect_to.replace("##rev##", ctrl.revision) redirect_to = redirect_to.replace("##type##", ctrl.type) return HttpResponseRedirect(redirect_to or ctrl.plmobject_url) ctx.update({ 'creation_form': creation_form, 'object_type': type_, 'creation_type_form': type_form, }) return r2r('create.html', ctx, request)
def decomposer_all(stp_file_pk, arbre, part_pk, native_related_pk, user_pk, old_arbre): """ :param arbre: Information contained in file **.arb** that allows to generate a :class:`.Product` that represents the arborescense of the :class:`~django.core.files.File` .stp to decompose , his nodes contains doc_id and doc_path of new :class:`.DocumentFile` created in the arborescense :type plmobject: :class:`.Product` :param stp_file_pk: primery key of a :class:`.DocumentFile` that contains the :class:`~django.core.files.File` that will be decomposed :param part_pk: primery key of a :class:`.Part` attached to the :class:`.Document3D` that contains the :class:`.DocumentFile` that will be decomposed :param native_related_pk: If exists a native file related to the :class:`.DocumentFile` that will be decomposed , contains the primary key of the :class:`.DocumentFile` related to the native file This function departs from a :class:`.DocumentFile` (**stp_file_pk**) associated with a :class:`.Document3D` attached to a :class:`.Part` (``part_pk``) and from the :class:`.Product` related to the :class:`.DocumentFile` in order to decompose :class:`~django.core.files.File` .stp.With this purpose it realizes a call to the subprocess :meth:`.generateDecomposition.py`. -**Preconditions** ,before calling to this function, the following steps must have been realized: -The bom-child of Parts (in relation to the :class:`.Product` (generate across the **arbre**)) has been generated -For every :class:`.ParentChildLink` generated in the previous condition we attach all the :class:`.Location_link` relatives -To every generated :class:`.Part` a :class:`.Document3D` has been attached and the :class:`.Document3D` has been set like the attribute PartDecompose of the :class:`.Part` -The attribute doc_id of every node of the :class:`.Product` (generate across the **arbre**) is now the relative id of :class:`.Document3D` generated in the previous condition -To every generated :class:`.Document3D` has been added a new empty(locked) :class:`.DocumentFile` .stp -The attribute doc_path of every node of the :class:`.Product` is now the path of :class:`.DocumentFile` generated in the previous condition -The :class:`.DocumentFile` (**stp_file_pk**) is locked -If exists a native :class:`.DocumentFile` (**native_related_pk**) related to the :class:`.DocumentFile` (**stp_file_pk**), then this one was depreciated (afterwards will be promoted) -**Treatment** -The subprocess :meth:`.generateDecomposition.py` is going to write in to doc_path of every node of the :class:`.Product` (generate across the **arbre**) the corresponding decomposed file -**Postconditions** -For every generated :class:`.Document3D` , the new :class:`.DocumentFile` added is unlocked -For every new :class:`.DocumentFile` , his :class:`.GeometryFile` and :class:`.ArbreFile` have been generated -The root :class:`.DocumentFile` (**stp_file_pk**) has been deprecated and unlocked -A new root :class:`.DocumentFile` has been generated according to the situation -If exists a native :class:`.DocumentFile` (**native_related_pk**) related to the :class:`.DocumentFile` (**stp_file_pk**), then this one was promoted -We set the :class:`.Part` (**part_pk**) like the attribute PartDecompose of the :class:`.Document3D` that contains the :class:`.DocumentFile` (**stp_file_pk**) """ try: stp_file = pmodels.DocumentFile.objects.get(pk=stp_file_pk) ctrl = get_controller(stp_file.document.type) user = pmodels.User.objects.get(pk=user_pk) ctrl = ctrl(stp_file.document, user) part = pmodels.Part.objects.get(pk=part_pk) product = classes.Product.from_list(json.loads( arbre)) #whit doc_id and doc_path updated for every node old_product = classes.Product.from_list( json.loads(old_arbre)) # doc_id and doc_path original new_stp_file = pmodels.DocumentFile() name = new_stp_file.file.storage.get_available_name( (product.name + ".stp").encode("utf-8")) new_stp_path = os.path.join(new_stp_file.file.storage.location, name) f = File(open(new_stp_path, 'w')) f.close() product.doc_path = new_stp_path # the old documentfile will be deprecated product.doc_id = new_stp_file.id # the old documentfile will be deprecated temp_file = tempfile.NamedTemporaryFile(delete=True) temp_file.write(json.dumps(product.to_list())) temp_file.seek(0) dirname = os.path.dirname(__file__) if subprocess.call([ "python", os.path.join(dirname, "generateDecomposition.py"), stp_file.file.path, temp_file.name ]) == 0: update_child_files_BD(product, user, old_product) update_root_BD(new_stp_file, stp_file, ctrl, product, f, name, part) else: raise Document3D_decomposer_Error except: raise Document3D_decomposer_Error finally: if native_related_pk is not None: native_related = pmodels.DocumentFile.objects.get( pk=native_related_pk) native_related.deprecated = False native_related.save() stp_file.locked = False stp_file.locker = None stp_file.save()
def create_object(request, from_registered_view=False, creation_form=None): """ View to create a :class:`.PLMObject` or a :class:`.GroupInfo`. :url: ``/object/create/`` Requests (POST and GET) must contain a ``type`` variable that validates a :class:`.TypeForm`. POST requests must validate the creation form, fields depend on the given type. If the creation form is valid, an object is created and in case of success, this view redirects to the created object. Requests may contain a ``__next__`` variable. A successful creation will redirect to this URL. Some special strings are replaced: * ``##type##`` with the created object's type * ``##ref##`` with the created object's reference * ``##rev##`` with the created object's reference Requests may also contain other special variables (at most one of them): ``related_doc`` Id of a document. The created part will be attached to this document. Object's type is restricted to part types. Two context variables (``related_doc`` and ``related``) are set to the document controller. ``related_part`` Id of a part. The created document will be attached to this part. Object's type is restricted to document types. Two context variables (``related_part`` and ``related``) are set to the part controller. ``related_parent`` Id of a part. Object's type is restricted to part types. Two context variables (``related_parent`` and ``related``) are set to the part controller. .. note:: If *from_registered_view* is False, this view delegates its treatment to a registered view that handles creation of objects of the given type. (see :func:`.get_creation_view` and :func:`.register_creation_view`) :param from_registered_view: True if this function is called by another creation view :param creation_form: a creation form that will be used instead of the default one **Template:** :file:`create.html` **Context:** ``RequestContext`` ``creation_form`` ``creation_type_form`` :class:`.TypeForm` to select the type of the created object ``object_type`` type of the created object ``next`` value of the ``__next__`` request variable if given """ obj, ctx = get_generic_data(request) Form = forms.TypeForm # it is possible that the created object must be attached to a part # or a document # related_doc and related_part should be a plmobject id # If the related_doc/part is not a doc/part, we let python raise # an AttributeError, since a user should not play with the URL # and openPLM must be smart enough to produce valid URLs attach = related = None if "related_doc" in request.REQUEST: Form = forms.PartTypeForm doc = get_obj_by_id(int(request.REQUEST["related_doc"]), request.user) attach = doc.attach_to_part ctx["related_doc"] = request.REQUEST["related_doc"] related = ctx["related"] = doc elif "related_part" in request.REQUEST: Form = forms.DocumentTypeForm part = get_obj_by_id(int(request.REQUEST["related_part"]), request.user) attach = part.attach_to_document ctx["related_part"] = request.REQUEST["related_part"] related = ctx["related"] = part elif "related_parent" in request.REQUEST: Form = forms.PartTypeForm parent = get_obj_by_id(int(request.REQUEST["related_parent"]), request.user) ctx["related_parent"] = request.REQUEST["related_parent"] related = ctx["related"] = parent if "pfiles" in request.REQUEST: Form = forms.Document2TypeForm if "__next__" in request.REQUEST: redirect_to = request.REQUEST["__next__"] ctx["next"] = redirect_to else: # will redirect to the created object redirect_to = None type_form = Form(request.REQUEST) if type_form.is_valid(): type_ = type_form.cleaned_data["type"] cls = models.get_all_users_and_plmobjects()[type_] if not from_registered_view: view = get_creation_view(cls) if view is not None: # view has been registered to create an object of type 'cls' return view(request) else: ctx["creation_type_form"] = type_form return r2r('create.html', ctx, request) if request.method == 'GET' and creation_form is None: creation_form = forms.get_creation_form(request.user, cls, template="pfiles" not in request.GET) if related is not None: creation_form.fields["group"].initial = related.group creation_form.initial["lifecycle"] = related.lifecycle if "pfiles" in request.GET: pfiles = request.GET.getlist("pfiles") creation_form.initial["pfiles"] = pfiles try: name = filename_to_name(obj.files.get(id=int(pfiles[0])).filename) creation_form.initial["name"] = name except Exception: pass elif request.method == 'POST': if creation_form is None: creation_form = forms.get_creation_form(request.user, cls, request.POST) if creation_form.is_valid(): ctrl_cls = get_controller(type_) ctrl = ctrl_cls.create_from_form(creation_form, request.user) message = _(u"The %(Object_type)s has been created") % dict(Object_type = type_) messages.info(request, message) if attach is not None: try: attach(ctrl) message = _(u"The %(Object_type)s has been attached") % dict(Object_type = type_) messages.info(request, message) except (ControllerError, ValueError) as e: # crtl cannot be attached (maybe the state of the # related object as changed) # alerting the user using the messages framework since # the response is redirected message = _(u"Error: %(details)s") % dict(details=unicode(e)) messages.error(request, message) # redirecting to the ctrl page that lists its attached # objects if ctrl.is_document: return HttpResponseRedirect(ctrl.plmobject_url + "parts/") else: return HttpResponseRedirect(ctrl.plmobject_url + "doc-cad/") if redirect_to: redirect_to = redirect_to.replace("##ref##", ctrl.reference) redirect_to = redirect_to.replace("##rev##", ctrl.revision) redirect_to = redirect_to.replace("##type##", ctrl.type) return HttpResponseRedirect(redirect_to or ctrl.plmobject_url) ctx.update({ 'creation_form' : creation_form, 'object_type' : type_, 'creation_type_form' : type_form, }) return r2r('create.html', ctx, request)
def decomposer_all(stp_file_pk,arbre,part_pk,native_related_pk,user_pk,old_arbre): """ :param arbre: Information contained in file **.arb** that allows to generate a :class:`.Product` that represents the arborescense of the :class:`~django.core.files.File` .stp to decompose , his nodes contains doc_id and doc_path of new :class:`.DocumentFile` created in the arborescense :type plmobject: :class:`.Product` :param stp_file_pk: primery key of a :class:`.DocumentFile` that contains the :class:`~django.core.files.File` that will be decomposed :param part_pk: primery key of a :class:`.Part` attached to the :class:`.Document3D` that contains the :class:`.DocumentFile` that will be decomposed :param native_related_pk: If exists a native file related to the :class:`.DocumentFile` that will be decomposed , contains the primary key of the :class:`.DocumentFile` related to the native file This function departs from a :class:`.DocumentFile` (**stp_file_pk**) associated with a :class:`.Document3D` attached to a :class:`.Part` (``part_pk``) and from the :class:`.Product` related to the :class:`.DocumentFile` in order to decompose :class:`~django.core.files.File` .stp.With this purpose it realizes a call to the subprocess :meth:`.generateDecomposition.py`. -**Preconditions** ,before calling to this function, the following steps must have been realized: -The bom-child of Parts (in relation to the :class:`.Product` (generate across the **arbre**)) has been generated -For every :class:`.ParentChildLink` generated in the previous condition we attach all the :class:`.Location_link` relatives -To every generated :class:`.Part` a :class:`.Document3D` has been attached and the :class:`.Document3D` has been set like the attribute PartDecompose of the :class:`.Part` -The attribute doc_id of every node of the :class:`.Product` (generate across the **arbre**) is now the relative id of :class:`.Document3D` generated in the previous condition -To every generated :class:`.Document3D` has been added a new empty(locked) :class:`.DocumentFile` .stp -The attribute doc_path of every node of the :class:`.Product` is now the path of :class:`.DocumentFile` generated in the previous condition -The :class:`.DocumentFile` (**stp_file_pk**) is locked -If exists a native :class:`.DocumentFile` (**native_related_pk**) related to the :class:`.DocumentFile` (**stp_file_pk**), then this one was depreciated (afterwards will be promoted) -**Treatment** -The subprocess :meth:`.generateDecomposition.py` is going to write in to doc_path of every node of the :class:`.Product` (generate across the **arbre**) the corresponding decomposed file -**Postconditions** -For every generated :class:`.Document3D` , the new :class:`.DocumentFile` added is unlocked -For every new :class:`.DocumentFile` , his :class:`.GeometryFile` and :class:`.ArbreFile` have been generated -The root :class:`.DocumentFile` (**stp_file_pk**) has been deprecated and unlocked -A new root :class:`.DocumentFile` has been generated according to the situation -If exists a native :class:`.DocumentFile` (**native_related_pk**) related to the :class:`.DocumentFile` (**stp_file_pk**), then this one was promoted -We set the :class:`.Part` (**part_pk**) like the attribute PartDecompose of the :class:`.Document3D` that contains the :class:`.DocumentFile` (**stp_file_pk**) """ try: stp_file = pmodels.DocumentFile.objects.get(pk=stp_file_pk) ctrl=get_controller(stp_file.document.type) user=pmodels.User.objects.get(pk=user_pk) ctrl=ctrl(stp_file.document,user) part=pmodels.Part.objects.get(pk=part_pk) product=classes.Product.from_list(json.loads(arbre)) #whit doc_id and doc_path updated for every node old_product=classes.Product.from_list(json.loads(old_arbre)) # doc_id and doc_path original new_stp_file=pmodels.DocumentFile() name = new_stp_file.file.storage.get_available_name((product.name+".stp").encode("utf-8")) new_stp_path = os.path.join(new_stp_file.file.storage.location, name) f = File(open(new_stp_path, 'w')) f.close() product.doc_path=new_stp_path # the old documentfile will be deprecated product.doc_id=new_stp_file.id # the old documentfile will be deprecated temp_file = tempfile.NamedTemporaryFile(delete=True) temp_file.write(json.dumps(product.to_list())) temp_file.seek(0) dirname = os.path.dirname(__file__) if subprocess.call(["python", os.path.join(dirname, "generateDecomposition.py"), stp_file.file.path,temp_file.name]) == 0: update_child_files_BD(product,user,old_product) update_root_BD(new_stp_file,stp_file,ctrl,product,f,name,part) else: raise Document3D_decomposer_Error except: raise Document3D_decomposer_Error finally: if native_related_pk is not None: native_related = pmodels.DocumentFile.objects.get(pk=native_related_pk) native_related.deprecated=False native_related.save() stp_file.locked = False stp_file.locker = None stp_file.save()