Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Скриптовые языки программирования > PHP
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 13.09.2010, 11:08   #1
ACE Valery
Сама себе режиссер
Старожил
 
Аватар для ACE Valery
 
Регистрация: 27.04.2007
Сообщений: 3,365
По умолчанию Сетевое программирование PHP

Привет) Никогда раньше не работала с сетью, а тут пришлось. Помогите, пожалуйста, ссылками или советами.

Клиент - Flash (ActionScript), сервер - PHP.
Скажем так, нужно написать обмен сообщениями между двумя людьми. Человек заходит на сайт и видит перед собой список тех, кто хочет пообщаться. Он может или выбрать одного из предоставленных собеседников, или сам создать заявку на общение. При создании заявки человек ждет, пока к нему не присоединится собеседник(только один). Если ждать надоело, то он может нажать кнопку "Отмена" и вернуться на экран выбора собеседников.

Собственно, главный вопрос: как это реализовать с помощью сокетов? Список собеседников - это будет список открытых соединений? Как передавать сообщения именно своему собеседнику? Ну и так далее в том же духе.
Код не прошу, прошу алгоритм или пинок в нужном направлении. Литературу и статьи по этому делу уже рыла и рою сейчас.
Если я вас напрягаю или раздражаю, вы всегда можете забиться в угол и поплакать
ACE Valery вне форума Ответить с цитированием
Старый 13.09.2010, 19:05   #2
Linel
Форумчанин
 
Аватар для Linel
 
Регистрация: 21.02.2009
Сообщений: 372
По умолчанию

Цитата:
Литературу и статьи по этому делу уже рыла и рою сейчас.
Если найдете статьи/учебники, киньте ссылку в пм, пожалуйста.
No name. Just Linel.
Linel вне форума Ответить с цитированием
Старый 13.09.2010, 19:26   #3
Dj_smart
Капсула от спама
Форумчанин
 
Аватар для Dj_smart
 
Регистрация: 04.03.2008
Сообщений: 779
По умолчанию

Сокеты - наше все
Цитата:
Список собеседников - это будет список открытых соединений?
Да.
Цитата:
Как передавать сообщения именно своему собеседнику?
Тут все просто. Используем неблокирующие сокеты и при создании нового соединения выбираем "собеседника". Добавляем сокет в список, и не просто сокета, а массив, скажем такой:
$connections[] = array('socket'=>$new_socket,'talkwi th'=>0);
И до создании такого массива выбираем того, у кого talkwith==0, и ставим соотв. talkwith = id собеседника для каждого из владельцев соединений. Дальше - при чтении и обнаружении данных тупо слать их по $connections[talkwith][socket]
както так
Если данный ответ не столь конкретен, как Вы желаете его увидеть, возможно необходимо поразмыслить, стоит ли вопрос того, чтобы о нём спрашивать на форуме?
CncFiles.ru - бесплатный файловый хостинг
Dj_smart вне форума Ответить с цитированием
Старый 14.09.2010, 11:50   #4
ACE Valery
Сама себе режиссер
Старожил
 
Аватар для ACE Valery
 
Регистрация: 27.04.2007
Сообщений: 3,365
По умолчанию

Dj_smart, благодарю вас, сейчас буду пробовать.
Linel. зачем в ПМ? Вдруг кому-то еще пригодится?
Вот список статей. По полезности еще не отфильтрован, поэтому я не виновата, если там будет написана лажа
PHP 5 Sockets With Flash (English)
PHP Socket server and Chat Gateway for Flash clients (English)
PHP 5, AC2(AC3) Sockets (ответы на форуме)
Статьи по веб-программированию
Сокеты в PHP
Если я вас напрягаю или раздражаю, вы всегда можете забиться в угол и поплакать
ACE Valery вне форума Ответить с цитированием
Старый 14.09.2010, 22:33   #5
Dj_smart
Капсула от спама
Форумчанин
 
