如何在firebase上执行sql“LIKE”操作?

Posted

技术标签:

【中文标题】如何在firebase上执行sql“LIKE”操作?【英文标题】:How to perform sql "LIKE" operation on firebase? 【发布时间】:2014-04-25 17:41:56 【问题描述】:

我正在使用 firebase 进行数据存储。数据结构是这样的:

products:
   product1:
      name:"chocolate",
   
   product2:
      name:"chochocho",
   

我想对此数据执行自动完成操作,通常我这样编写查询:

"select name from PRODUCTS where productname LIKE '%" + keyword + "%'";

因此,对于我的情况,例如,如果用户键入“cho”,我需要同时带上“chocolate”和“chochocho”作为结果。我考虑将所有数据放在“产品”块下,然后在客户端进行查询,但这可能需要大量内存用于大型数据库。那么,如何进行 sql LIKE 操作呢?

谢谢

【问题讨论】:

您找到使用 firebase 的方法了吗? @FaridAlHaddad 我已经很久没有问这个问题了,我什至不记得问过这个问题,但看起来我可能还没有找到解决方案并决定做其他事情。 哈哈 .. 解决方案是什么?你能分享一下吗?谢谢 @FaridAlHaddad 我真的不记得了,但看起来很多人都在寻找这个问题的答案,所以我会再次搜索这个主题并发布如果我发现有用的东西。跨度> 这个问题有解决方案吗?谢谢 【参考方案1】:

更新:随着 Cloud Functions for Firebase 的发布,linking Firebase to Algolia via Functions 还提供了另一种优雅的方法。这里的权衡是 Functions/Algolia 几乎是零维护,但可能比在 Node 中滚动你自己的成本更高。

目前 Firebase 中没有内容搜索。随着 API 的不断扩展,许多更常见的搜索场景(例如按属性搜索)将被纳入 Firebase。

与此同时,您当然可以自己种植。然而,搜索是一个庞大的话题(想想创建一个巨大的实时数据存储),被大大低估了,并且是您的应用程序的一个关键特性——不是您想要临时提供的,甚至不需要像 Firebase 这样的人代表您提供.因此,使用可扩展的第三方工具来处理索引、搜索、标签/模式匹配、模糊逻辑、加权排名等通常会更简单。

Firebase 博客中有一个 blog post on indexing with ElasticSearch,它概述了一种将快速但功能非常强大的搜索引擎集成到您的 Firebase 后端的简单方法。

基本上,它分两步完成。监控数据并为其编制索引:

var Firebase = require('firebase');
var ElasticClient = require('elasticsearchclient')

// initialize our ElasticSearch API
var client = new ElasticClient( host: 'localhost', port: 9200 );

// listen for changes to Firebase data
var fb = new Firebase('<INSTANCE>.firebaseio.com/widgets');
fb.on('child_added',   createOrUpdateIndex);
fb.on('child_changed', createOrUpdateIndex);
fb.on('child_removed', removeIndex);

function createOrUpdateIndex(snap) 
   client.index(this.index, this.type, snap.val(), snap.name())
     .on('data', function(data)  console.log('indexed ', snap.name()); )
     .on('error', function(err)  /* handle errors */ );


function removeIndex(snap) 
   client.deleteDocument(this.index, this.type, snap.name(), function(error, data) 
      if( error ) console.error('failed to delete', snap.name(), error);
      else console.log('deleted', snap.name());
   );

当你想进行搜索时查询索引:

<script src="elastic.min.js"></script>
 <script src="elastic-jquery-client.min.js"></script>
 <script>
    ejs.client = ejs.jQueryClient('http://localhost:9200');
    client.search(
      index: 'firebase',
      type: 'widget',
      body: ejs.Request().query(ejs.MatchQuery('title', 'foo'))
    , function (error, response) 
       // handle response
    );
 </script>

There's an example, and a third party lib to simplify integration, here.

【讨论】:

