Russian Qt Forum

Qt => Работа с сетью => Тема начата: djfile от Сентябрь 28, 2012, 20:34



Название: Клиент -> сервер -> бд?
Отправлено: djfile от Сентябрь 28, 2012, 20:34
Здравствуйте. Объясните пожалуйста, правильно ли я понимаю принцип работы клиент-серверного приложения и помогите кое-какие пробелы заполнить?
Есть клиент, он хочет сделать запрос к серверу (как его делать в виде какого-то самописного протокола или в самом клиенте формировать SQL-запросы и передавать их серверу?), сервер получает запрос, обрабатывает его, делает выборку в бд и так далее. Результат запроса отдаем обратно клиенту (в каком виде? XML?).
Это вариант работы на выборку, а как реализовать вариант на добавление/изменение записей? Всё ещё сложнее...


Название: Re: Клиент -> сервер -> бд?
Отправлено: Bepec от Сентябрь 28, 2012, 20:40
Всё очень просто. Клиент - серверное приложение. Найдёте тут упоминание БД - кричите, я прибегу :)

Клиент отправляет запрос на сервер. Сервер получает, обрабатывает, посылает ответ. Всё.

Остальное лишь подробности реализации :)


Название: Re: Клиент -> сервер -> бд?
Отправлено: djfile от Сентябрь 29, 2012, 07:28
Вот меня эти подробности и интересуют. Например, данные хранятся в MySQL, клиент хочет получить какие-то данные. Во-первых нужно проверить залогинен ли он, потом только выполнять запрос. В таком случае, как я понимаю необходима программа-сервер, которая и будет отслеживать запросы к БД. Тогда в каком формате нужно передавать запросы и получать ответы?


Название: Re: Клиент -> сервер -> бд?
Отправлено: Bepec от Сентябрь 29, 2012, 08:39
В каком вам угодно. Посмотрите, погуглите, почитайте. Если нужна безопасность - один, если не нужна - другой. Если бесплатно - третий, если платно - четвёртый, если сам - то самому писать протокол.

Самое простое - пока клиент не залогинен, сервер от него пакеты в базу не принимает.

Вообще - почитайте о клиент-серверных приложениях и базах данных. Книг полно.


Название: Re: Клиент -> сервер -> бд?
Отправлено: djfile от Сентябрь 29, 2012, 13:34
Ответьте на следующие вопросы и тему можно закрыть.
1) Клиент общается с сервером, по принципу: отправили пакет, в котором стоит какая-то команда (число), получили соответствующий ей ответ?
2) В каком формате передаются данные от клиента к серверу?


Название: Re: Клиент -> сервер -> бд?
Отправлено: V1KT0P от Сентябрь 29, 2012, 13:40
Ответьте на следующие вопросы и тему можно закрыть.
1) Клиент общается с сервером, по принципу: отправили пакет, в котором стоит какая-то команда (число), получили соответствующий ей ответ?
2) В каком формате передаются данные от клиента к серверу?
1) Не обязательно, ты сам решаешь на какие команды нужны ответы на какие не нужны.
2) Да как захочешь, можешь текстом, можешь в бинарном виде, можешь в XML/JSON. А можешь вообще комбинировать.


Название: Re: Клиент -> сервер -> бд?
Отправлено: djfile от Сентябрь 29, 2012, 14:01
Ответьте на следующие вопросы и тему можно закрыть.
1) Клиент общается с сервером, по принципу: отправили пакет, в котором стоит какая-то команда (число), получили соответствующий ей ответ?
2) В каком формате передаются данные от клиента к серверу?
1) Не обязательно, ты сам решаешь на какие команды нужны ответы на какие не нужны.
2) Да как захочешь, можешь текстом, можешь в бинарном виде, можешь в XML/JSON. А можешь вообще комбинировать.

Запросы к БД может выполнять только мой сервер?


Название: Re: Клиент -> сервер -> бд?
Отправлено: V1KT0P от Сентябрь 29, 2012, 14:08
БД может выполнять только мой сервер?
Как ты захочешь так и будет, можешь открыть доступ к БД наружу без авторизации, можешь с авторизацией, можешь закрыть и дать возможность получать информацию через свой сервер(самое лучшее решение).


