1. PHP / Говнокод #1703

    +156

    1. 01
    2. 02
    3. 03
    4. 04
    5. 05
    6. 06
    7. 07
    8. 08
    9. 09
    10. 10
    11. 11
    12. 12
    $sql = "SELECT MAX(user_id) AS total
    				FROM " . USERS_TABLE;
    			if ( !($result = $db->sql_query($sql)) )
    			{
    				message_die(GENERAL_ERROR, 'Could not obtain next user_id information', '', __LINE__, __FILE__, $sql);
    			}
    
    			if ( !($row = $db->sql_fetchrow($result)) )
    			{
    				message_die(GENERAL_ERROR, 'Could not obtain next user_id information', '', __LINE__, __FILE__, $sql);
    			}
    			$user_id = $row['total'] + 1;

    Найдено в phpBB-wap. Перед регистрацией пользователя. $user_id - id регистрирующегося юзера. Похоже, автор не знает про auto_increment

    Запостил: 123qweawdsf12fasfa, 27 Августа 2009

    Комментарии (21) RSS

    • может там postgresql можно подключить?
      Ответить
      • именно — http://www.phpbb.com/about/features/#data-management
        Ответить
        • Круто! А ещё там в списке СУБД есть SQLite. Но есть одна проблема: SQLite не нужен.
          Ответить
    • А, собственно, причём здесь СУБД? Любая система, которая сама пытается прибавить единичку к идентификатору самостоятельно, обречена на конфликты регистрации пользователей с одинаковым идентификатором. То есть, придётся изобретать велосипед: вручную закрывать и открывать таблицы и прочее.
      СУБД такие вещи сама должна делать, для того поля auto_increment и существуют.
      Кроме того в postgresql есть serial квалификатор similar to the AUTO_INCREMENT property supported by some other databases
      Ответить
    • Йопт. Знал что пыхББ дурная, но чтоб настолько... :(
      Ответить
    • К данному коду можно и ещё одно замечание написать.
      Речь об "универсальности" и разработке.
      Даже предположив, что существует такая СУБД (а это вполне реально, просто я с ними не знаком), которая не умеет генерировать последовательности автоматически, возникает ужаснейшая ситуация.
      Мало того, что мы "универсализируем" код для того, чтобы он работал с некоторой СУБД, которая просто неприменима в нашем проекте, кроме того этот код будет неэффективно работать с теми СУБД, что всё же имеют систему автоматических последовательностей.
      Подобные вещи указывают на очень серьёзные просчёты на этапе разработки.
      Ответить
    • странно что никто не написал про mysql_last_insert_id() (ну или как там... не помню уже как сами комманды выглядят)
      Ответить
      • Потому что код оправдывают универсальностью, а, например, API для postgresql в PHP устроено так, что никаких pg_last_insert_id() там нет. Возвращение идентификатора вставленной записи обеспечивается дописыванием RETURNING <serial field name> к INSERT, если не ошибаюсь. Или иными приёмами, использующими возможности самой СУБД.
        Ответить
        • Только начиная с 8.3. Раньще надо было самостоятельно сгенерировать следующее значение в последовательности (безопасная операция) или же прочитать максимальный ИД после инсерта.
          Ответить
        • Не работал с «PostgreSQL» на таком глубоком уровне.
          Ответить
      • неверное не писали потому, что mysql_last_insert_id тут совершенно не в тему
        Ответить
    • Даже если это написано с целью абстрагирования от конкретной СУБД, это говнокод. Потому что существует ненулевая вероятность, что двое пользователей начнут регистрироваться в один и тот же момент и этот алгоритм присвоит им один id, соответственно зарегистрируется только один из них, второму выдадут ошибку. Эмуляция автоинкремента в СУБД, не имеющих такой функциональности происходит с помощью триггеров и последовательностей. Таким образом и код будет универсальным и будет присутствовать атомарность операции добавления пользователя.
      Ответить
      • Да это редко бывает. Как часто на вашем сайте регатся пользователи? А если кому и вылезит еррор, то снова зарегится.
        Ответить
    • Как и большинство "говнокода" здесь, он "говнокод" только будучи выдранным из контекста.
      В пхпбб (частично исторически, частично из-за совместимости с другими БД, частично из-за совместимости с другими приложениями) могут быть юзеры с -1 идентификатором.
      Как ведет себя в таком случае автоинкримент не знает только полный идиот.

      Более того, в тех версиях пхпбб что я смотрел, обработчик ошибок дубля автоинкримента есть, просто постер кода сюда "забыл" "по какой-то причине" его сюда написать.
      Ответить
      • Всё, что вы говорите, совершенно не важно. В любом случае данный код берёт на себя то, что должна делать СУБД.
        Если есть два пользователя с одним идентификатором, то зачем он нужен? Это всю идею и строгость базы нарушает. Это даже тогда даже не проблема плохого программирования, а проблема логики с неопределённостями. Без всякого контекста ясно, что это грубая ошибка этапа разработки, вызванная "потугами" универсальности. А дальше её было просто очень дорого исправить.
        Ответить
    • phpBB-WAP вообще не известно что хрень. По моему по хлеще будет чем TBDev от юны.
      Ответить
    • http://phpbb-wap.ru LOOOL))
      Ответить
      • > http://phpbb-wap.ru/info/index.htm

        "на вашем форуме появлялся автологин
        вида http://ваш_форум/login.php?username=ваш_ник&password=ваш_ пароль"


        Ну да, а чтобы "вспомнить" пароль, теперь достаточно посмотреть в access.log.
        Ответить
        • В access.log прокси-сервера, через который заходил клиент.

          P.S. Или не так:
          «Вы принесли в базу новый реферер: http://ваш_форум/login.php?username=vasya15&password=1234 5»
          Ответить
          • Да не, там же редирект. А вот когда приносили в реферрере валидный session id, случаи наверняка были.
            Ответить

    Добавить комментарий