最新消息:

社工库的搭建思路与代码实现

技术 admin 6030浏览 0评论

貌似很多朋友拿着库,用BAT 或者PHP读取TXT的形式来扫,文件太大了的话,1,2分钟估计都查不出来,因为导入库是一个不错的方法,很多都不知道怎么搭建的吧,用MSSQL或则 ORACLE来搭建的,个人感觉没那必要,原因在于安装他们需要的空间很大,运行也占内存,因此,个人推荐MYSQL,对于的亿级以上的数据也是不超过 10秒钟,下面是我最近的搭建过程与一些心得:
1.首先得准备一个MYSQL+PHP环境,我用的是PHPSTUDY集成环境工具,自己下载安装就行了。
2.接下来就是MYSQL的表的设计了,之前一直采用的是 USERNAME,NICKNAME,PASSWORD,EMAIL,MOBILE,IDCARD,SALT,SITE(用户名,昵称,密码,邮箱,手 机,身份证,SALT,来源网站)这样的字段,如图(NAVICATE FOR MYSQL工具截图):

sgk-300x120

字段类型采用varchar 长度一般在50就行了,索引是必须要的。

如果觉得就这样的话,那就大错特错了,我举个例:


QQ库一般只占用 username,password两项,那么其他字段都为空

126邮箱 只占用 email,password两项 ,其他为空

建立索引时,这些为空的字段也占用了空间,这是一点

第二点,有些库密码是明文 ,有些又是密文,密文一般都没啥可查询的,如果都建索引的话,就浪费了空间了,不建立索引,那查询速度又不行了

因此,个人建议分表导入,每个不同类型的库,都采用一个表来存,查询时,根据需要,只查询我们需要查询的库,这样节约空间了,也节约了时间

我以我的库结构来说吧

sgk1

前缀都采用统一的字符,下划线后面跟这个表有关的名称,比如shegongku_qq,shegongku_126这样的,每个表都是采用USERNAME,NICKNAME,PASSWORD,EMAIL,MOBILE,IDCARD,SALT,SITE这样的字段

查询界面:

sgk2

主要PHP流程代码:

