2024-07-18 21:35:17 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								import  becca  from  "../becca/becca.js" ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								import  utils  from  "../services/utils.js" ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								import  eu  from  "./etapi_utils.js" ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								import  mappers  from  "./mappers.js" ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								import  noteService  from  "../services/notes.js" ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								import  TaskContext  from  "../services/task_context.js" ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								import  v  from  "./validators.js" ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								import  searchService  from  "../services/search/services/search.js" ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								import  SearchContext  from  "../services/search/search_context.js" ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								import  zipExportService  from  "../services/export/zip.js" ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								import  zipImportService  from  "../services/import/zip.js" ;  
						 
					
						
							
								
									
										
										
										
											2025-01-13 23:18:10 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								import  type  {  Request ,  Router  }  from  "express" ;  
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:36:24 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								import  type  {  ParsedQs  }  from  "qs" ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								import  type  {  NoteParams  }  from  "../services/note-interface.js" ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								import  type  {  SearchParams  }  from  "../services/search/services/types.js" ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								import  type  {  ValidatorMap  }  from  "./etapi-interface.js" ;  
						 
					
						
							
								
									
										
										
										
											2024-04-07 16:56:45 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								function  register ( router : Router )  {  
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    eu . route ( router ,  "get" ,  "/etapi/notes" ,  ( req ,  res ,  next )  = >  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-07 14:56:22 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  {  search  }  =  req . query ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 13:18:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-04-07 16:56:45 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        if  ( typeof  search  !==  "string"  ||  ! search ? . trim ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            throw  new  eu . EtapiError ( 400 ,  "SEARCH_QUERY_PARAM_MANDATORY" ,  "'search' query parameter is mandatory." ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 13:18:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-12 21:14:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 13:18:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  searchParams  =  parseSearchParams ( req ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-10 17:09:20 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  searchContext  =  new  SearchContext ( searchParams ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-12 21:14:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-10 17:09:20 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  searchResults  =  searchService . findResultsWithQuery ( search ,  searchContext ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  foundNotes  =  searchResults . map ( ( sr )  = >  becca . notes [ sr . noteId ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-12 21:14:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-04-07 16:56:45 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  resp : any  =  { 
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            results : foundNotes.map ( ( note )  = >  mappers . mapNoteToPojo ( note ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-10 17:09:20 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        } ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-12 21:14:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-10 17:09:20 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        if  ( searchContext . debugInfo )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            resp . debugInfo  =  searchContext . debugInfo ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-12 21:14:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-10 17:09:20 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        res . json ( resp ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 13:18:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    eu . route ( router ,  "get" ,  "/etapi/notes/:noteId" ,  ( req ,  res ,  next )  = >  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-10 17:09:20 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  note  =  eu . getAndCheckNote ( req . params . noteId ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:33:59 +01:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        res . json ( mappers . mapNoteToPojo ( note ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-04-07 16:56:45 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    const  ALLOWED_PROPERTIES_FOR_CREATE_NOTE : ValidatorMap  =  { 
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        parentNoteId :  [ v . mandatory ,  v . notNull ,  v . isNoteId ] , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        title :  [ v . mandatory ,  v . notNull ,  v . isString ] , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        type :  [ v . mandatory ,  v . notNull ,  v . isNoteType ] , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        mime :  [ v . notNull ,  v . isString ] , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        content :  [ v . notNull ,  v . isString ] , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        notePosition :  [ v . notNull ,  v . isInteger ] , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        prefix :  [ v . notNull ,  v . isString ] , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        isExpanded :  [ v . notNull ,  v . isBoolean ] , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        noteId :  [ v . notNull ,  v . isValidEntityId ] , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        dateCreated :  [ v . notNull ,  v . isString ,  v . isLocalDateTime ] , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        utcDateCreated :  [ v . notNull ,  v . isString ,  v . isUtcDateTime ] 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-12 19:32:23 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    } ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-12 21:14:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    eu . route ( router ,  "post" ,  "/etapi/create-note" ,  ( req ,  res ,  next )  = >  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-07 16:56:45 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  _params  =  { } ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        eu . validateAndPatch ( _params ,  req . body ,  ALLOWED_PROPERTIES_FOR_CREATE_NOTE ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        const  params  =  _params  as  NoteParams ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:33:59 +01:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        try  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            const  resp  =  noteService . createNewNote ( params ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-12 21:14:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            res . status ( 201 ) . json ( { 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:33:59 +01:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								                note : mappers.mapNoteToPojo ( resp . note ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                branch : mappers.mapBranchToPojo ( resp . branch ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            } ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        }  catch  ( e : any )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-12 19:32:23 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            return  eu . sendError ( res ,  500 ,  eu . GENERIC_CODE ,  e . message ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:33:59 +01:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    const  ALLOWED_PROPERTIES_FOR_PATCH  =  { 
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        title :  [ v . notNull ,  v . isString ] , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        type :  [ v . notNull ,  v . isString ] , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        mime :  [ v . notNull ,  v . isString ] , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        dateCreated :  [ v . notNull ,  v . isString ,  v . isLocalDateTime ] , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        utcDateCreated :  [ v . notNull ,  v . isString ,  v . isUtcDateTime ] 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:33:59 +01:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    } ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    eu . route ( router ,  "patch" ,  "/etapi/notes/:noteId" ,  ( req ,  res ,  next )  = >  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-05 09:23:42 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  note  =  eu . getAndCheckNote ( req . params . noteId ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 23:06:04 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:33:59 +01:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        if  ( note . isProtected )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-05 09:23:42 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            throw  new  eu . EtapiError ( 400 ,  "NOTE_IS_PROTECTED" ,  ` Note ' ${ req . params . noteId } ' is protected and cannot be modified through ETAPI. ` ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:33:59 +01:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 23:06:04 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-10 17:09:20 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        eu . validateAndPatch ( note ,  req . body ,  ALLOWED_PROPERTIES_FOR_PATCH ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-12 19:32:23 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        note . save ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 23:06:04 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:33:59 +01:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								        res . json ( mappers . mapNoteToPojo ( note ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    eu . route ( router ,  "delete" ,  "/etapi/notes/:noteId" ,  ( req ,  res ,  next )  = >  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-07 14:56:22 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  {  noteId  }  =  req . params ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:33:59 +01:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        const  note  =  becca . getNote ( noteId ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-06-05 09:23:42 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        if  ( ! note )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:33:59 +01:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								            return  res . sendStatus ( 204 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        note . deleteNote ( null ,  new  TaskContext ( "no-progress-reporting" ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:33:59 +01:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        res . sendStatus ( 204 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 12:01:54 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    eu . route ( router ,  "get" ,  "/etapi/notes/:noteId/content" ,  ( req ,  res ,  next )  = >  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-10 17:09:20 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  note  =  eu . getAndCheckNote ( req . params . noteId ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 12:01:54 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-06-05 09:23:42 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        if  ( note . isProtected )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            throw  new  eu . EtapiError ( 400 ,  "NOTE_IS_PROTECTED" ,  ` Note ' ${ req . params . noteId } ' is protected and content cannot be read through ETAPI. ` ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 12:01:54 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  filename  =  utils . formatDownloadTitle ( note . title ,  note . type ,  note . mime ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        res . setHeader ( "Content-Disposition" ,  utils . getContentDisposition ( filename ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 12:01:54 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        res . setHeader ( "Cache-Control" ,  "no-cache, no-store, must-revalidate" ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        res . setHeader ( "Content-Type" ,  note . mime ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 12:01:54 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        res . send ( note . getContent ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    eu . route ( router ,  "put" ,  "/etapi/notes/:noteId/content" ,  ( req ,  res ,  next )  = >  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-10 17:09:20 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  note  =  eu . getAndCheckNote ( req . params . noteId ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 12:01:54 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-06-05 09:23:42 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        if  ( note . isProtected )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								            throw  new  eu . EtapiError ( 400 ,  "NOTE_IS_PROTECTED" ,  ` Note ' ${ req . params . noteId } ' is protected and cannot be modified through ETAPI. ` ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 12:01:54 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        note . setContent ( req . body ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-11 23:22:51 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-01-26 20:32:27 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        noteService . asyncPostProcessContent ( note ,  req . body ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 12:01:54 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        return  res . sendStatus ( 204 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-24 21:30:29 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    eu . route ( router ,  "get" ,  "/etapi/notes/:noteId/export" ,  ( req ,  res ,  next )  = >  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-24 21:30:29 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  note  =  eu . getAndCheckNote ( req . params . noteId ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        const  format  =  req . query . format  ||  "html" ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-04-07 16:56:45 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        if  ( typeof  format  !==  "string"  ||  ! [ "html" ,  "markdown" ] . includes ( format ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-05 09:23:42 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            throw  new  eu . EtapiError ( 400 ,  "UNRECOGNIZED_EXPORT_FORMAT" ,  ` Unrecognized export format ' ${ format } ', supported values are 'html' (default) or 'markdown'. ` ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-24 21:30:29 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  taskContext  =  new  TaskContext ( "no-progress-reporting" ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-24 21:30:29 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        // technically a branch is being exported (includes prefix), but it's such a minor difference yet usability pain
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        // (e.g. branchIds are not seen in UI), that we export "note export" instead.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        const  branch  =  note . getParentBranches ( ) [ 0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-04-07 16:56:45 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        zipExportService . exportToZip ( taskContext ,  branch ,  format  as  "html"  |  "markdown" ,  res ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-24 21:30:29 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    } ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-11 23:18:51 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    eu . route ( router ,  "post" ,  "/etapi/notes/:noteId/import" ,  ( req ,  res ,  next )  = >  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-15 23:21:40 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  note  =  eu . getAndCheckNote ( req . params . noteId ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  taskContext  =  new  TaskContext ( "no-progress-reporting" ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-15 23:21:40 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        zipImportService . importZip ( taskContext ,  req . body ,  note ) . then ( ( importedNote )  = >  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-15 23:21:40 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            res . status ( 201 ) . json ( { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								                note : mappers.mapNoteToPojo ( importedNote ) , 
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								                branch : mappers.mapBranchToPojo ( importedNote . getParentBranches ( ) [ 0 ] ) 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-15 23:21:40 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        } ) ;  // we need better error handling here, async errors won't be properly processed.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    eu . route ( router ,  "post" ,  "/etapi/notes/:noteId/revision" ,  ( req ,  res ,  next )  = >  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-11 23:18:51 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  note  =  eu . getAndCheckNote ( req . params . noteId ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-06-04 23:01:40 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        note . saveRevision ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-11 23:18:51 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        return  res . sendStatus ( 204 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-05 09:23:42 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    eu . route ( router ,  "get" ,  "/etapi/notes/:noteId/attachments" ,  ( req ,  res ,  next )  = >  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-05 09:23:42 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  note  =  eu . getAndCheckNote ( req . params . noteId ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        const  attachments  =  note . getAttachments ( {  includeContentLength : true  } ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-05 09:23:42 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        res . json ( attachments . map ( ( attachment )  = >  mappers . mapAttachmentToPojo ( attachment ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-05 09:23:42 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    } ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:33:59 +01:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-12-10 22:35:23 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								function  parseSearchParams ( req : Request )  {  
						 
					
						
							
								
									
										
										
										
											2024-04-07 16:56:45 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    const  rawSearchParams : SearchParams  =  { 
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        fastSearch : parseBoolean ( req . query ,  "fastSearch" ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        includeArchivedNotes : parseBoolean ( req . query ,  "includeArchivedNotes" ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        ancestorNoteId : parseString ( req . query [ "ancestorNoteId" ] ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        ancestorDepth : parseString ( req . query [ "ancestorDepth" ] ) ,  // e.g. "eq5"
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        orderBy : parseString ( req . query [ "orderBy" ] ) , 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-07 16:56:45 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        // TODO: Check why the order direction was provided as a number, but it's a string everywhere else.
 
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        orderDirection : parseOrderDirection ( req . query ,  "orderDirection" )  as  unknown  as  string , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        limit : parseInteger ( req . query ,  "limit" ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        debug : parseBoolean ( req . query ,  "debug" ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 13:18:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    } ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-04-07 16:56:45 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    const  searchParams : SearchParams  =  { } ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 13:18:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-04-07 16:56:45 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    for  ( const  paramName  of  Object . keys ( rawSearchParams )  as  ( keyof  SearchParams ) [ ] )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 13:18:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        if  ( rawSearchParams [ paramName ]  !==  undefined )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-07 16:56:45 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								            ( searchParams  as  any ) [ paramName ]  =  rawSearchParams [ paramName ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 13:18:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    return  searchParams ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								const  SEARCH_PARAM_ERROR  =  "SEARCH_PARAM_VALIDATION_ERROR" ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-04-07 16:56:45 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								function  parseString ( value : string  |  ParsedQs  |  string [ ]  |  ParsedQs [ ]  |  undefined ) :  string  |  undefined  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( typeof  value  ===  "string" )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        return  value ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    return  undefined ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								function  parseBoolean ( obj : any ,  name : string )  {  
						 
					
						
							
								
									
										
										
										
											2022-01-08 13:18:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    if  ( ! ( name  in  obj ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        return  undefined ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    if  ( ! [ "true" ,  "false" ] . includes ( obj [ name ] ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-05 09:23:42 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        throw  new  eu . EtapiError ( 400 ,  SEARCH_PARAM_ERROR ,  ` Cannot parse boolean ' ${ name } ' value ' ${ obj [ name ] } , allowed values are 'true' and 'false'. ` ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 13:18:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    return  obj [ name ]  ===  "true" ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 13:18:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-04-07 16:56:45 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								function  parseOrderDirection ( obj : any ,  name : string )  {  
						 
					
						
							
								
									
										
										
										
											2024-04-16 21:10:39 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    if  ( ! ( name  in  obj ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        return  undefined ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 13:18:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    const  integer  =  parseInt ( obj [ name ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-09 18:07:02 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    if  ( ! [ "asc" ,  "desc" ] . includes ( obj [ name ] ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-05 09:23:42 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        throw  new  eu . EtapiError ( 400 ,  SEARCH_PARAM_ERROR ,  ` Cannot parse order direction value ' ${ obj [ name ] } , allowed values are 'asc' and 'desc'. ` ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 13:18:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    return  integer ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-04-07 16:56:45 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								function  parseInteger ( obj : any ,  name : string )  {  
						 
					
						
							
								
									
										
										
										
											2022-01-08 13:18:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    if  ( ! ( name  in  obj ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								        return  undefined ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    const  integer  =  parseInt ( obj [ name ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    if  ( Number . isNaN ( integer ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-05 09:23:42 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								        throw  new  eu . EtapiError ( 400 ,  SEARCH_PARAM_ERROR ,  ` Cannot parse integer ' ${ name } ' value ' ${ obj [ name ] } '. ` ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-08 13:18:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								    } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								    return  integer ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-18 21:42:44 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								export  default  {  
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:33:59 +01:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								    register 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 23:06:04 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								} ;