Qt

Динамическое создание виджетов Qt. QGridLayout

В этом сообщении хотелось бы немного отредактировать предыдущий подобный пост Qt. Динамическое создание виджетов на форме.

Задача такая же: Есть объект QGroupBox groupBox, в него надо запихнуть виджеты (labels & lineEdits) в QGridLayout лэйауте. Данные берутся из запроса (он представлен в сообщении по ссылке выше).

Более универсальный способ будет выглядеть так:

if(ui->groupBox->layout()) {
	QLayoutItem *child;
    while ((child = ui->groupBox->layout()->takeAt(0)) != 0) {
    	delete child->widget();
        delete child;
    }
    delete ui->groupBox->layout();
}
QGridLayout *layout = new QGridLayout(ui->groupBox);
ui->groupBox->setLayout(layout);
int pos = 0; //устанавливаем позицию расположения виджетов в 0
int colsCount = 2; //Количество колонок в лэйауте
while (query.next()) { //берем результаты запроса
	QLabel *newLabel = new QLabel(this);
    newLabel->setText(query.value("caption").toString()+":");
    newLabel->setObjectName("label_"+query.value("name_").toString());
    layout->addWidget(newLabel,pos/colsCount,pos%colsCount);
    pos++; //сдвигаемся

    QLineEdit *newEdit = new QLineEdit(this);
    newEdit->setObjectName(query.value("name_").toString());
    layout->addWidget(newEdit,pos/colsCount,pos%colsCount);
    lineEdits.push_back(newEdit);
    pos++;
}

В данном случае мне необходимо было разместить объекты в бокс с двумя колонками. Поэтому colsCount = 2. Если их должно быть больше, то значение переменной нужно поменять. Очищение лэйаута позволяет при изменении результатов запроса все очистить и нарисовать все в соответствии с актуальными данными.

PostgreSQL, Qt, Портфолио

DBServerWizard — автоматизация работы с базами данных PostgreSQL

Сегодня хочу познакомить вас с утилитой DBServerWizard, написание которой закончила намедни. Если коротко, ее предназначение — самые базовые элементы управления базами данных PostgreSQL.

МенюУстановка сервераРезервное копирование/ восстановление из копииСоздание базы данных
Меню
Установка сервера
Бэкап/рестор
Создание БД

А если расписать немного подробнее, то перечень такой:

  • Установка сервера PostgreSQL (включает предварительную проверку наличия уже установленного сервера).
  • Создание и удаление баз данных. Есть некоторый обязательный набор баз данных; при подключении к серверу происходит проверка наличия этого минимального набора, если какие-либо БД из этого списка отсутствуют, то предлагается произвести создание БД и восстановление из бэкапа. Доступно принудительное удаление при наличии «застрявших» подключений, мешающих операции.
  • Резервное копирование и восстановление из копии. Перед восстановлением базы данных производится резервное копирование «на всякий случай».
  • Обновление баз данных из скриптов. Скрипт разделяется на отдельные инструкции, которые выполняются последовательно. Невыполненные инструкции записываются в отдельный файл.

Следующие сообщения были написаны в течение работы над утилитой:

Qt: Восстановление pg_restore БД PostgreSQL в Windows

Принудительное удаление базы данных в PostgreSQL

Qt: Резервная копия pg_dump БД PostgreSQL в Windows

Файл паролей PostgreSQL pgpass в Windows

Путь к каталогу bin PostgreSQL Windows

Чтобы заказать проект или получить консультацию, перейдите, пожалуйста, на страницу Контакты.

Моё портфолио

Инфо обо мне

PostgreSQL, Qt

Qt: Восстановление pg_restore БД PostgreSQL в Windows

Здесь: Qt: Резервная копия pg_dump БД PostgreSQL в Windows я показала один из способов организации создания резервной копии базы данных.

Сейчас речь пойдет о восстановлении базы из бэкапа. Здесь тоже будем использовать пакетный файл для вызова pg_restore.

