From cddb946e10932b6c8f5f4a919badee8dccaab62a Mon Sep 17 00:00:00 2001 From: rootphantomer Date: Wed, 14 Sep 2022 11:06:49 +0800 Subject: [PATCH] =?UTF-8?q?v1.6=20=E4=BC=98=E5=8C=96=E4=BB=A3=E7=A0=81?= =?UTF-8?q?=E9=80=BB=E8=BE=91=E5=92=8C=E6=96=B0=E5=A2=9E=E4=B8=BB=E6=9C=BA?= =?UTF-8?q?=E6=95=B0=E6=8D=AE=E5=AE=9E=E6=97=B6=E6=9F=A5=E8=AF=A2?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 7 +++- main.go | 49 ++++++++++++++---------- src/apis/api.go | 75 +++++++++++++++++++++++++++++------- src/model/reqjson.go | 4 +- src/model/respjson.go | 89 +++++++++++++++++++++++++++++++++++++++++-- src/utils/LoadJson.go | 14 ++++++- 6 files changed, 196 insertions(+), 42 deletions(-) diff --git a/README.md b/README.md index 871aa28..ab155df 100644 --- a/README.md +++ b/README.md @@ -2,7 +2,7 @@ * @Author: ph4nt0mer * @Date: 2022-09-01 18:39:52 * @LastEditors: rootphantomer - * @LastEditTime: 2022-09-10 13:06:50 + * @LastEditTime: 2022-09-14 11:05:21 * @FilePath: /quake_go/README.md * @Description: * @@ -29,6 +29,11 @@ rust 项目代码 移步这里——https://github.com/360quake/quake_rs/ ## 更新日志 +- 2022-09-14 v1.6: + + - 新增主机数据接口,增加主机数据实时查询功能(example:./quake host 'service:http' -st 0 -sz 20) + - 优化命令行提示和代码逻辑 + - 2022-09-10 v1.5: - 替换解析的 response 的 json 由 struct 变为 map,方便可以自定义需要返回的结果 diff --git a/main.go b/main.go index 4294c7e..1e035da 100644 --- a/main.go +++ b/main.go @@ -2,9 +2,9 @@ * @Author: ph4nt0mer * @Date: 2022-08-31 17:03:03 * @LastEditors: rootphantomer - * @LastEditTime: 2022-09-10 12:56:58 + * @LastEditTime: 2022-09-14 11:03:15 * @FilePath: /quake_go/main.go - * @Description: + * @Description:主函数 * * Copyright (c) 2022 by ph4nt0mer, All Rights Reserved. */ @@ -36,7 +36,8 @@ func hflag_init() { hflag.AddFlag("end_time", "-e time to end time flag", hflag.Shorthand("e"), hflag.Type("time"), hflag.DefaultValue(time.Now().Format("2006-01-02 15:04:05"))) hflag.AddFlag("field", "-fe swich body,title,host,html_hash,x_powered_by to show infomation", hflag.Shorthand("fe"), hflag.Type("string"), hflag.DefaultValue("")) hflag.AddFlag("query_txt", "-qt ./file.txt file to query search", hflag.Shorthand("qt"), hflag.Type("string"), hflag.DefaultValue("")) - hflag.AddPosFlag("option", "init,info,search") + hflag.AddPosFlag("option", "init,info,search,host") + hflag.AddPosFlag("args", "query value,example port:443", hflag.DefaultValue("")) if err := hflag.Parse(); err != nil { panic(err) } @@ -45,10 +46,18 @@ func hflag_init() { fmt.Println("./quake -h get help!") return } - + var reqjson Reqjson + reqjson.Query = hflag.GetString("args") + reqjson.Start = hflag.GetString("start") + reqjson.Size = hflag.GetString("size") + reqjson.Start_time = hflag.GetTime("start_time") + reqjson.End_time = hflag.GetTime("end_time") + reqjson.Ignore_cache = hflag.GetBool("ignore_cache") + reqjson.Field = hflag.GetString("field") + reqjson.Query_txt = hflag.GetString("query_txt") switch strings.ToLower(hflag.GetString("option")) { case "version": - fmt.Println("version:1.4") + fmt.Println("version:1.6") case "init": if num < 3 { fmt.Println("!!!!token is empty !!!!") @@ -60,28 +69,28 @@ func hflag_init() { if !status { return } - apis.InfoGet2(token.Token) + apis.InfoGet(token.Token) case "search": token, status := utils.ReadYaml("./config.yaml") if !status { return } - var reqjson Reqjson - reqjson.Query = os.Args[2] - reqjson.Start = hflag.GetString("start") - reqjson.Size = hflag.GetString("size") - reqjson.Start_time = hflag.GetTime("start_time") - reqjson.End_time = hflag.GetTime("end_time") - reqjson.Ignore_cache = hflag.GetBool("ignore_cache") - reqjson.Field = hflag.GetString("field") - reqjson.Query_txt = hflag.GetString("query_txt") apis.SearchServicePost(reqjson, token.Token) case "host": - fmt.Println("主机数据接口待完成。。。") - case "favicon": - fmt.Println("favicon相似度接口待完成。。。") - case "domain": - fmt.Println("domain ") + token, status := utils.ReadYaml("./config.yaml") + if !status { + return + } + apis.HostSearchPost(reqjson, token.Token) + // case "favicon": + // fmt.Println("favicon相似度接口待完成。。。") + // token, status := utils.ReadYaml("./config.yaml") + // if !status { + // return + // } + // apis.HostSearchPost(reqjson, token.Token) + // case "domain": + // fmt.Println("domain ") default: fmt.Println("args failed !!!!") } diff --git a/src/apis/api.go b/src/apis/api.go index d24f67f..640978a 100644 --- a/src/apis/api.go +++ b/src/apis/api.go @@ -2,9 +2,9 @@ * @Author: ph4nt0mer * @Date: 2022-09-01 15:36:10 * @LastEditors: rootphantomer - * @LastEditTime: 2022-09-10 12:55:37 + * @LastEditTime: 2022-09-14 10:59:15 * @FilePath: /quake_go/src/apis/api.go - * @Description: + * @Description:封装请求接口 * * Copyright (c) 2022 by ph4nt0mer, All Rights Reserved. */ @@ -18,6 +18,7 @@ import ( "quake/src/tools" "quake/src/utils" "strconv" + "strings" ) func FilterableServiceGET(token string) { @@ -37,6 +38,7 @@ func SearchServicePost(reqjson Reqjson, token string) { // "end_time": "2021-02-01 00:00:00" // }' uri := "/search/quake_service" + reqjson.Query = strings.ReplaceAll(reqjson.Query, " ", "") if reqjson.Query == "" || reqjson.Query == "?" { fmt.Println("No query specified") return @@ -59,6 +61,7 @@ func SearchServicePost(reqjson Reqjson, token string) { if err != nil { panic(err) } + fmt.Println(string(setting.URL + uri)) fmt.Println(string(datajson)) body := tools.ApisPost(setting.URL+uri, datajson, token) data_result := utils.SeriveLoadJson(body).Data @@ -111,19 +114,20 @@ func AggregationServicePost(query []byte, start string, size string, token strin uri := "/aggregation/quake_service" tools.ApisPost(setting.URL+uri, query, token) } + +// func InfoGet(token string) { +// // 个人信息接口 +// uri := "/user/info" +// info := tools.ApisGet(setting.URL+uri, token) +// resut := utils.InfoLoadJson(info) +// data := resut.Data +// fmt.Println("#用户名:", data.User.Username) +// fmt.Println("#邮 箱:", data.User.Email) +// fmt.Println("#手机:", data.MobilePhone) +// fmt.Println("#月度积分:", data.MonthRemainingCredit) +// fmt.Println("#长效积分:", data.ConstantCredit) +// } func InfoGet(token string) { - // 个人信息接口 - uri := "/user/info" - info := tools.ApisGet(setting.URL+uri, token) - resut := utils.InfoLoadJson(info) - data := resut.Data - fmt.Println("#用户名:", data.User.Username) - fmt.Println("#邮 箱:", data.User.Email) - fmt.Println("#手机:", data.MobilePhone) - fmt.Println("#月度积分:", data.MonthRemainingCredit) - fmt.Println("#长效积分:", data.ConstantCredit) -} -func InfoGet2(token string) { // 个人信息接口 uri := "/user/info" info := tools.ApisGet(setting.URL+uri, token) @@ -140,3 +144,46 @@ func FaviconPost(query string, token string) { uri := "/query/similar_icon/aggregation" tools.ApisGet(setting.URL+uri, token) } + +func HostSearchPost(reqjson Reqjson, token string) { + // curl -X POST "https://quake.360.cn/api/v3/search/quake_host" -H "X-QuakeToken: d17140ae-xxxx-xxx-xxxx-c0818b2bbxxx" -H "Content-Type: application/json" -d '{ + // "query": "service: http", + // "start": 20, + // "size": 10, + // "ignore_cache": false, + // "start_time": "2021-01-01 00:00:00", + // "end_time": "2021-02-01 00:00:00" + // }' + + uri := "/search/quake_host" + reqjson.Query = strings.ReplaceAll(reqjson.Query, " ", "") + if reqjson.Query == "" || reqjson.Query == "?" { + fmt.Println("No query specified") + return + } + if reqjson.Query_txt != "" { + bytedata, _ := utils.ReadLine(reqjson.Query_txt) + tmp := "" + for _, v := range bytedata { + if tmp == "" { + tmp = v + } else { + tmp += " OR " + v + } + + } + // fmt.Println(tmp) + reqjson.Query = tmp + } + datajson, err := json.Marshal(reqjson) + if err != nil { + panic(err) + } + fmt.Println(string(setting.URL + uri)) + fmt.Println(string(datajson)) + body := tools.ApisPost(setting.URL+uri, datajson, token) + data_result := utils.HostLoadJson(body).Data + for index, value := range data_result { + fmt.Println(strconv.Itoa(index+1) + "# " + value.IP) + } +} diff --git a/src/model/reqjson.go b/src/model/reqjson.go index e0b0c29..f841230 100644 --- a/src/model/reqjson.go +++ b/src/model/reqjson.go @@ -2,9 +2,9 @@ * @Author: rootphantomer zhoufei1@360.cn * @Date: 2022-09-06 17:58:31 * @LastEditors: rootphantomer - * @LastEditTime: 2022-09-10 12:54:02 + * @LastEditTime: 2022-09-14 10:25:53 * @FilePath: /quake_go/src/model/reqjson.go - * @Description:model + * @Description:请求包结构体 * * Copyright (c) 2022 by rootphantomer, All Rights Reserved. */ diff --git a/src/model/respjson.go b/src/model/respjson.go index 3ced0a3..7554ca0 100644 --- a/src/model/respjson.go +++ b/src/model/respjson.go @@ -2,9 +2,9 @@ * @Author: rootphantomer zhoufei1@360.cn * @Date: 2022-09-06 18:10:53 * @LastEditors: rootphantomer - * @LastEditTime: 2022-09-10 12:50:32 + * @LastEditTime: 2022-09-14 10:39:09 * @FilePath: /quake_go/src/model/respjson.go - * @Description: + * @Description:返回包结构体 * * Copyright (c) 2022 by rootphantomer, All Rights Reserved. */ @@ -95,7 +95,90 @@ type ServiceJson struct { } `json:"pagination"` } `json:"meta"` } - +type HostJson struct { + Code int `json:"code"` + Data []struct { + Asn int `json:"asn"` + Cdn struct { + Domain string `json:"domain"` + IsCdn bool `json:"is_cdn"` + } `json:"cdn"` + Components []map[string]interface{} `json:"Components"` + // Components []struct { + // ID string `json:"id"` + // ProductCatalog []string `json:"product_catalog"` + // ProductLevel string `json:"product_level"` + // ProductNameCn string `json:"product_name_cn"` + // ProductNameEn string `json:"product_name_en"` + // ProductType []string `json:"product_type"` + // ProductVendor string `json:"product_vendor"` + // Version string `json:"version"` + // } `json:"components"` + Hostname string `json:"hostname"` + ID string `json:"id"` + Images []string `json:"images"` + IP string `json:"ip"` + IsIpv6 bool `json:"is_ipv6"` + // Location map[string]string `json:"location"` + Location struct { + CityCn string `json:"city_cn"` + CityEn string `json:"city_en"` + CountryCn string `json:"country_cn"` + CountryCode string `json:"country_code"` + CountryEn string `json:"country_en"` + DistrictCn string `json:"district_cn"` + DistrictEn string `json:"district_en"` + Isp string `json:"isp"` + ProvinceCn string `json:"province_cn"` + ProvinceEn string `json:"province_en"` + Radius float64 `json:"radius"` + SceneCn string `json:"scene_cn"` + SceneEn string `json:"scene_en"` + } `json:"location"` + Org string `json:"org"` + OsName string `json:"os_name"` + OsVersion string `json:"os_version"` + Port int `json:"port"` + Service struct { + Banner string `json:"banner"` + Cert string `json:"cert"` + HTTP map[string]interface{} `json:"http"` + // HTTP struct { + // Body string `json:"body"` + // Favicon struct { + // Data string `json:"data"` + // Hash string `json:"hash"` + // Location string `json:"location"` + // } `json:"favicon"` + // Host string `json:"host"` + // HTMLHash string `json:"html_hash"` + // MetaKeywords string `json:"meta_keywords"` + // Path string `json:"path"` + // ResponseHeaders string `json:"response_headers"` + // Server string `json:"server"` + // StatusCode int `json:"status_code"` + // Title string `json:"title"` + // XPoweredBy string `json:"x_powered_by"` + // } `json:"http"` + Name string `json:"name"` + Product string `json:"product"` + Response string `json:"response"` + Version string `json:"version"` + } `json:"service"` + SysTag []string `json:"sys_tag"` + Time string `json:"time"` + Transport string `json:"transport"` + } `json:"data"` + Message string `json:"message"` + Meta struct { + Pagination struct { + Count int `json:"count"` + PageIndex int `json:"page_index"` + PageSize int `json:"page_size"` + Total int `json:"total"` + } `json:"pagination"` + } `json:"meta"` +} type InfoJson struct { Code int `json:"code"` Data struct { diff --git a/src/utils/LoadJson.go b/src/utils/LoadJson.go index c848973..97e0e57 100644 --- a/src/utils/LoadJson.go +++ b/src/utils/LoadJson.go @@ -2,9 +2,9 @@ * @Author: rootphantomer zhoufei1@360.cn * @Date: 2022-09-06 16:04:43 * @LastEditors: rootphantomer - * @LastEditTime: 2022-09-09 18:13:59 + * @LastEditTime: 2022-09-14 10:39:54 * @FilePath: /quake_go/src/utils/LoadJson.go - * @Description: + * @Description:解析json的逻辑代码 * * Copyright (c) 2022 by rootphantomer, All Rights Reserved. */ @@ -26,6 +26,16 @@ func SeriveLoadJson(body string) (result ServiceJson) { } return } +func HostLoadJson(body string) (result HostJson) { + var hostjson HostJson + + if err := json.Unmarshal([]byte(body), &hostjson); err == nil { + result = hostjson + } else { + fmt.Println(err) + } + return +} func SeriveLoadJson2(body string) (result []map[string]string) { var servicemapjson map[string][]map[string]string