ElasticSearch的使用方式和代码

1 . ElasticSearch(简称ES)

  • ES即为了解决原生Lucene使用的不足,优化Lucene的调用方式,并实现了高可用的分布式集群的搜索方案,其第一个版本于2010年2月出现在GitHub上并迅速成为最受欢迎的项目之一。
    首先,ES的索引库管理支持依然是基于Apache Lucene™的开源搜索引擎。
    ES也使用Java开发并使用Lucene作为其核心来实现所有索引和搜索的功能,但是它的目的是通过简单的 RESTful
    API来隐藏Lucene的复杂性,从而让全文搜索变得简单。 不过,ES的核心不在于Lucene,其特点更多的体现为:
    分布式的实时文件存储,每个字段都被索引并可被搜索 分布式的实时分析搜索引擎 可以扩展到上百台服务器,处理PB级结构化或非结构化数据
    高度集成化的服务,你的应用可以通过简单的 RESTful API、各种语言的客户端甚至命令行与之 交互。
    上手Elasticsearch非常容易。它提供了许多合理的缺省值,并对初学者隐藏了复杂的搜索引擎理论。它拥有开瓶即饮的效果(安装即可使用),只需很少的学习既可在生产环境中使用。

2. ES的使用者及类似框架

  1. 典型使用案例

    ①Github使用Elasticsearch搜索20TB的数据,包括13亿的文件和1300亿行的代码.
    ②Foursquare实时搜索5千万地点信息?Foursquare每天都用Elasticsearch做这样的事.
    ③德国SoundCloud使用Elasticsearch来为1.8亿用户提供即时精准的音乐搜索服务.
    ④Mozilla公司以火狐著名,它目前使用 WarOnOrange 这个项目来进行单元或功能测试,测试的结果以 json的方式索引到elasticsearch中,开发人员可以非常方便的查找 bug.
    ⑤Sony公司使用elasticsearch 作为信息搜索引擎.

  2. 类似框架

    ① Solr(重量级对手)
    Apache Lucene项目的开源企业搜索平台。其主要功能包括全文检索、命中标示、分面搜索、动态聚类、数据库集成,以及富文本(如Word、PDF)的处理。Solr是高度可扩展的,并提供了分布式搜索和索引复制。Solr是最流行的企业级搜索引擎,Solr4 还增加了NoSQL支持。
    Solr和ES比较:
    Solr 利用 Zookeeper 进行分布式管理,支持更多格式的数据(HTML/PDF/CSV),官方提供的功能更多在传统的搜索应用中表现好于 ES,但实时搜索效率低。
    ES自身带有分布式协调管理功能,但仅支持json文件格式,本身更注重于核心功能,高级功能多有第三方插件提供,在处理实时搜索应用时效率明显高于 ES。
    ② Katta
    基于 Lucene 的,支持分布式,可扩展,具有容错功能,准实时的搜索方案。
    优点:开箱即用,可以与 Hadoop 配合实现分布式。具备扩展和容错机制。
    缺点:只是搜索方案,建索引部分还是需要自己实现。在搜索功能上,只实现了最基本的需求。成功案例较少,项目的成熟度稍微差一些。
    ③ HadoopContrib
    Map/Reduce 模式的,分布式建索引方案,可以跟 Katta 配合使用。
    优点:分布式建索引,具备可扩展性。
    缺点:只是建索引方案,不包括搜索实现。工作在批处理模式,对实时搜索的支持不佳。

3.安装ES

  1. ES服务只依赖于JDK,推荐使用JDK1.7+。

    ① 下载ES安装包
    官方下载地址:https://www.elastic.co/downloads/elasticsearch
    本课程以在window环境下,ES 5.2.2版本为例,下载对应的ZIP文件
    在这里插入图片描述
    ② 运行ES
    bin/elasticsearch.bat
    ③ 验证
    访问:http://localhost:9200/
    在这里插入图片描述
    看到上图信息,恭喜你,你的ES集群已经启动并且正常运行.

3.java 操作 es 增删查改

ES对Java提供一套操作索引库的工具包,即Java API。所有的ES操作都使用Client对象执行。
ES的Maven引入
<dependency>
    <groupId>org.elasticsearch.client</groupId>
    <artifactId>transport</artifactId>
    <version>5.2.2</version>
</dependency>
<dependency>
    <groupId>org.apache.logging.log4j</groupId>
    <artifactId>log4j-api</artifactId>
    <version>2.7</version>
</dependency>
<dependency>
    <groupId>org.apache.logging.log4j</groupId>
    <artifactId>log4j-core</artifactId>
    <version>2.7</version>
