› MySQL 5.5 Community Server
› MySQL 5.6 Community Server
› Percona Configuration Wizard
› XtraBackup 搭建主从复制
Great Sites on MySQL
› Percona
› MySQL Performance Blog
› Severalnines
推荐管理工具
› Sequel Pro
› phpMyAdmin
推荐书目
› MySQL Cookbook
MySQL 相关项目
› MariaDB
› Drizzle
参考文档
› http://mysql-python.sourceforge.net/MySQLdb.html
KagamineLenKai2
V2EX  ›  MySQL

看到别人写 SQL 会在 where 后面写 1=1,是什么意思?

  •  
  •   KagamineLenKai2 · Sep 2, 2016 · 23784 views
    This topic created in 3716 days ago, the information mentioned may be changed or developed.

    SELECT * FROM operation_log o
    where 1=1
    and o.operation_time>='2016/6/1'
    and o.operation_time<'2016/7/28'
    这个 1=1 好像写不写都没关系哦?

    77 replies  •  2016-09-05 18:58:44 +08:00
    yatesun
    yatesun
    Sep 2, 2016
    1
    感觉主要是有些人喜欢拼接 sql ,这样能保证一定有个 where 字段,其实没什么意义。
    solaya
    solaya
    Sep 2, 2016
    2
    就是为了加 and   拼接 sql 语句
    tabris17
    tabris17
    Sep 2, 2016
    3
    为了拼接方便
    php230
    php230
    Sep 2, 2016
    4
    拼接条件
    wyntergreg
    wyntergreg
    Sep 2, 2016❤️3
    5
    楼上说的都对,跟 2=2 没什么区别,为了语法凑字数用的。如果不加这个 1=1 ,那么在拼 sql 的时候你要判断拼上去的第一个条件是不带 and 的,然而很多查询都是多条件组合查询的,你并不知道哪一个条件会拼在第一个上,所以干脆把第一个条件写成 sql 认为的"true",其他所有条件都是 and
    est
    est
    Sep 2, 2016❤️1
    6
    知道真像的我。。。。😂

    没有 ORM 你么肿么活下来的。。。
    KagamineLenKai2
    KagamineLenKai2
    OP
    Sep 2, 2016❤️1
    7
    抱歉刚接触 SQL ,你们说的没听懂……
    SELECT * FROM operation_log o
    where o.operation_time>='2016/6/1'
    and o.operation_time<'2016/7/28'
    这样写不也可以么?
    tmkook
    tmkook
    PRO
    Sep 2, 2016❤️1
    8
    $sql = "SELECT * FROm table WHERE 1=1":
    if($_GET['filed1']){
    $sql .= "AND filed1=1":
    }
    if($_GET['filed2']){
    $sql .= "AND filed2=2":
    }

    哈哈哈,曾经也是玩的很溜的
    caixiexin
    caixiexin
    Sep 2, 2016 via Android❤️2
    9
    一般是这个方法里的 SQL 是根据入参动态生成的,比如有多个条件,这些条件又不是必填,那就在 where 1=1 ,后面接多个 and xxx 就行了。不然要是哪天 where 条件的参数变了,还要改 where xxx 。
    where 1=1 MySQL 查询分析器会自动优化,没有性能问题。
    Clarencep
    Clarencep
    Sep 2, 2016
    10
    都是不会用 implode 的程序猿惹的祸
    ijustdo
    ijustdo
    Sep 2, 2016
    11
    我看到都蛋疼 不说 直接上代码

    $conditions_str = implode(',', array_map(function($x){return sprintf('%s=:%s', $x, $x);}, array_keys($conditions)));
    if (!empty($conditions_str)){
    $conditions_str = " where {$conditions_str} ";
    }
    liqingcan
    liqingcan
    Sep 2, 2016❤️3
    12
    有人发现了吗。在座的发代码出来的全都是 phper
    ijustdo
    ijustdo
    Sep 2, 2016
    13
    呵呵 我不是咧 主营不是拍好 p 我只是看到上面都用 php 举例子 也就去翻了下以前的代码
    flydogs
    flydogs
    Sep 2, 2016
    14
    1.不需要判断有没有条件
    2.不需要判断第一个条件还是第 N 个条件
    Infernalzero
    Infernalzero
    Sep 2, 2016
    15
    @liqingcan 因为 java 的话用 mybatis 会自动帮你去掉多余的 and 所以根本不需要写 1=1 去拼接
    ebony0319
    ebony0319
    Sep 2, 2016 via Android
    16
    这个是为了保持语法正确,比如有很多文本框 txt ,但是不能保证用户都输入数值。比如
    temp="select * from a where 1=1"
    if txt<>"" then
    temp=temp+"and id=" +txt

    手机写的,大概就是这个意思。
    yueyoum
    yueyoum
    Sep 2, 2016
    17
    上面说 为了拼接 SQL 方便的, 其实是 那个程序员太懒,太 LOW 而已。

    1 , 为何不用 ORM ?
    2 , 就算不用 ORM , 拼接那些 SQL 很难?
    jydeng
    jydeng
    Sep 2, 2016
    18
    因为懒的判断。
    ming2050
    ming2050
    Sep 2, 2016
    19
    我也挺喜欢用这种拼接 sql 的方式 进行查询,非常方便,但是得注意安全性问题
    linescape
    linescape
    Sep 2, 2016
    20
    @yueyoum
    1.ORM 底层也是拼 sql
    2.复杂的多表联查, ORM 就蛋疼了
    ytmsdy
    ytmsdy
    Sep 2, 2016
    21
    为了拼 sql 的时候方便一点,不用判断是否为第一个条件。
    后面的条件,直接加 and 就可以了
    hubertZheng
    hubertZheng
    Sep 2, 2016
    22
    同拼接 sql
    caixiexin
    caixiexin
    Sep 2, 2016
    23
    @Infernalzero 讲真,现在用 mybatis 有时候还会这么写 = =|| ,对 orm 老是有种本能的排斥
    caixiexin
    caixiexin
    Sep 2, 2016
    24
    @yueyoum 为什么会 low 呢,某些场景下这么写可读性挺好的,也没有性能问题= =
    FrankFang128
    FrankFang128
    Sep 2, 2016 via Android
    25
    少一个 if
    zuotech
    zuotech
    Sep 2, 2016
    27
    一般用于条件的拼接, 在 mysql 里可以写成 where 1 , oracle 才需要 where 1=1 这么 low 的写法...哈哈
    riverphoenix
    riverphoenix
    Sep 2, 2016❤️2
    28
    当初公司的 orm 也是这么写的,然后就被人注入了
    dong3580
    dong3580
    Sep 2, 2016
    29
    @zuotech
    MSSQL 也是 where 1=1 ,顺便问一下,哪儿 low 了?
    zuotech
    zuotech
    Sep 2, 2016
    30
    @dong3580 开个玩笑, 因为非要写个表达式 , 如果别人写个 where 123 = 123 ,你说行不行, 当然行, 就是感觉上很 low
    dong3580
    dong3580
    Sep 2, 2016
    31
    @zuotech
    哈哈,笑点一下变低了。。。
    jy01264313
    jy01264313
    Sep 2, 2016
    32
    完全有点不知所措
    mfu
    mfu
    Sep 2, 2016
    33
    一般直接写个 where 1 and XXX...
    yueyoum
    yueyoum
    Sep 2, 2016
    34
    @caixiexin

    别总是把性能挂在嘴上, 我说 low 指的是 拼接完全不需要 where 1 = 1 啊, 这样 LZ 就不会有这样的疑问了
    wyntergreg
    wyntergreg
    Sep 2, 2016
    35
    @yueyoum 有的企业级报表的一条 sql 就 100 多行,各种联表各种嵌套,你不懒你 orm 搞一搞。你不 low 你搞一种比拼接字符串或者字符串匹配效率更高的方式出来。
    gdtv
    gdtv
    Sep 2, 2016
    36
    @riverphoenix 这个写法和注入没有任何关系
    yueyoum
    yueyoum
    Sep 2, 2016
    37
    @linescape ORM 确实在 处理复杂查询, 写出来的 代码 比 raw sql 还要复杂。

    ORM 为啥 拼接的 SQL 就没有 where 1 =1 这种蛋疼的东西? 你想想
    yueyoum
    yueyoum
    Sep 2, 2016
    38
    @wyntergreg 见 LS
    wyntergreg
    wyntergreg
    Sep 2, 2016
    39
    @yueyoum oracle 你不写 1=1 你试试
    zhs227
    zhs227
    Sep 2, 2016
    40
    很早很早以前,在某些数据库使用不带条件的 delete 时不会返回删除记录数,就会有人给加上一个 where 1=1 ,这样会返回 affected rows 。至于 select 中的 1=1 的话,应该就是纯粹的方便串拼接吧
    wyntergreg
    wyntergreg
    Sep 2, 2016
    41
    @yueyoum orm 浪费性能加了个判断,把拼好的条件的第一个 and 给 replace 了。用 1=1 的方式性能绝无问题
    Ixizi
    Ixizi
    Sep 2, 2016
    42
    没有 ORM 不会用数据库
    wyntergreg
    wyntergreg
    Sep 2, 2016
    43
    @Ixizi orm 用到最后会发现不会写 sql 了。而且复杂的 sql 用 orm 是做不到的
    tjxjj
    tjxjj
    Sep 2, 2016
    44
    编程技巧而已。
    linescape
    linescape
    Sep 2, 2016
    45
    @riverphoenix 拼接无问题,做好变量绑定
    yueyoum
    yueyoum
    Sep 2, 2016
    46
    @wyntergreg

    我知道你的意思, 就是 添加一个新 条件, 就往老条件后面 + " and " + 新条件
    最后还要把 最前面的 and 去掉。

    如果要判断 还有性能损失。


    1 , 在操作数据库, 有大量 IO 的情况下, 判断一个 空字符串 也能给你的程序 带来 性能担忧, 那也就不用讨论了, 我还没达到你的高度

    2 , 就算不判断, 也可以直接拼接 两个 API 罢了。 一个 初始化条件, 一个 append 其他条件



    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>

    void append_the_fucking_condition(char* conditon, const char* other)
    {
    strcat(conditon, " and ");
    strcat(conditon, other);
    }

    char* make_condition(const char* first_condition)
    {
    char* conditon = (char*)malloc(sizeof(char) * 512);
    strcat(conditon, first_condition);
    return conditon;
    }



    int main()
    {
    char* conditon = make_condition("o.operation_time>=\'2016/6/1\'");
    append_the_fucking_condition(conditon, "o.operation_time<\'2016/7/28\'");

    printf("%s\n", conditon);

    free(conditon);
    return 0;
    }
    plan9
    plan9
    Sep 2, 2016
    47
    @yueyoum 程序有 bug😓
    barbery
    barbery
    Sep 2, 2016
    48
    这种 SQL ,我也醉了
    shinwood
    shinwood
    Sep 2, 2016
    49
    用 1 AND 不是更方便。

    这样写还有一种原因,为了 debug 起来方便。
    alexapollo
    alexapollo
    Sep 2, 2016
    50
    Python 大法好
    ykrl089
    ykrl089
    Sep 2, 2016
    51
    拼接 sql 很容易出问题的,竟然还有人敢这么干!
    SoloCompany
    SoloCompany
    Sep 3, 2016❤️3
    52
    从这么多回复看来很多人要么是强迫症或者自我感觉太良,要么从来没有维护过数据库
    事实上 1=1 已经几乎可以说成为了一种约定

    如果需要我要手写一个复杂一些的 SQL 语句,习惯上也都会在编辑器里面的条件前面加一个 1=1 然后回车,然后每个 AND 条件写一行,最后加上分号

    好处是什么呢?
    你后面继续写下面的 AND 条件根本无需担心关键字和顺序
    你可以随便交换两个 AND 条件(可能仅仅是为了更好看)
    可以随便复制粘贴一行条件到其它位置再修改
    可以随便删除一行条件包括第一个而不需要手工修正任何内容

    再举另一个例子
    java 或者 js 的数组都允许最后一个元素悬挂一个逗号
    目的也是为了可以让多行元素来定义数组的时候,能够保持对称性,去除首尾效应
    美观有时候并不是这么重要
    so898
    so898
    Sep 3, 2016❤️4
    53
    我要是告诉你们还有 WHERE 1=2 OR 这种技巧,楼上几个有洁癖的是不是要炸
    ivvei
    ivvei
    Sep 3, 2016
    54
    我写 SQL 一般是这样写的:

    select a
    ,b
    ,c
    ,d
    from tble
    where 1=1
    and xxxxx
    and xxxxx

    逗号都写前面,方便调试。

    如果是程序里拼接,加判断当然可以。但是既然可以不加判断直接写,为什么非要多写个判断呢?
    mgcnrx11
    mgcnrx11
    Sep 3, 2016 via iPhone
    55
    我说一个碰到的问题。项目使用 druid 做数据库连接池,自带某安全功能会校验永真条件,只要出现永真条件就不会让 SQL 跑,目的猜是为了防 SQL 注入,一般的 SQL 注入手法之一。然后问题来了, 1=1 就是一个永真条件……从安全觉度再讨论,是否不应该去建议这样拼 SQL 呢
    blacklee
    blacklee
    Sep 3, 2016
    56
    按楼上很多人的说法,这样拼 sql 我用了 10 来年了,怎么就没出过问题呢?这是个问题。

    我看是你们满眼觉得 1=1 是何等的不爽,而忽略了更为重要的事情。这才是问题。
    iyangyuan
    iyangyuan
    Sep 3, 2016 via iPhone
    57
    造成 sql 注入的根本原因是用户输入参数未转义,和 1=1 有什么关系?关键在于不要直接拼接参数,而是将其用占位符表示。难道 ORM 底层的 sql 不是拼接出来的吗?
    caixiexin
    caixiexin
    Sep 3, 2016 via Android
    58
    @ykrl089 拼接 SQL ,然后参数转义并 Prepared Statements 化就没问题。
    Fedor
    Fedor
    Sep 3, 2016
    59
    我一般
    WHERE 1
    AND ....
    AND ....
    AND ....
    AND ....
    ytmsdy
    ytmsdy
    Sep 3, 2016
    60
    @SoloCompany 同意。。
    benson458
    benson458
    Sep 3, 2016 via Android
    61
    原来还有这种方式, get 到了
    badcode
    badcode
    Sep 3, 2016
    62
    有一种场景
    删表中全数据的时候
    DELETE FROM `table` WHERE 1=1
    ykrl089
    ykrl089
    Sep 3, 2016 via iPhone
    63
    @caixiexin 问题是很多人拼着拼着就忘了,或者换个人开发不定按套路来。所以还是 orm 安全点
    516654246
    516654246
    Sep 3, 2016
    64
    查询时偶尔也会这样写。为了调试...
    select xx from table where
    a=x?
    and b=y?
    我如果调试不要过滤条件是不是把 2 、 3 行干掉还得去把 where 删掉?
    我如果加了 1=1...
    至于性能...?和强迫症
    blacklee
    blacklee
    Sep 3, 2016
    65
    一起写 Java 的时候经常这么干,并没有什么不好的。
    现在自己写 Rails 就不需要这么干了

    ``
    <code>
    @topics = Topic.all
    if params[:name] && !params[:name].empty?
    @topics = @topics.where("title like ?", "%#{params[:name]}%")
    end
    if params[:id] && !params[:id].empty?
    @topics = @topics.where("id = ?", "#{params[:id]}")
    end
    if params[:status] && !params[:status].empty?
    @topics = @topics.where("status = ?", params[:status])
    end
    </code>
    ``

    顺便看看 V2 的编辑器能不能搞代码
    tabris17
    tabris17
    Sep 3, 2016 via iPhone
    66
    复杂的 sql 虽然用的少,但是绝对是必要的,一般会写个自动拼接 sql 的助手类,可以避免注入
    mind3x
    mind3x
    Sep 3, 2016 via Android
    67
    楼上写 Java 的各位,即使不用 ORM ,还有个东西叫 jOOQ
    conglovely
    conglovely
    Sep 4, 2016
    68
    经常用 plsql ,写 1=1 美化后, and 在下一行,方便注释。。。
    dungeonsnd
    dungeonsnd
    Sep 4, 2016
    69
    大家都在用 ORM 吗?
    如果有些平台或者库没有特别好的怎么办? 比如 iOS 平台,我不想用 CoreData ,想用 fmdb 。那怎么用 ORM? 自己开发一套 ORM?
    fortunezhang
    fortunezhang
    Sep 4, 2016
    70
    为以后用填坑呢.如果哪天想要添加条件直接在 1=1 后面写,或者替换 1=1 就可以了
    ETO
    ETO
    Sep 5, 2016
    71
    @yueyoum 不能赞同。:)
    wilddog
    wilddog
    Sep 5, 2016
    72
    是为了拼接 sql !
    lbp0200
    lbp0200
    Sep 5, 2016 via Android
    73
    SQL 注入欢迎您
    initdrv
    initdrv
    Sep 5, 2016
    74
    看似简单的问题,其实不简单啊,在下输了,只知道方便拼接条件,却没想到能涉及那么多方面的知识……
    Lucups
    Lucups
    Sep 5, 2016
    75
    这种 where 1 = 1 的写法我几年前年第一次见到同事写时觉得有点 low ,但发现确实很实用。

    ORM 在 SQL 比较复杂的情况下确实比较乏力,所以有时候用这种方式快捷方便,也容易理解, ORM 写出来的代码可能更难理解。

    另外,这个用法跟 SQL Injection 有半毛钱关系?
    wmhx
    wmhx
    Sep 5, 2016
    76
    1=1 和注入没关系, 只是为了拼接方便, 拼接当然是拼接有占位符的 sql, 以下是我用 jfinal 的示例:
    String sqlExceptSelect = " from t1 where 1=1 ";
    List < Object > paras = new ArrayList < Object > ( );
    if ( !"".equals ( pinfen1 ) ) {// /评分 start
    sqlExceptSelect += " and {pinfen}>=? ";
    paras.add ( pinfen1 );
    }
    if ( !"".equals ( pinfen2 ) ) {// /评分 end
    sqlExceptSelect += " and {pinfen} <=? ";
    paras.add ( pinfen2 );
    }
    sqlExceptSelect = sqlExceptSelect.replaceAll ( "\\{pinfen\\}" , "cast( `评分` as decimal(10,2))" )// /
    Page < Record > llpg = DB ( db ).paginate ( 1,20, "select * " , sqlExceptSelect , paras.toArray ( new Object [ paras.size ( ) ] ) );

    pinfen1 和 pinfen2 是界面输入的, 您看能注入么?
    dhssingle
    dhssingle
    Sep 5, 2016
    77
    注入和 1=1 有毛关系
    About   ·   Help   ·   Advertise   ·   Blog   ·   API   ·   FAQ   ·   Privacy   ·   Solana   ·   1696 Online   Highest 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 143ms · UTC 17:15 · PVG 01:15 · LAX 09:15 · JFK 12:15
    ♥ Do have faith in what you're doing.