#define _CRT_SECURE_NO_WARNINGS
#include "epm_handler_common.h"

static void replace_design_representation(tag_t partRevTag, tag_t oldDesignRevTag, tag_t newDesignRevTag)
{
	int ifail = ITK_ok;

	tag_t priDesRepTypeTag = NULLTAG;
	ifail = GRM_find_relation_type("TC_Primary_Design_Representation",
		&priDesRepTypeTag);
	if (ifail != ITK_ok) {/*  your error logic here  */ }

	//tag_t isRepByTypeTag = NULLTAG;
	//ifail = ifail = GRM_find_relation_type("TC_Is_Represented_By",
	//	&isRepByTypeTag);
	//if (ifail != ITK_ok) {/*  your error logic here  */ }

	ifail = AOM_refresh(partRevTag, TRUE);
	if (ifail != ITK_ok) {/*  your error logic here  */ }

	ifail = AOM_refresh(oldDesignRevTag, TRUE);
	if (ifail != ITK_ok) {/*  your error logic here  */ }

	ifail = ifail = AOM_refresh(newDesignRevTag, TRUE);
	if (ifail != ITK_ok) {/*  your error logic here  */ }

	tag_t relationTag = NULLTAG;
	ifail = GRM_find_relation(partRevTag, oldDesignRevTag, priDesRepTypeTag,
		&relationTag);
	if (ifail != ITK_ok) {/*  your error logic here  */ }

	ifail = GRM_delete_relation(relationTag);
	if (ifail != ITK_ok) {
		printf("删除TC_Primary_Design_Representation关系失败 \r\n");
	}

	//relationTag = NULLTAG;
	//ifail = GRM_find_relation(partRevTag, oldDesignRevTag, isRepByTypeTag,
	//	&relationTag);
	//if (ifail != ITK_ok) {/*  your error logic here  */ }

	//ifail = GRM_delete_relation(relationTag);
	if (ifail != ITK_ok) {/*  your error logic here  */ }
	printf("添加TC_Primary_Design_Representation关系 \r\n");
	relationTag = NULLTAG;
	ifail = GRM_create_relation(partRevTag, newDesignRevTag, priDesRepTypeTag,
		NULLTAG, &relationTag);
	ifail = GRM_save_relation(relationTag);
	if (ifail != ITK_ok) {
		printf("添加TC_Primary_Design_Representation关系失败 \r\n");
	}

	//printf("添加TC_Is_Represented_By关系 \r\n");
	//relationTag = NULLTAG;
	//ifail = GRM_create_relation(partRevTag, newDesignRevTag, isRepByTypeTag,
	//	NULLTAG, &relationTag);
	//ifail = GRM_save_relation(relationTag);

	ifail = ifail = AOM_save(partRevTag);
	if (ifail != ITK_ok) {/*  your error logic here  */ }

	ifail = AOM_save(oldDesignRevTag);
	if (ifail != ITK_ok) {/*  your error logic here  */ }

	ifail = ifail = AOM_save(newDesignRevTag);
	if (ifail != ITK_ok) {/*  your error logic here  */ }

	ifail = ifail = AOM_refresh(partRevTag, FALSE);
	if (ifail != ITK_ok) {/*  your error logic here  */ }

	ifail = AOM_refresh(oldDesignRevTag, FALSE);
	if (ifail != ITK_ok) {/*  your error logic here  */ }

	ifail = ifail = AOM_refresh(newDesignRevTag, FALSE);
	if (ifail != ITK_ok) {/*  your error logic here  */ }
}