Про каталог bin, файл паролей pgpass написано в статье по ссылке выше.

//name - имя базы данных
//file - файл резервной копии
void myClass::restoreDatabase(QString name, QString file)
{
    QString errorMsg;
    QString connectionName = connectToDB(name, errorMsg);
    if (connectionName.isEmpty()){
        error(errorMsg);
        return;
    }
    QString binDir = postgresBinDirectory();
    if (binDir.isEmpty()) {
        error(tr("Системный каталог bin сервера не найден. Операция "
                 "восстановления базы данных %1 из резервной копии %2 прервана")
              .arg(name).arg(file));
        QSqlDatabase::removeDatabase(connectionName);
        return;
    }
    QSqlQuery query(QSqlDatabase::database(connectionName));
	//сначала удаляем схему (у меня паблик), 
	//затем ее снова создаем - чистенькую
    if (!query.exec(QString("DROP SCHEMA public cascade;  "
                            "CREATE SCHEMA public "
                            "AUTHORIZATION postgres; "
                            "COMMENT ON SCHEMA public "
                            "IS 'standard public schema'; "
                            "GRANT ALL ON SCHEMA public TO PUBLIC; "
                            "GRANT ALL ON SCHEMA public TO %1;")
                    .arg(postgresUser))) {
        error(tr("Ошибка удаления схемы базы данных %1: %2")
              .arg(name).arg(query.lastError().text()));
        QSqlDatabase::removeDatabase(connectionName);
        return;
    }
    QSqlDatabase::removeDatabase(connectionName);
	//текст batch-файла
    QString batText = QString("@ECHO OFF \n"
                              "SET dmpfile=%1 \n"
                              "set text = Begin to restore...  \n"
                              "echo %text% \n"
                              "cd /d %2 \n"
                              "pg_restore --host=%4 --port=%5 "
                              "--username=%6 --verbose -d "
                              " %3 \"%dmpfile%\"\n"
                              "set /p id=\"The process is finished successfully. "
                              "Press Enter to exit...\"")
            .arg(file, binDir, name,
                 host, ui->port->text(), postgresUser);
    QString fileName = QString("%1-restore.bat")
            .arg(name);
    if (!writeBatFile(batText, fileName, 
					  QCoreApplication::applicationDirPath()+"/temp"))
        return;
	//обновляем файл паролей, если нужно
    updatePgPassFile(QString("%1:%2:%3:%4:%5")
                     .arg(host,
                          ui->port->text(),
                          name,
                          postgresUser,
                          ui->password->text()));
	//вызываем пакетный файл для выполнения восстановления базы данных
    system(qPrintable("cmd.exe /c \""+
                      QDir::toNativeSeparators(
                          QString("%1/%2")
                          .arg(QCoreApplication::applicationDirPath()+"/temp")
                          .arg(fileName)+"\"")));
}

 

PostgreSQL, Qt, Базы данных

Qt: Резервная копия pg_dump БД PostgreSQL в Windows

Пример того, как можно реализовать резервное копирование базы данных PostgreSQL в Qt. Создается batch-файл, где вызывается утилита pg_dump.

