Source code for ccpn.core.Note

"""
"""
#=========================================================================================
# Licence, Reference and Credits
#=========================================================================================
__copyright__ = "Copyright (C) CCPN project (http://www.ccpn.ac.uk) 2014 - 2022"
__credits__ = ("Ed Brooksbank, Joanna Fox, Victoria A Higman, Luca Mureddu, Eliza Płoskoń",
               "Timothy J Ragan, Brian O Smith, Gary S Thompson & Geerten W Vuister")
__licence__ = ("CCPN licence. See http://www.ccpn.ac.uk/v3-software/downloads/license")
__reference__ = ("Skinner, S.P., Fogh, R.H., Boucher, W., Ragan, T.J., Mureddu, L.G., & Vuister, G.W.",
                 "CcpNmr AnalysisAssign: a flexible platform for integrated NMR analysis",
                 "J.Biomol.Nmr (2016), 66, 111-124, http://doi.org/10.1007/s10858-016-0060-y")
#=========================================================================================
# Last code modification
#=========================================================================================
__modifiedBy__ = "$modifiedBy: Ed Brooksbank $"
__dateModified__ = "$dateModified: 2022-01-13 17:23:25 +0000 (Thu, January 13, 2022) $"
__version__ = "$Revision: 3.0.4 $"
#=========================================================================================
# Created
#=========================================================================================
__author__ = "$Author: Ed Brooksbank $"
__date__ = "$Date: 2017-04-07 10:28:41 +0000 (Fri, April 07, 2017) $"
#=========================================================================================
# Start of code
#=========================================================================================

import typing
from datetime import datetime

from ccpn.util import Constants as utilConstants
from ccpn.core.Project import Project
from ccpn.core._implementation.AbstractWrapperObject import AbstractWrapperObject
from ccpn.core.lib import Pid
from ccpnmodel.ccpncore.api.ccp.nmr.Nmr import Note as ApiNote
from ccpn.core.lib.ContextManagers import newObject, renameObject, ccpNmrV3CoreSetter
from ccpn.util.decorators import logCommand


[docs]class Note(AbstractWrapperObject): """Project note.""" #: Short class name, for PID. shortClassName = 'NO' # Attribute it necessary as subclasses must use superclass className className = 'Note' _parentClass = Project #: Name of plural link to instances of class _pluralLinkName = 'notes' #: List of child classes. _childClasses = [] # Qualified name of matching API class _apiClassQualifiedName = ApiNote._metaclass.qualifiedName() # Internal NameSpace _COMMENT = 'comment' #========================================================================================= # CCPN properties #========================================================================================= @property def _apiNote(self) -> ApiNote: """ CCPN Project Note""" return self._wrappedData @property def _key(self) -> str: """Note local ID""" return self._wrappedData.name.translate(Pid.remapSeparators) @property def serial(self) -> int: """serial number of note - immutable, part of identifier""" return self._wrappedData.serial @property def name(self) -> str: """Name of note, part of identifier""" return self._wrappedData.name @name.setter @logCommand(get='self', isProperty=True) def name(self, value: str): """set Name of note, part of identifier""" self.rename(value) @property def _parent(self) -> Project: """Parent (containing) object.""" return self._project @property def text(self) -> str: """Free-form text comment""" return self._wrappedData.text @text.setter @logCommand(get='self', isProperty=True) @ccpNmrV3CoreSetter() def text(self, value: str): if value is not None: if not isinstance(value, str): raise TypeError("Note text must be a string") self._wrappedData.text = value @property def created(self) -> typing.Optional[str]: """Note creation time""" return self._wrappedData.created.strftime(utilConstants.stdTimeFormat) @created.setter @logCommand(get='self', isProperty=True) @ccpNmrV3CoreSetter() def created(self, value): # bypass the api because frozen for timeFormat in (utilConstants.stdTimeFormat, utilConstants.isoTimeFormat): try: # loop until the correct format is found self._wrappedData.__dict__['created'] = datetime.strptime(value, timeFormat) break except: continue else: raise TypeError("time created is not the correct format") @property def lastModified(self) -> str: """Note last modification time""" return self._wrappedData.lastModified.strftime(utilConstants.stdTimeFormat) @lastModified.setter @logCommand(get='self', isProperty=True) @ccpNmrV3CoreSetter() def lastModified(self, value): # bypass the api because frozen for timeFormat in (utilConstants.stdTimeFormat, utilConstants.isoTimeFormat): try: # loop until the correct format is found self._wrappedData.__dict__['lastModified'] = datetime.strptime(value, timeFormat) break except: continue else: raise TypeError("time created is not the correct format") @property def header(self) -> typing.Optional[str]: # ejb - changed from str """Note header == first line of note""" text = self._wrappedData.text if text: ll = text.splitlines() if ll: return ll[0] return None #========================================================================================= # Implementation functions #========================================================================================= @classmethod def _getAllWrappedData(cls, parent: Project) -> list: """get wrappedData for all Notes linked to NmrProject""" return parent._wrappedData.sortedNotes()
[docs] @renameObject() @logCommand(get='self') def rename(self, value: str): """Rename Note, changing its name and Pid. """ return self._rename(value)
#========================================================================================= # CCPN functions #========================================================================================= #=========================================================================================== # new<Object> and other methods # Call appropriate routines in their respective locations #=========================================================================================== #========================================================================================= # Connections to parents: #========================================================================================= @newObject(Note) def _newNote(self: Project, name: str = None, text: str = None, comment: str = None) -> Note: """Create new Note. See the Note class for details. :param name: name for the note. :param text: contents of the note. :return: a new Note instance. """ name = Note._uniqueName(project=self, name=name) if text is not None: if not isinstance(text, str): raise TypeError("Note text must be a string") apiNote = self._wrappedData.newNote(text=text, name=name) result = self._data2Obj.get(apiNote) if result is None: raise RuntimeError('Unable to generate new Note item') result.comment = comment return result #EJB 20181205: moved to Project # Project.newNote = _newNote # del _newNote # # Notifiers: # Project._apiNotifiers.append(('_finaliseApiRename', {}, # ApiNote._metaclass.qualifiedName(), 'setName'))