Название: Re: Клиент -> сервер -> бд?
Отправлено: djfile от Сентябрь 29, 2012, 14:23
БД может выполнять только мой сервер?
Как ты захочешь так и будет, можешь открыть доступ к БД наружу без авторизации, можешь с авторизацией, можешь закрыть и дать возможность получать информацию через свой сервер(самое лучшее решение).
Вот так понятнее=)
Короче, это я копаю тему для курсовой. Тема курсовой: учет тех осмотра ТС. Понятно, что данные должны быть закрыты от посторонних. Вот я и думаю как лучше это всё сделать. Раньше на Qt только интерфейсы делал, а тут решил 2х зайцев убить: и курсач и работу с сетью изучить.


Название: Re: Клиент -> сервер -> бд?
Отправлено: joker от Сентябрь 29, 2012, 15:44
А можно, можно я влезу?

На практике используют 2 вида клиент-серверных архитектур : двузвенная и трехзвеннная.

Двузвенная выглядит так: сервером выступает сама БД. Клиент цепляется к БД и выполняет необходимые запросы.

В трехзвенной же есть промежуточный сервер:  клиент общается с промежуточным сервером, сервер общается с БД.

Плюсы и минусы есть у каждого способа:

двузвенка на порядок проще и гораздо менее требовательна к ресурсам. Однако вся логика переносится на клиента = более высокие требования к оборудованию.

трехзвенка позволяет унифицировать обработку при разных клиентах (Rich-клиента, тонкий веб клиент, Android и iOS клиенты), позволит иметь возможность смены СУБД (клиент то запрос отправляет серверу), облегчит масштабирование системы (опять же потому что клиенту все равно что там будет твориться).
Однако такую систему сложнее разрабатывать и поддерживать.

В результате, ИМХО конечно же, Вам все же было бы проще работать с двузвенкой, а не трехзвенкой (которую вы и обсуждаете).

 


Название: Re: Клиент -> сервер -> бд?
Отправлено: djfile от Сентябрь 29, 2012, 20:46
А можно, можно я влезу?
Конечно влезайте.

Цитировать
На практике используют 2 вида клиент-серверных архитектур : двузвенная и трехзвеннная.

Двузвенназя выглядит так: сервером выступает сама БД. Клиент цепляется к БД и выполняет необходимые запросы.

В трехзвенной же есть промежуточный сервер:  клиент общается с промежуточным сервером, сервер общается с БД.

Плюсы и минусы есть у каждого способа:

двузвенка на порядок проще и гораздо менее требовательна к ресурсам. Однако вся логика переносится на клиента = более высокие требования к оборудованию.

трехзвенка позволяет унифицировать обработку при разных клиентах (Rich-клиента, тонкий веб клиент, Android и iOS клиенты), позволит иметь возможность смены СУБД (клиент то запрос отправляет серверу), облегчит масштабирование системы (опять же потому что клиенту все равно что там будет твориться).
Однако такую систему сложнее разрабатывать и поддерживать.

В результате, ИМХО конечно же, Вам все же было бы проще работать с двузвенкой, а не трехзвенкой (которую вы и обсуждаете).

 
Про это я почитал.
То есть получается, что при двухзвенной архитектуре SQL-запросы пишутся на клиенте, при трехзвенной на промежуточном сервере, при этом пишется свой протокол общения между клиентом и промежуточным сервером?


Название: Re: Клиент -> сервер -> бд?
Отправлено: joker от Сентябрь 30, 2012, 14:58
Про это я почитал.
То есть получается, что при двухзвенной архитектуре SQL-запросы пишутся на клиенте, при трехзвенной на промежуточном сервере, при этом пишется свой протокол общения между клиентом и промежуточным сервером?

Абсолютно верно.

Кста, могу еще обратить внимание, что в обоих случаях нагрузка на SQL сервер фактически одинаковая :) 
(да можно начать рассуждать о том, что в некоторых случаях app-сервер может кешировать, а с другой стороны унификация запросов приведет к более тяжелым запросам но это все будут уже особенности реализации)


Название: Re: Клиент -> сервер -> бд?
Отправлено: djfile от Сентябрь 30, 2012, 15:50
Про это я почитал.
То есть получается, что при двухзвенной архитектуре SQL-запросы пишутся на клиенте, при трехзвенной на промежуточном сервере, при этом пишется свой протокол общения между клиентом и промежуточным сервером?