Аватар для Dj_smart
 
Регистрация: 04.03.2008
Сообщений: 779
По умолчанию

Кстати так держать! Девушка и программист - обычно взаимоисключающие вещи Могу закинуть свои наброски по онлайн-чату, не закончено после 10 минут кодинга
Если данный ответ не столь конкретен, как Вы желаете его увидеть, возможно необходимо поразмыслить, стоит ли вопрос того, чтобы о нём спрашивать на форуме?
CncFiles.ru - бесплатный файловый хостинг

Последний раз редактировалось Dj_smart; 14.09.2010 в 23:09.
Dj_smart вне форума Ответить с цитированием
Старый 15.09.2010, 00:26   #6
ACE Valery
Сама себе режиссер
Старожил
 
Аватар для ACE Valery
 
Регистрация: 27.04.2007
Сообщений: 3,365
По умолчанию

Dj_smart, скиньте, пожалуйста... Буду очень благодарна.
А то у меня появилась глобальная проблема: при установке соединения флеш выдает ошибку 2048(SecurityErrorEvent). В статьях вычитала, что он хочет файл crossdomain.xml:
Код:
<?xml version="1.0"?>
<cross-domain-policy>
 <allow-access-from domain="*" />
</cross-domain-policy>
В корне с проектом у меня он лежит, но почему-то флеш не видит. Security.loadPolicyFile("crossdomai n.xml"); не помогает...
Сказали, что при работе с сокетами нужно прослушивать два порта: первый - для самого кроссдомейна(порт 843), а второй(любой) - для передачи данных. Теперь я вообще запуталась. Получается. мне нужно создавать на флеше два сокета, и одним коннектиться к 843-му порту, а вторым - к порту данных? Или же один сокет и каждый раз при отправлении сообщения с сервера передавать и этот кроссдомейн?
Еще я не совсем понимаю, зачем нужен этот файлик, если и флешка, и PHP -файл находятся в одном месте.
И почему-то все примеры, которые я нахожу, идут без него. Значит, у людей все работает и так?
Если я вас напрягаю или раздражаю, вы всегда можете забиться в угол и поплакать
ACE Valery вне форума Ответить с цитированием
Старый 15.09.2010, 01:21   #7
Dj_smart
Капсула от спама
Форумчанин
 
Аватар для Dj_smart
 
Регистрация: 04.03.2008
Сообщений: 779
По умолчанию

Собственно 6 файлов
style.css - стили
page_top/page_bottom.php - шапка и дно "сайта"
server.php - сам сервер
config.php - настройки
chat.php - "клиент", то есть пользователи открывают ее.

приведу код сервера(в следующем посте)

фух вроде все закомментировал... остальные файлы не требуют комментариев.
Вложения
Тип файла: rar smartchat.rar (3.4 Кб, 114 просмотров)
Если данный ответ не столь конкретен, как Вы желаете его увидеть, возможно необходимо поразмыслить, стоит ли вопрос того, чтобы о нём спрашивать на форуме?
CncFiles.ru - бесплатный файловый хостинг
Dj_smart вне форума Ответить с цитированием
Старый 15.09.2010, 01:22   #8
Dj_smart
Капсула от спама
Форумчанин
 
Аватар для Dj_smart
 
Регистрация: 04.03.2008
Сообщений: 779
По умолчанию

PHP код:
<?php
  
  
include_once('config.php');
  
  
$conn mysql_connect($mysql_addr$mysql_user$mysql_pass);
  
mysql_select_db($mysql_name);

  
header('Expires: Mon, 26 Jul 1997 05:00:00 GMT'); 
  
header('Cache-Control: no-store, no-cache, must-revalidate'); 
  
header('Cache-Control: post-check=0, pre-check=0'FALSE); 
  
header('Pragma: no-cache');
  
// все выше понятно
 // error_reporting(E_ALL ^ E_WARNING);
  
set_time_limit(0);
  