啊,谢谢,但我实际上是在为我的 android 应用程序使用 firebase,而且我对 javascript 知之甚少。你能给我一个链接或一个小例子,比如这个用java代码编写的javascript例子吗?我现在也将尝试理解该 javascript 代码 :) 谢谢 这在 2016 年还有意义吗? 概念相关。 API 调用的语法略有不同。 您好 Kato,我在这里发布了一个关于使用新 Firebase 进行手电筒设置的问题,希望您能提供一些知识!我真的很感激,谢谢! ***.com/questions/38276209/… 遗憾的是,您必须升级到 Blaze 计划才能在 Algolia 中使用 Firebase Cloud Functions【参考方案2】:

我相信你可以做到:

admin
.database()
.ref('/vals')
.orderByChild('name')
.startAt('cho')
.endAt("cho\uf8ff")
.once('value')
.then(c => res.send(c.val()));

这将找到名称以 cho 开头的 val。

source

【讨论】:

根据我的理解 startAt() 和 endAt() 用于限制数据库中两个特定对象之间的结果 - 不是查询字符串的内容。 @Heisenbug 有效,源视频来自谷歌本身。 这帮助我构建了一个小型搜索功能。我为每个单词创建了一个索引,将每个单词链接到相关项目。然后,在搜索时,我会计算每个项目的点击次数。 @Ced 有什么办法可以得到包含 cho的名字,而不仅仅是以它们开头(qwertycho, abchoba)? 这行得通,谢谢!希望 Firebase 开发人员的管道中有一个更“原生”的解决方案。【参考方案3】:

弹性搜索解决方案基本上绑定到 add set del 并提供一个 get by ,您可以完成文本搜索。 然后将内容保存在 mongodb 中。

虽然我喜欢并推荐弹性搜索项目的成熟度,但同样可以在没有其他服务器的情况下完成,只使用 firebase 数据库。 那就是我的意思: (https://github.com/metaschema/oxyzen)

对于索引部分基本上是功能:

    JSON 对文档进行字符串化。 删除所有属性名称和 JSON 以仅保留数据 (正则表达式)。 删除所有 xml 标签(因此也是 html)和属性(记住 老指导,“数据不应该在xml属性中”)只留下 如果存在 xml 或 html,则为纯文本。 删除所有特殊字符并用空格替换(正则表达式) 用一个空格替换多个空格的所有实例(正则表达式) 拆分为空格和循环: 为每个单词在某个索引结构中的文档中添加参考 您的数据库 tha 基本上包含以带有子项的单词命名的子项 以“ref/inthedatabase/dockey”的转义版本命名 然后像普通的 firebase 应用程序那样插入文档

在 oxyzen 实现中,文档的后续更新实际上会读取索引并更新它,删除不再匹配的单词,并添加新单词。

后续的单词搜索可以直接找到单词child中的文档。使用 hits 实现多词搜索

【讨论】:

【参考方案4】:

可以在 firebase 上执行 SQL“LIKE”操作

let node = await db.ref('yourPath').orderByChild('yourKey').startAt('!').endAt('SUBSTRING\uf8ff').once('value');

【讨论】:

如果数据库很大,不要使用这个建议。执行此请求后,我的数据库停止工作,并且在大约 5 分钟内没有从不同的设备发送响应。也许这个问题与 firebase 数据库逻辑有关。【参考方案5】:

这个查询对我有用,它看起来像下面的 mysql 语句

select * from StoreAds where University Like %ps%;

query = database.getReference().child("StoreAds").orderByChild("University").startAt("ps").endAt("\uf8ff");

【讨论】:

这不能正常工作,运行更多测试你会看到。

以上是关于如何在firebase上执行sql“LIKE”操作?的主要内容,如果未能解决你的问题,请参考以下文章

在 python 中,如何执行缓解 SQL 注入的 postgresql 'LIKE %name%' 查询?

如何在同一SQL查询中合并子句LIKE和BETWEEN?

如何使 LINQ 执行(SQL)LIKE 范围搜索

sqlserver like '%' 性能问题

Pandas 文本匹配像 SQL 的 LIKE?

Firebase 的喜欢/不喜欢功能