Абсолютно верно.

Кста, могу еще обратить внимание, что в обоих случаях нагрузка на SQL сервер фактически одинаковая :)  
(да можно начать рассуждать о том, что в некоторых случаях app-сервер может кешировать, а с другой стороны унификация запросов приведет к более тяжелым запросам но это все будут уже особенности реализации)

Спасибо большое за помощь. Теперь бы выбрать как лучше сделать для курсовой=) Прочел, что с QSqlDataBase нельзя работать в нескольких потоках. Точнее QSqlQuery не может делать запросы из базы, находящейся в другом потоке.
И ещё как лучше держать связь с клиентами? Постоянно держать открытым сокет?


Название: Re: Клиент -> сервер -> бд?
Отправлено: joker от Сентябрь 30, 2012, 21:38
Спасибо большое за помощь. Теперь бы выбрать как лучше сделать для курсовой=) Прочел, что с QSqlDataBase нельзя работать в нескольких потоках. Точнее QSqlQuery не может делать запросы из базы, находящейся в другом потоке.
И ещё как лучше держать связь с клиентами? Постоянно держать открытым сокет?

Ну пункт номер раз - а зачем тебе несколько потоков?
В стандатном варианте:
 - или нужно показывать виджет - таблицу / форму - тут все стандартно без потоков.
 - или нужно делать апдейты/инсерты - но они обычно много времени не занимают (иначе надо перепроектировать приложение).
 - или нужно считать отчеты... но ползателю все равно их ждать - раз ему нужны отчеты - поэтому проще вывести какое нибудь окошко статуса чтобы скрасить ожидание.

Вообще, имхо, - при старте приложения поднимаешь соединение. Ну а закрываешь уже при закрытии программы. И в процессе кидаешь сколько угодно запросов.





Название: Re: Клиент -> сервер -> бд?
Отправлено: k0p4 от Октябрь 02, 2012, 13:54
Цитировать
Прочел, что с QSqlDataBase нельзя работать в нескольких потоках. Точнее QSqlQuery не может делать запросы из базы, находящейся в другом потоке.
И ещё как лучше держать связь с клиентами? Постоянно держать открытым сокет?

1. QSqlDatabase можно вынести в отдельный трэд. В каждом трэде можно открыть коннекшн. Соотвтветственно, работа для БД будет приезжать с сигналом, и результат выполнения - тоже будет уезжать с сигналом.
2. Помимо основной таблицы БД тебе нужен стол пользователей, где будут хранится, например, логин-пасс.
3. Коннекшн с твоим сервером должен висеть только ПОСЛЕ аутентификации. Время на прохождение аутентификации должно быть маленьким. Так же не забудь про таймауты. Т.е. если соккет, к примеру, минуту тебе ничего не шлёт - ты его отрубаешь. Что бы не отрубать нормальные соккеты, который сейчас просто не активны, каждые 55 секунд шлёшь какую-нибудь команду и рестартуешь таймер.



Название: Re: Клиент -> сервер -> бд?
Отправлено: panAlexey от Октябрь 03, 2012, 16:58
облегчит масштабирование системы
за счет чего?


Название: Re: Клиент -> сервер -> бд?
Отправлено: V1KT0P от Октябрь 03, 2012, 20:33
облегчит масштабирование системы
за счет чего?
За счет того, что сервер можно заменить на прокси-сервер который будет объединять локальную сеть серверов.


Название: Re: Клиент -> сервер -> бд?
Отправлено: panAlexey от Октябрь 04, 2012, 19:49
облегчит масштабирование системы
за счет чего?
За счет того, что сервер можно заменить на прокси-сервер который будет объединять локальную сеть серверов.
ога. типа еще один тип сервака надо писать :)
Да уж. Это не дипломная получится, а пахота месяцев на надцать :)


Название: Re: Клиент -> сервер -> бд?
Отправлено: Bepec от Октябрь 04, 2012, 20:00
Тут на нобелевку потянет, если кросплатформенно да ещё и с шифрованием :)