ob_implicit_flush();
  
ignore_user_abort();
  
// игнорируем закрытие
  
  
  
echo '<style> body,html {font-family: Tahoma; font-size:11px;} </style>
  <b>CHAT SERVER</b>'
;
// заголовок
  
  
g_info(($sock socket_create(AF_INETSOCK_STREAMSOL_TCP))<0,'Socket create');
  
// создаем сокет (g_info описана в config.php)
  
g_info(socket_bind($sock$adress$port)<0,'Socket bind to '.$adress);
  
// связываем
  
g_info(socket_listen($sock5)<0,'Socket listen');
// слушаем
  //$sock = socket_create_listen($port);
  // или так
  
  
socket_set_nonblock($sock);
 
// неблокирующий
  
$current_conn 0;
  
$connections = array();
  
  function 
server_shutdown(){
    global 
$sock;
    
socket_close($sock);
    die(
'<br><b>SERVER CLOSED!</b>');
  }
  
// это закрывать

  
$listen true;
  echo 
'<br>You may close this page or admin it by special soft.';

  function 
get_u($uid, &$r){
    
$result mysql_query('SELECT * FROM `sm_users` WHERE `user_uniq`='.$uid);
    if (
$result and mysql_num_rows($result)){
      
$r mysql_fetch_array($result);
      return 
true;
    }
    return 
false;
  }
  
// приплел даже mysql, выбирает пользователя (его запись) через уникальный id
  
function send_head($sock,$send_styles=false){
    
send_text($sock
                    
"HTTP/1.1 200 OK\n".
                    
"Expires: Mon, 26 Jul 1997 05:00:00 GMT\n".
                    
"Content-Type: text/html; charset=UTF-8\n".
                    
"Cache-Control: no-store, no-cache, must-revalidate\n".
                    
"Cache-Control: post-check=0, pre-check=0\n".
                    
"Connection: Keep-Alive\n".
                    
"Pragma: no-cache\n\n".($send_styles?'<style> body,html {font-family: Tahoma; font-size:11px;} </style>':''));
                    
  }
  
// очевидно
  
function trunc($what, &$w1, &$w2){
    if (
$ps strpos($what,'-')){
      
$w1 substr($what0$ps);
      
$w2 substr($what$ps+1strlen($what));
    } else {
      
$w1 $what;
      
$w2 '';
    }
  }
  
// если есть "-" то в первое записать то что слева а во второе то что справа, иначе все записать в первое
  
function send_clientlist(){
    
$ucl '';
    foreach(
$connections as $id => $conn){
      
$ucl .= $conn[user][user_name].'<br>';
    }
    foreach(
$connections as $id => $conn){
      
send_text($connections[$id]['socket'], '<script>ucl("'.$ucl.'");</script>');
    }
  }
  
// разослать список пользователей
Если данный ответ не столь конкретен, как Вы желаете его увидеть, возможно необходимо поразмыслить, стоит ли вопрос того, чтобы о нём спрашивать на форуме?
CncFiles.ru - бесплатный файловый хостинг
Dj_smart вне форума Ответить с цитированием
Старый 15.09.2010, 01:22   #9
Dj_smart
Капсула от спама
Форумчанин
 
Аватар для Dj_smart
 
Регистрация: 04.03.2008
Сообщений: 779
По умолчанию

Не влазит и все...
PHP код:
// ДАЛЕЕ ГЛАВНЫЙ ЦИКЛ
  