int ML_ItemRevUpdate(METHOD_message_t* msg, va_list args)
{
	printf("=========================版本修订 Start===================\n");
	int ifail = ITK_ok;
	tag_t old_rev = va_arg(args, tag_t);//要修订的旧版本
	char*  operation = va_arg(args, char*);//rev_id
	tag_t* new_rev = va_arg(args, tag_t*);//修订后的新版本

	printf("operation：%s\n", operation);

	int n_references = 0;
	int *levels = 0;
	tag_t * references_tag = NULLTAG;
	char ** relation_type_name = NULL;
	//通过引用关系查找到变更单
	WSOM_where_referenced(old_rev, 1, &n_references, &levels, &references_tag, &relation_type_name);
	for (int i = 0; i < n_references; i++)
	{
		char *itemType = NULL;
		tag_t spec_relation = NULLTAG, relation = NULLTAG;

		AOM_ask_value_string(references_tag[i], "object_type", &itemType);
		printf("type_class : %s \r\n", itemType);

		if (strcmp(itemType, "ML8_CNoticeRevision") == 0 || strcmp(itemType, "ML8_CDocumentRevision") == 0 || strcmp(itemType, "ML8_MCNoticeRevision") == 0)
		{
			//添加到更改前属性中
			//先lock
			AOM_lock(references_tag[i]);

			//获取关系类型
			GRM_find_relation_type("ML8_GXBGH", &spec_relation);
			//创建关系，在没有做关联的时候
			GRM_create_relation(references_tag[i], new_rev[0], spec_relation, NULLTAG, &relation);
			GRM_save_relation(relation);
			//再save
			AOM_save(references_tag[i]);
			//最后unlock
			AOM_unlock(references_tag[i]);
			AOM_refresh(references_tag[i], FALSE);
		}
		//if (strcmp(itemType, "ML8_MCNoticeRevision") == 0)
		//{
		//	//添加到更改前属性中
		//	//先lock
		//	AOM_lock(references_tag[i]);

		//	//获取关系类型
		//	GRM_find_relation_type("ML8_MCBGH", &spec_relation);
		//	//创建关系，在没有做关联的时候
		//	GRM_create_relation(references_tag[i], new_rev[0], spec_relation, NULLTAG, &relation);
		//	GRM_save_relation(relation);
		//	//再save
		//	AOM_save(references_tag[i]);
		//	//最后unlock
		//	AOM_unlock(references_tag[i]);
		//	AOM_refresh(references_tag[i], FALSE);
		//}
		DOFREE(itemType);
	}

	char * objectType = NULL;
	AOM_ask_value_string(old_rev, "object_type", &objectType);
	printf("objectType : %s \r\n", objectType);

	POM_AM__set_application_bypass(TRUE);
	if (strcmp(objectType, "ML8_DesignRevision") == 0)
	{
		//获取representation_for下的对象
		int num = 0;
		tag_t * tags = NULLTAG;
		DESIGN_rev_ask_associated_part_revs(old_rev, &num, &tags);
		printf("part数量 : %d \r\n", num);
		
		for (int i = 0; i < num; i++)
		{
			AOM_lock(tags[i]);
			AOM_lock(new_rev[0]);
			tag_t rel = NULLTAG;
			PART_rev_associate_design_rev(tags[i], new_rev[0], &rel);
			AOM_unlock(tags[i]);
			AOM_unlock(new_rev[0]);
			AOM_save(tags[i]);
			AOM_save(new_rev[0]);
			AOM_refresh(tags[i], false);
			AOM_refresh(new_rev[0], false);



			//替换TC_Primary_Design_Representation
			//replace_design_representation(tags[i], old_rev, new_rev[0]);

			printf("添加PART成功!");

		}
		DOFREE(tags);
	}
	else if (strcmp(objectType, "ML8_RefrigeratorRevision") == 0 || strcmp(objectType, "ML8_WashingRevision") == 0 || strcmp(objectType, "ML8_ColdRevision") == 0
		|| strcmp(objectType, "ML8_OthersRevision") == 0 || strcmp(objectType, "ML8_PartRevision") == 0)
	{
		//获取representation_for下的对象
		int num = 0;
		tag_t * tags = NULLTAG;
		AOM_ask_value_tags(old_rev, "TC_Is_Represented_By", &num, &tags);

		for (int i = 0; i < num; i++)
		{
			AOM_lock(tags[i]);
			AOM_lock(new_rev[0]);
			tag_t rel = NULLTAG;
			PART_rev_associate_design_rev(new_rev[0], tags[i], &rel);
			AOM_unlock(tags[i]);
			AOM_unlock(new_rev[0]);
			AOM_save(tags[i]);
			AOM_save(new_rev[0]);
			AOM_refresh(tags[i], false);
			AOM_refresh(new_rev[0], false);
/*

			int designNum = 0;
			tag_t * designTags = NULLTAG;
			DESIGN_rev_ask_associated_part_revs(tags[i], &designNum, &designTags);
			designTags[designNum + 1] = new_rev[0];

			AOM_lock(tags[i]);
			AOM_set_value_tags(tags[i], "representation_for", designNum + 1, designTags);
			AOM_unlock(tags[i]);
			AOM_save(tags[i]);
			AOM_refresh(tags[i], false);
			DOFREE(designTags);*/
		}

		DOFREE(tags);
	}

	POM_AM__set_application_bypass(FALSE);

	DOFREE(operation);
	DOFREE(new_rev);
	DOFREE(references_tag);
	DOFREE(levels);

	printf("=========================版本修订 End===================\n");
	return ifail;
}






