// aplStepManager.h

#pragma once

#include <StepData.h>
#include <aplNetStepData.h>
#include <apl_gui.h>
#include <aplCryptManager.h>
#include <aplpacket.h>
#include <map>
#include <list>
#include <vector>
//class CaplNetStepData;
//class CaplLoadData;
//class CaplQLQuery;

class CaplMgrPrgsDlg;
///////////////////////
//definies для иконок//
///////////////////////
#define ICON_NULL 0
#define ICON_DESKTOP 1
#define ICON_FOLDERS 2
#define ICON_FOLDER 4
#define ICON_PERS_FOLDER 8
#define ICON_PERSON_LOCK_FOLDER 9
#define ICON_PERSON_LOCK_FOLDER_OPEN 10
#define ICON_VIRTUAL_DOC_FOLDER 11
#define ICON_CATEGORIES	12

#define ICON_CLASSIFIER_SYSTEM	ICON_CATEGORIES+2
#define ICON_CLASSIFIER_ELEMENT_M	ICON_CLASSIFIER_SYSTEM+2
#define ICON_CLASSIFIER_ELEMENT_S	ICON_CLASSIFIER_SYSTEM+3
#define ICON_CLASSIFIER_ELEMENT_M_DELETED ICON_CLASSIFIER_SYSTEM+4
#define ICON_CLASSIFIER_ELEMENT_S_DELETED ICON_CLASSIFIER_SYSTEM+5
#define ICON_CLASSIFIER_ELEMENT_M_ANALOGUE ICON_CLASSIFIER_SYSTEM+6
#define ICON_CLASSIFIER_ELEMENT_M_KIT ICON_CLASSIFIER_SYSTEM+7
#define ICON_CLASSIFIER_ELEMENT_S_ANALOGUE ICON_CLASSIFIER_SYSTEM+8
#define ICON_CLASSIFIER_ELEMENT_S_KIT ICON_CLASSIFIER_SYSTEM+9
#define ICON_FINAL_ITEM ICON_CLASSIFIER_SYSTEM+10
#define ICON_LSS_SYSTEM ICON_CLASSIFIER_SYSTEM+11
#define ICON_LSS_TASK	ICON_CLASSIFIER_SYSTEM+12
#define ICON_LSS_TASK_CHECK_OUT	ICON_CLASSIFIER_SYSTEM+13
#define ICON_LSS_TASK_DELETED	ICON_CLASSIFIER_SYSTEM+14
#define ICON_LSS_TASK_Z	ICON_CLASSIFIER_SYSTEM+15
#define ICON_LSS_TASK_Z_CHECK_OUT	ICON_CLASSIFIER_SYSTEM+16
#define ICON_LSS_TASK_Z_DELETED	ICON_CLASSIFIER_SYSTEM+17
#define ICON_LSS_FINAL_ITEM_TANK	ICON_CLASSIFIER_SYSTEM+18

#define ICON_APPR_INDEX					40
#define ICON_MSG_INDEX					60
#define ICON_DOC_INDEX					80
#define ICON_CHARACT_INDEX				100
#define ICON_INST_INDEX					120
#define ICON_ORGSTRUCT_INDEX			140
#define ICON_ALERT_INDEX				160
#define ICON_WF_INDEX					180
#define ICON_PRODUCT_INDEX				220
#define ICON_PRJ_INDEX					270
#define ICON_CONTINUE_INDEX				300
#define ICON_QUERY_INDEX				360
#define ICON_CONFIG_INDEX				400
#define ICON_STATICTREEITEMS_INDEX		420

#define ICON_MESSAGES ICON_MSG_INDEX+1
#define ICON_MESSAGES_LOST ICON_MSG_INDEX+3


#define ICON_APPROVAL	ICON_APPR_INDEX

#define ICON_DOCUMENT					ICON_DOC_INDEX
#define ICON_DOCUMENT_CHECKOUTED		ICON_DOCUMENT+2
#define ICON_DOCUMENT_REV				ICON_DOCUMENT+3
#define ICON_DOCUMENT_ACTIVE_REV		ICON_DOCUMENT+5
#define ICON_DOCUMENT_COPY				ICON_DOCUMENT+7
#define ICON_DOCUMENT_COPY_OUT_OF_DATE	ICON_DOCUMENT+8
#define ICON_DOCUMENT_MARKUP        	ICON_DOCUMENT+9
#define ICON_DOCUMENT_ACT				ICON_DOCUMENT+10
#define ICON_REQUIMENT					ICON_DOCUMENT+11
#define ICON_REQUIMENT_SEVERAL			ICON_DOCUMENT+12
#define ICON_REQUIMENT_NO_NEED			ICON_DOCUMENT+13
#define ICON_NOTE						ICON_DOCUMENT+14
#define ICON_NOTE_WITH_MARKUP			ICON_DOCUMENT+15
#define ICON_NOTE_EDIT					ICON_DOCUMENT+16

#define ICON_CHARACTERISTIC_GROUP ICON_CHARACT_INDEX
#define ICON_CHARACTERISTIC ICON_CHARACTERISTIC_GROUP+3

#define ICON_BP_RES		ICON_INST_INDEX
#define ICON_BP			ICON_BP_RES+1
#define ICON_BP_VERTICS	ICON_BP+4
#define ICON_BP_QM		ICON_BP_VERTICS+2
#define ICON_BP_INST	ICON_BP_QM+2
#define ICON_BP_INST_CO	ICON_BP_INST+2
#define ICON_REFUSAL	ICON_BP_INST_CO+4

#define ICON_LOT        ICON_PRODUCT_INDEX+1
#define ICON_PRD_INST   ICON_PRODUCT_INDEX+2
#define ICON_PROD       ICON_PRODUCT_INDEX+3

#define ICON_ZONE		ICON_PROD+1
#define ICON_SYSTEM		ICON_PROD+2
#define ICON_COMPONENT	ICON_PROD+3
#define ICON_MODULE		ICON_PROD+4
#define ICON_KOMPLEX    ICON_PROD+5
#define ICON_ASSEMBLY   ICON_PROD+6
#define ICON_PART       ICON_PROD+7
#define ICON_MATERIAL   ICON_PROD+8
#define ICON_KIT        ICON_PROD+9
#define ICON_OTHER      ICON_PROD+10

#define ICON_CHANGE   ICON_OTHER+1

#define ICON_PRD_DELTA_VERSION   30
#define ICON_PRD_DELTA_MATER     25
#define ICON_PRD_DELTA_MAKE      20
#define ICON_PRD_DELTA_ALTERNATE 15
#define ICON_PRD_DELTA_SUPLIED   10
#define ICON_PRD_DELTA_WHERE_USED 5


#define ICON_TASK            ICON_WF_INDEX+2
#define ICON_LOG_TASK        ICON_TASK+4
#define ICON_PROCESS         ICON_WF_INDEX+8
#define ICON_PROCESS_TMPL    ICON_WF_INDEX+10
#define ICON_ACTIVITY        ICON_WF_INDEX+11

#define ICON_PROJECT ICON_PRJ_INDEX+1

#define ICON_ORGANIZATION ICON_ORGSTRUCT_INDEX
#define ICON_OFFICIAL ICON_ORGANIZATION + 1
#define ICON_PERSON ICON_OFFICIAL + 1
#define ICON_ORGANIZATION_DELETE ICON_PERSON + 1 // удаленная организация

#define ICON_ALERT ICON_ALERT_INDEX


#define ICON_QUERYES ICON_QUERY_INDEX
#define ICON_FIND ICON_QUERYES+1
#define ICON_QUERY			ICON_QUERY_INDEX+2
#define ICON_QUERY_SAVED	ICON_QUERY+1
#define ICON_QUERY_N		ICON_QUERY+2
#define ICON_QUERY_N_SAVED	ICON_QUERY+3
#define ICON_QUERY_Q		ICON_QUERY+4
#define ICON_QUERY_Q_SAVED	ICON_QUERY+5
#define ICON_COMB_TABLE		ICON_QUERY+6
#define ICON_COMB_TABLE_SAVED	ICON_QUERY+7

#define ICON_FILE			ICON_COMB_TABLE_SAVED+1

#define ICON_OPTION			ICON_CONFIG_INDEX
#define ICON_OPTION_VALUE	ICON_CONFIG_INDEX+1
#define ICON_RULE			ICON_CONFIG_INDEX+2
#define ICON_BASIS			ICON_CONFIG_INDEX+3
#define ICON_CONFIG			ICON_CONFIG_INDEX+4

#define ICON_CLIPBOARD		ICON_STATICTREEITEMS_INDEX

///////////////////////
//definies для иконок//
///////////////////////

//////////////////////////////////////////////////////////////////////////////////////////////
//                                 definies для комбинированных иконок                      //
//////////////////////////////////////////////////////////////////////////////////////////////
#define ICO_REL_VER			1
#define ICO_REL_MATER		2
#define ICO_REL_MAKE		3
#define ICO_REL_ALTERNATE	4
#define ICO_REL_SUPLIED		5
#define ICO_REL_WHERE_USED	6
#define ICO_REL_ACTIVE_VER	7
#define ICO_REL_DEPEND_DOC	8
#define ICO_REL_WO_4NOTE	10
#define ICO_REL_RULE		11

#define ICO_EFF_NO			0
#define ICO_EFF_EFF			1
#define ICO_EFF_CON			2
#define ICO_EFF_EFFCON		3
#define ICO_EFF_NOT_USED	7
#define ICO_EFF_HIGH		8
#define ICO_EFF_NORMAL		9
#define ICO_EFF_LOW			10
#define ICO_EFF_LINK		14


#define ICO_STATE_WORKING 1
#define ICO_STATE_APPROVING 2
#define ICO_STATE_APPROVED 3
#define ICO_STATE_CHANGING 4
#define ICO_STATE_APPROVING_CHANGE 5
#define ICO_STATE_CANCELED 6
#define ICO_STATE_MUST_REVISION 7

#define ICO_SUBTYPE_NO 0
#define ICO_SUBTYPE_UNIFIED 1
#define ICO_SUBTYPE_HAS_REF 8


/////////////////////////////////////////////////////////////////////////////////////////////
//                                     конец                                                //
//////////////////////////////////////////////////////////////////////////////////////////////

#define APL_NOT_TEST_POSSIBLE_STATES 1

// Проверка корректности определения атрибута
#define CHECK_ZERO_ATTR(par1,par2) par1=par2;m_AllAttrDefined&=(par1!=0);
// Атрибут менеджера был задан некорректно. Чтобы у клиентов все не полетело
#define a_access_form a_apl_doc_rev_access_form


#ifdef APL_STEP_MGR_IMPL
#define CLASS_DECL_APL_STEP_MGR  _declspec(dllexport)
#else
#define CLASS_DECL_APL_STEP_MGR  _declspec(dllimport)
#endif


#define API_DLG_TEST if(m_api==0) {EndDialog(0); return FALSE;}

/** Преобразует строку состояния в индекс иконки*/
int AFX_EXT_API aplState2Ico(LPCTSTR state, int default_ico=-1);



/** Выводит диалог выбора точки во времени*/
bool AFX_EXT_API aplSelectDateTime(COleDateTime &odt, const TCHAR *title=0);

/** Выводит диалог выбора строкового значения */
bool AFX_EXT_API aplGetStringValue(CString &val);

/** Сортирует массив по дате или строковому атрибуту в указанном диапазоне
		@param m_data  указатель на кеш
		@param ext сортируемый экстент
		@param left	элемент, с которого экстент будет отсортирован
		@param right элемент, до которого экстент будет отсортирован
		@param date_attr атрибут, по которому будет сортировка
		@return true в случае успеха */
bool AFX_EXT_API aplSortByDate(CaplNetStepData* m_data, aplExtent &ext, int left, int right, CaplAttr* date_attr);
bool AFX_EXT_API aplSortByDate(CaplNetStepData* m_data, aplExtent &ext, int left, int right, CaplAttr* date_attr1, CaplAttr* date_attr2);

int AFX_EXT_API aplQFindInstInExtentByAttr(CaplNetStepData* m_data, aplExtent &ext, CaplAttr* attr, CaplValue *val, bool full_cycle = true);
/** Сортирует массив по любому атрибуту в указанном диапазоне
		@param m_data  указатель на кеш
		@param ext сортируемый экстент
		@param left	элемент, с которого экстент будет отсортирован
		@param right элемент, до которого экстент будет отсортирован
		@param attr атрибут, по которому будет сортировка
		@return true в случае успеха */
bool AFX_EXT_API aplQSortByAttr(CaplNetStepData* m_data, aplExtent &ext, int left, int right, CaplAttr* attr);
/** Сортирует массив по значению, полученному взятием цепочки 2 атрибутов подряд )в указанном диапазоне, например 
	сортировка pdf по значению product.id (pdf->of_product->id; первый атрибут должен иметь тип aplINSTANCE
		@param m_data  указатель на кеш
		@param ext сортируемый экстент
		@param left	элемент, с которого экстент будет отсортирован
		@param right элемент, до которого экстент будет отсортирован
		@param attr1 атрибут, по которому будет сортировка
		@param attr2 атрибут, по которому будет сортировка
		@return true в случае успеха */
bool AFX_EXT_API aplQSortByAttr(CaplNetStepData* m_data, aplExtent &ext, int left, int right, CaplAttr* attr1, CaplAttr* attr2);

/** Сортирует массив по значению нескольких атрибутов (не цепочки, а атрибутов элементов массива
		@param m_data  указатель на кеш
		@param ext сортируемый экстент
		@param attr1 первый атрибут, по которому будет сортировка
		@param attr2 второй атрибут, по которому будет сортировка (среди тех, у которых первый атрибут одинаковый)
		@param attr3 третий атрибут, по которому будет сортировка (среди тех, у которых первый и второй атрибут одинаковый)
		@param attr4 четвертый атрибут, по которому будет сортировка
		@param attr5 пятый атрибут, по которому будет сортировка
		@return true в случае успеха */
bool AFX_EXT_API aplQSortByMultiAttr(CaplNetStepData* m_data, aplExtent &ext, CaplAttr* attr1, CaplAttr* attr2=0, CaplAttr* attr3=0, CaplAttr* attr4=0, CaplAttr* attr5=0);


// Функция сравнивает 2 строки исходя из предположения, что в начале будет иерархия из цифр (например, в обозначении справочников)
int AFX_EXT_API aplCompare2StringAsClassifier(CString &str1, CString &str2);

/** 
	Возвращает путь к папке Мои документы
		@return путь к папке мои документы */
CString AFX_EXT_API GetMyDocPath();

CImageList AFX_EXT_API *aplGetInstImageList();
CImageList AFX_EXT_API *aplGetRelImageList();
CImageList AFX_EXT_API *aplGetEffImageList();
CImageList AFX_EXT_API *aplGetStateImageList();
CImageList AFX_EXT_API *aplGetObjStateImageList();
CImageList AFX_EXT_API *aplGetItemSubtypeImageList();
CImageList AFX_EXT_API *aplGetTabCtrlImageList();


#ifndef APL_NO_INSET_IN_DOC
// Просто служебный классик
class CaplOldSelInstItem
{
public:
	CaplOldSelInstItem(CaplOldSelInstItem *parent, CaplInstance *inst)
	{
		m_parent=parent;
		m_inst=inst;
		m_item=0;
	};
	CaplOldSelInstItem *m_parent;
	CaplInstance *m_inst;
	HTREEITEM m_item;
};

typedef CaplTAggr <CaplOldSelInstItem*, CaplOldSelInstItem*, APLAGGR_UNIQUE|APLAGGR_LIST|APLAGGR_AUTOKILLREF> TUAKListPCaplOldSelInstItem;
#endif

class CaplAPI;
class CDocCopyFilter;

//объявление саllback функции для selectinst
typedef bool (*fnValidateInst)(CaplAPI *, aplExtent&);
typedef bool (*fnValidateInst2)(CaplAPI *, aplExtent&, DWORD data);

/** Базовый класс высокоуровневого API*/
class CLASS_DECL_APL_STEP_MGR CaplStepManager
{
public:
	CaplStepManager(); /**<Конструктор */
	~CaplStepManager();

	// Attributes
	CaplNetStepData *m_data;
	CaplAPI *m_api;

	static void SaveGlobalParams();  // Сохраняет параметры не зависящие от приложения
	static void LoadGlobalParams();

#ifndef APL_NO_INSET_IN_DOC

	TUAKListPCaplOldSelInstItem m_old_items;
#endif

	//WFState
	
	CaplEntity *e_wf_state_history;
	CaplAttr *a_wf_new_state;
	CaplAttr *a_wf_old_state;
	CaplAttr *a_wf_date;
	CaplAttr *a_wf_item;
	CaplAttr *a_wf_user;

	//Notes
	CaplEntity *e_note;
	CaplAttr *a_note_item;
	CaplAttr *a_note_author;
	CaplAttr *a_note_date;
	CaplAttr *a_note_source;
	CaplAttr *a_note_descr;
	CaplAttr *a_note_parent;
	CaplAttr *a_note_markup;
	CaplAttr *a_note_date_revocation;
	CaplAttr *a_note_approval;
	CaplAttr *a_note_nohide;

	/**@name Флаги */
	//@{
	/** Флаг предписывющий автоматический вызов сохранения информации в БД (по умолчанию true)*/
	bool m_AutoSave;
	
	/** Флаг предписывющий автоматический вызов "стать владельцем" c вывовом SaveChanges при соотв. настройке работы с БД (по умолчанию true)*/
	bool m_AutoUsurpire;

	/** Флаг указывающий возможность работы в диалоговом режиме (по умолчанию true)*/
	//bool m_ModeInteractive; отменен 03.05.2006  вместо него нудно m_api->m_ModeInteractive

	static bool m_bUseVersions; /**<Использовать версии */

	/** Размер порции элементов читаемых за 1 прием*/
	int m_MaxItemsLoad;

	/** true указыват, что все атрибуты и entity определены корректно*/
	bool m_AllAttrDefined;
	
	/** true указыват, что требуется проверка уникальности*/
	bool m_TestUnique;

	/** указатель на переменную, позволяющую прервать текущую операцию*/
	bool *m_bContinue;

	//@}


	/**@name Контекст (элементы словаря) */
	//@{
	CaplEntity *e_pd_context; /**<product_definition_context */
	CaplAttr *a_pd_context_name;/**<product_definition_context -> name */
	CaplAttr *a_pd_context_life_cycle_stage;/**<product_definition_context -> life_cycle_stage */
	//@}

	/**@name Пользователь (элементы словаря)  - см CaplAutorizationManager */ 
	//@{
//	CaplEntity *e_user;		/**<apl_user */
//	CaplAttr *a_user_name;	/**<apl_user -> name */
//	CaplAttr *a_user_po;	/**<apl_user -> personality */
	//@}

	/**@name Аналоги (элементы словаря) */
	//@{
	CaplEntity *e_alt_bidir;					/**<alternate_product_relationship_bidirect */
	CaplAttr *a_alt_bidir_type;					/**<alternate_product_relationship_bidirect -> type */
	CaplAttr *a_alt_bidir_type_descr;			/**<alternate_product_relationship_bidirect -> type_descr */
	CaplAttr *a_alt_bidir_reserved;				/**<alternate_product_relationship_bidirect -> reserved */
	CaplAttr *a_alt_base_pdf;					/**<alternate_product_relationship_bidirect -> base_pdf */
	CaplAttr *a_alt_alt_pdf;					/**<alternate_product_relationship_bidirect -> alt_pdf */
	CaplAttr *a_alt_alt_interchange_type;		/**<alternate_product_relationship_bidirect -> interchange_type */
	//@}

	// Methods
	/** Инициализирует класс (Ассоциация с классом базы данных) 
	    @return true при удачном выполнении и false в случае ошибки */
	virtual bool Attach(CaplAPI *api);
	virtual void Detach(); /**Удаляет ассоциацию с источником данных< */
	

	/** Выводит дерево выбора объекта 
		@param  SelectMode  значение определяющее типы данных которые можно выбрать 
				
		  APL_MODE_SELECT_CATEGORY			- можно выбирать категорию<br>
		  APL_MODE_SELECT_FOLDER			- можно выбирать папку<br>
		  APL_MODE_SELECT_PRD				- можно выбирать  изделие<br>
		  APL_MODE_SELECT_PDF				- можно выбирать версию изделия<br>
		  APL_MODE_SELECT_DOC				- можно выбирать документ<br>
		  APL_MODE_SELECT_BP				- можно выбирать бизнес-процесс<br>
		  APL_MODE_SELECT_CHARACT			- можно выбирать хар-ки<br>
		  APL_MODE_SELECT_CHARACT_REVISION	- можно выбирать версии хар-к<br>
		  APL_MODE_SELECT_DOC_REVISION		- можно выбирать версии документов<br>
		  APL_MODE_SELECT_BP_REVISION		- можно выбирать версии бизнес-процессов<br>
		  APL_MODE_SELECT_CATEG_REVISION	- можно выбирать версии бизнес-процессов<br>
		  APL_MODE_SELECT_ORG				- можно выбирать рабочую группу<br>
		  -- APL_MODE_SELECT_PERSON			- сотрудника выбирать нельзя, для них специальный диалог<br>
		  -- APL_MODE_SELECT_PERSORG		- связь сотрудника и рабочей группы выбирать нельзя, для них специальный диалог<br>

		@param  title  заголовок окна выбора 
		@param  base_items  объекты верхнего уровня 
		
		@return выбранный объект 	*/
	CaplInstance *SelectInstance(long SelectMode, const TCHAR *title=0, aplExtent *base_items=0, fnValidateInst fn = NULL);
	CaplInstance *SelectInstanceEx(long SelectMode, const TCHAR *title=0, aplExtent *base_items=0, fnValidateInst fn = NULL);
	bool SelectInstanceEx(long SelectMode, aplExtent &res, const TCHAR *title=0, aplExtent *base_items=0, fnValidateInst fn = NULL);
	CaplInstance *SelectInstanceEx2(long SelectMode, const TCHAR *title=0, aplExtent *base_items=0, fnValidateInst2 fn = NULL, DWORD data = NULL);
	bool SelectInstanceEx2(long SelectMode, aplExtent &res, const TCHAR *title=0, aplExtent *base_items=0, fnValidateInst2 fn = NULL, DWORD data = NULL);
	
	// Выводит диалог редактирования списка объектов
	// SelectMode как в SelectInstance
	// ext - список объектов
	// title - заголовок окна
	// list title - заголовок списка
	// sprav - справочник, если не 0, то бобавляется из указанного справочника
	// возвращает true, если была нажата "OK", и false, если "Отмена"
	bool EditExtent(long SelectMode, aplExtent &ext, const TCHAR *title=0, const TCHAR *list_title=0, CaplInstance *sprav=0);

	#define APL_MODE_SELECT_CATEGORY			0x00000001
	#define APL_MODE_SELECT_FOLDER				0x00000002
	#define APL_MODE_SELECT_PRD					0x00000004
	#define APL_MODE_SELECT_PDF  				0x00000008
	#define APL_MODE_SELECT_DOC  				0x00000010
	#define APL_MODE_SELECT_BP					0x00000020
	#define APL_MODE_SELECT_LOT					0x00000040
	#define APL_MODE_SELECT_PRDINST				0x00000080
	#define APL_MODE_SELECT_DOC_REVISION		0x00000100
	#define APL_MODE_SELECT_BP_REVISION			0x00000200
	#define APL_MODE_SELECT_CATEG_REVISION		0x00000400
	#define APL_MODE_SELECT_PROJECT				0x00000800
	
	#define APL_MODE_SELECT_ORG					0x00001000
	#define APL_MODE_SELECT_PERSORG				0x00002000
	#define APL_MODE_SELECT_PERSON				0x00004000
	#define APL_MODE_SELECT_OFFICIAL			0x00008000
	#define APL_MODE_SELECT_BPINST				0x00010000   // И неисправность, т.к. биты закончились
	#define APL_MODE_SELECT_CHANGE				0x00020000
	#define APL_MODE_SELECT_CLASSIF_SYSTEM		0x00040000
	#define APL_MODE_SELECT_CLASSIF_ELEMENT		0x00080000
			
	#define APL_MODE_SELECT_CHARACT				0x00100000
	#define APL_MODE_SELECT_CHARACT_REVISION	0x00200000
	#define APL_MODE_SELECT_USER				0x00400000
	#define APL_MODE_SELECT_USER_GROUP			0x00800000
	#define APL_MODE_SELECT_BP_RES				0x01000000
	#define APL_MODE_SELECT_ORDER				0x02000000
	#define APL_MODE_SELECT_REQUIREMENT			0x04000000

	#define APL_MODE_SELECT_DBLCLICK			0x08000000  //выбирает объект по двойному клику 

	#define APL_MODE_SELECT_MULTY				0x10000000
	#define APL_MODE_HIDE_TOOLBAR				0x20000000	// не показывать тулбар
	#define APL_MODE_HIDE_ASSOCIATED_DOCS		0x40000000	// не показывать ассоциированные документы
	#define APL_MODE_NO_RESTORE					0x80000000	// заново раскрывать корневые элементы

	/** Возвращает в буфер строку идентифицирующую item 
	    @return true при удачном выполнении и false в случае ошибки */
	bool GetItemName(CaplInstance * item, CString &buf);

	/** Чтение в кэш данных обо всех объектах, содержащихся в ext 
	    @return true при удачном выполнении и false в случае ошибки */
	bool LoadExtentInfo(aplExtent &ext);

	/**@name Работа с контекстами */
	//@{

	/** Чтение в кэш данных о контекстах  
	    @return true при удачном выполнении и false в случае ошибки */
	bool LoadContextInfo();

	/** Выбор контекстов для объекта  
		Отображает диалог выбора контекстов
	    @return true при удачном выполнении и false в случае ошибки */
	bool ChangeItemContext(aplExtent &ext);

	/** Разбивает строку на части, разделенные devider */
	void Split(const CString &str, CString devider, std::vector<CString> &result, bool bParseAsCsv = false);

	/** Записывает в строку список контекстов объекта  
	    @return true при удачном выполнении и false в случае ошибки */
	bool PrintItemContextInString(CaplInstance *item,CString &buf);

	/** Записывает в строку список контекстов из aggr  
	    @return true при удачном выполнении и false в случае ошибки */
	bool PrintItemContextInString(aplExtent &ext,CString &buf);

	/** Проверяет находится ли item в контексте  context 
	    @return true если находится и false если нет */
	bool IsItemInContext(CaplInstance *item, CaplInstance *context, CaplAttr *attr=0);
	
	/** Фильтрует extent ext_in по списку  контекстов ext_context.
		attr - атрибут с контекстами, читаемый у элементов ext_in.
		Результат возвращается в ext_out.
	    @return true при удачном выполнении и false в случае ошибки */
	bool FilterExtentByContext(aplExtent &ext_in, aplExtent &ext_contexts, aplExtent &ext_out, CaplAttr *attr=0);
	//@}
	
	/** Проверяет, является ли текущий пользователь администратором 
	    @return true если является и false если нет */
	bool IsAdmin();
	
	/** Проверяет, является ли пользователь администратором 
		@param bIsSystemAdmin - возвращает true, если указанная уч. запись = системной записи админа для БД
	    @return true если является и false если нет */
	bool IsAdmin(CaplInstance* pUser, bool* bIsSystemAdmin=NULL);
	
/** Возвращает группу администраторов
		@param bLoadFromDB - загружать ли данные о группах из БД
	    @return группу или NULL, если не найдена */
	CaplInstance* GetAdminGroup(bool bLoadFromDB=false);

	/** Возвращает группу "all" (все пользователи)
		@return группу, если группа не найдена, она будет создана */
	CaplInstance* GetAllUsersGroup();

	/**Возвращает пользователя, который ассоциирован с текущим пользователем
		@return пользователя или NULL, если с пользователем нет ассоциации*/
	CaplInstance* GetCurrentPerson();

	/**Возвращает доступные статусы, типы документов и контексты для текущего пользователя.
	   @param status - значения доступных статусов (out)
	   @param doc_types - значения доступных типов документов (out)
	   @param contexts - значения доступных контекстов (out)
	   @return true - в случае успешного завершения и false в случае ошибки*/
	
	/** Меняет состояние объекта
		@param inst объект (документ, версия изделия и бизнес процесс)
		@param nState новое состояние
		@param flag Если 0, то переводит, если можно, если равно APL_NOT_TEST_POSSIBLE_STATES, то переводит без проверки
		@return новый объект истории состояний объекта*/
	CaplInstance* ChangeWFState(CaplInstance *inst, const TCHAR *nState, UINT flag = 0);

	/** Меняет состояние объекта. Предыдущее состояние не учитывает. Требует администраторских привилегий. 
		@param ext список объектов (документ, версия изделия и бизнес процесс)*/
	bool ChangeWFState(aplExtent &ext);
	
	/** Возвращает доступные состояния, в которые можно перевести объект
		@param inst объект (документ, версия изделия и бизнес процесс)
		@param states список состояний
		@return текущее состояние объекта*/
	CString GetPossibleWFState(CaplInstance *inst, CStringArray &states);

	/** Возможные состояния для изделий в разрезе работы с маршрутными картами */
	CString TranslateMkState(const CString &state);

	/** Показывает историю состояний объекта
		@param inst объект (документ, версия изделия и бизнес процесс)*/
	bool ShowWFStateHistory(CaplInstance *inst);

	/**	Возвращает ниаменование статуса по внутреннему имени
		@param state внутреннее имя состояния
		@return Наименование состояния*/
	static CString GetWFStateName(CString state);
	
	/**	Возвращает ниаменование статуса по внутреннему имени
		@param state внутреннее имя состояния
		@return Наименование состояния*/
	static CString GetWFStateNameEng(CString state);

	/**	Создает примечание для объекта
		@param inst объект для которого создается примечание
		@param parent примечание с которым будет связано новое примечание
		@return true при успешном создании примечания и false  в случае ошибки*/
	bool CreateNote(CaplInstance *inst, CaplInstance *parent = NULL, CaplInstance **ciNote = NULL);
	
	/**	Показывает примечания объекта
		@param inst объект
		@param ciNote если нужно сразу выделить какое то замечание
		@reurn true при успешном выполнении функции и false в случае ошибки*/
	bool ShowNotes(CaplInstance *inst, CaplInstance *ciNote=NULL, bool bShowTree=true);

	/**	Показывает примечание объекта
		@param ciNote замечание
		@reurn true при успешном выполнении функции и false в случае ошибки*/
	bool ShowNote(CaplInstance *ciNote, bool bReadOnly=true);

	// Удалить примечание
	bool DeleteNote(CaplInstance *ciNote);

	/**	Поиск ассоциированых примечаний
		@param inst объект для которого ищутся связанные примечания
		@paran notes ассоциированые примечания*/
	bool FindAssociatedNotes(CaplInstance *inst, aplExtent &notes);
	
	/**	Записывает в CaplRichEditCtrl текст примечаний связаный с объектом
		@param richedit указатель на CaplRichEditCtrl
		@param inst объект
		@return true при успешном выполнении и false в случае ошибки*/
	bool SetRTFToRichEdit(CaplRichEditCtrl *richedit, CaplInstance *inst);
	
	CaplInstance* FindContextByName(LPCTSTR sName);

	bool GetListTopLevelEntities(TUListPEntity &list_entities);


public:

	CaplEntity* e_apl_object_locker;
	CaplAttr* a_apl_object_locker_item; // кого залочили
	CaplAttr* a_apl_object_locker_user; // кто залочил
	CaplAttr* a_apl_object_locker_description; // описание


	/**	Ищет блокиратор для инстанса
	@param pInst проверяемый инстанс
	@return NULL если не нашли*/
	CaplInstance* FindLockInstance(const CaplInstance* pInst);

	/**	Проверяет заблокировн ли инстанс для редактирования
	@param pInst проверяемый инстанс
	@return true при заблокированности*/
	bool IsInstanceLocked(const CaplInstance* pInst);

	/**	Блокирует инстанс
	@param pInst блокируемый инстанс
	@param pUser пользователь
	@param message описание лока
	@return Указатель на созданный инстанс при успехе*/
	CaplInstance* SetInstanceLocked(const CaplInstance* pInst, const CaplInstance* pUser, const CString& description = _T("")  );

	/**	Разблокирует инстанс
	@param pInst блокируемый инстанс
	@return Указатель на созданный инстанс при успехе*/
	bool SetInstanceUnLocked(const CaplInstance* pInst );

	/**	Получает информацию о заблокированном инстансе
	@param pInst инстанс
	@param pUser пользователь
	@param message причина лока
	@return true при успехе*/
	bool GetLockInfo(const CaplInstance* pInst, CaplInstance** ppUser, CString *pDescription /* = NULL */ );

};

// *************************************************************************
// *************************************************************************
// не добавляйте здесь комментарии!!
/** Менеджер категорий*/
class CLASS_DECL_APL_STEP_MGR CaplCategoryManager: public CaplStepManager
{
public:
	/** Инициализирует класс (Ассоциация с классом базы данных) 
		@return true при удачном выполнении и false в случае ошибки */
	virtual bool Attach(CaplAPI *api);
	virtual void Detach();

	// Attributes

	/**@name product_category (элементы словаря) */
	//@{
	CaplEntity *e_categ;				/**<product_category */
	CaplAttr *a_categ_id;				/**<product_category -> id */
	CaplAttr *a_categ_name;				/**<product_category -> name */
	CaplAttr *a_categ_descr;			/**<product_category -> description */
	CaplEntity *e_prd_rel_prd_categ;	/**<product_related_product_category */
	CaplAttr *a_categ_products ;		/**<product_related_product_category -> products */
	CaplAttr *a_categ_charact;			/**<product_related_product_category -> characteristics*/
	CaplAttr *a_categ_all_charact;		/**<product_related_product_category -> all_characteristics*/
	//@}

	/**@name product_category_relationship (элементы словаря) */
	//@{
	CaplEntity *e_categ_rel;			/**<product_category_relationship */
	CaplAttr *a_categ_rel_category;		/**<roduct_category_relationship -> category */
	CaplAttr *a_categ_rel_sub_category; /**<product_category_relationship -> sub_category */
	//@}

	/**@name Изменения (элементы словаря) */
	//@{
	// Изменения
	CaplEntity *e_apl_product_category_ver; /**<apl_product_category_version */
	CaplAttr *a_categ_ver_categ;			/**<apl_product_category_version -> category */
	CaplAttr *a_categ_ver_id;				/**<apl_product_category_version -> id */
	CaplAttr *a_categ_ver_name;				/**<apl_product_category_version -> name */
	CaplAttr *a_categ_ver_descr;			/**<apl_product_category_version -> description */
	CaplAttr *a_categ_ver_products;			/**<apl_product_category_version -> products */
	CaplAttr *a_categ_ver_author;			/**<apl_product_category_version -> author */
	CaplAttr *a_categ_ver_start;			/**<apl_product_category_version -> start_date */
	CaplAttr *a_categ_ver_end;				/**<apl_product_category_version -> end_date */
	CaplAttr *a_categ_ver_num;				/**<apl_product_category_version -> number */
	CaplAttr *a_categ_ver_prev;				/**<apl_product_category_version -> previous */
	CaplAttr *a_categ_act;					/**<product_category -> active_version */
	CaplAttr *a_categ_lock;					/**<product_category -> locker */
	//@}
	
	CaplEntity* e_categ_content;
	CaplAttr* a_categ_content_id;
	CaplAttr* a_categ_content_content;
	CaplAttr* a_local_query_name;

	CaplEntity* e_local_query;
	CaplAttr* a_local_query_text;
	CaplAttr* a_local_query_person;
	CaplAttr* a_local_query_date;

	// Методы
public:

	/** Читает информацию о всех категориия в кэш клиента  
		@param load_products - true, ecли необходимо скачивать входящие в категории изделия
		@return true при удачном выполнении и false в случае ошибки */
	bool Load(bool load_products=false);

	/** Читает информацию о конкретной категориии в кэш клиента  
		@param bLoadPrdInfo - true, если необходимо скачивать в кэш обозначение и наименование изделий*/
	bool LoadCategoryInfo(CaplInstance *categ, bool bLoadPrdInfo= false);
	
	/** Читает информацию о категориях в ext в кэш клиента  
		@param bLoadPrdInfo - true, если неоходимо скачивать в кэш обозначение и наименование изделий*/
	bool LoadCategoryInfo(aplExtent &ext, bool bLoadPrdInfo= false);

	/** Возвращает категорию в базе ее по обозначению или NULL если такой категории нет   */
	CaplInstance *FindCateg(const TCHAR *id);


	/**@name Структура категорий */
	//@{
	// **************************************************
	// Структура категорий
	// **************************************************

	//*************************************************************
	/** Возвращает возвращает в ext все входящие в categ категории
		@param categ исходная категория. Если categ == 0 , то возвращается верхний уровень
		@param ext экстент для записи результата
		@param recursive надо ли возвращать все категории на всех уровнях
		@param load_prd надо ли читать в память список содержащихся в категориях изделий
		@return true при удачном выполнении и false в случае ошибки */
	bool GetAllSubCategory(CaplInstance *categ, aplExtent &ext, bool recursive=false, bool load_prd=false);
	
	/** Возвращает возвращает в ext все входящие в categ категории
		@param categ исходная категория. Если categ == 0 , то возвращается верхний уровень
		@param ext экстент для записи результата
		@param rel экстент для записи связей
		@param recursive надо ли возвращать все категории на всех уровнях
		@param load_prd надо ли читать в память список содержащихся в категориях изделий
		@return true при удачном выполнении и false в случае ошибки */
	bool GetAllSubCategory2(CaplInstance *categ, aplExtent &ext, aplExtent &rels, bool recursive=false, bool load_prd=false);
	
	/** возвращает в ext все категории в которые входит categ 
		@return true при удачном выполнении и false в случае ошибки */
	bool GetAllParentCategory(CaplInstance *categ, aplExtent &ext);

	/** вставляет категорию sub в категорию base 
		@return true при удачном выполнении и false в случае ошибки */
	bool InsertSubCategory(CaplInstance *base, CaplInstance *sub);

	/** удаляет категорию sub из категории base 
		@return true при удачном выполнении и false в случае ошибки */
	bool RemoveSubCategory(CaplInstance *base, CaplInstance *sub);

	/** создает категорию 
		@param id обозначение категории
		@param descr описание категории
		@return созданная категория или NULL в случае ошибки */
	CaplInstance *CreateCategory(const TCHAR *id, const TCHAR *name, const TCHAR *descr);

	/** Читает атрибуты категории  
		@param id буффер для обозначение категории
		@param name буффер для наименование категории
		@param descr буффер для описания категории
		@return true при удачном выполнении и false в случае ошибки */
	bool GetCategoryAttr(CaplInstance *categ, CString &id, CString &name, CString &descr);

	/** уничтожает категорию и все ее связи 
		@return true при удачном выполнении и false в случае ошибки */
	bool RemoveCategory(CaplInstance *categ);

	/** Перестройка корневых категорий
		@return true при удачном выполнении и false в случае ошибки
		*/
	bool RefreshRootCategories();
	//@}

	/**@name Ассоциация с изделиями */
	//@{

	// **************************************************
	// Ассоциация с изделиями
	// **************************************************

	/** Возвращает в ext все изделия входящие в categ
		Если all==true => рекурсивно просматриваются все входящие катгории 
		@param bLoadPrdInfo - true, если неоходимо скачивать в кэш обозначение и наименование изделий
		@return true при удачном выполнении и false в случае ошибки */
	bool GetCategoryContents(CaplInstance *categ, aplExtent &ext, bool all=false, bool bLoadPrdInfo= false);


	/** Отображает содержимое категории в види таблицы
		@param categ категория
		@param is_hide_move_button
		@param redraw
		@return true при удачном выполнении и false в случае ошибки */	
	bool MakeTable(CaplInstance *categ,bool is_hide_move_button=true,bool *redraw=0);

	/** Возвращает true, если prd находится в categ
		Если all==true => рекурсивно просматриваются все входящие катгории */
	bool FindProductInCategory(CaplInstance *prd, CaplInstance *categ,bool all=false);

	/** добавляет prd в categ 
		@return true при удачном выполнении и false в случае ошибки */
	bool AddPrdToCategory(CaplInstance *prd, CaplInstance *categ,bool bLoadCategInfo=true);

	/** удаляет prd из categ 
		@return true при удачном выполнении и false в случае ошибки */
	bool RemovePrdFromCategory(CaplInstance *prd, CaplInstance *categ,bool bLoadCategInfo=true);

	/** возвращает в ext все категории, куда входит prd 
		@return true при удачном выполнении и false в случае ошибки */
	bool GetProductCategories(CaplInstance *prd, aplExtent &ext);
	
	/** Выводит историю категории
		@param categ исходная категория. 
		@return true при удачном выполнении и false в случае ошибки */
	bool CategoryHistory(CaplInstance *categ);

	//@}
	
	/**@name Блокировка */
	//@{

	// **************************************************
	// Блокировка
	// **************************************************
	
	/** Взять категорию на редактирование */
	bool CheckOut( CaplInstance *categ);

	/** Завершить  редактирование категори  */
	bool CheckIn( CaplInstance *categ,bool make_new_version_active=true);

	/** Проверяет наличие блокировки и если такая есть возвращает на нее ссылку */
	CaplInstance *GetLock(CaplInstance *categ, bool bShowMessages);

	/** Проверяет наличие блокировки текущим пользователем, и если такая есть возвращает на нее ссылку */
	CaplInstance *CheckMyLock(CaplInstance *categ, bool bShowMessages);

	/** Отменить редактирование */
	bool UndoCheckOut( CaplInstance *categ);

	/** Возвращает все версии категории 
		@param categ категория
		@param outExt  список версий категории (результат)
		@return true при удачном выполнении и false в случае ошибки */
	bool GetAllCategoryVersion(CaplInstance *categ,aplExtent &outExt);

	/** Возвращает все изделия которые входят в категорию и ее подкатегории.
		@param categ - категория
		@param inExt - список продуктов (возвращает список не вошедших продуктов);
		@param outExt - пустой список (возвращает список вошедших в категорию продуктов)
		@return 1 - если все продукты найдены, 0 если в категории только часть продуктов из списка.*/
	int IsProductsInCategory(aplExtent &categ, aplExtent &inExt, aplExtent &outExt);
	
	/** Создает новыю версию категории на основе объекта "категория" или другой версии категории
		@param categ категория или версия категории
		@param num обозначение создаваемой версии
		@param make_active делать созданную версию активной или нет
		@return ссылку на созданную категорию и 0 в случае ошибки */
	CaplInstance *CaplCategoryManager::CreateCategoryVersion(CaplInstance *categ,CString num,bool make_active=true);
	/** Делает версию категории активной
		@param categ версия бизнес-процесса 
		@return true при удачном выполнении и false в случае ошибки */
	bool MakeCategoryVersionActive(CaplInstance *categ_ver);
	//@}
};


// *************************************************************************
// *************************************************************************
// *************************************************************************
/** Менеджер документов*/
#define APL_DOC_DEPENDENCE _T("depend")
#define APL_DOC_RELATION _T("relation")
#define APL_DOCUMENT_RELATION 1
#define APL_DOCUMENT_DEPENDENCE 2

#define APL_SETACTIVEVER 1

#define APL_COPY_DOCS 0
#define APL_CHECKOUT_DOCS 1
#define APL_PRINT_DOCS 2

#define APL_SHOW_REV_HISTORY 0
#define APL_SHOW_OWNER_HISTORY 1

class CDocCopyFilter
{
public:
	CDocCopyFilter() {m_id=_T("");m_doc=0;m_owner=0;m_place_of_use=0;m_state=_T("используется");m_date_begin=_T("");m_date_end=_T("");m_b_only_out_of_order=true;};
	~CDocCopyFilter(){};
	CString m_id;
	CaplInstance *m_doc;
	CaplInstance *m_owner;
	CaplInstance *m_place_of_use;
	CString m_state;
	CString m_date_begin;
	CString m_date_end;
	BOOL m_b_only_out_of_order;
};
class mymsiMap;
class CLASS_DECL_APL_STEP_MGR CaplDocManager: public CaplStepManager
{
	// Инициализация
private:
	BOOL m_lastflag;
public:
	/** Инициализирует класс (Ассоциация с классом базы данных) 
		@return true при удачном выполнении и false в случае ошибки */
	virtual bool Attach(CaplAPI *api);
	virtual void Detach();

	static BOOL m_bUseAplMarkView;

	// Attributes
protected:
	BOOL GetLastFlag();
	aplExtent m_service_ext;
	bool m_service_ext_lock;
public:	
	CaplEntity *e_apl_doc_ref;					///< Ассациация документа с объектом 
	CaplAttr *a_apl_doc_ref_item;				///< Объект
	CaplAttr *a_apl_doc_ref_inner_label;		///< Метка (ставится и спользуется в софте)
	CaplAttr *a_apl_doc_ref_doc;				///< Документ
	CaplAttr *a_apl_doc_ref_src;				
	CaplAttr *a_doc_rel_frames_of_reference;	///< Контексты
	CaplAttr *a_apl_doc_ref_type;				///<Тип связи объектов
	CaplAttr *a_apl_doc_ref_start_date;				///<Тип связи объектов
	CaplAttr *a_apl_doc_ref_end_date;	

	CaplEntity *e_doc;					///< Документ
	CaplAttr *a_doc_id;					///< Обозначенеие документа
	CaplAttr *a_doc_name;				///< Наименование документа
	CaplAttr *a_doc_descr;				///< Описание документа
	CaplAttr *a_doc_kind;				///< Вид документа
	CaplAttr *a_doc_code;				///< Код документа
	CaplAttr *a_doc_authentic;			///< Признак аутентичности документа
	CaplAttr *a_doc_add_dt_code;		///< Дополнительный код вида документа
	CaplAttr *a_doc_code_depend_desp;	///< Код документа в зависимости от характера использования
	CaplAttr *a_doc_struct_kind;		///< Тип структуры документа
	CaplAttr *a_doc_incl_in_doc;		///< Включать в документацию
	CaplAttr *a_doc_format;				///< Формат
	CaplAttr *a_doc_sheets;				///< Листы
	CaplAttr *a_doc_total_sheets_count;	///< Листов
	CaplAttr *a_doc_total_sheets_count_a4;	 ///< Листов приведенные к формату А4
	CaplAttr *a_doc_litera;				///< Литера
	CaplAttr *a_doc_part;				///< Часть
	CaplAttr *a_doc_accept_archive_date;	///< Дата принятия в архив
	CaplAttr *a_doc_released_by;			///< Кем выпущен
	CaplAttr *a_doc_accept_approval;		///< Подпись о приеме в сектор КД
	CaplAttr *a_doc_pdf_code;				///< Шифр изделия
	CaplAttr *a_doc_is_dublicate;			///< Является дубликатом
	CaplAttr *a_doc_dublicate_inv_num;		///< Инвентарный номер дубликата
	CaplAttr *a_doc_subst_inv_num;			///< Взамен инвентарного номера
	CaplAttr *a_doc_inv_num;				///< Инвентарный номер
	CaplAttr *a_doc_mail_list;				///< Список рассылки
	CaplAttr *a_doc_src_item;				///< Ссылка на исходный объект (для ИИ - изменение)
	CaplAttr *a_doc_guid;	
	CaplAttr *a_doc_external_ref;           ///< Обозначение для внешней ссылки
	CaplAttr *a_doc_group;                  ///< Является групповым

	CaplAttr *a_doc_from;		// Автор
	CaplAttr *a_doc_to;			// Получатель  (заменен на a_doc_recipients)
	CaplAttr *a_doc_recipients;	// Получатели
	CaplAttr *a_doc_urgency;						// Срочность
	CaplAttr *a_doc_date;							// Дата 
	CaplAttr *a_doc_date_of_execution_required;		// Дата исполнения требуемая
	CaplAttr *a_doc_of_execution_planned;			// Дата исполнения плановая
	CaplAttr *a_doc_of_execution_fact;				// Дата исполнения фактическая


	CaplEntity *e_dt;				///< Вид документа
	CaplAttr *a_dt_pdt;				///< Наименование вида документа
	CaplAttr *a_dt_id;				///< Обозначение вида документа
	CaplAttr *a_dt_entries; 		///< Реквизиты конкретного документа
	CaplAttr *a_dt_sort_num;		///< Номер при сортировке
	CaplAttr *a_dt_auth_formats;	///< Разрешенные форматы
	CaplAttr *a_dt_basis;			///< Стандарт
		
	CaplEntity *e_dt_entry;			///< Реквизит документа
	CaplAttr   *a_dt_entry_opt;		///< Определяет является ли реквизит обязательным
	CaplAttr   *a_dt_entry_status;	///< Набор статусов, связанных с реквизитом
	CaplAttr   *a_dt_entry_entry;	///< Ссылка на реквизит

	CaplEntity *e_doc_entry_val;		///< Значение реквизита документа
	CaplAttr   *a_doc_entry_val_val;	///< Значение
	CaplAttr   *a_doc_entry_val_prev;	///< Предыдущее значение реквизита
	CaplAttr   *a_doc_entry_val_entry;	///< Реквизит
	CaplAttr   *a_doc_entry_val_stored; ///< Привязан ли реквизит к подписям
	CaplAttr   *a_doc_entry_val_descr;	///< Описание

	CaplEntity *e_entry;			// реквизит
	CaplAttr   *a_entry_id;			// обозначение реквизита
	CaplAttr   *a_entry_name;		// наименование реквизита
	CaplAttr   *a_entry_descr;		// описание реквизита
	CaplAttr   *a_entry_basis;		// нормативный документ вводящий реквизит
	CaplAttr   *a_entry_val;		// значения реквизита
	CaplAttr   *a_entry_card_field; // что заполняется в карту

	CaplEntity *e_apl_doc;			///< Документ PSS
	CaplAttr *a_apl_doc_wf_state;
	CaplAttr *a_apl_doc_active;		///< Активная версия документа
	CaplAttr *a_apl_doc_lock;		///< Блокировка документа
	CaplAttr *a_apl_doc_system;		///< Cистема создавшая документ
	CaplAttr *a_apl_doc_inner_label;		///< Метка (ставится и спользуется в софте)
	CaplAttr *a_apl_doc_reg_num;	///< Регистрационный номер (Используется в журнале нормоконтроля)
	CaplAttr *a_apl_doc_reg_type;	///< Тип (КД, ТД, НД) используется в журнале нормоконтроля
	CaplAttr *a_ils_doc_type;		///< Вид документа(ссылка на классификатор)

	CaplEntity *e_apl_doc_rev;		///< Версия документа
	CaplAttr *a_apl_doc_rev_id;		///< Обозначенеие версия документа
	CaplAttr *a_apl_doc_rev_doc;	///< Ссылка на документ
	CaplAttr *a_apl_doc_rev_label;
	CaplAttr *a_apl_doc_rev_format;
	CaplAttr *a_apl_doc_rev_litera;
	CaplAttr *a_apl_doc_rev_descr;
	CaplAttr *a_apl_doc_rev_crc;
	CaplAttr *a_apl_doc_rev_base;
	CaplAttr *a_apl_doc_rev_start_s;
	CaplAttr *a_apl_doc_rev_end_s;
	CaplAttr *a_apl_doc_rev_user;
	CaplAttr *a_apl_doc_rev_autor;
	CaplAttr *a_apl_doc_rev_edit_path;
	CaplAttr *a_apl_doc_rev_access_form;
	CaplAttr *a_apl_doc_rev_char_val_versions;
	CaplAttr *a_apl_doc_rev_pictures;
	CaplAttr *a_apl_doc_rev_entries;
	CaplAttr *a_apl_doc_rev_sheets;				///< Листы документа
	CaplAttr *a_apl_doc_rev_total_sheets;		///< Общее количество листов документа
	CaplAttr *a_apl_doc_rev_total_sheets_count_a4;	 ///< Листов приведенные к формату А4
	CaplAttr *a_apl_doc_rev_src_doc_ver;		///< Версия исходного документа из которой получена текущая
	CaplAttr *a_apl_doc_rev_inner_label;		///< Метка (ставится и спользуется в софте)
	CaplAttr *a_apl_doc_rev_it_needs_work;		/// флаг - Требует пересмотра

	CaplAttr *a_apl_doc_rev_src_author;
	CaplAttr *a_apl_doc_rev_src_date;
	CaplAttr *a_apl_doc_rev_language;
	CaplAttr *a_apl_doc_rev_stored_on; ///< имя компьютера, на котором была сохранена версия документа для редактирования 

	CaplAttr *a_apl_doc_rev_gen_by_software;
	CaplAttr *a_apl_doc_rev_lss_dic_ver;

	CaplEntity *e_apl_digital_document;

	CaplEntity *e_apl_stored_document;
	CaplAttr *a_apl_stored_document_file_name, *a_apl_stored_document_source;
	CaplAttr *a_apl_stored_document_code;

	CaplEntity *e_apl_assigned_document;
	CaplAttr *a_apl_assigned_document_location_path;

	CaplEntity *e_apl_doc_change;
	CaplAttr *a_apl_doc_change_id,*a_apl_doc_change_name,*a_apl_doc_change_descr,*a_apl_doc_change_user,*a_apl_doc_change_person;
	CaplAttr *a_apl_doc_change_doc,*a_apl_doc_change_old,*a_apl_doc_change_new,*a_apl_doc_change_date_s;
	CaplAttr *a_apl_doc_change_attachment, *a_apl_doc_change_basis;

	CaplEntity *e_dt_group;			///< Группа типов документа
	CaplAttr *a_dt_group_id;		///< Обозначение группы типов документа
	CaplAttr *a_dt_group_name;		///< Наименование группы типов документа
	CaplAttr *a_dt_group_descr;		///< Описание группы типов документа
	CaplAttr *a_dt_group_par;		///< Родительская группа для группы типов документа
	CaplAttr *a_dt_group_content;	///< Содержимое группы типов документа

	CaplEntity *e_doc_copy;			///<Твердая копия документа
	CaplAttr *a_doc_copy_id;
	CaplAttr *a_doc_copy_state;
	CaplAttr *a_doc_copy_first_rev;
	CaplAttr *a_doc_copy_cur_rev;
	CaplAttr *a_doc_copy_issue_date;
	CaplAttr *a_doc_copy_last_update;
	CaplAttr *a_doc_copy_owner;
	CaplAttr *a_doc_copy_place_of_use;
	CaplAttr *a_doc_copy_doc;
	CaplAttr *a_doc_copy_pur_order;
	CaplAttr *a_doc_copy_real_state;	///< Состояние реальной твердой копии
	CaplAttr *a_doc_copy_who;			///< Кто виноват, что копия пришла в негодность
	CaplAttr *a_doc_copy_destroy_act;	///< Тут указывается информация об акте об уничтожении, в котором есть данная копия

	CaplEntity*		e_apl_order_issue;				///< Выдача по заказ-наряду
	CaplAttr*		a_apl_order_issue_order;		///< По заказ-наряду
	CaplAttr*		a_apl_order_issue_shop;			///< Для цеха
	CaplAttr*		a_apl_order_issue_date;			///< Дата
	CaplAttr*		a_apl_order_issue_doc_number;	///< Номер документа о получении комплекта КД
	CaplAttr*		a_apl_order_issue_reciever;		///< Сотрудник получивший КД
	CaplAttr*		a_apl_order_issue_document;		///< Отчет о получении
	
	CaplEntity	*e_doc_copy_order;			///< Заказ-наряд на изготовление твердых копий
	CaplAttr	*a_purchase_order_els;		///< содержание заказ-наряда
	CaplAttr	*a_purchase_order_id;		///< номер заказ-наряда
	CaplAttr	*a_purchase_order_order;	///< номер заказа (куда входит заказ-наряд)
	CaplAttr	*a_purchase_order_code;		///< шифр
	CaplAttr	*a_purchase_order_introd;	///< указание о внедрении
	CaplAttr	*a_purchase_order_descr;	///< указания
	CaplAttr	*a_purchase_order_date;		///< срок исполнения работ
	CaplAttr	*a_purchase_order_cust;		///< заказчик
	CaplAttr	*a_purchase_order_type;		///< тип заказа (пока или на уничтожение, или на печать)
	CaplAttr	*a_purchase_order_hc;		///< список твердых копий (если заказ на уничтожение)
	CaplAttr	*a_purchase_order_of_change;///< изменение, к которому прикреплен заказ-наряд

	CaplEntity	*e_order_elem;				///< Элемент заказ-наряда
	CaplAttr	*a_order_elem_count;		///< Сколько нужно копий
	CaplAttr	*a_order_elem_doc;			///< Документ для изготовления копий
	CaplAttr	*a_order_elem_order;		///< ССылка на заказ-наряд

	CaplEntity *e_doc_copy_rev_change;	///<Изменения в теле твердой копии документа
	CaplAttr *a_doc_copy_rev_change_doc_change;
	CaplAttr *a_doc_copy_rev_change_author;
	CaplAttr *a_doc_copy_rev_change_apply_date;
	CaplAttr *a_doc_copy_rev_change_hard_copy;

	CaplEntity *e_doc_copy_owner_change;	///<Изменения владельца документа
	CaplAttr *a_doc_copy_owner_change_basis;
	CaplAttr *a_doc_copy_owner_change_hand_date;
	CaplAttr *a_doc_copy_owner_change_new_owner;
	CaplAttr *a_doc_copy_owner_change_new_place_of_use;
	CaplAttr *a_doc_copy_owner_change_hard_copy;
	
	CaplEntity *e_apl_xml_index;	/// Используемые обьекты
	CaplAttr *a_apl_xml_index_cur_doc_rev;
	CaplAttr *a_apl_xml_index_lps_system;
	CaplAttr *a_apl_xml_index_sys_id;
	CaplAttr *a_apl_xml_index_type;
	CaplAttr *a_apl_xml_index_id;
	CaplAttr *a_apl_xml_index_name;
	CaplAttr *a_apl_xml_index_name_eng;
	CaplAttr *a_apl_xml_index_type_name;
	CaplAttr *a_apl_xml_index_config_info;
	CaplAttr *a_apl_xml_index_ref_guid;
	CaplAttr *a_apl_xml_index_cfg;

//	CaplEntity *e_apl_xml_index_relation;	/// Используемые обьекты
//	CaplAttr *a_apl_xml_index_relation_relating;
//	CaplAttr *a_apl_xml_index_relation_related;

	CStringArray m_sel_doc_types_names;
	// Методы
private:
	/** Удаляет папку avred, которая может быть у документа, если над ним
		были использованы функции "красного карандаша" в плагине AutoVue 
		(просмотр 2D/3D чертежей и моделей)
		@param doc документ**/
	bool DeleteAvred(CaplInstance *doc);	
public:

	/**@name Базовые операции*/
	//@{

	/** Показывает свойства документа или его версии 
		@param doc_or_revision документ или его версия
		@param item_rel связь с объектом для задания конттекстов
		@return true при удачном выполнении и false в случае ошибки */ 
	bool ShowDocProperties(CaplInstance *doc_or_revision, CaplInstance* item_rel=0);

	/** Показать карточку учета подлинника
		@pDocument - документ, который хочется посмотреть
		@bReadOnly - режим для пользователя
		@bOffset - нужно ли смещать положение диалога при открытии*/
	bool ShowCardAccount(CaplInstance *pDocument, bool bReadOnly);

	/** Возвращает список рассылки по умолчанию*/
	CString GetDefaultMailList(CaplInstance *pDocument) const;

	/** Создать (если нет) опцию "Редактор_КТС3\\Шифры изделий"*/
	bool CreateDefaultPdfSeriesOption() const;

	/** Создать (если нет) опцию "Редактор_КТС3\\Начиная с инвентарного номера"*/
	bool CreateDefaultInventoryBookSearchNumberOption() const;

	/** Показывает свойства копии документа
		@param doc_copy копия документа
		@return true при удачном выполнении и false в случае ошибки */ 
	bool ShowDocCopyProperties(CaplInstance *doc_copy);

	/** Отображает диалог с перечнем твердых копий документов
		@param filter фильтр для отбора копий документов  */
	void ShowAllDocCopyes(CDocCopyFilter *filter=0);
	
	/** Читает в кэш информацию о типах документов*/
	bool LoadDictionary();

	/** Возвращает документ в базе его по обозначению (id) или NULL, если тагого документа нет.*/
	CaplInstance *FindDocById(const TCHAR *id);

	/** Возвращает версию документа в базе его её обозначению (id) или NULL, если такой версии нет.*/
	CaplInstance *FindDocRevById(CaplInstance *doc, const TCHAR *id);

	/** Возвращает документ в базе его по обозначению (id) и nbge или NULL, если тагого документа нет.*/
	CaplInstance *FindDocByIdAndType(const TCHAR *id, CaplInstance *doc_type);

	/** Возвращает документ в базе его GUID  (для интеграций)*/
	CaplInstance *FindDocByGUID(const TCHAR *s_guid);

	/** Возвращает последнюю по дате версию документа  (не обязательно активную)*/
	CaplInstance *GetLastDocumenrRevision(CaplInstance *doc);

	/** Возвращает вид документа в базе  по наименованию вида документа (type) или NULL, если тагого типа нет.*/  
	CaplInstance *GetDocumentTypeBN(const TCHAR *type);

	/** Возвращает вид документа в базе его по коду вида документа (id) или NULL, если тагого типа нет.*/  
	CaplInstance *GetDocumentTypeByID(const TCHAR *id);

	/** Возвращает в buf имя файла без пути 
		@param doc_or_revision документ или его версия
		@param buf буффер в котором возвращается путь
		@return true при удачном выполнении и false в случае ошибки */ 
	bool GetFileName(CaplInstance *doc_or_revision, CString &buf);

	/** Возвращает в buf полное имя файла (с путем)
		@param doc_or_revision документ или его версия
		@param buf буффер в котором возвращается путь
		@return true при удачном выполнении и false в случае ошибки */ 
	bool GetFullFileName(CaplInstance *doc_or_revision, CString &buf);

	/** Выводит диалог выбора вида документа с учетом пользовательских групп типов документов  
	@param selected_doc_type выбранная тип документа по умолчанию 
	@param selected_group выбранная группа по умолчанию 
	@param m_show_all_doc если true - показывает все типы документов. Если false - только положенные по роли текщего сотрудника
	@param b_select_group если true, то возвращается группа
	@return instance выбранного вида документа, иначе 0 */ 
	CaplInstance *SelectDocType(CaplInstance *selected_doc_type=0,CaplInstance *selected_group=0,bool m_show_all_types=false, bool b_select_group=false);

	/** Возвращает в  ext_dt все документы определенной группы
	@param bRecursive если  true, то включить все подгруппы
	@return true при удачном выполнении и false в случае ошибки */ 
	bool GetAllDocTypeInGroup(CaplInstance *group, aplExtent &ext_dt, bool bRecursive);


	//@}

	// *************************************************************************
	// Редактирование файлов
		// doc_or_revision - документ или редакция документа
		// path - путь 
		// 	если указан файл, то пишется в этот файл
		//  если указан каталог (последний символ '\') - имя берется по умолчанию
		//  если указан NULL - путь запрашивается
	// *************************************************************************

		/**@name Создание и изменение документов*/
		//@{

	/** Создает документ из файла (если какой-то параметр ==0 - то он запрашивается) 
		@param id обозначение документа
		@param name наименование документа
		@param descr описание документа
		@param type вид документа
		@param path путь к файлу 
		@param stored true если документ требуется сохранить в базе данных
		@param item объект с которым ассоциировать документ
		@param created_rel созданная связь item с документом
		@param bAlwaysShowDlg если true - всегда отображается диалог
		и false, если на файл необходимо сделать ссылку
		@return Созданный документ  
		если какой-либо из папаметров не указан, то выводится диалоговое окно создания документа*/
	CaplInstance *CreateDocument(const TCHAR *id, const TCHAR *name, const TCHAR *descr,
		CaplInstance *type, const TCHAR *path, bool stored=true, CaplInstance *item=0, CaplInstance **created_rel=0,
		UINT apl_type = APL_DOCUMENT_RELATION, bool bAlwaysShowDlg=false, bool bShowCRCCalcDlg = true, LPCTSTR sFormat=0);


	/** Создает версию документа из файла 
		@param doc документ
		@param path путь к файлу 
		@param stored true если файл версии документа требуется сохранить в базе данных
		и false, если на файл необходимо сделать ссылку
		@param set_active true если версию документа  требуется сделать активной	и false в противном случае
		@param base_rev базовая для вновь создаваемой версия документа
		@param bShowDlg  показывать диалог с галочками
		@return Созданная версия */
	CaplInstance *CreateDocumentRevision(CaplInstance *doc,
		const TCHAR *path, bool stored=true, bool set_active=false, CaplInstance *base_rev=0, bool bShowDlg=false);
	
	/** Создает описание файла в БД из файла на диске 
		@param path путь к файлу на диске
		@param stored true если файл требуется сохранить в базе данных
		и false, если на файл необходимо сделать ссылку
		@return Созданый файл */
	CaplInstance *CreateFile(const TCHAR *path, bool stored=true);

	/** Создает изменение документа и меняет активную версию 
		@param rev новая версия документа
		@param make_change true если сразу назначается активная
		@param show_dlg true, если надо показать диалог
		@return Созданное изменение */
	CaplInstance *CreateChange(CaplInstance *rev, bool make_change=true, bool show_dlg = true, bool bLSS = false);

	/** Показывает изменения документа 
		@param doc документ
		@return true */
	bool ShowDocChanges(CaplInstance *doc);

	/** Пишет документ или версию на диск устанавливая для файла атрибут RO 
		@param doc_or_revision документ или его версия
		@param path путь к файлу <br>
		 	<ol> если указан файл, то пишется в этот файл </ol>
			<ol> если указан каталог (последний символ '\') - имя берется по умолчанию </ol>
			<ol> если указан NULL - путь запрашивается</ol>
		@param iUseSubDoc +1, если надо обрабатывать вложенные документы, -1, если не надо, 0, если надо спросить
		@return Созданная версия */
	bool LoadRevision(CaplInstance *doc_or_revision, const TCHAR *path, int iUseSubDoc=0,bool bSetRO=true);

	/** Пишет пачку документов или версий документов на диск устанавливая для файла атрибут RO 
		@param doc_or_revisions экстент документ или его версия
		@param path путь к папке, в которую будут записаны документы <br>
			<ol> если параметр не пустой - указаный каталог создается при необъходимости </ol>
			<ol> если указан NULL - путь возвращается ошибка</ol>
		@param names - массив имен файлов, в которые были выгружены файлы. Порядок имен соответсвтует порядку во входном экстенте
		@param bUseSubDoc - true, если надо обрабатывать вложенные документы 
		@return Созданная версия */
	bool LoadMultyRevisions(aplExtent doc_or_revisions, const TCHAR *path,CStringArray &names, bool bUseSubDoc=false,bool bSetRO=true);

	bool CopyDocsOnDisk(aplExtent &docs, CString &defpath, int mode = APL_COPY_DOCS);

	/** Пишет документ на диск устанавливая атрибут RO и запускает ассоциированное
		c данным типом файла приложение для просмотра, после завершения работы приложения файл удаляется 
		@param doc_or_revision документ или его версия
 		@param show_app_dlg true, если требуется диалог выбора приложения
		@param iUseSubDoc +1, если надо обрабатывать вложенные документы, -1, если не надо, 0, если надо спросить
		@return true при удачном выполнении и false в случае ошибки */
	bool View(CaplInstance *doc_or_revision, bool show_app_dlg=false, int iUseSubDoc=0 );

	// Открывает на просмотр встроенным просмотровщиком 
	//   Если просмотровщик не запущен - запускает .  Если bOpenInNewProcess== true - принудительно запускает новый
	// bOpenInNewProcess:  0 - в старом, 1 - в новом, -1 - проверить shift
	bool ViewWithMarkView(CaplInstance *doc_or_revision, int bOpenInNewProcess=-1);


	// Просматривает файл std c выгруженной ЭСИ
	bool ViewESI(CaplInstance *doc_or_revision);

	/** Пишет документ на диск устанавливая атрибут RO и запускает ассоциированное
		c данным типом файла приложение для печати, после завершения работы приложения файл удаляется 
		@param doc_or_revision документ или его версия
 		@param show_app_dlg true, если требуется диалог выбора приложения
		@return true при удачном выполнении и false в случае ошибки */
	bool Print(CaplInstance *doc_or_revision, bool show_app_dlg=false);

	/** Завершает редактированиие документа (doc - документ)
		Если bAlwaysShowDlg -> всегда диалог запроса 
		@param doc документ 
		@param path путь к файлу. Если файл не задан, то он запрашивается 
		@param set_active true если версию документа  требуется сделать активной	и false в противном случае
		@param bAlwaysShowDlg требуется ли всегда выводить диалог (вне зависимости от того задан ли путь).
				true если требуется и false в противном случае
		@param bIgnoreState - true, если необходимо игнорировать состояние документа
		@param bCharact - true, если необходим возврат редактируемых вложенных характеристик
		@return true при удачном выполнении и false в случае ошибки */
	bool CheckIn(CaplInstance *doc, const TCHAR *path, bool set_active=false, bool bAlwaysShowDlg=false, bool bUseSubDoc=false, bool bIgnoreState = false,bool bCharact = true, bool bLoadInfo = true, bool bLSS = false);
	
	/** Проверяет доступ и состояние на возможность сделать версию активной (doc - документ)
		@param bShowMsg выводить или нет сообщение при отказе 
		@return true если можно и false в любом другом случае */
	bool TestMakeVersionActive(CaplInstance *doc,bool bShowMsg=false);

	/** Завершает редактированиие документа (doc - документ)
		Если bAlwaysShowDlg -> всегда диалог запроса 
		@param doc документ 
		@param path путь к файлу. Если файл не задан, то он запрашивается 
		@param set_active true если версию документа  требуется сделать активной	и false в противном случае
		@param bAlwaysShowDlg требуется ли всегда выводить диалог (вне зависимости от того задан ли путь).
				true если требуется и false в противном случае
		@param bIgnoreState - true, если необходимо игнорировать состояние документа
		@return true при удачном выполнении и false в случае ошибки */
	bool CheckInEx(CaplInstance *doc, const TCHAR *path, bool set_active=false, bool bAlwaysShowDlg=false, bool bUseSubDoc=false, bool bIgnoreState = false);

	/** Сохраняет промежуточную версию в БД
		@param doc документ
		@param path путь к файлу
		@param set_active true если версию документа  требуется сделать активной и false в противном случае
		@param bSetRO true установить файлу флаг "Только для чтения".
		@param bIgnoreState - true, если необходимо игнорировать состояние документа
		@param bIgnoreState - true, если необходимо игнорировать состояние документа
		@return true при удачном выполнении и false в случае ошибки */
	bool CheckInOut(CaplInstance *doc, const TCHAR *path, bool bSetActive=false, bool bSetRO = false, bool bAlwaysShowDlg=false, bool bUseSubDoc=false, bool bIgnoreState = false);

	/** Берет документ на редактирование и запускает ассоциированное
		для редактирования c данным типом файла приложение 
		@param doc_or_revision документ или его версия
		@param path путь к файлу. Если файл не задан, то он запрашивается 
 		@param show_app_dlg true, если требуется диалог выбора приложения
		@param bIgnoreState - true, если необходимо игнорировать состояние документа
		@return true при удачном выполнении и false в случае ошибки */
	bool Edit(CaplInstance *doc_or_revision, const TCHAR *path,bool show_app_dlg=false, bool bUseSubDoc= false, bool bIgnoreState = false);

	int CheckForCheckOut(CaplInstance* doc_or_revision);

	/** Берет документ на редактирование 
		@param doc_or_revision документ или его версия
		@param path путь к файлу. Если файл не задан, то он запрашивается 
		@param bAlwaysShowDlg требуется ли всегда выводить диалог (вне зависимости от того задан ли путь).
		true если требуется и false в противном случае
		@param bUseSubDoc - true, если надо обрабатывать вложенные документы 
		@param bIgnoreState - true, если необходимо игнорировать состояние документа
		@param bIgnoreState - true, если необходимо игнорировать состояние документа
		@param bCharact - true, если надо забирать на редактирование вложенные характеристики
		@param bGenNewName - true, если надо генерить новое имя когда такой файл уже есть 
		@param bLoadInfo - true, если надо загрузить из БД информацию о документе
		@return true при удачном выполнении и false в случае ошибки */
	bool CheckOut(CaplInstance *doc_or_revision, const TCHAR *path, bool bAlwaysShowDlg=false, bool bUseSubDoc=false, bool bIgnoreState = false, bool bCharact = true, bool bGenNewName = false, bool bLoadInfo = true);
	
	/** Берет документ на редактирование пачку документов
		@param ext_doc_or_revision список документов или их версий
		@param path путь к файлу. Если файл не задан, то он запрашивается 
		@param bAllMustCheckOut false если надо прервать взятие на редактирование в случае если один из документов не взялся
		@param ext_doc_or_revision список документов или их версий
		@param pCheckOutExt список документов взятых на редактирование, если не нужен, то передать NULL.
		true если требуется и false в противном случае
		@param bUseSubDoc - true, если надо обрабатывать вложенные документы 
		@return true при удачном выполнении и false в случае ошибки */
	bool MultiCheckOut(aplExtent &ext_doc_or_revision, const TCHAR *path, CStringArray& filenames, bool bAllMustCheckOut = true,aplExtent * pCheckOutExt = 0, bool bAlwaysShowDlg=false, bool bUseSubDoc=false);
	
	/** Берет документ на редактирование проверяет документ на зависимость
		@param doc_or_revision документ или его версия
		@param path путь к файлу. Если файл не задан, то он запрашивается 
		@param bAlwaysShowDlg требуется ли всегда выводить диалог (вне зависимости от того задан ли путь).
		true если требуется и false в противном случае
		@param bUseSubDoc - true, если надо обрабатывать вложенные документы 
		@param bIgnoreState - true, если необходимо игнорировать состояние документа
		@return true при удачном выполнении и false в случае ошибки */
	bool CheckOutEx(CaplInstance *doc_or_revision, const TCHAR *path, bool bAlwaysShowDlg =false, bool bUseSubDoc =false, bool bIgnoreState = false);

	/** Отменяет редактированиие документа 
		@param doc документ
		@param bIgnoreState - true, если необходимо игнорировать состояние документа
		@param bCharact - true, если надо отменить редактирование вложенных характеристик
 		@return true при удачном выполнении и false в случае ошибки */
	bool UndoCheckOut(CaplInstance *doc, bool bUseSubDoc=false, bool bIgnoreState = false, bool bCharact = true, bool bFromDB = true);
	
	/** Отменяет редактированиие документа 
		@param doc документ
		@param bIgnoreState - true, если необходимо игнорировать состояние документа
 		@return true при удачном выполнении и false в случае ошибки */
	bool UndoCheckOutEx(CaplInstance *doc, bool bUseSubDoc=false, bool bIgnoreState = false);

	/**Удаляет документ (doc - документ) 
		@param doc документ
 		@return true при удачном выполнении и false в случае ошибки */
	bool DeleteDoc(CaplInstance *doc);

	/** Удаляет версию документа
		@param rev  удаляемая версия документа
		@param delete_doc  если удаляется документ со всеми версиями - true. При этом функция не просит подтвердить удаление версии и не ищет версии - наследники удаляемой
		@return true при удачном выполнении и false в случае ошибки */
	bool DeleteRevision(CaplInstance *rev, bool delete_doc = false, bool bLoadInfo = true, bool bAdditionalCheck = true);

	/** Удаляет все реквизиты документа/версии
		@param ciItem  документ или версия документа
		@return true при удачном выполнении и false в случае ошибки */
	bool DeleteAssociatedEntries(CaplInstance *ciItem);
	
	/** Удаляет копию документа
		@param doc_copy  удаляемая копия документа
		@return true при удачном выполнении и false в случае ошибки */
	bool DeleteDocHardCopy(CaplInstance *doc_copy);

	/**Поставтиь отметку о внесении необходимых изменений в копию документа
		@param doc_copy  копия документа
		@param author  сотрудник, вносящий изменения
		@param doc_change ссылка на объект 'изменение' документа
		@param apply_date дата вненсения изменений
		@return true при удачном выполнении и false в случае ошибки */
	bool ApplyHardCopyRevChanges(CaplInstance *doc_copy,CaplInstance *author=0,CaplInstance *doc_change=0,const TCHAR *apply_date=0);
	
	/**Отображает историю изменений, внесенных в копию документа
		@param doc_copy  копия документа
		@return true при удачном выполнении и false в случае ошибки */
	bool ShowHardCopyRevChanges(CaplInstance *doc_copy);

	/**Отображает историю смены владельцев копии документа
		@param doc_copy  копия документа
		@return true при удачном выполнении и false в случае ошибки */
	bool ShowHardCopyOwnerChanges(CaplInstance *doc_copy);
	//@}

	HANDLE RunFile(const TCHAR *file, bool bShowAppDlg = false);
	// Вызывается перед запуском ассоциированного приложения
	bool AfterSaveDocumentFile(CaplInstance *doc, LPCTSTR lpszFileName);

	// *************************************************************************
	// Работа ассоциированием документа
	// *************************************************************************

	/**@name Работа с реквизитами*/
	//@{

	/** Получаем реквизит по имени
		@param sEntryName наименование искомого реквизита*/
	CaplInstance* GetEntryBN(LPCTSTR sEntryName);
	
	/** Получаем  (у версии документа)последнее значение реквизита (объект) по имени
		@param ciRev версия документа (если документ, то берется активная)
		@param sEntryName наименование искомого реквизита*/
	CaplInstance* GetEntryValBN(CaplInstance *ciRev, LPCTSTR sEntryName, bool bLoadInfo = true);
	
	/** Получаем (у версии документа)последнее значение реквизита (объект) по объекту "реквизит"
		@param ciRev версия документа (если документ, то берется активная)
		@param bLoadInfo зачитывать информацию из БД
		@param Entry реквизит*/
	CaplInstance* GetEntryVal(CaplInstance *ciRev, CaplInstance *Entry, bool bLoadInfo = true);
	
	/** Получаем (у версии документа) последнее значение реквизита 
		@param ciRev версия документа (если документ, то берется активная)
		@param Entry реквизит
		@param bLoadInfo зачитывать информацию из БД
		@param value сюда пишется прочитанное значение
		*/
	bool GetEntryVal(CaplInstance *ciRev, CaplInstance *Entry,  CString &Value, bool bLoadInfo = true);

	/** Получаем (у версии документа) последнее значение реквизита 
		@param ciRev версия документа (если документ, то берется активная)
		@param EntryName наименование реквизита
		@param bLoadInfo зачитывать информацию из БД
		@param value сюда пишется прочитанное значение
		*/	
	bool GetEntryValBN(CaplInstance *ciRev, LPCTSTR EntryName, CString &Value, bool bLoadInfo = true);


	/** Создает значения реквизитов необходимых по умолчанию
		@param ciActRev активная версия документа
		@param ciItem элемент, к котрому прикреплен документ*/
	bool CreateDefaultEntries(CaplInstance *ciActRev, CaplInstance *ciItem = NULL);

	/** Получаем актуальные (то есть текущие) значения реквизитов
	@param ciItem - объект с реквизитаим
	@param aeResult - итоговый массив
	*/
	bool GetActualEntriesVal(CaplInstance *ciItem, aplExtent &aeResult);
	
	/** Проверяет наличие у версии документа всех обязательных реквизитов
		@param ciRev	версия документа для проверки
		@param bLoadFromBase загружать информацию из базы
		@param sMisingEntry если задан, то возвращается имя отсутствующего реквизита*/
	bool HasAllNecessaryEntries(CaplInstance *ciRev, bool bLoadFromBase = true, CString *sMisingEntry=0);

	/** Проверяет наличие у версии документа всех обязательных атрибутов (формат и кол-во листов)
		@param ciRev	версия документа для проверки
		@param bLoadFromBase загружать информацию из базы*/
	bool HasAllNecessaryDocRevAttr(CaplInstance *ciRev);

	/** Создает новый массив значений реквизитов для версии документа на основе другой версии
		@param ciRev версия куда копируется
		@param ciSource весрия документа источник 
		@param bLoadInfo загружать ли атрибуты из БД*/
	bool CopyEntryValues(CaplInstance *ciRev, CaplInstance *ciSource, bool bLoadInfo = true);

	// Копирует атрибуты из одной версии документа в другую, при создании новой
	bool CopyDocRevAttrsToNewRev(CaplInstance *from_rev, CaplInstance *to_rev);

	/** Обновляет массив значений реквизитов для версии документа на основе другой версии
		@param pReciever версия куда копируется
		@param pSource весрия документа источник 
		@param entries названия реквизитов, которые должны быть скопированы*/
	bool UpdateEntryValues(CaplInstance *pSource, CaplInstance *pReciever, const CStringArray &entries) const;


	/** Изменяем поля карточки в соответствии со значеними реквизитов версии документа 
		@param ciRev версия документа*/
	bool FromEntryValToDoc(CaplInstance *ciRev);

	/** Читает значение атрибута по имени поля карточки
		@param ciRev версия документа
		@param sCardField имя карточки
		@param sCardValue результат	*/
	bool GetCardValue(CaplInstance *ciRev, LPCTSTR sCardField, CString &sCardValue);


	/**	Создает значение реквизита по его наименованию
		@param cit			инстанс документа или его активной версии
		@param sEntryName	наименование реквизита
		@param sValue		значение 
		@param bShowErrorMsg	показывать/нет сообщение, что реквизита не существует*/
		bool CreateEntryVal(CaplInstance *cit, CString sEntryName, CString sValue, bool bShowErrorMsg = true, bool bCopyToDocAttr = true, bool bFindPrevValue = true);



	/** Берет ciEntry, смотрит за что отвечает в карточке документа
		и меняет этот атрибут на новое значение (sValue)*/
		bool ChangeDocAttrByEntryVal(CaplInstance *ciRev, CaplInstance *ciEntry, CString sValue);

	/** Берет значения реквизитов у версии, смотрит за что отвечает в карточке документа
		и записывает значение атрибута документа (версии) в реквизит*/
		bool ChangeEntriesValByDocAttr(CaplInstance *ciRevision);

	/** Показывает свойства значения реквизита
		@param DocTypeEntry_Entry реквизит или реквизит документа
		@return true при удачном выполнении и false в случае ошибки */ 
	bool ShowEntryValProperties(CString &sValue, CaplInstance *DocTypeEntry_Entry);

	/** Относится реквизит к версии документа или к самому документу*/
	bool EntryForDocumentVersion(const CString &sCardField);
	bool EntryForDocumentVersion(CaplInstance *ciEntry);

	/** Добавить реквизит для типа документа
		@ciEntry - реквизит
		@ciDT - тип документа
		@bOptional - будет ли реквизит необязательным*/
	bool AddEntryToDocType(CaplInstance *ciEntry, CaplInstance *ciDT, bool bOptional = true);

	/** Фунции возвращают наименования реквизитов*/
	CString GetEntryFormatName() const;
	CString GetEntryInventoryNumberName() const;
	CString GetEntryMailListName() const;
	CString GetEntryTotalListCountName() const;
	CString GetEntryReleasedByName() const;
	CString GetEntryAcceptApprovalName() const;
	CString GetEntryPdfCodeName() const;
	CString GetEntrySubstInventoryNumberName() const;
	CString GetEntryDublicateInentoryNumberName() const;
	CString GetEntryDublicateName() const;
	CString GetEntryArchiveAcceptDateName() const;

	// Читает реквизиты из файла реквизитов
	static bool LoadRequisiteFromFile(LPCTSTR sFileName, CaplStrStrMap &mapRequisite);

	// Записывает реквизиты в версию 
	// bAddReqToDocType - добавлять создаваеые реквизиты в вид документа
	bool SaveRequisiteToRevision(CaplInstance *rev, CaplStrStrMap &mapRequisite, bool bAddNewReqToDocType);

	//@}	
	/**@name Работа ассоциированием документа*/
	//@{

	/** Возвращает в out_ext ассоцаторы документов с Instance 
		@param inst  объект, ассоцияции с которым ищутся 
		@param out_ext  список в котором возвращаются найденные документы (результат)
		@param out_rel  список в котором возвращаются найденные ассоциаторы (результат)
		@param context  контекст для которого берутся документы (результат)
		@return true при удачном выполнении и false в случае ошибки */
	bool FindAssociatedDocuments(CaplInstance *inst, aplExtent &out_ext, aplExtent &out_rel, CaplInstance *context=0,bool from_base=true); 
	
	/** Возвращает в out_ext ассоцаторы документов со списком объектов в ext
		@param ext  список объект, ассоцияции с которым ищутся 
		@param out_ext  список в котором возвращаются найденные документы (результат)
		@param out_rel  список в котором возвращаются найденные ассоциаторы (результат)
		@param context  контекст для которого берутся документы (результат)
		@return true при удачном выполнении и false в случае ошибки */
	bool FindAssociatedDocuments(aplExtent &ext, aplExtent &out_ext, aplExtent &out_rel, CaplInstance *context=0,bool from_base=true);
	
	/** Возвращает в out_ext ассоцаторы документов со списком объектов в ext с учетом вложенных документов
		@param ext  список объект, ассоцияции с которым ищутся 
		@param out_ext  список в котором возвращаются найденные документы с учетом вложенных документов
		@param out_rel  список в котором возвращаются найденные ассоциаторы с учетом вложенных документов
		@param context  контекст для которого берутся документы (результат)
		@return true при удачном выполнении и false в случае ошибки */
	bool FindAssociatedDocumentsRec(aplExtent &ext, aplExtent &out_ext, aplExtent &out_rel, CaplInstance *context=0);
	
	/** Ищет объекты, с которыми ассоциирован документ inst (функция обратная FindAssociatedDocuments)
		Возвращает в out_ext ассоцаторы документов с Instance 
		@param inst  документ, ассоцияции с которым ищутся 
		@param out_ext  список в котором возвращаются найденные документы (результат)
		@param out_rel  список в котором возвращаются найденные ассоциаторы (результат)
		@param context  контекст для которого берутся документы (результат)
		@return true при удачном выполнении и false в случае ошибки */
	bool FindAssociatingDocuments(CaplInstance *inst, aplExtent &out_ext, aplExtent &out_rel, CaplInstance *context=0,bool from_base=true); 
	
	/** Ищет объекты, с которыми ассоциированы документы из ext (функция обратная FindAssociatedDocuments)
		Возвращает в out_ext ассоцаторы документов со списком объектов в ext
		@param ext  список документов, ассоцияции с которыми ищутся 
		@param out_ext  список в котором возвращаются найденные документы (результат)
		@param out_rel  список в котором возвращаются найденные ассоциаторы (результат)
		@param context  контекст для которого берутся документы (результат)
		@return true при удачном выполнении и false в случае ошибки */
	bool FindAssociatingDocuments(aplExtent &ext, aplExtent &out_ext, aplExtent &out_rel, CaplInstance *context=0,bool from_base=true);
	
	/** Создает ассоциатор inst c doc 
		@param inst  объект, ассоцияция с которым создается 
		@param doc  документ, ассоцияция которого создается
		@param контексты  для создаваемой связи
		@param source  назначение создаваемой связи
		@return созданный ассоциатор и NULL в случае ошибки */
	CaplInstance *CreateAssociation(CaplInstance *inst,CaplInstance *doc, aplExtent *contexts=0, const TCHAR * source=0, UINT apl_type = APL_DOCUMENT_RELATION, bool bCheckExist = true);

	/// Добавляет документы из extDocs к объекту item(если item==0, по появлется диалог выбора)
	bool CreateAssociation( CaplInstance *item, aplExtent &extDocs, aplExtent *contexts=0, const TCHAR * source=0);

	/** Ищет ассоциацию документа с inst 
		@param inst  объект, ассоцияция с которым ищется 
		@param doc  документ, ассоцияция которого ищется
		@return найденный ассоциатор и NULL если тагого нет  */
	CaplInstance *FindAssociation(CaplInstance *inst,CaplInstance *doc);

	/** Поиск твердых копий документа
		@param out_ext  список в котором возвращаются найденные копии
		@param id  обозначение копии
		@param doc  документ
		@param owner сотрудник отв. за копию
		@param place_of_use ссылка на элемент оргструктуры - место использования 
		@param state состояние (используется,аннулирован,уничтожен)
		@param change_date_behin дата начала периода проведения изменений документов
		@param change_date_end дата окончания периода проведения изменений документов
		@param b_only_out_of_date флаг поиска только неактуальных копий
		return true при удачном выполнении и false в случае ошибки */
	bool FindHardCopyes(aplExtent &out_ext,const TCHAR *id=0,CaplInstance *document=0,CaplInstance *owner=0,CaplInstance *place_of_use=0,const TCHAR *state=0,const TCHAR *change_date_begin=0,const TCHAR *change_date_end=0,BOOL b_only_out_of_date=false);

	/** Проверяет наличие связанных документов для документа или его верии 
		@param doc_or_revizion  документ или его версия
		@return true если связанные документы есть и false если нет  */
	bool CheckSubDocument(CaplInstance *doc_or_revision);

	/** Проверяет наличие объектов, с которыми связан указанный документ или его верии 
		@param doc_or_revizion  документ или его версия
		@return true если документ связан и false если нет  */
	bool CheckSuperDocument(CaplInstance *doc_or_revision);

	//@}

	// *************************************************************************
	// Чтение из базы
	// *************************************************************************

	/**@name Чтение из базы */
	//@{

	/** Читает из базы информацию о документе 
		@param doc  документ, информация о котором читается из базы
		@return true при удачном выполнении и false в случае ошибки */
	bool LoadDocInfo(CaplInstance *doc);
	/** Читает из базы информацию о документах 
		@param ext  список документов, информация о которых читается из базы
		@param bLoadEntries  Зачитывать значения реквизитов
		@return true при удачном выполнении и false в случае ошибки */
	bool LoadDocInfo(aplExtent &ext, bool bLoadEntries=false);

	/** Читает из базы все версии документа 
		@param doc  документ, версии которого читаются
		@param rev_ext  список в котором возвращаются версии (результат)
		@return true при удачном выполнении и false в случае ошибки */
	bool LoadAllDocumentRevision(CaplInstance *doc, aplExtent &rev_ext);

	/** Возвращает последнюю версию документа*/
	CaplInstance *GetLasRevision(CaplInstance *doc);

	/** Читает из базы информацию о копии документа
		@param doc_copy  копия документа, информация о которой читается из базы
		@return true при удачном выполнении и false в случае ошибки */
	bool CaplDocManager::LoadDocCopyInfo(CaplInstance *doc_copy);
	
	/** Читает из базы информацию о копиях документов
		@param ext  список копий документов, информация о которых читается из базы
		@return true при удачном выполнении и false в случае ошибки */
	bool CaplDocManager::LoadDocCopyInfo(aplExtent &ext);
	//@}

	// выводит диалог выбора приложения
	// возвращает true, если ok и false, если отмена
	// если app пустое - использовать стандартное
	bool SelectApp(const TCHAR *file, CString &app);

	/** Создает документ по шаблону
		@param i_doc документ-шаблон 
		@param m_inst объект, с которым должен быть ассоциирован новый документ
		@return указатель на инстанс нового документа*/
	CaplInstance *CreateDocumentByDot(CaplInstance *i_doc, CaplInstance *inst);
	
	/** Поиск зависимых документов
		@param doc документ
		@param docs найденные зависимые и исходные документы
		@param ref найденные связи
		@return true при удачном выполнении и false в случае ошибки */
	bool FindDependenceDocuments(CaplInstance *doc, aplExtent &docs, aplExtent&ref);

	/** Поиск зависимых документов
		@param doc документ
		@param docs указатель на массив найденных зависимых и исходных документов
		@param ref указатель на массив найденных связей
		@return true при удачном выполнении и false в случае ошибки */
	CaplInstance* IsDependenceDocument(CaplInstance *doc, aplExtent *docs=0, aplExtent *ref=0);

	/** Поиск зависимых документов
		@param deps массив зависимых документы
		@return true если хоть один из документов изменен*/
	bool TestOnChange(aplExtent &deps);

	/** Поиск всех заказ-нарядов
		@param subItems массив возвращаемых заказ-нарядов
		@param bLoadFromBase загружать ли из базы
		@return true при удачном выполнении и false в случае ошибки */
	bool GetAllPurchaseOrder(aplExtent &subItems, bool bLoadFromBase=true);

	/** Сравнивает файл в версии и на диске	Возвразает   0 - равны, 1 - не равын, -1 - ошибка*/
	int CompareRevisionWithFile(CaplInstance *doc_or_rev, LPCTSTR file_path);
	

	// *************************************************************************
	// Настройка полей-статусов в документах, созданных Конструктором Отчетов
	// *************************************************************************

	bool SetupApprovalFieldsInReports();
	
	// *************************************************************************
	// Твердые копии документов
	// *************************************************************************
	/** Создание копии документа
		@param doc документ
		@param id обозначение
		@param owner владелец
		@param place_of_use место использования
		@param basis основание выдачи
		@param issue_date дата выдачи
		@param b_show_dlg показывать или нет диалоговое окно создания копии документа
		@return true если документ создан, иначе - false*/
	CaplInstance *CaplDocManager::CreateDocumentHardCopy(CaplInstance *doc=0,const TCHAR *id=0,CaplInstance *owner=0,CaplInstance *place_of_use=0,const TCHAR *basis=0,const TCHAR *issue_date=0,bool b_show_dlg=true);
	/** Определение очередного номера твердой копии
		@param doc документ
		@return очередной номер в случае успеха, иначе -1*/
	int CaplDocManager::GetNextHardCopyNumber(CaplInstance *doc);
	/************************************************************************/
	/*            Данные функции необходимы для работы интеграции           */
	/************************************************************************/
	//++ Колесников данная функция необходима для работы интеграции
	/** Поиск ассоциированных с документом изделий
		@param extIn список документов, для которых необходимо найти ассоциированные изделия
		@param extPdfs список pdf'ов, ассоциированных с документами
		@param extPrds список изделий для pdf'ов
		@param extRefs список связей между докментами и изделиями apl_dpc_ref
		@return true в случае если найден хотя бы один pdf, иначе false*/
	bool FindAssociatedPdfs(aplExtent& extIn, aplExtent& extPdfs, aplExtent& extPrds, aplExtent& extRefs);
	//++ Колесников данная функция необходима для работы интеграции
	/** Получение чистого имени документа - без расширения
		@param sFileName входное имя
		@param sOnlyName выходное имя - без расширения
		@return true в случае успещности операции*/
	bool GetOnlyName(const CString& sFileName, CString &sOnlyName);
	//++ Колесников данная функция необходима для работы интеграции
	/** Вспомогательная функция для загрузки информации об ассоциированном pdf'e
		@param api mapi
		@param ld loaddata
		@param data*/
	static void AddPdfDocRefInfo(CaplAPI *api, CaplLoadData &ld, DWORD data);
	//++ Колесников данная функция необходима для работы интеграции
	/** Загрузка правил для сохранения характеристик интеграции
		@param siMapOptions - карта правил*/
	void LoadOptions(mymsiMap& siMapOptions);

	/** Добавляет информацию об использовании обьекта справочника */
	CaplInstance* AddXmlUsedItem( CaplInstance *currentDocRevision, CaplInstance *lpsSystem,
					const CString& sysId, int type,const CString& typeName, const CString& id, const CString& name, const CString& name_eng,
					const CString& configInfo,
					const CString& refGuid,
					CaplInstance *cfgInst);

	/** Проверяет, используется ли элемент справочника с определённым sys id в лсс1 */
	bool IsUsedInXml( const CString& sysId );

	/** Проверяет, используется ли элементы справочника в xml */
	bool IsUsedInXml(const aplExtent& in_ext,  std::map<CaplInstance*, bool>& outMap);

	bool FindXmlUsedRefs(const CString& sysId, aplExtent& out_ext);
	bool FindXmlUsedRefs(const std::list<CString>& in_sysIds, aplExtent& out_ext);
	bool FindXmlUsedRefs(const aplExtent& in_ext, std::map<CaplInstance*, std::vector<CaplInstance*>>& out_map);

	// Очищает информацию об использовании для заданной ревизии
	void ClearAllXmlUsages( CaplInstance *doc_or_revision );

	/** Выгружает на диск файл из блоба локера.
		@param lockInst
			Локер.
		@param filename
			Имя файла, куда выгружать блоб.
	*/
	bool LoadFileFromLocker( CaplInstance * lockInst, const CString& filename );

	/** Сохраняет файл в блоб локера.
		@param lockInst
			Локер.
		@param filename
			Имя файла для сохранения в блоб.
	*/
	bool SaveFileToLocker( CaplInstance* lock, const CString& filename );

	// возвращает значение атрибута документа или версии по имени
	CString GetAttrByCardField(CaplInstance *ciRevision, const CString &name);

	// Определение номера максимальной существующей версии документа
	int GetMaxDocRevId(CaplInstance *doc);

	// Вычисление кол-ва листов приведенных к А4 с округлением вверх до большего; возвращает "" при непонятных данных
	bool CalcA4SheetsCount(LPCTSTR sFormat, LPCTSTR sSheetsCount, CString &sA4Count);

	// Определяет обозначение изделия по обозначению документа (берет левую часть относительно кода вида документа)
	// Версия изделия - чать после тире.
	// Обозначение возвращается в верхнем регистре
	bool GetPrdIdFromDocId(CaplInstance *doc, CString &prd_id, CString &prd_ver);

	// Ищет версию изделия, скотороым стоило бы ассоциировать документ.
	// Если изделие есть, а связи еще нет, то предлагает создать
	bool AttachDocToPrd(CaplInstance *doc);

	// при сложном наборе форматов листов документа
	// вычисляет общее количество листов из строки, которая описывает сложный набор форматов
	// (исходные данные из атрибута document->total_sheets_count)
	// Если задан указатель format_description, то в эту строку пишется человеческое описание набора форматов
	// Если задан указатель countA4, то в него пишется количество листов, приведенных к формату А4
	// Если в исходном атрибуте только одно число, то 1) возвращается это число 2) в строку format_description пишется это 
	// число без указания формата 3) в countA4 так же возвращается это число
	static int CalcAllSheetsFromMultiFormats(LPCTSTR scOfLists, CString* format_description = 0, int *countA4=0);

	// при сложном наборе форматов листов документа
	// вычисляет общее количество листов из строки, которая описывает сложный набор форматов
	// (исходные данные из атрибута document->total_sheets_count)
	// Если задан указатель list_formats, то в эту строку пишется список форматов
	static int GetListFormats(LPCTSTR scOfLists, CString* list_formats = 0);

	// Протоколирование
	void LogDocAccess(CaplInstance *inst, LPCTSTR function, LPCTSTR fpath);

	// Функция читающая данные для отображения в отчетах
	bool LoadKdFields(CaplInstance *rev, CaplStrStrMap &map_params);

protected:
	bool CaplDocManager::SetRevisionAccessOnCreate(CaplInstance *rev);
};

// *************************************************************************
// *************************************************************************
// *************************************************************************
// Массив значений типа double
//typedef CaplTAggr <double,long*,0> aplRealArray;
typedef CArray <double,double> aplRealArray;
typedef CaplTAggr <CaplInstance*,long*,0> aplInstArray;

#define APL_LOAD_ASSEMBLY_COMPONENT_USAGE 1
#define APL_LOAD_MAKE_FROM_USAGE_OPTION 2
#define APL_LOAD_DESING_MAKE_FROM_RELATIONSHIP 4

typedef enum {aplModeEdit, aplModeCreateProduct, aplModeCreateVersion, aplModeCreateSubProduct,aplModeCreateProductIfNew} aplPrdDlgmode;

/** Менеджер изделий*/
class CLASS_DECL_APL_STEP_MGR CaplProductManager: public CaplStepManager
{
	static bool FnNULLInst(const CaplInstance *&inst){return (inst == NULL);}
	
	// Инициализация
public:
	/** Инициализирует класс (Ассоциация с классом базы данных) 
		@return true при удачном выполнении и false в случае ошибки */
	virtual bool Attach(CaplAPI *api);
	virtual void Detach();

	// Attributes
public:	

	/**@name Изделие (элементы словаря) */
	//@{
	CaplEntity *e_prd;		/**<product */
	CaplAttr *a_prd_id;		/**<product -> id */
	CaplAttr *a_prd_name;	/**<product -> name */
	CaplAttr *a_prd_descr;  /**<product -> description */
	CaplAttr *a_prd_code;	/**<product -> code */
	CaplAttr *a_prd_guid;	
	//@}
	

	/**@name Версия изделия (элементы словаря) */
	//@{
	CaplEntity *e_pdf;		/**<product_definition_formation */
	CaplAttr *a_pdf_id;		/**<product_definition_formation -> id */
	CaplAttr *a_pdf_prd;	/**<product_definition_formation -> of_product */
	CaplAttr *a_pdf_descr;	/**<product_definition_formation -> description */
	CaplAttr *a_pdf_code;	/**<product_definition_formation -> code */
	CaplAttr *a_pdf_code1;	/**<product_definition_formation -> code2 */
	CaplAttr *a_pdf_code2;	/**<product_definition_formation -> code3 */
	CaplAttr *a_pdf_okpd_code; //*<product_definition_formation -> okpd_code */
	CaplAttr *a_pdf_ils_component;

	CaplAttr*    a_apl_pdf_grpz_id;
	CaplAttr*    a_apl_pdf_grpz_name;
	CaplAttr*    a_apl_pdf_grpz_pdf_id;

	 
	CaplEntity *e_apl_pdf;			/**apl_product_definition_formation< */
	CaplAttr *a_pdfwss_source;		/**<apl_product_definition_formation -> make_or_buy */
	CaplAttr *a_apl_pdf_type;		/**<apl_product_definition_formation -> formation_type */
	CaplAttr *a_apl_pdf_standard;	/**<apl_product_definition_formation -> is_standard_part */
	CaplAttr *a_apl_pdf_state;		/**<product_definition_formation -> cp_state*/
	CaplAttr *a_apl_pdf_relevance;		/**<product_definition_formation -> relevance Актуальность для сербов*/
	CaplAttr *a_apl_pdf_cp_state;		/**<product_definition_formation -> state*/
	CaplAttr *a_apl_pdf_unit;		/**<product_definition_formation -> unit*/
	CaplAttr *a_apl_pdf_logbook;	/**<product_definition_formation -> logbook_type*/
	CaplAttr *a_apl_pdf_first_usage;/**<product_definition_formation -> first_usage*/
	CaplAttr *a_apl_pdf_additional_data;/**<product_definition_formation -> additional_data*/
	CaplAttr *a_apl_pdf_average_life_refusal;	/**<product_definition_formation -> average_life_refusal*/
	CaplAttr *a_apl_pdf_par_flow_refusal;	/**<product_definition_formation -> par_flow_refusal*/
	CaplAttr *a_apl_pdf_average_life_removal;	/**<product_definition_formation -> average_life_removal*/
	CaplAttr *a_apl_pdf_locker;
	CaplAttr *a_apl_pdf_parent;
	CaplAttr *a_apl_pdf_guid;
	CaplAttr *a_apl_pdf_cataloging_params;
	CaplAttr *a_apl_pdf_refusal_count;
	//@}

	// техпроцесс
	CaplEntity*  e_apl_tech_process;
	CaplAttr*    a_tech_process_id;
	CaplAttr*    a_tech_process_pdf;
	CaplAttr*    a_tech_process_processing_class;
	CaplAttr*    a_tech_process_minimum_quantity;
	CaplAttr*    a_tech_process_type;
	CaplAttr*    a_tech_process_author;
	CaplAttr*    a_tech_process_create_date;
	CaplAttr*    a_tech_process_last_edit_person;
	CaplAttr*    a_tech_process_last_edit_date;
	CaplAttr*    a_tech_process_xml_material;
	CaplAttr*    a_tech_process_xml_material_value;
	CaplAttr*    a_tech_process_approved_date;
	CaplAttr*    a_tech_process_canceled_date;
	CaplAttr*    a_tech_process_ver;
	CaplAttr*    a_tech_process_x;
	CaplAttr*    a_tech_process_y;
	CaplAttr*    a_tech_process_z;
	CaplAttr*    a_tech_process_l;
	CaplAttr*	 a_tech_process_fiber_direction;
	CaplAttr*	 a_tech_process_angel_90;
	CaplAttr*	 a_tech_process_samples_count;
	CaplAttr*	 a_tech_process_lots_count;
	CaplAttr*	 a_tech_process_sample_size;

	// элемент импорта, который не удалось найти сразу по обозначению
	CaplEntity*	 e_apl_pez_import_item;
	CaplAttr*    a_pez_item_pdf;
	CaplAttr*    a_pez_item_position;
	CaplAttr*    a_pez_item_print_id;
	CaplAttr*    a_pez_item_print_name;
	CaplAttr*    a_pez_item_foreign_name;
	CaplAttr*    a_pez_item_print_unit;
	CaplAttr*    a_pez_item_price;
	CaplAttr*    a_pez_item_count;

	// договор поставки
	CaplEntity*  e_apl_supply_contract;
	CaplAttr*    a_sc_document;
	CaplAttr*    a_sc_abonent;
	CaplAttr*    a_sc_registration_date;
	CaplAttr*    a_sc_activation_date;
	CaplAttr*    a_sc_end_date;
	CaplAttr*    a_sc_notes;
	CaplAttr*    a_sc_author;
	CaplAttr*	 a_sc_annulate_date;

	// операция техпроцесса
	CaplEntity*  e_apl_tech_process_operation;
	CaplAttr*    a_tpo_production_time;
	CaplAttr*    a_tpo_laboriousness;
	CaplAttr*    a_tpo_worker_category;
	CaplAttr*    a_tpo_id;
	CaplAttr*    a_tpo_operation;
	CaplAttr*    a_tpo_process;
	CaplAttr*    a_tpo_profession;
	CaplAttr*    a_tpo_work_condition;
	CaplAttr*    a_tpo_workers_count;
	CaplAttr*    a_tpo_limit_operation;
	CaplAttr*    a_tpo_fictive_operation;
	CaplAttr*    a_tpo_units_at_same_time;
	CaplAttr*    a_tpo_preporation_time;
	CaplAttr*    a_tpo_one_unit_time;
	CaplAttr*	 a_tpo_laboriousness_show_in_minutes;
	CaplAttr*	 a_tpo_locker;
	CaplAttr*	 a_tpo_check_out_date;
	CaplAttr*	 a_tpo_check_in_date;
	CaplAttr*	 a_tpo_edit_person;
	CaplAttr*	 a_tpo_new_revision;
	CaplAttr*	 a_tpo_base_revision;
	CaplAttr*	 a_tpo_internal_number;

	// выгрузка КС->ТС для заявки
	CaplEntity*  e_kit_unload_item;
	CaplAttr*    a_kit_unload_item_kit;
	CaplAttr*    a_kit_unload_item_ks;
	CaplAttr*    a_kit_unload_item_ts;
	CaplAttr*    a_kit_unload_item_date;
	CaplAttr*    a_kit_unload_item_person;


	// технологическая операция
	CaplEntity*  e_apl_tech_operation;
	CaplAttr*    a_tech_operation_pdf;
	CaplAttr*    a_tech_operation_operation_level;
	CaplAttr*    a_tech_operation_shop;
	CaplAttr*    a_tech_operation_level;
	CaplAttr*    a_tech_operation_fictive;
	CaplAttr*    a_tech_operation_limit;


	// комплектовочная карта
	CaplEntity* e_apl_complectation_card;
	CaplAttr*    a_complectation_card_parent_pdf;
	CaplAttr*    a_complectation_card_id;
	CaplAttr*    a_complectation_card_name;
	CaplAttr*    a_complectation_card_stage;
	CaplAttr*    a_complectation_card_dscr;
	CaplAttr*    a_complectation_card_time;

	/**@name Связи меежду изделияти (элементы словаря) */
	//@{
	CaplEntity *e_pdr;					/**<product_definition_relationship */
	CaplEntity *e_acu;					/**<assembly_component_usage */
	CaplAttr *a_acu_ref_des;			/**<assembly_component_usage -> reference_designator */

	CaplEntity *e_nauo;					/**<next_assembly_usage_occurrence */
	CaplEntity *e_apl_qacu;				/**<apl_quantified_assembly_component_usage */
	 
	CaplEntity *e_qacu_nauo;			/**<apl_quantified_assembly_component_usage+next_assembly_usage_occurrence */
	CaplAttr *a_pdr_id;					/**<product_definition_relationship -> id */
	CaplAttr *a_pdr_name;				/**<product_definition_relationship -> name */
	CaplAttr *a_pdr_descr;				/**<product_definition_relationship -> description */
	CaplAttr *a_pdr_r_ting;				/**<product_definition_relationship -> relating_product_definition */
	CaplAttr *a_pdr_r_ted;				/**<product_definition_relationship -> related_product_definition */
	CaplAttr *a_apl_qacu_unit;			/**<apl_quantified_assembly_component_usage -> unit_component */
	CaplAttr *a_apl_qacu_value;			/**<apl_quantified_assembly_component_usage -> value_component */
	CaplAttr *a_pdr_frames_of_reference;/**<product_definition_relationship -> apl_frames_of_reference */
	CaplAttr *a_pdr_inner_id;			/**<product_definition_relationship -> assembly_item_id */
	CaplAttr *a_pdr_parent_reference;	/**<product_definition_relationship -> parent_reference */
	CaplAttr *a_pdr_parent_reference_type;/**<product_definition_relationship -> parent_reference_type */
	CaplAttr *a_pdr_guid;
	//@}

	// объет выгруженный в 1с (нормы)
	CaplEntity*  e_apl_1c_upload_item;
	CaplAttr*    a_1c_upload_item_zakaz;
	CaplAttr*    a_1c_upload_item_sklad;
	CaplAttr*    a_1c_upload_item_ceh;
	CaplAttr*    a_1c_upload_item_nn;
	CaplAttr*    a_1c_upload_item_num_lim;
	CaplAttr*    a_1c_upload_item_pdf_name;
	CaplAttr*    a_1c_upload_item_pdf_id;
	CaplAttr*    a_1c_upload_item_export_result;
	CaplAttr*    a_1c_upload_item_pdf_unit;
	CaplAttr*    a_1c_upload_item_type_lim;
	CaplAttr*    a_1c_upload_item_prim_lim;
	CaplAttr*    a_1c_upload_item_post_date;
	CaplAttr*    a_1c_upload_item_create_date;
	CaplAttr*    a_1c_upload_item_color_flag;
	CaplAttr*    a_1c_upload_item_kol;
	CaplAttr*    a_1c_upload_item_last_upload_kol;	
	CaplAttr*	 a_1c_upload_item_mat_rel;
	CaplAttr*	 a_1c_upload_item_last_last_upload_kol;

	CaplEntity*  e_limit_change_upload_history;
	CaplAttr*	 a_limit_change_upload_history_item;
	CaplAttr*	 a_limit_change_upload_history_zakaz;
	CaplAttr*	 a_limit_change_upload_history_num_lim;
	CaplAttr*	 a_limit_change_upload_history_type_lim;

	/**@name Связи меежду изделияти (элементы словаря) */
	//@{
	CaplEntity *e_shared_pdf_rel;		/**<shared_pdf_relationship */
	CaplAttr *a_shared_pdf_rel_ed;		/**<shared_pdf_relationship -> related_pdf */
	CaplAttr *a_shared_pdf_rel_ing;		/**<shared_pdf_relationship -> related_pdf */

	/**@name Применяемость (элементы словаря) */
	//@{
	CaplEntity *e_pd_eff;			/**<product_definition_effectivity */
	CaplAttr *a_pde_id;				/**<product_definition_effectivity -> id */
	CaplAttr *a_pde_usage;			/**<product_definition_effectivity -> usage */
	CaplAttr *a_pde_prev;			/**<product_definition_effectivity -> previouse */
	CaplAttr *a_pde_not_active;		/**<product_definition_effectivity -> is_not_active */

	CaplEntity *e_sn_eff;		/**<serial_numbered_effectivity */
	CaplAttr *a_sn_eff_start;	/**<serial_numbered_effectivity -> effectivity_start_id */
	CaplAttr *a_sn_eff_end;		/**<serial_numbered_effectivity -> effectivity_end_id */
	
	CaplEntity *e_dat_eff;		/**<dated_effectivity */
	CaplAttr *a_dat_eff_start_s;/**<dated_effectivity -> effectivity_start_date_s */
	CaplAttr *a_dat_eff_end_s;	/**<dated_effectivity -> effectivity_end_date_s */
	//@}
	 
	/**@name Полуфабрикаты (элементы словаря) */
	//@{
	CaplEntity *e_make_from;					/**<apl_make_from_usage_option */
	CaplEntity *e_design_make_from;				/**<design_make_from_relationship */
	CaplAttr *a_make_from_ranking;				/**<apl_make_from_usage_option -> ranking */
	CaplAttr *a_make_from_ranking_rationale;	/**<apl_make_from_usage_option -> ranking_rationale */
	CaplAttr *a_make_from_value;				/**<apl_make_from_usage_option -> value_component */
	CaplAttr *a_make_from_unit;					/**<apl_make_from_usage_option -> unit_component */
	CaplAttr *a_make_from_derive_value;			/**<apl_make_from_usage_option -> derive_value_component */
	CaplAttr *a_make_from_derive_unit;			/**<apl_make_from_usage_option -> derive_unit_component */
	CaplAttr *a_make_from_assortment;			/**<apl_make_from_usage_option -> apl_assortment */
	CaplAttr *a_make_from_param;				/**<apl_make_from_usage_option -> parameter_of_sortament */
	CaplAttr *a_make_from_waste;				/**<apl_make_from_usage_option -> from_waste */
	//@}

	CaplEntity *e_spr;	/**<supplied_part_relationship */

	/**@name Аналоги (элементы словаря) */
	//@{
	CaplEntity *e_alt;		/**<alternate_product_relationship */
	CaplAttr *a_alt_base;	/**<alternate_product_relationship -> base */
	CaplAttr *a_alt_alt;	/**<alternate_product_relationship -> alternate */
	CaplAttr *a_alt_basis;	/**<alternate_product_relationship -> basis */
	CaplAttr *a_alt_name;	/**<alternate_product_relationship -> name */
	CaplAttr *a_alt_descr;	/**<alternate_product_relationship -> description */
	CaplAttr *a_alt_koeff;	/**<alternate_product_relationship -> koeff */
	//@}

	/**@name Аналоги версии изделия(элементы словаря) */
	//@{
	CaplEntity *e_alt_pdf;		
	CaplAttr *a_alt_pdf_base;	
	CaplAttr *a_alt_pdf_alt;	
	CaplAttr *a_alt_pdf_id;			
	CaplAttr *a_alt_pdf_basis;	
	CaplAttr *a_alt_pdf_descr;
	CaplAttr *a_alt_pdf_koeff;	
	//@}

	/**@name Сортамент (элементы словаря) */
	//@{
	 
	CaplEntity *e_assortment;			/**<apl_assortment */
	CaplEntity *e_assortment_shape;		/**<apl_assortment_shape */
	CaplEntity *e_prd_assortment;		/**<apl_product_assortment */
	 
	CaplAttr *a_assortment_id;			/**<apl_assortment -> id */
	CaplAttr *a_assortment_name;		/**<apl_assortment -> name */
	CaplAttr *a_assortment_descr;		/**<apl_assortment -> description */
	CaplAttr *a_assortment_std;			/**<apl_assortment -> standard */
	CaplAttr *a_assortment_shape;		/**<apl_assortment -> shape */
	 
	CaplAttr *a_assortment_dim_name;	/**<apl_assortment -> dimension_name */
	CaplAttr *a_assortment_possible_dim;/**<apl_assortment -> possible_dimensions */
	CaplAttr *a_assortment_shape_id;	/**<apl_assortment_shape -> id */
	CaplAttr *a_assortment_shape_name;	/**<apl_assortment_shape -> name */
	CaplAttr *a_assortment_shape_descr;	/**<apl_assortment_shape -> description */
	CaplAttr *a_assortment_shape_unit;	/**<apl_assortment_shape -> unit */
	CaplAttr *a_prd_assortment_prd;		/**<apl_product_assortment -> of_product */
	CaplAttr *a_prd_assortment_assort;	/**<apl_product_assortment -> assortment */
	//@}

	/**@name Заменяющие изделия в контексте сборки (элементы словаря) */
	//@{
	CaplEntity *e_pdf_subst;			/**<product_definition_substitute */

	CaplAttr *a_pdf_subst_id;			/**<product_definition_substitute -> id */
	CaplAttr *a_pdf_subst_name;			/**<product_definition_substitute -> name */
	CaplAttr *a_pdf_subst_description;	/**<product_definition_substitute -> description */
	CaplAttr *a_pdf_subst_pdr;			/**<product_definition_substitute -> context_relationship */
	CaplAttr *a_pdf_subst_pdf;			/**<product_definition_substitute -> substitute_definition */
	CaplAttr *a_pdf_subst_value;		/**<product_definition_substitute -> value_component */
	CaplAttr *a_pdf_subst_unit;			/**<product_definition_substitute -> unit_component */
	CaplAttr *a_pdf_subst_parent_item;	/**<product_definition_substitute -> parent_item */
	CaplAttr *a_pdf_subst_guid;
	//@}

	/**@name Язык, на котором указываются атрибуты изделия постовляемого на экспорт */
	//@{
	CaplEntity *e_apl_language;			/**<apl_language */
	
	CaplAttr *a_apl_language_name;	/**<apl_language -> name */
	//@}

	/**@name Атрибуты изделия указываемые при его поставке на экспорт */
	//@{
	CaplEntity *e_apl_export_product;			/**<apl_export_product */
	
	CaplAttr *a_apl_export_product_ofproduct;	/**<apl_export_product -> of_product */
	CaplAttr *a_apl_export_product_language;	/**<apl_export_product -> language */
	CaplAttr *a_apl_export_product_id;			/**<apl_export_product -> id */
	CaplAttr *a_apl_export_product_name;		/**<apl_export_product -> name */
	CaplAttr *a_apl_export_product_code;		/**<apl_export_product -> code */
	CaplAttr *a_apl_export_product_pdf_id;		/**<apl_export_product -> pdf_id */
	CaplAttr *a_apl_export_product_pdf_code;	/**<apl_export_product -> pdf_code */
	CaplAttr *a_apl_export_product_pdf_code1;	/**<apl_export_product -> pdf_code1 */
	CaplAttr *a_apl_export_product_pdf_code2;	/**<apl_export_product -> pdf_code2 */
	CaplAttr *a_apl_export_product_descr;		/**<apl_export_product -> description */
	//@}

	/**@name Изменение атрибутов изделия */
	//@{
	CaplEntity *e_apl_product_attrs_change;			/**<apl_product_attrs_change */
	
	CaplAttr *a_apl_product_attrs_change_item;	/**<apl_product_attrs_change -> item */
	CaplAttr *a_apl_product_attrs_change_id;	/**<apl_product_attrs_change -> id */
	CaplAttr *a_apl_product_attrs_change_name;	/**<apl_product_attrs_change -> name */
	CaplAttr *a_apl_product_attrs_change_code;	/**<apl_product_attrs_change -> code */
	CaplAttr *a_apl_product_attrs_change_pdf_id;	/**<apl_product_attrs_change -> pdf_id */
	CaplAttr *a_apl_product_attrs_change_pdf_code;	/**<apl_product_attrs_change -> pdf_code */
	CaplAttr *a_apl_product_attrs_change_pdf_code1;	/**<apl_product_attrs_change -> pdf_code1 */
	CaplAttr *a_apl_product_attrs_change_pdf_code2;	/**<apl_product_attrs_change -> pdf_code2 */

	CaplAttr *a_apl_product_attrs_change_person;	/**<apl_product_attrs_change -> person */
	CaplAttr *a_apl_product_attrs_change_datetime;	/**<apl_product_attrs_change -> datetime */
	CaplAttr *a_apl_product_attrs_change_status;	/**<apl_product_attrs_change -> status */
	CaplAttr *a_apl_product_attrs_change_next;	/**<apl_product_attrs_change -> prev */
	//@}
	/**@name Связь между изделиями, используемая дл ОГМет (элементы словаря) */
	//@{
	CaplEntity* e_comp_mf;					/**<apl_component_make_from */
	CaplAttr* a_comp_mf_id;					/**<apl_component_make_from -> id */
	CaplAttr* a_comp_mf_ting;				/**<apl_component_make_from -> product_definition */
	CaplAttr* a_comp_mf_ted;				/**<apl_component_make_from -> material */
	CaplAttr* a_comp_mf_unit;				/**<apl_component_make_from -> unit */
	CaplAttr* a_comp_mf_value;				/**<apl_component_make_from -> value */
	CaplAttr* a_comp_mf_derived_unit;		/**<apl_component_make_from -> derived_unit */
	CaplAttr* a_comp_mf_derived_value;		/**<apl_component_make_from -> derived_value */
	CaplAttr* a_comp_mf_type_id;			/**<apl_component_make_from -> type_id */
	CaplAttr* a_comp_mf_type;				/**<apl_component_make_from -> type */
	CaplAttr* a_comp_mf_descr;				/**<apl_component_make_from -> description */
	//@}				

	//**@name Применяемость по заказам */
	//@{
	CaplEntity* e_order_eff;				//*<apl_order_effectivity */
	CaplAttr*    a_order_eff_type;			//*<apl_order_effectivity -> type */
	CaplAttr*    a_order_eff_number;		//*<apl_order_effectivity -> number */
	//@]
	
	//**@name Вариантные правила */
	CaplEntity* e_rule_rels;				//*<apl_rule_select_relation */
	CaplAttr*	a_rule_rels_item;				//*<apl_rule_select_relation -> item */
	CaplAttr*	a_rule_rels_rule;				//*<apl_rule_select_relation -> rule */
	CaplAttr*	a_rule_rels_type;				//*<apl_rule_select_relation -> relation_type */

	CaplEntity*	e_rule_cont;				//*<apl_rule_container */
	CaplAttr*	a_rule_cont_rule;				//*<apl_rule_container -> rule */
	//@]

	// связь между основанием и нормой
	CaplEntity* e_apl_mat_limit_change_rel;
	CaplAttr*    a_mat_limit_change_rel_pdf;
	CaplAttr*    a_mat_limit_change_rel_basis;

	// основание для изменения нормы
	CaplEntity*  e_apl_mat_limit_change_basis;
	CaplAttr*    a_mat_limit_change_basis_id;
	CaplAttr*    a_mat_limit_change_basis_pdf;
	CaplAttr*    a_mat_limit_change_basis_person;
	CaplAttr*    a_mat_limit_change_basis_date_create;
	CaplAttr*    a_mat_limit_change_basis_date_approved;
	CaplAttr*	 a_mat_limit_change_basis_state;
	
	// элемент основания изменения нормы
	CaplEntity*  e_apl_mat_limit_change_item;
	CaplAttr*    a_mat_limit_change_item_change;
	CaplAttr*    a_mat_limit_change_item_descr;
	CaplAttr*    a_mat_limit_change_item_date;
	CaplAttr*    a_mat_limit_change_item_delta;
	CaplAttr*    a_mat_limit_change_item_new_value;
	CaplAttr*	 a_mat_limit_change_item_relation;
	CaplAttr*    a_mat_limit_change_item_material_relation;
	CaplAttr*    a_mat_limit_change_item_new_material;
	CaplAttr*    a_mat_limit_change_item_old_material;
	CaplAttr*    a_mat_limit_change_item_old_warehouse;
	CaplAttr*    a_mat_limit_change_item_new_warehouse;
	CaplAttr*    a_mat_limit_change_item_old_shop;
	CaplAttr*    a_mat_limit_change_item_new_shop;	

	bool bNoCreateAndChangePDF;  // Флаг показывающий что создание pdf и изменение их атрибутов  запрещены. Устанавливается в PSM по настройке при конекте
	int (*funcCompareSN)(CString&, CString&); // Метод для сравнения серийных номеров.
	CString (*funcGetPrevSN)(CString&); // Метод для получения предыдущего серийного номера.
	CString (*funcGetNextSN)(CString&); // Метод для получения следующего серийного номера.
	BOOL (*funcIsKVZSN)(CString&); // Метод для проверки серийного номера на соответствие формату КВЗ.
	BOOL (*funcIntervalIsVerified)(CString&, CString&); // Метод для проверки интервала серийных номеров на соответствие одному из форматов КВЗ.

	// Методы
public:

	// возвращает обозначение изделия
	CString GetProductId(CaplInstance *pdfOrProduct, CString *name = 0);

	// по списку обозначений находит изделия в БД
	bool FindPdfsByIds(const std::set<CString> &ids, aplExtent &result, bool loadAttrs) const;
	
	// Инициализация библиотеки сравнения верийных номеров
	BOOL InitCompareSNLibrary();

	// удаление НРМ и всех входящих в нее элементов
	bool DeleteLimit(CaplInstance *nrm);

	/** формирует норму по конструкторскому составу*/
	bool GenerateLimitByPdf(CaplInstance *nrm, CaplInstance *pdf);

	/** формирует комплект по конструкторскому составу*/
	CaplInstance* GenerateComplectByPdf(CaplInstance *order, CaplInstance *pdf);

	/** Ищет в БД связь между указанными элементами*/
	CaplInstance *FindPdfRelation(CaplInstance* PdfRelating, CaplInstance* PdfRelated);

	/** Считывает информацию о возможных сортаментах в кэш */
	bool LoadAssortment();

	/** Для переданных pdf выводит диалог смены состояния в разрезе создания/заполнения маршрутных карт */
	bool ChangeMkState(CaplInstance *pdf);
	bool ChangeMkState(aplExtent &pdfs);

	/** Возвращает возможные сортаменты изделия
		@param prd  изделиt (PRD)
		@param out_ext список в котором возвращаются найденные сортаменты
		@return true при удачном выполнении и false в случае ошибки */
	bool LoadPrdAssortment(CaplInstance *prd, aplExtent &out_ext);

	/** Сравнивает состав изделий 
		@param exp_pdf - первоначальный список сравниваемых изделий
		@return true при удачном выполнении и false в случае ошибки */
	bool StartCompareProduct(aplExtent &exp_pdf);

	/** Возвращает состав всех версий изделия 
		@param ci конфигурация (не используется)
		@param context контекст (не используется)
		@param prd изделие (PRD)
		@param out_ext список в котором возвращаются найденные версии изделия (PDF)
		@param ext_pdf список в котором возвращаются найденные версии входящих изделий (PDF)
		@param ext_rel список в котором возвращаются найденные связи (NAUO)
		@param from_base  просматривать ли данные из БД. Если false то просматривается только кэш
		@return true при удачном выполнении и false в случае ошибки */
	bool LoadAllSubProduct(CaplInstance *ci, CaplInstance *context,
		CaplInstance *prd, aplExtent &out_ext, aplExtent &ext_rel, aplExtent &ext_pdf, bool from_base=true);
	
	/** Возвращает состав изделия 
		@param ci конфигурация (не используется)
		@param context контекст (не используется)
		@param pdf версия изделия (PDF)
		@param out_ext список в котором возвращаются найденные версии изделий (PDF)
		@param out_rel список в котором возвращаются найденные связи (NAUO)
		@param from_base  просматривать ли данные из БД. Если false то просматривается только кэш
		@return true при удачном выполнении и false в случае ошибки */
	bool LoadAllSubProduct(CaplInstance *ci, CaplInstance *context,
		CaplInstance *pdf, aplExtent &ext_rel, aplExtent &ext_pdf, bool from_base=true);
	bool LoadAllSubProduct(aplExtent &parents, aplExtent &ext_rel, aplExtent &ext_pdf, bool from_base=true);
	/** Возвращает состав изделия 
		@param ci конфигурация (не используется)
		@param context контекст (не используется)
		@param pdf версия изделия (PDF)
		@param out_ext список в котором возвращаются найденные версии изделий (PDF)
		@param out_rel список в котором возвращаются найденные связи (NAUO)
		@param from_base  просматривать ли данные из БД. Если false то просматривается только кэш
		@return true при удачном выполнении и false в случае ошибки */
	bool LoadAllSubProductEx(CaplInstance *ci, CaplInstance *context,
		CaplInstance *pdf, aplExtent &ext_rel, aplExtent &ext_pdf, bool from_base=true,
		UINT flag = APL_LOAD_ASSEMBLY_COMPONENT_USAGE|APL_LOAD_MAKE_FROM_USAGE_OPTION|APL_LOAD_DESING_MAKE_FROM_RELATIONSHIP);

	/** Возвращает заготовки (материалы) из которых может быть изготовлена данная версия изделия
		@param pdf версия изделия (PDF)
		@param out_ext список в котором возвращаются найденные версии изделий (PDF)
		@param out_rel список в котором возвращаются найденные связи (MFUO)
		@param include_design  указывает включать ли design_make_from_relationship. Если true то включать
		@param from_base  просматривать ли данные из БД. Если false то просматривается только кэш
		@return true при удачном выполнении и false в случае ошибки */
	bool LoadAllZagotov(CaplInstance *pdf, aplExtent &ext_rel, aplExtent &ext_pdf,
		bool include_design = false ,bool from_base=true);

	/** Возвращает заготовки (материалы) из которых может быть изготовлен перечень изделий
		@param ext_pdf версия изделия (PDF)
		@param out_ext список в котором возвращаются найденные версии изделий (PDF)
		@param out_rel список в котором возвращаются найденные связи (MFUO)
		@param include_design  указывает включать ли design_make_from_relationship. Если true то включать
		@param from_base  просматривать ли данные из БД. Если false то просматривается только кэш
		@param show_status_dlg показывать диалог состояния загрузки (только при загрузке из БД)
		@return true при удачном выполнении и false в случае ошибки */
	bool CaplProductManager::LoadAllZagotov(aplExtent &ext_pdf, aplExtent &ext_rel, aplExtent &out_ext,
		bool include_design , bool from_base=true,bool show_status_dlg=false);

	/** Возвращает заготовки (материалы) из которых может быть изготовлена данная версия изделия
		@param pdf версия изделия (PDF)
		@param out_ext список в котором возвращаются найденные версии изделий (PDF)
		@param out_rel список в котором возвращаются найденные связи (MFUO)
		@param from_base  просматривать ли данные из БД. Если false то просматривается только кэш
		@return true при удачном выполнении и false в случае ошибки */
	bool LoadAllOGmet(CaplInstance *pdf, aplExtent &ext_rel, aplExtent &ext_pdf,
		bool from_base=true);

	/** Возвращает материалы ОГМет из которых может быть изготовлен перечень изделий
		@param ext_pdf версия изделия (PDF)
		@param out_ext список в котором возвращаются найденные версии изделий (PDF)
		@param out_rel список в котором возвращаются найденные связи (MFUO)
		@param from_base  просматривать ли данные из БД. Если false то просматривается только кэш
		@param show_status_dlg показывать диалог состояния загрузки (только при загрузке из БД)
		@return true при удачном выполнении и false в случае ошибки */
	bool LoadAllOGmet(aplExtent &ext_pdf, aplExtent &ext_rel, aplExtent &out_ext,
		bool from_base,bool show_status_dlg=false);

	/** Возвращает изделия-заменители в контексте сборки
		@param pdr сборка (PDR)
		@param ext_rel список в котором возвращаются найденные связи (PRODUCT_DEFINITION_SUBSTITUTE)
		@param ext_pdf список в котором возвращаются найденные версии изделий (PDF)
		@param from_base  просматривать ли данные из БД. Если false то просматривается только кэш
		@return true при удачном выполнении и false в случае ошибки */
	bool LoadAllSubstitutes(CaplInstance *pdr, aplExtent &ext_rel, aplExtent &ext_pdf,bool from_base=true);

	/** Поиск экземпляра изделия, партии и/или версии изделия
		@param ciItem - выбранная версия изделия или экземпляр изделия
		@param ciLot - выбранная партия
		@param bOnlyPrdIns - позволить выбрать именно prd_inst, а не pdf
		@param bDisableLot - убрать возможность выбора партии
		@param bDisablePrdInst - убрать возможность выбора экземпляра изделия
		@param sSpravId - обозначение справочника изделий*/
	bool FindPKIEx(CaplInstance **ciItem, CaplInstance **ciLot, bool bOnlyPrdIns=false, bool bDisableLot=false, bool bDisablePrdInst=false,LPCTSTR sSpravId=0);

	/** Возвращает список сборок, в которых используется в качестве заменителя
		@param subst_pdf версия изделия, для которой производится поиск (PDF)
		@param ext_rel список в котором возвращаются найденные связи (PRODUCT_DEFINITION_SUBSTITUTE)
		@param ext_pdr список в котором возвращаются найденные 'контексты замены' (NAUO)
		@param from_base  просматривать ли данные из БД. Если false то просматривается только кэш
		@return true при удачном выполнении и false в случае ошибки */
	bool WhereUsedAsSubstitute(CaplInstance *subst_pdf, aplExtent &ext_rel, aplExtent &ext_pdr,bool from_base);

	/** Возвращает список версий изделий в которых данное используется 
		@param pdf версия изделия (PDF)
		@param out_ext список в котором возвращаются найденные версии изделий (PDF)
		@param out_rel список в котором возвращаются найденные связи (NAUO)
		@param from_base  просматривать ли данные из БД. Если false то просматривается только кэш
		@param bPdr просматривать ли связи между изделиями
		@param bAlt просматривать ли аналоги
		@return true при удачном выполнении и false в случае ошибки */
	bool WhereUsedProduct(CaplInstance *pdf, aplExtent &ext_rel, aplExtent &ext_pdf, bool from_base=true, bool bPdr=true, bool bAlt=true);
	bool WhereUsedProduct(aplExtent &pdfs, aplExtent &ext_rel, aplExtent &ext_pdf, bool from_base=true, bool bPdr=true, bool bAlt=true);

	/** Возвращает список версий изделий являющихся внешними обозначениями 
		@param pdf версия изделия (PDF)
		@param out_ext список в котором возвращаются найденные версии изделий (PDF)
		@param out_rel список в котором возвращаются найденные связи (SPR)
		@param from_base  просматривать ли данные из БД. Если false то просматривается только кэш
		@return true при удачном выполнении и false в случае ошибки */
	bool LoadSupliedProduct(CaplInstance *pdf, aplExtent &ext_rel, aplExtent &ext_pdf, bool from_base=true);

		/** Возвращает список заменяющих изделий 
		@param prd заменяемое изделие (PDF)
		@param out_ext список в котором возвращаются заменяющие изделия (PRD)
		@param out_rel список в котором возвращаются найденные связи (alternate)
		@return true при удачном выполнении и false в случае ошибки */
	bool LoadProductAlternates(CaplInstance *prd, aplExtent &ext_rel, aplExtent &ext_prd);

		/** Возвращает список заменяющих версий изделий 
		@param prd заменяемая версия изделия (PDF)
		@param ext_rel список в котором возвращаются свзи замен (apl_alternate_pdf_relation)
		@param ext_pdf список в котором возвращаются найденные версии изделия (apl_alternate_pdf_relation)
		@return true при удачном выполнении и false в случае ошибки */
	bool LoadPdfAlternates(CaplInstance *pdf, aplExtent &ext_rel, aplExtent &ext_pdf);


		/** Возвращает список заменяемых версий изделий 
		@param prd заменяемая версия изделия (PDF)
		@param ext_rel список в котором возвращаются свзи замен (apl_alternate_pdf_relation)
		@param ext_pdf список в котором возвращаются найденные версии изделия (apl_alternate_pdf_relation)
		@return true при удачном выполнении и false в случае ошибки */
	bool LoadPdfAlternateReady(CaplInstance *pdf, aplExtent &ext_rel, aplExtent &ext_pdf);

		/** Возвращает список заменяющих изделий (список связей состоит из объектов c учётом типа взаимозаменяемости (e_alt_bidirect))
		@param prd заменяемое изделие (PDF)
		@param out_ext список в котором возвращаются заменяющие изделия (PRD)
		@param out_rel список в котором возвращаются найденные связи (alternate)
		@return true при удачном выполнении и false в случае ошибки */
	bool LoadProductBidirectAlternates(CaplInstance *prd, aplExtent &ext_relBase, aplExtent &ext_prdBase, aplExtent &ext_relAlt, aplExtent &ext_prdAlt);

		/** Возвращает разузлованный состав изделия (со связями между ними)
		@param context контекст 
		@param pdf версия изделия (PDF)
		@param ext_rel список в котором возвращаются связи (ACU) между изделиями
		@param ext_out список в котором возвращаются версии изделий (PDF) входящие в pdf
		@param count_array список в котором i-ый элемент указывает количество входящих в pdf i-ых элементов ext_pdf
		@param ext_unit список в котором котором i-ый элемент указывает единицу измерения для ext_pdf
		@param not_disas_types типы изделий, которые не нужно разузловывать
		@param not_disas_sources източники изделий, которые не нужно разузловывать
		@return true при удачном выполнении и false в случае ошибки */
	bool DisassemblyProduct(CaplInstance *context,CaplInstance *pdf,aplExtent &ext_rel,aplExtent &ext_out, aplRealArray &count_array, aplExtent &ext_unit,const TCHAR *filter_date=0,const TCHAR *filter_sn=0,bool ReturnOnlyPart=false,CStringArray *not_disas_types=0,CStringArray *not_disas_sources=0, CaplInstance *pComplectation = NULL);

	/** Возвращает разузлованный состав изделия 
		@param ci конфигурация 
		@param context контекст (не используется)
		@param pdf версия изделия (PDF)
		@param ext_pdf список в котором возвращаются версии изделий (PDF) входящие в pdf
		@param count_array список в котором i-ый элемент указывает количество входящих в pdf i-ых элементов ext_pdf
		@param ext_unit список в котором котором i-ый элемент указывает единицу измерения для ext_pdf
		@param ReturnOnlyPart указывет возвращать ли все входящие изделия или только нижний уровень. Если ReturnOnluPart
		ReturnOnlyPart == true, то выполняется разузлование, в противном случае возвращаются все промежуточные уровни
		@return true при удачном выполнении и false в случае ошибки */
	bool DisassemblyProduct(CaplInstance *ci, CaplInstance *context,	CaplInstance *pdf, 
		aplInstArray &ext_pdf, aplRealArray &count_array, aplInstArray &ext_unit, bool ReturnOnlyPart=true, CaplInstance *pComplectation = NULL);

	/** Возвращает разузлованный состав изделия c учетом применяемости
		@param ci конфигурация 
		@param context контекст (не используется)
		@param pdf версия изделия (PDF)
		@param ext_pdf список в котором возвращаются версии изделий (PDF) входящие в pdf
		@param count_array список в котором i-ый элемент указывает количество входящих в pdf i-ых элементов ext_pdf
		@param ext_unit список в котором котором i-ый элемент указывает единицу измерения для ext_pdf
		@param ReturnOnlyPart указывет возвращать ли все входящие изделия или только нижний уровень. Если ReturnOnluPart
		ReturnOnlyPart == true, то выполняется разузлование, в противном случае возвращаются все промежуточные уровни
		@param pComplectation Комплектация (только для КВЗ)
		@param IsNoDisasemblyItem - функция определяющая надо ли разузловывать pdf
		@return true при удачном выполнении и false в случае ошибки */
	bool DisassemblyProductEx(CaplInstance *ci, CaplInstance *context,	CaplInstance *pdf, 
		aplInstArray &ext_pdf, aplRealArray &count_array, aplInstArray &ext_unit,
		COleDateTime *time=0, const TCHAR *sn=0, bool ReturnOnlyPart=true, CaplInstance *pComplectation = NULL,
		bool (*IsNoDisasemblyItem)(CaplInstance *pdf)=0);

	bool DisassemblyProductEx2(CaplInstance *ci, CaplInstance *context,	CaplInstance *pdf, 
		aplInstArray &ext_pdf, aplRealArray &count_array, aplInstArray &ext_unit,
		COleDateTime *time=0, const TCHAR *sn=0, bool ReturnOnlyPart=true, CaplInstance *pComplectation = NULL,
		bool (*IsNoDisasemblyItem)(CaplInstance *pdf)=0);

	/** Фильтрует  связи изделий (NAUO) по серийным номерам  
		@param inExt  список связей изделий (NAUO) который фильтруется
		@param sn  серийный номер
		@param out_rel  полученный список связей изделий (NAUO) (результат)
		@return true при удачном выполнении и false в случае ошибки */
	bool FilterlBySN(aplExtent &inExt, const TCHAR *sn, aplExtent &outExt);

	/** Фильрует ограниченные (с заполненным граничным значением "по") связи изделий (NAUO) 		
		@param inExt  список связей изделий (NAUO) который фильтруется
		@param out_rel  полученный список связей изделий (NAUO) (результат)
		@return true при удачном выполнении и false в случае ошибки */
	bool FilterlByLastSN(aplExtent &inExt, aplExtent &outExt);

	/** Фильтрует связи изделий (NAUO) по дате 
		@param inExt  список связей изделий (NAUO) который фильтруется
		@param time дата
		@param out_rel  полученный список связей изделий (NAUO) (результат)
		@return true при удачном выполнении и false в случае ошибки */
	bool FilterlByDate(aplExtent &inExt, COleDateTime &time, aplExtent &outExt);

	/** фильтрует связки (apl_qacu) по изменению
	  @param rels - исходный набор связок (apl_qacu)
	  @param change - изменение (apl_change)
	  @param extOut - полученный набор (!может содержать qacu и psc!)
	  @param extParents - сборки, для которых будет учитываться изменение на добавление (если NULL, то будут учтены все добавления)
	  @param bLoadFromBase - надо ли загружать элементы изменения и их атрибуты */
	bool FilterByChange(aplExtent &rels, CaplInstance *change, aplExtent &extOut, aplExtent *extParents = NULL, bool bLoadFromBase = false);

	/** Отображает диалог выбора фильтра по серийному номеру, дате и контексту
		@param time дата по умолчанию
		@param sn серийный номер по умолчанию
		@param context по умолчанию
		@param chosen_context выбранный контекст
		@return true при удачном выполнении и false в случае ошибки */
	bool SelectDateSN(CString &sn, COleDateTime &time, CaplInstance *context,CaplInstance **chosen_context);
	
	/** Отображает диалог выбора конфигурации для объекта
		@param pPdf изделие, из конфигураций которого можно выбирать
		@param pConfiguration выбранная конфигурация
		@param pOrder выбранный заказ, соответствующий выбранной конфигурации
	*/
	bool SelectConfiguration(CaplInstance *pPdf, CaplInstance** pConfiguration, CaplInstance** pOrder=NULL);

	/** Возвращает все версии изделия 
		@param prd  изделие
		@param prds массив изделий
		@param outExt  список версий изделия (результат)
		@return true при удачном выполнении и false в случае ошибки */
	bool GetAllProductVersion(CaplInstance *prd,aplExtent &outExt);
	bool GetAllProductVersion(aplExtent &prds,aplExtent &outExt);

	/** Ищет изделие (PRD) по обозначению 
		@param id  обозначение изделия
		@return найденное изделие (PRD) и NULL если тагого нет */
	CaplInstance *FindPrdById(const TCHAR *id, bool bIgnoreSpaces= false);

	/** Ищет версию изделия (PDF) по обозначению
		@param prd  изделие (PRD)
		@param id  обозначение версии изделия
		@return найденное изделие (PDF) и NULL если тагого нет */
	CaplInstance *FindPdfById(CaplInstance *prd, const TCHAR *id, bool bIgnoreSpaces= false);

	/** Ищет версию изделия (PDF) по коду
		@param code  код версии изделия
		@return найденное изделие (PDF) и NULL если тагого нет */
	CaplInstance *FindPdfByCode(const TCHAR *code, bool bIgnoreSpaces= false);
	CaplInstance *FindPdfByCode1(const TCHAR *code1, bool bIgnoreSpaces= false);


	/** Читает информацию об изделии из базы в кэш 
		@param prd  изделие (PRD или PDF)
		@return true при удачном выполнении и false в случае ошибки */
	bool LoadPrdInfo(CaplInstance *inst);

	/** Читает информацию об изделиях из базы в кэш 
		@param ext  список изделий (PRD или PDF)
		@return true при удачном выполнении и false в случае ошибки */
	bool LoadPrdInfo(aplExtent &ext);
	
	/** Создает версию изделия 
		@param id  обозначение изделия
		@param name  наименование изделия
		@param ver  обозначение версии изделия
		@param testunique  требуется ли искать подобное в БД. true если требуется и false в противном случае
		@return созданная версия изделия (PDF) и NULL в случае ошибки  */
	CaplInstance *CreatePdf(const TCHAR *id,const TCHAR *name, const TCHAR *ver, bool testunique=true);
	CaplInstance *CreatePdf(CaplInstance* prd, const TCHAR *ver, bool testunique=true);
	
	/** Создает связь "вхождение в сборку" (NAUO) между версиями изделий 
		@param context контекст (не используется)
		@param relating_pdf  включающая версия изделия
		@param related_pdf  включаемая версия изделия
		@param id  обозначение связи (позиция)
		@param name  наименование связи
		@param count  количесво
		@param unit  единица измерения количества
		@return созданная связь (NAUO) и NULL в случае ошибки  */
	CaplInstance *CreatePdfRelation(CaplInstance *context,
		CaplInstance *relating_pdf, CaplInstance *related_pdf,
		const TCHAR *id,const TCHAR *name, double count, CaplInstance *unit=0, bool bTestUnique=false, bool bTestForCycle = true);
	
	/** Создает связь "взаимозамеянемость" между версиями изделий 
		@param context контекст (не используется)
		@param base_pdf  основное изделие
		@param alternate_pdf  изделие аналог
		@param name  наименование связи
		@param descr описание связи
		@param type  тип связи
		@param type_descr описание типа связи
		@param reserved зарезервированное текстовое поле (на данный момент не используется)
		@return созданная связь (NAUO) и NULL в случае ошибки  */
	CaplInstance *CreatePdfAlternateRelation(CaplInstance *context,
		CaplInstance *base_pdf, CaplInstance *alternate_pdf,
		const TCHAR *name, const TCHAR *descr, int type, const TCHAR* type_descr, const TCHAR* reserved, bool bTestUnique=false);

	/** Проверяет цикличность связи "взаимозаменяемость" между версиями изделий
	@return <b>false</b> если цикл будет и <b>true</b> если нет */
	bool TestCycleInAlternateRelation (CaplEntity *ent, CaplAttr *in_attr, CaplAttr *out_attr, CaplInstance *in_val, CaplInstance *out_val);

	/** Создает связь "вхождение в контексте сборки" (PDF_SUBSTITUTE)  
		@param context_pdr контекст (сб.единица)
		@param subst_pdf  включаемая (заменяющая) версия изделия
		@param id    обозначение связи (позиция)
		@param descr описание связи
		@param count количесво
		@param unit  единица измерения количества
		@return созданная связь (NAUO) и NULL в случае ошибки  */
	CaplInstance *CaplProductManager::CreateSubstitute(CaplInstance *context_pdr,
		CaplInstance *subst_pdf,const TCHAR *id=0,const TCHAR *name=0,const TCHAR *descr=0, double count=0, CaplInstance *unit=0);
	CaplInstance *CaplProductManager::CreateSubstitute(CaplInstance *pdr, CaplInstance *subst_pdf, CaplInstance *parent_pdf, const TCHAR *id=0, double count=0, CaplInstance *unit=0);

	/**	Поиск вариантов замены версии изделия. Применяется в ATLAS*/
	bool FindPdfSubstitutes(CaplInstance *pdr, CaplInstance *parent_item, aplExtent &ext_pdfs, aplExtent *ext_subst = NULL, bool bFromBase = true);
	
	/**	Поиск вариантов замены версии изделия. Применяется в ATLAS*/
	bool FindPdfSubstitutes(aplExtent &pdrs, CaplInstance *parent_item, aplExtent &ext_pdfs, aplExtent *ext_subst = NULL, bool bFromBase = true);

	/** Вызывает менеджер применямости изделия
		@param ci конфигурация (не используется)
		@param context контекст (не используется)
		@param pdf версия изделия (PDF)
		@param rel список связей изделия(ACU)
		@return true при удачном выполнении и false в случае ошибки */
	bool StartEffectivityManager(CaplInstance *ci, CaplInstance *pdf, CaplInstance *context, CaplEntity * rel);

	/** Удаляет версию изделия и само изделие если эта версия единственная
		@param inInst кверсия изделия (pdf)
		@param recursive надо ли удалять входящие (true если надо)
		@return true при удачном выполнении и false в случае ошибки */
	bool DeleteProductVersion(CaplInstance *pdf, bool recursive=false);
	bool DeleteProductWithAllVersion(CaplInstance *prd, bool recursive=false);

	/**Создает изделие по шаблону и привязывает его к item
	@param item указатель на объект, к которому необходимо привязать изделие
	@param res массив содержащий все новые изделия, версии, документы, характеристики
	@return созданное изделие (его версию) и NULL в случае ошибки*/
	CaplInstance *CreatePdfByDot(CaplInstance *item, aplExtent &res);

	/**Отображает свойства изделия, версии изделия, связи.
	@param Inst изделие, версия изделия
	@param lpszEditMode режим работы:aplPrdDlgmode
	@param rel связь
	@param subs связь-замена
	@return true в случае, когда свойства объекта изменились и false в противном случае*/
	bool ShowProperties(CaplInstance* Inst, aplPrdDlgmode editMode = aplModeEdit, CaplInstance* rel = NULL, CaplInstance* subst = NULL);

	/**Создать изделие, версию изделия, связи.
	@param Inst базовое изделие, базовая версия изделия
	@param lpszEditMode режим работы:aplPrdDlgmode
	@return true в случае, когда свойства объекта изменились и false в противном случае*/
	CaplInstance* CreateProduct(CaplInstance* Inst = NULL, aplPrdDlgmode editMode = aplModeCreateVersion);
	bool CreateSubProduct(CaplInstance* Parent, CaplInstance **BaseItem, CaplInstance** nuao);

	/** Создать копию изделия*/
	bool CreateProductCopy(CaplInstance* Parent, CaplInstance **BaseItem, CaplInstance** nuao);

	/** Преобразует англ. тип изделия в русский*/
	static	const TCHAR *StrConvertPdfType2Rus(const TCHAR *type);

	/** Преобразует руссий тип изделия в англ.*/
	static	const TCHAR *StrConvertRus2PdfType(const TCHAR *type);

	//* Преобразует англ. тип изделия в русский*/
	static	const TCHAR *StrConvertMakeOrBuy2Rus(const TCHAR *src);

	//* Преобразует руссий тип изделия в англ.*/
	static	const TCHAR *StrConvertRus2MakeOrBuy(const TCHAR *src);

	/** Создать описание языка в БД
	@param name наименование языка
	@return созданное или найденное в БД описание языка*/
	CaplInstance* CreateLanguage(LPCTSTR lpszName);

	/** Есть у техпроцесса (маршрутки) операции с зачекиненым локером
	@param techprocess проверяемый техпроцесс */
	bool IsTechprocessContainsLockers(CaplInstance *techprocess);

	/** Удаляет описание языка из БД
	return true если язык удален и false в противном случае*/
	bool DeleteLanguage(CaplInstance* Language);

	/** Отображает диалоговое окно выбора языка
	@param <in> язык по-умолчанию <out> выбранный язык
	return true если выбран язык и нажата клавиша ОК и false в противном случае*/
	bool SelectLanguage(CaplInstance** SelectedLanguage = NULL);

	/** Создает описание изделия на другом языке
	@param Prd изделие (версия изделия), для которого создается описание на другом языке
	@param language язык, на котором создается описание изделия
	@param lpszId обозначение изделия на языке language
	@param lpszName наименование изделия на языке language
	@param lpszCode код изделия на языке language
	@return созданное описание изделия на другом языке*/
	CaplInstance* CreateExportProduct(CaplInstance* Item, CaplInstance* language, LPCTSTR lpszId = NULL, LPCTSTR lpszName = NULL, LPCTSTR lpszCode = NULL,
		LPCTSTR lpszPdfId = NULL, LPCTSTR lpszPdfCode = NULL, LPCTSTR lpszPdfCode1 = NULL, LPCTSTR lpszPdfCode2 = NULL, LPCTSTR lpszDescr = NULL);
	
	/** Поиск описаний изделия на иностранных языках
	@param Product изделие, для которого ищутся описания на иностранных языках
	@param ExPrds найденные описания
	@param Langs указатель на массив используемых языков
	@return true при удачном выполнении и false в случае ошибки */
	bool FindExportProducts(CaplInstance* Product, aplExtent &ExPrds, aplExtent *Langs = NULL);

	/** Возвращает описание изделия на указанном языке
	@param Product изделие, для которого ищутся описания на иностранных языках
	@param Language язык
	@param bFromBase зачитывать информацию из БД или использовать информацию имеющуюся в КЕШе
	@return найденное описание изделия на иностранном языке и NULL в противном случае*/
	CaplInstance* GetExportProduct(CaplInstance* Product, CaplInstance* Language, bool bFromBase = true);

	/** Отображает описания изделия на иностранных языках
	@param Product изделие, для которого ищутся описания на иностранных языках
	@param Language язык отображаемый по умолчанию
	@return true при удачном выполнении и false в случае ошибки */
	bool ShowExportProduct(CaplInstance* Product, CaplInstance* Language = NULL);

	/** Читает в КЭШ информацию о языках*/
	bool LoadDictionary();

	/** Создает объект изменение атрибутов изделия
	@param Item изделие или описание изделия на другом языке, у которого меняются атрибуты
	@param lpszId новое обозначение изделия
	@param lpszName новое наименование изделия
	@param lpszCode новый код изделия
	@return созданное изменение атрибутов изделия*/
	CaplInstance* CreateProductAttrsChange(CaplInstance* Item, LPCTSTR lpszId = NULL, LPCTSTR lpszName = NULL, LPCTSTR lpszCode = NULL, 
		LPCTSTR lpszPdfId = NULL, LPCTSTR lpszPdfCode = NULL, LPCTSTR lpszPdfCode1 = NULL, LPCTSTR lpszPdfCode2 = NULL);

	/** Поиск предпоследних значений атрибутов изделия (последние значения записаны в объекте <изделие> или <описание на иностранном языке>)
	@param Item изделие или описание изделия на другом языке
	@param bFromBase зачитывать информацию из БД или использовать информацию имеющуюся в КЕШе
	@return найденный объект изменение атрибутов и NULL, если такой не найден*/
	CaplInstance* FindLastestAttrChange(CaplInstance* Item, bool bFromBase);
	
	/** Поиск всех изменений атрибутов изделия
	@param Item изделие или описание изделия на другом языке
	@param ext найденные изменения атрибутов
	@return true при удачном выполнении и false в случае ошибки */
	bool FindallAttrsChanges(CaplInstance* Product, aplExtent &ext);

	/** Отобразить историю изменения атрибутов изделия
	@param Item изделие или описание изделия на другом языке, у которого меняются атрибуты
	@return true при удачном выполнении и false в случае ошибки */
	bool ShowHistory(CaplInstance* Item);

	/** Поиск всех применяемостей для product_definition_relationship
	@param Pdr связь изделий
	@param ext найденные применяемости
	@param load_from_server bcrfnm на сервере
	@return true при удачном выполнении и false в случае ошибки */
	bool FindAllPDFEffectiviti(CaplInstance* Pdr, aplExtent &ext, bool load_from_server=false);

	/** Для переданных операций маршрутки меняет внутреннюю нумерацию по цехам
	@param tpo все операции техпроцесса
	@param bSaveChanes сохранять ли изменения сразу */
	void ReNumberOperations(aplExtent &tpo, bool bSaveChanes);

	/** Читает информацию о заменах из базы в кэш 
	@param ext  список замен (PDF_substitute)
	@return true при удачном выполнении и false в случае ошибки */
	bool LoadSubstituteInfo(aplExtent &ext);

	/** заполняет комбобокс возможными видами техпроцесса */
	void FillTechProcessTypeCombo(CComboBox &combo, CaplInstance *process);

	/** заполняет комбобокс возможными классами техпроцесса */
	void FillTechProcessClassCombo(CComboBox &combo, CaplInstance *process);

	/** сохранить класс техпроцесса на основе выделенного элемента в комбобоксе */
	void SaveTechProcessClass(CComboBox &combo, CaplInstance *process);
	void SaveTechProcessClass(const CString &clas, CaplInstance *process);

	/** сохранить класс техпроцесса на основе выделенного элемента в комбобоксе */
	void SaveTechProcessType(CComboBox &combo, CaplInstance *process);
	void SaveTechProcessType(const CString &type, CaplInstance *process);

	/** проверка цеха на "гальванику" */
	bool IsGalvanicKvzShop(LPCTSTR shop);
	
	//* Список типов изделий - деталь, сборка и т.п.*/
	CArray<CString,CString> m_list_pdf_types;
	
	//* Список типов изделий - покупное, изготавливаемое и т.п.*/
	CArray<CString,CString> m_list_mob_types;

	/** Список русско-английскких видов техпроцессов */
	std::vector<std::pair<CString, CString>> m_techProcessType;

	/** Список русско-английскких классов техпроцессов */
	std::vector<std::pair<CString, CString>> m_techProcessClass;

	/** цеха покрытия и термообработки КВЗ */
	std::set<CString> m_kvzTermoShops;

	// Создает ассоциированный с PDF документ ЭСИ  (Такая хрень для Созвездия) 
	// Возвращает ссылку на версию
	// num_change - номер изменения для записи в метку 
	// bShowResultMessage - вывести сообщение о результате
	// sLog - Переменная для записи лога (вместо сообщений)
	CaplInstance *GenerateESI(CaplInstance *pdf, LPCTSTR num_change, bool bShowResultMessage, CString *sLog=0);


	bool GenerateESI4Ext(aplExtent &ext,  bool bShowResultMessage);

	// Сравнивает ЭСИ в документе и структуру в БД
	bool CompareDocWintESI(CaplInstance *doc_or_revision);
};


// *************************************************************************
// *************************************************************************
// *************************************************************************
/** Менеджер папок*/
class CLASS_DECL_APL_STEP_MGR CaplFolderManager: public CaplStepManager
{
private:
	long m_wait_dialog;
	// Инициализация

public:
	static BOOL m_create_assoc_folder_doc;

	CMap<DWORD, DWORD, CString, CString> *m_folders_map;
	/** Инициализирует класс (Ассоциация с классом базы данных) 
		@return true при удачном выполнении и false в случае ошибки */
	virtual bool Attach(CaplAPI *api);
	virtual void Detach();

	CaplEntity *e_folder;
	CaplAttr *a_folder_name,*a_folder_descr,*a_folder_parent, *a_folder_guid;
	CaplAttr 	*a_folder_content, *a_folder_contexts;
	CaplAttr 	*a_folder_packet_date,*a_folder_packet_size,*a_folder_packet_body;
	// Методы
public:
	/** Читает всю информацию о папке 
		@param folder папка
		@param bLoadContent если true, то грузятся все атрибуты включая содержимое, иначе только мин. надор атрибутов 
		@return true при удачном выполнении и false в случае ошибки */	
	bool LoadFolderInfo(CaplInstance *folder, bool bLoadContent = true);

	/** Читает всю информацию о папках 
		@param ext папки
		@param bLoadContent если true, то грузятся все атрибуты включая содержимое, иначе только мин. надор атрибутов 
		@return true при удачном выполнении и false в случае ошибки */	
	bool LoadFolderInfo(aplExtent &ext, bool bLoadContent = true);

	/** Возвращает входящие папки 
		@param folder папка
		@param out_ext список входящих папок (результат)
		@param recursive если true то раскручивает папки рекрсивно. Если false - то только первый уровень
		@param bLoadContent если true, то грузятся все атрибуты включая содержимое, иначе только мин. надор атрибутов 
		@return true при удачном выполнении и false в случае ошибки */
	bool GetAllSubFolder(CaplInstance *folder,aplExtent &out_ext,bool recursive=false, bool bLoadContent = true);

	/** Создает папку 
		@param parent родительская папка
		@param name наименование папки
		@param descr описание папки
		@return созданная папка и NULL в случае ошибки  */
	CaplInstance *CreateFolder(CaplInstance *parent, const TCHAR * name, const TCHAR *descr);

	/** Удаляет папку 
		@param folder папка
		@return true при удачном выполнении и false в случае ошибки */
	bool DeleteFolder(CaplInstance *folder);

	/** Возвращает содержимое папки 
		@param folder папка ( или уровень справочника)
		@param out_ext список входящих объектов (результат)
		@return true при удачном выполнении и false в случае ошибки */
	bool GetFolderContents(CaplInstance *folder,aplExtent &out_ext, bool bWithAttrs = true);
	/** Поиск item в folder 
		@param folder папка
		@param item искомый объект
		@return true если найден,иначе - false */
	bool FindInFolder(CaplInstance *folder, CaplInstance *item);

	/** Поиск папок, в которые входит item 
		@param item искомый объект
		@param folders список папок
		@return true при удачном выполнении и false в случае ошибки */
	bool FindFolderContained(CaplInstance *item, aplExtent &folders);

	/** Добавляет item в folder 
		@param folder папка
		@param item добавляемый объект
		@return true при удачном выполнении и false в случае ошибки */
	bool AddToFolder(CaplInstance *folder, CaplInstance *item);
	bool AddToFolder(CaplInstance *folder, aplExtent &items);
	
	/** Удаляет item из folder 
		@param folder папка
		@param item удаляемый объект
		@return true при удачном выполнении и false в случае ошибки */
	bool RemoveFromFolder(CaplInstance *folder,CaplInstance *item);
	bool RemoveFromFolder(CaplInstance *folder, aplExtent &items);

	/** Показывает свойства папки 
		@param folder папка
		@return true при удачном выполнении и false в случае ошибки */
	bool ShowFolderProperties(CaplInstance *folder);

	/** Перемещает папку  
		@param folder перемещаемая папка
		@param parent папка в которую происходит перемещение
		@param message - если не равно NULL, то сообщения не выводятся, а помещаются в этот параметр
		@return true при удачном выполнении и false в случае ошибки */	
	bool MoveFolder(CaplInstance *folder, CaplInstance *parent, CString *message = NULL);

	/** Отображает содержимое папки в виде таблицы
		@param folder папка
		@param is_hide_move_button
		@param redraw
		@return true при удачном выполнении и false в случае ошибки */	
	bool MakeTable(CaplInstance *folder,bool is_hide_move_button=true,bool *redraw=0,bool show_assoc_doc=false,bool is_context_menu_categ = false);

	//  Функции для работы с SourceSafe
	
	/** Сохраняет все документы из выбранной папки на диск
	    @param folder выбранная папка
		@param defpath папка на диске
		@param checkout брать документы на редактирование или брать активную версию
		@return true при удачном выполнении и false в случае ошибки */	
	bool CopyDocOnDisk(CaplInstance *folder, CString &defpath, int mode = APL_COPY_DOCS);

	/** Сохраняет все документы из выбранной папки на диск, взять все документы из папки на редактирование, печатать все документы из папаки
	    @param folder выбранная папка
		@param defpath папка на диске
		@param checkout брать документы на редактирование или брать активную версию
		@param rec_doc обрабатывать связанные документы
		@param set_RO устанавливать на файл атрибут "Только для чтения"
		@return true при удачном выполнении и false в случае ошибки */	
	bool CopyDocOnDisk(aplExtent &docs, CString path, bool recursive = true, int mode = APL_COPY_DOCS, bool rec_doc = true, bool set_RO = true);

	/**	Берет на редактирование или копирует активные версии на диск
		@param doc документ
		@param path папка на диске
		@param checkout брать на редактирование или копировать активные версии
		@return true при удачном выполнении и false в случае ошибки */	
	bool RecursiveCopyDocs(CaplInstance *doc, CString path, int mode = APL_COPY_DOCS, bool set_RO = true);
	
	/** Добавляет файлы с диска
		@param folder папка, к которой необходимо привязать документ
		@param defpath папка на диске
		@return true при удачном выполнении и false в случае ошибки */	
	bool AddDocFromDisk(CaplInstance *folder, CString &defpath);
	
	/** Добавляет файлы из выбранной папки
		@param folder папка, к которой необходимо привязать документ
		@param defpath папка на диске
		@return true при удачном выполнении и false в случае ошибки */	
	bool AddDocFromPath(CaplInstance *folder, CString &defpath);

	/** Добавляет файлы из выбранной папки
		@param folder папка, к которой необходимо привязать документ
		@param path папка на диске
		@param recirsive обрабатывать вложенные папки
		@return true при удачном выполнении и false в случае ошибки */	
	bool AddDocPath(CaplInstance *folder, CString path, bool recursive, BOOL UnSetRO = false);
	
	/** Завершить редактирование. Выводит диалог настройки параметров
		@param folder папка БД
		@param defpath папка на диске
		@return true при удачном выполнении и false в случае ошибки */	
	bool CheckInAllDocs(CaplInstance *folder, CString &defpath);	
	
	/** Завершить редактирование. Выводит диалог настройки параметров
		@param folder список папок БД
		@param checkoutdocs список документов взятых на редактирование текущим пользователем
		@param recursive обрабатывать вложенные папки
		@param rec_doc обрабатывать связанные документы
		@param activate дулать версии документов активными
		@return true при удачном выполнении и false в случае ошибки */	
	bool CheckInAllDocs(aplExtent &folder, aplExtent &checkoutdocs, bool recursive = true, bool rec_doc = true, bool activate = true);

	/** Отменить редактирование
		@param folder папка БД
		@return true при удачном выполнении и false в случае ошибки */	
	bool UndoCheckOut(CaplInstance *folder);

	/** Завершить редактирование. Выводит диалог настройки параметров
		@param folder список папок БД
		@param cdoc список документов взятых на редактирование
		@return true при успешном выполнении и false в случае ошибки */	
	bool UndoCheckOut(aplExtent &folder, aplExtent &cdocs);

	/**	Получить все вложенные в папку документы
		@param folder папка БД
		@param docs список документов в папке
		@param recursive обрабатывать вложенные папки
		@return true при успешном выполнении и false в случае ошибки */	
	bool GetAllSubDocuments(CaplInstance *folder, aplExtent &docs, bool recursive = true);

	/** Сравнивает папки в БД и папки на диске
		@param folder папка нв БД
		@param defpath папка на диске
		@return true при успешном выполнении и false в случае ошибки */	
	bool CompareFolders(CaplInstance *folder, CString &defpath);
	
	/**	Поиск папки по её имени
		@param name имя папки
		@param parent родительская папка
		@return папка в БД и NULL если ничего не найдено*/
	CaplInstance *FindFolderByName(const TCHAR *name, CaplInstance *parent = 0);

	/// Поиск папки по GUID
	CaplInstance *FindFolderByGUID(const TCHAR *s_guid);
	
	/**	Создать папку на диске
		@param folder путь к папке на диске
		@return true при успешном выполнении и false в случае ошибки*/
	bool CreateFolderOndisk(CString folder);

};
// *************************************************************************
// *************************************************************************
// *************************************************************************
/** Менеджер характеристик*/
class CLASS_DECL_APL_STEP_MGR CaplCharacteristicManager: public CaplStepManager
{
	// Инициализация

public:
	struct SCharType
	{
	public:
		SCharType(CaplInstance *charact0, CaplInstance *type0)
		{charact=charact0; type=type0;};
		CaplInstance *charact;
		CaplInstance *type;
	};
	

	/** Инициализирует класс (Ассоциация с классом базы данных) 
		@return true при успешном выполнении и false в случае ошибки */
	virtual bool Attach(CaplAPI *api);
	virtual void Detach();

	CStringArray m_sel_charact_names;

	CaplEntity *e_apl_charact;
	CaplAttr *a_apl_charact_id,	*a_apl_charact_name, *a_apl_charact_descr;
	CaplAttr *a_apl_charact_unit, *a_apl_charact_code, *a_apl_charact_full_name;
	CaplAttr *a_apl_charact_module, *a_apl_charact_method;
	CaplAttr *a_apl_charact_dynamic, *a_apl_charact_system,*a_apl_charact_GUID;
	CaplAttr *a_apl_charact_mask_input;
	
	//Изменение значения характеристики
	CaplEntity	*e_apl_change_charact;
	CaplAttr	*a_apl_change_charact_old_val;
	CaplAttr	*a_apl_change_charact_new_val;
	CaplAttr	*a_apl_change_charact_charact;
	CaplAttr	*a_apl_change_charact_delta;
	CaplAttr	*a_apl_change_charact_type;
	CaplAttr	*a_apl_change_charact_basis;

	CaplEntity *e_apl_charact_union;
	CaplAttr *a_apl_charact_union_id,*a_apl_charact_union_name, *a_apl_charact_union_descr;
	CaplAttr *a_apl_charact_union_characteristics;

	CaplEntity *e_apl_charact_value,*e_meas_value, *e_descr_value;
	CaplEntity *e_enum_value, *e_monet_value;
	CaplEntity *e_apl_reference_value;
	CaplEntity *e_aggr_val, *e_time_val;
	CaplEntity *e_table_val, *e_table_row, *e_table_cell;
	CaplEntity *e_apl_reference_comp_unit,	*e_apl_reference_maint_unit, *e_apl_reference_proc_chart_unit;

	CaplAttr *a_apl_charact_val_item, *a_apl_charact_val_charact;
	CaplAttr *a_apl_charact_val_type,*a_apl_charact_val_num,*a_apl_charact_val_scope;
	CaplAttr *a_apl_charact_val_group, *a_apl_charact_val_function;
	CaplAttr *a_apl_charact_val_system, *a_apl_charact_val_notes;

	CaplAttr *a_apl_charact_val_meas_val, *a_apl_charact_val_meas_max, *a_apl_charact_val_meas_min;
	CaplAttr *a_apl_charact_val_descr_val, *a_apl_charact_val_enum_val;
	CaplAttr *a_apl_charact_val_monet_val, *a_apl_charact_val_time_val_s;
	CaplAttr *a_apl_charact_val_aggr_val,*a_apl_charact_val_table_val;
	CaplAttr *a_apl_charact_val_unit;
	CaplAttr *a_apl_charact_val_element;
	CaplAttr *a_apl_charact_val_guid;

	CaplAttr *a_table_cell_column,	*a_table_cell_val;
	CaplAttr *a_table_row_items;
	CaplAttr *a_apl_reference_val;

	CaplEntity *e_apl_charact_type;
	CaplAttr *a_apl_charact_type_name;

	CaplEntity *e_charact_val_group;
	CaplAttr *a_charact_val_group_item,*a_charact_val_group_def;

	CaplEntity *e_apl_unit,*e_apl_aggr_unit,*e_apl_descript_unit;
	CaplEntity *e_apl_time_unit,*e_apl_enum_unit,*e_apl_monetary_unit;
	CaplEntity *e_apl_step_unit,*e_apl_named_unit,*e_apl_derived_unit;
	CaplEntity *e_apl_conv_base_unit,*e_apl_si_unit,*e_apl_cont_dep_unit, 
			   *e_apl_alp_base_unit, *e_mission_apl_alp_base_unit, *e_year_apl_alp_base_unit, *e_flight_days_apl_alp_base_unit;
	CaplEntity *e_table_unit,*e_table_column,*e_apl_reference_unit;
	
	CaplAttr *a_table_column_name,*a_table_column_unit;

	CaplAttr *a_apl_unit_id, *a_apl_unit_shown_id, *a_apl_unit_name, *a_apl_unit_name_eng, *a_apl_unit_prefix, *a_apl_unit_descr, *a_apl_unit_code;

	CaplAttr *a_apl_reference_types,*a_apl_reference_base,*a_apl_reference_format;

	CaplEntity *e_apl_unit_group;
	CaplAttr *a_apl_unit_group_id,*a_apl_unit_group_name,*a_apl_unit_group_description,*a_apl_unit_group_content,*a_apl_unit_group_parent;

	CaplEntity *e_apl_charact_group;
	CaplAttr *a_apl_charact_group_id,*a_apl_charact_group_name,*a_apl_charact_group_description,*a_apl_charact_group_content,*a_apl_charact_group_parent;

	CaplEntity *e_apl_charact_union_group;
	CaplAttr *a_apl_charact_union_group_id,*a_apl_charact_union_group_name,*a_apl_charact_union_group_description,*a_apl_charact_union_group_content,*a_apl_charact_union_group_parent;


	CaplAttr *a_apl_charact_val_act_ver,*a_apl_charact_val_lock_ver,*a_apl_charact_val_base_item;
	
	//Версии 
	CaplEntity *e_apl_charact_value_ver;
	CaplEntity *e_enum_value_ver, *e_monet_value_ver,*e_meas_value_ver;
	CaplEntity *e_apl_reference_value_ver, *e_time_val_ver,*e_descr_value_ver;
	CaplEntity *e_aggr_val_ver, *e_table_val_ver;
	CaplEntity *e_table_row_ver, *e_table_cell_ver;


	CaplAttr *a_apl_charact_val_ver_char_value,*a_apl_charact_val_ver_author,*a_apl_charact_val_ver_start_date;
	CaplAttr *a_apl_charact_val_ver_end_date,*a_apl_charact_val_ver_version_num,*a_apl_charact_val_ver_base;
	CaplAttr *a_apl_charact_val_ver_item,*a_apl_charact_val_ver_charact,*a_apl_charact_val_ver_scope;
	CaplAttr *a_apl_charact_val_ver_num,*a_apl_charact_val_ver_type;
	CaplAttr *a_apl_charact_val_ver_is_changed, *a_apl_charact_val_ver_function;
	
	CaplAttr *a_apl_charact_val_ver_meas_val, *a_apl_charact_val_ver_meas_max, *a_apl_charact_val_ver_meas_min;
	CaplAttr *a_apl_charact_val_ver_descr_val, *a_apl_charact_val_ver_enum_val;
	CaplAttr *a_apl_charact_val_ver_monet_val, *a_apl_charact_val_ver_time_val_s,*a_apl_reference_val_ver_val;
	CaplAttr *a_apl_charact_val_ver_aggr_val;
	CaplAttr *a_apl_charact_val_ver_table_val,*a_table_row_ver_items;
	CaplAttr *a_table_cell_ver_column,	*a_table_cell_ver_val;

	//Связка справочника, характеристики и её типа
	CaplEntity	*e_apl_characteristic_and_type;
	CaplAttr	*a_apl_characteristic_and_type_base_item;
	CaplAttr	*a_apl_characteristic_and_type_characteristic;
	CaplAttr	*a_apl_characteristic_and_type_type;
	CaplAttr	*a_apl_characteristic_and_type_required;
	
	//	Связка, задающая соотношение основной и дополнительной единиц измерения.
	CaplEntity	*e_apl_unit_convertion;
	CaplAttr	*a_apl_unit_convertion_item;
	CaplAttr	*a_apl_unit_convertion_base_unit;
	CaplAttr	*a_apl_unit_convertion_add_unit;
	CaplAttr	*a_apl_unit_convertion_base_unit_koef;
	CaplAttr	*a_apl_unit_convertion_add_unit_koef;
	

		
	static bool m_bUseVersions;
	// Методы
public:
	/** Выводит диалог выбора  группы характеристик с учетом пользовательских классов этих групп  
	@param selected_charact_union выбранная группа характеристик по умолчанию 
	@param selected_group выбранная группа по умолчанию 
	@return instance выбранной группы характеристик, иначе 0 */ 	
	CaplInstance *SelectCharactUnionGroup(CaplInstance *selected_charact_union=0,CaplInstance *selected_group=0);

	/** Выводит диалог выбора характеристики с учетом пользовательских групп характеристик  
	@param selected_characteristic выбранная характеристика по умолчанию 
	@param selected_group выбранная группа по умолчанию 
	@return instance выбранной характеристики, иначе 0 */ 
	CaplInstance *SelectCharacteristic(CaplInstance *selected_characteristic=0,CaplInstance *selected_group=0);
	
	/** Выводит диалог выбора единицы измерения с учетом пользовательских групп единиц измерения  
	@param selected_unit  выбранная ед.измерения по умолчанию 
	@param selected_group выбранная группа по умолчанию 
	@return instance выбранной единицы измерения, иначе 0 */ 
	CaplInstance *SelectUnit(CaplInstance *selected_unit=0,CaplInstance *selected_group=0);
	/** Читает из базы словарь характеристик и ед. изм. 
		@return true при удачном выполнении и false в случае ошибки */ 
	bool LoadDictionary();

	/** Возвращает определение единицы измерения по ее обозначению 
		@param id  обозначение единицы измерения
		@return найденное  определение единицы измерения и NULL если такой нет */
	CaplInstance *GetUnitById(const TCHAR * id);

	/** Возвращает определение характеристики по ее обозначению 
		@param id  обозначение характеристики
		@return найденное  определение характеристики и NULL если такой нет */
	CaplInstance *GetCharacteristicById(const TCHAR * id);

	/** Возвращает определение характеристики по ее наименованию 
		@param name  обозначение характеристики
		@return найденное  определение характеристики и NULL если такой нет */
	CaplInstance *GetCharacteristicBN(const TCHAR * name);


	/** Возвращает характеристику для объекта 
		@param inst  объект
		@param characteristic  характеристика
		@return найденное  значение характеристики и NULL если такого нет */
	CaplInstance * GetInstCharacteristic(CaplInstance *inst,CaplInstance *characteristic);

	/** Перечитывает изменение характеристики 
		@param ass - ассоциатор 
		@return true при удачном выполнении и false в случае ошибки */ 
	bool LoadCharacteristicChange(CaplInstance *val);

	/** Перечитывает изменения списка характеристик 
		@param aggr - список ассоциаторов 
		@return true при удачном выполнении и false в случае ошибки */ 
	bool LoadCharacteristicChange(aplExtent& ext);

	/** Перечитывает значение характеристики 
		@param ass - ассоциатор 
		@return true при удачном выполнении и false в случае ошибки */ 
	bool LoadCharacteristic(CaplInstance *val);
	/** Перечитывает значение списка характеристик 
		@param aggr - список ассоциаторов 
		@return true при удачном выполнении и false в случае ошибки */ 
	bool LoadCharacteristic(CaplAggr &aggr);
	/** Перечитывает значение списка характеристик 
		@param ext - список ассоциаторов 
		@return true при удачном выполнении и false в случае ошибки */ 
	bool LoadCharacteristic(aplExtent &ext,bool show_status_dlg=false);

	/** Ищет изменения характеристик с заданным типом для объекта 
		@param item  объект
		@param ext список найденных изменений характеристик
		@param characreristic характеристика*/
	bool FindAssociatedCharacteristicChange(CaplInstance *item, aplExtent &ext, CaplInstance *characreristic = 0);

	/** Ищет характеристику с заданным типом для объекта 
		@param item  объект
		@param characreristic характеристика
		@param type тип характеристики */ 
	CaplInstance *FindCharacteristic(CaplInstance *item,CaplInstance *characreristic, CaplInstance *type,bool find_in_all_versions=false,bool load_from_bd=true);
	/** Возвращает все характеристики для объекта 
		@param inst  объект
		@param out_ext  список в котором возвращаются найденные значения характеристик (результат)
		@param out_group  список в котором возвращаются найденные группы (результат)
		@param load_table  true, если требуется считывать значения списков и таблиц
		@param find_in_all_versions  true, если требуется искать присоединенные характеристики во всех версиях объекта
		@param from_base  просматривать ли данные из БД. Если false то просматривается только кэш
		@return найденное  значение характеристики и NULL если такого нет */
	bool FindAssociatedCharacteristic(CaplInstance *inst, aplExtent &out_ext, aplExtent &out_group,bool load_table=false,bool find_in_all_versions=false, bool from_base=true, bool with_system=true);
	bool FindAssociatedCharacteristic(CaplInstance *inst, aplExtent &out_ext, bool load_table=false,bool find_in_all_versions=false,bool show_status_dlg=false, bool from_base=true, bool with_system=true);
	bool FindAssociatedCharacteristics(CaplInstance *inst, aplExtent &out_ext, bool bFromBase=true);
	/** Возвращает все характеристики для группы объектов 
		@param ext группа объектов
		@param out_ext  список в котором возвращаются найденные значения характеристик (результат)
		@param out_group  список в котором возвращаются найденные группы (результат)
		@param load_table  true, если требуется считывать значения списков и таблиц
		@param find_in_all_versions  true, если требуется искать присоединенные характеристики во всех версиях объектов
		@param show_status_dlg показывать диалог состояния загрузки (при загрузке из БД)
		@return найденное  значение характеристики и NULL если такого нет */
	bool FindAssociatedCharacteristic(aplExtent &ext, aplExtent &out_ext, aplExtent &out_group,bool load_table=false,bool find_in_all_versions=false,bool show_status_dlg=false, bool from_base=true, bool with_system=true);
	bool FindAssociatedCharacteristic(aplExtent &ext, aplExtent &out_ext, bool load_table=false,bool find_in_all_versions=false,bool show_status_dlg=false, bool from_base=true, bool with_system=true);
	bool FindAssociatedCharacteristics(aplExtent &ext, aplExtent &out_ext, bool bFromBase=true);
	/** Возвращает содержимое группы характеристик 
		@param группа характеристик
		@param out_ext  список в котором возвращаются найденные значения характеристик (результат)
		@return true при удачном выполнении и false в случае ошибки */ 
	bool GetGroupContents(CaplInstance *group,aplExtent &ext_out);
	/** Возвращает тип характеристики по обозначению 
		@param type  обозначение типа характеристики
		@return найденный тип  характеристики и NULL если такого нет */
	CaplInstance *GetCharacteristicType(const TCHAR * type);


	/** Показывает свойства характеристики  
		@param val - значение  
		@return true при удачном выполнении и false в случае ошибки */ 
	bool ShowProperties(CaplInstance *val,bool locked_type=false);
	
	/** Показывает свойства объекта  
		@param  item - объект 
		@return true при удачном выполнении и false в случае ошибки */ 
	bool ShowItemProperties(CaplInstance *item);

	/** Показывает свойства группы характеристик  
		@param  group - группа 
		@return true при удачном выполнении и false в случае ошибки */ 

	bool ShowGroupProperties(CaplInstance *group);
	/** Создает значение характеристики c выводом диалога 
		@param item  объект
		@param base_val - базовое значение  (для данных по умолчанию)
		@param val - созданное значение 
		@param new_charact - создаваемая характеристика
		@param val_ver - создаваемая версия характеристики
		@param check_out - брать на редактирование (не используется)
		@return true при удачном выполнении и false в случае ошибки */ 
	bool CreateCharacteristic(CaplInstance *item, CaplInstance *base_val, CaplInstance **val, CaplInstance *new_charact=0,CaplInstance **val_ver=0,bool check_out=false,CaplInstance *group=0,bool show_dlg=true,CaplInstance *new_type=(CaplInstance*)-1);

	/** Создает значение групповой характеристики c выводом диалога 
		@param item  объект
		@param base_group - базовая группа (для данных по умолчанию)
		@param group - созданная группа
		@return true при удачном выполнении и false в случае ошибки */ 
	bool CreateCharacteristicGroup(CaplInstance *item, CaplInstance **group, CaplInstance *base_group=0,bool show_dlg=true);

	/** Возвращает столбец табличной единицы измерения по его имени 
		@param unit  табличная единицы измерения
		@param name  имя столбца 
		@return найденный столбец и NULL если такого нет */
	CaplInstance *GetColumnByName(CaplInstance *unit, const TCHAR * name);

	/** Возвращает значение ячейки из табличной характеристики 
		@param row  строка таблицы
		@param column  столбец 
		@return найденное значение и NULL если такого нет */
	CaplInstance *GetColumnValue(CaplInstance *row, CaplInstance *column);

	/** Возвращает значение ячейки из табличной характеристики 
		@param table_value  значение табличной характеристики
		@param row индекс  строки таблицы
		@param column  столбец 
		@return найденное значение и NULL если такого нет */
	CaplInstance *GetColumnValue(CaplInstance *table_value, int row, CaplInstance *column);

	/** Создает (перезаписывает) значение ячейки табличной характеристики 
		@param row  строка таблицы
		@param column  столбец 
		@param value  новое значение 
		@return созданная ячейка значение и NULL в случае ошибки  */
	CaplInstance *PutCellInRow(CaplInstance *row, CaplInstance *column, CaplInstance *value);

	/** Удаляет значение характеристики или ее версии 
		@param val - базовое значение 
		@param delete_all - удалять все версии (иначе единственная не удаляется и происходит изменение активной (при ее удалении))
		@param delete_only_version - удалять только редактируемую версию (для характеристик бизнес-процессов) 
		@return true при удачном выполнении и false в случае ошибки */
	bool DeleteCharacteristic( CaplInstance *val,bool delete_all=false,bool delete_only_version=false, bool bLoadFromBase = true);
	
	/** Удаляет значение группы характеристик
		@param group - группа ъарактеристик
		@return true при удачном выполнении и false в случае ошибки */
	bool DeleteCharacteristicGroup(CaplInstance *group);
	
	/** Удаление всех характеристик и групп характеристик у item*/
	bool DeleteAllAssociatedCharacteristic(CaplInstance *item);

	/** Создает значение описательной характеристики  
		@param item  объект
		@param characteristic  характеристика
		@param type  тип характеристики
		@param value  значение  характеристики
		@return созданная значение характеристики и NULL в случае ошибки  */
	CaplInstance *CreateDescriptiveCharacteristic(CaplInstance *item,CaplInstance *characreristic, CaplInstance *type, const TCHAR *value);
	
	/** Создает значение образмеренной характеристики  
		@param item  объект
		@param characteristic  характеристика
		@param type  тип характеристики
		@param value  значение  характеристики
		@param max_dev  максимальное отклонение  характеристики
		@param min_dev  минимальное отклонение  характеристики
		@return созданная значение характеристики и NULL в случае ошибки  */
	CaplInstance *CreateMeasuredCharacteristic(CaplInstance *item,CaplInstance *characreristic, CaplInstance *type, double value, double max_dev,  double min_dev);

	/** Создает значение денежной характеристики  
		@param item  объект
		@param characteristic  характеристика
		@param type  тип характеристики
		@param value  значение  характеристики
		@return созданная значение характеристики и NULL в случае ошибки  */
	CaplInstance *CreateMonetaryCharacteristic(CaplInstance *item,CaplInstance *characreristic, CaplInstance *type, double value);

	/** Создает значение характеристики перечисление 
		@param item  объект
		@param characteristic  характеристика
		@param type  тип характеристики
		@param value  значение  характеристики
		@return созданная значение характеристики и NULL в случае ошибки  */
	CaplInstance *CreateEnumerationCharacteristic(CaplInstance *item,CaplInstance *characreristic, CaplInstance *type, const TCHAR *value);

	/** Создает значение ссылочной характеристики 
		@param item  объект
		@param characteristic  характеристика
		@param type  тип характеристики
		@param value  значение  характеристики
		@return созданная значение характеристики и NULL в случае ошибки  */
	CaplInstance *CreateReferenceCharacteristic(CaplInstance *item,CaplInstance *characreristic, CaplInstance *type, CaplInstance *value);
	
	/** Создает значение  характеристики точка во времени
		@param item  объект
		@param characteristic  характеристика
		@param type  тип характеристики
		@param value  значение  характеристики
		@return созданная значение характеристики и NULL в случае ошибки  */
	CaplInstance *CreateDateTimeCharacteristic(CaplInstance *item,CaplInstance *characreristic, CaplInstance *type, COleDateTime &value);
	/** Создает значение  характеристики точка во времени
		@param item  объект
		@param characteristic  характеристика
		@param type  тип характеристики
		@param value  значение  характеристики
		@return созданная значение характеристики и NULL в случае ошибки  */
	CaplInstance *CreateDateTimeCharacteristic(CaplInstance *item,CaplInstance *characreristic, CaplInstance *type, const TCHAR *s_value);

	/** Создает значение агрегативной характеристики
		@param item  объект
		@param characteristic  характеристика
		@param type  тип характеристики
		@param value  значение  характеристики
		@return созданная значение характеристики и NULL в случае ошибки  */
	CaplInstance* CreateAggrCharacteristicValue(CaplInstance *item,CaplInstance *characreristic, CaplInstance *type, aplExtent& value);

	/** Возвращает имя единицы измерения 
		@param unit единица измерения
		@param buf буффер в который возвращается имя
		@param bAlwaysReturnName Если true - будет возвращать наименование, если false - наименование или обозначения, в зависимости от настроек
		@return true при удачном выполнении и false в случае ошибки */
	bool GetUnitName(CaplInstance *unit, CString &buf, bool bAlwaysReturnName=false);

	/** Преобразует значенеи характеристики в строку 
		@param val значение зарактеристики
		@param unit единица измерения
		@param buf буффер в который возвращается имя
		@return true при удачном выполнении и false в случае ошибки */
	bool PrintCharacteristicValue(CaplInstance *val,CaplInstance *unit,CString &buf, bool full_print=false);

	/** Копируетует значенеи характеристики
		@param old_inst копируемое значение зарактеристики
		@param new_inst куда копировать (если 0 - то создать новую копию)
		@return скопированное значение характеристики и NULL в случае ошибки  */
	CaplInstance* CreateCopyCharacteristicVal(CaplInstance* old_inst, CaplInstance* new_inst=0, CaplMap *inst_map=0);

	/** Дополняет список всеми ссылками из значения характеристики 
		@param val значение зарактеристики
		@param ext дополняемый extent
		@return true при удачном выполнении и false в случае ошибки */
	bool AppendExtReferenceValues(CaplInstance *val, aplExtent &ext);

	/** Выводит окно выбора ссылочного значения характеристики
		@param unit единица измерения для ссылочного значения
		@return выбранный объект или NULL в случае oтмены  */
	CaplInstance* BrowseReferenceVal(CaplInstance* unit);
	/** берет на редактирование характеристику
		@param val значение характеристики или ее версии
//		@param create_new_version создавать версию характеристики (если == false, 
		 считается, что передается версия характеристики,которую надо сделать локером характеристики) 
		@return true при успешном выполнении и false в случае ошибки */
//	bool CheckOut(CaplInstance *val,bool create_new_version=true);
	bool CheckOut(CaplInstance *val);
	/** берет на редактирование характеристики
		@param val значение характеристики
		//@param create_new_version создавать новую версию бп (если == false, то только меняется активная версия)
		@param make_new_version_active делать новую версию активной 
		@return true при удачном выполнении и false в случае ошибки */
	bool CheckIn(CaplInstance *val,bool make_new_version_active=true);
//	bool CheckIn(CaplInstance *val,bool create_new_version=true,bool make_new_version_active=true);
	/** завершение редактирования списка характеристик
		@param ext список значений версий характеристик
		@param ext_out список значений характеристик 
		@return true при удачном выполнении и false в случае ошибки */
	CaplInstance *GetLock(CaplInstance *val,bool bShowMessages); 
	/** проверяет блокировку текущим пользователем характеристики
		@param val значение характеристики или ее версии
		@param bShowMessages показывать или нет сообщение о наличии блокировки
		@return instance локера характеристики */
	CaplInstance *CheckMyLock(CaplInstance *val,bool bShowMessages); 
	/** отменяет редактирование характеристики
		@param val значение характеристики
		@param ask_before_undo спрашивать подтверждение на отмену редактирования
		@return instance характеристики */
	bool UndoCheckOut(CaplInstance *val,bool ask_before_undo=true);
	/** берет на редактирование группу характеристик
		@param group группа характеристик
		@return true при удачном выполнении и false в случае ошибки */
	bool CheckOutGroup(CaplInstance *group);
	/** завершает редактирование группы характеристик
		@param group группа характеристик
		@return true при удачном выполнении и false в случае ошибки */
	bool CheckInGroup(CaplInstance *group);
	/** отменяет редактирование группы характеристик
		@param group группа характеристик
		@param ask_before_undo спрашивать подтверждение удаления
		@return true при удачном выполнении и false в случае ошибки */
	bool UndoCheckOutGroup(CaplInstance *group,bool ask_before_undo=true);
	/** сравнивает значения характеристики и ее версии или двух версий
		@param val значение характеристики или ее версии
		@param val_ver значение версии характеристики
		@return true если значения разные, иначе - false*/
	bool IsValueChanged(CaplInstance *val,CaplInstance *val_ver);	
	/** получает все версии значения характеристики
		@param val значение характеристики или ее версии
		@param ext_out список версий (результат)
		@return true в случае успешного выполнения,иначе false*/
	bool GetAllCharactVersion(CaplInstance *val,aplExtent &outExt, bool bLoadFromBase = true);
	/** получает все версии значения характеристики
		@param vals значения характеристики или их версии
		@param ext_out список версий (результат)
		@return true в случае успешного выполнения,иначе false*/
	bool GetAllCharactVersion(aplExtent& vals, aplExtent &outExt, bool bLoadFromBase = true);
	/** создает версию значения характеристики
		@param val значение характеристики или ее версии
		@param num номер создаваемой версии (если равен "-1" присваивается очередной номер)
		@param make_active делать создаваемую версию активной (иначе номер версии и дата завершения редактирования не присваивается)
		@param only_values переписывать в версию только значения характеристик (для аггров и таблиц)
		@return instance созданной версии */
	CaplInstance *CreateCharValVersion(CaplInstance *val,CString num=_T("-1"),bool make_active=true,bool only_values=false);
	/** получает последнюю (по номеру) версию характеристики
		@param val значение характеристики
		@param num номер последней версии
		@return instance последней версии или 0 если нет версий */
	CaplInstance *GetLatestCharValVersion(CaplInstance *val,CString &num, bool load_from_db=true);
	/** копирует версию значения характеристики в значение характеристики
		@param val_ver значение версии характеристики
		@param val значение характеристики (если 0,то создается значение) 
		@param load_from_db зачитывать ли информацию из базы данных перед выполнением (если true, то да)
		@return instance созданного значения характеристики */
	CaplInstance *CopyValVersionToVal(CaplInstance *val_ver,CaplInstance *val=0);
	/** делает активной версию характеристики
		@param val_ver значение версии характеристики
		@return true в случае успешного выполнения,иначе false*/
	bool MakeCharValVersionActive(CaplInstance *val_ver);
	/**	Меняет значение характеристики на величину delta
		@param value значение характеристики
		@param delta изменение характеристики
		@param type тип изменения характеристики
		@param bp_inst экземпляр бизнес процесса на который будет ссылаться изменение
		@param new_val указатель на новое значение характеристики
		@return изменение значения характеристики*/
	CaplInstance* ChangeCharactValue(CaplInstance* value, double delta, CaplInstance* bp_inst, CString type = _T("delta"), CaplInstance **new_val_ver=0);

	/**	Читает конкретные характеристики конкретного типа для списка объектов.
		@param map карта объектов. Входное значение - приведенный к long объект, выходное должно быть 0;
		@param characteristic  искомой характеристики
		@param type  тип искомой характеристики
		@param num_izm номер измерения. Если равен -1, то возвращается с первым попавшимся номером измерения
		@return true при удачном выполнении и false в случае ошибки. Найденные значения характеристики заносятся как выходные в map.*/

	bool GetInstancesCharact(CaplMap &map, CaplInstance *charact, CaplInstance *type,bool load_from_bd=true, int num_izm=-1);

	/**	Создает объект-связку характеристики и типа характеристики
		@param characteristic характеристика
		@param type тип характеристики
		@param item базовый элемент, на который ссылается связка
		@param required флаг обязательности характеристики
		@param ext_mode если true, то в диалоге не отображается галочка "обязательный"
		@param ext_tested если параметр задан, то перед созданем нового объекта пара характеристика-тип
	ищется в указанном массиве; в случае успеха возврашается найденная, в случае неуспеха - 
	создается новая
		@return объект связка характеристика-тип характеристкики в случае успешного выполнения и 0 в обратном случае*/
	CaplInstance* CreateCharacteristicAndType(CaplInstance* characteristic, CaplInstance* type, CaplInstance *item=0,bool required=false,bool ext_mode=false,aplExtent *ext_tested=0);

	/**	Отображает свойства объекта-связки характеристики и типа характеристики
		@param characteristic_and_type объект связка характеристика-тип характеристкики
		@return true при удачном выполнении и false в случае ошибки.*/
	bool CharacteristicAndTypeProperties(CaplInstance* characteristic_and_type,bool forced_ro=false,bool ext_mode=false);

	/**	
		@param 
		@param 
		@param 
		@param 
		@return объект связка характеристика-тип характеристкики в случае успешного выполнения и 0 в обратном случае*/
	int ShowCharacteristicAndTypeDialog(CaplInstance** characteristic, CaplInstance** type, bool &required,bool ext_mode=false);

	/**	
		@param item единица измерения или характеристика или значение характеристики
		@param 
		@return true если характеристика числовая, false если хараткеристика строковая*/
	bool IsCharacteristicNumber(CaplInstance* item);

		/**	
		@param item единица измерения или характеристика или значение характеристики
		@param 
		@return true если характеристика имеет тип даты, false если иной тип*/
	bool IsCharacteristicDate(CaplInstance* item);
	
	/** Отображает диалог с изменениями характеристики */
	bool ShowCharactChanges(CaplInstance *characteristic);

	/** Отображает диалог преобразования единиц измерения */
	bool SetupUnitConvertion(CaplInstance *ciPdf, CaplInstance *ciUnit, double dBaseCount);


	/** Возвращает список единиц измерения в которых можно задавать кол-во pdf*/
	void GetPossiblePdfUnits( CaplInstance *ciPdf, aplExtent &unitsExt );

};

// *************************************************************************
// *************************************************************************
// *************************************************************************
// *************************************************************************
// *************************************************************************
// *************************************************************************
/** Менеджер бизнес-процессов*/
class CLASS_DECL_APL_STEP_MGR CaplBPManager: public CaplStepManager
{
	// Инициализация
public:
	virtual bool Attach(CaplAPI *api);
	virtual void Detach();

	/**@name Бизнес-процесс (элементы словаря) */
	//@{
	CaplEntity *e_bp;		/**<apl_business_process */
	CaplAttr *a_bp_id;		/**<apl_business_process -> id */
	CaplAttr *a_bp_name;	/**<apl_business_process -> name */
	CaplAttr *a_bp_descr;	/**<apl_business_process -> description */
	CaplAttr *a_bp_code;	/**<apl_business_process -> code */
	CaplAttr *a_bp_elements;/**<apl_business_process -> elements */ 
	CaplAttr *a_bp_type;	/**<apl_business_process -> type */
	CaplAttr *a_bp_lock;	/**<apl_business_process -> locker */
	CaplAttr *a_bp_act;		/**<apl_business_process -> active_version */
	CaplAttr *a_bp_res;		/**<apl_business_process -> resources */
	CaplAttr *a_bp_parent;	/**<apl_business_process -> main_parent */
	CaplAttr *a_bp_label;	/**<apl_business_process -> label */
	CaplAttr *a_bp_state;	/**<apl_business_process -> state */
	CaplAttr *a_bp_guid;	/**<apl_business_process -> guid */
	CaplAttr *a_bp_date_time;	/**<apl_business_process -> date_time */
	CaplAttr *a_bp_customized;	/**<apl_business_process -> customized */
	CaplAttr *a_bp_optional;	/**<apl_business_process -> optional */
	CaplAttr *a_bp_source;		/**<apl_business_process -> source */

	CaplAttr *a_bp_org;	/**<apl_business_process -> organization */
	CaplAttr *a_bp_class;	/**<apl_business_process ->  class*/
	CaplAttr *a_bp_percentage_of_otk;	/**<apl_business_process -> percentage_of_otk */
	CaplAttr *a_bp_number_of_simultaneously_processed_parts;	/**<apl_business_process -> number_of_simultaneously_processed_parts */
	CaplAttr *a_bp_t_sht;	/**<apl_business_process -> t_sht */
	CaplAttr *a_bp_t_pz;	/**<apl_business_process -> t_pz */
	CaplAttr *a_bp_coat;	/**<apl_business_process -> coat */
	CaplAttr *a_bp_directive;	/**<apl_business_process -> directive */


	//@}

	/**@name Тип бизнес-процесса (элементы словаря) */
	//@{
	CaplEntity *e_bp_rel;					/**<apl_business_process_relation */
	CaplAttr *a_bp_rel_id;					/**<apl_business_process_relation -> id */
	CaplAttr *a_bp_rel_name;				/**<apl_business_process_relation -> name */
	CaplAttr *a_bp_rel_descr;				/**<apl_business_process_relation -> description */
	CaplAttr *a_bp_rel_from;				/**<apl_business_process_relation -> from */
	CaplAttr *a_bp_rel_to;					/**<apl_business_process_relation -> to */
	//@}

	/**@name Тип бизнес-процесса (элементы словаря) */
	//@{
	CaplEntity *e_bp_type;		/**<apl_business_process_type */
	CaplAttr *a_bp_type_name;	/**<apl_business_process_type -> name */
	//@}

	/**@name Ассоциация бизнес-процесса (элементы словаря) */
	//@{
	CaplEntity *e_bp_ref;					/**<apl_business_process_reference */
	CaplAttr *a_bp_ref_item;				/**<apl_business_process_reference -> item */
	CaplAttr *a_bp_ref_process;				/**<apl_business_process_reference -> assigned_process */
	CaplAttr *a_bp_ref_id;					/**<apl_business_process_reference -> id */
	CaplAttr *a_bp_ref_name;				/**<apl_business_process_reference -> name */
	CaplAttr *a_bp_ref_ranking;				/**<apl_business_process_reference -> ranking */
	CaplAttr *a_bp_ref_ranking_rat;			/**<apl_business_process_reference -> ranking_rationale */
	CaplAttr *a_bp_ref_frames_of_reference;	/**<apl_business_process_reference -> apl_frames_of_reference */
	CaplAttr *a_bp_ref_zagotov;				/**<apl_business_process_reference -> zagotov */
	CaplAttr *a_bp_ref_guid;
	//@}

	/**@name Ресурс (элементы словаря) */
	//@{
	CaplEntity *e_bp_res;					/**<apl_business_process_resource */
	CaplAttr *a_bp_res_id;					/**<apl_business_process_resource -> id */
	CaplAttr *a_bp_res_name;				/**<apl_business_process_resource -> name */
	CaplAttr *a_bp_res_descr;				/**<apl_business_process_resource -> description */
	CaplAttr *a_bp_res_type;				/**<apl_business_process_resource -> type */
	CaplAttr *a_bp_res_object;				/**<apl_business_process_resource -> object */
	 
	CaplAttr *a_bp_res_val;					/**<apl_business_process_resource -> value_component */
	CaplAttr *a_bp_res_unit;				/**<apl_business_process_resource -> unit -> component */
	CaplAttr *a_bp_res_process;				/**<apl_business_process_resource -> process */
	CaplAttr *a_bp_res_derive_val;			/**<apl_business_process_resource -> derive_value_component */
	CaplAttr *a_bp_res_derive_unit;			/**<apl_business_process_resource -> derive_unit_component */
	CaplAttr *a_bp_res_assortment;			/**<apl_business_process_resource -> apl_assortment */
	CaplAttr *a_bp_res_ranking;				/**<apl_business_process_resource -> ranking */
	CaplAttr *a_bp_res_ranking_rationale;	/**<apl_business_process_resource -> ranking_rationale */
	//@}

	/**@name Тип ресурса (элементы словаря) */
	//@{
	CaplEntity *e_bp_res_type;				/**<apl_business_process_resource_type */
	CaplAttr *a_bp_res_type_name;			/**<apl_business_process_resource_type -> name */
	//@}

	/**@name Изменения (элементы словаря) */
	//@{
	CaplEntity *e_apl_bp_ver;				/**<apl_business_process_version */
	CaplAttr *a_bp_ver_bp;					/**<apl_business_process_version -> process */
	CaplAttr *a_bp_ver_id;					/**<apl_business_process_version -> id */
	CaplAttr *a_bp_ver_name;				/**<apl_business_process_version -> name */
	CaplAttr *a_bp_ver_descr;				/**<apl_business_process_version -> description */
	CaplAttr *a_bp_ver_code;				/**<apl_business_process_version -> code */
	CaplAttr *a_bp_ver_type;				/**<apl_business_process_version -> type */
	CaplAttr *a_bp_ver_author;				/**<apl_business_process_version -> author */
	CaplAttr *a_bp_ver_start;				/**<apl_business_process_version -> start_date */
	CaplAttr *a_bp_ver_end;					/**<apl_business_process_version -> end_date */
	CaplAttr *a_bp_ver_num;					/**<apl_business_process_version -> number */
	CaplAttr *a_bp_ver_elements;			/**<apl_business_process_version -> elements */
	CaplAttr *a_bp_ver_base;				/**<apl_business_process_version -> base */
	CaplAttr *a_bp_ver_res;					/**<apl_business_process_version -> resources */
	CaplAttr *a_bp_ver_label;				/**<apl_business_process_version -> label */
	CaplAttr *a_bp_ver_char_val_versions;	/**<apl_business_process_version -> characteristic_value_versions */
	CaplAttr *a_bp_ver_basis;				/**<apl_business_process_version -> basis */
	CaplAttr *a_bp_ver_guid;				/**<apl_business_process_version -> guid */
	CaplAttr *a_bp_ver_customized;				/**<apl_business_process_version -> customized */
	CaplAttr *a_bp_ver_optional;			/**<apl_business_process_version -> optional */

	CaplAttr *a_bp_ver_org;				/**<apl_business_process_version -> org */
	CaplAttr *a_bp_ver_class;				/**<apl_business_process_version -> class */
	CaplAttr *a_bp_ver_percentage_of_otk;				/**<apl_business_process_version -> percentage_of_otk */
	CaplAttr *a_bp_ver_number_of_simultaneously_processed_parts;				/**<apl_business_process_version -> number_of_simultaneously_processed_parts */
	CaplAttr *a_bp_ver_t_sht;				/**<apl_business_process_version -> t_sht */
	CaplAttr *a_bp_ver_t_pz;				/**<apl_business_process_version -> t_pz */
	CaplAttr *a_bp_ver_coat;				/**<apl_business_process_version -> coat */
	CaplAttr *a_bp_ver_directive;				/**<apl_business_process_version -> directive */

	//@}
	
	/**@name Экземпляр бизнес-процесса (элементы словаря) */
	//@{
	CaplEntity *e_apl_bp_inst;				/**<apl_business_process_instance */
	CaplAttr *a_bp_inst_id;					/**<apl_business_process_instance -> id */
	CaplAttr *a_bp_inst_name;				/**<apl_business_process_instance -> name */
	CaplAttr *a_bp_inst_descr;				/**<apl_business_process_instance -> description */
	CaplAttr *a_bp_inst_process;			/**<apl_business_process_instance -> process */
	CaplAttr *a_bp_inst_elements;			/**<apl_business_process_instance -> elements */
	CaplAttr *a_bp_inst_res;				/**<apl_business_process_instance -> resources */
	CaplAttr *a_bp_inst_date_time;          /**<apl_business_process_instance -> date_time */
	CaplAttr *a_bp_inst_state;				/**<apl_business_process_instance -> new_state> */
	CaplAttr *a_bp_inst_end_datetime;		/**<apl_business_process_instance -> end_date> */
	CaplAttr *a_bp_inst_basis;				/**<apl_business_process_instance -> basis> */
	CaplAttr *a_bp_inst_duration;			/**<apl_business_process_instance -> duration> */
	CaplAttr *a_bp_inst_guid;
	//@}

	/**@name Ассоциация экземпляра бизнес-процесса (элементы словаря) */
	//@{
	CaplEntity *e_bp_inst_ref;					 /**<apl_business_process_instance_reference */
	CaplAttr *a_bp_inst_ref_item;				 /**<apl_business_process_instance_reference -> item */
	CaplAttr *a_bp_inst_ref_process;			 /**<apl_business_process_instance_reference -> assigned_process_instance */
	CaplAttr *a_bp_inst_ref_id;					 /**<apl_business_process_instance_reference -> id */
	CaplAttr *a_bp_inst_ref_name;				 /**<apl_business_process_instance_reference -> name */
	CaplAttr *a_bp_inst_ref_frames_of_reference; /**<apl_business_process_instance_reference -> apl_frames_of_reference */
	CaplAttr *a_bp_inst_ref_guid;
	//@}

	static bool m_bShowId;
	static bool m_bShowName;
	static bool m_bShowType;
	static bool m_bRecursive;
	static bool m_bCheckUniqs;

	#define APL_MODE_COPY_BP      0x00000
	#define APL_MODE_CREATE_BP    0x00001

	CString m_sIdPostfixForCreateBPCopy; // Строка добавляемая к обозначению в CreateBPCopy. Если нет, то добавляется "_копия" 

	//флаги для рекурсивного завершения редактирования
	bool m_apply_to_all;/** применять или нет для всех вложенных подпроцессов **/
	bool m_undo_check_out;/** отменять или нет рекурсивно редактирование **/
protected:
	//управляющие данные для индикации рекурсивного взятия/завершения редактирования
	bool m_status_dlg_created;/** диалог индикации создан **/ 
	int m_status_count;/** количество обработанных бп **/
	int m_level;
	
	//данные, накапливающие информацию о скопированных бизнес-процессах/экземплярах бп
	aplExtent ext_bps;

	// Методы
public:
	/** Читает в кэш информацию о типах ресурсов и бизнес-процессов*/
	bool LoadDictionary();

	/** Создает описание бизнес-процесса 
	  @param  base_bp  базовый бизнес-процесс 
	  @param  item  объект, с которым необходимо ассоциировать сознанный бизнес-процесс 
	  @param  id  id бизнес-процесса по умолчанию 
	  @param  name наименование бизнес-процесса по умолчанию 
	  @param  type тип бизнес-процесса по умолчанию 
	  @param  creation_mode  значение определяющее режим создания бизнес-процесса 
  		  APL_MODE_COPY_BP - копирование атрибутов базового бизнес-процесса (base_bp) <br>
		  APL_MODE_CREATE_BP - создание нового бизнес-процесса<br>
	  @param  rel созданная связь с бизнес-процесса с item				
	  @param  context используемый контекст по умолчанию 
	  @param  descr описание бизнес-процесса по умолчанию
	  @param  code код бизнес-процесса по умолчанию
	  @param  label метка бизнес-процесса по умолчанию
	  @param  show_dlg показывать диалог создания бизнес-процесса (если задан корректный id и код (код может быть не задан либо уникален))
	  @return созданный объект 	*/
	CaplInstance *CreateBP(CaplInstance *base_bp=0,CaplInstance *item=0, const TCHAR *id=0, const TCHAR *name=0, CaplInstance *type=0,long creation_mode=APL_MODE_CREATE_BP,CaplInstance **rel=0,CaplInstance *context=0,const TCHAR *descr=0,const TCHAR *code=0,const TCHAR *label=0,bool show_dlg=true);

	/** Создает копию бизнес-процесса 
	  @param  base_bp  бизнес-процесс, данные которого копируются 
	  @param  id  обозначение бизнес-процесса
	  @param  name наименование бизнес-процесса 
	  @param  descr описание бизнес-процесса
	  @param  item  объект, с которым необходимо ассоциировать сознанный бизнес-процесс 
	  @param  context контекст создаваемой связи c item
	  @param  rel созданная связь с бизнес-процесса с item				
	  @param  parent_bp бизнес-процесс родитель (при рекурсивном копировании всех вложенных)
	  @param  recursive копировать ли все вложенные подпроцессы
	  @return созданный объект 	*/
	CaplInstance *CreateBPCopy(CaplInstance *base_bp,const TCHAR *id=0, const TCHAR *name=0,const TCHAR *descr=0,CaplInstance *item=0, CaplInstance *context=0,CaplInstance **rel=0,CaplInstance *parent_bp=0,bool recursive=true);

	/** Создает описание ресурса для бизнес-процесса
	  @param  inst бизнес-процесс или экземпляр бизнес-процесса 
	  @param  base_res_or_pdr базовый ресурс или pdr
	  @param  object объект, с которым создается связь
	  @param  id обозначение ресурса
	  @param  name наименование ресурса
	  @param  descr описание ресурса
	  @param  type тип ресурса
	  @param  show_dlg показывать диалог создания ресурса или сразу создавать объект (должен быть задан object) 
	  @return созданный объект 	*/	
	CaplInstance *CreateBPResource(CaplInstance *inst,CaplInstance *base_res_or_pdr=0,CaplInstance *object=0,const TCHAR *id=0, const TCHAR *name=0,const TCHAR *descr=0, CaplInstance *type=0,bool show_dlg=true);

	/** Отображает диалог со свойствами бизнес-процесса */
	bool ShowBPProperties(CaplInstance *bp,CaplInstance *bp_ref=0,bool *is_ok=0);

	/** Отображает диалог со свойствами ресурса бизнес-процесса 
	  @param  res ресурс бизнес-процесса 
	  @param  new_res ресурс бизнес-процесса после показа диалога 
	  @param  bp_rev версия бизнес-процесса (для отображения диалога свойств ресурса версии бп) */
	bool CaplBPManager::ShowBPResourceProperties(CaplInstance *res,CaplInstance **new_res,CaplInstance *bp_rev=0);

	/** Читает информацию из базы о бизнес-процессе */
	bool LoadBPInfo(CaplInstance *bp,bool bLoadSubBpInfo=true);

	/** Читает информацию из базы о нескольких бизнес-процессах */
	bool LoadBPInfo(aplExtent  &ext,bool bLoadSubBpInfo=false,bool show_status_dlg=false);

	/** Удаляет информацию о действии */
	bool DeleteBP(CaplInstance *bp, bool delete_sub_bp=true, CaplInstance *deleted_parent=0);

	/** Возвращает бизнес-процесс в базе по его  обозначению или NULL если такого нет   */
	CaplInstance *FindBPById(const TCHAR *id, bool bAutoLoadInfo = true);

	/** Читает информацию об бизнес-процессах, которые используют данный бизнес-процесс (родители)
		@param bp бизнес-процесс
		@param ext  список в котором возвращаются найденные бизнес-процессы (результат)
		@return true при удачном выполнении и false в случае ошибки */
	bool WhereUsedBP(CaplInstance *bp, aplExtent &ext, aplExtent *refs = NULL, bool bReferenceOnly = false);
	bool WhereUsedBP(aplExtent &items, aplExtent &ext, aplExtent *refs = NULL, bool bReferenceOnly = false);

	/** Возвращает в out_ext ассоцаторы бизнес-процессов с Instance 
		@param inst  объект, ассоцияции с которым ищутся 
		@param out_ext  список в котором возвращаются найденные бизнес-процессы (результат)
		@param out_rel  список в котором возвращаются найденные ассоциаторы (результат)
		@param context  определенный контекст (если ==0 все контексты)
		@return true при удачном выполнении и false в случае ошибки */
	bool FindAssociatedBP(CaplInstance *inst, aplExtent &out_ext, aplExtent &out_rel,CaplInstance *context=0,bool from_base=true); 
	/** Возвращает в out_ext ассоцаторы бизнес-процессов с массивом ext 
		@param ext список объектов, ассоцияции с которыми ищутся 
		@param out_ext  список в котором возвращаются найденные бизнес-процессы (результат)
		@param out_rel  список в котором возвращаются найденные ассоциаторы (результат)
		@param context  определенный контекст (если ==0 все контексты)
		@param show_status_dlg показывать диалог состояния загрузки (при загрузке из БД)
		@return true при удачном выполнении и false в случае ошибки */
	bool FindAssociatedBP(aplExtent &ext, aplExtent &out_ext, aplExtent &out_rel,CaplInstance *context=0,bool b_loadInfo=true,bool show_status_dlg=false); 
	/** Создает ассоциатор inst c bp 
		@param inst  объект, ассоцияция с которым создается 
		@param bp  бизнес-процесс, ассоцияция с которым создается
		@param id  идентификатор создаваемой связи
		@param zagotov связь с материалом или нормой расхода (pdr)
		@return созданный ассоциатор и NULL в случае ошибки */
	CaplInstance *CreateAssociation(CaplInstance *inst,CaplInstance *bp, const TCHAR *id=0,CaplInstance *zagotov=0);
	/** Ищет ассоциацию действия с inst 
		@param inst  объект, ассоцияция с которым ищется 
		@param bp  бизнес-процесс, ассоцияция которого ищется
		@return найденный ассоциатор и NULL если тагого нет  */
	CaplInstance *FindAssociation(CaplInstance *inst,CaplInstance *bp);

	/** Читает информацию о ресурсах действия */
	bool LoadAllBPResources(CaplInstance *bp, aplExtent &ext);

	/** Добавляет бизнес-процесс в другой бизнес-процесс
		@param base_bp бизнес-процесс, в который добавляем
		@param sub_bp  добавляемый бизнес-процесс */
	bool AddBPToBP(CaplInstance *sub_bp, CaplInstance *base_bp);
	
	/** Возвращает все версии бизнес-процесса  
		@param bp бизнес-процесс
		@param outExt  список версий бизнес-процесса (результат)
		@return true при удачном выполнении и false в случае ошибки */
	bool CaplBPManager::GetAllBPVersion(CaplInstance *bp,aplExtent &outExt);
	bool CaplBPManager::GetAllBPVersion(aplExtent& bp_ext,aplExtent &outExt);

	/** Удаляет связь между бизнес-процессами
		@param sub_bp подпроцесс
		@param base_bp родительский процесс или его версия (локер)
		@return true при удачном выполнении и false в случае ошибки */
	bool DeleteBPRelation(CaplInstance *sub_bp,CaplInstance *base_bp);

	/** Получает (рекурсивно) список подпроцессов бизнес-процесса.
		В список включаются также не утвержденные подпроцессы для редактируемых
		тек.пользователем процессов
		@param bp бизнес-процесс или его версия
		@param ext_out список найденных подпроцессов 
		@return true при удачном выполнении и false в случае ошибки */
	bool GetAllSubBP(CaplInstance *bp,aplExtent &ext_out);
		/** Получает (рекурсивно) список подпроцессов списка бизнес-процессов
		В список включаются также не утвержденные подпроцессы для редактируемых
		тек.пользователем процессов
		@param bp_ext список бизнес-процессов или версий
		@param ext_out список найденных подпроцессов 
		@return true при удачном выполнении и false в случае ошибки */
	bool GetAllSubBP(aplExtent &bp_ext,aplExtent &ext_out);

	/** Получает список экземпляров бизнесс-процессов для списка бизнес-процессов
		@param bp_ext список бизнес-процессов
		@param ext_out список найденных экземпляров бизнесс-процессов 
		@return true при удачном выполнении и false в случае ошибки */
	bool GetBPInstForBP(aplExtent &bp_ext,aplExtent &ext_out);

	/** Получает список экземпляров бизнесс-процессов для бизнес-процесса
		@param bp бизнес-процесс
		@param ext_out список найденных экземпляров бизнесс-процессов 
		@return true при удачном выполнении и false в случае ошибки */
	bool GetBPInstForBP(CaplInstance* bp,aplExtent &ext_out);
	
		/** Получает (рекурсивно) список экземпляров БП, входящих в заданный экземпляр БП
		@param inst экземпляр бизнес-процесса
		@param ext_out список найденных подпроцессов 
		@return true при удачном выполнении и false в случае ошибки */
	bool GetAllSubBPInst(CaplInstance *inst, aplExtent &ext);

	/** Выводит диалог выбора типа бизнес-процесса с учетом пользовательских групп типов документов  
		@param selected_doc_type выбранный тип бизнес-процесса по умолчанию 
		@param selected_group выбранная группа по умолчанию - пока не используется
		@return instance выбранного типа бизнес-процесса, иначе 0 */ 
	CaplInstance* SelectBpType(CaplInstance *selected_bp_type,CaplInstance *selected_group);

	/** Устанавливает флаг customized (индивидуальный) для БП и всех в него входящих
		@param bp корневой БП
		@param bСustomized устанавливаемый флаг
		@return true при удачном выполнении и false в случае ошибки */
	bool SetCustomizedRecursive(CaplInstance *bp, bool bСustomized);

	/**@name Блокировка и версии */
	//@{

	// **************************************************
	// Блокировка и версии
	// **************************************************
	
	/** Взять бизнес-процесс на редактирование 
		@param bp  бизнес-процесс или его версия */
	bool CheckOut( CaplInstance *bp,bool recursive=false);
	/** Взять бизнес-процесс на редактирование c выводом диалога запроса
		@param bp  бизнес-процесс или его версия 
		@param recursive брать на редактирование все входящие бизнес-процессы */
	bool CheckOutWithRequest( CaplInstance *bp,bool &recursive=m_bRecursive);

	/** Завершить  редактирование бизнес-процесса  
		@param bp  бизнес-процесс 
		@param recursive завершать редактирование всех входящих бизнес-процессов 
		//@param create_new_version создавать новую версию бп (если == false, то только меняется активная версия)
		@param make_new_version_active делать новую версию активной */
	//bool CheckIn( CaplInstance *bp,bool recursive=false,bool create_new_version=true,bool make_new_version_active=true);
	bool CheckIn(CaplInstance *bp,bool recursive=false,bool make_new_version_active=true);
	/** Завершить редактирование бизнес-процесса c выводом диалога запроса
		@param bp  бизнес-процесс 
		@param recursive завершить редактирование все входящих бизнес-процессов */
	bool CheckInWithRequest( CaplInstance *bp,bool &recursive=m_bRecursive);

	/** Отменить редактирование  */
	bool UndoCheckOut( CaplInstance *bp,bool recursive=false);
	/** Отменить редактирование бизнес-процесса c выводом диалога запроса
		@param bp  бизнес-процесс */
	bool UndoCheckOutWithRequest(CaplInstance *bp,bool &recursive=m_bRecursive);

	/** Проверяет наличие блокировки, и если такая есть возвращает на нее ссылку  
		@param bp  проверяемый бизнес-процесс или его версия
		@return локер бизнес-процесса,иначе 0 */
	CaplInstance *GetLock(CaplInstance *bp, bool bShowMessages);

	/** Проверяет наличие блокировки текущим пользователем, и если такая есть возвращает на нее ссылку  */
	CaplInstance *CheckMyLock(CaplInstance *bp, bool bShowMessages);

	/** Проверяет,взят ли бизнес-процесс на редактирование текущим пользователем
		@param bp  проверяемый бизнес-процесс или его версия
		@return true,если заблокирован текущим пользователем,false - если другим пользователем.Если не заблокирован,выводит запрос на блокировку */
	bool CheckMyLockAndCheckOut(CaplInstance *bp);
	/** Возвращает последюю версию бизнес-процесса (наибольшую по номеру)
		@param bp  бизнес-процесс 
		@param num номер возвращаемой версии
		@return последняя версия бизнес-процесса,0 если не найдена */
	CaplInstance *GetLatestBPVersion(CaplInstance *bp,CString &num);
	/** Создает версию бизнес-процесса
		@param bp  бизнес-процесс или его версия
		@param num номер создаваемой версии (-1 создавать очередную версию)
		@param make_active делать созданную версию активной
		@return созданная версия бизнес-процесса,или 0 в случае ошибки */
	CaplInstance *CreateBPVersion(CaplInstance *bp,CString num=_T("-1"),bool make_active=true);
	/** Делает версию бизнес-процесса активной
		@param bp версия бизнес-процесса 
		@return true при удачном выполнении и false в случае ошибки */
	bool MakeBPVersionActive(CaplInstance *bp_ver);
	/** Проверяет, изменился ли бизнес-процесс по сравнению с версией.
		@param bp бизнес-процесс
		@param bp_ver версия бизнес-процесса
		@return true если изменился (или произошла ошибка) и false противном случае */
	bool IsBPChanged(CaplInstance *bp,CaplInstance *bp_ver);
	/** Отображает диалог с изменениями бизнес-процесса */
	bool ShowBPChanges(CaplInstance *bp);
	// **************************************************
	// Экземпляр бизнес-процесса
	// **************************************************
	/** Создает описание экземпляра бизнес-процесса 
	  @param  base_bp_inst экземпляр бизнес-процесса - родитель
	  @param  id  id экземпляра бизнес-процесса по умолчанию 
	  @param  name наименование экземпляра бизнес-процесса по умолчанию 
	  @param  descr описание экземпляра бизнес-процесса по умолчанию 
	  @param  bp  базовый бизнес-процесс 
	  @param  item экземпляр изделия для создания связи
	  @param  context используемый контекст по умолчанию 
	  @param  rel созданная связь с бизнес-процесса с item				
	  @param  show_dlg показывать диалог создания экземпляра бизнес-процесса (если задан корректный id)
	  @return созданный объект 	*/
	CaplInstance *CreateBPInst(CaplInstance *base_bp_inst=0,const TCHAR *id=0,const TCHAR *name=0,const TCHAR *descr=0,CaplInstance *bp=0,CaplInstance *item=0,CaplInstance *context=0,CaplInstance **rel=0,bool show_dlg=true);
	/** Создает копию экземпляра бизнес-процесса 
	  @param  base_bp_inst экземпляр бизнес-процесса, данные которого копируются 
	  @param  id  обозначение экземпляра бизнес-процесса
	  @param  name наименование экземпляра бизнес-процесса 
	  @param  descr описание экземпляра бизнес-процесса
	  @param  bp  базовый бизнес-процесс 
	  @param  item  объект, с которым необходимо ассоциировать сознанный экземпляр бизнес-процесс 
	  @param  context контекст создаваемой связи c item
	  @param  rel созданная связь с экземпляра бизнес-процесса с item				
	  @param  parent_bp экземпляра бизнес-процесса родитель (при рекурсивном копировании всех вложенных)
	  @param  recursive копировать ли все вложенные подпроцессы
	  @return созданный объект 	*/
	CaplInstance *CreateBPInstCopy(CaplInstance *base_bp_inst,const TCHAR *id=0, const TCHAR *name=0,const TCHAR *descr=0,CaplInstance *bp=0,CaplInstance *item=0, CaplInstance *context=0,CaplInstance **rel=0,CaplInstance *parent_bp_inst=0,bool recursive=true);
	/** Читает информацию из базы об экземпляра бизнес-процесса 
	  @param  bp_inst экземпляр бизнес-процесса 
	  @return true при удачном выполнении и false в случае ошибки */
	bool LoadBPInstInfo(CaplInstance *bp_inst,bool bLoadSubBpInfo=true);
	/** Читает информацию из базы о нескольких экземплярах бизнес-процессов 
	  @param  ext экземпляры бизнес-процессов
	  @return true при удачном выполнении и false в случае ошибки */
	bool LoadBPInstInfo(aplExtent &ext,bool bLoadSubBpInfo=true);
	/** Читает информацию из базы о ресурсе
	    @return true при удачном выполнении и false в случае ошибки */
	bool LoadBPResourcesInfo(CaplInstance *res);
	/** Читает информацию из базы о нескольких ресурсах
	    @return true при удачном выполнении и false в случае ошибки */
	bool LoadBPResourcesInfo(aplExtent &ext);

	/** Создает ассоциатор экземпляра бизнес-процесса c экземпляром изделия 
		@param item  объект, ассоцияция с которым создается 
		@param bp_inst экземпляр бизнес-процесса, ассоцияция с которым создается
		@param context контекст, в котором создается связь 
		@param id  идентификатор создаваемой связи
		@return созданный ассоциатор и NULL в случае ошибки */
	CaplInstance *CreateInstanceAssociation(CaplInstance *item,CaplInstance *bp_inst,CaplInstance *context=0, const TCHAR *id=0, bool bTestUnique = true);
	/** Отображает диалог со свойствами экземпляра бизнес-процесса 
		@param bp_inst экземпляр бизнес-процесса 
		@param bp_inst_ref указатель на связь с экземпляра бизнес-процесса с экземпляром изделия 
		@return true при удачном выполнении и false в случае ошибки */
	bool ShowBPInstProperties(CaplInstance *bp_inst,CaplInstance *bp_inst_ref=0);
	/** Добавляет экземпляр бизнес-процесса в другой экземпляр бизнес-процесса
		@param sub_bp_inst экземпляр бизнес-процесса (подпроцесс)
		@param base_bp_inst экземпляр бизнес-процесса (процесс)
		@return true при удачном выполнении и false в случае ошибки */
	bool AddBPInstToBPInst(CaplInstance *sub_bp_inst, CaplInstance *base_bp_inst);
	/** Читает информацию об экземплярах бизнес-процессов, которые используют данный экземпляр бизнес-процесса (родители)
		@param bp_inst экземпляр бизнес-процесса
		@param ext  список в котором возвращаются найденные бизнес-процессы (результат)
		@param bFromBase читать из БД или только из КЭШ
		@param bReferenceOnly обрабатывать только связи (bp_inst_reference)
		@return true при удачном выполнении и false в случае ошибки */
	bool WhereUsedBPInst(CaplInstance *bp_inst, aplExtent &ext, bool bFromBase = true, bool bReferenceOnly = false);
	bool WhereUsedBPInst(aplExtent &bp_insts, aplExtent &ext, bool bFromBase = true, bool bReferenceOnly = false);
	bool WhereUsedBPInst(aplExtent &bp_insts, aplExtent &ext, aplExtent &refs, bool bFromBase = true);
	/** Удаляет связь между экземплярами бизнес-процессов
		@param sub_bp подпроцесс
		@param base_bp родительский процесс 
		@return true при удачном выполнении и false в случае ошибки */
	bool DeleteBPInstRelation(CaplInstance *sub_bp_inst,CaplInstance *base_bp_inst);
	/** Удаляет информацию об экземпляре бизнес-процесса 
		@param bp_inst экземпляр бизнес-процесса
		@param delete_sub_bp_inst удалять или нет подпроцессы
		@param deleted_parent ссылка на родительский процесс (служебный,используется при удалении подпроцессов) 
		@return true при удачном выполнении и false в случае ошибки */
	bool DeleteBPInst(CaplInstance *bp_inst, bool delete_sub_bp_inst=true, CaplInstance *deleted_parent=0);
	/** Ищет ассоциацию экземпляра изделия с экземляром бизнес-процесса
		@param item объект, ассоцияция с которым ищется 
		@param bp_inst экземпляр бизнес-процесса, ассоцияция c которым ищется
		@return найденный ассоциатор и NULL если такого нет  */
	CaplInstance *FindInstanceAssociation(CaplInstance *item,CaplInstance *bp_inst);
	/** Возвращает ассоцаторы экземпляров бизнес-процессов с item и экземпляры бизнес-процессов
		@param item объект, ассоциации с которым ищутся 
		@param out_ext  список в котором возвращаются найденные экземпляры бизнес-процессов (результат)
		@param out_rel  список в котором возвращаются найденные ассоциаторы (результат)
		@param context  контекст, в котором ищутся связи
		@return true при удачном выполнении и false в случае ошибки */
	bool FindAssociatedBPInst(CaplInstance *item, aplExtent &out_ext, aplExtent &out_rel,CaplInstance *context=0,bool from_base=true) ;
	/** Возвращает ассоцаторы экземпляров бизнес-процессов с массивом ext и экземпляры бизнес-процессов
		@param ext список объектов, ассоцияции с которыми ищутся 
		@param out_ext  список в котором возвращаются найденные экземпляры бизнес-процессов (результат)
		@param out_rel  список в котором возвращаются найденные ассоциаторы (результат)
		@param context  контекст, в котором ищутся связи
		@return true при удачном выполнении и false в случае ошибки */
	bool FindAssociatedBPInst(aplExtent &ext, aplExtent &out_ext, aplExtent &out_rel,CaplInstance *context=0) ;
	/** Возвращает бизнес-процессы и экземпляры бизнес-процессов,котрорые используют item в качестве ресурса
		@param item объект, который используется в качестве ресурса
		@param ext_bp  список в котором возвращаются найденные бизнес-процессы (результат)
		@param ext_bp_inst  список в котором возвращаются найденные экземпляры бизнес-процессов (результат)	*/
	bool ItemWhereUsedAsResource(CaplInstance *item,aplExtent &ext_bp,aplExtent &ext_bp_inst);
	/**	Возвращает Instance типа бизнес процесса с указаным именем.
		@param lpctstrName имя типа бизнес процесса
		@return Instance этого типа и NULL если такой не найден*/
	CaplInstance* GetBpTypeByName(LPCTSTR lpctstrName);

	/**	Создает связь между процессами.
		@param BpFrom - процесс на входе
		@param BpTo - процесс на выходе
		@param bTestUnique - проверять связь на уникальность.
		@param id - обозначение связи (не обязательное поле)
		@param name - наименование связи (не обязательное поле)
		@param descr - описание связи (не обязательное поле)
		@return Созданная связь*/
	CaplInstance* CreateBPRelation(CaplInstance* BpFrom, CaplInstance* BpTo, bool bTestUnique = true, TCHAR* id=0, TCHAR* name=0, TCHAR* descr=0);

	/**	Находит все поцессы на входе к заданному.
		@param Bp - процесс на входе
		@param ext - процессы на выходе
		@param rels - связи (не обязательное поле)*/
	bool FindBpFrom(CaplInstance* Bp, aplExtent &ext, aplExtent* rel = NULL);

	/**	Находит все поцессы на выходе к заданному.
		@param Bp - процесс на выходе
		@param ext - процессы на входе
		@param rels - связи (не обязательное поле)*/
	bool FindBpTo(CaplInstance* Bp, aplExtent &ext, aplExtent* rel = NULL);
	
	//	 основные функции для работы с расцеховкой

	/**	Получает расцеховку, начинающуюся с ciRootBP в виде строки
		@param ciRootBP		- корневой бизнес-процесс
		@param ciOffsetChar	- характеристика, используемая для задания групп опережения
		@param csDepotSep	- разделитель цехов
		@param csGrpSep		- разделитель групп
		@param bReadGrps	- читать группы опережения
		@param csOutRasc	- расцеховка на выходе*/
	bool GetRascString(CaplInstance* ciRootBP,CaplInstance* ciOffsetChar,
			CString& csDepotSep,CString& csGrpSep,bool bReadGrps,CString& csOutRasc);

	/** Удаляет расцеховку, начинающуюся с ciRootBP. Удаляет все бизнес-процессы, версии
		бизнес-процессов, значения характеристик, версии значений характеристик. 
		Доступ не проверяется! 
		(работает только с кешем!).
		@param ciRootBPRel	- связь изделия с корневым бизнес-процессом
		@param bDelRoot		- удалять корневой бизнес-процесс*/
	bool DeleteRasc(CaplInstance* ciRootBPRel,bool bDelRoot);

	/** Проверяет расцеховку на валидность - на недопустимые символы и на существование 
		цехов
		@param csInRasc		- расцеховка на входе
		@param csDepotSep	- разделитель цехов
		@param csGrpSep		- разделитель групп*/
	bool ValidateRasc(CString& csInRasc,CString& csDepotSep,CString& csGrpSep);

	/** Создает расцеховку для версии изделия
		@param ciInPdf		- изделие, для которого создается расцеховка на входе
		@param ciBPRascType	- тип корневого бизнес-процесса
		@param ciBPDepotType- тип бизнес-процесса - цеха
		@param ciShopChar	- характеристика - ссылка на рабочую группу
		@param ciOffsetChar - характеристика - группа опережения
		@param csInRasc		- расцеховка на входе
		@param csDepotSep	- разделитель цехов
		@param csGrpSep		- разделитель групп
		@param aeOutRasc	- массив созданных инстансов на выходе*/
	bool CreateRasc(CaplInstance* ciInPdf,
			CaplInstance* ciBPRascType,CaplInstance* ciBPDepotType,
			CaplInstance* ciShopChar,CaplInstance* ciOffsetChar,
			CString& csInRasc,CString& csDepotSep,CString& csGrpSep,
			aplExtent& aeOutRasc);



	//	дополнительные функции для работы с расцеховкой

	/** Получает значение характеристики для инстанса (работает только с кешем!)
		@param ciInst		- инстанс, для которого ищутся характеристики
		@param ciChar		- характеристика, для которой ищутся значения*/
	CaplInstance* GetInstCharVal(CaplInstance* ciInst,CaplInstance* ciChar);

	/**	Разбирает строку с расцеховкой на массив цехов и массив групп опережения.
		Если csapOutDepots или csapOutGrps равен NULL - в него ничего не добавляется.
		Организации должны быть загружены в кеш.
		@param csInRasc		- расцеховка на входе
		@param csDepotSep	- разделитель цехов
		@param csGrpSep		- разделитель групп
		@param csapOutDepots- массив цехов на выходе
		@param csapOutGrps	- массив групп опережения на выходе*/
	void ParseRasc(CString& csInRasc,CString& csDepotSep,CString& csGrpSep,
			CStringArray* csapOutDepots,CStringArray* csapOutGrps);

	/**	Возвращает инстансы, связанные с расцеховкой. Возвращает бизнес-процессы, версии
		бизнес-процессов, значения характеристик, версии значений характеристик.
		Доступ не проверяется! 
		(работает только с кешем!).
		@param ciRootBPRel	- связь изделия с корневым бизнес-процессом
		@param aeOutInsts	- массив инстансов на выходе
		@param bIncludeRoot	- включать инстансы для корневого процесса и связь с изделием*/
	void GetRascInsts(CaplInstance* ciRootBPRel,aplExtent& aeOutInsts,bool bIncludeRoot);

	/** Создаёт корневой бизнес-процесс расцеховки
		@param ciInItem			- инстанс, для которого создается бизнес-процесс
		@param csBPId			- обозначение бизнес-процесса
		@param ciRootBPType		- тип бизнес-процесса
		@param ciOutRootBP		- созданный бизнес-процесс на выходе
		@param ciOutRootBPRev	- созданная версия бизнес-процесса на выходе
		@param aeOutRasc		- массив созданных инстансов на выходе*/
	void CreateRootRascBP(CaplInstance* ciInItem,
			CString& csBPId,CaplInstance* ciRootBPType,CaplInstance*& ciOutRootBP,
			CaplInstance*& ciOutRootBPRev,aplExtent& aeOutRasc);
	
	/**	Создает элемент расцеховки. Создает бизнес-процесс, хар-ку - ссылку на организацию,
		хар-ку - группу опережения (если есть)
		@param ciInParentBP		- корневой бизнес-процесс на входе
		@param csBPIdPrefix		- префикс обозначения бизнес-процесса
		@param iNum				- порядковый номер в расцеховке
		@param csDepot			- цех
		@param csGrp			- группа опережения
		@param ciDepotBPType	- тип бизнес-процесса - цеха
		@param ciShopChar		- характеристика - ссылка на цех
		@param ciOffsetChar		- характеристика - группа опережения
		@param ciOutDepotBP		- созданный бизнес-процесс на выходе
		@param aeOutRasc		- массив созданных инстансов на выходе*/
	void CreateRascItem(CaplInstance* ciInParentBP,CString& csBPIdPrefix,int iNum,
			CString& csDepot,CString& csGrp,CaplInstance* ciDepotBPType,
			CaplInstance* ciShopChar,CaplInstance* ciOffsetChar,
			CaplInstance*& ciOutDepotBP,aplExtent& aeOutRasc);

	/** Создает бизнес-процесс для расцеховки.
		@param ciInParentBP		- родительский бизнес-процесс на входе
		@param ciBPType			- тип бизнес-процесса
		@param ciOutBP			- созданный бизнес-процесс на выходе
		@param ciOutBPRev		- созданная версия бизнес-процесса на выходе*/
	void CreateRascBP(CaplInstance* ciInParentBP,CaplInstance* ciBPType,
			CaplInstance*& ciOutBP,CaplInstance*& ciOutBPRev);

	/** Создает значение ссылочной характеристики
		@param ciItem			- инстанс, для которого создается значение характеристики
		@param ciChar			- характеристика, для которой создается значение
		@param ciVal			- инстанс - значение 
		@param ciOutCV			- созданное значение характеристики
		@param ciOutCVRev		- созданная версия значения характеристики*/
	void CreateRascRefCV(CaplInstance* ciItem,CaplInstance* ciChar,CaplInstance* ciVal,
			CaplInstance*& ciOutCV,CaplInstance*& ciOutCVRev);

	/** Создает значение measured характеристики
		@param ciItem			- инстанс, для которого создается значение характеристики
		@param ciChar			- характеристика, для которой создается значение
		@param dVal				- число - значение 
		@param ciOutCV			- созданное значение характеристики
		@param ciOutCVRev		- созданная версия значения характеристики*/
	void CreateRascMeasuredCV(CaplInstance* ciItem,CaplInstance* ciChar,double dVal,
			CaplInstance*& ciOutCV,CaplInstance*& ciOutCVRev);
	
	/** Задает новое значение характеристики "Расцеховка" после изменений бизнес-процессов расцеховки
		@param iBP				- инстанис изменяемого бизнес-процесса*/
	void RebuildCharactRasc(CaplInstance *iBP);


	/** Возвращает экземпляр бизнес-процесса в базе по его  обозначению или NULL если такого нет   */
	CaplInstance *FindBPInstById(const TCHAR *id, bool bAutoLoadInfo = true);

	//@}

};

// *************************************************************************
// *************************************************************************
// *************************************************************************
/** Менеджер экземпляров изделий*/
class CLASS_DECL_APL_STEP_MGR CaplPrdInstManager: public CaplStepManager
{
	// Инициализация

public:
	virtual bool Attach(CaplAPI *api);
	virtual void Detach();
	
	// Экземпляры
	CaplEntity *e_prd_inst;
	CaplAttr *a_prd_inst_id,*a_prd_inst_descr,*a_prd_inst_pdf,*a_prd_inst_sn;
	CaplAttr *a_prd_inst_rfid;
	CaplAttr *a_prd_inst_lot;
	CaplAttr *a_prd_inst_guid;
	CaplAttr *a_prd_inst_seria;
	CaplAttr *a_prd_inst_ils_product_instance;

	CaplEntity *e_prd_inst_rel,*e_apl_component;
	CaplAttr *a_prd_inst_rel_id, *a_prd_inst_rel_name, *a_prd_inst_rel_descr,*a_prd_inst_rel_pdr;
	CaplAttr *a_prd_inst_rel_relating, *a_prd_inst_rel_related;
	CaplAttr *a_prd_inst_rel_date_installed, *a_prd_inst_rel_date_removed;
	CaplAttr *a_prd_inst_rel_frames_of_reference;
	CaplAttr *a_prd_inst_rel_position;
	CaplAttr *a_prd_inst_rel_place;
	CaplAttr *a_prd_inst_rel_person;
	CaplAttr *a_prd_inst_rel_prototipe;
	CaplAttr *a_prd_inst_rel_guid;

	CaplAttr *a_prd_inst_datetime;
	CaplAttr *a_prd_inst_state;
	CaplAttr *a_prd_inst_baseitem;
	CaplAttr *a_prd_inst_additional_data;
	CaplAttr *a_prd_inst_code;

	CaplAttr *a_prd_inst_vniis_shipment_date;
	CaplAttr *a_prd_inst_vniis_customer;

//	CaplAttr *a_prd_inst_place;
	// Партии
	CaplEntity *e_lot;
	CaplAttr *a_lot_id,*a_lot_descr,*a_lot_pdf,*a_lot_size, *a_lot_parent;

	// Замена
	CaplEntity *e_pi_subst;
	CaplAttr *a_pi_subst_predecessor;
	CaplAttr *a_pi_subst_successor;
	CaplAttr *a_pi_subst_reason;
	CaplAttr *a_pi_subst_bp;
	CaplAttr *a_pi_subst_description;
	CaplAttr *a_pi_subst_job;//для ЖПС - работа, при которой зафиксировали замену
	CaplAttr *a_pi_subst_date;//для ЖПС - дата,  --//--
	CaplAttr *a_pi_subst_guid;
	

	CaplEntity *e_mwu;
	CaplAttr *a_mwu_val,*a_mwu_unit;

	bool m_bUseIlsProducrInstance; // Использовать экземпляры изделий ILS

	// Методы
public:
	/** Создает описание экземпляра изделия */
	CaplInstance *CreatePrdInst(CaplInstance *pdf=0,CaplInstance *lot=0);

	/** Создает копию описания экземпляра изделия */
	CaplInstance *CopyPrdInst(CaplInstance *base_inst=0);

	/** Отображает свойства экземпляра изделия */
	bool ShowPrdInstProperties(CaplInstance *pi,CaplInstance *pi_rel=0);
	
	/** Читает информацию об экземпляре изделия из базы в кэш */
	bool LoadPrdInstInfo(CaplInstance *inst);

	/** Читает информацию об экземплярах изделий из базы в кэш */
	bool LoadPrdInstInfo(aplExtent &ext);
	
	/** Удаляет информацию об экземпляре изделия */
	bool DeletePrdInst(CaplInstance *inst);
	
	/** Возвращает в out_ext все экземпляры изделия pdf */
	bool FindAllPdfInstances(CaplInstance *pdf, aplExtent &out_ext);
	bool FindAllPdfInstances(aplExtent &pdf, aplExtent &out_ext);

	/** Поиск экземпляра изделия по версии изделия и серийному номеру
		@param pdf - версия изделия
		@param lpszSN - серийный номер
		@return указатель на найденную Instance и NULL в противном случае*/
	CaplInstance* FindPrdInstByPDFSN(CaplInstance *pdf, LPCTSTR lpszSN);

	/** Вставка одного экземпляра в другой */
	CaplInstance *InsertInPI(CaplInstance *parent_prdinst, CaplInstance *sub_prdinst, CaplInstance *pdr=0);

	/** Замена одного экземпляра другим
	@param old_rel - заменяемая связь между экземплярами изделия
	@param new_pi  - заменяющий экземпляр изделия
	@return созданный объект - замена и 0 в случае ошибки */
	CaplInstance *ChangePIinPI(CaplInstance *old_rel, CaplInstance *new_pi = 0);
	
	/** Возвращает входящие экземпляры   */
	bool LoadInsertedInstances(CaplInstance *prdinst, aplExtent &out_rel, aplExtent &out_ext);
	bool LoadInsertedInstances(aplExtent &prdinsts, aplExtent &out_rel, aplExtent &out_ext);

	/** Возвращает экземпляры в которые входит  */
	bool WhereUsedPIinPI(CaplInstance *prdinst, aplExtent &out_rel, aplExtent &out_ext);
	
	// Методы для партий

	/** Создает описание партии изделий */
	CaplInstance *CreateLot(CaplInstance *pdf=0, CaplInstance *parent_lot=0);

	/** Отображает диалог со свойствами партии изделий */
	bool ShowLotProperties(CaplInstance *lot);

	/** Читает информацию о партии изделий из базы в кэш */
	bool LoadLotInfo(CaplInstance *lot);

	/** Читает информацию о партиях изделий из базы в кэш  */
	bool LoadLotInfo(aplExtent &ext);

	/** Удаляет информацию о партии изделий */
	bool DeleteLot(CaplInstance *lot);
	
	/** Возвращает в out_ext все партии изделий для PDF */
	bool FindAllPdfLoot(CaplInstance *pdf, aplExtent &out_ext);

	/** Возвращает в out_ext все экземпляры изделий для партии lot */
	bool FindAllLotProductInstance(CaplInstance *lot, aplExtent &out_ext, bool bFromBalse = true);
	bool FindAllLotProductInstance(aplExtent &lots, aplExtent &out_ext, bool bFromBalse = true);
	
	/** Возвращает входящие в партию партии   */
	bool LoadIncomingLots(CaplInstance *lot, aplExtent &out_ext);
	
};
// *************************************************************************
// *************************************************************************
// *************************************************************************

enum TypeAdj {adj_appr=0,adj_char=1,adj_doc=2,adj_res=3,adj_blob=4,adj_class=5};

enum TypeFindObject{
	FindObject_NDef=-1,
	FindObject_Product=0,
	FindObject_ProductVer=1,
	FindObject_Document=2,
	FindObject_Lot=3,
	FindObject_ProductInst=4,
	FindObject_BP=5,
	FindObject_BPInst=6,
	FindObject_Category=7,
	FindObject_Folder=8,
	FindObject_Project=9,
	FindObject_Person=10,
	FindObject_Organization=11,
	FindObject_Find=12,
	FindObject_All=13,
	FindObject_Change=14,
	FindObject_CombinedTable=15,
	FindObject_ClassifSystem=16,
	FindObject_ClassifLevel=17,
	FindObject_Process=18,
	FindObject_Task=19,
	FindObject_Requirement=20,
	FindObject_Refusal=21,
	FindObject_MAX=22 // При добавлении нового значения - надо добавлять влять значение перед этой константой, а значение константы увеличивать!!!
	// Константа определяет размер массива для всяких служебных нужд !!!
};

enum TypeFOAttr{
	TFO_Id		=	0,// - обозначение объекта 
	TFO_Name	=	1,// - наименование оъекта (или серийный номер экземпляра)
	TFO_Descr	=	2,// - описание объекта
	TFO_Type	=	3,// - тип (вид) объекта
	TFO_Code	=	4,// - код версии изделия или другого объекта
	TFO_Source	=	5,// - источник
	TFO_Ver		=	6,// - обозначение версии изделия
	TFO_CodeVer1=	7,// - код версии изделия 1, документ - инвентарный номер
	TFO_CodeVer2=	8,// - код версии изделия 2
	TFO_CodeIzd=	9,// - код изделия 
	TFO_VerDescr=	10,// - описание версии объекта, неисправность - Внешний вид
	TFO_Standart=	11,// - версия издедия - стандартное или нет. Документ: Включать в комплект документации
	TFO_Part	=	12,// часть документа
	TFO_Label	=	13,//версия документа - метка
	TFO_InAggr  =   14,// изменения - зависимые изделия
	TFO_VerList	=	15,//версия документа - лист
	TFO_VerLists=	16,//версия документа - листы
	TFO_VerFormat=	17,//версия документа - формат, проект - планирование
	TFO_VerLitera=	18,//версия документа - литера
	TFO_DocCode1=	19,//код вида документа, задача - Приоритет
	TFO_DocCode2=	20,//версия документа - литера, задача - Состояние
 	TFO_RelContext=	21,//контекст сборки, документа
	TFO_ProjCustomer	=22,	//проект - заказчик, изменение - пользователь
	TFO_ProjKurator		=23,		//проект - ответственный, изменение - Сотрудник, документ - Исполнитель
	TFO_ProjExecutors	=24,	//проект - Исполнители, документ - Получатель
	TFO_ProjCoexecutors	=25,	//проект - Соисполнители

	TFO_Date1	=	26,//проект - дата начала по плану; версия документа - дата источника // неисправность - Дата регистрации
	TFO_Date2	=	27,//проект - дата начала по факт, документ - Исполнить к, изменение - Срок действия ПИ // неисправность - Дата обнаружения
	TFO_Date3	=	28,//проект - дата окончания по плану, документ - Срок исп. план. // неисправность - Дата устранения
	TFO_Date4	=	29,//проект - дата окончания по факт, документ - Срок исп. факт.
	TFO_DocUrgency = 30, // документ - Срочность
	TFO_StrExt		= 31, // изменение - срок изменений

	TFO_RefDocType		= 32, // неисправность - Тип документа
	TFO_RefDocNum		= 33, // неисправность - Номер документа
	TFO_RefState		= 34, // неисправность - Состояние

	TFO_RefOrg			= 35, // неисправность - Цех, где обнаружена неисправность
	TFO_RefSector		= 36, // неисправность - Участок, где обнаружена неисправность
	TFO_RefCulprit		= 37, // неисправность - Виновник
	TFO_RefStage		= 38, // неисправность - Этап

	TFO_RefMainPDF		= 39, // неисправность - Основное изделие
	TFO_RefMainItem		= 40, // неисправность - Экземпляр основного изделия
	TFO_RefSystem		= 41, // !!!не используется!!! неисправность - Система
	TFO_RefFailedItem	= 42, // неисправность - Компонент (блок)
	TFO_RefFailedPart	= 43, // неисправность - Отказавший элемент
	TFO_RefConditions	= 44, // неисправность - Обстоятельства обнаружения
	TFO_RefDof			= 45, // неисправность - Характер
	TFO_RefFaultReason	= 46, // неисправность - Причина
	TFO_RefMethod		= 47, // неисправность - Способ устранения
	TFO_RefConsequence	= 48, // неисправность - Последствия
	TFO_RefManif		= 49, // неисправность - Виновник
	TFO_RefManifDescr	= 50, // неисправность - Внешние проявления
	
	TFO_ProcTaskId = 51,	// Процесс - Обозначение задания
	TFO_ProcTaskName = 52,	// Процесс - Наименование задания
	TFO_ProcTaskPerformer = 53,	// Процесс - Исполнитель задания
	TFO_ProcTaskExpired = 54,	// Процесс - Задание просрочено
	TFO_ProcTaskExpiredNDays = 55,	// Процесс - До просрочки задания меньше заданного количества дней
	TFO_ProcState = 56,	// Процесс - Состояние

	TFO_ProcRefusalCulprit = 57,	// Процесс - Виновник неисправности. Под вопросом, непонятно как делать запрос
	TFO_ProcTemplate = 58,	// Процесс - Шаблон
	TFO_ProcActivity = 59,	// Процесс - Действие (шаблон задания)
	TFO_ProcOwner = 60,	// Процесс - Владелец
	TFO_DocMaillist = 61, // Документ - Список рассылки
	TFO_State = 62, // для версии изделия, документа, бизнес-процесса и требования поиск по атрибуту "Состояние".
	TFO_Groupe =	63	// - документ - групповой или нет

	
// 	TFO_RelPos	=	91,// - сборка - позиция
// 	TFO_RelPosId=	92,// - сборка - позиционное обозначение
// 	TFO_RelName	=	93,// - сборка - наименование
// 	TFO_RelDescr=	94// - сборка - описание
};



////////////////////////////////////////////////////////
// Структуры для хранения:
// Характеристик
struct ElValChar{
	ElValChar(){Init();};
	ElValChar(ElValChar* old){
		Init();
		if(old!=0){
			*this = old;
		}
	}
	~ElValChar(){if(dtt!=0){delete dtt;}};
	void Init(){is_exist=true;apl_char=0;b_val=false;b_max=false;b_min=false;dtt=0;dtt_max=0;type=0;m_cur_ref_val=0;};
	void operator = (ElValChar* old){
		if(old==0){return;}
		is_exist=old->is_exist;
		apl_char=old->apl_char;
		b_val=old->b_val;
		log_relation=old->log_relation;
		val=old->val;
		b_max=old->b_max;
		log_relation_max=old->log_relation_max;
		val_max=old->val_max;
		b_min=old->b_min;
		log_relation_min=old->log_relation_min;
		val_min=old->val_min;
		if(old->dtt!=0){dtt=new COleDateTime(*old->dtt);}else{dtt=0;}
		type=old->type;
		m_cur_ref_val=old->m_cur_ref_val;
	}
	bool Compare(ElValChar* par){
		if(par==0)return false;
		if(is_exist!=par->is_exist)return false;
		if(apl_char!=par->apl_char)return false;
		if(b_val!=par->b_val)return false;
		if(log_relation!=par->log_relation)return false;
		if(val!=par->val)return false;
		if(b_max!=par->b_max)return false;
		if(log_relation_max!=par->log_relation_max)return false;
		if(val_max!=par->val_max)return false;
		if(b_min!=par->b_min)return false;
		if(log_relation_min!=par->log_relation_min)return false;
		if(val_min!=par->val_min)return false;
		if(dtt!=par->dtt)return false;
		if(type!=par->type)return false;
		if(m_cur_ref_val!=par->m_cur_ref_val)return false;
		return true;
	}
	bool is_exist;
	CaplInstance* apl_char;
	bool b_val;
	CaplQLQuery::aplQLLogRelation log_relation;
	CString val;//
	bool b_max;
	CaplQLQuery::aplQLLogRelation log_relation_max;
	CString val_max;//
	bool b_min;
	CaplQLQuery::aplQLLogRelation log_relation_min;
	CString val_min;//
	COleDateTime *dtt;
	COleDateTime *dtt_max;
	CaplInstance* type;
	CaplInstance* m_cur_ref_val;
};
// Тел Документов
struct ElValBLOB{
	ElValBLOB(){is_equal=false;word=_T("");}
	ElValBLOB(ElValBLOB *old){is_equal=old->is_equal;word=old->word;}
	bool Compare(ElValBLOB* par){
		if(is_equal!=par->is_equal)return false;
		if(word!=par->word)return false;
		return true;
	}
	bool is_equal;
	CString word;
};
// Документов
struct ElValDoc{
	ElValDoc(){Init();}
	ElValDoc(ElValDoc *old){
		if(old==0){Init();return;}
		is_exist=old->is_exist;
		name=old->name;
		is_eq_name=old->is_eq_name;
		id=old->id;
		is_eq_id=old->is_eq_id;
		type=old->type;
	}
	void Init(){is_exist=true;type=0;}
	bool Compare(ElValDoc *par){
		if(par==0)return false;
		if(is_exist!=par->is_exist)return false;
		if(name!=par->name)return false;
		if(is_eq_name!=par->is_eq_name)return false;
		if(id!=par->id)return false;
		if(is_eq_id!=par->is_eq_id)return false;
		if(type!=par->type)return false;
		return true;
	}
	bool is_exist;
	CString name;
	bool is_eq_name;
	CString id;
	bool is_eq_id;
	CaplInstance* type;
};
// Справочников
struct ElValClass{
	ElValClass(){Init();}
	ElValClass(ElValClass *old){
		if(old==0){Init();return;}
		is_exist=old->is_exist;
		classif=old->classif;
		//is_eq=old->is_eq;
	}
	void Init(){is_exist=true;classif=0;}
	bool Compare(ElValClass *par){
		if(par==0)return false;
		if(is_exist!=par->is_exist)return false;
		//if(is_eq!=par->is_eq)return false;
		if(classif!=par->classif)return false;
		return true;
	}
	bool is_exist;
	CaplInstance* classif;
	//bool is_eq;
};
// Ресурсов
struct ElValRes{
	enum TypeResObj{TRONoType=0,TROProduct=1,TROPerson=2,TROOrg=3};
	ElValRes(){Init();}
	ElValRes(ElValRes *old){
		if(old==0){Init();return;}
		is_exist=old->is_exist;
		name_res=old->name_res;
		name_obj=old->name_obj;
		is_eq_name_res=old->is_eq_name_res;
		is_eq_name_obj=old->is_eq_name_obj;
		id_res=old->id_res;
		id_obj=old->id_obj;
		is_eq_id_res=old->is_eq_id_res;
		is_eq_id_obj=old->is_eq_id_obj;
		type_res=old->type_res;
		type_obj=old->type_obj;
	}
	void Init(){is_exist=true;type_res=0;type_obj=TRONoType;}
	bool Compare(ElValRes *par){
		if(par==0)return false;
		if(is_exist!=par->is_exist)return false;
		if(name_res!=par->name_res)return false;
		if(name_obj!=par->name_obj)return false;
		if(is_eq_name_res!=par->is_eq_name_res)return false;
		if(is_eq_name_obj!=par->is_eq_name_obj)return false;
		if(id_res!=par->id_res)return false;
		if(id_obj!=par->id_obj)return false;
		if(is_eq_id_res!=par->is_eq_id_res)return false;
		if(is_eq_id_obj!=par->is_eq_id_obj)return false;
		if(type_res!=par->type_res)return false;
		if(type_obj!=par->type_obj)return false;
		return true;
	}
	bool is_exist;
	CString name_res;
	CString name_obj;
	bool is_eq_name_res;
	bool is_eq_name_obj;
	CString id_res;
	CString id_obj;
	bool is_eq_id_res;
	bool is_eq_id_obj;
	CaplInstance* type_res;
	TypeResObj type_obj;
};
// Статусов
struct ElValApproval{
	ElValApproval(){Init();}

	ElValApproval(ElValApproval* old)
	{
		if(old==0){Init();return;}
		is_exist=old->is_exist;
		is_dig_sign=old->is_dig_sign;
		status=old->status;
		person=old->person;
		pers_org_role=old->pers_org_role;
		descr=old->descr;
		descr_relation=old->descr_relation;
		pers_org_role_eq=old->pers_org_role_eq;
		is_single_date=old->is_single_date;
		if(old->date_time_beg){date_time_beg=new COleDateTime(*old->date_time_beg);}else{date_time_beg=0;}
		if(old->date_time_end){date_time_end=new COleDateTime(*old->date_time_end);}else{date_time_end=0;}
		if(old->revoc_date_time_beg){revoc_date_time_beg=new COleDateTime(*old->revoc_date_time_beg);}else{revoc_date_time_beg=0;}
		if(old->revoc_date_time_end){revoc_date_time_end=new COleDateTime(*old->revoc_date_time_end);}else{revoc_date_time_end=0;}
	}
	~ElValApproval()
	{
		if(date_time_beg!=0)delete date_time_beg;
		if(date_time_end!=0)delete date_time_end;
		if(revoc_date_time_beg!=0)delete revoc_date_time_beg;
		if(revoc_date_time_end!=0)delete revoc_date_time_end;
	}
	void Init()
	{
		is_exist=true;status=0;person=0;pers_org_role=_T("");descr=_T("");descr_relation=CaplQLQuery::aplLIKE;is_dig_sign=-1;
		date_time_beg=0;date_time_end=0;
		is_single_date=true;
		revoc_date_time_beg=0;revoc_date_time_end=0;
	}
	bool Compare(ElValApproval* par)
	{
		if(par==0)return false;
		if(is_exist!=par->is_exist)return false;
		if(is_dig_sign!=par->is_dig_sign)return false;
		if(status!=par->status)return false;
		if(person!=par->person)return false;
		if(pers_org_role!=par->pers_org_role)return false;
		if(descr!=par->descr)return false;
		if(descr_relation!=par->descr_relation)return false;
		if(pers_org_role_eq!=par->pers_org_role_eq)return false;
		if(is_single_date!=par->is_single_date)return false;
		if(date_time_beg!=par->date_time_beg)return false;
		if(date_time_end!=par->date_time_end)return false;
		if(revoc_date_time_beg!=par->revoc_date_time_beg)return false;
		if(revoc_date_time_end!=par->revoc_date_time_end)return false;
		return true;
	}
	bool IsEmpty()
	{
		return (status==0 && person==0 && pers_org_role==_T("") && descr==_T("") && 
		date_time_beg==0 && date_time_end==0 &&
		revoc_date_time_beg==0 && revoc_date_time_end==0 && is_dig_sign==-1);
	}
	bool is_exist;
	int is_dig_sign;
	CaplInstance* status;
	CaplInstance* person;
	CString pers_org_role;
	CString descr;
	// Допустимые отношения для descr_relation
	//	aplLIKE=9,// "содержит"
	//	aplNOTLIKE=10,// "не содержит"
	// 	aplEQUAL=5,//"равно"
	// 	aplNOTEQUAL=6,//"не равно"
	CaplQLQuery::aplQLLogRelation descr_relation;
	bool pers_org_role_eq;
	bool is_single_date;
	COleDateTime* date_time_beg;
	COleDateTime* date_time_end;
	COleDateTime* revoc_date_time_beg;
	COleDateTime* revoc_date_time_end;
};

class CFindDlg;

/** Менеджер запросов и сводных таблиц*/
class CLASS_DECL_APL_STEP_MGR CaplQueryManager: public CaplStepManager
{
	// Инициализация
public:
	CaplQueryManager();
	~CaplQueryManager();
	/** Инициализирует класс (Ассоциация с классом базы данных) 
		@return true при удачном выполнении и false в случае ошибки */
	virtual bool Attach(CaplAPI *api);
	virtual void Detach();
	
	// Методы
public:

	/** Читает информацию из базы о объекте сводной таблицы */
	bool LoadCombinedTableInfo(CaplInstance *ct,bool load_content=false,bool hide_error=false);
	
	/** Читает информацию из базы о нескольких объектах сводной таблицы*/
	bool LoadCombinedTableInfo(aplExtent  &ext,bool load_content=false,bool hide_error=false);
	
	/** Получить буфер с данными о ширине и наличии столбцов */
	bool ReadCombinedTableColumnsInfo(CaplInstance *ct,CaplDataBuf &dbuf,bool hide_error=false);
	/** Записать буфер с данными о ширине и наличии столбцов */
	bool SaveCombinedTableColumnsInfo(CaplInstance *ct,CaplDataBuf &dbuf,bool hide_error=false);
	/** Создать и показать сводную таблицу на основании предыдйщего запроса или уже существующей инстансы таблицы*/
	CaplInstance* ShowCombinedTable(CaplInstance *basic,CString name=_T(""));

	/** Читает информацию из базы о объекте поиска */
	bool LoadQueryInfo(CaplInstance *query,bool load_content=false,bool hide_error=false);
	
	/** Читает информацию из базы о нескольких объектах поиска*/
	bool LoadQueryInfo(aplExtent  &ext,bool load_content=false,bool hide_error=false);
	
	/** Формирует запрос на языке запросов с помощью диалога создания запросов или 
	путем ввода вручную
		@param query - объект поиска. Если на входе 0 - создает его
		@param dbuf - !!! устарел - буфер, в который будет записано состояние диалога
		@param name - имя поиска, которое будет выводиться в поле "имя запроса"
		@param only_lng - если true, то сразу выводится диалог редактирования языка запроса
		@param can_make_table - доступна ли для изменения галочка "вывести результат в таблицу"
		@param can_save - если true, то поиск можно сохранить в БД
		@param mode_slave - если true, то запрос самостоятельный (есть инстанс, имя и т.п.); если false - запрос вспомогательный (напритмер из подетального состава, или из SelectDialog)
		@param mode - вид создаваемого поиска. Может быть:
			"Query" (или значение по умолчанию "") - стандартный расширенный поиск
			"Query_niiao" - поиск для НИИАО - связка pdf-product_instance-bisness process
			для уже существующего поиска игнорируется
		@param type_find_object - маска списка объектов, которые будут отоюбражаться в поле выбора "найти"
		@param text_query - текст запроса на языке запросов. Имеет значение только для вновь 
			создаваемых запросов; для них если параметр не пустой, то вне зависимости от 
			состояния параметра only_lng создается запрос в режиме языка запросов.
		@return указатель на объект поиска в случае успеха и 0 в случае ошибки */
	CaplInstance* PrepareQuery(CaplInstance *query/*,CaplDataBuf *dbuf=0*/,CString name=_T(""),
				bool only_lng=false,bool can_make_table=true,bool can_save=true,bool mode_slave=false,
				CString mode_quiery=_T(""),long type_find_object=0,CString text_query=_T(""),bool *is_new_window=0);

	CaplInstance* PrepareQueryOld(CaplInstance *query/*,CaplDataBuf *dbuf=0*/,CString name=_T(""),
				bool only_lng=false,bool can_make_table=true,bool can_save=true,bool mode_slave=false,
				CString mode_quiery=_T(""),long type_find_object=0,CString text_query=_T(""));
	CaplInstance* PrepareQueryNew(CaplInstance *query/*,CaplDataBuf *dbuf=0*/,CString name=_T(""),
				bool only_lng=false,bool can_make_table=true,bool can_save=true,bool mode_slave=false,
				CString mode_quiery=_T(""),long type_find_object=0,CString text_query=_T(""),bool *is_new_window=0);

	CaplInstance* CopyQuery(CaplInstance *query,bool force_temporary);

	void SetStyleDlg(DWORD m_show_old_query_dlg);

	bool m_is_old_dlg;
public:
	/** Выводит диалог быстрого поиска
		@param query - объект поиска. Если на входе 0 - создает его
		@param dbuf - !!! устарел - буфер, в который будет записано состояние диалога
		@param mode - указывает тип искомого объекта. Может быть:
			"product"
			"document"
			"lot"
			"product_instance"
			"bp"
		@param predef_id - параметр id искомого объекта должен быть равен указанному
			значению. Если это условие или predef_name задано, то диалог не выводится, а
			автоматически выполняется поиск.
		@param predef_name - параметр name искомого объекта должен быть равен указанному
			значению. Если это условие или predef_id задано, то диалог не выводится, а
			автоматически выполняется поиск.
		@return указатель на объект поиска в случае успеха и 0 в случае ошибки */
	CaplInstance* PrepareFind(CaplInstance *query/*,CaplDataBuf *dbuf=0*/,CString mode=_T(""),
								CString predef_id=_T(""),CString predef_name=_T(""));
		
	/** Получает параметры быстрого поиска
		@param query - объект поиска. 
		@param mode - указывает тип искомого объекта. Может быть:
			"product"
			"document"
			"lot"
			"product_instance"
			"bp"
		@param is_id - надо ли выполнять поиск по id
		@param id - значение на поиск по id
		@param is_name - надо ли выполнять поиск по наименованию (или серийному номеру)
		@param name - значение на поиск по наименованию (или серийному номеру)
		@param is_equal - если true, то ищутся инстансы с атрибутами, равные указанным
						если false - то с атрибутами, в которые входят указанные значения
		@return true в случае успеха и false в случае ошибки */
	bool GetFindParams(CaplInstance *query,CString &mode,BOOL &is_id,CString &id,
								BOOL &is_name,CString &name,BOOL &is_equal);
	bool GetFindParams(CaplInstance *query,CFindDlg *dlg=0);
	
	/** Устанавливает параметры быстрого поиска
		@param query - объект поиска. 
		@param mode - указывает тип искомого объекта. Может быть:
			"product"
			"document"
			"lot"
			"product_instance"
			"bp"
		@param is_id - надо ли выполнять поиск по id
		@param id - значение на поиск по id
		@param is_name - надо ли выполнять поиск по наименованию (или серийному номеру)
		@param name - значение на поиск по наименованию (или серийному номеру)
		@param is_equal - если true, то ищутся инстансы с атрибутами, равные указанным
						если false - то с атрибутами, в которые входят указанные значения
		@return true в случае успеха и false в случае ошибки */
	bool SetFindParams(CaplInstance *query,CString &mode,BOOL is_id,CString &id,
								BOOL is_name,CString &name,BOOL is_equal);
	bool SetFindParams(CaplInstance *query,CFindDlg *dlg=0);
	
	/** Выполняет запрос, предварительно сформированный с помощью функции MakeQueryLngWithDlg.
		@param item - объект поиска
		@param out_ext - список с результатами запроса 
		@return true в случае успеха и false в случае ошибки */
	bool ExecuteQuery(CaplInstance *query,aplExtent &out_ext);

	/** Выполняет запрос, предварительно сформированный с помощью функции MakeQueryLngWithDlg.
		@param query - объект поиска
		@param out_ext - список с результатами запроса 
		@return true в случае успеха и false в случае ошибки */
	bool ExecuteQuery(CString query,aplExtent &out_ext);

	bool ExecuteFind(CaplInstance *query/*,CaplDataBuf &dbuf*/,aplExtent &out_ext);

	bool CheckRemoveLowLevelInstances(aplExtent &ckecked_ext);

	/** Возвращает результат предыдущего выполнения запроса
		@param item - объект поиска
		@param out_ext - список с результатами запроса 
		@param time - дата вполнения запроса
		@return true в случае успеха и false в случае ошибки */
	bool GetFindResult(CaplInstance *query,aplExtent &out_ext,COleDateTime &time,bool only_temporary=false);

	/** Выводит в таблице экстент, имеющийся у объекта item. Если параметр is_hide_move_button 
		равен false, показывает кнопку "Переместить в дерево". При  на эту кнопку возвращает 
		@return true при нажатии на кнопку "Переместить в дерево" и false нажатии на кнопку "Выход"*/
	//bool MakeTable(CaplInstance *query,bool is_hide_move_button,bool ignore_flag=false,aplExtent* ext_in=0);

	/** Возвращает в name описание запроса item*/
	bool GetName(CaplInstance *query,CString &name,CString &description);

	/** Проверяет уникальность имени запроса (для всех запросов кроме указанного)*/
	bool TestNameQuery(CString name,CaplInstance *query,bool report=true);

	/** Проверяет уникальность имени запроса (для всех запросов кроме указанного)*/
	bool TestNameCombinedTable(CString name,CaplInstance *ct,bool report=true);

	/** Удаляет запрос item*/
	bool DeleteQuery(CaplInstance *query);
	
	/** Поиск по составу изделия*/
	bool FindIntoContent(CaplInstance *pdf);

	/** Формирует текст условия для атриюута - с учетом разбиения на подстроки символами | и & и и группировки скобками*/
	bool MakeAttrConditionWithGroup(CString &str_par,CString &attr,CString &name4user,bool is_brackets,CString &attr_condition, const TCHAR* str_rel = _T("LIKE"));
	
	/** Сохраняет запрос*/
	bool SaveQuery(CaplInstance *query);

	bool UpdateTypeQuery(CaplInstance *query);
	
public:
	// Attributes
	CaplEntity *e_apl_query;
	CaplAttr *a_apl_query_name;
	CaplAttr *a_apl_query_description;
	CaplAttr *a_apl_query_is_text_query;	
	CaplAttr *a_apl_query_text_query;	
	CaplAttr *a_apl_query_dialog_data;	
	CaplAttr *a_apl_query_content;	
	CaplAttr *a_apl_query_execution_date;	
	CaplAttr *a_apl_query_execution_size;	
	CaplAttr *a_apl_query_make_table;
	CaplAttr *a_apl_query_temp_data_index;
	CaplAttr *a_apl_query_mode;
	CaplAttr *a_apl_query_combined_table;
	CaplAttr *a_apl_query_type;
	CaplAttr *a_apl_query_dot_name;
	CaplAttr *a_apl_query_folder;

	CaplEntity *e_apl_ct;
	CaplAttr *a_apl_ct_name;
	CaplAttr *a_apl_ct_description;
	CaplAttr *a_apl_ct_columns_data;
	CaplAttr *a_apl_ct_temp_data_index;
	CaplAttr *a_apl_ct_query;

	CaplMap m_ListTopLevelEntities;
	
};	
// *************************************************************************
// *************************************************************************
// *************************************************************************
/**Менеджер авторизации (оргструктура и статусы)*/
class CLASS_DECL_APL_STEP_MGR CaplAutorizationManager: public CaplStepManager
{
	// Инициализация
public:

	CaplAutorizationManager();
	~CaplAutorizationManager();

	/** Инициализирует класс (Ассоциация с классом базы данных) 
		@return true при удачном выполнении и false в случае ошибки */
	virtual bool Attach(CaplAPI *api);
	virtual void Detach();

	/** читает в кэш данные об оргструктуре, ролях и статусах*/
	bool LoadOrgStruct(aplExtent *ext=NULL);

	bool LoadDictionary(); // Читает только настройки Вызывается из LoadOrgStructж

	/** Читает статусы объекта Item*/
	// bReturnRevocated - если true вернет и отозванные тоже
	bool LoadItemApproval(CaplInstance* item, aplExtent &ext_approval,bool from_base=true, bool bReturnRevocated=false);
	bool LoadItemApproval(aplExtent &ext, aplExtent &ext_approval,bool from_base=true, bool bReturnRevocated=false);

	bool LoadApprovalInfo(aplExtent &ext_approval);


	/** Создает статус для item (выводит диалог если недостаточно параметров);
	  @param  item объект базы данных
	  @param  status присваиваемый статус
	  @param  level уровень
	  @param  person_org ссылка на сотрудника, создающего статус
	  @param  app_owner ссылка на владельца статуса
	  @param  role роль сотрудника
	  @param  date_time дата создания статуса
	  @param  system система ЭЦП (учитывается, если item является документом или версией документа)
	  @param  key путь к фалу с закрытым ключом
	  @param  password пароль доступа к файлу
	  @param  statusesToHide перечень статусов, которые не будт отображаться в комбобоксе
	  @param  bNoCheckRepeatStatus если true, то можно присваивать одинаковые статусы несколько раз*/
	CaplInstance *CreateApproval(CaplInstance *item,CaplInstance *status=0,const TCHAR *level=0,CaplInstance *person_org=0,CaplInstance *app_owner=0,const TCHAR *role=0,const TCHAR *date_time=0,
		const TCHAR* sSignMethod= 0, const TCHAR* sKeyPath= 0, const TCHAR* sPassword= 0,LPCTSTR sign_owner=NULL, LPCTSTR cert_file=NULL, aplExtent *statusesToHide=NULL,
		bool bNoCheckRepeatStatus=false,bool CheckStatusForRole=true);
	int CreateApprovalMulti(aplExtent *items,CaplInstance *status=0,const TCHAR *level=0,CaplInstance *person_org=0,CaplInstance *app_owner=0,const TCHAR *role=0,const TCHAR *date_time=0,
		const TCHAR* sSignMethod= 0, const TCHAR* sKeyPath= 0, const TCHAR* sPassword= 0,LPCTSTR sign_owner=NULL, LPCTSTR cert_file=NULL, aplExtent *statusesToHide=NULL);
	CaplInstance* CreateWfApproval(CaplInstance* task, CaplInstance* item, CaplInstance *defStatus= NULL);
	bool PostUpdateApprovalItems(aplExtent& items);

	bool AddLabel4DocRevision(CaplInstance *doc_rev, LPCTSTR sLabel); // Служебная
	bool SetNeedWork4DocRevision(CaplInstance *doc_rev, bool bSetNeedWork, bool bFromCreateApproval=false); // Служебная
	
	/** Вычисляет ЭЦП для документа или версии документа
	  @param  inst объект для которого вычисляется ЭЦП (doc | doc_rev |PDF )
	  @param  system система ЭЦП
	  @param  key путь к фалу с закрытым ключом
	  @param  password пароль доступа к файлу
	  @param  sSign значение ЭЦП (возвращается функцией)
	  @param  sHash значение хэш-фунции (возвращается функцией)
	  @param  sOpenKey открытый ключ (возвращается функцией)
	  @param  UserName Владелец ключа (возвращается функцией)
	  @param  CertFileName Имя файла сертификата (возвращается функцией)
	  @param  sInventory опись подписываемых объектов
	  @param  sShapShot опись снимок подписываемых объектов
	  @param  person родписывающий сторудник, если 0, то текущий. Усди -2 - определяется по открытому ключу. Возвращает подписавшего

	  @return true при удачном выполнении или false в случае ошибки*/	
	bool SignObject(CaplInstance* inst, const TCHAR* system,  
		CString &sSign, CString &sHash, CString &sOpenKey,CString &UserName, CString &CertFileName,
		CString &sInventory, CString &sShapShot, CaplInstance **pPerson=0);

	/** Сохраняет в строке значение актуальных реквизитов*/
	int GetDSInfo(CaplInstance *ciDoc, char *&addInfo);	

	/** Используется ли реквизит в подписях ЭЦП
		@param ciEntry реквизит
		@param sEntryName наименование реквизита
		@param ciDocType искать подпись только у конкретного типа документа*/
	bool IsEntryUsedInEDS(CaplInstance *ciEntry, CaplInstance *ciDocType = 0);
	bool IsEntryUsedInEDS(CString sEntryName, CaplInstance *ciDocType = 0);

	/** Загружает атрибуты для объектов, использующихся в функции IsEntryUsedInEDS*/ 
	bool LoadDTinfoOfApprovalItem(aplExtent &aeApproval);

	/** Показывает окно сертификата (нашего образца)*/
	bool ShowCertificateProperties(CaplInstance *ciCert);

	/** Проверяет ЭЦП в статусе для для версии документа*/
	int CheckApproval(CaplInstance* approval, bool bShowResult= true);

	/** Актуальна ли подпись по реквизитам */
	bool IsApprovalActual(CaplInstance *ciApproval);

	/** Отображает свойства статуса*/
	bool ShowApproval(CaplInstance *appr);

	//** Возвращает имя текущего сотрудника (пользователя) для записи в строку оператор*/
	CString  GetOperatorName(); 

	/** Возвращает имя сотрудника или абонента   nMaxNameLen Образать фамилию до указанного числа символов*/
	bool GetPersonName(CaplInstance* po, CString &buf,bool is_short=true,bool reverse_user=false, int nMaxNameLen=-1);
	
	/** В ext возвратятся должностей, в которых 
	 - сотрудник является владельцем - bOwner= true
	 - сотрудник является получателем - bOwner= false */
	bool GetPersonOfficials(CaplInstance* person, aplExtent& officials, bool bOwner= false);

	/// В ext возвратятся организации, в которые входит сотрудник.  Если bActualOnly==false, буду включены те, в которые входил
	bool GetPersonOrganizations(CaplInstance* person, aplExtent& organizations, bool bActualOnly = true);

	/**	Функция отображает диалоговое окно выбора подразделения
		return <b>true</b> если выбрано подразделение и нажата клавиша OK и <b>false</b> в проивном случае*/
	bool SelectOrganization(CaplInstance **inst, LPCTSTR lpszTitle = NULL, aplExtent *RootItems = NULL);
	
	/** Позволяет выбирать несколько сотрудников и (или) рабочих групп */
	bool SelectPersonsOrganizations(long lMode, aplExtent &ext, 
		bool bShowUserWG= true, bool Traverse= true,
		CString sTitle= _T(""), CString sTreeTitle= _T(""), aplExtent* rootPO= NULL, 
		bool bExpand= false);
	
	/** Позволяет выбирать сотрудника или рабочую группу*/
	CaplInstance* SelectPersonOrOrganization(long lMode, aplExtent &rootPO, 
		CString sTitle= _T(""), CString sTreeTitle= _T(""), bool bExpand= false);

	/** Позволяет выбирать пользователя или группу пользователей*/
	CaplInstance* SelectAplUserOrGroup(long lMode,  
		CString sTitle= _T(""), CString sTreeTitle= _T(""), bool bExpand= false);

	/** Показывает историю для абонента*/
	void ShowOfficialHistory(CaplInstance* official, int hist_type =0);

	/** Показывает абоненты для персона*/
	void ShowPersonOfficials(CaplInstance* person);

	/** Создает абонентский ящик*/
	CaplInstance *CreateOfficial(const TCHAR *id,const TCHAR *descr=0);

	/** Поиск абонентского ящика по id*/
	CaplInstance *FindOfficialById(const TCHAR *id,bool bLoadFromBase=false);

	/** Получить список цехов КВЗ*/
	void GetKVZShops(CStringArray &shops) const;

	/** Получить список отделв КВЗ*/
	void GetKVZDepartments(CStringArray &departments) const;

	/** Поиск организаций по персону */ 
	bool FindPersonOrganizations(CaplInstance *person,aplExtent &ext_out, bool bFromBase = false);

	/** Создание нового типа статуса */
	CaplInstance *CreateApprovalStatus(const TCHAR *name);
	
	/** Поиск типа статуса по имени*/
	CaplInstance *FindApprovalStatusBN(const TCHAR *name,bool bLoadFromBase=false, bool bCreateIfNotFound=false);

	/** Поиск роли по имени*/
	CaplInstance *FindRoleBN(const TCHAR *name,bool bLoadFromBase, bool bCreateIfNotFound=false);

	/** Поиск присвоенного персоном с указанной ролью статуса у item*/
	CaplInstance *CaplAutorizationManager::FindRoleApproval(CaplInstance *item,const TCHAR *role,CaplInstance *status);

	/** Удаление статуса*/
	bool DeleteApproval(CaplInstance *approval);

	/** Удаление всех статусов у item*/
	bool DeleteAllApproval(CaplInstance *item);

	/** Удаление всех статусов c заданными типами статуса у item*/
	bool DeleteAllApprovalByStatus(CaplInstance *item,aplExtent &ext_status);

	/**Поиск рабочей группы по обозначению*/	
	CaplInstance* FindOrganizationById(const TCHAR* id, bool bFromBase = false, bool bLoadAttrs = false);
	
	/**Поиск сотрудников по обозначению*/	
	bool FindPersonById(const TCHAR *id,aplExtent &ext_out,bool is_substring=false);
	
	/**Создание описания сотрудника */
	CaplInstance *CreatePerson(const TCHAR *id,const TCHAR *last_name=0,const TCHAR *first_name=0,CaplAggr *mid_names=0, bool bTestUnique = true);
	CaplInstance *CreatePerson(const TCHAR *id,const TCHAR *last_name,const TCHAR *first_name, const TCHAR *mid_name, bool bTestUnique = true);

	/*Возвращает список всех входящих организаций*/
	bool GetAllSubOrganization(CaplInstance *inst, aplExtent &out, aplExtent *rel = 0);
	bool GetAllSubOrganization(aplExtent &inExt, aplExtent &out, bool bRecursive);
	
	/*Возвращает список всех входящих person и official*/
	bool GetAllSubPerson(CaplInstance *inst, aplExtent &out, aplExtent &pers_org);

	/*Отображает в диалоге свойства person и official*/
	bool ShowPersonProperties(CaplInstance *inst);

	/*Отображает в диалоге свойства организации*/
	bool ShowOrganizationProperties(CaplInstance *inst);
	
	bool GetUserEnveroment(aplExtent &status, aplExtent &doc_types, aplExtent &contexts);
	
	// Возвращает список шаблонов, в которых учавствует указанный пользователь или группа пользователей
	bool GetUserPatterns(CaplInstance *user,aplExtent &patterns);

	//Создает связь между рабочими группами
	CaplInstance *CreateOrgRel(CaplInstance *relating_org,CaplInstance *related_org);

	//поиск связи между элементами орг. структуры
	CaplInstance* FindOrgRel(CaplInstance *relating_org, CaplInstance *related_org);

	//поиск куда входит
	bool WhereUsedOrg(CaplInstance *org, aplExtent &ext, aplExtent *rels = NULL, bool bFromBase = false);

	//Создает элемент оргструктуры с обязательным выводом диалога свойств.
	CaplInstance* CreateOrganization(CaplInstance* org = NULL, bool bCanEdit = false);
	CaplInstance* CreateOrganization(LPCTSTR lpszId, LPCTSTR lpszName);

	//Создать тип элемента оргструктуры
	CaplInstance* CreateOrganizationType(LPCTSTR lpName);

	//Найти тип элемента оргструктуры в БД
	CaplInstance* GetOrganizationTypeBN(LPCTSTR lpName);

	bool DeleteOrganization(CaplInstance* nInst);

	// записывает значения реквизитов, участвующих в подписи (только для apl_doc_revision)
	void CreateEntryApproval(CaplInstance *ciItem, CaplInstance *ciAppr);
	
	// Возвращает первую попавшуюся организацию, куда сейчасвходит сотрудник
	// Eсли bReturnOrg==true - возвращает организацию, иначе person_organization 
	CaplInstance*	GetActualPersOrg(CaplInstance *pers, bool bReturnOrg=false); //Если bReturnOrg==false возвращаяет PO, иначе возвращаяет ORG
	
	// Возвращает все организации, куда сейчас входит сотрудник
	// Eсли bReturnOrg==true - возвращает организации, иначе person_organization
	bool GetActualPersOrgs(CaplInstance *pers, aplExtent &ext_org, bool bReturnOrg);
	
	// Возвращает все организации, куда сейчас входит сотрудник и все вышестоящие организации
	// ext_org возвращается отсортированный
	// bWithOfficials если true, то возвращает группы, в которые сотрудник входит как абонент
	bool GetAllActualPersOrgs(CaplInstance *pers, aplExtent &ext_org, bool bWithOfficials=true);
	
	bool GetUserData(CaplInstance* item, CaplInstance** user, CaplInstance** pers, CaplInstance **po);
	bool GetPersonByUser(CaplInstance* user, CaplInstance** pers, CaplInstance **po);
	bool GetUserByPerson(CaplInstance* pers, CaplInstance** user, CaplInstance **po);
	bool GetUserByPO(CaplInstance* po, CaplInstance** user, CaplInstance **pers);


	/// Проверяет наличие роли у person. Возвращяет true, если такая роль есть.
	/// Если  person==0 ,проверяет у текущего
	/// В строке с ролью можно задавать несколько ролей разделенных символм '|'. Возвращает true, если есть хотя бы одна из указанных ролей
	bool CheckPersonRole(CaplInstance *person, LPCTSTR role);

	/// Проверяет у person хотя бы одной роли заданной опцией option. Возвращяет true, если такая роль есть.
	/// Если  опция не задана возвращает true
	/// Если  person==0 ,проверяет у текущего
	/// Если bShowMsg==true - выводит сообщение "нет роли"
	/// В строке с ролью можно задавать несколько ролей разделенных символм '|'. Возвращает true, если есть хотя бы одна из указанных ролей
	bool CheckPersonRoleByOption(CaplInstance *person, LPCTSTR option, bool bShowMsg);


	/// Определяет список видов документов по ролям сотрудника 
	/// Если  хотя бы у одной роли задано "все виды", то ext_doc_types будет пустой, а bAllDocTypes будет равен true
	/// В противном случае ext_doc_types будет заполнен видами документов, а bAllDocTypes будет равен false
	/// Если ролей нет, то ext_doc_types будет пустой и  bAllDocTypes будет равен false
	bool GetPersonDocumentTypes(CaplInstance *person, aplExtent &ext_doc_types, bool &bAllDocTypes);

	// Проверяет наличие подписи со статусом status и ролью role у inst. Если role не задан - любая роль.
	// в ext_approvals возвращаются найденные 
	bool CheckItemStatus(CaplInstance *inst, CaplInstance *status, LPCTSTR role=0, aplExtent *ext_approvals=0);


	// Проверяет вхождение сотрудника в ту-же рабочую группу, что и человек поставивший на item подпись
	// person - проверяемый сотрудник, если 0, то текущий
	// item - объект на котором стоит подпись
	// status_name - наименование статуса
	// возвращает true, если входит, или если подписей нет
	bool CheckPersonInWgApproval(CaplInstance *person, CaplInstance *item, LPCTSTR status_name, LPCTSTR role_name );

	bool CreateSnapShot4DigSign(CaplInstance *inst, CString & sData, CString& sInventoy);
	// Создает снимок по описи
	// psOldData - старый снимок 
	// psDiff - Если есть старый снимок, то сюда будет писаться протокол раздичий
	bool CreateSnapShotByInventory(CString &sInventoy, CString &sData, CString *psOldData=0, CString *psDiff=0);

	// Зачитывает все выходные в кэш (вызывается автоматически)
	bool LoadHolydaysInCash();

	// Определяет является ли день выходным. day  в формате ГГГГММДД (можно ГГГГММДДЧЧММСС)
	bool IsDayHolyday(CString &day);
	
	// Определяет является ли день выходным.
	bool IsDayHolyday(COleDateTime day);

	// Определяет количество выходных дней между датами включительно (если первое входной, то с первого по первое будет 1 день)
	bool GetHolydayCount(COleDateTime day_start,COleDateTime day_end, int &day_count);

	// Определяет рабочих дней между датами включительно (с первого по первое будет 1 день, если он не выходной)
	bool GetWorkdayCount(COleDateTime day_start,COleDateTime day_end, int &day_count);

	// Определяет день через iWorkDayCount рабочих дней после first_date (через 1 рабочий день после первого будет второе, если нет выходных)
	bool AddWorkdayToDate(COleDateTime first_date, int iWorkDayCount, COleDateTime &new_date);
	bool AddWorkdayToDate(COleDateTime first_date, double dWorkDayCount, COleDateTime &new_date);
	
	// Показывает диалог со списком всех статусов переданного инстанса
	bool ShowItemApprovals(CaplInstance* item);

	// Генерит сертификат ЭП для сотрудника
	CaplInstance *CreateDigSignCert4Person(CaplInstance *person, CaplCryptographicManager::TCertInfo &certInfo, bool bSaveKeyInBase);

	//Генерация сертификата ЭП для текущего сотрудника им самим
	bool CreateDigSignCert4CurrentPerson();

protected:
	
	CaplCryptographicManager m_Crypto;
	bool m_bHolydeysLoaded;

public:

	CaplMap m_holydays_map;

	bool m_bAllowCreateOrgInSelect; // разрешить создание рабочих групп при их выборе
	bool m_bAllowCreatePersonInSelect; // разрешить создание сотрудников при их выборе

	ESignMode SeSignModeForCryptMgr(ESignMode mode, bool bResetPassword=false); //Если bResetPassword==true - сбрасывается последний пароль

	//CCryptographicProvider *GetCryptProv();
	bool ConfidentialCertExistInBase(CString sIssure);

// Attributes
	CaplEntity *e_official, *e_official_hist;
	CaplAttr *a_official_id, *a_official_descr, *a_official_roles,*a_official_owner, *a_official_owner_hist;
	CaplAttr *a_official_act_person, *a_official_act_person_hist, *a_official_possible_persons;
	CaplAttr *a_off_hist_person, *a_off_hist_date, *a_off_hist_descr, *a_off_hist_user;
	
	CaplEntity *e_apl_appr,*e_apl_appr_pers_org;
	CaplAttr *a_appr_status,*a_appr_level,*a_appr_item,*a_appr_role,*a_appr_active;
	CaplAttr *a_appr_state,*a_appr_pers_org;
	CaplAttr *a_appr_notes;
	CaplAttr *a_appr_attachment;
	CaplAttr *a_appr_revocation_date_time;
	CaplAttr *a_appr_dg_sign_hash,*a_appr_dg_sign_met,*a_appr_dg_sign,*a_appr_dg_sign_open_key;
	CaplAttr *a_appr_dg_sign_author,*a_appr_dg_sign_cert;
	CaplAttr *a_appr_dg_sign_inventory,*a_appr_dg_sign_snapshot;
	CaplAttr *a_appr_appr_date_time_s,*a_appr_appr_owner;
	CaplAttr *a_appr_po_entries, *a_appr_po_item_note;
	CaplAttr *a_appr_entries_used;
	CaplAttr *a_appr_format;				///< Формат
	CaplAttr *a_appr_total_sheets_count;	///< Листов
	CaplAttr *a_appr_total_sheets_count_a4;	 ///< Листов приведенные к формату А4
	
	CaplEntity *e_appr_rel;
	CaplAttr *a_appr_rel_name,*a_appr_rel_descr,*a_appr_rel_relating,*a_appr_rel_related;
	
	CaplEntity	*e_appr_status;
	CaplAttr	*a_appr_status_name;
	CaplAttr	*a_appr_status_icon;
	CaplAttr	*a_appr_status_set_state;
	CaplAttr	*a_appr_status_str4label;
	CaplAttr	*a_appr_status_set_needs_work; // Установить флаг "Требует доработки"
	CaplAttr	*a_appr_status_unset_needs_work; // Снять флаг "Требует доработки" (Добавлен для ЦКБА через 15 лет после предыдущего)
	CaplAttr	*a_appr_status_need_description; // Требовать заполнение обоснования

	CaplEntity*  e_appr_cont;
	CaplAttr*    a_appr_cont_abbreviation;
	CaplAttr*    a_appr_cont_description;
	CaplAttr*    a_appr_cont_approval;
	CaplAttr*	 a_appr_cont_person;
	CaplAttr*	 a_appr_cont_item;
	CaplAttr*	 a_appr_cont_status_code;
	CaplAttr*	 a_appr_cont_date;
		
	CaplEntity	*e_po_role;
	CaplAttr	*a_po_role_name;
	CaplAttr	*a_po_role_system;

	CaplAttr *a_po_role_contexts;
	CaplAttr *a_po_role_document_types;
	CaplAttr *a_po_role_status;
	CaplAttr *a_po_role_specified_contexts_set;
	CaplAttr *a_po_role_specified_document_types_set;
	CaplAttr *a_po_role_specified_status_set;
	CaplAttr *a_po_role_system_buf;
	CaplAttr *a_po_role_ro_buf;
	CaplAttr *a_pers_forum_last_visit_date;
	CaplAttr *a_po_role_interface_elements;
	CaplAttr* a_po_role_data_class;
	CaplAttr* a_po_role_auto_save_user_column_settings;

	CaplEntity *e_person;
	CaplAttr *a_pers_id;
	CaplAttr *a_pers_last_name;
	CaplAttr *a_pers_first_name;
	CaplAttr *a_pers_code;
	CaplAttr *a_pers_roles;
	CaplAttr *a_pers_middle_names;
	CaplAttr *a_pers_prefix_titles;
	CaplAttr *a_pers_suffix_titles;
	CaplAttr *a_pers_descr;
	CaplAttr *a_pers_phone;
	CaplAttr *a_pers_e_mail;
	CaplAttr *a_pers_actual_address;
	CaplAttr *a_pers_send_copy_message_to_email;
	CaplAttr *a_pers_mail_template; 
	CaplAttr *a_pers_options; 
	
	CaplEntity *e_pers_org;		/**<person_and_organization */
	CaplAttr *a_po_the_pers;	/**<person_and_organization -> the_person*/
	CaplAttr *a_po_the_org;		/**<person_and_organization -> the_organization*/
	CaplAttr *a_po_start_date;	/**<person_and_organization -> start_date*/
	CaplAttr *a_po_end_date;	/**<person_and_organization -> end_date*/
	CaplAttr *a_po_person_pos;	/**<person_and_organization -> person_position*/
	CaplAttr *a_po_code;		/**<person_and_organization -> code */

	CaplEntity *e_org;				/**<organization */ 
	CaplAttr *a_org_id;				/**<organization -> id */
	CaplAttr *a_org_name;			/**<organization -> name */
	CaplAttr *a_org_name_eng;		/**<organization -> name_eng */
	CaplAttr *a_org_descr;			/**<organization -> description */
	CaplAttr *a_org_type;			/**<organization -> type */
	CaplAttr *a_org_warehouse;		/**<organization -> recalc_goods_count */
	CaplAttr *a_org_tranz_counter;	/**<organization -> tranzaction_counter */
	CaplAttr *a_org_successor;		/**<organization -> successor */
	CaplAttr *a_org_guid;			/**<organization -> guid */

	CaplAttr *a_org_inn;		/**<organization -> org_inn */
	CaplAttr *a_org_kpp;		/**<organization -> org_kpp */
	CaplAttr *a_org_ogrn;		/**<organization -> org_ogrn */
	CaplAttr *a_org_okpo;		/**<organization -> org_okpo */
	CaplAttr *a_org_cage_code;	/**<organization -> cage_code */
	CaplAttr *a_org_legal_address;		/**<organization -> org_legal_address */
	CaplAttr *a_org_actual_address;		/**<organization -> org_actual_address */
	CaplAttr *a_org_postal_address;		/**<organization -> org_postal_address */
	CaplAttr *a_org_start_date;		/**<organization -> org_start_date */
	CaplAttr *a_org_end_date;		/**<organization ->org_end_date */
	CaplAttr *a_org_phone;		/**<organization -> org_phone */
	CaplAttr *a_org_fax;		/**<organization -> org_fax */
	CaplAttr *a_org_e_mail;		/**<organization -> org_e_mail */
	CaplAttr *a_org_web;		/**<organization -> org_web */
	CaplAttr *a_org_bik;				/**<organization -> bik */
	CaplAttr *a_org_default_account;	/**<organization -> default_account */
	CaplAttr *a_org_chief;				/**<organization -> chief */
	CaplAttr *a_org_country;
	CaplAttr *a_org_federal_subject;	/**<organization -> federal_subject */
	CaplAttr *a_org_classes;
	CaplAttr *a_org_date_actual;		/**<organization -> date_actual */
	CaplAttr *a_org_city;				/**<organization -> city */
	CaplAttr *a_org_coordinates;		/**<organization -> coordinates */

	CaplEntity *e_org_account;
	CaplAttr *a_org_account_org;	/**<organization_account -> organization */
	CaplAttr *a_org_account_bank;	/**<organization_account ->  bank*/
	CaplAttr *a_org_account_type;	/**<organization_account -> type */
	CaplAttr *a_org_account_number;	/**<organization_account ->  number*/
	CaplAttr *a_org_account_description;	/**<organization_account -> description */
	CaplAttr *a_org_account_cor_account;	/**<organization_account -> correspondent_account */


	CaplEntity *e_org_rel;
	CaplAttr *a_org_rel_name;
	CaplAttr *a_org_rel_descr;
	CaplAttr *a_org_rel_relating;
	CaplAttr *a_org_rel_related;
	
	
	CaplEntity	*e_apl_org_type;
	CaplAttr	*a_apl_org_type_name;

	CaplEntity *e_calendar_holyday;
	CaplAttr *a_calendar_holyday_day;

	CaplEntity *e_apl_user;
	CaplEntity *e_apl_access_agent;
	CaplEntity *e_apl_workgroup;
	CaplAttr *a_apl_user_for_web_server;
	CaplAttr *a_apl_user_name,*a_apl_user_po,*a_apl_user_descript,*a_apl_user_groups;
	CaplAttr *a_apl_user_is_ro,*a_apl_user_is_ar,*a_apl_user_is_disabled, *a_apl_user_access_pattern;

	CaplEntity *e_apl_acc_pat;
	CaplAttr *a_apl_acc_pat_name,*a_apl_acc_pat_pattern;

	// настройка АРМ'ов
	CaplEntity	*e_arm;
	CaplAttr	*a_arm_name;
	CaplAttr	*a_arm_roles;

	CaplEntity	*e_arm_role;
	CaplAttr	*a_arm_unwork_role;
	CaplAttr	*a_arm_unwork_status;
	CaplAttr	*a_arm_role_name;
	CaplAttr	*a_arm_role_rules;

	CaplEntity	*e_role_rule;
	CaplAttr	*a_role_rule_set;
	CaplAttr	*a_role_rule_name;


	CaplEntity*             e_apl_digital_sign_open_key;
	CaplAttr*				a_apl_digital_sign_open_key_person;
	CaplAttr*				a_apl_digital_sign_open_key_open_key_metod;
	CaplAttr*				a_apl_digital_sign_open_key_open_key_cert_serial_num;
	CaplAttr*				a_apl_digital_sign_open_key_open_key_cert_issuer;
	CaplAttr*				a_apl_digital_sign_open_key_open_key_cert_subject;
	CaplAttr*				a_apl_digital_sign_open_key_open_key_cert_blob;
	CaplAttr*				a_apl_digital_sign_open_key_open_key;
	CaplAttr*				a_apl_digital_sign_open_not_before;
	CaplAttr*				a_apl_digital_sign_open_not_after;
	CaplAttr*				a_apl_digital_sign_open_revocation_date;
	CaplAttr*				a_apl_digital_sign_open_key_container;
	CaplAttr*				a_apl_digital_sign_open_key_author;
	CaplAttr*				a_apl_digital_sign_cert_type;
	CaplAttr*				a_apl_digital_sign_open_key_confidential;

	CaplEntity	*e_role_colset;
	CaplAttr	*a_role_colset_role;
	CaplAttr	*a_role_colset_view_name;
	CaplAttr	*a_role_colset_column_set;

};

// *************************************************************************
// *************************************************************************
// *************************************************************************
#define MESSAGE_DLG_CANCEL -1
#define MESSAGE_DLG_REPLY 1
#define MESSAGE_DLG_FORWARD 3
#define MESSAGE_DLG_DELETE 4
#define MESSAGE_DLG_SEND 5
#define MESSAGE_DLG_SAVE 6
#define MESSAGE_DLG_OPEN_NOMODAL 7
#define MESSAGE_DLG_REPLY_ALL 8

/** Менеджер сообщений*/
class CLASS_DECL_APL_STEP_MGR CaplMessageManager: public CaplStepManager
{
	// Инициализация 
public:
	const static TCHAR m_alert_state_active[];
	const static TCHAR m_alert_state_completed[];
	// Attributes
	CaplEntity *e_message;
	CaplAttr *a_message_sender;
	CaplAttr *a_message_recipient;
	CaplAttr *a_message_recipient_in_copy;
	CaplAttr *a_message_subject;
	CaplAttr *a_message_content_lenght; // длинна сообщения включая 0
	CaplAttr *a_message_content_source; // blob c сообщением
	CaplAttr *a_message_content;        // текст сообщения (для коротких сообщений, которых нет в BLOB)
	CaplAttr *a_message_content_format;	// html или rtf
	CaplAttr *a_message_items;
	CaplAttr *a_message_priority;
	CaplAttr *a_message_ask_notify;
	CaplAttr *a_message_status;
	CaplAttr *a_message_date_send;
	CaplAttr *a_message_date_received;
	CaplAttr *a_message_prev_message;
	CaplAttr *a_message_forward;
	CaplAttr *a_message_sender_kill;
	CaplAttr *a_message_recipient_kill;

	
	CaplAttr *a_message_copy;
	CaplAttr *a_message_copies;
	CaplAttr *a_message_sender_folder;
	CaplAttr *a_message_recipient_folder;
	CaplAttr *a_message_complete_date;
	CaplAttr *a_message_required_complete_date;
	CaplAttr *a_message_message_type;
	
	CaplAttr *a_message_rec_offisial;
	CaplAttr *a_message_rec_nick;
	CaplAttr *a_message_send_nick;

	CaplAttr *a_message_code;
	CaplAttr *a_message_last_reply;
	CaplAttr *a_message_note;

	CaplAttr *a_message_kurator;
	CaplAttr *a_message_complete_date2;
	CaplAttr *a_message_required_complete_date2;
	
	CaplAttr *a_message_counter;
	CaplAttr *a_message_parent;

	CaplAttr *a_message_sender_color;
	CaplAttr *a_message_recipient_color;


	CaplEntity *e_subscr;
	CaplAttr *a_subscr_item;
	CaplAttr *a_subscr_subscriber;
	
	CaplEntity* e_alert;
	CaplAttr* a_alert_person;
	CaplAttr* a_alert_item;
	CaplAttr* a_alert_code;
	CaplAttr* a_alert_date;
	CaplAttr* a_alert_next_date;
	CaplAttr* a_alert_text;
	CaplAttr* a_alert_span;
	CaplAttr* a_alert_module;
	CaplAttr* a_alert_function;
	CaplAttr* a_alert_author;
	CaplAttr* a_alert_state;
	CaplAttr* a_alert_delete_completed;
	CaplAttr* a_alert_notify_author;

public:
	// Методы
	/** Инициализирует класс (Ассоциация с классом базы данных) 
		@return true при удачном выполнении и false в случае ошибки. */
	virtual bool Attach(CaplAPI *api);
	virtual void Detach();
	
	/** Создает сообщение 
		@param recipient  получатель сообщения.
		@param subject  тема сообщения.
		@param content  текст сообщения.
		@param ext  прикрепленные к сообщению элементы.
		@param priority  важность сообщения Может быть равно: 0, 1, 2.
		@param status  статус сообщения. Может быть равно: "draft", "sendet", "readed", "replyed".
		@param ask_notify  уведомлять ли отправителя при изменении статуса сообщения true<\b> если уведомлять false<\b> в противном случае.
		@param silent  выводить ли диалог запроса true<\b> если не выводить false<\b> в противном случае .
		@param sArrayFiles  Масиив полных путей файлов, которые надо прикрепить к сообщению .
		@return созданное сообщение и NULL в случае ошибки.  */	
	CaplInstance* CreateMessage(CaplInstance* sender, CaplInstance* recipient, 
		const TCHAR* subject, const TCHAR* content, aplExtent& items, 
		int priority= 1, const TCHAR* status= _T("sendet"),
		bool ask_notify= false, bool silent= false,
		CaplInstance* copy= NULL, aplExtent* possibleRecipient= NULL,
		CStringArray *sArrayFiles=NULL);

	// Запускает создание сообщения во внешнем exe
	bool CreateMessageExternal(CStringArray *sArrayFiles=NULL); 

	
	/** Пересылает сообщение другому пользователю 
		@param message  сообщение, которое переправляется.
		@return переправленное сообщение и NULL в случае ошибки.*/
	CaplInstance* Forward(CaplInstance *message);


	// Запускает пересылку сообщения во внешнем exe
	bool ForwardExternal(CaplInstance *message);

	/** Отвечает на сообщение 
		@param message  сообщение, на которое создается ответ.
		@param bForAll если true, ответить всем
		@return новое сообщение и NULL в случае ошибки.*/
	CaplInstance* Reply(CaplInstance *message, bool bForAll=false);

	// Запускает Ответ на сообщение во внешнем exe
	bool ReplyExternal(CaplInstance *message);


	/** Проверяет является ли пользователь отправителем или получателем (
		@param message  сообщение.
		@return true<\b> если является и false<\b> в ином случае*/	
	bool IsUserSenderOrRecipient(CaplInstance *message);
	
	/** Выводит диалог со свойствами сообщения 
		@param message  сообщение.
		@return 0<\b> - при выходе из диалога, 1<\b> - при удалении, 2<\b> - при пересылке или ответе, 3<\b> - при отправке сообщения из черновиков.*/
	int ShowMessageProperty(CaplInstance *message, bool bNoActionMode=false);

	/** Выводит открывает сообщение в немодальном режиме
		@param message  сообщение.
		@return */
	bool OpenMessageNoModal(CaplInstance *message);
	
	/** Выводит диалог с текущим состоянием сообщений рассылки 
		@param message  сообщение.
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки.*/
	bool ShowDispMessageState(CaplInstance *message);
	/** Читает из базы информацию о сообщении 
		@param message  сообщение, информация о котором читается из базы.
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки.*/
	bool LoadMessageInfo(CaplInstance* message);
	bool LoadMessageInfo(aplExtent &messages);
	/** Возвращает все сообщения пользователя 
		@param out_extent  сообщения пользователя.
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки.*/
	bool GetAllMessages(aplExtent &out_extent);
	
	bool GetPersonDraftedMessages(aplExtent &out_extent, CaplInstance* person= NULL, bool bWithFolder= false);
	bool GetPersonSendedMessages(aplExtent &out_extent, CaplInstance* person= NULL, bool bWithDeleted= false, bool bWithFolder= false);
	bool GetPersonIncomingMessages(aplExtent &out_extent, CaplInstance* person= NULL, bool bWithDeleted= false, bool bWithLosted= false, bool bWithFolder= false);
	int SendDraftMessage(CaplInstance *message, bool bShowDlg= true);

	/** Возвращает все сообщения пользователя, которые были отправлены ему, но получены другими пользователями 
		@param out_extent  пропущенные сообщения пользователя.
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки.*/		
	bool GetAllLostMessages(aplExtent &out_extent, CString sStartDate= _T(""), CString sEndDate= _T(""));
	
	/** Удаляет сообщение 
		@param message  сообщение, которое удаляется.
		@param end_operation  результат, устанавливается в true, если надо прекратить удаление сообщений
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool DeleteMessage(CaplInstance *message, bool *end_operation=0);
	
	
	/** Рассылает уведомление группе сотрудников 
		@param sender отправитель сообщения. Если sender==NULL, уведомление считается системным.
		@param recipientes  получатели сообщения.
		@param subject  тема сообщения.
		@param content  текст сообщения.
		@param items  прикрепленные к уведомлению элементы.
		@return созданное сообщение или NULL в случае ошибки.*/	
	CaplInstance* SendNotifyMessage(CaplInstance* sender, aplExtent &recipientes, const TCHAR* subject, 
		const TCHAR* content, aplExtent &items, bool bSubscribe= false);

	/** Рассылает уведомление группе сотрудников 
		@param sender отправитель сообщения. Если sender==NULL, уведомление считается системным.
		@param possible_recipients возможные получатели
  	    @param recipients выбранные получатели (должны быть из возможных)
		@param subject  тема сообщения.
		@param content  текст сообщения.
		@param items  прикрепленные к уведомлению элементы.
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки.*/	
	bool SendGroupMessage(CaplInstance* sender, aplExtent &possible_recipients, aplExtent &recipients, const TCHAR *subject,const TCHAR *content, aplExtent &items);

	/** Создает подписку сотрудника на объект 
		@param item объект подписки.
		@param person сотрудник, который подписывается на объект. Если person==NULL, на объект подписывается текущий сотрудник.
		@param bSave сохранение в базе данных. Если bSave==true, подписка сохраняется в базе данных.
		@return созданный объект подписки или NULL в случае ошибки.*/
	CaplInstance* CreateSubscribe(CaplInstance* item, CaplInstance* person= NULL, bool bSave= true);

	/** Создает подписку сотрудника на объект 
		@param item объект подписки.
		@param persons сотрудник, который подписывается на объект. Если person==NULL, на объект подписывается текущий сотрудник.
		@param bSave сохранение в базе данных. Если bSave==true, подписка сохраняется в базе данных.
		@return созданный объект подписки или NULL в случае ошибки.*/
	CaplInstance* CreateSubscribe(CaplInstance* item, aplExtent &persons, bool bSave= true);
	
	/** Выводит диалог для редактирования подписки на объект базы данных 
		@param item объект базы данных.
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки.*/		
	bool EditItemSubscribeList(CaplInstance* item);

	/** Удаляет подписку сотрудника на объект 
		@param sbscr подписка сотрудника на объект.
		@param bSave сохранение в базе данных. Если bSave==true, изменение сохраняется в базе данных.
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки.*/		
	bool DeleteSubscribe(CaplInstance* sbscr, bool bSave= true);

	/** Возвращает список объектов, на которые подписался сотрудник
		@param person сотрудник, который подписывается на объект. Если person==NULL, берется текущий сотрудник.
		@param ext все объекты, на которые подписан сотрудник.
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки.*/		
	bool GetPersonSubscribeList(CaplInstance* person, aplExtent &ext);

	/** Возвращает список сотрудников, которые подписаны на объект
		@param item объект подписки.
		@param ext сотрудники, на которые подписаны на объект.
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки.*/
	bool GetItemsSubscribers(CaplInstance* item, aplExtent &ext);
	
	/** Чтение тела собщения
		@param message сообщение
		@param content тело сообщения
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки.*/
	bool GetMessageContent(CaplInstance *message,CString &content);
		/** Запись тела собщения
		@param message сообщение
		@param content тело сообщения
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки.*/
	bool SetMessageContent(CaplInstance *message,CString &content);

	//Напоминания 
	CaplInstance* CreateAlert(CaplInstance* person, CaplInstance* item, const TCHAR* text, const TCHAR* code,
		COleDateTime alert_date, COleDateTime next_date, COleDateTimeSpan alert_span,
		CString sModule= _T(""), CString sFunction= _T(""),
		CaplInstance* author=0,bool delete_completed=false,bool notify_author=false);
	bool FindAlerts(aplExtent &alerts, CaplInstance* person, CaplInstance* item, const TCHAR* code= NULL);
	// Зачитывает в ext_alerts все напоминания для person
	// bAsPerson - если получатель, bAsAuthor - если авток
	bool LoadPersonAlerts(CaplInstance* person, bool bAsAuthor, bool bAsPerson, aplExtent &ext_alerts);
	bool ShowAlert(CaplInstance* alert);
	bool ShowAlert(aplExtent &alert);
	bool DeleteAlert(CaplInstance* alert);
	bool ShowAlertProperties(CaplInstance *alert);
	/**Пометить задание (напоминание) как выполненное
		@param alert напоминание
		@param state новое состояние (возможные значения: m_alert_state_active,m_alert_state_completed); 
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки.*/
	bool SetAlertState(CaplInstance* alert,const TCHAR *state);
	CaplInstance *CaplMessageManager::CreateAlert(CaplInstance *recipient=0);
	/** Читает из базы информацию о напоминаниях 
		@param alert напоминание, информация о котором читается из базы.
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки.*/
	bool LoadAlertInfo(CaplInstance* alert);
	bool LoadAlertsInfo(aplExtent &alerts);
	bool ShowPersonAlerts(CaplInstance *person);
	bool AddItemToAlert(CaplInstance *alert,CaplInstance *item);
	bool DeleteItemFromAlert(CaplInstance *alert);

	/** находит и возвращает ссылку на адресную книгу текущего пользователя. Если адресная книга не создана и параметр create равен true - то создает ее
		@param create создавать ли адресную книгу, если она не задана для текущего пользователя
		@return объект адресной книги если он есть или его надо создать и 0 - если его нет*/
	CaplInstance* GetAddressBook(bool create=false);

	/** Добавляет в адресную книгу сотрудника(ов) или абонента(ов)
		@param item объект сотрудника или абонента
		@param items список сотрудников и/или абонентов
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки.*/
	bool Add2AddressBook(CaplInstance *item);
	bool Add2AddressBook(aplExtent &items);

	/** Возвращает всех получателей сообщения, самостоятельно определяя - получталь сотрудник
	или абонент, или сообщение отправлено нескольким адресатам
		@param item объект сообщения
		@param recipients экстент, в который заносятся все получатели
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки.*/
	bool GetMessageRecipients(CaplInstance *item,aplExtent &recipients);

	/** Перемещает указанные сообщения в папку/из папки. 
		@param messages экстент с перемещаемыми сообщениями
		@param folder папка, в которую надо переместить сообщения. Если равна нулю, то выводится диалог выбора личной папки
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки.*/
	bool MoveMessages2Folder(aplExtent &messages, CaplInstance *folder=0);
	bool RemoveMessagesFromFolder(aplExtent &messages);

	/** Сохраняет указанное сообщение в формат eml и записывает его в буфер или в файл.
		Если к сообщению присоединены какие-либо объекты, к письму прикладывается текстовый файл "Вложенные элементы.txt" в котором 
		перечисляются типы и названия присоединенных объектов (названия получаются функцией GetItemName).
		Если к сообщению присоединены документы, размер которых не превышает 10 мегабайт - прикладывает их к письму с пометкой в файле "Вложенные элементы.txt"
		Если задан максимальный размер почтового вложения _max_size_mail, то к письму прикладываются только те вложения, с которыми 
		письмо уложится в заданный размер.
		Выгружаются только объекты/документы непосредственно приложенные к сообщению; документы ассоциированные с приложенными не обрабатываются .
		Для получения списка получателей письма используется функция GetMessageRecipients
		@param message сообщение
		@body_eml буфер с телом сообщения
		@eml_file полное имя файла в которое будет сохранено сообщение
		@_max_size_mail максимальный размер почтового сообщения вместе с вложениями
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки.*/
	bool SaveMessageToEml(CaplInstance *message, CaplDataBuf &body_eml, int _max_size_mail = -1);
	bool SaveMessageToEml(CaplInstance *message, LPCTSTR eml_file, int _max_size_mail = -1);

	/** Отправляет указанное сообщение на почтовый сервер, указанный в группе опций Email:
	"Email\\Server"
	"Email\\Port"
	"Email\\Login"
	"Email\\Password"
	"Email\\IsProtocoling"
		Если сервер в процессе обмена указывает максимальный размер письма - в письмо вкладываются только те вложения, которые укладываются в заданный размер.
		Авторизация на почтовом сервер только простая; логин и пароль берутся из группы опций Email. 
		Если опция "Email\IsProtocoling" установлена в 1, то в лог приложения (такой как PSM.exe.log) выводится подробная информация по обмену с сервером.
		Если для отправителя сообщения указан Email, то письмо уйдет от имени этого email. Если не задано - письмо уйдет от имени логина из опции "Email\Login" 
		@param message сообщение
		@param err_mess если задано, то при ошибке отправки в нее будет помещено описание ошибки
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки.*/
	bool SendMessageToEmlServer(CaplInstance *message, CString *err_mess = 0);


	// Сохраянет html содержание во временный файл с необходимыми преобразованиями.
	// В sResultTempFile возвращает имя созданного временного фафла
	bool static SaveHtmlContentToTempFile(const CString &sContent, CString &sResultTempFile);


protected:
	//Служебная
	bool RunExternalCmd(LPCTSTR cmd);

};

// *************************************************************************
// *************************************************************************
// *************************************************************************
/** Структурка для передачи параметров в функции импорта-экспорта*/

class CLASS_DECL_APL_STEP_MGR CaplExternalSender
{
	virtual void SetText(const TCHAR *txt){}
	virtual void SetRange(long range){}
	virtual void SetPos(long pos){}
	virtual void SetRange(long pos,long max_pos){}
};

struct CLASS_DECL_APL_STEP_MGR SParamExchangeManager
{
	SParamExchangeManager();
	BOOL m_ExportProductInstance;
	BOOL m_ExportSubCategory;
	BOOL m_ExportClassifiers;
	BOOL m_ExportSubProduct;
	BOOL m_ExportProductMaterial;
	BOOL m_ExportProductCharacteristics;
	BOOL m_ExportRequirments;
	BOOL m_ExportAssDocuments;
	BOOL m_ExportApproval;
	BOOL m_ExportPrj;
	BOOL m_ExportPrjVer;
	BOOL m_ExportFolders;
	BOOL m_ExportBP;
	BOOL m_ExportBPRes;
	BOOL m_ExportNotes;
	BOOL m_bFormateETDPacket;
	BOOL m_bDeleteTempraryFiles;
	BOOL m_bIgnoreAddDict;
	CaplExternalSender* m_ext_sender;
};
/** Менеджер обмена данными */
class CSelectName;
class CLASS_DECL_APL_STEP_MGR CaplExchangeManager: public CaplStepManager  
{
	friend CSelectName;
	// Инициализация
public:
	CaplExchangeManager();

	/** Инициализирует класс (Ассоциация с классом базы данных) 
		@return true при удачном выполнении и false в случае ошибки */
	virtual bool Attach(CaplAPI *api);
	virtual void Detach();
	
	aplExtent m_array;
	aplExtent m_exported_prd;
	aplExtent m_exported_pdf;
	aplExtent m_exported_doc;
	aplExtent m_exported_bp;
	aplExtent m_exported_bp_res;
	aplExtent m_exported_obj_inst;

	aplExtent m_exported_items_4_approval;

	CaplTAggr <CaplValue*,CaplValue*, APLAGGR_DEFAULT> m_changed_values;
	CStringArray m_changed_values_new;
	CStringArray m_changed_values_old;

	CaplAPI	*m_fileApi;
	CaplNetStepData *m_FileData;

	// Настройки экспорта
	static BOOL m_ExportProductInstance;
	static BOOL m_ExportSubCategory;
	static BOOL m_ExportClassifiers;
	static BOOL m_ExportSubProduct;
	static BOOL m_ExportProductMaterial;
	static BOOL m_ExportProductCharacteristics;
	static BOOL m_ExportRequirments;
	static BOOL m_ExportAssDocuments;
	static BOOL m_ExportApproval;
	static BOOL m_ExportPrj;
	static BOOL m_ExportPrjVer;
	static BOOL m_ExportFolders;
	static BOOL m_ExportBP;
	static BOOL m_ExportBPRes;
	static BOOL m_ExportNotes;
	static BOOL m_IgnoreAddDict;

	static BOOL m_ExportDocWithOriginalNames;
	static BOOL m_ExportDocReqvToExtFile;

	CString m_OutPath;
	CString m_OutFile;
	CString m_LastErrDescr;

	// Настройки Импорта
	static BOOL m_ImportCategory;
	static BOOL m_ImportClassifiers;
	static BOOL m_ImportProductStruct;
	static BOOL m_ImportProductMaterial;
	static BOOL m_ImportProductCharacteristics;
	static BOOL m_ImportAssDocuments;
	static BOOL m_ImportApproval;
	static BOOL m_ImportProductInst;
	static BOOL m_ImportFolders;
	static BOOL m_ImportProject;
	static BOOL m_ImportBP;
	static BOOL m_ImportBPRes;
	BOOL	m_ImportRequirement;
	CString m_InPath;
	CString m_InFile;


public:	
	/** Сохраняет документ (или входящие в папку документы) в пакет WinETD*/
	bool SaveDocsToWinETDpackage(CaplInstance *ciItem, bool bShowMsg = true);
	bool FormateWinETDPacket(LPCTSTR lpszFileName, CaplInstance* inst, bool bDeleteTempraryFiles,CString *err_mess=0);
//	/** Экспорт словарей
//		@param data - переменная для экспорта словарей
//		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
//	bool ExportDictionary(CaplNetStepData * data);
	/** Экспорт словарей
		@param ашду - имя файла для экспорта словарей
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportDictionary(const TCHAR * filename=0);
	/** Создает и копирует инстэнсы 
		@param ext_copy - массив инстэнсов для копирования
		@param map		- карта соответствия инстэнсов загружаемого файла и сети
		@param data		- переменная, принимающая инстансы
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool CopyData(aplExtent &ext_copy, CaplMap &map, CaplStepData * data);

	/** Добавляет к объекту пакета WinETD реквизиты
		@param packet - пакет WinETD
		@param pFileDS - объект пакета WinETD
		@param	ciItem - документ или его версия
	*/
	bool AddEntriesAndApprovalToDataSet(CaplStepData &data, CaplPacket &packet, CFileDataSet *pFileDS, CaplInstance *ciItem, CString &sAddInfoMsg, bool bInstFromFile = true, CString sDir = _T(""));		
	
	/** Импортирует данные из файла 
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ImportDictionary(CaplMap &map, aplExtent &ext_copy);
	
	/** Загружает данные из файла 
		@param filename - имя файла
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ImportDataFromFile(const TCHAR *filename, CaplInstance *packet = NULL);

	/** Экспортирует данные в файл 
		@param inst - базовый инстэнс
		@param filename - имя файла
		@param bRecursive - true - если функция вызывается рекурсивно (ничего не спрашивает, ничего не пишет)
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportInstance(CaplInstance * inst, const TCHAR *filename=0,
						bool bRecursive=false,SParamExchangeManager* params=0,CString *err_mess=0);
	/** Экспортирует данные в файл 
		@param ext - экстент базовых инстэнсов
		@param filename - имя файла
		@param bRecursive - true - если функция вызывается рекурсивно (ничего не спрашивает, ничего не пишет)
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportExtent(aplExtent &ext, const TCHAR *filename=0,
		bool bRecursive=false,SParamExchangeManager* params=0,CString *err_mess=0);
	
	/** Экспортирует значения характеристик  в файл 
		@param inst - сохраняемый инстэнс
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportCharacteristic(CaplInstance * inInst);

	/** Экспортирует значения характеристик  в файл 
		@param ext - объекты для которых берутся характеристики
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportCharacteristic(aplExtent &ext);
	 
	/** Экспортирует папку и ее содержимое  в файл 
		@param inst - сохраняемый инстэнс
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportFolder(CaplInstance * inInst);

	/** Экспортирует проект и его содержимое  в файл 
		@param inst - сохраняемый инстэнс
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportProject(CaplInstance * inInst);

	/** Экспортирует статусы объекта 
		@param inst - сохраняемый инстэнс
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportItemApproval(CaplInstance * item);

	/** Экспортирует статусы объектов 
		@param ext - объекты
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportItemsApproval(aplExtent &ext);

	/** Экспортирует документы в файл 
		@param inst - сохраняемый инстэнс
		@param path - путь для сохранямого файла
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportDocument(CaplInstance *inInst, const TCHAR* path=0);
	
	/** Экспортирует категории в файл 
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportCategory(CaplInstance *category);

	/** Экспортирует сроавочники и элементы структуры в файл 
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportClassifier(CaplInstance *classifier);
	
	/** Экспортирует изделие в файл 
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportProduct(CaplInstance *inInst);
	
	/** Экспортирует бизнес-процесс в файл 
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportBP(CaplInstance *inInst);
	
	/**  Экспортирует экземпляр изделия
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportProductInst(CaplInstance *inInst);
	
	/**  Экспортирует примечание
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportNotes(CaplInstance *inInst);

	/**  Экспортирует орг структуру
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportOrg(CaplInstance *inInst);

	/**  Экспортирует роли
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportRoles(CaplInstance *inInst);

	/**  Экспортирует настройки
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportOptions(CaplInstance *inInst);
	
	bool ExportLogbookAccess(CaplInstance *inInst);
	bool ExportPrdInstRelations(CaplInstance *inInst);
	
	/**  Экспортирует сообщения
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportMessages(CaplInstance *inInst);

	/**  Экспортирует характеристики
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportCharacteristicType(CaplInstance *inInst);
	
	/**  Экспортирует типы документов
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportDocumentType(CaplInstance *inInst);

	/**  Экспортирует изменение
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportChange(CaplInstance* inInst);

	/**  Экспортирует требование
	@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportRequirement(CaplInstance *inInst);

	/**  Экспортирует конфигурационный опцион
	@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportConfigartionOptions(CaplInstance* inInst);

	/**  Экспортирует конфигурационный базис
	@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportAppearance(CaplInstance* inInst);

	/**  Экспортирует связь конф.базис<->правило
	@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportAppLimitRel(CaplInstance* inInst);

	/**  Экспортирует правило
	@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportAppLimit(CaplInstance* inInst);

	/**  Экспортирует связь конф.базис<->опцион
	@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportAppOptionRel(CaplInstance* inInst);

	/**  Экспортирует комплектацию
	@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportComplectation(CaplInstance* inInst);

	/**  Экспортирует значение опциона
	@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportOptionValue(CaplInstance* inInst);

	/**  Экспортирует ассоциацию уровня и опциона
	@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportClassifierAssociation(CaplInstance* inInst);

	/** Экспортирует данные технологических сборок в файл 
		@param inst - базовый инстэнс
		@param filename - имя файла
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ExportTechAssemblies(aplExtent &ext, const TCHAR *filename=0,
						CString *err_mess=0);

	/**
	Для КВЗ. Убирает признак проведенного технологического изменения
	*/
	bool UndoAptc(CaplInstance *change);

	bool SaveArr2File();
protected:
	int m_recurs_level;	
	CaplMgrPrgsDlg *m_prgs_dlg;
	void ImportCharacteristics(CaplMap &map,aplExtent &ext_copy,  int &prgs_count);
	void ImportCategory(CaplMap& map ,aplExtent& ext_copy );
	void ImportProject(CaplMap& map ,aplExtent& ext_copy);
	void ImportChanges(CaplMap& map ,aplExtent& ext_copy);
	void ImportBP(CaplMap &map,aplExtent &ext_copy,  int &prgs_count);
	void ImportPI(CaplMap &map,aplExtent &ext_copy,  int &prgs_count);
	void ImportClassifierEsquisse(CaplInstance* inst_api,CaplInstance* inst_file);
};

// *************************************************************************
// *************************************************************************
// *************************************************************************
/** Менеджер изменений*/
class CLASS_DECL_APL_STEP_MGR CaplChangeManager: public CaplStepManager  
{
	// Инициализация
public:
	/** Инициализирует класс (Ассоциация с классом базы данных) 
		@return true при удачном выполнении и false в случае ошибки */
	virtual bool Attach(CaplAPI *api);
	virtual void Detach();

	/**@name Изменение */
	//@{
	CaplEntity* e_chng;				/**<apl_change */
	CaplAttr* a_chng_id;			/**<apl_change -> id */
	CaplAttr* a_chng_pdf;			/**<apl_change -> pdf */
	CaplAttr* a_chng_name;			/**<apl_change -> name */
	CaplAttr* a_chng_dscr;			/**<apl_change -> description */
	CaplAttr* a_chng_user;			/**<apl_change -> user */
	CaplAttr* a_chng_autor;			/**<apl_change -> autor */
	CaplAttr* a_chng_create_user;	/**<apl_change -> create_user */
	CaplAttr* a_chng_create_autor;	/**<apl_change -> create_autor */
	CaplAttr* a_chng_create_date;	/**<apl_change -> create_state */
	CaplAttr* a_chng_apply_date;	/**<apl_change -> apply_state */
	CaplAttr* a_chng_state;			/**<apl_change -> state */
	CaplAttr* a_chng_items;			/**<apl_change -> items */
	CaplAttr* a_chng_basis;			/**<apl_change -> basis */
	CaplAttr* a_chng_stock;			/**<apl_change -> stock */
	CaplAttr* a_chng_stock_ceh;		/**<apl_change -> stock_ceh  Списк цехов для проверки изменения */
	CaplAttr* a_chng_asm_pdf;		/**<apl_change -> assembly_pdf */
	CaplAttr* a_chng_changed_assemlies;		/**<apl_change -> changed_assemlies */
	CaplAttr* a_chng_is_modify;		
	CaplAttr* a_chng_eff_type;			/**<apl_change -> effectivity_type */
	CaplAttr* a_chng_start_date;		/**<apl_change -> start_date */
	CaplAttr* a_chng_end_date;			/**<apl_change -> end_date */
	CaplAttr* a_chng_start_num;			/**<apl_change -> start_number */
	CaplAttr* a_chng_end_num;			/**<apl_change -> end_number */
	CaplAttr* a_chng_export_num;		/**<apl_change -> export_num */
	CaplAttr* a_chng_order_directive;	/**<apl_change -> order_directive */
	CaplAttr* a_chng_type;				/**<apl_change -> type */
	CaplAttr* a_chng_event_number;		/**<apl_change -> event_number */
	CaplAttr* a_chng_rejection_reason;	/**<apl_change -> rejection_reason */
	CaplAttr* a_chng_helicopter_usage;	/**<apl_change -> helicopter_usage */
	CaplAttr* a_chng_handmade_copy;		/**<apl_change -> handmade_copy */
	CaplAttr* a_chng_base;				/**<apl_change -> base база (для ДИ)*/
	CaplAttr* a_chng_src_pi;			/**<apl_change -> Исходное ПИ для ИИ)*/
	CaplAttr* a_chng_urgency;			/**<apl_change -> urgency  Срочность */
	CaplAttr* a_chng_issue_date;		/**<apl_change -> ssue_date  дата выпуска ПИ */
	CaplAttr* a_chng_validity_pi_date;	/**<apl_change -> validity_pi_date  Срок действия ПИ */
	CaplAttr* a_chng_validity_pi_date_actual;	/**<apl_change -> validity_pi_date  Срок действия ПИ актуальный (с учетом продления)*/
	
	CaplAttr* a_chng_org_code;			/** код предприятия */
	CaplAttr* a_chng_grp_num;			/** номер подразделения */
	CaplAttr* a_chng_doc_id;			/** обозначение документа */
	CaplAttr* a_chng_basis_code;		/** код причнины изменения */
	CaplAttr* a_chng_usage;				/** применяемость */
	CaplAttr* a_chng_complect_num;		/** номер комлекта внед. изм. */
	CaplAttr* a_chng_list;				/** список рассылки */
	CaplAttr* a_chng_stock_introd;		/** указание о внедрении */
	CaplAttr* a_chng_stock_introd_type; /** способ задания указании о внедрении */
	CaplAttr* a_chng_to_date;			/** срок доработки ТО */
	CaplAttr* a_chng_otd_date;			/** дата передачи в ОТД */
	CaplAttr* a_chng_critical_date;		/** срок изменения */
	CaplAttr* a_chng_plan_lead_date;	/** плановая дата согласования у руководителя */
	CaplAttr* a_chng_plan_otd_date;		/** плановая дата сдачи в архив */
	CaplAttr* a_chng_date_of;			/** дата составления */
	CaplAttr* a_chng_usage_ing;			/** применяемость (изменяеме изделия уровнем вверх) */
	CaplAttr* a_chng_group_id;			/** группа */
	CaplAttr* a_chng_notice;			/** ссылка на документ - извещение */
	CaplAttr* a_chng_dependent_items;	

	// элемент лога изменения расцеховки
	CaplEntity*  e_rasc_chng_log;
	CaplAttr*    a_rasc_chng_log_pdf;
	CaplAttr*    a_rasc_chng_log_change;
	CaplAttr*    a_rasc_chng_log_position;
	CaplAttr*    a_rasc_chng_log_shop;
	CaplAttr*    a_rasc_chng_log_date;


	// Объект содержит данные, необходимые для 	определения серии внедрения  
	// КИ в ПДО по процедуре workflow.
	CaplEntity*	 e_stock_introd_signal;
	CaplAttr*    a_stock_intr_signal_pdf;
	CaplAttr*    a_stock_intr_signal_stock_introd;
	CaplAttr*    a_stock_intr_signal_event_number;
	CaplAttr*    a_stock_intr_signal_blank_changed;
	CaplAttr*    a_stock_intr_signal_change;
	CaplAttr*    a_stock_intr_signal_pdf_from;
	CaplAttr*    a_stock_intr_signal_stock_introd_series;
	CaplAttr*    a_stock_intr_signal_rasc;
	CaplAttr*    a_stock_intr_signal_signal_number;
	CaplAttr*    a_stock_intr_signal_notes;
	CaplAttr*    a_stock_intr_signal_production_series;

	// внедрение изменения по цеху
	CaplEntity*  e_apl_introd_change_by_shop;
	CaplAttr*    a_intr_chng_shop_view_tech;
	CaplAttr*    a_intr_chng_shop_view_master;
	CaplAttr*    a_intr_chng_shop_view_pdb;
	CaplAttr*    a_intr_chng_shop_view_btk;
	CaplAttr*    a_intr_chng_shop_introd_tech;
	CaplAttr*    a_intr_chng_shop_introd_master;
	CaplAttr*    a_intr_chng_shop_introd_pdb;
	CaplAttr*    a_intr_chng_shop_introd_btk;
	CaplAttr*    a_intr_chng_shop_introd_customer;
	CaplAttr*    a_intr_chng_shop_is_printed;
	CaplAttr*    a_intr_chng_shop_date;
	CaplAttr*    a_intr_chng_shop_change;
	CaplAttr*    a_intr_chng_shop_shop;
	CaplAttr*    a_intr_chng_shop_short_descr;	
	CaplAttr*    a_intr_chng_shop_result_check;
	CaplAttr*    a_intr_chng_shop_view_tech_date;
	CaplAttr*    a_intr_chng_shop_view_master_date;
	CaplAttr*    a_intr_chng_shop_view_pdb_date;
	CaplAttr*    a_intr_chng_shop_view_btk_date;
	CaplAttr*    a_intr_chng_shop_introd_tech_date;
	CaplAttr*    a_intr_chng_shop_introd_master_date;
	CaplAttr*    a_intr_chng_shop_introd_pdb_date;
	CaplAttr*    a_intr_chng_shop_introd_btk_date;
	CaplAttr*    a_intr_chng_shop_result_check_date;




	// связь между изменениями
	CaplEntity*  e_apl_chng_rel;
	CaplAttr*    a_chng_rel_related;
	CaplAttr*    a_chng_rel_relating;
						
	//@}
	
	/**@name Элемент изменения */
	//@{
	CaplEntity* e_chng_item;			/**<apl_changed_item */
	CaplAttr* a_chng_item_id;			/**<apl_changed_item -> id */
	CaplAttr* a_chng_item_name;			/**<apl_changed_item -> id */
	CaplAttr* a_chng_item_dscr;			/**<apl_changed_item -> description */
	CaplAttr* a_chng_item_notes;		/**<apl_changed_item -> notes */
	CaplAttr* a_chng_item_basis;		/**<apl_changed_item -> basis */
	CaplAttr* a_chng_item_stock;		/**<apl_changed_item -> stock */
	CaplAttr* a_chng_item_attachment;	/**<apl_changed_item -> attachment */
 	CaplAttr* a_chng_item_autor;		/**<apl_changed_item -> autor */
 	CaplAttr* a_chng_item_user;			/**<apl_changed_item -> user */
 	CaplAttr* a_chng_item_accept_date;	/**<apl_changed_item -> accept_date */
	CaplAttr* a_chng_item_of_chng;		/**<apl_changed_item -> of_change */
	CaplAttr* a_chng_item_item;			/**<apl_changed_item -> item_of_basis */
	CaplAttr* a_chng_item_replace_state;			/**<apl_changed_item -> replace_state */
	//@}

	/**@name Элемент основания */
	//@{
	CaplEntity* e_basis_item;			/**<apl_basis_item */
	CaplAttr*	a_basis_item_parent;	/**<apl_basis_item -> parent_basis */
	CaplAttr*	a_basis_item_old_rasc;	/**<apl_basis_item -> old_rasc */
	CaplAttr*	a_basis_item_new_rasc;	/**<apl_basis_item -> new_rasc */
	CaplAttr*	a_basis_item_old_count;	/**<apl_basis_item -> old_count */
	CaplAttr*	a_basis_item_new_count;	/**<apl_basis_item -> new_count */
	CaplAttr*	a_basis_item_old_unit;	/**<apl_basis_item -> old_unit */
	CaplAttr*	a_basis_item_new_unit;	/**<apl_basis_item -> new_unit */
	CaplAttr*	a_basis_item_old_mat;	/**<apl_basis_item -> old_mat */
	CaplAttr*	a_basis_item_new_mat;	/**<apl_basis_item -> new_mat */
	CaplAttr*	a_basis_item_pdf;		/**<apl_basis_item -> pdf */
	CaplAttr*	a_basis_item_pdr;		/**<apl_basis_item -> pdr */
	CaplAttr*	a_basis_item_old_cust;	/**<apl_basis_item -> old_customer */
	CaplAttr*	a_basis_item_new_cust;	/**<apl_basis_item -> new_customer */
	CaplAttr*	a_basis_item_old_gab;	/**<apl_basis_item -> old_gabarit  */
	CaplAttr*	a_basis_item_new_gab;	/**<apl_basis_item -> new_gabarit  */
	CaplAttr*	a_basis_item_old_fw;	/**<apl_basis_item -> old_from_waste  */
	CaplAttr*	a_basis_item_new_fw;	/**<apl_basis_item -> new_from_waste  */
	CaplAttr*	a_basis_item_rasc_owner;	
	CaplAttr*	a_basis_item_mat_owner;		
	//@}

	CaplEntity* e_psc;					/**<apl_product_structure_change */
	CaplAttr* a_psc_changed_product;	/**<apl_product_structure_change -> changed_product */
	CaplAttr* a_psc_changing_product;	/**<apl_product_structure_change -> changing_product */
	CaplAttr* a_psc_position;			/**<apl_product_structure_change -> position */
	CaplAttr* a_psc_position_num;		/**<apl_product_structure_change -> position_number */
	CaplAttr* a_psc_value;				/**<apl_product_structure_change -> value */
	CaplAttr* a_psc_unit;				/**<apl_product_structure_change -> unit */
	CaplAttr* a_psc_eff_type;			/**<apl_product_structure_change -> effectivity_type */
	CaplAttr* a_psc_start_date;			/**<apl_product_structure_change -> start_date */
	CaplAttr* a_psc_end_date;			/**<apl_product_structure_change -> end_date */
	CaplAttr* a_psc_start_num;			/**<apl_product_structure_change -> start_number */
	CaplAttr* a_psc_end_num;			/**<apl_product_structure_change -> end_number */
	CaplAttr* a_psc_addit;				/**<apl_product_structure_change -> additional */
	CaplAttr* a_psc_frames_of_reference;/**<apl_product_structure_change -> apl_frames_of_reference */
	CaplAttr* a_psc_cancel_set;			/**<apl_product_structure_change -> canceled_effectivities */
	CaplAttr* a_psc_add_set;			/**<apl_product_structure_change -> added_effectivities */
	CaplAttr* a_psc_modif_set;			/**<apl_product_structure_change -> modified_effectivities */
	CaplAttr* a_psc_created_pdr;		/**<apl_product_structure_change -> created_pdr */
	
	CaplEntity* e_mat;				/**<apl_material_change */
	CaplAttr* a_mat_renking;		/**<apl_material_change -> ranking*/
	CaplAttr* a_mat_der_value;		/**<apl_material_change -> derive_value*/
	CaplAttr* a_mat_der_unit;		/**<apl_material_change -> derive_unit*/
	CaplAttr* a_mat_assort;			/**<apl_material_change -> assortment*/
	CaplAttr* a_mat_size;			/**<apl_material_change -> billet_size*/
	CaplAttr* a_mat_requir;			/**<apl_material_change -> requirements*/

	CaplEntity* e_avc;				/**<apl_document_change_item */
	CaplAttr* a_avc_new_rev;		/**<apl_document_change -> new_revision*/
	CaplAttr* a_avc_old_rev;		/**<apl_document_change -> old_revision*/
	CaplAttr* a_avc_doc;			/**<apl_document_change -> document*/
	CaplAttr* a_avc_method;			/**<apl_document_change -> method*/
	CaplAttr* a_avc_items_for_add_relation;			/**<apl_document_change -> items_for_add_relation*/
	CaplAttr* a_avc_items_for_del_relation;			/**<apl_document_change -> items_for_add_relation*/
	
	CaplEntity* e_abpc;				/**<apl_business_process_change */
	CaplAttr* a_abpc_new_rev;		/**<apl_business_process_change -> new_revision */
	CaplAttr* a_abpc_old_rev;		/**<apl_business_process_change -> old_revision */
	CaplAttr* a_abpc_bp;			/**<apl_business_process_change -> business_process */

	CaplEntity* e_char_change;		/**<apl_characteristic_change_item */
	CaplAttr* a_char_change_new_rev;/**<apl_characteristic_change_item -> new_revision*/
	CaplAttr* a_char_change_old_rev;/**<apl_characteristic_change_item -> old_revision*/
	CaplAttr* a_char_change_val;	/**<apl_characteristic_change_item -> characteristic*/

	/**@name Изменение компонента ОГМет */
	//@{
	CaplEntity* e_cmf_change_item;			/**<apl_component_make_from_change_item*/
	CaplAttr*    a_cmf_comp_mf;				/**<apl_component_make_from_change_item -> make_from*/
	CaplAttr*    a_cmf_pdf;					/**<apl_component_make_from_change_item -> product_definition*/
	CaplAttr*    a_cmf_mat;					/**<apl_component_make_from_change_item -> material*/
	CaplAttr*    a_cmf_unit;				/**<apl_component_make_from_change_item -> unit*/
	CaplAttr*    a_cmf_value;				/**<apl_component_make_from_change_item -> value*/
	CaplAttr*    a_cmf_derived_unit;		/**<apl_component_make_from_change_item -> derived_unit*/	
	CaplAttr*    a_cmf_derived_value;		/**<apl_component_make_from_change_item -> derived_value*/
	CaplAttr*    a_cmf_type_id;				/**<apl_component_make_from_change_item -> type_id*/		
	CaplAttr*    a_cmf_type;				/**<apl_component_make_from_change_item -> type*/
	CaplAttr*    a_cmf_descr;				/**<apl_component_make_from_change_item -> description*/
	CaplAttr*    a_cmf_id;					/**<apl_component_make_from_change_item -> id*/
	CaplAttr*    a_cmf_author;				/**<apl_component_make_from_change_item -> author*/
	CaplAttr*    a_cmf_new_mat;				/**<apl_component_make_from_change_item -> new_material*/
	CaplAttr*    a_cmf_new_unit;			/**<apl_component_make_from_change_item -> new_unit*/
	CaplAttr*    a_cmf_new_value;			/**<apl_component_make_from_change_item -> new_value*/
	CaplAttr*    a_cmf_new_derived_unit;	/**<apl_component_make_from_change_item -> new_derived_unit */
	CaplAttr*    a_cmf_new_derived_value;	/**<apl_component_make_from_change_item -> new_derived_value*/
	CaplAttr*    a_cmf_new_type_id;			/**<apl_component_make_from_change_item -> new_type_id*/
	CaplAttr*    a_cmf_new_type;			/**<apl_component_make_from_change_item -> new_type*/
	CaplAttr*    a_cmf_new_descr;			/**<apl_component_make_from_change_item -> new_description*/
	CaplAttr*    a_cmf_new_id;				/**<apl_component_make_from_change_item - >new_id*/
	CaplAttr*    a_cmf_of_change;			/**<apl_component_make_from_change_item -> of_change*/
	CaplAttr*    a_cmf_action;				/**<apl_component_make_from_change_item -> action*/
	//@}

	CaplEntity* e_cmf_chng;					/**<apl_component_make_from_change*/
	CaplAttr*    a_cmf_chng_of_change;		/**<apl_component_make_from_change -> of_change*/
	CaplAttr*    a_cmf_chng_items;			/**<apl_component_make_from_change -> items*/

	/**@name Изменение характеристики ОГМет */
	//@{
	CaplEntity* e_cmf_char_ch_item;			/**<apl_component_make_from_characteristic_change_item*/
	CaplAttr*    a_cmf_char_ch_of_change;	/**<apl_component_make_from_characteristic_change_item -> of_change*/
	CaplAttr*    a_cmf_char_ch_pdf;			/**<apl_component_make_from_characteristic_change_item -> product_defnition_formation*/
	CaplAttr*    a_cmf_char_ch_old_rev;		/**<apl_component_make_from_characteristic_change_item -> old_revision*/
	CaplAttr*    a_cmf_char_ch_new_rev;		/**<apl_component_make_from_characteristic_change_item -> new_revision*/
	CaplAttr*    a_cmf_char_ch_char;		/**<apl_component_make_from_characteristic_change_item -> characteristic*/
	//@}

	/**@name Указание о внедрении для экспортного номер */
	//@{
	CaplEntity* e_order_directive;					/**<apl_order_directive*/
	CaplAttr*    a_order_directive_numbers;			/**<apl_order_directive -> numbers */
	CaplAttr*    a_order_directive_org;				/**<apl_order_directive -> org */
	CaplAttr*    a_order_directive_id;				/**<apl_order_directive -> id */
	CaplAttr*    a_order_directive_name;			/**<apl_order_directive -> name */
	CaplAttr*    a_order_directive_description;		/**<apl_order_directive -> description */
	//@}

	/**@name Экспортный номер */
	//@{
	CaplEntity* e_order_number;						/**<apl_order_number*/
	CaplAttr*    a_order_number_directive;			/**<apl_order_number -> directive */
	CaplAttr*    a_order_number_id;					/**<apl_order_number -> id */
	//@}
	
	/** Проводит изменение 
		@param change - изменение
		@param paeWrongRels - массив связей, где цеха-потребители неверны
		@return true при удачном выполнении и false в случае ошибки*/
	#define APL_CH_NO_TECH_APPLY	0x00100000
	#define APL_CH_NO_TECH_CHECK	0x00200000
	#define APL_CH_NO_DRAFT_CHECK	0x00400000

	#define APL_CN_NO_ERR		 1
	#define APL_CH_STD_ERR		 2
	#define APL_CH_MAT_CH_ERR	 4
	#define APL_CH_SHOP_CH_ERR	 8
	#define APL_CH_OGM_ERR		16
	#define APL_CH_STATE_ERR	32

	int ApplyChange(CaplInstance* change, aplExtent *paeWrongRels = NULL, DWORD flag= 0);

	int ApplyChangeGrpz(CaplInstance* change); // Проведение дроби для ГРПЗ, выхывается из ApplyChange

	bool CheckGrpzChangeGroupById(aplExtent &ext_ch, CString &sErr);
	
	bool ReturnChangeToEdit(CaplInstance* change); // Отзывает изменение с согласования (и анулирует все подписи

protected:
	int ApplyChangeContent(aplExtent &extAccess, CaplInstance* change, aplExtent *paeWrongRels = NULL, DWORD flag= 0, bool bKVZ=false); // Непосредственно проведение изменения, выхывается из ApplyChange
public:
	
	/** Откатывает проведенное изменение
		@param chnage - изменение
		@return true при удачном выполнении и false в случае ошибки*/		
	bool UndoChange(CaplInstance* chnage);

	/** Создает изменение 
		@param id - обозначение изменения.
		@param name - наименование изменения.
		@param dscr - описание изменения.
		@param user - пользователь, создающий изменение.
		@param person - сотрудник, создающий изменение.
		@return созданный объект изменения или NULL в случае ошибки.*/
	CaplInstance* CreateChange(const TCHAR* id, const TCHAR* name, const TCHAR* dscr,
		const TCHAR* user, CaplInstance* person, aplExtent &chngItems, CaplInstance *base_change=0);

	// Создать ИИ заменяющее ПИ
	CaplInstance* CreateRepaymentChange(CaplInstance *pi_change);

	// Создать связанное ИИ (дробь)
	CaplInstance* CreateLinkedChange(CaplInstance *old_change);

	// работаем с типами "указания о внедрении"
	enum EStockIntrodType {helicopter_number, date, complect, competition, series, pdo_signal, none};
		
	/** Удаление объекта изменения 
		@param change - изменение.
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool DeleteChange(CaplInstance* change);
	
	/** Возвращает список изменений для версии изделия 
		@param pdf_or_doc - версия изделия или документ.
		@param changes - список изменений.
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool GetAllChanges(CaplInstance* pdf_or_doc, aplExtent &changes, bool bNotAppliedOnly= false);

	/** Возвращает изменения для которых change является базовым */
	bool GetSubChanges(CaplInstance *change, aplExtent &ext_subchanges);

	// Нати заменяющее ИИ для ПИ
	CaplInstance *FindRepaymentChange(CaplInstance *pi_change);
	
	/** Читает из базы информацию об изменении 
		@param change - изменение.
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool LoadChangeInfo(aplExtent& changes, bool bFullLoad= true);
	bool LoadChangeInfo(CaplInstance* change, bool bFullLoad= true);
	
	/** Читает из базы информацию об элементе изменения 
		@param item - элемент изменения.
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool LoadItemInfo(CaplInstance* item);
	
	/** Читает из базы информацию об элементах изменения 
		@param items - элементы изменения.
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool LoadItemInfo(aplExtent& items);
	
	/** Выводит диалог со свойствами изменения 
		@param change - изменение.
		@return ненулевое значение при удачном выполнении и нуль в случае ошибки*/
	int ShowChangeProperties(CaplInstance* change);
	
	/** Выводит диалог с деревом последующих изменений 
		@param change - изменение, для которого выводится дерево.
		@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
	bool ShowChangesTree(CaplInstance* change);

	/// Добавляет объекты в пакет изменений (если change==0, по появлется диалог выбора)
	bool AddItemsToChange(aplExtent &extItems, CaplInstance *change);
	
	/** Возвращает следующий идентификатор (порядковый номер) изменения для версии изделия
		@param pdf версия изделия
		@return идентификатор изменения или пустую строку в случае ошибки*/
	CString	GetPSCId(CaplInstance *pdf);

	/** Возвращает следующий идентификатор (порядковый номер) изменения для документа
		@param doc_rev документ или версия документа
		@return идентификатон изменения или пустую строку в случае ошибки*/
	CString	GetAVCId(CaplInstance *doc_rev);
	
	/** Возвращает следующий идентификатор (порядковый номер) изменения для бизнес-процесса
		@param bp_ver бизнес-процесс или версия бизнес-процесса
		@return идентификатор изменения или пустую строку в случае ошибки*/
	CString	GetBPCId(CaplInstance *bp_ver);
	
	/** Возвращает следующий идентификатор (порядковый номер) изменения для версии изделия
		@param pdf версия изделия
		@return идентификатор изменения или пустую строку в случае ошибки*/
	CString	GetMFCId(CaplInstance *pdf);
	
	/** Возвращает следующий идентификатор (порядковый номер) изменения для характеристики
		@param ch_ver характеристика или версия характеристики
		@return идентификатор изменения или пустую строку в случае ошибки*/
	CString GetCHCId(CaplInstance* ch_ver);
	
	CaplInstance* FoundCharactAndType();
	
	/**Выводит диалог для редактирования применяемости для всего изменения в целом
		@param change - пакет изменений
		@return true в случе удачного выполнения или false в пртивном случае*/
	bool SetChangeEffectivity(CaplInstance* change, CString& sEffType, CString& sStartCond, CString& sEndCond);
	//Нет реализации
	CaplInstance* CreateProductStructureChange(const TCHAR* id, const TCHAR* basis, const TCHAR* zadel,
		CaplInstance* pdr_or_pd, CaplInstance* pdf, CaplInstance* value, CaplInstance* unit, 
		const TCHAR* effType, const TCHAR* start_cond, const TCHAR* end_cond);
	/**Выводит диалог для просмотра записи об изменении активной версии или структуры изделия
		@param item - запись об изменении в пакете изменений. Тип item может быть apl_product_structure_change или apl_document_change_item
		@return 1 в случе удачного выполнения или 0 в пртивном случае*/
	int ShowPSCItemProperty(CaplInstance* item);
	/**Выводит диалог для просмотра или редактирования изменений сборочной единицы
		@param pdf - версия изделия
		@param change - пакет изменений
		@param newItems - массив, содержащий новые созданны записи об изменении сборочной единицы
		@return true при удачном выполнении или false  в случае ошибки*/
	bool ShowAssemblyChanges(CaplInstance* pdf, CaplInstance* change, aplExtent&newItems);
	/** Возвращает записи в пакете изменения относящиеся к версии изделия
		@param pdf - версия изделия
		@param change - пакет изменений
		@param items - массив, содержащий записи об изменении
		@return true при удачном выполнении или false  в случае ошибки*/
	bool GetPdfChangeItems(CaplInstance* pdf, CaplInstance* change, aplExtent& items);

	/** Возвращает связанные изменения*/
	bool GetLinkedChange(CaplInstance* change, aplExtent &ext_linked_chagesext_linked_chages);

	bool GenerateChangeId(CString &change_id);  // Генерирует новое обозначение изменения

	bool IsChangeAptc(CaplInstance *change);

	/**
	Для КВЗ. Убирает признак проведенного технологического изменения
	*/
	bool UndoAptc(CaplInstance *change);

	CString GetAdditionalMakeChangeLog() { return m_sAdditionalMakeChangeLog; }


	// Для отображения в отчете ИИ
	bool LoadChangeFields(CaplInstance *change, CaplStrStrMap &map_params);

private:
	bool GetPrdEffectivity(CaplInstance* pdr, CString sType, CString sStart, CString sEnd,
		aplExtent &eff_ext, aplExtent *pdrEff = 0);
	bool ResetPrdEffectivity(CaplInstance* eff, 
		CString sType, CString sStart, CString sEnd,
		aplExtent &pdr_ext, aplExtent &eff_ext);
	bool CreateDatedEffSet(BOOL bReset, 
		CString sId, CString sStart, CString sEnd, CaplInstance* pdr_ed, 
		aplExtent &pdr_ext, aplExtent &eff_ext, CaplInstance* pdr_ing= NULL);
	bool CreateNumedEffSet(BOOL bReset, CString sId, CString sStart,
		CString sEnd, CaplInstance* pdr_ed, 
		aplExtent &pdr_ext, aplExtent &eff_ext, CaplInstance* pdr_ing= NULL);
	bool CreateFictiveEff(aplExtent &pdr_ext, CString sType);

	//выстраивает из eff_set замкнутую цепочку правил применяемости
	bool FillEffChain(aplExtent &eff_set);
	
	bool SetActive(CaplInstance* bp, CaplInstance* bp_ver);

	aplExtent m_addedEffSet;
	aplExtent m_deletedEffSet;
	aplExtent m_chngedEffSet;

	// дополнительные сведения о невозможности проведения изменения
	CString m_sAdditionalMakeChangeLog;
};

// *************************************************************************
// *************************************************************************
// *************************************************************************
/** Менеджер единиц измерения*/
class CLASS_DECL_APL_STEP_MGR CaplUnitExchangeManager: public CaplStepManager  
{
public:

#ifndef APL_NO_INSET_IN_DOC

    class BASE //"база" единицы измерения
    {  
	public:
		BASE();
		CaplInstance *cUnit;//единица измерения
		double conv_factor;//коэффициент относительно базовых единиц Си (с учетом префиксов)
		CString id;
		CString name;
		//базис единицы измерения
		double length;
		double mass;
		double time;
		double electric_cur;
		double therm_temp;
		double am_of_sub;
		double lum_intens;
    };
	
#endif

	/**инициализирует указатели на объекты и базисы для единиц измерения
	@param load_units - true ecли необходимо скачивать единицы измерения в кэш*/
	virtual bool Attach(CaplAPI *api);
	
	/** Читает единицы измерения из БД*/
	bool LoadUnits();

	/** Инициализация базисов */
	bool InitUnitsBases();

	/** Возвращает единицы измерения для изделий */
	bool GetPrdUnits(aplExtent &units);

	//сравнивает базисы единиц измерения
	bool IsSameBase(BASE *first_base,BASE *second_base);
	
	/**сравнивает базисы единиц измерения*/
	bool IsSameBase(CaplInstance *first_unit,CaplInstance *second_unit);
	
	/**получает список единиц измерения с тем же базисом*/
	bool FindUnitsWithSameBase(CaplInstance *unit,aplExtent *units);
	
	/**преобразует amount_to_convert ед.изм.whatUnit к result ед.изм.inWhatUnit*/
	bool Convert(CaplInstance *whatUnit,CaplInstance *inWhatUnit,double amount_to_convert,double &result);
	
	CaplAttr *a_apl_named_unit_dimensions;
	CaplAttr *a_apl_conv_base_unit_conv_factor;
	CaplAttr *a_apl_derived_unit_elements;
	CaplAttr *a_apl_si_unit_prefix;
	CaplAttr *a_apl_unit_name;
	CaplAttr *a_apl_unit_id;

	CaplEntity	*e_apl_measure_with_unit;
	CaplAttr *a_apl_measure_with_unit_unit_comp,*a_apl_measure_with_unit_value_comp;

	CaplEntity	*e_apl_derived_unit_element;
	CaplAttr *a_apl_derived_unit_element_exponent,*a_apl_derived_unit_element_unit;
	
	CaplEntity *e_apl_dimensional_exponents;
	CaplAttr *a_apl_dim_exp_length_exponent,*a_apl_dim_exp_mass_exponent,*a_apl_dim_exp_time_exponent;
	CaplAttr *a_apl_dim_exp_electric_current_exponent,*a_apl_dim_exp_thermodynamic_temperature_exponent;
	CaplAttr *a_apl_dim_exp_amount_of_substance_exponent,*a_apl_dim_exp_luminous_intensity_exponent;
	
	CaplUnitExchangeManager();
	virtual ~CaplUnitExchangeManager();
protected:
	bool attached;//флаг инициализированности экземпляра класса

	//все единицы измерения и базисы
	CArray<BASE,BASE> all_unit_bases;

	//получает базисы единицы измерения
	BASE *GetBase(CaplInstance *unit);

	aplExtent m_ext_prd_unit; // Список ед. изм. для кол-ва изделий


	//получает базисы и коэффициент пересчета единиц Си и контекстно-зависимых единиц измерения
	bool GetSiAndContextUnitsBases();
	
	//получает остальные базисы и коэффициенты
	bool GetAllOtherUnitsBases();
	bool GetConvBasedUnitBase(CaplInstance *convUnitAttr,CaplInstance *Unit,double exponent=1,double conv_factor=1);
	bool GetDerUnitBases(CaplInstance *derUnitAttr,CaplInstance *Unit,double exponent=1,double conv_factor=1);
	bool AddUnitBase(CaplInstance *inst,CaplInstance *Unit,double exponent=1,double conv_factor=1);
};

class AFX_EXT_CLASS CaplDeclareWorkflowManager : public CaplStepManager
{
	// Инициализация 
public:
	/** Инициализирует класс (Ассоциация с классом базы данных) <p>
	@return true при удачном выполнении и false в случае ошибки */
	virtual bool Attach(CaplAPI *api){return true;}
	virtual void Detach(){;}
	
	/*Функции, вынесенные для доступа к ним из CaplWorkFlowManager*/
	/*см. описание CaplWorkFlowManager*/
	virtual bool GetUserTaskList(CaplInstance* performer, aplExtent&task_list, bool bCompleted=true, bool bCanceled=true, bool bSuspended=true){return true;}
	virtual bool GetWorkObjects(CaplInstance* task_or_process, aplExtent&objects){return true;}

	virtual bool FindProcessContained(CaplInstance *ciItem, aplExtent &aeExtOut){return false;}
	virtual bool FindProcessContained(aplExtent& extItems, aplExtent& extOut){return false;}
	virtual bool LoadProcessInfo(CaplInstance* process){return false;}
	virtual bool LoadProcessInfo(aplExtent& process){return false;}
	virtual bool GetUserProcessTempList(CaplInstance* owner, aplExtent& proc_tmpls){return false;}

	#define APL_MODE_WFL_SELECT_TEMPLATE			0x00000001
	#define APL_MODE_WFL_SELECT_ACTIVITI			0x00000002


	/** Выводит диалог выбора шаблона процесса или 
	@param templates - список доступных шаблонов процессов
	@param sel_template - шаблон по умолчанию
	@param bShowAllTemplates - показывать в дереве все шаблоны процессов
	@param SelectMode - значение определяющее типы данных которые можно выбрать <br>

		APL_MODE_WFL_SELECT_TEMPLATE - можно выбирать шаблон процесса
		APL_MODE_WFL_SELECT_ACTIVITI - можно выбирать apl_activity

	@return выбранный объект 	*/
	virtual CaplInstance *SelectTemplateSchema(aplExtent &templates, CaplInstance *sel_template=0, bool bShowAllTemplates = true, long SelectMode = APL_MODE_WFL_SELECT_TEMPLATE){return false;}

	virtual void LoadParamsFromDB(){};
};

class AFX_EXT_CLASS CaplPreConfigurationMgr : public CaplStepManager
{
	// Инициализация 
public:
	CaplPreConfigurationMgr() { m_bReadOnlyWindow = false; };

	/** Инициализирует класс (Ассоциация с классом базы данных) <p>
	@return true при удачном выполнении и false в случае ошибки */
	virtual bool Attach(CaplAPI *api){return true;}
	virtual void Detach(){;}		

	/** глобальная переменная для всех окон, связанных с этим менеджером. само по себе ничего не делает
		readonly для каждого окна, нужно реализовывать самому =)) */
	bool m_bReadOnlyWindow;
};

class AFX_EXT_CLASS CaplPreForumManager : public CaplStepManager
{
	// Инициализация 
public:
	CaplPreForumManager() {};
	~CaplPreForumManager() {};

	/** Инициализирует класс (Ассоциация с классом базы данных) <p>
	@return true при удачном выполнении и false в случае ошибки */
	virtual bool Attach(CaplAPI *api){return true;}
	virtual void Detach(){;}

	virtual CaplInstance* ShowRefusalQuestions(CaplInstance *refusalInst) { return NULL; };
};

class AFX_EXT_CLASS CaplPreProjectManager : public CaplStepManager 
{
public:
/** Инициализирует класс (Ассоциация с классом базы данных) <p>
	@return true при удачном выполнении и false в случае ошибки */
	virtual ~CaplPreProjectManager(){;}
	
	bool Attach(CaplAPI *api);
	void Detach();
	bool LoadDictionary();

	// Читает в кэш информацию о проектах.  Если  bLoadPrevRelations==true - зачитываются и предыдущие связи (без предыдущих проектов)
	bool LoadProjectInfo(CaplInstance *project, bool bLoadPrevRelations=false);
	bool LoadProjectInfo(aplExtent &ext, bool bLoadPrevRelations=false);

	// Является ли дочерним для другого проекта
	bool IsProjectInContentOfParent(CaplInstance *project);

	//*************************************************************************
	//******   Ассоциации проекта с объектами  ********************************
	//*************************************************************************

	// Возвращает связи ассоциации  проекта с объектами
	bool FindAssociatedItems(CaplInstance *project, aplExtent &out_ext, aplExtent &out_rel); 
	
	// Возвращает связанные с объектом проекты
	bool FindAssociatedProjects(CaplInstance *item, aplExtent &out_ext, aplExtent &out_rel); 

	// Создание связи
	CaplInstance *CreateAssociation(CaplInstance *project,CaplInstance *item,const TCHAR *id=0,const TCHAR *name=0,CaplInstance *control_status=0);
	
	// Создание связи
	bool DeleteAssociation(CaplInstance *project,CaplInstance *item);
	
	// Поиск связи
	CaplInstance *FindAssociation(CaplInstance *project,CaplInstance *item);

	// Зачитывает в кэш ассоциации проектов с другими объектами
	bool LoadProjectReferenceInfo(CaplInstance *project);
	bool LoadProjectReferenceInfo(aplExtent &ext);


	//*************************************************************************
	//******   Горизонтальные связи (последовательность) **********************
	//*************************************************************************

	// Берем связи проекта. Если previous_only==true - берем только связи с предыдущим проектом
	bool GetProjectSequenceRelation(CaplInstance *prj, aplExtent &ext_rel, bool previous_only, bool bLoadFromDB=true);

	// Читает из базы связи множества проектов. Если previous_only==true - берем только связи с предыдущим проектом
	bool LoadProjectsSequenceRelations(aplExtent &projects, aplExtent &ext_rel, bool previous_only, bool bLoadFromDB=true);


	//*************************************************************************
	//******   Версии проектов       ******************************************
	//*************************************************************************
	CaplInstance *GetLatestProjectVersion(CaplInstance *project,CString &num);
	/** Создает версию проекта
	@param project  проект или его версия
	@param num номер создаваемой версии (-1 создавать очередную версию)
	@param make_active делать созданную версию активной
	@return созданная версия проекта,или 0 в случае ошибки */

	CaplInstance *CreateProjectVersion(CaplInstance *project,CString num=_T("-1"),bool make_active=true);
	/** Делает версию проекта активной
	@param project версия проекта 
	@return true при удачном выполнении и false в случае ошибки */

	/** Делает версию проекта активной
	@param project версия проекта 
	@return true при удачном выполнении и false в случае ошибки */
	bool MakeProjectVersionActive(CaplInstance *project_ver);

	/** Проверяет наличие блокировки, и если такая есть возвращает на нее ссылку  
	@param project  проверяемый проект или его версия
	@return локер проекта,иначе 0 */
	CaplInstance *GetLock(CaplInstance *project, bool bShowMessages);
	
	/** Проверяет наличие блокировки текущим пользователем, и если такая есть возвращает на нее ссылку  */
	CaplInstance *CheckMyLock(CaplInstance *project, bool bShowMessages);


	// виртуальные, т.к. используются в классификаторах и назначении доступа 
	virtual bool ShowProjectProperties(CaplInstance *project,bool b_read_only=false){return true;};
	virtual CaplInstance *CreateProject(CaplInstance *base_project=0,const TCHAR id=0,bool add_to_contents=true,CaplInstance *item=0,CaplInstance **rel=0){return 0;};
	virtual bool InsertProjectIntoParent(CaplInstance *project,CaplInstance *parent_project,bool add_to_content=false){return true;};
	virtual void GetAllSubProject(aplExtent &project_ext,aplExtent &ext_out,bool recursive=false,bool include_associated=false,bool from_base=true){ext_out.Clear();return;}

public:
	CaplEntity* e_project;
	CaplAttr* a_project_id;
	CaplAttr* a_project_name;
	CaplAttr* a_project_descr;
	CaplAttr* a_project_descr2;
	CaplAttr* a_project_owner;
	CaplAttr* a_project_kurator;
	CaplAttr* a_project_executors;
	CaplAttr* a_project_co_executors;
	CaplAttr* a_project_co_customers;
	CaplAttr* a_project_prev_sequences;
	CaplAttr* a_project_customer;
	CaplAttr* a_project_date_planned_begin;
	CaplAttr* a_project_date_planned_end;
	CaplAttr* a_project_date_planned_end2;
	CaplAttr* a_project_date_planned_duration;
	CaplAttr* a_project_date_set_mask;
	CaplAttr* a_project_date_actual_begin;
	CaplAttr* a_project_date_actual_end;
	CaplAttr* a_project_date_actual_end2;
	CaplAttr* a_project_labor_useness;             // Плановая трудоемкость [ссылка на labor_useness_value, который value_component + unit_component]
	CaplAttr* a_project_labor_useness_actual;      // Фактическая трудоемкость [ссылка на labor_useness_value, который value_component + unit_component]
	CaplAttr* a_project_labor_useness_actual_date; // Дата задания фактической трудоемкость
	CaplAttr* a_project_labor_of_item;             // Трудоемкость единицы продукции  (при расчете по кол показателям) [ссылка на labor_useness_value]
	CaplAttr* a_project_persentage;
	CaplAttr* a_project_state;
	CaplAttr* a_project_parent;
	CaplAttr* a_project_content;
	CaplAttr* a_project_type;
	CaplAttr *a_project_prototype;
	CaplAttr *a_project_prd_amount_planned;         // Требемый объем продукции [real]  (при расчете по кол показателям)
	CaplAttr *a_project_prd_amount_actual;			// Выполненный объем продукции [real] (при расчете по кол показателям)
	CaplAttr *a_project_calc_by_amount;				// Рассчитывать трудоемкость и % выполнения по количественным показателям (Галочка ) [bool]
	CaplAttr *a_project_prd_amount_unit;			// Единица измерения объема продукции (при расчете по кол показателям)
	CaplAttr *a_project_control_type;
	CaplAttr *a_project_transactions;
	CaplAttr *a_project_number;

	CaplAttr *a_project_taken_measures;
	CaplAttr *a_project_payment_condition;
	CaplAttr *a_project_note1;
	CaplAttr *a_project_note2;
	CaplAttr *a_project_note3;
	
	CaplEntity* e_labor_useness_value;
	CaplAttr* a_labor_value;
	CaplAttr* a_labor_unit;
	
	CaplEntity* e_project_type;
	CaplAttr* a_project_type_name;
	
	/*Версии-------------------------------------------*/
	CaplAttr* a_project_act_adm_version;
	CaplAttr* a_project_locker_adm_version;
	CaplAttr* a_project_act_cont_version;
	CaplAttr* a_project_locker_cont_version;
	
	CaplEntity* e_project_adm_ver;
	CaplAttr* a_project_adm_ver_id;
	CaplAttr* a_project_adm_ver_name;
	CaplAttr* a_project_adm_ver_number;
	CaplAttr* a_project_adm_ver_descr;
	CaplAttr* a_project_adm_ver_type;
	CaplAttr* a_project_adm_ver_customer;
	CaplAttr* a_project_adm_ver_labor_useness;
	CaplAttr* a_project_adm_ver_labor_of_item;
	CaplAttr* a_project_adm_ver_persentage;
	CaplAttr* a_project_adm_ver_kurator;
	CaplAttr* a_project_adm_ver_executors;
	CaplAttr* a_project_adm_ver_co_executors;
	CaplAttr* a_project_adm_ver_co_customers;
	CaplAttr* a_project_adm_ver_prev_sequences;

	CaplAttr* a_project_adm_ver_date_planned_begin;
	CaplAttr* a_project_adm_ver_date_planned_end;
	CaplAttr* a_project_adm_ver_date_planned_end2;
	CaplAttr* a_project_adm_ver_date_planned_duration;
	CaplAttr* a_project_adm_ver_date_set_mask;
	CaplAttr* a_project_adm_ver_project;
	CaplAttr* a_project_adm_ver_num;
	CaplAttr *a_project_adm_ver_author;
	CaplAttr *a_project_adm_ver_start;
	CaplAttr *a_project_adm_ver_end;	
	CaplAttr *a_project_adm_ver_content;
	CaplAttr *a_project_adm_ver_parent;
	CaplAttr *a_project_adm_ver_basis;
	CaplAttr *a_project_adm_ver_prd_amount_planned;
	CaplAttr *a_project_adm_ver_prd_amount_unit;
	CaplAttr *a_project_adm_ver_calc_by_amount;
	CaplAttr *a_project_adm_ver_control_type;
	
	
	CaplEntity* e_project_cont_ver;
	CaplAttr* a_project_cont_ver_project;
	CaplAttr* a_project_cont_ver_num;
	CaplAttr* a_project_cont_ver_act_content;
	/*---------------------------------------------------*/

	/* Связи -------------------------------------------*/

	CaplEntity* e_project_ref;
	CaplAttr* a_project_ref_item;
	CaplAttr* a_project_ref_project;
	CaplAttr* a_project_ref_id;
	CaplAttr* a_project_ref_name;
	CaplAttr* a_project_ref_control_status;

	CaplEntity* e_project_seg;
	CaplAttr* a_project_seq_prev;
	CaplAttr* a_project_seq_next;
	CaplAttr* a_project_seq_type;
	CaplAttr* a_project_seq_offset;
	
	bool m_bShowMessages;
	int m_show_ass_projects;//показывать ассоциированные проекты, не включенные в основной состав проекта-родителя

	//Money Transaction
	CaplEntity* e_money_transaction;//транзакция
	CaplAttr* a_money_transaction_id;//номер счета (код, обозначение)
	CaplAttr* a_money_transaction_name;//наименование
	CaplAttr* a_money_transaction_descr;//описание
	CaplAttr* a_money_transaction_type;//тип
	CaplAttr* a_money_transaction_date;//дата
	CaplAttr* a_money_transaction_summ;//сумма
	CaplAttr* a_money_transaction_account;//счет
	CaplAttr* a_money_transaction_nds;//НДС в %
};
 
class AFX_EXT_CLASS CaplOptionsManager : public CaplStepManager 
{
public:
/** Инициализирует класс (Ассоциация с классом базы данных) <p>
	@return true при удачном выполнении и false в случае ошибки */
	bool Attach(CaplAPI *api);
	void Detach();
public:
	CaplEntity *e_str;
	CaplEntity *e_int;
	CaplEntity *e_inst;
	CaplEntity *e_ext;
	CaplEntity *e_double;
	CaplAttr *a_str_name;
	CaplAttr *a_str_value;
	CaplAttr *a_int_name;
	CaplAttr *a_int_value;
	CaplAttr *a_inst_name;
	CaplAttr *a_inst_value;
	CaplAttr *a_ext_name;
	CaplAttr *a_ext_value;
	CaplAttr *a_double_name;
	CaplAttr *a_double_value;
	/*---------------------------------------------------*/
	#define OPTION_TYPE_STRING 0x00000001
	#define OPTION_TYPE_INT 0x00000002

	bool m_bShowMessages;

	CaplStrMap m_params;
	CaplMap m_paterns;

protected:
	CString m_sInstallCode; // Значение опции "код установки" из БД в нижнем регистре

public:
	bool LoadDictionary();
	bool LoadOptionsInfo(CaplInstance *option);
	bool LoadOptionsInfo(aplExtent &ext);

	bool InitDefaultOptions();


	int GetCounterWithIncrementBN(const TCHAR *name); // Возвращает увеличенное на 1 значение счетчика из БД. Это значение записывает в БД.

	CaplInstance *FindOptionBN(const TCHAR *name);

	bool GetOptionValueBN(const TCHAR *name,CaplInstance **val, CaplInstance* DefVal = NULL);
	bool GetOptionValueBN(const TCHAR *name,CString &val,const TCHAR *def_value=_T(""));
	bool GetOptionValueBN(const TCHAR *name,int &val, int def_value=0);
	bool GetOptionValueBN(const TCHAR *name, aplExtent& val);
	bool GetOptionValueBN(const TCHAR *name,double &val, double def_value=0);
	int GetIntOptionValueBN(const TCHAR *name, int def_value);
	CaplInstance *GetInstOptionValueBN(const TCHAR *name, CaplInstance* DefVal = NULL);

	CaplInstance *CreateOption(const TCHAR *name,const TCHAR *value);
	CaplInstance *CreateOption(const TCHAR *name,int value);
	CaplInstance *CreateOption(const TCHAR *name,CaplInstance* value);
	CaplInstance *CreateOption(const TCHAR *name, aplExtent &ext);
	CaplInstance *CreateOption(const TCHAR *name, double value);
	CaplInstance *CreateOption(const TCHAR *name);
	
	bool ShowOptionProperties(CaplInstance *option);
	bool DeleteOption(CaplInstance *option);

	bool GetOptionName(CaplInstance *option, CString &name);
	bool WherePatternUsed(CString &pattern_name, CString &option_used);
	
	CaplInstance* GetDefPatern(CaplEntity* entity);
	BOOL GetDefTmplName(CaplEntity* entity, CString& sTmplName);
	BOOL GetDefPatern(CaplEntity* entity, CString& sPatern);

	bool SetPattern4AutoAccess();
	bool SetFirewallProperties();
	
	inline CString GetPdfSeriesOptionName() const;
	inline CString GetInventoryBookOrderFromOptionName() const;

	INT_PTR CreateDlgADProperties ();

	// Проверяет код установки (опция в БД).  Если совпадает с code - возвразает true. Иначе false
	// Код установки читается в LoadDictionary
	bool CheckInstallCode(LPCTSTR code);

	// Запускает диалог "Личные настройки"
	bool EditPersonalOptions();

	// Берет строчку и разделяет ее на части по символу "|".  
	bool DivideStringOptions(LPCTSTR str, CStringArray &strings);

	
	// Личные настройки сотрудника
	bool LoadPersonalOptionString(CString &sOptions, CaplInstance *person=0); // Читает персональные настройки из БД. Если 0==person, то у текущего
	bool SavePersonalOptionString(CString &sOptions); // Сохранякт персональные настройки в БД Только для текущего сотрудника

	int GetIntPersonalOptionValueBN(CString &sOptions, const TCHAR *name, int def_value); //Читает опцию из строчки
	bool SetIntPersonalOptionValueBN(CString &sOptions, const TCHAR *name, int value); //Читает опцию в строчку
	bool DeletePersonalOptionValueBN(CString &sOptions, const TCHAR *name); //Удаляет опцию из строчки

	// Читает из БД опцию для конкретного пользователя
	// Если опции нет - возвращает 0. Если 0==person, то для текущего
	int GetIntPersonOption(CaplInstance *person, LPCTSTR sOption); 
};

class CLASS_DECL_APL_STEP_MGR CaplFormManager : public CaplStepManager
{
protected:

	/** Комиляторы 2003 и 2005 студии не допускают параметров по умолчанию
		у callback функций...
	*/
	BOOL (*m_FShowFormI)(CaplAPI*, CaplInstance*,
		aplExtent& aeInInsts,aplExtent& aeOutInsts,
		aplExtent* aeChars,LPCTSTR csInstChg,
		CString csPath/*=""*/,
		BOOL bAutoSave/*=TRUE*/, BOOL bTst/*=FALSE*/,
		BOOL bHideAdd /*=FALSE*/);

public:
	CaplFormManager();

	/** Инициализирует класс (Ассоциация с классом базы данных) 
		@return true при удачном выполнении и false в случае ошибки */
	virtual bool			Attach(CaplAPI *api);
	virtual void			Detach();

	void					LoadData();
	BOOL					LoadInstAttrs(CaplInstance* cit);
	BOOL					LoadLockerAttrs(CaplInstance* ciLocker);
	BOOL					GetFormEntityName(CaplInstance* form,CString &entity_name);
	CaplInstance*			GetFormBN(LPCTSTR lpszName);
	bool					ShowForm(CaplInstance* form,
		aplExtent& aeInInsts, aplExtent& aeOutInsts, aplExtent* aeChars, LPCTSTR csInstChg,
							   CString csPath=_T(""), BOOL bAutoSave=TRUE, BOOL bTst=FALSE, BOOL bHideAdd=FALSE);
	inline bool				TestFormCompatible(CaplInstance* form,CString &test_entity_name);
	inline bool				TestFormCompatible(CaplInstance* form,CaplEntity *test_entity);

	CaplEntity*				e_form;
	CaplAttr*				a_form_name;
	CaplAttr*				a_form_width;
	CaplAttr*				a_form_height;
	CaplAttr*				a_form_instances;
	CaplAttr*				a_form_elements;
	CaplAttr*				a_form_active;
	CaplAttr*				a_form_locker;
	CaplAttr*				a_form_descr;
	
	CaplEntity*				e_form_revision;
	CaplAttr*				a_form_rev_id;
	CaplAttr*				a_form_rev_name;
	CaplAttr*				a_form_rev_width;
	CaplAttr*				a_form_rev_height;
	CaplAttr*				a_form_rev_start_date;
	CaplAttr*				a_form_rev_end_date;
	CaplAttr*				a_form_rev_author;
	CaplAttr*				a_form_rev_user;
	CaplAttr*				a_form_rev_of_form;
	CaplAttr*				a_form_rev_elements;
	CaplAttr*				a_form_rev_instances;
	CaplAttr*				a_form_rev_descr;
							
	CaplEntity*				e_form_instance;
	CaplAttr*				a_form_instance_base_instance;
	CaplAttr*				a_form_instance_base_instance_attr_name;
	CaplAttr*				a_form_instance_entity_name;
	CaplAttr*				a_form_instance_child_instances;
	CaplAttr*				a_form_instance_attrs;
	
	CaplEntity*				e_form_el_access;
	CaplAttr*				a_form_el_acc_type;
	CaplAttr*				a_form_el_acc_dis;
	CaplAttr*				a_form_el_acc_roles;
							
	CaplEntity*				e_form_element;
	CaplAttr*				a_form_element_point;
	CaplAttr*				a_form_element_cx;
	CaplAttr*				a_form_element_cy;
	CaplAttr*				a_form_element_text;
	CaplAttr*				a_form_element_form_instance;
	CaplAttr*				a_form_element_tab_order;
	CaplAttr*				a_form_element_is_req;
	CaplAttr*				a_form_element_access;
							
	CaplEntity*				e_characteristic_element;
	CaplAttr*				a_characteristic_element_characteristic;
	CaplAttr*				a_characteristic_element_characteristic_type;
							
	CaplEntity*				e_attr_element;
	CaplAttr*				a_attr_element_attr_name;
	CaplAttr*				a_attr_element_attr_id;
	CaplAttr*				a_attr_element_subst_form;
							
	CaplEntity*				e_text_element;
	CaplEntity*				e_frame_element;

	CaplEntity*				e_inst_select_element;
	CaplAttr*				a_inst_select_element_name;
	CaplAttr*				a_inst_select_element_instance_name;
	
	CaplEntity*				e_picture_element;
	CaplAttr*				a_pic_element_mode;
	CaplAttr*				a_pic_element_pic;

	CaplEntity*				e_chars_list_element;
	CaplAttr*				a_chars_list_element_name;
	CaplAttr*				a_chars_list_element_chars_list;	

};

class CLASS_DECL_APL_STEP_MGR CaplRequirementMgr : public CaplStepManager
{
protected:

public:
	//CaplRequirementMgr();

	/** Инициализирует класс (Ассоциация с классом базы данных) 
	@return true при удачном выполнении и false в случае ошибки */
	virtual bool			Attach(CaplAPI *api);
	virtual void			Detach();

	// загрузка всей информации о требовании
	bool LoadReqInfo(aplExtent &aeItems, bool bLoadDocuments = false);
	bool LoadReqInfo(CaplInstance *ciRequirement, bool bLoadDocuments = false);
	
	// редактирование требования
	bool ShowProperties(CaplInstance *ciRequirement);

	// удаление требования
	bool DeleteRequirement(CaplInstance *ciRequirement, bool bShowMsg = true, bool bSaveChanges = true);

	// добавить в требование информацию о родителе и верхнем родителе
	CaplInstance* AddChild(CaplInstance *ciParent, CaplInstance *ciChild);
	
	// создать требование
	CaplInstance* CreateRequirement(CaplInstance *ciParent = 0);

	// переносим требование в новое место
	bool MoveRequirement(CaplInstance *ciMoved, CaplInstance *ciTo);

	// есть ли у требования дочерние элементы
	bool RequirementHasChild(CaplInstance *ciRequirement);

	// уникально ли обозначение в пределах самого верхнего (корневого)
	bool IsRequirementUniqueId(CaplInstance *ciParent, CaplInstance *ciRequirement, CString sId);

	// замена ссылок на картинки в код html
	bool ReplaceReferenceInHTML(CString &html, CString oldSource, CString newSource);

	// создать требование с основными атрибутами без вывода диалога
	CaplInstance* CreateRequirementInderect(CaplInstance *ciParent, CString id, CString name, CString html);

	// импорт требований из XML, который был сформирован через Word 2003
	bool ImportRequirementsFromXMLword2003(aplExtent &aeRootItems, CString sPath = _T(""), CaplInstance *ciParent = 0);

	// получить неформатированный текст из текста HTML
	bool GetUnformattedTextFromHTML( CString &sText, CString sHTML );

	// получить все дочерние требования с загрузкой из базы
	void LoadChildsFromBase(CaplInstance *ciRequirement, aplExtent &aeChild, bool bRecursive);

	// получить все дочерние требования с загрузкой из кэша
	void LoadChildsFromCash(CaplInstance *ciRequirement, aplExtent &aeChild, bool bRecursive);

	// создать копию требования
	CaplInstance* CreateRequirementCopy(CaplInstance *ciRequirement);

	// копируем весь состав требования
	void CopyRequirementsRecursive(CaplInstance *ciParent, CaplInstance *ciParentCopy, CaplInstance *ciSource);

	// грузим только обозначения
	bool LoadRequirementId(aplExtent &aeItems);	 
	bool LoadRequirementId(CaplInstance *ciRequirement);

	// выгрузить требование в html
	bool ExportBasisToHTML(CaplInstance *ciRequirement, CString sPath = _T(""));

	// выгрузить перечень документов, ассоциированных с требованием и всеми его чалдовыми элементами
	bool ExportAssociatedDocumentsToHTML(CaplInstance *ciRequirement, CString sPath = _T(""));

	// запрашиваем путь к какому-либо файлу
	CString GetFilePath(BOOL open, CString sExtension, CString sFilter);

	// состояние только что созданного требования
	CString GetInitialRequirementState();

	// преобразует обозначение требования для дальнейшей нормальной сортировки требований
	CString ConvertForRequirementSort( CString str );

	// заменяет ссылки картинок на имена файлов
	bool SubstituteImgReferencesWithFilesNames(CString &html, CStringArray &saImgReferences);

	// создаем в указанной папке файлы, которые берем из базы по блобу
	bool CreateFilesByBlobs(CaplInstance *ciReq, CString sPath, CStringArray &saBlobsAndFileNames);

	// импорт Авиационных Правил Часть 25 из файла TXT, полученного конвертором из PDF
	bool ImportAP25FromTxt(aplExtent &aeRootItems, CaplInstance *ciRequirement, CString sPath = _T(""));

	// создать связь между требованием и элементом
	CaplInstance* CreateAssociation(CaplInstance *ciReq, CaplInstance *ciItem);

	// получить все требования, связанные с элементом
	bool FindAssociatedReqs(CaplInstance *ciItem, aplExtent &aeReq, aplExtent &aeAssoc, bool bLoadFromBase = true);

	// получить ассоциированные элементы
	bool FindAssociatedItems(CaplInstance *ciReq, aplExtent &aeItems, aplExtent &aeAssoc, bool bLoadFromBase = true);

	// у всех чалдовых (рекурсивно) поменять значения атрибутов на основе ciReq
	bool SetAttrForChilds(CaplInstance *ciReq);

protected:

	// вывод диалога с переключением ресурсов
	CaplInstance* ShowPropertiesDialog(CaplInstance *ciRequirement, CaplInstance *ciParent, CString &sVS, CString &sDeveloper);

	// перевод из кодировки UTF-8 в Win1251
	CString ConvertFromUTF8toWIN1251(CString sSource);

	// удалить все требования из базы
	bool DeleteAllRequirementFromBase();

	// получить чилдовые элементы
	void GetChildsRecursiveFromBase(aplExtent &aeParents, aplExtent &aeChild, bool bRecursive);

	// строим тело таблицы (сертификационного базиса)
	void BuildHTMLTable(CaplInstance *ciRequirement, CString &html);

	// получить чилдовые элементы
	void GetChildsRecursiveFromCash(aplExtent &aeParents, aplExtent &aeChild, bool bRecursive);

	// получаем обозначение требования из строки (первые цифры с точками)
	int GetRequirementIdLastIndex(CString str);

public:
	
	// атрибуты
	CaplEntity*				e_requirement;
	CaplAttr*    			a_req_state;
	CaplAttr*    			a_req_parent;
	CaplAttr*    			a_req_root_parent;
	CaplAttr*    			a_req_source;
	CaplAttr*    			a_req_id;
	CaplAttr*    			a_req_name;
	CaplAttr*    			a_req_html;
	CaplAttr*    			a_req_files;
	CaplAttr*    			a_req_no_need;
	CaplAttr*    			a_req_last_updated;
	CaplAttr*    			a_req_updated_person;
	CaplAttr*    			a_req_mos;
	CaplAttr*    			a_req_executor;
	CaplAttr*    			a_req_equivalence_date;
	CaplAttr*    			a_req_pictures;
	CaplAttr*    			a_req_developer;
	CaplAttr*    			a_req_vs;
	CaplAttr*				a_req_wf_state;
	CaplAttr*				a_req_notes;

	CaplEntity*				e_requirement_association;
	CaplAttr*				a_req_assoc_item;
	CaplAttr*				a_req_assoc_req;

	CaplEntity*  			e_requirement_stage;
	CaplAttr*    			a_req_stage_requirement;
	CaplAttr*    			a_req_stage_mos;
	CaplAttr*    			a_req_stage_project;
	CaplAttr*				a_req_cfg_oject;
};

class CLASS_DECL_APL_STEP_MGR CaplPreWMSManager : public CaplStepManager
{
public:
	CaplPreWMSManager();
	virtual ~CaplPreWMSManager();

	/** Инициализирует класс (Ассоциация с классом базы данных) 
	@return true при удачном выполнении и false в случае ошибки */
	virtual bool			Attach(CaplAPI *api);
	virtual void			Detach(); 
	 	
public:

	// атрибуты
	CaplEntity*		e_wms_tranzaction; 
	CaplAttr*		a_wms_tranz_source;
	CaplAttr*		a_wms_tranz_recipient;
	CaplAttr*		a_wms_tranz_type;
	CaplAttr*		a_wms_tranz_state;
	CaplAttr*		a_wms_tranz_priority;
	CaplAttr*		a_wms_tranz_items;
	CaplAttr*		a_wms_tranz_inner_moving_items;
	CaplAttr*		a_wms_tranz_last_update;
	CaplAttr*		a_wms_tranz_parent;
	CaplAttr*		a_wms_tranz_id;
	CaplAttr*		a_wms_tranz_descr;
	CaplAttr*		a_wms_tranz_project;
	CaplAttr*		a_wms_tranz_plan_date;
	CaplAttr*		a_wms_tranz_log;
	CaplAttr*		a_wms_tranz_last_edit;
	CaplAttr*		a_wms_tranz_last_planed;
	CaplAttr*		a_wms_tranz_last_reserved;
	CaplAttr*		a_wms_tranz_last_ready;
	CaplAttr*		a_wms_tranz_last_distribute;
	CaplAttr*		a_wms_tranz_last_accepted; 
	CaplAttr*		a_wms_tranz_last_closed; 
	CaplAttr*		a_wms_tranz_last_complect;
	CaplAttr*		a_wms_tranz_total_nds;
	CaplAttr*		a_wms_tranz_user_nds;
	CaplAttr*		a_wms_tranz_sum_with_nds;
	CaplAttr*		a_wms_tranz_user_sum_with_nds;
	CaplAttr*		a_wms_tranz_sum_without_nds;
	CaplAttr*		a_wms_tranz_user_sum_without_nds;
	CaplAttr*		a_wms_tranz_demand_ref;
	CaplAttr*		a_wms_tranz_transporter;
	CaplAttr*		a_wms_tranz_region;
	CaplAttr*		a_wms_tranz_doc_number;
	CaplAttr*		a_wms_tranz_doc_target;
	CaplAttr*		a_wms_tranz_doc_date;
	CaplAttr*		a_wms_tranz_doc2_number;
	CaplAttr*		a_wms_tranz_doc2_date;
	CaplAttr*		a_wms_tranz_doc3_number;
	CaplAttr*		a_wms_tranz_doc3_date;
	CaplAttr*		a_wms_tranz_doc3_type;
	CaplAttr*		a_wms_tranz_account;

	CaplAttr*		a_wms_tranz_ticket_number;
	CaplAttr*		a_wms_tranz_ticket_date;
	CaplAttr*		a_wms_tranz_expeditor;

	CaplAttr*		a_wms_tranz_purchase_schedule;
	CaplAttr*		a_wms_tranz_purchase_stage;
	CaplAttr*		a_wms_tranz_positions_allowing_state;
	CaplAttr*		a_wms_tranz_note;

	CaplEntity*		e_wms_tranzaction_item;
	CaplAttr*		a_wms_tranz_item_tranz;
	CaplAttr*		a_wms_tranz_item_parent;
	CaplAttr*		a_wms_tranz_item_pdf;
	CaplAttr*		a_wms_tranz_item_storage_source;
	CaplAttr*		a_wms_tranz_item_storage_recipient;
	CaplAttr*		a_wms_tranz_item_id;
	CaplAttr*		a_wms_tranz_item_count_plan;
	CaplAttr*		a_wms_tranz_item_count_fact;
	CaplAttr*		a_wms_tranz_item_prd_inst; 
	CaplAttr*		a_wms_tranz_item_lot;
	CaplAttr*		a_wms_tranz_item_cell;
	CaplAttr*		a_wms_tranz_item_confirm;
	CaplAttr*		a_wms_tranz_item_tot_quantity;
	CaplAttr*		a_wms_tranz_item_one_quantity;
	CaplAttr*		a_wms_tranz_item_massa;
	CaplAttr*		a_wms_tranz_item_cost;
	CaplAttr*		a_wms_tranz_item_nds;
	CaplAttr*		a_wms_tranz_item_sum_nds;
	CaplAttr*		a_wms_tranz_item_sum_with_nds;
	CaplAttr*		a_wms_tranz_item_sum_without_nds;
	CaplAttr*		a_wms_tranz_item_package;
	CaplAttr*		a_wms_tranz_item_acceptance;
	CaplAttr*		a_wms_tranz_item_release_date;
	CaplAttr*		a_wms_tranz_item_is_import;
	CaplAttr*		a_wms_tranz_item_unit;
	CaplAttr*		a_wms_tranz_item_provider_id;
	CaplAttr*		a_wms_tranz_item_remain;
	CaplAttr*		a_wms_tranz_item_dispatch;
	CaplAttr*		a_wms_tranz_item_card_number;
	CaplAttr*		a_wms_tranz_item_supplier_cost;
	CaplAttr*		a_wms_tranz_item_supplier_unit;
	CaplAttr*		a_wms_tranz_item_supplier_count;

	CaplAttr*		a_wms_tranz_item_delivery_doc_number;
	CaplAttr*		a_wms_tranz_item_delivery_doc_date;
	CaplAttr*		a_wms_tranz_item_self_cost;
	CaplAttr*		a_wms_tranz_item_prd_instances;
	CaplAttr*		a_wms_tranz_item_responsible;
	CaplAttr*		a_wms_tranz_item_description;

	CaplEntity*		e_wms_dispatch_info;
	CaplAttr*		a_wms_dispatch_waybill_item;
	CaplAttr*		a_wms_dispatch_count;

	CaplEntity*		e_wms_storage_item;
	CaplAttr*		a_wms_storage_item_pdf;
	CaplAttr*		a_wms_storage_item_available;
	CaplAttr*		a_wms_storage_item_ordered;
	CaplAttr*		a_wms_storage_item_reserved;
	CaplAttr*		a_wms_storage_item_last_update;
	CaplAttr*		a_wms_storage_item_org;
	CaplAttr*		a_wms_storage_item_unit;
	CaplAttr*		a_wms_storage_item_acc_type;
	CaplAttr*		a_wms_storage_item_transferred;
	CaplAttr*		a_wms_storage_item_ready;
	CaplAttr*		a_wms_storage_item_order_point;
	CaplAttr*		a_wms_storage_item_last_inv_count;
	CaplAttr*		a_wms_storage_item_last_inv;
	CaplAttr*		a_wms_storage_item_last_inv_item;
	CaplAttr*		a_wms_storage_item_opt_lot;
	CaplAttr*		a_wms_storage_item_base_provider;
	CaplAttr*		a_wms_storage_item_cost;
	CaplAttr*		a_wms_storage_item_min_order_volume;
	
	CaplEntity*		e_wms_cell;
	CaplAttr*		a_wms_cell_organization;
	CaplAttr*		a_wms_cell_id;
	CaplAttr*		a_wms_cell_zone;
	CaplAttr*		a_wms_cell_parent;
	CaplAttr*		a_wms_cell_type;
	CaplAttr*		a_wms_cell_weight;
	CaplAttr*		a_wms_cell_lenght_outter;
	CaplAttr*		a_wms_cell_width_outter;
	CaplAttr*		a_wms_cell_height_outter;
	CaplAttr*		a_wms_cell_lenght_inner;
	CaplAttr*		a_wms_cell_width_inner;
	CaplAttr*		a_wms_cell_height_inner;
	CaplAttr*		a_wms_cell_seats_number;
	CaplAttr*		a_wms_cell_authorized_products;
	CaplAttr*		a_wms_cell_zoom_scheem;

	CaplEntity*		e_wms_authorized_product;
	CaplAttr*		a_wms_ap_pdf;
	CaplAttr*		a_wms_ap_priority;

	CaplEntity*		e_wms_provider_item;
	CaplAttr*		a_wms_provider_item_pdf;
	CaplAttr*		a_wms_provider_item_org;
	CaplAttr*		a_wms_provider_item_price;
	CaplAttr*		a_wms_provider_item_unit;
	CaplAttr*		a_wms_provider_item_duration;
	CaplAttr*		a_wms_provider_item_id;
	CaplAttr*		a_wms_provider_item_priority;
	CaplAttr*		a_wms_provider_item_price_date;
	CaplAttr*		a_wms_provider_item_nds;

	CaplEntity*		e_wms_inner_moving_item;
	CaplAttr*		a_wms_inner_moving_item_item;
	CaplAttr*		a_wms_inner_moving_item_new_cell;
	CaplAttr*		a_wms_inner_moving_item_old_cell;
	CaplAttr*		a_wms_inner_moving_item_id;

	CaplEntity*		e_wms_demand_ref;
	CaplAttr*		a_wms_demand_ref_count;
	CaplAttr*		a_wms_demand_ref_item;
	CaplAttr*		a_wms_demand_ref_pdf;
	CaplAttr*		a_wms_demand_ref_project;

	CaplEntity*		e_wms_zoom_scheem;
	CaplAttr*		a_wms_zoom_scheem_objects;
	CaplAttr*		a_wms_zoom_scheem_cx;
	CaplAttr*		a_wms_zoom_scheem_cy;

	CaplEntity*		e_wms_zoom_scheem_object;
	CaplAttr*		a_wms_zoom_scheem_object_cell;

	CaplEntity*		e_wms_zoom_scheem_rect_object;
	CaplAttr*		a_wms_rect_object_x;
	CaplAttr*		a_wms_rect_object_y;
	CaplAttr*		a_wms_rect_object_cx;
	CaplAttr*		a_wms_rect_object_cy;

	CaplEntity*		e_wms_zoom_scheem_triangle_object;
	CaplAttr*		a_wms_triangle_object_direction;
	CaplAttr*		a_wms_triangle_object_entrance;

	CaplEntity*		e_wms_zoom_scheem_way_object;
	CaplAttr*		a_wms_way_object_points;

	CaplEntity*		e_wms_change_state_log;
	CaplAttr*		a_wms_change_state_log_tranzaction;
	CaplAttr*		a_wms_change_state_log_person;
	CaplAttr*		a_wms_change_state_log_person_organization;
	CaplAttr*		a_wms_change_state_log_date;
	CaplAttr*		a_wms_change_state_log_from_state;
	CaplAttr*		a_wms_change_state_log_to_state;
};

/** Отображает диалог состава изделия
	@param api класс базы данных
	@param pdf версия издедия, состав которого надо отобразить
	@param mode отображать полный (если 1) или подетальный (если 0) состав. Если -1, то
		режим отображения состава выбирается пользователем
	@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
bool AFX_EXT_API DoShowContentsDialog(CaplAPI *api,CaplInstance *pdf=0,int mode=-1);

/** Отображает диалог выбора подмножества из некоторого списка елементов (например,
			списка отображаемых характеристик)
	@param columns массив заголовков столбцов для элементов списка
	@param items массив структур, каждая  которых содержит строчку списка
	@param mask массив индексов выбранных строк списка 
	@param dialog_name заголовок диалога
	@param left_name имя области выбранных элементов
	@param right_name имя области еще не выбранных элементов
	@return <b>true<\b> при удачном выполнении и <b>false<\b> в случае ошибки*/
bool AFX_EXT_API DoChooseCharacteristicsDlg(CStringArray *columns,
			CaplTAggr<CStringArray*,CStringArray*,APLAGGR_AUTOKILLREF|APLAGGR_LIST> *items,
			CUIntArray *mask,CString dialog_name=_T(""),CString left_name=_T(""),CString right_name=_T(""));

/** Отображает таблицу всех аттрибутов заданных объектов; позволяет выбрать наличие и порядок столбцов атрибутов
		а так же просмотреть характеристики заданных объектов
	@param api класс базы данных
	@param ext список объектов для отображения
	@param is_hide_move_button если <b>true<\b>, то скрыть кнопку "отобразить в дереве"
	@param res_move если была нажата кнопка "отобразить в дереве", то возвращает true
	@param can_delete если <b>true<\b>, то в контекстном меню доступен пункт "удалить из списка"
	@param id_changed если состав был изменен с попощью пункта контекстного меню "удалить из списка", то <b>true<\b>
	@param delete_message текст предупреждения, который выводится при выборе пункта контекстного меню "удалить из списка"
	@return true<\b> при удачном выполнении и false<\b> в случае ошибки*/
bool AFX_EXT_API MakeInstListTable(CaplAPI *api,aplExtent *ext,
								   bool is_hide_move_button,bool *res_move=0,
								   bool can_delete=false,bool *id_changed=0,CString *delete_message=0,bool is_context_menu_categ = false);
/*
bool AFX_EXT_API MakeNIIAOFindResult(CaplAPI *api,aplExtent *ext,
								   bool is_hide_move_button,bool *res_move=0);
*/

/** Отображает таблицу анализа групп объектов pdf-pi-bpi; позволяет выбрать наличие и порядок столбцов атрибутов
		а так же просмотреть характеристики заданных объектов
	@param api класс базы данных
	@param ext список объектов для отображения
	@return true<\b> при удачном выполнении и false<\b> в случае ошибки* /
bool AFX_EXT_API AnalizeGroupInstances(CaplAPI *api,CaplInstance *basic=0);
*/

CaplInstance AFX_EXT_API *aplSelectPrdInst(CaplInstance* Pdf_or_PrdInst, CaplAPI* api,
							   CStringArray* FName = NULL, CStringArray *FId = NULL, CStringArray *FVer = NULL, CStringArray *FSN = NULL,
							   bool bNFN = true, bool bNFI = true, bool bNFV = true, bool bNFS = true);

bool AFX_EXT_API LoadInstanceTree(CaplInstance *inst, aplExtent &array,CaplExchangeManager* exch_mgr=0);


/** Отображает таблицу всех шаблонов доступа; позволяет создавать, изменять, удалять шаблоны доступа
	@param api класс базы данных*/
void AFX_EXT_API EditAccessPattern(CaplAPI *m_api);

/** Отображает таблицу всех шаблонов доступа; позволяет выбрать шаблон доступа
	@param api класс базы данных
	@param curr_pattern текущий выделенный шаблон доступа
	@return выбранный шаблон доступа или 0 если шаблон не был выбран (нажата кнопка Cancel)*/
CaplInstance AFX_EXT_API *SelectAccessPattern(CaplAPI *m_api,CaplInstance *curr_pattern=0);

/** создание фрейма для работы с классификаторами*/
CMDIChildWnd AFX_EXT_API *aplCreateClassifiersFrame(CMDIFrameWnd *pMainFrame, CaplAPI* api, CaplInstance *Classifier, UINT nFrameResourceID);

/** создание child фрейма для формы поиска версии изделия и его результатами*/
CMDIChildWnd AFX_EXT_API *aplCreateQueryFrame(CMDIFrameWnd *pMainFrame, CaplAPI* api, UINT nFrameResourceID);
/** создание сплиттера для формы поиска версии изделия и его результатами */
CSplitterWnd AFX_EXT_API *aplCreateQuerySplitter(CWnd* pParentWnd, CaplAPI* api, CCreateContext *pContext);


void AFX_EXT_API aplShowAboutDlg(CaplAPI *api, const TCHAR* text, const TCHAR* title = NULL, HICON logo_icon = NULL);

int AFX_EXT_API aplErrorMessage(const TCHAR* message,CaplInstance* inst=0);

bool AFX_EXT_API aplShowFilterDlg(CaplAPI *api, LPCTSTR StringNameQuery, long vis_mode, CaplDataBuf &filter_query_buf, 
									CString &out_extents, CString &out_fields, CString &out_descrtiption, CString &stepql_query);