while ($listen) {
    if ((
$new_connection = @socket_accept($sock)) !== false){
      
// если ктото появился
      
usleep(500000);
      
// полсекунды ждем
      
@socket_recv($new_connection,$recvdat2048,0);
      
// читаем то что прислал и если это гет-запрос то
      
if (preg_match("/GET \/(.*?) HTTP/"$recvdat$res)){
        
trunc($res[1],$page,$info);
        
// смотрим что спрашивали. если спросили client-111 то 
        // в page запишет client, в info - 111
        
if ($page=='client'){
          
// если это слушатель
          
$uid = (int)$info;
          
          if (
get_u($uid$r)){
            
// получили пользователя
            
socket_getpeername($new_connection,$peer);
            
// взяли ip
            
$connections[] = array('socket'=>$new_connection,'peer'=>$peer,'user'=>$r);
              
send_head($new_connection,true);
                  
send_clientlist();
           
// отправили ему недоделанную голову + клиенты
            
} else {
                      
// иначе сообщили что польз. с таким уник. ид нету
              
send_head($new_connection);
            
send_text($new_connection,'ERR-'.$uid);
              
socket_close($new_connection);
            }
            } elseif (
$page=='add'){
                            
// если это запрос типа "добавькасообщение"
              
trunc($info$u_t$message);
                          
// выдираем
            
$uid = (int)$u_t;
                   
            
send_head($new_connection);
          if (
get_u($uid$r)){
            
// если автор достоверный то рассылаем
            
foreach($connections as $id => $conn){
              
send_text($connections[$id]['socket'], $r['user_name'].' > '.$message.'<br>');
            }
            
send_text($new_connection,'OK');
          } else {
            
send_text($new_connection,'ERR');
          }
          
socket_close($new_connection);
          } elseif (
$page=='closeserver'){
                    
// если запрос типа ануказавалитесервер
            
if ($info==SECRET_WORD){
              
server_shutdown();
              
send_head($new_connection,true);
              
send_text($new_connection'SERVER CLOSED');
            }
          
socket_close($new_connection);
          } elseif (
$page=='serverinfo'){
                    
// если возжелили информации
            
if ($info==SECRET_WORD){
              
send_head($new_connection,true);
              
$serverinfo "SERVER INFORMATION:<br><br>".
              
"Commands:<br>".
              
"&nbsp;1. <a href='closeserver-".SECRET_WORD."' target='_blank'>Close server</a><br>".
              
"Information:<br>".
              
"&nbsp;1. ClientsList:<br>";
              foreach (
$connections as $conn){
                
$serverinfo.="&nbsp;&nbsp;IP:".$conn['peer']." USER-NAME:".$conn['user']['user_name']."<br>";
              }
              
send_text($new_connection$serverinfo);
            }
          
socket_close($new_connection);
          }
      } else {
        
socket_close($new_connection);
        die(
'ERROR');
      }
    }
    
usleep(1);
  }
?> 
Если данный ответ не столь конкретен, как Вы желаете его увидеть, возможно необходимо поразмыслить, стоит ли вопрос того, чтобы о нём спрашивать на форуме?
CncFiles.ru - бесплатный файловый хостинг
Dj_smart вне форума Ответить с цитированием
Старый 17.09.2010, 11:54   #10
ACE Valery
Сама себе режиссер
Старожил
 
Аватар для ACE Valery
 
Регистрация: 27.04.2007
Сообщений: 3,365
По умолчанию

Dj_smart, спасибо за исходник) Посмотрела. А можно еще дамп базы данных для "поиграться вживую"?
C PHP вроде пока вопрос закрыт - сокет создается, цикл отрабатывает. Только вот клиентов он не дожидается. Наверное, тут проблема во флеше... Но это уже другая тема
Если я вас напрягаю или раздражаю, вы всегда можете забиться в угол и поплакать
ACE Valery вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Статья: Низкоуровневое сетевое программирование. Пишем клиент/серверное приложение на сокетах Беркли oleg kutkov C/C++ Сетевое программирование 42 22.01.2011 00:35
Сетевое программирование Тунец Помощь студентам 4 09.07.2009 00:07
Сетевое программирование Winnows-32 Помощь студентам 1 01.12.2008 07:16
Нужна помощь(сетевое программирование) mager Общие вопросы C/C++ 6 14.02.2008 06:47