Здравствуйте, vdimas, Вы писали:
V>Здравствуйте, gandjustas, Вы писали:
G>>При N=5 человек уже не может это делать.
V>Такой ты наивный... А как же раньше подобные задачи решались? )))
Также как и сейчас «решают», делают малое количество запросов\процедур, покрывающих сценарии. Запросы не эффективны, тормозят, пинают их хинтами, чтобы работало приемлемо.
V>Точно так же генерили SQL аж бегом.
Это только примитивные запросы, максимум джоины и простые предикаты, никаких группировок и подзапросов.
G>>Мой пример собирается в студии, я только оттуда несущественные детали убрал. Ты же пропустил довольно важные части.
V>А толку? Если в базе появилось лишнее поле, а ты забыл добавить его в свои объекты, то тебе компилятор не поможет. Зато помогли бы тулзы построения запросов — ты бы видел, что у тебя в базе.
Добавляй сразу в классы, ef добавит его в базу.
V>Более того, при ручной разработке запросов есть тенденция, что эти запросы будут оседать на стороне базы. А в твоём случае все запросы — динамические, даже когда 90% их статические или требует тривиальных аргументов. А у тебя выходит самый тормозной вариант из всех.
А с чего ты взял что динамические запросы — самый тормозной вариант? На практике как раз универсальный в среднем работает хуже, ибо кэширование планов и parameter sniffing problem, особенно когда запрос динамически строится внутри процедуры.
НС>... нового протокола не добавят.
В принципе это любопытно, и интересно будет следить чем закончится.
Интересно насколько сильно новый протокол окажется влияние на архитектуру SQL Server-а. Может они и реляционную модель собрались менять? Добавить поддержку связей типа message.Forum в сам SQL Server?
P.S. Пока ставлю на то, что эта благая затея закончится либо ничем, либо результат будет редко используемым. Никто не даст ломать SQL Server.
Здравствуйте, Ночной Смотрящий, Вы писали:
НС>Здравствуйте, gandjustas, Вы писали:
НС>>>Генерировать мапперы по IL можно и в компайл-тайме. То что EF этого не умеет вовсе не означает, что это вообще невозможно. G>>Только сейчас это нельзя включить в библиотеку.
НС>Можно и включить, ilmerge никто пока не отменял. Но ты не находишь, что от фатального недостатка ты перешел к мелким неудобствам?
А кто вызывать то будет? С Roslyn можно в один пакет собрать и рантайм, и расширение компилятора.
НС>>>Это никак не избавляет от того, о чем говорит IB. G>>Он говорит о тормознутом мепинге НС>Нет, он говорит о неправильной архитектуре, требующей лишних шагов.
Так шаги можно в compile time проходить.
G>>, при компиляции модели в код и генерации mapping view во время компиляции можно устранить тормоза полностью.
НС>Только тормоза во время компиляции. Но и этого у EF все равно нет.
О чем ты?
НС>>>При чем тут SOAP? G>>При то что это основа ws-* вебсервисов, на которые wcf рассчитан в первую очередь.
НС>То что он рассчитан в первую очередь, это уже твои фантазии. Я лично знаком с некоторыми из архитекторов WCF, и многопротокольность там закладывалась с самого начала как базовое требование. Причем не только в плане message протоколов, но и протоколов сетевых.
Наверное именно поэтому в wcf шандарахнутое управление соединением и такой же api для коллбеков. Такое ощущение что эти функции прикрутили сверху к api для обычных ws-* вебсервисов.
НС> И в том числе поэтому WCF на порядок гибче и шире по функционалу WebAPI, но и, как следствие, имеет более крутую learning curve.
Это все слова ни о чем. Без тулинга wcf вообще невозможно пользоваться, примерно также, как ef первой версии. Только ef прокачали, а wcf так и остался.
G>>>>Я написал что они взаимоисключающие? Самая проблема что они все разные. НС>>>Не вижу проблемы. G>>Ну попробуй сходу написать код для хоста wcf с di в классы сервисов.
НС>Да писал не раз. Если понимаешь как WCF устроен — особых проблем нет. Ну и DI сам по себе — далеко не серебряная пуля. G>> Что для этого нужно?
НС>Тривиально реализовать крошечный интерфейс — IInstanceProvider. Один раз, если уж тебе так DI мил.
Реализовать где? Там же еще behavior надо реализовать, а потом еще атрибут или трахаться с конфигом.
G>> Толи factory сделать, толи service behavior поменять и это настолько разные апи, что хрен разберешься как правильно. НС>Ну так и проблема в том что ты не разобрался, а не в WCF.
Я то разобрался, но дофига народу не могут. Причем в webapi проблем с этим нет. Там одна задача — один класс, в wcf надо 100500 классов.
НС>>>Это одна строчка. G>>Это больше, особенно когда у тебя хост не в asp.net
НС>Нет. Ты опять не разобрался.
Пример?
НС>>>Есть. G>>По сравнению с webapi считай что нет. НС>По сравнению с WebAPI она на порядок круче, потому что позволяет создавать собственные шаблоны конфигураций. Но ты, я понимаю, опять не разобрался.
Ага, но это еще 100500 классов.
G>Добавляй сразу в классы, ef добавит его в базу.
А можно мы будем разрабатывать БД сами отдельно. Дельта скрипты для новых версий схемы БД будем писать тоже сами. Пусть EF не беспокоится об этом.
Приложение шлет запросы к базе данных. Вот пусть ORM помогает только на уровне приложения. Проврка запросов на этапе компиляции -- замечательно. Например, поменяли схему БД и EF должна нам сказать, где в исходном коде приложения нужно внести изменения?
Если не сложно опиши, как в таком режиме работать с EF?
НС>Это означает что твой тип IMessageInfo adhoc, и нужен исключительно для этого конкретного запроса.
Не только для запроса. Ты, наверное, не обратил внимания, что свойства ForumShortName, CreatedOn, Subject у тебя находятся в MessageModel, а у меня их там нет, они в IMessageInfo. Т.е. IMessageInfo используется не только для запроса, а и для переноса данных наружу метода.
Замечу, что у тебя слова CreatedOn, Subject пришлось написать по два раза, у меня они пишутся по одному разу. Поэтому с IMessageInfo даже меньше писать пришлось, а, соответственно, и читается лучше.
НС>Вобщем, ты все отлично продемонстрировал. Я бы только не заикался после этого насчет сложности использования ExpressionMethod в linq2db.
что я продемонстрировал? ты, наверное, не обратил внимание, что поля переехали из MessageModel в IMessageInfo. Ты в ручную пишешь поля в MessageModel, у меня они автоматически генерируются в IMessageInfo.
AP>Вот пусть ORM помогает только на уровне приложения. Проврка запросов на этапе компиляции -- замечательно. Например, поменяли схему БД и EF должна нам сказать, где в исходном коде приложения нужно внести изменения?
Можно даже термин такой ввести "ненавязчивый ORM" (unobtrusive).
Здравствуйте, gandjustas, Вы писали:
НС>>Можно и включить, ilmerge никто пока не отменял. Но ты не находишь, что от фатального недостатка ты перешел к мелким неудобствам? G>А кто вызывать то будет?
В смысле? Прописываешь таску в файл проекта, при компиляции msbuild позовет.
НС>>Нет, он говорит о неправильной архитектуре, требующей лишних шагов. G>Так шаги можно в compile time проходить.
Я бы не был так в этом уверен.
НС>>Только тормоза во время компиляции. Но и этого у EF все равно нет. G>О чем ты?
О том что EF не умеет прекомпиляцию.
НС>>То что он рассчитан в первую очередь, это уже твои фантазии. Я лично знаком с некоторыми из архитекторов WCF, и многопротокольность там закладывалась с самого начала как базовое требование. Причем не только в плане message протоколов, но и протоколов сетевых. G>Наверное именно поэтому в wcf шандарахнутое управление соединением
В чем оно шандарахнутое?
G>Такое ощущение что эти функции прикрутили сверху к api для обычных ws-* вебсервисов.
Это только ощущение.
G>Это все слова ни о чем.
Это не слова, это факты — функционал у WCF шире.
G> Без тулинга wcf вообще невозможно пользоваться
Не знаю о каком тулинге речь, но я в свое время пользовался.
НС>>Тривиально реализовать крошечный интерфейс — IInstanceProvider. Один раз, если уж тебе так DI мил. G>Реализовать где?
В своем проекте или в библиотеке DI.
G> Там же еще behavior надо реализовать,
Не надо.
G> а потом еще атрибут
Там всего строчек 5. Можно скопировать из примеров не включая моск. И, повторяю, сделать это надо ровно один раз. Проблема не стоит и выеденного яйца, не в пример старому ASP.NET, спроектированному через жопу.
НС>>Ну так и проблема в том что ты не разобрался, а не в WCF. G>Я то разобрался, но дофига народу не могут.
Кому надо, те могут.
G> Причем в webapi проблем с этим нет.
Зато там с другим проблемы есть.
G> Там одна задача — один класс, в wcf надо 100500 классов.
Не надо.
НС>>>>Это одна строчка. G>>>Это больше, особенно когда у тебя хост не в asp.net НС>>Нет. Ты опять не разобрался. G>Пример?
У меня совсем умолчальных примеров под рукой нет. Есть с некоторым конфигурированием из собственного конфига.
using (var host = new ServiceHost(info.Type, svcUris))
{
for (var i = 0; i < svcUris.Length; i++)
host.AddServiceEndpoint(
info.ContractType,
_commHelper.CreateBinding(_endpointConfigs[i].Transport),
svcUris[i]);
host.Open();
}
Конфигурирование WebAPI без IIS требует примерно сопоставимого объема кода.
НС>>По сравнению с WebAPI она на порядок круче, потому что позволяет создавать собственные шаблоны конфигураций. Но ты, я понимаю, опять не разобрался. G>Ага, но это еще 100500 классов.
В WebAPI тебе и 100500 классов не поможет. У каждого инструмента свои особенности.
Здравствуйте, Alexander Polyakov, Вы писали:
НС>>Вобщем, ты все отлично продемонстрировал. Я бы только не заикался после этого насчет сложности использования ExpressionMethod в linq2db. AP>что я продемонстрировал?
Кучу гемороя и раздутый плохочитаемый код на ровном месте вместо изящного и лаконичного решения на LINQ.
AP> ты, наверное, не обратил внимание, что поля переехали из MessageModel в IMessageInfo
MessageModel это вообще из другой области, это модель MVC вьюхи, и в ней есть данные, которые не из этого запроса берутся. Так что твои типы не спасут.
НС>Кучу гемороя и раздутый плохочитаемый код на ровном месте вместо изящного и лаконичного решения на LINQ.
Напиши какие элементы в моем коде раздули его, т.е. какие лишние элементы?
Какой геморой?
На EF6 у меня вот такой код падает в рантайме
List<int> list = entities.Message.Select(_ => _.Account.Field1).ToList();
с сообщением
Additional information: The cast to value type 'System.Int32' failed because the materialized value is null. Either the result type's generic parameter or the query must use a nullable type.
В моем подходе такое отловится на этапе CheckAllQueries. Т.е. геморрой получили на LINQ EF6.
AP>> ты, наверное, не обратил внимание, что поля переехали из MessageModel в IMessageInfo НС>MessageModel это вообще из другой области, это модель MVC вьюхи, и в ней есть данные, которые не из этого запроса берутся. Так что твои типы не спасут.
В общем случае ты прав. А практически три из четырех полей все равно нужны в MessageModel, т.е. три поля, скорее всего, будут и в других запросах, заполняющих MessageModel. Оставшееся поле Text, да, может заполнятся не как функция от Origin. Но в реальности это не так часто. И для этих частых случаев сделать почти автогенеренный тип не проблема.
Здравствуйте, Alexander Polyakov, Вы писали:
G>>Добавляй сразу в классы, ef добавит его в базу. AP>А можно мы будем разрабатывать БД сами отдельно. Дельта скрипты для новых версий схемы БД будем писать тоже сами. Пусть EF не беспокоится об этом. AP>Приложение шлет запросы к базе данных. Вот пусть ORM помогает только на уровне приложения. Проврка запросов на этапе компиляции -- замечательно. Например, поменяли схему БД и EF должна нам сказать, где в исходном коде приложения нужно внести изменения? AP>Если не сложно опиши, как в таком режиме работать с EF?
Как хочешь, хоть руками пиши, хоть генерируй. Проблема все равно переходит на этап развертывания, ибо синхронизировать базу и код в разных средах становится проблемой.
Вариант получше — используй миграции с помощью тех же скриптов, только не автоматически, а по запросу. Тогда код и база будут синхронизированы или приложение упадет.
G>Как хочешь, хоть руками пиши, хоть генерируй. Проблема все равно переходит на этап развертывания, ибо синхронизировать базу и код в разных средах становится проблемой. G>Вариант получше — используй миграции с помощью тех же скриптов, только не автоматически, а по запросу. Тогда код и база будут синхронизированы или приложение упадет.
Какой сейчас рекомендованный вариант для получения классов из схемы БД? Т.е. я добавил колонку в БД, какую кнопку нажиматься, чтобы поле в классе появилось?
Здравствуйте, Alexander Polyakov, Вы писали:
AP>Напиши какие элементы в моем коде раздули его, т.е. какие лишние элементы? AP>Какой геморой?
AP>На EF6 у меня вот такой код падает в рантайме AP>
AP>List<int> list = entities.Message.Select(_ => _.Account.Field1).ToList();
AP>
Это личные проблемы EF6. А точнее кривой модели, в которой для nullable поля должно быть int?.
НС>>MessageModel это вообще из другой области, это модель MVC вьюхи, и в ней есть данные, которые не из этого запроса берутся. Так что твои типы не спасут. AP>В общем случае ты прав.
НС>Это личные проблемы EF6. А точнее кривой модели, в которой для nullable поля должно быть int?.
Ты, наверное, не понял. В базе Field1 NOT NULL. Null получается за счет LEFT JOIN-а. Это протечка linq абстракций.
Здравствуйте, Alexander Polyakov, Вы писали:
НС>>Кучу гемороя и раздутый плохочитаемый код на ровном месте вместо изящного и лаконичного решения на LINQ. AP>Напиши какие элементы в моем коде раздули его, т.е. какие лишние элементы? AP>Какой геморой?
AP>На EF6 у меня вот такой код падает в рантайме AP>
AP>List<int> list = entities.Message.Select(_ => _.Account.Field1).ToList();
AP>
AP>с сообщением AP>
AP>Additional information: The cast to value type 'System.Int32' failed because the materialized value is null. Either the result type's generic parameter or the query must use a nullable type.
AP>В моем подходе такое отловится на этапе CheckAllQueries. Т.е. геморрой получили на LINQ EF6.
Каким образом? Нельзя замапить nullable поле запроса, на non-nullable поле объекта? Но ведь мотом можно написать присвоение в select и получить ту же ошибку.
Здравствуйте, Alexander Polyakov, Вы писали:
G>>Как хочешь, хоть руками пиши, хоть генерируй. Проблема все равно переходит на этап развертывания, ибо синхронизировать базу и код в разных средах становится проблемой. G>>Вариант получше — используй миграции с помощью тех же скриптов, только не автоматически, а по запросу. Тогда код и база будут синхронизированы или приложение упадет. AP>Какой сейчас рекомендованный вариант для получения классов из схемы БД? Т.е. я добавил колонку в БД, какую кнопку нажиматься, чтобы поле в классе появилось?
Update model from database. Доступно еще с ef4.
G>Update model from database. Доступно еще с ef4.
Ну, т.е. это правильный способ? А то я волнуюсь вдруг эту ветку они закроют, ты вон агрессивно проповедуешь code first.
G>Каким образом? Нельзя замапить nullable поле запроса, на non-nullable поле объекта? Но ведь мотом можно написать присвоение в select и получить ту же ошибку.
У меня в аналогичном запросе проблем нет:
var list = Query<int>.New(new {threshold = 10m}, @"
SELECT Field1
FROM Message
LEFT JOIN Account ON Account.Id = Message.AccountId
").List();
CheckAllQueries указывает, что int надо заменить на "int?". Никаких протекших абстракций нет.