Вопрос, поднятый пользователем, заключается в переводе SQL-запроса в OCL для повышения удобства поддержки кода в проекте, использующем Delphi 2007, Interbase 2009, а также фреймворк Bold и методы model-driven разработки. Пользователь столкнулся с SQL-запросом, который он хочет переписать на OCL, чтобы сделать код более поддерживаемым и простым в обслуживании.
Исходный SQL-запрос
Исходный SQL-запрос, представленный пользователем, включает выборку данных из таблицы ScaniaEdiSolMessage, с использованием подзапроса и условий фильтрации. Запрос выглядит следующим образом:
SELECT Bold_Id, MessageId, ScaniaId, MessageType, MessageTime, Cancellation, ChassiNumber, UserFriendlyFormat, ReceivingOwner, Invalidated, InvalidationReason,
(SELECT Parcel.MCurrentStates FROM Parcel
WHERE ScaniaEdiSolMessage.ReceivingOwner = Parcel.Bold_Id) as ParcelState
FROM ScaniaEdiSolMessage
WHERE MessageType = 'IFTMBP' AND
NOT EXISTS (SELECT * FROM ScaniaEdiSolMessage EdiSolMsg
WHERE EdiSolMsg.ChassiNumber = ScaniaEdiSolMessage.ChassiNumber AND
EdiSolMsg.ShipFromFinland = ScaniaEdiSolMessage.ShipFromFinland AND
EdiSolMsg.MessageType = 'IFTMBF') AND
invalidated = 0
ORDER BY MessageTime DESC
После упрощения запрос выглядит так:
SELECT Bold_Id, (SELECT Parcel.MCurrentStates FROM Parcel
WHERE ScaniaEdiSolMessage.ReceivingOwner = Parcel.Bold_Id) FROM ScaniaEdiSolMessage
WHERE MessageType = 'IFTMBP' AND NOT EXISTS (SELECT * FROM ScaniaEdiSolMessage
EdiSolMsg WHERE EdiSolMsg.ChassiNumber = ScaniaEdiSolMessage.ChassiNumber AND
EdiSolMsg.ShipFromFinland = ScaniaEdiSolMessage.ShipFromFinland AND
EdiSolMsg.MessageType = 'IFTMBF') AND invalidated = 0
Запрос предназначен для работы с таблицей ScaniaEdiSolMessage, которая имеет атрибуты, такие как MessageType (тип данных String), ChassiNumber (тип данных String), ShipFromFinland (тип данных Boolean), Invalidated (тип данных Boolean), а также связь с таблицей Parcel через ассоциацию ReceivingOwner, ключом для которой служит BoldId.
Перевод SQL в OCL
Перевод SQL-запроса в OCL требует понимания объектно-ориентированного подхода и работы с ассоциациями между объектами. В OCL для получения всех экземпляров объекта используется выражение allInstances, а для фильтрации - метод select.
Пример OCL для фильтрации записей
ScaniaEdiSolMessage.allInstances->select(shipFromFinland and not invalidated)
Переписываем исходный SQL в OCL
Используя подход, предложенный в альтернативном ответе, можно переписать SQL-запрос в OCL, используя оператор пересечения (->intersection) для объединения различных наборов данных. Вот пример такого перевода:
ScaniaEdiSolMessage.allInstances->select(shipFromFinland and not invalidated)
->intersection(ScaniaEdiSolMessage.allInstances->select(m|m.ReceivingOwner.MessageType = 'IFTMBP'))
->intersection(Parcel.allInstances->select(p|p.Messages->exists(m|m.MessageType = 'IFTMBF')).Messages)
Или упрощенный вариант:
ScaniaEdiSolMessage.allInstances->select(m|
m.shipFromFinland and
m.not invalidated and
m.ReceivingOwner.MessageType = 'IFTMBP')
->intersection(ScaniaEdiSolMessage.allInstances->select(p|
p.Messages->exists(m|m.MessageType = 'IFTMBF')).Messages
))
Важно отметить, что в данном примере используется упрощение, предложенное в сообщениях пользователей, и предполагается, что методы и атрибуты используются в соответствии с контекстом и типизацией, определенными в модели данных.
Заключение
Перевод SQL-запросов в OCL может быть полезен для упрощения поддержки кода, особенно в среде, где используется объектно-ориентированный подход. Однако важно понимать различия между этими двумя подходами и их ограничения. Необходимо также учитывать, что OCL является более специализированным инструментом, чем SQL, и может потребоваться больше усилий для поиска разработчиков, знакомых с OCL, в случае передачи проекта.
Перевод SQL-запросов на объектно-ориентированный запросный язык (OCL) помогает повысить удобство поддержки кодовой базы в проектах, использующих Delphi и Interbase с методологией model-driven разработки.
Комментарии и вопросы
Получайте свежие новости и обновления по Object Pascal, Delphi и Lazarus прямо в свой смартфон. Подпишитесь на наш Telegram-канал delphi_kansoftware и будьте в курсе последних тенденций в разработке под Linux, Windows, Android и iOS