Название: Re: Клиент -> сервер -> бд?
Отправлено: Krysk от Октябрь 05, 2012, 03:33
Если требования к проекту не жесткие, т.е. можно использовать альтернативные языки и платформы, то я бы на твоем месте выбрал джаву - в качестве сервера, c++/qt - в качестве клиента. Сервер выстроил на базе spring-mvc + rest + spring-security... Готовых примеров масса, освоить все это студенту с базовыми знаниями в программировании более чем реально, ну и на будущее развиваться в данном направлении куда выгоднее, чем писать сервера на с++ + qt не говоря уже об устройстве на работу...


Название: Re: Клиент -> сервер -> бд?
Отправлено: k0p4 от Октябрь 05, 2012, 14:54
Цитировать
чем писать сервера на с++ + qt не говоря уже об устройстве на работу...

Ну да, джава-сервера куда лучше нативного С++ кода. К тому же, не вижу ничего плохого писать сервер на Qt, который, к тому же, предоставляет отличные классы для этих задач.
А с работой - вы это бросьте. Работа есть.

Для реализации простого TCP сервера потребуются пару классов :

- Для сети :
  QTcpServer;
  QSslSocket;
- Данные :
  QByteArray;
  QDataStream;

И всё это дело, для простого (даже многопоточного) сервера займёт порядка 400-500 строк. А учитывая сколько есть екземплов - то разобратся для студента тоже не составит проблемы.




Название: Re: Клиент -> сервер -> бд?
Отправлено: xokc от Октябрь 05, 2012, 15:11
1. Понятно, что в общем случае джава код, никуда не лучше нативного. Но мы сейчас говорим о коде, который будет писаться студентом. Готов поставить очень много, что студенческий нативный код будет НАМНОГО хуже (причем во всех смыслах) интерпретируемого промышленного.
2. Классы в Qt плохо подходят для разработки нормального TCP сервера, способного обрабатывать большое количество соединений. Растекаться тут на эту тему не буду, всё уже неоднократно на этом форуме обсуждалось.
3. Какие классы в Qt помогают для разработки многопоточного масштабируемого трехзвенного отказоустойчивого безопасного сервера с балансировкой нагрузки, кешированием, поддержкой со стороны провайдеров и прочими фишками, которые мы автоматически получаем при использовании готовых промышленных решений? Сколько строк кода нужно для этого?



Название: Re: Клиент -> сервер -> бд?
Отправлено: Bepec от Октябрь 05, 2012, 15:41
Нужно 2 строчки естественного языка :D

Написанные на бумажке с печатью президента:
"написать трёхзвенныйсервер с бла бла бла."
"Быстро млиа!!!"


Название: Re: Клиент -> сервер -> бд?
Отправлено: xokc от Октябрь 05, 2012, 15:53
Подозреваю, что как только появится интерпретатор с такого языка я останусь без куска хлеба.


Название: Re: Клиент -> сервер -> бд?
Отправлено: k0p4 от Октябрь 05, 2012, 16:11
Уважаемый xock,
1. Студенческий код он будет, как минимум, в равной степени плох. Я пологаю, что на Qt с самого начала можно писать достаточно хороший код, а учитывая экземплы (кстати, которых хватит для этой задачи) так и вообще отличный(как для студента).
2. Классы Qt отлично подходят, если их правильно применять.
3.1 По порядку :
   - QTcpServer;
   - QSslSocket;
   - QThread;
   - QByteArray;
   - QDataStream;
   - QSqlDatabase.
3.2 Этих классов вполне хватит для достаточно серьёзного решения. Причём решение - будет весьма масштабируемое и быстрое. А если нужен хай-лоад, то сервер нужно запускать на бубунте, например, и использовать epoll. EventDispatcher дописать - проблем не составит. Тем более, что уже видел где-то на гитхабе готовое решение.
3.3 Объясню:
    -При старте сервера - запускаем n трэдов. При incomming connection - создаём сокет, и сразу запихиваем в трэд.
    -Последующая обработка протокола - в соккете.
    -БД вешаем в отдельный трэд и коммуницируем слотами\сигналами.
3.4
Цитировать
балансировкой нагрузки
     Хардварной или софтварной?
3.5 Кэширование - если встал такой вопрос - то вполне решаем. Можно кэшировать, например, даже в оперативную память. А студенту - ну ни к чему.
3.6
Цитировать
поддержкой со стороны провайдеров и прочими фишками, которые мы автоматически получаем при использовании готовых промышленных решений
Что Вы имели ввиду?
3.7 Порядка 2000. + - 1000. Зависит от обработки протокола.