</dependency>
<dependency>
        <groupId>junit</groupId>
        <artifactId>junit</artifactId>
        <version>4.12</version>
        <scope>test</scope>
  </dependency>
// 返回es java客户端
	public TransportClient getClient() throws Exception {
		// on startup
		TransportClient client = new PreBuiltTransportClient(Settings.EMPTY)
				.addTransportAddress(new InetSocketTransportAddress(InetAddress.getByName("localhost"), 9300));
		return client;
	}

	// 增
	@Test
	public void testAdd() throws Exception {
		TransportClient client = getClient();
		Map<String, Object> source = new HashMap<String, Object>();
		source.put("id", "1");
		source.put("price", 5000);
		source.put("gj", "cn");
		IndexResponse indexResponse = client.prepareIndex("shop", "goods", "1").setSource(source).get();
		System.out.println(indexResponse);
	}

	// 删除
	@Test
	public void testDelete() throws Exception {
		TransportClient client = getClient();
		DeleteResponse deleteResponse = client.prepareDelete("shop", "goods", "1").get();
		System.out.println(deleteResponse);
	}

	// 改
	@Test
	public void testUpdate() throws Exception {
		TransportClient client = getClient();
		Map<String, Object> source = new HashMap<String, Object>();
		source.put("id", "1");
		source.put("price", 6000);
		source.put("gj", "cn");
		UpdateResponse updateResponse = client.prepareUpdate("shop", "goods", "1").setDoc(source).get();
		System.out.println(updateResponse);
	}

	// save or update 如果文档有的话就修改,没有就新增
	@Test
	public void saveorupdate() throws Exception {
		TransportClient client = getClient();
		Map<String, Object> source = new HashMap<String, Object>();
		source.put("id", "1");
		source.put("price", 7000);
		source.put("gj", "cn");
		IndexRequest indexRequest = new IndexRequest("shop", "goods", "1").source(source);
		UpdateRequest updateRequest = new UpdateRequest("shop", "goods", "1").doc(source).upsert(indexRequest);
		client.update(updateRequest).get();
	}

	// 查
	@Test
	public void testQuery() throws Exception {
		TransportClient client = getClient();
		GetResponse getResponse = client.prepareGet("shop", "goods", "1").get();
		System.out.println(getResponse.getSource());
	}

	// 批量 同步数据库的数据到我们的索引库里面去
	@Test
	public void testBulk() throws Exception {
		TransportClient client = getClient();
		// 构建了请求批量对象
		BulkRequestBuilder bulkRequest = client.prepareBulk();

		for (int i = 0; i < 10; i++) {
			// 增加数据
			Map<String, Object> source = new HashMap<String, Object>();
			source.put("id", i);
			source.put("name", "iphone");
			source.put("price", 10 * i + i);
			source.put("gj", "cn");
			bulkRequest.add(client.prepareIndex("shop", "goods", i + "").setSource(source));
		}
		// 提交数据请求
		BulkResponse bulkResponse = bulkRequest.get();
		if (bulkResponse.hasFailures()) {
			System.out.println("出错误了");
		}
	}

	// 查询
/*	# 找出 名为 iphone 然后 价格范围为 [5000-9000]  发行国家:cn  分页数1 每页显示2条  按价格降序 
	#select *from goods where gj=cn and 5000<price<9000*/
	@Test
	public void testSearch() throws Exception {
		// 获取客户端对象
		TransportClient client = getClient();
		// 查询对象
		//BoolQueryBuilder boolQueryBuilder = new BoolQueryBuilder();
		BoolQueryBuilder boolQueryBuilder = QueryBuilders.boolQuery();
		// 必须查询对象 关键字匹配对象
		boolQueryBuilder.must(new MatchQueryBuilder("name", "iphone"));
		// 过滤对象
		List<QueryBuilder> filter = boolQueryBuilder.filter();
		filter.add(new TermQueryBuilder("gj", "cn"));
		filter.add(new RangeQueryBuilder("price").gte(20).lte(40));
		// GET shop/goods/_search 
		SearchResponse searchResponse = client.prepareSearch("shop").setTypes("goods").setQuery(boolQueryBuilder).setFrom(0).setSize(2).addSort("price", SortOrder.DESC).get();
		SearchHits hits = searchResponse.getHits();
		System.out.println("查询总数:"+hits.totalHits());
		// 获取真实的数据数组
		SearchHit[] hits2 = hits.hits();
		for (SearchHit searchHit : hits2) {
			Map<String, Object> source = searchHit.getSource();
			System.out.println(source);
		}
	}

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值