Имя: Пароль:
1C
1C 7.7
v7: Получить остатки с помощью SqLite
0 Zhuravlik
 
10.09.12
13:21
Здравствуйте. Пытаюсь собрать остатки по регистру запросом, с помощью ВК SqLite. Так как в этом вообще ноль, нашел пример в нете, пытаюсь подрезать его под себя, но что-то не получается.

Структура регистра:

Регистр.Авто_НаСкладах

Изм1: Склад (Справочник.Склады)
Изм2: Модель (Справочник.Авто_Модели);
Изм3: Автомобиль (Справочник.Автомобили)

Рес1: Количество (Число, 1, 0)

Вот код, который я нашел:

Функция ПолучитьОстаткиНа(ДатаОст)
Попытка
 база = СоздатьОбъект("SQLiteBase");
Исключение
 ЗагрузитьВнешнююКомпоненту("1sqlite.dll");
 база = СоздатьОбъект("SQLiteBase");
КонецПопытки;
база.Открыть(":memory:");
запрос = база.НовыйЗапрос();
запрос.Подставлять("ДатаИтогвНаКонецПрошлогоПериода", НачМесяца(НачМесяца(ДатаОст) - 1));
запрос.Подставлять("ДатаНачалаПериодаДвижений", НачМесяца(ДатаОст));
запрос.Подставлять("ДатаОстатков", ДатаОст);
Возврат запрос.ВыполнитьЗапрос("
|select
|Остатки.Номенклатура [Номенклатура :Справочник.Номенклатура],
|Остатки.Склад [Склад :Справочник.Склады],
|sum(Остатки.Количество) [Количество :Число.15.5]
|from (
| -- Итоги на конец предыдщего периода
| select
|  Номенклатура,
|  Склад,
|  Количество
| from РегистрИтоги_ОстаткиТМЦ where period = :ДатаИтогвНаКонецПрошлогоПериода
| -- Движения с конца прошлого периода до даты
| union all
| select
|  Номенклатура,
|  Склад,
|  case when debkred = 0 then Количество else -Количество end
| from Регистр_ОстаткиТМЦ Движения
| -- быстрой обработки движений нет, надо соединятся с журналом
| inner join Журнал on Журнал.iddoc = Движения.iddoc
| where Журнал.date > :ДатаНачалаПериодаДвижений
| and Журнал.date < :ДатаОстатков and Журнал.ОстаткиТМЦФр = 1
|)Остатки
|group by Остатки.Номенклатура, Остатки.Склад
|");
КонецФункции // ПолучитьОстатки



Вот код, который у меня сейчас:

Функция ПолучитьОстаткиНа(ДатаОст)
Попытка
 база = СоздатьОбъект("SQLiteBase");
Исключение
   Сообщить(ОписаниеОшибки());
   Возврат СоздатьОбъект("ТаблицаЗначений");
КонецПопытки;
база.Открыть(":memory:");
запрос = база.НовыйЗапрос();
запрос.Подставлять("ДатаИтогвНаКонецПрошлогоПериода", НачМесяца(НачМесяца(ДатаОст) - 1));
запрос.Подставлять("ДатаНачалаПериодаДвижений", НачМесяца(ДатаОст));
запрос.Подставлять("ДатаОстатков", ДатаОст);
Возврат запрос.ВыполнитьЗапрос("
|select
|Остатки.Автомобиль [Автомобиль :Справочник.Автомобили],
|Остатки.Склад [Склад :Справочник.Склады],
|sum(Остатки.Количество) [Количество :Число.15.5]
|from (
| -- Итоги на конец предыдщего периода
| select
|  Автомобиль,
|  Склад,
|  Количество
| from Регистр_Итоги_Авто_НаСкладах where period = :ДатаИтогвНаКонецПрошлогоПериода
| -- Движения с конца прошлого периода до даты
| union all
| select
|  Автомобиль,
|  Склад,
|  case when debkred = 0 then Количество else -Количество end
| from Регистр_Авто_НаСкладах Движения
| -- быстрой обработки движений нет, надо соединятся с журналом
| inner join Журнал on Журнал.iddoc = Движения.iddoc
| where Журнал.date > :ДатаНачалаПериодаДвижений
| and Журнал.date < :ДатаОстатков
|)Остатки
|group by Остатки.Номенклатура, Остатки.Склад
|");
КонецФункции // ПолучитьОстатки




Ругается, говорит: "no such table: Регистр_Авто_НаСкладах"
Подскажите, куда тыкнуть...
1 Zhuravlik
 
10.09.12
13:40
Чуть изменил, ошибка та-же



Функция ПолучитьОстаткиНа(ДатаОст)
   база = СоздатьОбъект("SQLiteBase");
   база.Открыть(":memory:");
   запрос = база.НовыйЗапрос();
   запрос.Подставлять("ДатаИтогвНаКонецПрошлогоПериода", НачМесяца(НачМесяца(ДатаОст) - 1));
   запрос.Подставлять("ДатаНачалаПериодаДвижений", НачМесяца(ДатаОст));
   запрос.Подставлять("ДатаОстатков", ДатаОст);
   Возврат запрос.ВыполнитьЗапрос("
       |select
       |Остатки.Автомобиль [Автомобиль :Справочник.Автомобили],
       |Остатки.Склад [Склад :Справочник.Склады],
       |sum(Остатки.Количество) [Количество :Число.1.0]
       |from (
       | -- Итоги на конец предыдщего периода
       | select
       |  Автомобиль,
       |  Склад,
       |  Количество
       | from РегистрИтоги_Авто_НаСкладах where period = :ДатаИтогвНаКонецПрошлогоПериода
       | -- Движения с конца прошлого периода до даты
       | union all
       | select
       |  Автомобиль,
       |  Склад,
       |  case when debkred = 0 then Количество else -Количество end
       | from Регистр_Авто_НаСкладах Движения
       | -- быстрой обработки движений нет, надо соединятся с журналом
       | inner join Журнал on Журнал.iddoc = Движения.iddoc
       | where Журнал.date > :ДатаНачалаПериодаДвижений
       | and Журнал.date < :ДатаОстатков
       |)Остатки
       |group by Остатки.Автомобиль, Остатки.Склад
       |having [Количество :Число.1.0] <> 0
       |");
КонецФункции // ПолучитьОстатки
2 Ёпрст
 
10.09.12
13:44
Токма останки нужны ?
3 orefkov
 
10.09.12
13:46
Где-то криогенную камеру открыли чтоли?
То по turbobl вопросы, то по 1sqlite :)
4 Ёпрст
 
10.09.12
13:47
Это.. писать
НачМесяца(НачМесяца(ДатаОст) - 1)); - моветон.
Не у всех периодичность хранения останков = месяц.
5 mehfk
 
10.09.12
13:51
6 Zhuravlik
 
10.09.12
13:52
Да, но нужно получать по дате (на конец-начало, чтобы работало аналогом РассчитатьРегистрыНа(По) в зависимости от флажка), и по позицию...

Переименовал регистр Авто_НаСкладах в АвтоНаСкладах, убрал галку "Быстрая обработка движений", запрос сработал, и почему-то если я использую его в функции, то код срабатывает, и выгружается в тз (тз.Загрузить(ПолучитьОстаткиНа(Дат))), а запрос.Выгрузить(тз) - говорит нет такого. В общем запрос срабатывает, но в тз - пустая...



//======================================================================
Процедура Выполнить()
   
   ДатаОст = дт;
   
   база = СоздатьОбъект("SQLiteBase");
   база.Открыть(":memory:");
   запрос = база.НовыйЗапрос();
   запрос.Подставлять("ДатаИтогвНаКонецПрошлогоПериода", НачМесяца(НачМесяца(ДатаОст) - 1));
   запрос.Подставлять("ДатаНачалаПериодаДвижений", НачМесяца(ДатаОст));
   запрос.Подставлять("ДатаОстатков", ДатаОст);
   запрос.ВыполнитьЗапрос("
       |select
       |Остатки.Автомобиль [Автомобиль :Справочник.Автомобили],
       |Остатки.Склад [Склад :Справочник.Склады],
       |sum(Остатки.Количество) [Количество :Число.1.0]
       |from (
       | -- Итоги на конец предыдщего периода
       | select
       |  Автомобиль,
       |  Склад,
       |  Количество
       | from РегистрИтоги_АвтоНаСкладах where period = :ДатаИтогвНаКонецПрошлогоПериода
       | -- Движения с конца прошлого периода до даты
       | union all
       | select
       |  Автомобиль,
       |  Склад,
       |  case when debkred = 0 then Количество else -Количество end
       | from Регистр_АвтоНаСкладах Движения
       | -- быстрой обработки движений нет, надо соединятся с журналом
       | inner join Журнал on Журнал.iddoc = Движения.iddoc
       | where Журнал.date > :ДатаНачалаПериодаДвижений
       | and Журнал.date < :ДатаОстатков
       |)Остатки
       |group by Остатки.Автомобиль, Остатки.Склад
       |having [Количество :Число.1.0] <> 0
       |");
       
       
   тз = СоздатьОбъект("ТаблицаЗначений");
   тз.Загрузить(запрос);
   Сообщить(тз.КоличествоСтрок());
   
   глНаЭкран(тз);
   
КонецПроцедуры // Выполнить
7 Ёпрст
 
10.09.12
13:59
(6)
1.выкинуть case из текста запроса, заменив операцией умножения
2.выкинуть неверные условия на дату, заменив на between
8 Ёпрст
 
10.09.12
13:59
3. из having выкинуть типизацию
9 Ёпрст
 
10.09.12
14:00
тз.Загрузить(запрос); //это жесть
10 Ёпрст
 
10.09.12
14:02
ТЗ = запрос.ВыполнитьЗапрос(ТекстЗапроса);
ТЗ.ВыбратьСтроку();

или

запрос.ВыполнитьЗапрос(ТекстЗапроса).ВыбратьСтроку();

или в индексированную тЗ или другой источник выгружать (см. параметры метода ВыполнитьЗапрос)
11 Zhuravlik
 
10.09.12
14:05
(7)1.Выкинул, выдал ошибку near "when": syntax error
  2. Вообще убрал эти проверки, поставил галку "БыстраяОбработкаДвижений" обратно
(10) Сделал)

Что-то выдал, вот что в итоге получилось



//======================================================================
Процедура Выполнить()
   
   ДатаОст = дт;
   
   база = СоздатьОбъект("SQLiteBase");
   база.Открыть(":memory:");
   запрос = база.НовыйЗапрос();
   запрос.Подставлять("ДатаИтогвНаКонецПрошлогоПериода", НачМесяца(НачМесяца(ДатаОст) - 1));
   запрос.Подставлять("ДатаНачалаПериодаДвижений", НачМесяца(ДатаОст));
   запрос.Подставлять("ДатаОстатков", ДатаОст);
   
   тз = СоздатьОбъект("ТаблицаЗначений");
   тз = запрос.ВыполнитьЗапрос("
       |select
       |Остатки.Автомобиль [Автомобиль :Справочник.Автомобили],
       |Остатки.Склад [Склад :Справочник.Склады],
       |sum(Остатки.Количество) [Количество :Число.1.0]
       |from (
       | -- Итоги на конец предыдщего периода
       | select
       |  Автомобиль,
       |  Склад,
       |  Количество
       | from РегистрИтоги_АвтоНаСкладах where period = :ДатаИтогвНаКонецПрошлогоПериода
       | -- Движения с конца прошлого периода до даты
       | union all
       | select
       |  Автомобиль,
       |  Склад,
       |  case when debkred = 0 then Количество else -Количество end
       | from Регистр_АвтоНаСкладах Движения
       |)Остатки
       |group by Остатки.Автомобиль, Остатки.Склад
       |having [Количество :Число.1.0] <> 0
       |");

   Сообщить(тз.КоличествоСтрок());
   
   глНаЭкран(тз);
   
КонецПроцедуры // Выполнить



А можно как-нибудь без переименовывания регистра еще обойтись? Хочу, чтобы название регистра оставалось Авто_НаСкладах, а не АвтоНаСкладах?
12 Zhuravlik
 
10.09.12
14:06
+ но если меняю "Case" на "*", выдает ошибку "when": syntax error
13 Ёпрст
 
10.09.12
14:17
Ё...

    |select
       |???????.?????????? [?????????? :??????????.??????????],
       |???????.????? [????? :??????????.??????],
       |sum(???????.??????????) [?????????? :?????]
       |from (
       | -- ????? ?? ????? ?????????? ???????
       | select
       |  ?????.?????????? ??????????,
       |  ?????.????? ?????,
       |  ?????.?????????? ???????????
       | from [????????????.?????????????] ?????
       | where ?????.period = :???????????????????????????????
       | -- ???????? ? ????? ???????? ??????? ?? ????
       | union all
       | select
       |  ????????.??????????,
       |  ????????.?????,
       |  ????????.?????????? * (1 - ????????.debkred * 2)
       | from [???????.?????????????] ????????
       | where ????????.date BETWEEN :????????????????????????? and :????????????
       |
       |
       |)???????
       |group by ???????.??????????, ???????.?????
       |having sum(???????.??????????) <> 0
14 Ёпрст
 
10.09.12
14:17
|select
       |Остатки.Автомобиль [Автомобиль :Справочник.Автомобили],
       |Остатки.Склад [Склад :Справочник.Склады],
       |sum(Остатки.Количество) [Количество :Число]
       |from (
       | -- Итоги на конец предыдщего периода
       | select
       |  Итоги.Автомобиль Автомобиль,
       |  Итоги.Склад Склад,
       |  Итоги.Количество Колдичество
       | from [РегистрИтоги.АвтоНаСкладах] Итоги
       | where Итоги.period = :ДатаИтогвНаКонецПрошлогоПериода
       | -- Движения с конца прошлого периода до даты
       | union all
       | select
       |  Движения.Автомобиль,
       |  Движения.Склад,
       |  Движения.Количество * (1 - Движения.debkred * 2)
       | from [Регистр.АвтоНаСкладах] Движения
       | where Движения.date BETWEEN :ДатаНачалаПериодаДвижений and :ДатаОстатков
       |
       |
       |)Остатки
       |group by Остатки.Автомобиль, Остатки.Склад
       |having sum(Остатки.Количество) <> 0
15 Zhuravlik
 
10.09.12
14:29
(14) Работает... А если вместо "ДатаОстатков" передавать позицию документа, прокатит?
Так быстро) Накачал себе литературы по 1С++, но в als файле нет раздела SQLite...
Где можно по нем алску достать, не подскажете?
16 Zhuravlik
 
10.09.12
14:41
(14) а как с позицией сделать?
17 Ёпрст
 
10.09.12
14:43
(15)
http://www.1cpp.ru/forum/YaBB.pl?num=1214205575
als-ка не нужна, есть chm со всей докой.
18 Ёпрст
 
10.09.12
14:46
с позицией.. так примерно:

Движения.idx_date_time_iddoc_lineno_actno BETWEEN :НачПериод And :КонПериод~~~


Запрос.Подставлять("КонПериод",ТекущийДокумент());
19 Zhuravlik
 
10.09.12
14:49
(18) Спасибо за помощь) Буду вчитываться.
20 Zhuravlik
 
10.09.12
14:53
(18) Получилось))