Решил поделится опытом решения частичной автоматизации документооборота на кафедре в ВУЗе. Это продолжение, в некотором смысле, моего поста Программа по составлению расписания занятий в ВУЗе. Решение построено на бесплатных продуктах и успешно эксплуатируются в течение 6 лет.
Описание системы
Ниже представлено головное окно. С каждой кнопкой связанно редактирование или просмотр соответствующей таблицы БД или выполнение перерасчета часов и генерация отчетов. По функциональной зависимости кнопки расположены сналево права. Поэтому первая колонка и расположенная ниже всех строка с кнопками должности и преподаватели являются словарями.
Выделение строки с кнопками должности и преподаватели связанно и их редким использованием.
Прокомментирую некоторые кнопки.
- Наверно я неправильно называю дисциплины в ВУЗе предметами.
- Разбиение это разбиение групп на подгруппы по проведению занятий (иностранный язык, лабораторные, компьютерные классы и т.д.).
- Потоки представляют в моем контексте те уникальные названия групп, подгрупп и всевозможных потоков (всевозможных объединений из групп и подгрупп), которые мы видим в расписании занятий.
Ниже расположено окно для занесения и правки специальностей, а также бакалавров, магистров и чего только министерство образования не придумает.
Подгруппы для следущей формы плохое название, но я лучше не придумал. Подгруппы представляют собой соединение двух потоков по разбиению. Поток представляющий собой группы по специальности «прикладная математика» имеет надпоток по лекционному разбиению по всем группам «прикладной математики» для чтения лекций.
Для удобства работы встроенны всевозможные фильтры, расположенные справа в форме. В данном окне включен фильтр по дневному отделению и по специальности «прикладная информатика».
Заявки это то, что спускает деканат на кафедру в качестве учебных поручений. Например провести занятия на таком-то потоке по дисциплине «Базы данных». Это значит это часы за лекции и практику + расчетные часы за проведение текущих консультаций, проверку контрольных работ, консультаций перед экзаменом, прием экзамена или теоретического зачета и т.д. Последние часы зависят от количества студентов, правил расчета конкретного ВУЗа и текущего года. В моем Вузе их раз в пару лет меняют. Для их пересчета на первом рисунке служит кнопка «Обновить».
Следующее окно по выбранной заявке позволяет привязать нагрузку к конкретным преподавателям.
Я не стал подробно показывать скриншоты для следующих кнопок с первого рисунка:
- ЗаявкиРуков — курсовые и дипломные
- НагрузкиРуков — расстановка преподавателей по курсовым и дипломным
- НагрузкиДоп — руководство аспирантами, участие в ГЭКах и ГАКах, руководство практикой и т.д. Вся эта нагрузка считается по очень запутанным правилам и поэтому ее проще вбить и ее достаточно мало.
- Кафедра — показывает как в текущий момент распределены часы по преподавателям и сколько часов еще осталось распределить
Основное целью здесь является генерация «Расчета часов», «Карточек учебных поручений» и других всевозможных бумаг. Они ниже представлены на трех скриншотах. Генерация делается в формате OpenDocument (ГОСТ Р ИСО/МЭК 26300-2010. Госстандарт России) с полным форматированием и подстановкой готовых формул для суммирования по колонкам и строкам.
Технические детали
Буду краток.
- СУБД PosgreSQL.
- GUI на PyQt.
- Перерасчет часов (кнопка «Обновить») на Python.
- Генерация отчетов посредством ODFPY.
По поводу русских названий и префиксов tbl, vw, pk_, fk_ я предлагаю здесь не обсуждать. Я специально напишу про топик.
CREATE TABLE tblФормыОбучения (
pk_ФормаОбучения SERIAL PRIMARY KEY,
мнемо TEXT UNIQUE,
название TEXT UNIQUE,
примечание TEXT
);
CREATE VIEW vwФормыОбучения AS
SELECT
pk_ФормаОбучения,
мнемо
FROM
tblФормыОбучения
ORDER BY
мнемо;
CREATE TABLE tblСпециальности (
pk_Специальность SERIAL PRIMARY KEY,
номер TEXT,
мнемо TEXT UNIQUE,
название TEXT UNIQUE,
примечание TEXT
);
CREATE VIEW vwСпециальности AS
SELECT
pk_Специальность,
мнемо
FROM
tblСпециальности
ORDER BY
мнемо;
CREATE TABLE tblФакультеты (
pk_Факультет SERIAL PRIMARY KEY,
мнемо TEXT UNIQUE,
название TEXT UNIQUE,
примечание TEXT
);
CREATE VIEW vwФакультеты AS
SELECT
pk_Факультет,
мнемо
FROM
tblФакультеты
ORDER BY
мнемо;
CREATE TABLE tblПредметы (
pk_Предмет SERIAL PRIMARY KEY,
название TEXT UNIQUE
);
CREATE VIEW vwПредметы AS
SELECT
pk_Предмет,
название
FROM
tblПредметы
ORDER BY
название;
CREATE TABLE tblДолжности (
pk_Должность SERIAL PRIMARY KEY,
название TEXT UNIQUE
);
CREATE VIEW vwДолжности AS
SELECT
pk_Должность,
мнемо
FROM
tblДолжности
ORDER BY
мнемо;
CREATE TABLE tblПреподаватели (
pk_Преподаватель SERIAL PRIMARY KEY,
фамилия TEXT,
имя TEXT,
отчество TEXT,
fk_Должность INTEGER REFERENCES tblДолжности(pk_Должность),
ставка TEXT,
примечание TEXT,
UNIQUE(фамилия, имя, отчество)
);
CREATE VIEW vwПреподаватели AS
SELECT
pk_Преподаватель,
фамилия
FROM
tblПреподаватели
ORDER BY
фамилия;
CREATE TABLE tblРазбиения (
pk_Разбиение SERIAL PRIMARY KEY,
название TEXT UNIQUE,
примечание TEXT
);
CREATE VIEW vwРазбиения AS
SELECT
pk_Разбиение,
название
FROM
tblРазбиения
ORDER BY
название;
CREATE TABLE tblПотоки (
pk_Поток SERIAL PRIMARY KEY,
название TEXT UNIQUE,
UNIQUE(название)
);
CREATE VIEW vwПотоки AS
SELECT
pk_Поток,
название
FROM
tblПотоки
ORDER BY
название;
CREATE TABLE tblПодгруппы (
pk_Подгруппа SERIAL PRIMARY KEY,
fk_Факультет INTEGER REFERENCES tblФакультеты(pk_Факультет),
fk_ФормаОбучения INTEGER REFERENCES tblФормыОбучения(pk_ФормаОбучения),
fk_Специальность INTEGER REFERENCES tblСпециальности(pk_Специальность),
fk_Разбиение INTEGER REFERENCES tblРазбиения(pk_Разбиение),
fk_НадПоток INTEGER REFERENCES tblПотоки(pk_Поток),
fk_Поток INTEGER REFERENCES tblПотоки(pk_Поток),
курс INTEGER,
комм BOOLEAN,
колБюджет INTEGER,
колКомм INTEGER,
примечание TEXT,
UNIQUE(fk_Разбиение, fk_НадПоток, fk_Поток)
);
CREATE VIEW vwПодгруппы AS
SELECT
tblПодгруппы.pk_Подгруппа,
tblПодгруппы.fk_Факультет,
tblПодгруппы.fk_ФормаОбучения,
tblПодгруппы.fk_Специальность,
SUM(
CASE
WHEN tblПодгруппы1.fk_Разбиение = 4 AND NOT tblПодгруппы1.комм THEN
1
ELSE
0
END) AS лекБюджет,
SUM(
CASE
WHEN tblПодгруппы1.fk_Разбиение = 4 AND tblПодгруппы1.комм THEN
1
ELSE
0
END) AS лекКомм,
SUM(
CASE
WHEN tblПодгруппы1.fk_Разбиение = 1 AND NOT tblПодгруппы1.комм THEN
1
ELSE
0
END) AS семБюджет,
SUM(
CASE
WHEN tblПодгруппы1.fk_Разбиение = 1 AND tblПодгруппы1.комм THEN
1
ELSE
0
END) AS семКомм,
SUM(
CASE
WHEN tblПодгруппы1.fk_Разбиение = 2 AND NOT tblПодгруппы1.комм THEN
1
ELSE
0
END) AS лабБюджет,
SUM(
CASE
WHEN tblПодгруппы1.fk_Разбиение = 2 AND tblПодгруппы1.комм THEN
1
ELSE
0
END) AS лабКомм,
tblПодгруппы.fk_Поток,
tblПодгруппы.курс,
tblПодгруппы.комм,
tblПодгруппы.колБюджет,
tblПодгруппы.колКомм
FROM
tblПодгруппы
LEFT JOIN tblПодгруппы AS tblПодгруппы1 ON tblПодгруппы.fk_Поток = tblПодгруппы1.fk_НадПоток
WHERE
tblПодгруппы.fk_Поток = tblПодгруппы.fk_НадПоток
GROUP BY
tblПодгруппы.pk_Подгруппа,
tblПодгруппы.fk_Факультет,
tblПодгруппы.fk_ФормаОбучения,
tblПодгруппы.fk_Специальность,
tblПодгруппы.fk_Поток,
tblПодгруппы.курс,
tblПодгруппы.комм,
tblПодгруппы.колБюджет,
tblПодгруппы.колКомм;
CREATE TABLE tblЗаявки (
pk_Заявка SERIAL PRIMARY KEY,
fk_Предмет INTEGER REFERENCES tblПредметы(pk_Предмет),
fk_Поток INTEGER REFERENCES tblПотоки(pk_Поток),
семестр BOOLEAN,
лек INTEGER,
сем INTEGER,
лаб INTEGER,
КСР INTEGER,
"т/конс" BOOLEAN,
экз BOOLEAN,
зач BOOLEAN,
"п/зач" BOOLEAN,
контр BOOLEAN,
CHECK(NOT(экз AND зач))
);
CREATE VIEW vw_fk_Заявки AS
SELECT
pk_Заявка AS fk_Заявка,
(CASE
WHEN tblЗаявки.семестр THEN
'1 '
ELSE
'2 '
END) || tblПредметы.название AS мнемо
FROM
tblЗаявки INNER JOIN tblПредметы
ON tblЗаявки.fk_Предмет = tblПредметы.pk_Предмет
ORDER BY
мнемо;
CREATE TABLE tblНагрузки (
fk_Заявка INTEGER REFERENCES tblЗаявки(pk_Заявка),
fk_Поток INTEGER REFERENCES tblПотоки(pk_Поток),
комм BOOLEAN,
лекцонная BOOLEAN,
лек INTEGER,
сем INTEGER,
лаб INTEGER,
КСР INTEGER,
"т/конс" REAL,
"э/конс" REAL,
экз REAL,
зач REAL,
контр REAL,
fk_Преподаватель INTEGER REFERENCES tblПреподаватели(pk_Преподаватель),
PRIMARY KEY(fk_Заявка, fk_Поток, лекцонная, комм),
CHECK(NOT(экз > 0.0 AND зач > 0.0))
);
CREATE VIEW vwНагрузки AS
SELECT
pk_Заявка,
tblФакультеты.мнемо AS Факультет,
tblФормыОбучения.мнемо AS ФормаОбучения,
tblСпециальности.мнемо AS спец,
курс,
tblПотоки.название AS поток,
(CASE
WHEN tblНагрузки.комм THEN
колКомм
ELSE
колБюджет
END) AS студентов,
tblПредметы.название AS предмет,
(CASE
WHEN семестр THEN
1
ELSE
2
END) AS семестр,
SUM(tblНагрузки.лек) AS лек,
SUM(tblНагрузки.сем) AS сем,
SUM(tblНагрузки.лаб) AS лаб,
SUM(tblНагрузки."т/конс") AS "т/конс",
SUM(tblНагрузки."э/конс") AS "э/конс",
SUM(tblНагрузки.экз) AS экз,
SUM(tblНагрузки.зач) AS зач,
SUM(tblНагрузки.контр) AS контр,
tblНагрузки.комм AS комм,
tblПреподаватели.фамилия AS препод
FROM
tblЗаявки
LEFT JOIN tblНагрузки ON tblЗаявки.pk_Заявка = tblНагрузки.fk_Заявка
LEFT JOIN vwПодгруппы ON tblЗаявки.fk_Поток = vwПодгруппы.fk_Поток
LEFT JOIN tblФакультеты ON vwПодгруппы.fk_Факультет = tblФакультеты.pk_Факультет
LEFT JOIN tblФормыОбучения ON vwПодгруппы.fk_ФормаОбучения = tblФормыОбучения.pk_ФормаОбучения
LEFT JOIN tblСпециальности ON vwПодгруппы.fk_Специальность = tblСпециальности.pk_Специальность
LEFT JOIN tblПредметы ON tblЗаявки.fk_Предмет = tblПредметы.pk_Предмет
LEFT JOIN tblПотоки ON tblЗаявки.fk_Поток = tblПотоки.pk_Поток
LEFT JOIN tblПреподаватели ON tblНагрузки.fk_Преподаватель = tblПреподаватели.pk_Преподаватель
GROUP BY
pk_Заявка,
tblФакультеты.мнемо,
tblФормыОбучения.мнемо,
tblСпециальности.мнемо,
tblПотоки.название,
курс,
студентов,
tblПредметы.название,
семестр,
tblНагрузки.комм,
tblПреподаватели.фамилия
ORDER BY
Факультет,
ФормаОбучения,
спец,
курс,
поток,
предмет,
семестр;
CREATE TABLE tblЗаявкиРуков (
pk_ЗаявкаРуков SERIAL PRIMARY KEY,
fk_Предмет INTEGER REFERENCES tblПредметы(pk_Предмет),
fk_Поток INTEGER REFERENCES tblПотоки(pk_Поток),
семестр BOOLEAN,
"курс/раб" BOOLEAN,
"дип/бак" BOOLEAN
);
CREATE VIEW vw_fk_ЗаявкиРуков AS
SELECT
pk_ЗаявкаРуков AS fk_ЗаявкаРуков,
(CASE
WHEN tblЗаявкиРуков.семестр THEN
'1 '
ELSE
'2 '
END) || tblПредметы.название AS мнемо
FROM
tblЗаявкиРуков INNER JOIN tblПредметы
ON tblЗаявкиРуков.fk_Предмет = tblПредметы.pk_Предмет
ORDER BY
мнемо;
CREATE TABLE tblНагрузкиРуков (
fk_ЗаявкаРуков INTEGER REFERENCES tblЗаявкиРуков(pk_ЗаявкаРуков),
-- fk_Поток INTEGER REFERENCES tblПотоки(pk_Поток),
комм BOOLEAN,
номер INTEGER,
часов INTEGER,
студент TEXT,
тема TEXT,
fk_Преподаватель INTEGER REFERENCES tblПреподаватели(pk_Преподаватель),
PRIMARY KEY(fk_ЗаявкаРуков, комм, номер)
);
CREATE VIEW vwНагрузкиРуков AS
SELECT
pk_ЗаявкаРуков,
tblФакультеты.мнемо AS Факультет,
tblФормыОбучения.мнемо AS ФормаОбучения,
tblСпециальности.мнемо AS спец,
курс,
tblПотоки.название AS поток,
COUNT(*) AS студентов,
tblПредметы.название AS предмет,
(CASE
WHEN семестр THEN
1
ELSE
2
END) AS семестр,
(CASE
WHEN "курс/раб" THEN
SUM(tblНагрузкиРуков.часов)
ELSE
0
END) AS курсов,
(CASE
WHEN "дип/бак" THEN
SUM(tblНагрузкиРуков.часов)
ELSE
0
END) AS димпл,
tblНагрузкиРуков.комм AS комм,
tblПреподаватели.фамилия AS препод
FROM
tblЗаявкиРуков
LEFT JOIN tblНагрузкиРуков ON tblЗаявкиРуков.pk_ЗаявкаРуков = tblНагрузкиРуков.fk_ЗаявкаРуков
LEFT JOIN vwПодгруппы ON tblЗаявкиРуков.fk_Поток = vwПодгруппы.fk_Поток
LEFT JOIN tblФакультеты ON vwПодгруппы.fk_Факультет = tblФакультеты.pk_Факультет
LEFT JOIN tblФормыОбучения ON vwПодгруппы.fk_ФормаОбучения = tblФормыОбучения.pk_ФормаОбучения
LEFT JOIN tblСпециальности ON vwПодгруппы.fk_Специальность = tblСпециальности.pk_Специальность
LEFT JOIN tblПредметы ON tblЗаявкиРуков.fk_Предмет = tblПредметы.pk_Предмет
LEFT JOIN tblПотоки ON tblЗаявкиРуков.fk_Поток = tblПотоки.pk_Поток
LEFT JOIN tblПреподаватели ON tblНагрузкиРуков.fk_Преподаватель = tblПреподаватели.pk_Преподаватель
GROUP BY
pk_ЗаявкаРуков,
tblФакультеты.мнемо,
tblФормыОбучения.мнемо,
tblСпециальности.мнемо,
tblПотоки.название,
курс,
tblПредметы.название,
семестр,
"курс/раб",
"дип/бак",
tblНагрузкиРуков.комм,
tblПреподаватели.фамилия
ORDER BY
Факультет,
ФормаОбучения,
спец,
курс,
поток,
предмет,
семестр;
CREATE TABLE tblНагрузкиДоп (
pk_НагрузкаДоп SERIAL PRIMARY KEY,
fk_Поток INTEGER REFERENCES tblПотоки(pk_Поток),
семестр BOOLEAN,
практ REAL,
ГЭК REAL,
ГАК REAL,
прием INTEGER,
курат INTEGER,
"каф/рук" INTEGER,
"асп/рук" INTEGER,
факул INTEGER,
комм BOOLEAN,
fk_Преподаватель INTEGER REFERENCES tblПреподаватели(pk_Преподаватель)
);
CREATE VIEW vwНагрузкиДоп AS
SELECT
pk_НагрузкаДоп,
(CASE
WHEN tblФакультеты.мнемо IS NULL THEN
'м/м'
ELSE
tblФакультеты.мнемо
END) AS Факультет,
(CASE
WHEN tblФормыОбучения.мнемо IS NULL THEN
'д/о'
ELSE
tblФормыОбучения.мнемо
END) AS ФормаОбучения,
tblСпециальности.мнемо AS спец,
курс,
tblПотоки.название AS поток,
(CASE
WHEN tblНагрузкиДоп.комм THEN
колКомм
ELSE
колБюджет
END) AS студентов,
(CASE
WHEN семестр THEN
1
ELSE
2
END) AS семестр,
практ,
ГЭК+ГАК AS ГАК,
"асп/рук",
"каф/рук",
факул,
курат,
прием,
tblНагрузкиДоп.комм AS комм,
tblПреподаватели.фамилия AS препод
FROM
tblНагрузкиДоп
LEFT JOIN vwПодгруппы ON tblНагрузкиДоп.fk_Поток = vwПодгруппы.fk_Поток
LEFT JOIN tblФакультеты ON vwПодгруппы.fk_Факультет = tblФакультеты.pk_Факультет
LEFT JOIN tblФормыОбучения ON vwПодгруппы.fk_ФормаОбучения = tblФормыОбучения.pk_ФормаОбучения
LEFT JOIN tblСпециальности ON vwПодгруппы.fk_Специальность = tblСпециальности.pk_Специальность
LEFT JOIN tblПотоки ON tblНагрузкиДоп.fk_Поток = tblПотоки.pk_Поток
LEFT JOIN tblПреподаватели ON tblНагрузкиДоп.fk_Преподаватель = tblПреподаватели.pk_Преподаватель
ORDER BY
Факультет,
ФормаОбучения,
спец,
курс,
поток,
семестр;
CREATE VIEW vwКарточки AS
SELECT
Факультет,
ФормаОбучения,
спец,
курс,
поток,
студентов,
предмет,
семестр,
SUM(лек) AS лек,
SUM(сем) AS сем,
SUM(лаб) AS лаб,
SUM("т/конс") AS "т/конс",
SUM("э/конс") AS "э/конс",
SUM(экз) AS экз,
SUM(зач) AS зач,
SUM(практ) AS практ,
SUM(курсов) AS курсов,
SUM(димпл) AS димпл,
SUM(ГАК) AS ГАК,
SUM(контр) AS контр,
SUM("асп/рук") AS "асп/рук",
SUM("каф/рук") AS "каф/рук",
SUM(факул) AS факул,
SUM(курат) AS курат,
SUM(прием) AS прием,
комм,
препод
FROM
(
(SELECT
Факультет,
ФормаОбучения,
спец,
курс,
поток,
студентов,
предмет,
семестр,
лек,
сем,
лаб,
"т/конс",
"э/конс",
экз,
зач,
0 AS практ,
0 AS курсов,
0 AS димпл,
0 AS ГАК,
контр,
0 AS "асп/рук",
0 AS "каф/рук",
0 AS факул,
0 AS курат,
0 AS прием,
комм,
препод
FROM
vwНагрузки)
UNION
(SELECT
Факультет,
ФормаОбучения,
спец,
курс,
поток,
студентов,
предмет,
семестр,
0 AS лек,
0 AS сем,
0 AS лаб,
0 AS "т/конс",
0 AS "э/конс",
0 AS экз,
0 AS зач,
0 AS практ,
курсов,
димпл,
0 AS ГАК,
0 AS контр,
0 AS "асп/рук",
0 AS "каф/рук",
0 AS факул,
0 AS курат,
0 AS прием,
комм,
препод
FROM
vwНагрузкиРуков)
UNION
(SELECT
Факультет,
ФормаОбучения,
спец,
курс,
поток,
студентов,
'' AS предмет,
семестр,
0 AS лек,
0 AS сем,
0 AS лаб,
0 AS "т/конс",
0 AS "э/конс",
0 AS экз,
0 AS зач,
практ,
0 AS курсов,
0 AS димпл,
ГАК,
0 AS контр,
"асп/рук",
"каф/рук",
факул,
курат,
прием,
комм,
препод
FROM
vwНагрузкиДоп)
) AS нагрука
GROUP BY
Факультет,
ФормаОбучения,
спец,
курс,
поток,
студентов,
предмет,
семестр,
комм,
препод
ORDER BY
Факультет,
ФормаОбучения,
спец,
курс,
поток,
предмет,
семестр;
CREATE VIEW vwНагрузкаПрепод AS
SELECT
комм,
SUM(часов) AS часов,
фамилия AS препод
FROM ((
(SELECT
комм,
SUM(лек + сем + лаб + "т/конс" + "э/конс" + экз + зач + контр) AS часов,
fk_Преподаватель
FROM
tblНагрузки
GROUP BY
комм,
fk_Преподаватель)
UNION
(SELECT
комм,
SUM(часов) AS часов,
fk_Преподаватель
FROM
tblНагрузкиРуков
GROUP BY
комм,
fk_Преподаватель)
UNION
(SELECT
комм,
SUM (практ + ГЭК + ГАК + прием + курат + "каф/рук" + "асп/рук" + факул) AS часов,
fk_Преподаватель
FROM
tblНагрузкиДоп
GROUP BY
комм,
fk_Преподаватель)
) AS нагрузка)
LEFT JOIN vwПреподаватели
ON нагрузка.fk_Преподаватель = vwПреподаватели.pk_Преподаватель
GROUP BY
комм,
препод
ORDER BY
препод,
комм;
CREATE VIEW vwНагрузка AS
SELECT
комм,
SUM(часов) AS часов
FROM (
(SELECT
комм,
SUM(лек + сем + лаб + "т/конс" + "э/конс" + экз + зач + контр) AS часов
FROM
tblНагрузки
GROUP BY
комм)
UNION
(SELECT
комм,
SUM(часов) AS часов
FROM
tblНагрузкиРуков
GROUP BY
комм)
UNION
(SELECT
комм,
SUM(практ + ГЭК + ГАК + прием + курат + "каф/рук" + "асп/рук" + факул) AS часов
FROM
tblНагрузкиДоп
GROUP BY
комм)
) AS Нагрузка
GROUP BY
комм;
-------------------------------------------------------------------------------------------
CREATE VIEW vwНагрузки1 AS
SELECT
fk_Заявка,
fk_Предмет,
tblЗаявки.fk_Поток AS fk_ПотокЗаявка,
tblНагрузки.fk_Поток AS fk_ПотокНагрузка,
(CASE
WHEN семестр THEN
1
ELSE
2
END) AS семестр,
SUM(tblНагрузки.лек) AS лек,
SUM(tblНагрузки.сем) AS сем,
SUM(tblНагрузки.лаб) AS лаб,
SUM(tblНагрузки."т/конс") AS "т/конс",
SUM(tblНагрузки."э/конс") AS "э/конс",
SUM(tblНагрузки.экз) AS экз,
SUM(tblНагрузки.зач) AS зач,
SUM(tblНагрузки.контр) AS контр,
tblНагрузки.комм AS комм,
fk_Преподаватель
FROM
tblЗаявки
LEFT JOIN tblНагрузки ON tblЗаявки.pk_Заявка = tblНагрузки.fk_Заявка
GROUP BY
fk_Заявка,
fk_Предмет,
tblЗаявки.fk_Поток,
tblНагрузки.fk_Поток,
семестр,
tblНагрузки.комм,
fk_Преподаватель;
CREATE VIEW vwНагрузкиРуков1 AS
SELECT
fk_ЗаявкаРуков,
fk_Предмет,
tblЗаявкиРуков.fk_Поток AS fk_Поток,
(CASE
WHEN семестр THEN
1
ELSE
2
END) AS семестр,
COUNT(*) AS студентов,
(CASE
WHEN "курс/раб" THEN
SUM(tblНагрузкиРуков.часов)
ELSE
0
END) AS курсов,
(CASE
WHEN "дип/бак" THEN
SUM(tblНагрузкиРуков.часов)
ELSE
0
END) AS димпл,
tblНагрузкиРуков.комм AS комм,
fk_Преподаватель
FROM
tblЗаявкиРуков
LEFT JOIN tblНагрузкиРуков ON tblЗаявкиРуков.pk_ЗаявкаРуков = tblНагрузкиРуков.fk_ЗаявкаРуков
GROUP BY
fk_ЗаявкаРуков,
fk_Предмет,
tblЗаявкиРуков.fk_Поток,
семестр,
"курс/раб",
"дип/бак",
tblНагрузкиРуков.комм,
fk_Преподаватель;
CREATE VIEW vwНагрузкиДоп1 AS
SELECT
pk_НагрузкаДоп AS fk_НагрузкаДоп,
fk_Поток,
(CASE
WHEN семестр THEN
1
ELSE
2
END) AS семестр,
практ,
ГЭК+ГАК AS ГАК,
"асп/рук",
"каф/рук",
факул,
курат,
прием,
комм,
fk_Преподаватель
FROM
tblНагрузкиДоп;
CREATE VIEW vwКарточки1 AS
SELECT
*
FROM
((
SELECT
fk_Предмет,
fk_ПотокЗаявка AS fk_Поток,
CASE
WHEN vwНагрузки1.комм THEN
колКомм
ELSE
колБюджет
END AS студентов,
CASE
WHEN vwНагрузки1.комм THEN
лекКомм
ELSE
лекБюджет
END AS лекГрупп,
CASE
WHEN vwНагрузки1.комм THEN
семКомм
ELSE
семБюджет
END AS семГрупп,
CASE
WHEN vwНагрузки1.комм THEN
лабКомм
ELSE
лабБюджет
END AS лабГрупп,
семестр,
SUM(vwНагрузки1.лек) AS лек,
SUM(vwНагрузки1.сем) AS сем,
SUM(vwНагрузки1.лаб) AS лаб,
SUM(vwНагрузки1."т/конс") AS "т/конс",
SUM(vwНагрузки1."э/конс") AS "э/конс",
SUM(vwНагрузки1.экз) AS экз,
SUM(vwНагрузки1.зач) AS зач,
0 AS практ,
0 AS курсов,
0 AS димпл,
0 AS ГАК,
SUM(vwНагрузки1.контр) AS контр,
0 AS "асп/рук",
0 AS "каф/рук",
0 AS факул,
0 AS курат,
0 AS прием,
vwНагрузки1.комм AS комм,
fk_Преподаватель
FROM
vwНагрузки1
LEFT JOIN vwПодгруппы ON vwНагрузки1.fk_ПотокЗаявка = vwПодгруппы.fk_Поток
GROUP BY
vwНагрузки1.fk_ПотокЗаявка,
fk_Предмет,
студентов,
лекГрупп,
семГрупп,
лабГрупп,
семестр,
vwНагрузки1.комм,
fk_Преподаватель
) UNION (
SELECT
fk_Предмет,
fk_Поток,
студентов,
0 AS лекГрупп,
0 AS семГрупп,
0 AS лабГрупп,
семестр,
0 AS лек,
0 AS сем,
0 AS лаб,
0 AS "т/конс",
0 AS "э/конс",
0 AS экз,
0 AS зач,
0 AS практ,
курсов,
димпл,
0 AS ГАК,
0 AS контр,
0 AS "асп/рук",
0 AS "каф/рук",
0 AS факул,
0 AS курат,
0 AS прием,
комм,
fk_Преподаватель
FROM
vwНагрузкиРуков1
) UNION (
SELECT
NULL AS fk_Предмет,
vwНагрузкиДоп1.fk_Поток AS fk_Поток,
CASE
WHEN vwНагрузкиДоп1.комм THEN
колКомм
ELSE
колБюджет
END AS студентов,
0 AS лекГрупп,
0 AS семГрупп,
0 AS лабГрупп,
семестр,
0 AS лек,
0 AS сем,
0 AS лаб,
0 AS "т/конс",
0 AS "э/конс",
0 AS экз,
0 AS зач,
практ,
0 AS курсов,
0 AS димпл,
ГАК,
0 AS контр,
"асп/рук",
"каф/рук",
факул,
курат,
прием,
vwНагрузкиДоп1.комм AS комм,
fk_Преподаватель
FROM
vwНагрузкиДоп1
LEFT JOIN vwПодгруппы ON vwНагрузкиДоп1.fk_Поток = vwПодгруппы.fk_Поток
)) AS нагрука;
CREATE VIEW vwКарточки2 AS
SELECT
*
FROM
((
SELECT
fk_Предмет,
fk_ПотокЗаявка AS fk_Поток,
CASE
WHEN vwНагрузки1.комм THEN
колКомм
ELSE
колБюджет
END AS студентов,
CASE
WHEN vwНагрузки1.комм THEN
лекКомм
ELSE
лекБюджет
END AS лекГрупп,
CASE
WHEN vwНагрузки1.комм THEN
семКомм
ELSE
семБюджет
END AS семГрупп,
CASE
WHEN vwНагрузки1.комм THEN
лабКомм
ELSE
лабБюджет
END AS лабГрупп,
семестр,
SUM(vwНагрузки1.лек) AS лек,
SUM(vwНагрузки1.сем) AS сем,
SUM(vwНагрузки1.лаб) AS лаб,
SUM(vwНагрузки1."т/конс") AS "т/конс",
SUM(vwНагрузки1."э/конс") AS "э/конс",
SUM(vwНагрузки1.экз) AS экз,
SUM(vwНагрузки1.зач) AS зач,
0 AS практ,
0 AS курсов,
0 AS димпл,
0 AS ГАК,
SUM(vwНагрузки1.контр) AS контр,
0 AS "асп/рук",
0 AS "каф/рук",
0 AS факул,
0 AS курат,
0 AS прием,
vwНагрузки1.комм AS комм
FROM
vwНагрузки1
LEFT JOIN vwПодгруппы ON vwНагрузки1.fk_ПотокЗаявка = vwПодгруппы.fk_Поток
GROUP BY
vwНагрузки1.fk_ПотокЗаявка,
fk_Предмет,
студентов,
лекГрупп,
семГрупп,
лабГрупп,
семестр,
vwНагрузки1.комм
) UNION (
SELECT
fk_Предмет,
fk_Поток,
SUM(студентов) AS студентов,
0 AS лекГрупп,
0 AS семГрупп,
0 AS лабГрупп,
семестр,
0 AS лек,
0 AS сем,
0 AS лаб,
0 AS "т/конс",
0 AS "э/конс",
0 AS экз,
0 AS зач,
0 AS практ,
SUM(курсов) AS курсов,
SUM(димпл) AS димпл,
0 AS ГАК,
0 AS контр,
0 AS "асп/рук",
0 AS "каф/рук",
0 AS факул,
0 AS курат,
0 AS прием,
комм
FROM
vwНагрузкиРуков1
GROUP BY
fk_Предмет,
fk_Поток,
семестр,
комм
) UNION (
SELECT
NULL AS fk_Предмет,
vwНагрузкиДоп1.fk_Поток AS fk_Поток,
CASE
WHEN vwНагрузкиДоп1.комм THEN
колКомм
ELSE
колБюджет
END AS студентов,
0 AS лекГрупп,
0 AS семГрупп,
0 AS лабГрупп,
SUM(семестр),
0 AS лек,
0 AS сем,
0 AS лаб,
0 AS "т/конс",
0 AS "э/конс",
0 AS экз,
0 AS зач,
SUM(практ),
0 AS курсов,
0 AS димпл,
SUM(ГАК),
0 AS контр,
"асп/рук",
"каф/рук",
SUM(факул),
SUM(курат),
SUM(прием),
vwНагрузкиДоп1.комм AS комм
FROM
vwНагрузкиДоп1
LEFT JOIN vwПодгруппы ON vwНагрузкиДоп1.fk_Поток = vwПодгруппы.fk_Поток
GROUP BY
fk_НагрузкаДоп,
vwНагрузкиДоп1.fk_Поток,
vwНагрузкиДоп1.комм,
колКомм,
колБюджет,
семестр,
"асп/рук",
"каф/рук"
)) AS нагрука;
Заключение
Повторно предлагаю следующие решение (набросок).
- GUI на PyQt или PySide
- СУБД PosgreSQL (у меня здесь готово примерно на 80%), в ней кроме самого расписания еще заявки и нагрузка преподавателей, учебные планы и еще много чего (с этой целью опубликую один или несколько топиков)
- web интерфейс на CherryPy+Cheetah (но это может обсуждаться)
- экспорт всяких отчетов (расписаний, карточек учебных поручений и т.д.) в формате OpenDocument (ГОСТ Р ИСО/МЭК 26300-2010. Госстандарт России (01.06.2011)) посредством ODFPY
- алгоритмы составления расписания от меня (напишу об этом топик)
- постановка от меня
- для заинтересованных работа над общим ядром
- для заинтересованных адаптация под собственный ВУЗ и возможность гибко все менять, жизнь идет, а чиновники не дремлют
Спасибо Всем кто откликнулся, после публикации топика по алгоритмам составления расписания можно будет со организоваться.
Автор: bya