А конкретно в данной теме - то вполне реально уложится до 1000 строк.


Название: Re: Клиент -> сервер -> бд?
Отправлено: Bepec от Октябрь 05, 2012, 16:42
Копч, тут на форуме уже разжёвано почему нельзя и почему стандартные классы Qt для этого не подходят :)

А для высоконагруженных тем более :)

PS для лабы - сойдёт. Для своего проекта - сойдёт. Для работы с высокой нагрузкой - не сойдёт :)


Название: Re: Клиент -> сервер -> бд?
Отправлено: k0p4 от Октябрь 05, 2012, 17:20
Bepec, если не затруднит, можно линки?
Интерестно будет почитать.


Название: Re: Клиент -> сервер -> бд?
Отправлено: panAlexey от Октябрь 06, 2012, 10:06
Копч, тут на форуме уже разжёвано почему нельзя и почему стандартные классы Qt для этого не подходят :)
А для высоконагруженных тем более :)
PS для лабы - сойдёт. Для своего проекта - сойдёт. Для работы с высокой нагрузкой - не сойдёт :)
надо это в FAQ записать с примерами и ссылками.


Название: Re: Клиент -> сервер -> бд?
Отправлено: Bepec от Октябрь 06, 2012, 10:55
K0p4 - запусти поиск по форуму на слова "сервер", "QTcpServer" и прочая.
Я этой темы касался только косвенно, в своём маленьком проекте.

А да, помоему четкое описание есть в теме  аля "Пишу свой сервр на С++" кажется.


Название: Re: Клиент -> сервер -> бд?
Отправлено: djfile от Октябрь 06, 2012, 22:16
Ничего себе тут творится=) Приятно, что люди отвечают, спасибо вам всем.
Прихожу примерно к такому выводу: держать несколько потоков обработчиков, в которые по сигналам передавать/забирать данные. Эти обработчики будут работать с потоком БД. Здесь мне всё более менее понятно. Не могу понять где лучше держать клиентов? Если в одном потоке, то все остальное теряет смысл. Можно завести несколько потоков и клиентов распределять между ними, но если в одном потоке будет большая активность клиентов, а в другом нулевая, то опять же получится только 1 активный поток.
Если б в Qt можно писать/читать в сокет из разных потоков, да и сам сокет перемещать по потокам, то может быть легче было б.

И ещё может кто-нибудь объяснить как используются callback-функции применительно к потокам? Как их используются для функций типа sort я понимаю, а вот с потоками никак.

Спасибо.


Название: Re: Клиент -> сервер -> бд?
Отправлено: V1KT0P от Октябрь 06, 2012, 22:34
Если б в Qt можно писать/читать в сокет из разных потоков, да и сам сокет перемещать по потокам, то может быть легче было б.
Я как-то делал подобное, у меня был класс балансировщик, который при подключении клиента помещал его в поток с наименьшим количеством клиентов. Но на сотне клиентов начиналось нереальное пожирание оперативки, да и производительность начинала сильно падать. В итоге переписал на asio, стало работать быстро и перестало жрать память. Плюс пропала привязанность клиента к потоку, любого клиента обрабатывает любой поток который к этому времени освободился.

И ещё может кто-нибудь объяснить как используются callback-функции применительно к потокам? Как их используются для функций типа sort я понимаю, а вот с потоками никак.
Вообще в кьюте принято посылать сигналы а не вызывать коллбэки.


Название: Re: Клиент -> сервер -> бд?
Отправлено: xokc от Октябрь 07, 2012, 11:59
2. Классы Qt отлично подходят, если их правильно применять.
...
    -При старте сервера - запускаем n трэдов. При incomming connection - создаём сокет, и сразу запихиваем в трэд.
    -Последующая обработка протокола - в соккете.
    -БД вешаем в отдельный трэд и коммуницируем слотами\сигналами.
...
А конкретно в данной теме - то вполне реально уложится до 1000 строк.
Ещё один теоретик? Или есть РЕАЛЬНО работающее серверное решение для Qt на базе QTCPSocket и сигнал/слотах, держащее хотя-бы 1000 соединений?

Bepec, если не затруднит, можно линки?
Интерестно будет почитать.
Ищите на этом форуме по слову asio.