//QString name - имя базы данных для создания копии
//file - "куда складывать" бэкап
bool myClass::backupDatabase(QString name, QString file)
{
    QString binDir = postgresBinDirectory();
    if (binDir.isEmpty()) {
        error(tr("Системный каталог bin сервера не найден. "
				 "Операция восстановления базы данных "
				 "%1 из резервной копии %2 прервана")
              .arg(name).arg(file));
        return false;
    }
    if (file.isEmpty()) {
        QDir dir(QCoreApplication::applicationDirPath()+
				 "/db_dumps/");
        if (!dir.exists())
            dir.mkpath(QCoreApplication::applicationDirPath()+
					   "/db_dumps/");
        file = QString("%1/%2-%3.dump")
                .arg(QCoreApplication::applicationDirPath()+
					 "/db_dumps")
                .arg(name)
                .arg(QDateTime::currentDateTime()
					 .toString("yyyyMMddhhmm"));
    }
    QString text = QString(
		"@ECHO OFF \n"
        "cd /d %1 \n"
        "pg_dump -Fc -U %4 -Z 9 -v %2 > \"%3\" \n"
        "set /p id=\"Press Enter to exit...\"\n")
            .arg(binDir)
            .arg(name)
            .arg(file)
            .arg(postgresUser);
    QString fileName = QString("%1-dump.bat")
            .arg(name);
	//запись Значения строки text в файл *.bat
    if (!writeBatFile(text, fileName, 
				 QCoreApplication::applicationDirPath()+"/temp"))
		return;
	//обновление файла паролей pgpass
    updatePgPassFile(QString("%1:%2:%3:%4:%5")
                     .arg(host,
                          ui->port->text(),
                          name,
                          postgresUser,
                          ui->password->text()));
	//вызов созданного batch файла
    system(qPrintable("cmd.exe /c \""+
                      QDir::toNativeSeparators(
                          QString("%1/%2")
                          .arg(QCoreApplication::applicationDirPath()+
							   "/temp")
                          .arg(fileName)+"\"")));
	//если файл бэкапа имеет ненулевой размер
    return QFileInfo(file).size() > 0;
}

Как узнать путь к каталогу bin сервера PostgreSQL, подробно написано здесь: Путь к каталогу bin PostgreSQL Windows. При условии известности имени пользователя и его пароля можно запустить утилиту pg_dump без необходимости авторизации пользователем при наличии соответствующей строки подключения в файле паролей pgpass, про что подробно писала в этой статье: Файл паролей PostgreSQL pgpass в Windows. В вышеприведенном коде используется функция updatePgPassFile(QString), код которой можно найти по обозначенной ссылке.

Более ранняя статья на схожую тему: Резервное копирование базы данных по расписанию: MS SQL Server и PostgreSQL

PostgreSQL, Qt, Базы данных

Файл паролей PostgreSQL pgpass в Windows

Для восстановления базы данных из резервной копии используется исполняемый файл сервера pg_restore. Если в настройках сервера выставлена авторизация по имени и паролю, то при использовании утилиты необходимо вводить пароль при каждой операции восстановления БД из бэкапа. Что не подходит в случае пакетной операции, например, или когда операция должна производится без взаимодействия с пользователем в этом ключе. Тогда сервер использует файл паролей pgpass. Он может и отсутствовать. Что тогда делать? Создать и обновлять. Продолжить чтение «Файл паролей PostgreSQL pgpass в Windows»

PostgreSQL, Qt, Базы данных

Путь к каталогу bin PostgreSQL Windows

Задача: получить значение пути к каталогу бинарников сервера — к каталогу bin. Путь к каталогу data, как и прочие значения параметров времени выполнения, найти совершенно несложно: достаточно выполнить запрос show, воспользоваться функцией current_setting() или обратиться к представлению pg_settings:

show data_directory;
select current_setting('data_directory');
select setting from pg_settings 
   where name = 'data_directory';
Три равнозначных примера получения значения пути к каталогу data

Еще парочку примеров показывала вот в этой записи: Количество подключений к БД PostgreSQL.

С значением пути к каталогу bin не все так просто — запросом его не получишь. Но можно узнать из реестра. В реестре не хранится чистый ключ со значением пути к каталогу, к сожалению, но можно узнать путь к исполняемому файлу службы сервера.

Итак, интересующий нас ключ: Продолжить чтение «Путь к каталогу bin PostgreSQL Windows»

"Нет" выгоранию, C++, PostgreSQL, Qt, Мысли вслух

Незамеченные записи 2019 года

