1С:Предприятие 8.3 (8.3.18.1208) 64
Firebird Server 3.07 64
Возникла необходимость сделать базу данных не в 1с. Выбрал Firebird.
СтрокаСоединения ="DRIVER={Firebird/InterBase(r) driver};CHARSET=utf8;UID=SYSDBA;PWD=masterkey;DBNAME=" + объект.ИмяФайлаБазы;
// Создаем соединение
мСоединение=Новый COMОбъект("ADODB.Connection");
мСоединение.ConnectionString=СтрокаСоединения;
Попытка
мСоединение.Open(мСоединение.ConnectionString);
ПоказатьОповещениеПользователя("ОК",,"Соединение успешно установлено!");
Исключение
Сообщить("Ошибка при установке соединения: "+ОписаниеОшибки());
мСоединение=Неопределено;
КонецПопытки;
Command = Новый COMОбъект("ADODB.Command");
RecordSet = Новый COMОбъект("ADODB.RecordSet");
Имена в БД английские. Сделал соответствие русских названий и английских(Имена таблиц и реквизитов).
// Перевод метаданных на английский язык для создания БД
&НаКлиенте
Процедура ТаблицаДобавить(Англ, Рус)
стр = Объект.ТаблицыБДшаблон.Добавить();
стр.ИмяАнгл = Англ;
стр.ИмяРус = Рус;
КонецПроцедуры
&НаКлиенте
Процедура РеквизитДобавить(Англ, Рус)
стр = Объект.РеквизитыШаблон.Добавить();
стр.ИмяАнгл = Англ;
стр.ИмяРус = Рус;
КонецПроцедуры
&НаКлиенте
Процедура ИнициализацияДанных() Экспорт
// Таблицы для создания БД порядок играет роль на загрузку в другие базы 1С.
// Сперва выгружаются простые таблицы.
ТаблицаДобавить( "Departments" , "Подразделения");
ТаблицаДобавить( "Employees" , "Сотрудники");
ТаблицаДобавить( "Posts" , "Должности");
ТаблицаДобавить( "Employment" , "ПриемНаРаботу");
ТаблицаДобавить( "TransferEmployee", "ПереводСотрудника");
// Реквизиты для создания БД
стр = Объект.РеквизитыШаблон.Добавить();
стр.ИмяАнгл = "ID";
стр.ИмяРус = "Ссылка";
стр.тип = "строка(36)";
РеквизитДобавить("Cod" , "Код");
РеквизитДобавить("DateDoc" , "Дата");
РеквизитДобавить("NumberDoc" , "Номер");
РеквизитДобавить("Name" , "Наименование");
РеквизитДобавить("Department" , "Подразделение");
РеквизитДобавить("Post" , "Должность");
РеквизитДобавить("Period" , "Период");
РеквизитДобавить("Summa" , "Сумма");
КонецПроцедуры
Вывел на основании метаданных таблицы и реквизиты для генерации SQL запроса на создание таблиц, индексов, внешних ключей.
// Создадим запрос на создание таблицы в БД
&НаКлиенте
Функция СоздатьSQL(таблица, Реквизиты)
sql = "RECREATE TABLE " + таблица.ИмяАнгл +"(";
Для каждого стрРеквизит из Реквизиты Цикл
тип = стрРеквизит.тип;
Если Найти(стрРеквизит.тип, "VARCHAR")+ Найти(стрРеквизит.тип, "DATE")+
Найти(стрРеквизит.тип, "DOUBLE PRECISION") + Найти(стрРеквизит.тип, "BOOLEAN NOT NULL") = 0 Тогда
тип = "VARCHAR(36)";
стрРеквизит.SQL_indexFK="";
Если стрРеквизит. ИмяАнгл <> "ID" тогда
стрРеквизит.SQL_indexFK = "ALTER TABLE " + таблица.ИмяАнгл + " add FOREIGN KEY (" +стрРеквизит. ИмяАнгл+") REFERENCES " + стрРеквизит.ТИП + " (ID);" ;
Конецесли;
Конецесли;
sql =sql + "
| " + стрРеквизит. ИмяАнгл + " " + тип +",";
Если стрРеквизит.индексировать и стрРеквизит. ИмяАнгл <> "ID" Тогда
стрРеквизит.SQL_index = "CREATE INDEX " +таблица.ИмяАнгл + "_" + стрРеквизит. ИмяАнгл+ "_IDX ON " +таблица.ИмяАнгл + " (" + стрРеквизит. ИмяАнгл+ ");"
КонецЕсли;
КонецЦикла;
sql =sql +"
| CONSTRAINT """ + таблица.ИмяАнгл + "_PK"" PRIMARY KEY (ID)
|);";
таблица.SQL_Create = sql;
КонецФункции
Сделал выгрузку в JSON сгенерированных таблиц.
&НаСервере
Функция ВыгрузкаЗапрос(имятаблицы, Тип, имяТЧ, имявладельца)
ПараметрыОтбора = Новый Структура;
ПараметрыОтбора.Вставить("Таблица", имятаблицы);
ПараметрыОтбора.Вставить("отметка", Истина);
реквизиты = Объект.Реквизиты.НайтиСтроки(ПараметрыОтбора);
Запрос = Новый Запрос;
//реквизиты
Если тип = "Справочник" или тип = "Документ" Тогда
Запрос.Текст ="
|ВЫБРАТЬ
| " + тип + имятаблицы + ".Ссылка" +",";
Для каждого стрРеквизит из Реквизиты Цикл
Запрос.Текст = Запрос.Текст + "
| " + тип +имятаблицы + "." +стрРеквизит.ИмяРус + ",";
КонецЦикла;
ИначеЕсли тип = "ТабличнаяЧасть" Тогда
// имятаблицы = Стрзаменить(имятаблицы,имяТЧ,"");
Запрос.Текст ="
|ВЫБРАТЬ
| " + имятаблицы + ".Ссылка" +",";
Для каждого стрРеквизит из Реквизиты Цикл
если стрРеквизит.ИмяРус = "ключ" Тогда продолжить конецесли;
Запрос.Текст = Запрос.Текст + "
| " + имятаблицы + "." +стрРеквизит.ИмяРус + ",";
КонецЦикла;
КонецЕсли;
Запрос.Текст = лев(Запрос.Текст, стрдлина(Запрос.Текст)-1);
//таблица
Если тип = "Справочник" или тип = "Документ" Тогда
Запрос.Текст = Запрос.Текст +"
|ИЗ
| " + Тип+"." + имятаблицы + " КАК " + тип + имятаблицы + "
|ГДЕ";
ИначеЕсли тип = "ТабличнаяЧасть" Тогда
имятаблицы1 = Стрзаменить(имятаблицы,имяТЧ,"");
Запрос.Текст = Запрос.Текст +"
|ИЗ
| " + имявладельца+"." + имяТЧ + "." + имятаблицы1 +" КАК " + имятаблицы + "
|ГДЕ";
КонецЕсли;
// отборы
Если тип = "Справочник" Тогда
Запрос.Текст = Запрос.Текст +"
| " + тип + имятаблицы +".ПометкаУдаления = ЛОЖЬ";
ИначеЕсли тип = "Документ" Тогда
Запрос.Текст = Запрос.Текст +"
| " + тип + имятаблицы +".Проведен >= Истина
| и " + тип + имятаблицы +".Дата >= &ДатаНачало
| и " + тип + имятаблицы +".Дата <= &ДатаОкончание";
ИначеЕсли тип = "ТабличнаяЧасть" Тогда
Запрос.Текст = Запрос.Текст +"
| " + имятаблицы + ".Ссылка.Проведен >= Истина
| и " + имятаблицы + ".Ссылка.Дата >= &ДатаНачало
| и " + имятаблицы + ".Ссылка.Дата <= &ДатаОкончание";
КонецЕсли;
Запрос.Параметры.Вставить("ДатаНачало",Объект.ДатаНачало);
Запрос.Параметры.Вставить("ДатаОкончание",КонецДня(Объект.ДатаОкончание));
РезультатЗапроса = Запрос.Выполнить();
ВыборкаДетальныеЗаписи = РезультатЗапроса.Выбрать();
мас1 = новый Массив;
Пока ВыборкаДетальныеЗаписи.Следующий() Цикл
струк = Новый Структура;
Для каждого стрРеквизит из Реквизиты Цикл
Если Найти(стрРеквизит.тип, "DATE") >0 Тогда
струк.Вставить(стрРеквизит.ИмяРус,Формат(ВыборкаДетальныеЗаписи[стрРеквизит.ИмяРус],"ДФ=dd.MM.yyyy"));
ИначеЕсли Найти(стрРеквизит.тип, "DOUBLE PRECISION")+ Найти(стрРеквизит.тип, "BIGINT") >0 Тогда
струк.Вставить(стрРеквизит.ИмяРус, стрзаменить(строка(ВыборкаДетальныеЗаписи[стрРеквизит.ИмяРус]),Символы.НПП,""));
ИначеЕсли Найти(стрРеквизит.тип, "перечисление") > 0 Тогда
струк.Вставить(стрРеквизит.ИмяРус, строка(ВыборкаДетальныеЗаписи[стрРеквизит.ИмяРус]));
ИначеЕсли Найти(стрРеквизит.тип, "VARCHAR") + Найти(стрРеквизит.тип, "BOOLEAN NOT NULL") = 0 Тогда
струк.Вставить(стрРеквизит.ИмяРус, строка(ВыборкаДетальныеЗаписи[стрРеквизит.ИмяРус].УникальныйИдентификатор()));
Иначе
если стрРеквизит.ИмяРус="ключ" Тогда продолжить КонецЕсли;
струк.Вставить(стрРеквизит.ИмяРус, ВыборкаДетальныеЗаписи[стрРеквизит.ИмяРус]);
КонецЕсли;
КонецЦикла;
мас1.Добавить(струк);
КонецЦикла;
возврат мас1;
КонецФункции
&НаКлиенте
Процедура ВыгрузкаJSON(Таблица)
параметрыЗаписиJSON = Новый ПараметрыЗаписиJSON(,символы.Таб);
мас1 = ВыгрузкаЗапрос(Таблица.Имярус, Таблица.Тип, Таблица.ВладелецРус, таблица.типвладельца);
ЗаписьJSON = Новый ЗаписьJSON;
ЗаписьJSON.ОткрытьФайл(Объект.Каталог + строка(Таблица.НомерСтроки)+ Таблица.Имярус + ".json","UTF-8",,параметрыЗаписиJSON);
ЗаписьJSON.ЗаписатьНачалоОбъекта();
ЗаписьJSON.ЗаписатьИмяСвойства(Таблица.Имярус);
ЗаписатьJSON(ЗаписьJSON,мас1);
ЗаписьJSON.ЗаписатьКонецОбъекта();
ЗаписьJSON.Закрыть();
КонецПроцедуры
В Firebird создал описания таблиц(mdTable) и реквизитов(mdrekvizit)
&НаКлиенте
Функция СоздатьМетаданныеТаблица()
возврат "
|RECREATE TABLE MDTABLE (
| NAMEENGL VARCHAR(100),
| NAMERUS VARCHAR(100),
| SYNONYM VARCHAR(100),
| TIP VARCHAR(100),
| OWNER VARCHAR(100),
| ID VARCHAR(36) NOT NULL,
| COMMENT VARCHAR(100),
| HINT VARCHAR(100),
| CONSTRAINT MDTABLE_PK PRIMARY KEY (ID)
|);";
КонецФункции
&НаКлиенте
Функция СоздатьМетаданныетРеквизиты()
sql = "
|RECREATE TABLE MDREKVIZIT (
| NAMEENGL VARCHAR(100),
| NAMERUS VARCHAR(100),
| SYNONYM VARCHAR(100),
| TIP VARCHAR(100),
| TABL VARCHAR(100),
| ID VARCHAR(36) NOT NULL,
| COMMENT VARCHAR(100),
| HINT VARCHAR(100),
| FORMAT VARCHAR(100),
| CONSTRAINT MDREKVIZIT_PK PRIMARY KEY (ID)
|);";
возврат sql;
КонецФункции
Заполнил их метаданными из 1С.
Если Объект.Метаданные Тогда
Command.ActiveConnection = мСоединение;
Command.CommandText = СоздатьМетаданныеТаблица();
Попытка
RecordSet = Command.Execute();
Исключение
Сообщить("Ошибка при выполнении запроса. Текст запроса:"+Символы.ПС+стр.SQL_index+Символы.ПС+"Описание ошибки: "+ОписаниеОшибки());
КонецПопытки;
Command.CommandText = СоздатьМетаданныетРеквизиты();
Попытка
RecordSet = Command.Execute();
Исключение
Сообщить("Ошибка при выполнении запроса. Текст запроса:"+Символы.ПС+стр.SQL_index+Символы.ПС+"Описание ошибки: "+ОписаниеОшибки());
КонецПопытки;
Для каждого стр из Объект.ТаблицыБД Цикл
Если стр.Отметка Тогда
Command.CommandText = "INSERT INTO MDTABLE (NAMEENGL,OWNER, NAMERUS, SYNONYM, TIP, ID, COMMENT, HINT)
| VALUES('" + стр.ИмяАнгл+ "', '" + стр.Владелец+ "', '" + стр.ИмяРус+ "', '" + стр.Синоним+ "', '" + стр.Тип+ "', '" +строка(стр.НомерСтроки)+ "', '" + стр.Комментарий+ "', '" + стр.Подсказка+ "');";
RecordSet = Command.Execute();
Для каждого стрР из Объект.Реквизиты Цикл
Если стрР.Отметка Тогда
Если стрР.Таблица = стр.ИмяРус Тогда
Command.CommandText = "INSERT INTO MDREKVIZIT (NAMEENGL, NAMERUS, SYNONYM, TIP, TABL, ID, COMMENT, HINT, FORMAT)
| VALUES('" + стрР.ИмяАнгл+ "', '" + стрР.ИмяРус+ "', '" + стрР.Синоним+ "', '" + стрР.Тип+ "', '" +строка(стрР.НомерСтроки)+ "', '"+ строка(стрР.НомерСтроки)+ "', '" + стрР.Комментарий+ "', '" + стрР.Подсказка+"', '" "');";
RecordSet = Command.Execute();
КонецЕсли;
КонецЕсли;
КонецЦикла;
КонецЕсли;
КонецЦикла;
КонецЕсли;
Результат работы:
1. В качестве создания БД использую привычный мне инструмент 1С.
2. Создаю SQL базу данных.
3. Заполняю их данными из 1с.
4. Делаю выгрузку JSON. Что дает мне интеграцию с 1С.
5. Метаданные дают мне возможность использовать синонимы, подсказки, сделанные в 1С.