Имеем бд на postgresql.Имеем некую форму для изменения данных ( назовем это карточка объекта) она очень большая - и располагается на нескольких страницах ( используется jquery tabs). Так вот - вывод и заполнение всех в форме это не проблема. Проблема заключается в том чтобы не обновлять все поля - а каким то образом обновить в бд только измененные .. а вот как это сделать - не совсем понимаю. Как определить что поле изменено.
Не заморачивайся насчет отдельных полей, обновляй всю запись целиком. Недавно сам озабачивался задачей "как определить какие из записей в табличной форме были изменены". Впервые использовал операцию clone и операцию сравнения объектов Всё когда-то бывает впервые. У меня есть некий Data Mapper и итератор для представления коллекции записей. После отправки формы в цикле проверяю элементы коллекции. Примерно так: Код (PHP): foreach ($Collection as $myObjects) { $row = $form[$myObject->id]; // форма как массив записей, проиндексированных по ID $shapshot = clone $myObject; // здесь будет "старая версия" объекта $repo->load($myObject, $row); // применяем поля из формы // не факт, что хоть то-нибудь изменилось if ($myObject != $shapshot) { // PHP умеет сравнивать объекты! $repo->persist($myObject); // сохраняем если были изменения } unset($shapshot); }
Я просто немного недорассказал - почему именно измененные поля меня интересуют .. Это корпоративная база данных - и иногда в процессе работы ктото данные меняет - и требуется хранить историю изменений за весь период. Т.е. в отдельную таблицу должны сваливаться данные - кто когда и что поменял. я немного не понял представленный кусок кода.. тут идет сравнение двух форм это понятно - но откуда взять изначальную форму - ведь она ушла пользователю и он ее правит.. получается пользователь должен вернуть две формы - новую и старую ?
сравнение не двух форм, а двух состояний одной и той же записи. состояние "до" и состояние "после". Добавлено спустя 3 минуты 43 секунды: из твоего объяснения про историю изменений никак не следует, что сохранять надо не все поля. это просто отдельная задача — логи изменений. часто решается триггерами в базе, либо если есть какая-то ORM, используются ее встроенные воможности. по сути те же триггеры. подумай вот о чем: в бумажном документообороте очень часто документ состоит из заголовка документа и табличной части. в базе заводят, как минимум, две таблицы чтобы это описать: собственно документ и детализация. история изменений относится к сущности "документ", даже когда изменилась строка в детализации. короче говоря, если нужна история, это хороший повод изучить какой-нибудь ORM. чтобы оперировать "объектами предметной области" и поменьше думать о таблицах.
Как обычно я сначала пытаюсь навязать своё видение мира, а потом даю буквальный ответ на вопрос ))) Если твоя запись в скрипте в виде массива, ты можешь вычислить чем новая версия записи отличается от старой: в PHP есть функции array_diff, array_diff_assoc и др. похожие названия. Учи матчасть, пробуй, экспериментируй. Добавлено спустя 14 минут 41 секунду: Вот еще в копилку: Версионность и история данных
Храни рядом таблицу с полями: дата| пользователь| запрос Где запрос - это SQL-запрос, приведший к изменениям. Одно из самых простых, но мощных решений. Как только кто-то что-то меняет, делаешь два запроса - один, который меняет и, если транзакция завершится без ошибки, шлем второй запрос в копилку.
транзакция должна включать в себя все связанные операции, в т.ч. запись истории. иначе смысл транзакции теряется.
Окей, это никак не противоречит самому принципу такого логгирования. Пусть в одной транзакции идут запросы. Это действительно правильнее, а результат тот же.