Начнем еще одну традицию — заведем тему о скромных темах. Стоят там в сторонке, никто на них не смотрит 🙂

  1. «Нет» выгоранию: прогулки на свежем воздухе
  2. Волшебство в обычном месте
  3. Мини-путешествие к Браславским озёрам
  4. Jobs trace: Учет потраченного на проекты времени
  5. Няня вместо мамы для больничных детей
  6. Qt: Добавить свой виджет на форму
  7. DBRecordWidget — Библиотека-виджет для работы с данными (Qt)
  8. Вывод даты с указанием часового и минутного смещения timezone в PostgreSQL
  9. Количество подключений к БД PostgreSQL
  10. Изменить цвет фона и текста ячейки или строки QTableView
Microsoft SQL Server, PostgreSQL, Qt, SQL, Базы данных

Лучшие записи 2019 года

Продолжим традицию: ниже темы, имеющие наилучшую статистику посещений за 2019 год. Пост за прошлый год: Лучшие записи за 2018 год

  1. Основы баз данных. ER-модель (сущность-связь)
  2. Добавление данных в таблицу QTableWidget. Очистка таблицы
  3. Функция, возвращающая таблицу returns table — в PostgreSQL и MS SQL Server
  4. PostgreSQL: unnest(array)
  5. PostgreSQL: Размер таблиц и базы данных
  6. PostgreSQL: Узнать данные о колонках таблицы
  7. Получить значения полей выделенной строки QTableView
  8. Qt. Динамическое создание виджетов на форме
  9. Триггеры в PostgreSQL
  10. Подключение к базе данных в Qt
C++, Qt, Портфолио

Jobs trace: Учет потраченного на проекты времени

В сообщении Qt: Добавить свой виджет на форму уже немного рассказала по поводу вышеуказанной темы. А тема — небольшая программка Jobs trace 🙂

Я вписывала в Гугл таблицы проведенное время над тем или иным проектом или отдельным заданием и , исходя из этих данных, высчитывала стоимость работы. Но для меня такой вариант не очень удобен — каждый раз регистрировать время начала и конца, потом это все подводить к итогу и т.д. Мне показалось это муторным, я решила поискать какой-то онлайн подсчитыватель отработанного времени. Но все это было не то. Было решено — напишу так, как надо мне, чтобы было просто и удобно:

  • Признак начала и конца работы над проектом — один клик по кнопке
  • Автоматический расчет стоимости работы по введенной почасовой ставке
  • Сохранение данных текущих заданий
  • Возможность ведения нескольких заданий
  • Каждое задание на своей вкладке
  • Присваивать заданию пользовательское название
  • После переоткрытия приложения разворачивать данные уже имеющихся заданий
  • Удаление заданий кликом по кнопке

[metaslider id=819]

Данные задания записываются в текстовый файл с содержимым вида:

<Название задания>

<Количество потраченных на проект секунд>

<Почасовая ставка>

При постановке задания на паузу и при выходе из программы этот файл обновляется. Также записывается текущий лог хода работы над проектом в отдельный файл (в качестве дополнительной аналитической информации).

Сам проект Jobs trace можно посмотреть/скачать/склонировать на bitbucket.org: https://bitbucket.org/secretsilent/jobstrace/

Qt

Qt: Добавить свой виджет на форму

Допустим, у нас есть определенный набор виджетов, который нужно повторить на каждой странице объекта QTabWidget. Этих страниц может быть очень много. Один из самых удобных и простых способов создавать такие страницы с нужным набором элементов — это создать виджет с этим набором и помещать его на каждую новую страницу.

Для создания виджета сделаем следующее: Файл->Создать файл или проект…->Qt (Класс формы Qt Designer), в разделе templates/forms выбираем Widget. Нам необходимо, чтобы наша форма была потомком QWidget.

На новой форме располагаем все необходимые элементы. Например, вот так: Продолжить чтение «Qt: Добавить свой виджет на форму»