/**
* 判断俩入参是否同源
*/
bool isTypeOf1(tag_t objtag, const char* type_name) {
	tag_t type = NULLTAG;
	TCTYPE_ask_object_type(objtag, &type);
	tag_t item_type = NULLTAG;
	TCTYPE_find_type(type_name, "", &item_type);
	bool is_type = false;
	if (item_type != NULLTAG) {
		logical isok = FALSE;
		TCTYPE_is_type_of(type, item_type, &isok);
		if (isok) {
			is_type = true;
		}
	}
	return is_type;
}
/**
* @brief 根据不确定类型的tag_t对象，获取item和itemRev对象
* @param check_tag
* @param item_tag
* @param rev_tag
* @return
*/
int get_item_and_rev(tag_t check_tag, tag_t* item_tag, tag_t* rev_tag) {
	int ifail = ITK_ok;
	if (isTypeOf1(check_tag, "Item")) {
		printf("====当前处理的对象是item对象！\n");
		*item_tag = check_tag;
		ITEM_ask_latest_rev(*item_tag, rev_tag);
	}
	else if (isTypeOf1(check_tag, "ItemRevision")) {
		printf("====当前处理的对象是Revision对象！\n");
		*rev_tag = check_tag;
		ITEM_ask_item_of_rev(*rev_tag, item_tag);
	}
	return ifail;
}
/*
* @brief 根据选中文件夹所在项目为创建的对象、文件夹自动指派项目
* @param msg
* @param args
* @return
*/
int ML_Automatic_Assignment_Item(METHOD_message_t* msg, va_list va) {
	printf("=========================自动指派项目 Start===================\n");
	printf("成功触发[自动指派项目]方法！\n");
	int ifail = ITK_ok;
	const char* item_id = va_arg(va, const char*);
	const char* item_name = va_arg(va, const char*);
	const char* item_type = va_arg(va, const char*);
	const char* rev_id = va_arg(va, const char*);
	//tag_t create_tag = va_arg(va, tag_t);
	tag_t* create_tag = va_arg(va, tag_t*);//创建后的对象
	tag_t projects[1] = { *create_tag };
	tag_t folder_tag = NULLTAG;
	//char* type = NULL;
	int url_num = 0;
	char** url_vals = NULL;
	int* getrenums, referNum;
	tag_t* renum;
	char** retags;
	int count = 0;
    tag_t* tags;

	//获取创建对象的类型
	printf("item_id=%s\n", item_id);
	printf("item_name=%s\n", item_name);
	printf("item_type=%s\n", item_type);
	printf("rev_id=%s\n", rev_id);

	//获取首选项中的数据，判断新建对象是否其中之一
	ITKCALL(ifail = PREF_ask_char_values("ML_AutoAssignProject_ObjectType", &url_num, &url_vals));
	if (url_num > 0) {
		printf("获取首选项-ML_AutoAssignProject_ObjectType成功！其中包含的对象类型有：\n");
		for (int i = 0; i < url_num; i++) {
			printf("==> %s\n", url_vals[i]);
		}

		if (item_type != NULL) {
			printf("当前创建的对象类型item_type=%s\n", item_type);
			for (int i = 0; i < url_num; i++) {
				if (strcmp(item_type, url_vals[i]) == 0) {//如果新建对象类型与首选项中的类型一致，则自动指派项目
					printf("当前创建的对象类型item_type=%s，与首选项中的类型一致，开始自动指派项目···\n", item_type);
					//引用者总数，层级数组，引用者数组，引用关系数组
					ITKCALL(ifail = WSOM_where_referenced2(*create_tag, 1, &referNum, &getrenums, &renum, &retags));
					if (referNum > 0) {
                        printf("成功获取到新建对象的关联对象（for：获取新建对象的所在文件夹）数量：referNum=%d\n", referNum);


						for(int j = 0; j < referNum; j++){
							char* refType = NULL;
							ITKCALL(ifail = AOM_ask_value_string(renum[j], "object_type", &refType));
							printf("获得的当前引用者类型：==>%s\n", refType);
							//获取新建对象的文件夹对象
                            if (isTypeOf1(renum[j], "Folder")) {
								printf("success->获取到文件夹对象\n");
								folder_tag = renum[j];
								//获取文件夹所在项目
								ITKCALL(ifail = AOM_ask_value_tags(folder_tag, "project_list", &count, &tags));
								printf("文件夹所在项目数量：%d，开始指派项目···\n", count);
								if (count > 0) {
									//for (int k = 0; k < count; k++) {
									//	//给新建对象指派项目
									//	tag_t project_tag = tags[k];
									//	printf("成功获取到文件夹所在项目\n");
									//	//PROJ_assign_objects
									//	
									//}
									ITKCALL(ifail = PROJ_assign_objects(count, tags, 1, projects));
									if (ifail == ITK_ok) {
										printf("成功指派项目！\n");
									}
									else
									{
										printf("指派项目失败！\n");
									}
								}
								else
								{
									printf("所在文件夹未指派到任何项目！\n");
								}
								MEM_free(tags);
								break;
							}
						}
					}
					else
					{
						printf("未获取到创建对象的文件夹！\n");
					}
					MEM_free(retags);
					MEM_free(renum);
					MEM_free(getrenums);
					break;
                }
			}
		}
		else
		{
			printf("未获取到创建对象的类型！\n");
		}
	}else {
		printf("首选项中未获取到对象类型！\n");
	}
	MEM_free(url_vals);
	//MEM_free(type);
    return ifail;
}