$kw=$_REQUEST['kw'];  //查询关键字
$type=$_REQUEST['type'];  //查询的字段,比如用户名,密码,还是其他等等
$search=$_REQUEST['search']; //查询类型,LIKE 模糊查找,=精确查找
private function len_check($kw='',$slen=3){  //检查待查询的字符长度
if (strlen(trim($kw))<$slen){
return true;
}else{
return false;
}
}
switch ($type) {
case 'username':
if($this->len_check($kw,3)){ $this->ajaxReturn(0,'查询长度不能小于:3',2);exit();}
$ret=$this->_getData('username',$kw,$search);
break;
case 'nickname':
if($this->len_check($kw,3)){ $this->ajaxReturn(0,'查询长度不能小于:3',2);exit();}
$ret=$this->_getData('nickname',$kw,$search);
break;
//......同上

满足条件后,就都调用了_getData函数,这里就是查询主要的函数

private function _getData($type='',$kw='',$search='like'){
if(empty($type)||empty($kw)||empty($search)){
return false;
}
$WebList=array(
'126'     =>array('site' => '126邮箱',        'username' => 2, 'nickname' => 2, 'password' => 1, 'mobile' => 2, 'idcard' => 2, 'email' => 1, 'salt' => 2),
'126disk' =>array('site' => '126网盘',        'username' => 1, 'nickname' => 1, 'password' => 1, 'mobile' => 2, 'idcard' => 2, 'email' => 1, 'salt' => 2),
.......//其他表都一样的
'changgui'=>array('site' => '',          'username' => 1, 'nickname' => 1, 'password' => 1, 'mobile' => 1, 'idcard' => 1, 'email' => 1, 'salt' => 1),
'163'     =>array('site' => '163邮箱',        'username' => 2, 'nickname' => 2, 'password' => 1, 'mobile' => 2, 'idcard' => 2, 'email' => 1, 'salt' => 2),
);
//上面的'username' => 2 表示此字段不需要查询,因此username字段可以不要(我是为了好看,都统一了字段,这里个人决定要不要), 'email' => 1 表示此字段需要查询
$ret=array();
$kws=array();
foreach ($WebList as $web=>$desc) {
$vs=array();
if ($desc[$type]=='1'){ //字段是否属于能查询的
foreach ($desc as $k=>$v)
if ($v==''||$v=='1')       //存在的字段处理,为空的SITE需要从表中获取
$vs[]=$k;
elseif ($v=='2')
$vs[]="'null' as $k";   //不存在的字段处理,用null填充
else
$vs[]="'$v' as $k";  //直接输出SITE来源比如:126邮箱
$col=implode(',',$vs);        //将字段用,连接起来
if ($search=="like")
$sql[]="SELECT * FROM  (  SELECT   $col FROM shegongku_".$web." WHERE `{$type}` like '$kw%' LIMIT 10   )  tmp_{$web} ";
else
$sql[]="SELECT * FROM  (  SELECT   $col FROM shegongku_".$web." WHERE `{$type}` = '$kw’ LIMIT 10   )  tmp_{$web} ";
}
}
$sql=implode(" UNION ALL ", $sql); //联合查询,此处将上面的每个表查询联合起来

接下来的$SQL就是需要执行的查询语句了,我就不贴代码了

给个实例联合查询SQL语句(模糊查询邮箱是ceshi@qq.com的结果,其他):

SELECT * FROM  (  SELECT   '126邮箱' as site,'null' as username,'null' as nickname,password,'null' as mobile,'null' as idcard,email,'null' as salt FROM shegongku_126 WHERE `email` like 'ceshi@qq.com%' LIMIT 10   )  tmp_126  UNION ALL SELECT * FROM  (  SELECT   '126网盘' as site,username,nickname,password,'null' as mobile,'null' as idcard,email,'null' as salt FROM shegongku_126disk WHERE `email` like 'ceshi@qq.com%' LIMIT 10   )  tmp_126disk  UNION ALL SELECT * FROM  (  SELECT   '163邮箱' as site,'null' as username,'null' as nickname,password,'null' as mobile,'null' as idcard,email,'null' as salt FROM shegongku_163 WHERE `email` like 'ceshi@qq.com%' LIMIT 10   )  tmp_163  UNION ALL SELECT * FROM  (  SELECT   '17173' as site,username,'null' as nickname,password,'null' as mobile,'null' as idcard,email,'null' as salt FROM shegongku_17173 WHERE `email` like 'ceshi@qq.com%' LIMIT 10   )  tmp_17173  UNION ALL SELECT * FROM  (  SELECT   site,username,nickname,password,mobile,idcard,email,salt FROM shegongku_changgui WHERE `email` like 'ceshi@qq.com%' LIMIT 10   )  tmp_changgui  UNION ALL SELECT * FROM  (  SELECT   'YS168' as site,username,'null' as nickname,password,'null' as mobile,'null' as idcard,email,'null' as salt FROM shegongku_ys168 WHERE `email` like 'ceshi@qq.com%' LIMIT 10   )  tmp_ys168

这样就排除了不想要查询的表,大大节约了搜索时间,也更加方便设置需要查询的字段

转自:https://forum.90sec.org/viewthread.php?tid=5859

转载文章请注明,转载自:小马’s Blog http://www.i0day.com

本文链接: http://www.i0day.com/1380.html

超快速TB级社工库,一起来搭建吧

这几年最火的项目是什么?当然是各种海量据量的处理,存储。我们已经迎来了大数据时代
大数据的科学价值和社会价值体现在于可以将数据转化为经济价值的来源。当然不仅仅是这样。

2009年H1N1流感爆发的时候,谷歌通过45亿数据建模分析每天保存的30亿条搜索指令,率先于疾病控制中心,判断出流感的传播的源头
2012年Farecast恭喜2000亿条飞行数据记录,分析出每一条航线上每一架飞机内的每一个位置一年内最便宜的价位。
....

 

当然,上述大数据的例子都设计到数据挖掘,这是我们以后可以讨论的
我相信,各位资深黑阔手上有不少裤子,像我们这种电脑硬盘才320G的渣渣,估计一个裤子就能装满- -。裤子大了,数据量大了,相信在查找的时候,那种卡个
一天半夜才搜索出结果的感觉,肯定是非常不爽。
不知道大家看没看过道哥写的一篇关于中国地下某黑客:中国黑客传说:游走在黑暗中的精灵
文中有一段是这样的:

对于V来说,想知道谁的密码,只需要在库中简单的查询一下,马上就得到了。有时候密码经过了哈希算 法的处理,需要经过彩虹表的反查,或者V会拿到一个云计算中心去用分布式计算框架破解(对技术有疑惑或者有兴趣的读者可以参阅拙作《白帽子讲Web安 全》)。所以V能够直接查到女孩的邮箱密码。

V估计使用的就是某搜索引擎框架(或者其他方法),搜索分布式存储的裤子。如果有加密,则通过分布式计算框架进行破解(比如hadoop)      由于我自己手上的几个项目,有涉及到搭建分布式计算集群(hadoop),分布式缓存nosql数据库(redis),数据挖掘R语言,搜索引擎 (lucene) 等等,所以对这方面稍微了解一点点、
所以今天我们的主题是,咱也装个b,搭建一个超快速TB级的社工库,简单的说,就是自己搭建一个搜索引擎,利用搜索引擎快速查找海量裤子中的数据(裤子当然得自己找),由于不涉及到数据挖掘,所以相对来说比较简单。
我们来看一下数据单位的换算关系:

      最小的基本单位是Byte,按顺序给出所有单位:bit、Byte、KB、MB、GB、TB、PB、EB、ZB、YB、DB、NB,
  它们按照进率1024(2的十次方)来计算:
  1Byte = 8 Bit
  1 KB = 1,024 Bytes 
  1 MB = 1,024 KB = 1,048,576 Bytes 
  1 GB = 1,024 MB = 1,048,576 KB = 1,073,741,824 Bytes
  1 TB = 1,024 GB = 1,048,576 MB = 1,073,741,824 KB = 1,099,511,627,776 Bytes

那么我们要用到的搜索引擎框架是基于Lucene的Hibernate Search.
lucene查询效率分析:http://www.stanford.edu/class/archive/cs/cs276a/cs276a.1032/projects/reports/dsu800.pdf

使用lucene的公司有apple,ibm,eclipse,wiki,twitter等等

我们先来看看twitter对搜索性能的要求:

Our demands on the new system are immense: With over 1,000 TPS (Tweets/sec) and 12,000 QPS (queries/sec) = over 1 billion queries per day (!) we already put a very high load on our machines. As we want the new system to last for several years, the goal was to support at least an order of magnitude more load.

 

所以大家不用质疑lucene搜索引擎的效率。由于Lucene是不完整的搜索引擎,它是一个java的工具包。所以需要我们去开发。下面我们来开始进入今天最重要的部分。搭建以及编码。
噢,忘了说,我们用的语言是java,搭配SSH框架,mysql数据库(不使用数据库,直接索引文件也是可以的).

首先导入所有jar包,包括lucene:

SSH配置文件,包含了数据库的账号密码连接信息:

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:context="http://www.springframework.org/schema/context"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
           http://www.springframework.org/schema/beans/spring-beans.xsd
           http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd">

         <!-- DAO -->
        <context:annotation-config/>
        <context:component-scan base-package="cn.edu">
    <context:exclude-filter expression="org.springframework.stereotype.Controller" type="annotation" />
  </context:component-scan>
        <bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource"
                destroy-method="close">
                <property name="driverClassName" value="com.mysql.jdbc.Driver" />
                <property name="url" value="jdbc:mysql://localhost:3306/h_search" />
                <property name="username" value="root" />
                <property name="password" value="123" />
        </bean>
        <bean id="sessionFactory"
                class="org.springframework.orm.hibernate4.LocalSessionFactoryBean">
                <property name="dataSource" ref="dataSource" />
                <property name="annotatedClasses">
                        <list>
                                <value>cn.edu.fjnu.Victim</value>
                        </list>
                </property>
                <property name="hibernateProperties">
                        <value>
                                hibernate.dialect=org.hibernate.dialect.MySQLDialect
                                hibernate.show_sql=true
                                hibernate.hbm2ddl.auto=update
                                current_session_context_class=thread
                                javax.persistence.validation.mode=none
                                hibernate.format_sql=true
                                hibernate.use_sql_comments=true
                                hibernate.search.default.directory_provider=filesystem
                                hibernate.search.default.indexBase=E:\\java\\lucene_index

                     </value>
                </property>
        </bean>
<bean id="transactionManager" class="org.springframework.orm.hibernate3.HibernateTransactionManager">
    <property name="sessionFactory" ref="sessionFactory" />
    <property name="dataSource" ref="dataSource" />
  </bean>

</beans>

接着创建一个被搜索类(在实体上标志@Indexed,表示被索引),我们假设为Victim,拥有id和name两个字段属性:

@Indexed
@Entity
public class Victim {

  public Integer getId() {
                return id;
        }

        public void setId(Integer id) {
                this.id = id;
        }

        public String getName() {
                return name;
        }

        public void setName(String name) {
                this.name = name;
        }

  @Id
  @GeneratedValue
  private Integer id;

  @Field(index=Index.YES, store=Store.YES)
  private String name;

  public Victim() {} 

  // standard getters/setters follow here
}

好了,我们可以进行测试。默认情况下,在你进行数据库插入更新等操作,Lucene会自动监听并且更新索引:

 @Test
        public void testAdd() {
                SessionFactory sessionFactory = (SessionFactory) TestUtil.ctx
                                .getBean("sessionFactory");
                Session session = sessionFactory.openSession();
                int i = 20;
                Transaction trans = null;
                trans = session.beginTransaction();
                while (i < 40) {
Victim victim= new Victim();
                        author.setName("王尼玛" + i);
                        i++;
                        session.save(victim);
                }
                trans.commit();

        }

 

我们可以用luke这个工具来查看lucene生成的索引:

成功生成索引。
我们可以通过以下方法查询:

 @Test
        public void testSearch() {
                SessionFactory sessionFactory = (SessionFactory) TestUtil.ctx
                                .getBean("sessionFactory");
                Session session = sessionFactory.openSession();
                FullTextSession fullTextSession = Search.getFullTextSession(session);
                QueryBuilder qb = fullTextSession.getSearchFactory()
            .buildQueryBuilder().forEntity( Victim.class ).get();
        org.apache.lucene.search.Query query = qb
          .keyword()
//要搜素name字段
          .onFields("name")
          .matching("王尼玛")
          .createQuery();

        // wrap Lucene query in a org.hibernate.Query
        org.hibernate.Query hibQuery = 
            fullTextSession.createFullTextQuery(query, Book.class);

        // execute search,返回结果到result中
        List result = hibQuery.list();

当然我们只是在自己一台机子上,lucene支持分布式扩展,也就是说,你加入的机子越多,速度也越来越快。理论上无限量扩展。包括把裤子扔到分布式存储上
今天的主题到这里就结束了,码字好辛苦………………,感觉不会再爱了。
看看反响怎么样吧….后面没准要写个:手动搭建分布式云计算框架破解md5

转载请注明:jinglingshu的博客 » 社工库的搭建思路与代码实现

发表我的评论
取消评论

表情

Hi,您需要填写昵称和邮箱!

  • 昵称 (必填)
  • 邮箱 (必填)
  • 网址

网友最新评论 (1)

  1. 上面的博客内容转自两篇不同的文章,这两篇实现社工库的思路不同。第一篇中,作者尽可能简化社工库的搭建,使用PHP+Mysql来实现。第二篇的作者,应用到了一些高深的技术:分布式计算集群(hadoop),分布式缓存nosql数据库(redis),数据挖掘R语言,搜索引擎 (lucene) 等等,作者尽可能利用先进技术来实现社工库的搭建。 可以说,这两篇文章的思路各有优劣,适用情况不同而已。
    admin12年前 (2013-08-24)回复