主頁 > 資料庫 > ELK太重?試試KFC日志采集

ELK太重?試試KFC日志采集

2021-08-21 06:37:20 資料庫

寫在前面

  ELK三劍客(ElasticSearch,Logstash,Kibana)基本上可以滿足日志采集、資訊處理、統計分析、可視化報表等一些日志分析的作業,但是對我們來說……太重了,并且技術堆疊不是一路的,我們的場景是需要采集各個業務部門服務器上面的各個業務系統,所以盡量不要影響到服務器的性能,以侵入性最低的方式進行采集,不做其他多余操作,因而,在前端日志采集這塊,對比其他Logstash、Flume等采集工具之后,決定采用輕量的Filebeat作為日志采集工具,Filebeat采用go開發,運行不需要額外部署環境,相比Flume依賴jdk輕量了不少,且占用記憶體低,

  采集鏈路如下所示:Filebeat日志采集、處理轉換之后,推送到kafka,采用Clickhouse的kafka引擎進行消費存盤,因而,我暫且稱之為KFC??組合,

Filebeat部署

  采集目標環境:

    系統:Window Server 2008 R2 Enterprise

    日志類別:IIS日志、業務系統日志

    日志路徑:D:/IIS/www.A.com/logs/*.txt 、D:/IIS/www.B.com/logs/*.txt、D:/IIS/www.C.com/logs/*.txt

    Filebeat:7.12.1(https://www.elastic.co/cn/downloads/beats/filebeat

  因為采集的是windows作業系統,建議下載Filebeat壓縮包,并以windows服務的方式運行,使用安裝包msi安裝不方便除錯,需要頻繁的卸載、安裝操作,下載之后解壓出來進行對組態檔 filebeat.yml 進行配置,

  業務系統日志格式示例:

2021-04-06 11:21:17,940 [39680] DEBUG Zc -  time:0ms update XXX set ModifyTime=GETDATE(), [State] = 190, [FuZeRen] = '張三' where [ID] = '90aa9a69-7a33-420e-808c-624693c65aef' and [CompanyID] = '9e52867e-2035-4148-b09e-55a90b3020d5' 
2021-04-06 11:21:21,612 [22128] DEBUG Service ModelBase -  time:0ms (/api/XXX/XXX/XXX?InfoID=6d43b831-6169-46d2-9518-f7c9ed6fe39c&ValidateStatus=1)更新材料狀態
2021-04-06 11:21:21,612 [22128] DEBUG Zc -  time:0ms select ID from XXX where InfoRelationID='6d43b831-6169-46d2-9518-f7c9ed6fe39c' 
2021-04-06 11:21:21,612 [22128] DEBUG Zc -  time:0ms insert into XXXX(ValidateDate ,[ID],[ValidateState],[ValidateUser],[ValidateUserID],[ValidateUnit],[ValidateUnitID],[ValidateUnitType],[InfoRelationID]) values( GETDATE(),'c77cf4ab-71b5-46c7-b91b-2829d73aa700',1,'XXXX','0387f889-e1d4-48aa-b275-2241da1d2c9e','XXXXX有限公司','2f2a94c8-c23c-4e8a-98b3-c32a9b0487f7',0,'6d43b831-6119-46d2-9518-f7c9ed6fe39c')
2021-04-06 03:25:22,237 [46840] ERROR ASP.global_asax - time:0ms 客戶端資訊:Ip:116.238.55.21, 173.131.245.61 瀏覽器:Chrome 版本:68 作業系統:WinNT服務端錯誤資訊:
頁面:http://www.A.com:803/dbapp_53475dbapp_e524534.php
錯誤源:System.Web.Mvc
堆疊跟蹤: at System.Web.Mvc.DefaultControllerFactory.GetControllerInstance(RequestContext requestContext, Type controllerType)
at System.Web.Mvc.DefaultControllerFactory.CreateController(RequestContext requestContext, String controllerName)
at System.Web.Mvc.MvcHandler.ProcessRequestInit(HttpContextBase httpContext, IController& controller, IControllerFactory& factory)
at System.Web.Mvc.MvcHandler.BeginProcessRequest(HttpContextBase httpContext, AsyncCallback callback, Object state)
at System.Web.HttpApplication.CallHandlerExecutionStep.System.Web.HttpApplication.IExecutionStep.Execute()
at System.Web.HttpApplication.ExecuteStep(IExecutionStep step, Boolean& completedSynchronously)

  FileBeat配置:

max_procs: 2
queue:
  mem:
    events: 2048
    flush.min_events: 2048
# ============================== Filebeat inputs ===============================

filebeat.inputs:

# 管理系統 
- type: log
  enabled: true
  encoding: GB2312
  paths:
    - D:/IIS/www.A.com/logs/*.txt
  
  multiline.pattern: '^\d{4}-\d{1,2}-\d{1,2}'
  multiline.negate: true
  multiline.match: after
  fields:
    topic: 'dlbZcZGBSyslogs'
  fields_under_root: true
  
# 單位系統 
- type: log
  enabled: true
  encoding: GB2312
  paths:
    - D:/IIS/www.B.com/logs/*.txt
  ### Multiline options
  multiline.pattern: '^\d{4}-\d{1,2}-\d{1,2}'
  multiline.negate: true
  multiline.match: after
  fields:
    topic: 'dlbZcDWSyslogs'
  fields_under_root: true
  
# 個人系統  
- type: log
  enabled: true
  encoding: GB2312
  paths:
    - D:/IIS/www.C.com/logs/*.txt
  ### Multiline options
  multiline.pattern: '^\d{4}-\d{1,2}-\d{1,2}'
  multiline.negate: true
  multiline.match: after
  fields:
    topic: 'dlbZcMySyslogs'
  fields_under_root: true

# 除錯輸出
#output.console:
#   pretty: true
#output.file:
#  path: "D:/bigData"
#  filename: filebeat.log

# -------------------------------- Kafka Output --------------------------------
output.kafka:
  # Boolean flag to enable or disable the output module.
  enabled: true
  hosts: ["192.168.1.10:9092"]

  # The Kafka topic used for produced events. The setting can be a format string
  # using any event field. To set the topic from document type use `%{[type]}`.
  topic: '%{[topic]}'

  # Authentication details. Password is required if username is set.
  #username: ''
  #password: ''

  # The number of concurrent load-balanced Kafka output workers.
  worker: 2

  max_message_bytes: 10000000

# ================================= Processors =================================
processors:
  - add_host_metadata:
      when.not.contains.tags: forwarded
  - add_cloud_metadata: ~
  - add_docker_metadata: ~
  - add_kubernetes_metadata: ~
  - script:
      lang: javascript
      id: my_filter
      tag: enable
      source: >
        function process(event) {
            var str = event.Get("message");
            var sp = str.split(" "); 
            var log_datetime = sp.slice(0,2).join(" ");
            var regEx = /^\d{4}-\d{2}-\d{2}$/;
            var prefix_date = log_datetime.substring(0, 10);
            if(prefix_date.match(regEx) != null)
            {
                event.Put("server","221");
                log_datetime = log_datetime.replace(",",".");
                log_datetime = log_datetime.replace("'","");
                regEx = /^\d{4}-\d{2}-\d{2}\s\d{2}:\d{2}:\d{2}.\d{3}$/;
                if(log_datetime.match(regEx) != null)
                {
                    event.Put("log_datetime",log_datetime);
                    event.Put("log_index",sp.slice(2,3).join(" ").replace("[","").replace("]",""));
                    event.Put("log_level",sp.slice(3,4).join(" "));
                    if(str.match(/(?<=time:)\S*(?=ms)/)!=null)
                    {
                        var spTime= str.split("time:");
                        var spPre = spTime[0].split(" ");
                        var spNext = spTime[1].split(" ");                    
                        event.Put("log_class",spPre.slice(4).join(" ")); 
                        
                        var log_execTime= spNext.slice(0,1).join(" ").replace("ms","");
                        regEx = /^(\-|\+)?\d+(\.\d+)?$/;
                        if(regEx.test(log_execTime))
                        {
                            event.Put("log_execTime",log_execTime);
                        }
                        else
                        {
                            event.Put("log_execTime","-1");
                        }
                        event.Put("log_message",spNext.slice(1).join(" "));
                    }
                    else
                    {
                        event.Put("log_class",sp.slice(4,5).join(" "));
                        event.Put("log_execTime","-1");
                        event.Put("log_message",sp.slice(6).join(" "));
                    }
                    return;
                }
            }
            event.Cancel();
        }
  - drop_fields:
      fields: ["@timestamp", "message", "host", "ecs", "agent", "@metadata", "log", "input"]

以上的配置說明:

  max_procs:設定可以同時執行的最大CPU數;

  queue :內部佇列資訊;

  Filebeat inputs:日志資料源采集的入口;

  其他欄位如下說明:

#日志型別
- type: log        
#開啟
  enabled: true
#編碼格式,有中文必須設定
  encoding: GB2312
#路徑
  paths:
    - D:/IIS/www.A.com/logs/*.txt
#多行匹配前綴
  multiline.pattern: '^\d{4}-\d{1,2}-\d{1,2}'
#開啟多行匹配
  multiline.negate: true
#開啟多行之后,匹配是合并到上一條資訊
  multiline.match: after
#增加一個欄位,用于kafka的topic的識別
  fields:
    topic: 'dlbZcZGBSyslogs'
# 欄位增加在輸出json的根目錄下
  fields_under_root: true

//https://www.cnblogs.com/EminemJK/p/15165961.html

  Kafka Output:kafka的配置資訊,主要是  topic: '%{[topic]}' 的設定,因為這里采集多個資料源,對于不同的topic,在資料源輸入的時候,已經設定好欄位如 topic: 'dlbZcZGBSyslogs' ,所以此處使用占位符靈活設定;

  Processors:配置處理器,即對采集的日志資訊進行處理,處理是按行處理,當字串處理即可,可以使用js語法進行對字串進行處理;Filebeat的處理器可以多種多樣,具體可以看檔案,

另外,在除錯的時候,可以采用檔案輸出或Console輸出來觀察處理后輸出的資料格式,再進行微調:

output.file:
  path: "D:/bigData"
  filename: filebeat.log

  IIS的日志也差不多,只是微調處理邏輯就可以了,一通百通,

  其他配置可以參考官網檔案:https://www.elastic.co/guide/en/beats/filebeat/current/index.html

Kafka配置

   Kafka沒有特別的處理,在這里只是進行訊息的接收,新建好主題就可以,

//個人系統
bin/kafka-topics.sh --create --zookeeper 192.168.1.10:2181 --replication-factor 1 --partitions 3 --topic dlbZcMySyslogs
//單位系統
bin/kafka-topics.sh --create --zookeeper 192.168.1.10:2181 --replication-factor 1 --partitions 3 --topic dlbZcDWSyslogs
//管理系統
bin/kafka-topics.sh --create --zookeeper 192.168.1.10:2181 --replication-factor 1 --partitions 3 --topic dlbZcZGBSyslogs

   partitions 磁區數的大小,取決設定了多少個消費者,這里我們有三臺服務器做了Clickhouse的集群作為消費者,所以磁區數設定為3,一般情況,消費者總數不應該大于磁區數,每個磁區只能分配一個消費者,

Clickhouse配置

  Clickhouse三個分片的集群,如果你是單機的,只需要把語法相應的修改一下即可,

  在每臺服務器上創建kafka引擎表:

CREATE TABLE kafka_dlb_ZC_My_syslogs (
    log_datetime DateTime64,
    log_index String,
    log_level String,
    log_class String,
    log_message String,
    log_execTime Float32,
    server String
  ) ENGINE = Kafka
  SETTINGS kafka_broker_list = '192.168.1.10:9092',
                        kafka_topic_list = 'dlbZcMySyslogs',
                        kafka_group_name = 'dlbZcMySyslogs_sys',
                        kafka_format = 'JSONEachRow',
                        kafka_num_consumers = 1;

  創建物體表:

  CREATE TABLE dlb_ZC_My_syslogs on cluster cluster_3s_1r
  (
    log_datetime DateTime64,
    log_index String,
    log_level String,
    log_class String,
    log_message String,
    log_execTime Float32,
    server String
  ) ENGINE = ReplicatedMergeTree('/clickhouse/tables/{layer}-{shard}/dlb_ZC_My_syslogs', '{replica}')
  ORDER BY toDate(log_datetime)
  PARTITION BY toYYYYMM(log_datetime);

//https://www.cnblogs.com/EminemJK/p/15165961.html

  物體表是使用集群來創建的,如果是單機請洗掉 on cluster cluster_3s_1r ,修改表引擎即可,如果已經開啟了zookeeper且開啟復制表,在任一一臺服務器運行運行一次即可,

  在每臺服務器上創建物化視圖:

  CREATE MATERIALIZED VIEW viem_dlb_ZC_My_syslogs_consumer TO dlb_ZC_My_syslogs
    AS SELECT *
    FROM kafka_dlb_ZC_My_syslogs;

  創建分布式視圖(可選,單機請忽略):

CREATE TABLE Dis_dlb_ZC_My_syslogs ON CLUSTER cluster_3s_1r
    AS LogsDataBase.dlb_ZC_My_syslogs
        ENGINE = Distributed(cluster_3s_1r, 'LogsDataBase',  'dlb_ZC_My_syslogs',rand());

  分布式表將聚合集群中每個分片的表資訊,進行執行一次,

運行

  順便提供一個快速運行Filebeat和卸載的bat腳本:

  運行服務:

//windows server2008以上版本的服務器
cd %~dp0
.\install-service-filebeat.ps1
pause

//windows server 2008 和以下的服務器
 cd %~dp0
 PowerShell.exe -ExecutionPolicy RemoteSigned -File .\install-service-filebeat.ps1
 pause

  卸載服務:

//windows server2008以上版本的服務器
cd %~dp0
.\uninstall-service-filebeat.ps1
pause

//windows server2008和以下版本的服務器
cd %~dp0
PowerShell.exe -ExecutionPolicy RemoteSigned -File .\uninstall-service-filebeat.ps1
pause

  運行之后,在任務管理器中,將服務設定為運行即可,

  查看分布式資料:

   資料采集完畢,完美,

  既然資料已經有了,資料可視化方面可以采用多種方式了,以Grafana為例:

 最后

  下班,周末愉快,

 

轉載請註明出處,本文鏈接:https://www.uj5u.com/shujuku/295063.html

標籤:大數據

上一篇:MySQL連接查詢操作總結和測驗代碼

下一篇:MySQL JOIN的使用

標籤雲
其他(157675) Python(38076) JavaScript(25376) Java(17977) C(15215) 區塊鏈(8255) C#(7972) AI(7469) 爪哇(7425) MySQL(7132) html(6777) 基礎類(6313) sql(6102) 熊猫(6058) PHP(5869) 数组(5741) R(5409) Linux(5327) 反应(5209) 腳本語言(PerlPython)(5129) 非技術區(4971) Android(4554) 数据框(4311) css(4259) 节点.js(4032) C語言(3288) json(3245) 列表(3129) 扑(3119) C++語言(3117) 安卓(2998) 打字稿(2995) VBA(2789) Java相關(2746) 疑難問題(2699) 细绳(2522) 單片機工控(2479) iOS(2429) ASP.NET(2402) MongoDB(2323) 麻木的(2285) 正则表达式(2254) 字典(2211) 循环(2198) 迅速(2185) 擅长(2169) 镖(2155) 功能(1967) .NET技术(1958) Web開發(1951) python-3.x(1918) HtmlCss(1915) 弹簧靴(1913) C++(1909) xml(1889) PostgreSQL(1872) .NETCore(1853) 谷歌表格(1846) Unity3D(1843) for循环(1842)

熱門瀏覽
  • GPU虛擬機創建時間深度優化

    **?桔妹導讀:**GPU虛擬機實體創建速度慢是公有云面臨的普遍問題,由于通常情況下創建虛擬機屬于低頻操作而未引起業界的重視,實際生產中還是存在對GPU實體創建時間有苛刻要求的業務場景。本文將介紹滴滴云在解決該問題時的思路、方法、并展示最終的優化成果。 從公有云服務商那里購買過虛擬主機的資深用戶,一 ......

    uj5u.com 2020-09-10 06:09:13 more
  • 可編程網卡芯片在滴滴云網路的應用實踐

    **?桔妹導讀:**隨著云規模不斷擴大以及業務層面對延遲、帶寬的要求越來越高,采用DPDK 加速網路報文處理的方式在橫向縱向擴展都出現了局限性。可編程芯片成為業界熱點。本文主要講述了可編程網卡芯片在滴滴云網路中的應用實踐,遇到的問題、帶來的收益以及開源社區貢獻。 #1. 資料中心面臨的問題 隨著滴滴 ......

    uj5u.com 2020-09-10 06:10:21 more
  • 滴滴資料通道服務演進之路

    **?桔妹導讀:**滴滴資料通道引擎承載著全公司的資料同步,為下游實時和離線場景提供了必不可少的源資料。隨著任務量的不斷增加,資料通道的整體架構也隨之發生改變。本文介紹了滴滴資料通道的發展歷程,遇到的問題以及今后的規劃。 #1. 背景 資料,對于任何一家互聯網公司來說都是非常重要的資產,公司的大資料 ......

    uj5u.com 2020-09-10 06:11:05 more
  • 滴滴AI Labs斬獲國際機器翻譯大賽中譯英方向世界第三

    **桔妹導讀:**深耕人工智能領域,致力于探索AI讓出行更美好的滴滴AI Labs再次斬獲國際大獎,這次獲獎的專案是什么呢?一起來看看詳細報道吧! 近日,由國際計算語言學協會ACL(The Association for Computational Linguistics)舉辦的世界最具影響力的機器 ......

    uj5u.com 2020-09-10 06:11:29 more
  • MPP (Massively Parallel Processing)大規模并行處理

    1、什么是mpp? MPP (Massively Parallel Processing),即大規模并行處理,在資料庫非共享集群中,每個節點都有獨立的磁盤存盤系統和記憶體系統,業務資料根據資料庫模型和應用特點劃分到各個節點上,每臺資料節點通過專用網路或者商業通用網路互相連接,彼此協同計算,作為整體提供 ......

    uj5u.com 2020-09-10 06:11:41 more
  • 滴滴資料倉庫指標體系建設實踐

    **桔妹導讀:**指標體系是什么?如何使用OSM模型和AARRR模型搭建指標體系?如何統一流程、規范化、工具化管理指標體系?本文會對建設的方法論結合滴滴資料指標體系建設實踐進行解答分析。 #1. 什么是指標體系 ##1.1 指標體系定義 指標體系是將零散單點的具有相互聯系的指標,系統化的組織起來,通 ......

    uj5u.com 2020-09-10 06:12:52 more
  • 單表千萬行資料庫 LIKE 搜索優化手記

    我們經常在資料庫中使用 LIKE 運算子來完成對資料的模糊搜索,LIKE 運算子用于在 WHERE 子句中搜索列中的指定模式。 如果需要查找客戶表中所有姓氏是“張”的資料,可以使用下面的 SQL 陳述句: SELECT * FROM Customer WHERE Name LIKE '張%' 如果需要 ......

    uj5u.com 2020-09-10 06:13:25 more
  • 滴滴Ceph分布式存盤系統優化之鎖優化

    **桔妹導讀:**Ceph是國際知名的開源分布式存盤系統,在工業界和學術界都有著重要的影響。Ceph的架構和演算法設計發表在國際系統領域頂級會議OSDI、SOSP、SC等上。Ceph社區得到Red Hat、SUSE、Intel等大公司的大力支持。Ceph是國際云計算領域應用最廣泛的開源分布式存盤系統, ......

    uj5u.com 2020-09-10 06:14:51 more
  • es~通過ElasticsearchTemplate進行聚合~嵌套聚合

    之前寫過《es~通過ElasticsearchTemplate進行聚合操作》的文章,這一次主要寫一個嵌套的聚合,例如先對sex集合,再對desc聚合,最后再對age求和,共三層嵌套。 Aggregations的部分特性類似于SQL語言中的group by,avg,sum等函式,Aggregation ......

    uj5u.com 2020-09-10 06:14:59 more
  • 爬蟲日志監控 -- Elastc Stack(ELK)部署

    傻瓜式部署,只需替換IP與用戶 導讀: 現ELK四大組件分別為:Elasticsearch(核心)、logstash(處理)、filebeat(采集)、kibana(可視化) 下載均在https://www.elastic.co/cn/downloads/下tar包,各組件版本最好一致,配合fdm會 ......

    uj5u.com 2020-09-10 06:15:05 more
最新发布
  • day02-2-商鋪查詢快取

    功能02-商鋪查詢快取 3.商鋪詳情快取查詢 3.1什么是快取? 快取就是資料交換的緩沖區(稱作Cache),是存盤資料的臨時地方,一般讀寫性能較高。 快取的作用: 降低后端負載 提高讀寫效率,降低回應時間 快取的成本: 資料一致性成本 代碼維護成本 運維成本 3.2需求說明 如下,當我們點擊商店詳 ......

    uj5u.com 2023-04-20 08:33:24 more
  • MySQL中binlog備份腳本分享

    關于MySQL的二進制日志(binlog),我們都知道二進制日志(binlog)非常重要,尤其當你需要point to point災難恢復的時侯,所以我們要對其進行備份。關于二進制日志(binlog)的備份,可以基于flush logs方式先切換binlog,然后拷貝&壓縮到到遠程服務器或本地服務器 ......

    uj5u.com 2023-04-20 08:28:06 more
  • day02-短信登錄

    功能實作02 2.功能01-短信登錄 2.1基于Session實作登錄 2.1.1思路分析 2.1.2代碼實作 2.1.2.1發送短信驗證碼 發送短信驗證碼: 發送驗證碼的介面為:http://127.0.0.1:8080/api/user/code?phone=xxxxx<手機號> 請求方式:PO ......

    uj5u.com 2023-04-20 08:27:27 more
  • 快取與資料庫雙寫一致性幾種策略分析

    本文將對幾種快取與資料庫保證資料一致性的使用方式進行分析。為保證高并發性能,以下分析場景不考慮執行的原子性及加鎖等強一致性要求的場景,僅追求最終一致性。 ......

    uj5u.com 2023-04-20 08:26:48 more
  • sql陳述句優化

    問題查找及措施 問題查找 需要找到具體的代碼,對其進行一對一優化,而非一直把關注點放在服務器和sql平臺 降低簡化每個事務中處理的問題,盡量不要讓一個事務拖太長的時間 例如檔案上傳時,應將檔案上傳這一步放在事務外面 微軟建議 4.啟動sql定時執行計劃 怎么啟動sqlserver代理服務-百度經驗 ......

    uj5u.com 2023-04-20 08:26:35 more
  • 云時代,MySQL到ClickHouse資料同步產品對比推薦

    ClickHouse 在執行分析查詢時的速度優勢很好的彌補了MySQL的不足,但是對于很多開發者和DBA來說,如何將MySQL穩定、高效、簡單的同步到 ClickHouse 卻很困難。本文對比了 NineData、MaterializeMySQL(ClickHouse自帶)、Bifrost 三款產品... ......

    uj5u.com 2023-04-20 08:26:29 more
  • sql陳述句優化

    問題查找及措施 問題查找 需要找到具體的代碼,對其進行一對一優化,而非一直把關注點放在服務器和sql平臺 降低簡化每個事務中處理的問題,盡量不要讓一個事務拖太長的時間 例如檔案上傳時,應將檔案上傳這一步放在事務外面 微軟建議 4.啟動sql定時執行計劃 怎么啟動sqlserver代理服務-百度經驗 ......

    uj5u.com 2023-04-20 08:25:13 more
  • Redis 報”OutOfDirectMemoryError“(堆外記憶體溢位)

    Redis 報錯“OutOfDirectMemoryError(堆外記憶體溢位) ”問題如下: 一、報錯資訊: 使用 Redis 的業務介面 ,產生 OutOfDirectMemoryError(堆外記憶體溢位),如圖: 格式化后的報錯資訊: { "timestamp": "2023-04-17 22: ......

    uj5u.com 2023-04-20 08:24:54 more
  • day02-2-商鋪查詢快取

    功能02-商鋪查詢快取 3.商鋪詳情快取查詢 3.1什么是快取? 快取就是資料交換的緩沖區(稱作Cache),是存盤資料的臨時地方,一般讀寫性能較高。 快取的作用: 降低后端負載 提高讀寫效率,降低回應時間 快取的成本: 資料一致性成本 代碼維護成本 運維成本 3.2需求說明 如下,當我們點擊商店詳 ......

    uj5u.com 2023-04-20 08:24:03 more
  • day02-短信登錄

    功能實作02 2.功能01-短信登錄 2.1基于Session實作登錄 2.1.1思路分析 2.1.2代碼實作 2.1.2.1發送短信驗證碼 發送短信驗證碼: 發送驗證碼的介面為:http://127.0.0.1:8080/api/user/code?phone=xxxxx<手機號> 請求方式:PO ......

    uj5u.com 2023-04-20 08:23:11 more