diff --git a/docs/create/linux/index-linux.mdx b/docs/create/linux/index-linux.mdx new file mode 100644 index 00000000000..f365b918b26 --- /dev/null +++ b/docs/create/linux/index-linux.mdx @@ -0,0 +1,44 @@ +--- +id: index-linux +title: Create a Redis database on Linux +description: A step by step guide to create a Redis database on Linux. +sidebar_label: Redis on Linux +slug: /create/linux/ +authors: [prasan] +--- + +import Authors from '@site/src/theme/Authors'; + + + +### From the official Debian/Ubuntu APT Repository + +You can install recent stable versions of Redis Stack from the official packages.redis.io APT repository. The repository currently supports Debian Bullseye (11), Ubuntu Xenial (16.04), Ubuntu Bionic (18.04), and Ubuntu Focal (20.04) on x86 processors. Add the repository to the apt index, update it, and install it: + +```sh +curl -fsSL https://packages.redis.io/gpg | sudo gpg --dearmor -o /usr/share/keyrings/redis-archive-keyring.gpg +echo "deb [signed-by=/usr/share/keyrings/redis-archive-keyring.gpg] https://packages.redis.io/deb $(lsb_release -cs) main" | sudo tee /etc/apt/sources.list.d/redis.list +sudo apt-get update +sudo apt-get install redis-stack-server +``` + +### From the official RPM Feed + +You can install recent stable versions of Redis Stack from the official packages.redis.io YUM repository. The repository currently supports RHEL7/CentOS7, and RHEL8/Centos8. Add the repository to the repository index, and install the package. + +Create the file /etc/yum.repos.d/redis.repo with the following contents + +``` +[Redis] +name=Redis +baseurl=http://packages.redis.io/rpm/rhel7 +enabled=1 +gpgcheck=1 +``` + +```sh +curl -fsSL https://packages.redis.io/gpg > /tmp/redis.key +sudo rpm --import /tmp/redis.key +sudo yum install epel-release +sudo yum install redis-stack-server +``` diff --git a/docs/howtos/quick-start/cli/_cli-basic-querying.mdx b/docs/howtos/quick-start/cli/_cli-basic-querying.mdx new file mode 100644 index 00000000000..3ceb8b7a78e --- /dev/null +++ b/docs/howtos/quick-start/cli/_cli-basic-querying.mdx @@ -0,0 +1,104 @@ + +- Connect to Redis using CLI or **[RedisInsight](https://redis.io/docs/stack/insight/)** (a GUI tool to visualize data & run commands) + +**RedisInsight** +![RedisInsight](../images/redis-insight.svg) + +```shell +# syntax 1 : connect using host & port, followed by password +$ redis-cli -h host -p port +> AUTH password +OK + +# example 1 +$ redis-cli -h redis15.localnet.org -p 6390 +> AUTH myUnguessablePassword +OK + +# syntax 2 : connect using uri +$ redis-cli -u redis://user:password@host:port/dbnum + +# example 2 +$ redis-cli -u redis://LJenkins:p%40ssw0rd@redis-16379.hosted.com:16379/0 + +``` + +- Basic CLI / RedisInsight workbench commands + +```shell +# syntax : Check specific keys +> KEYS pattern + +# example +> KEYS * + +#------------ +# syntax : Check number of keys in database +> DBSIZE + +#------------ +# syntax : set a key value +> SET key value EX expirySeconds + +# example +> SET company redis EX 60 + +#------------ +# syntax : get value by key +> GET key + +# example +> GET company + +#------------ +# syntax : delete keys +> DEL key1 key2 key3 ... keyN + +# example +> DEL company + +#------------ +# syntax : Check if key exists +> EXISTS key1 + +# example +> EXISTS company + +#------------ +# syntax : set expiry to key +> EXPIRE key seconds + +# example +> EXPIRE lastname 60 + +#------------ +# syntax : remove expiry from key +> PERSIST key + +# example +> PERSIST lastname + +#------------ +# syntax : find (remaining) time to live of a key +> TTL key + +# example +> TTL lastname + +#------------ +# syntax : increment a number +> INCR key + +# example +> INCR counter + +#------------ +# syntax : decrement a number +> DECR key + +# example +> DECR counter +``` + +Detailed CLI instructions can be viewed [here](https://redis.io/docs/manual/cli/) and +commands can be checked [here](https://redis.io/commands/) diff --git a/docs/howtos/quick-start/cli/_cli-secondary-indexing.mdx b/docs/howtos/quick-start/cli/_cli-secondary-indexing.mdx new file mode 100644 index 00000000000..ebe29d2140b --- /dev/null +++ b/docs/howtos/quick-start/cli/_cli-secondary-indexing.mdx @@ -0,0 +1,156 @@ + +Redis Stack enables the JSON data type in Redis. + +```shell +# syntax : set an object value to a key +> JSON.SET objKey $ value + +# example +> JSON.SET person $ '{"name":"Leonard Cohen","dob":1478476800,"isActive": true, "hobbies":["music", "cricket"]}' + +#------------ +# syntax : get object value of a key +> JSON.GET objKey $ + +# example +> JSON.GET person $ + +#------------ +# syntax : find object key length +> JSON.OBJLEN objKey $ + +# example +> JSON.OBJLEN person $ + +#------------ +# syntax : find object keys +> JSON.OBJKEYS objKey $ + +# example +> JSON.OBJKEYS person $ + +#------------ +# syntax : update nested property +> JSON.SET objKey $.prop value + +# example +> JSON.SET person $.name '"Alex"' + +#------------ +# syntax : update nested array +> JSON.SET objKey $.arrayProp fullValue +> JSON.SET objKey $.arrayProp[index] value + +# example +> JSON.SET person $.hobbies '["music", "cricket"]' +> JSON.SET person $.hobbies[1] '"dance"' + +#------------ +# syntax : remove nested array item by index +> JSON.ARRPOP objKey $.arrayProp index + +# example +> JSON.ARRPOP person $.hobbies 1 +``` + +More details can be found in the [Redis Stack docs](https://redis.io/docs/stack/json/) + +--- + +Redis Stack enables a query and indexing engine for Redis, providing secondary indexing, full-text search and aggregations capabilities. + +- We have to create index on schema to be able to search on its data + +```shell +# syntax +> FT.CREATE {index_name} ON JSON PREFIX {count} {prefix} SCHEMA {json_path} AS {attribute} {type} +# NOTE: attribute = logical name, json_path = JSONPath expressions + +# example +> FT.CREATE userIdx ON JSON PREFIX 1 users: SCHEMA $.user.name AS name TEXT $.user.hobbies AS hobbies TAG $.user.age as age NUMERIC +# NOTE: You can search by any attribute mentioned in the above index for keys that start with users: (e.g. users:1). +``` + +- More details on Indexing JSON can be found [here](https://redis.io/docs/stack/search/indexing_json/) + +Once index is created, any pre-existing/ new/ modified JSON document is automatically indexed. + +```json +//sample json document +{ + "user": { + "name": "John Smith", + "hobbies": "foo,bar", + "age": 23 + } +} +``` + +```shell +# adding JSON document +> JSON.SET myDoc $ '{"user":{"name":"John Smith","hobbies":"foo,bar","age":23}}' +``` + +- Search + +```shell +# search all user documents with name 'John' +> FT.SEARCH userIdx '@name:(John)' +1) (integer) 1 +2) "myDoc" +3) 1) "$" + 2) {"user":{"name":"John Smith","hobbies":"foo,bar","age":23}}" +``` + +- Search & project required fields + +```shell +# search documents with name 'John' & project only age field +> FT.SEARCH userIdx '@name:(John)' RETURN 1 $.user.age +1) (integer) 1 +2) "myDoc" +3) 1) "$.user.age" + 2) "23" +``` + +```shell +# project multiple fields +> FT.SEARCH userIdx '@name:(John)' RETURN 2 $.user.age $.user.name +1) (integer) 1 +2) "myDoc" +3) 1) "$.user.age" + 2) "23" + 3) "$.user.name" + 4) "John Smith" + +#------------ +# project with alias name +> FT.SEARCH userIdx '@name:(John)' RETURN 3 $.user.age AS userAge + +1) (integer) 1 +2) "myDoc" +3) 1) "userAge" + 2) "23" +#------------ + +# multi field query +> FT.SEARCH userIdx '@name:(John) @hobbies:{foo | me} @age:[20 30]' +1) (integer) 1 +2) "myDoc" +3) 1) "$" + 2) {"user":{"name":"John Smith","hobbies":"foo,bar","age":23}}" +``` + +More details on [query syntax](https://redis.io/docs/stack/search/reference/query_syntax/) + +- Drop index + +```shell +> FT.DROPINDEX userIdx +``` + +### Useful Resources + +1. [Redis and JSON explained (Revisited in 2022)](https://www.youtube.com/watch?v=I-ohlZXXaxs) video +1. [Searching with Redis Stack](https://redis.io/docs/stack/search/) +1. [Redis University 204, Storing, Querying, and Indexing JSON at Speed](https://university.redis.com/courses/ru204/) diff --git a/docs/howtos/quick-start/csharp/_csharp-basic-querying.mdx b/docs/howtos/quick-start/csharp/_csharp-basic-querying.mdx new file mode 100644 index 00000000000..59d6d57644e --- /dev/null +++ b/docs/howtos/quick-start/csharp/_csharp-basic-querying.mdx @@ -0,0 +1,78 @@ +The .NET Community has built many [client libraries](https://redis.io/clients#c-sharp) to help handle requests to Redis Server. In this guide, we'll mostly be concerned with using the [StackExchange.Redis](https://github.com/StackExchange/StackExchange.Redis) client library. As the name implies the StackExchange client is developed by StackExchange for use on popular websites like [StackOverflow](https://stackoverflow.com/). + +```shell +# install redis in the project +dotnet add package StackExchange.Redis +``` + +```csharp +// Impport the required namespace +using StackExchange.Redis; + +// Initialize the connection +static readonly ConnectionMultiplexer _redis = ConnectionMultiplexer.Connect("localhost:6379"); +``` + +```csharp +var redis = _redis.GetDatabase(); + +// Check specific keys +var server = _redis.GetServer(_redis.GetEndPoints()[0]); +server.Keys(pattern: "*"); + +//------------ +// Check number of keys in database +server.DatabaseSize(); + +//------------ +// set key value +redis.StringSet("key", "value"); +redis.StringSet("key", "value", expiry: TimeSpan.FromSeconds(10), when: When.NotExists); + +//------------ +// get value by key +var value = redis.StringGet("key"); + +//------------ +// syntax : delete keys +redis.KeyDelete("key"); +redis.KeyDelete(new RedisKey[] { "key1", "key2", "key3"}); + +//------------ +// Check if key exists +redis.KeyExists("key"); + +//------------ +// set expiry to key +redis.KeyExpire("key", DateTime.Now.AddSeconds(30)); + +//------------ +// remove expiry from key +redis.KeyPersist("key"); + + +//------------ +// find (remaining) time to live of a key +redis.KeyTimeToLive("key"); + + +//------------ +// increment a number +redis.StringIncrement("key"); + + +//------------ +// decrement a number +redis.StringDecrement("key"); + + +//------------ +// use the method below to execute commands directly +redis.Execute("SET", "key", "value"); +``` + +### Additional Resources + +1. [StackExchange.Redis Github repo](https://github.com/StackExchange/StackExchange.Redis) +1. [Detailed .NET Guide](/develop/dotnet) +1. C# apps on the [Redis Launchpad](https://launchpad.redis.com/) diff --git a/docs/howtos/quick-start/csharp/_csharp-secondary-indexing.mdx b/docs/howtos/quick-start/csharp/_csharp-secondary-indexing.mdx new file mode 100644 index 00000000000..2edd1b7faf3 --- /dev/null +++ b/docs/howtos/quick-start/csharp/_csharp-secondary-indexing.mdx @@ -0,0 +1,159 @@ +The following example uses [Redis OM .NET](https://github.com/redis/redis-om-dotnet), but you can also use any other supported [client](https://redis.io/resources/clients/). The examples also use the synchronous methods of Redis OM .NET, but it is recommended that you use the asynchronous methods in a production application. + +```shell +# install Redis OM in the project +dotnet add package Redis.OM +``` + +- Create a JSON model + +```csharp title="Model.cs" +using Redis.OM.Modeling; + +namespace RedisApp.Model +{ + [Document(StorageType = StorageType.Json, Prefixes = new[] { "Person" })] + public class Person + { + [RedisIdField] + public string Id { get; set; } + + [Indexed] + public string FirstName { get; set; } + + [Indexed] + public string? LastName { get; set; } + + [Indexed(Sortable = true)] + public int Age { get; set; } + + [Indexed] + public bool Verified { get; set; } + + [Indexed] + public GeoLoc Location { get; set; } + + [Indexed] + public string[] Skills { get; set; } = Array.Empty(); + + [Searchable] + public string PersonalStatement { get; set; } + } +} +``` + +- Setup your main program + +```csharp title="Program.cs" +using System; +using System.Linq; +using Redis.OM; +using Redis.OM.Modeling; +using RedisApp.Model; + +namespace RedisApp +{ + class Program + { + static void Main(string[] args) + { + + } + } +} +``` + +The rest of the code will be inside of `Main`. + +- Create your provider used to call into Redis + +```csharp +var provider = new RedisConnectionProvider("redis://localhost:6379"); +``` + +- Conditionally create index necessary for searching + +```csharp +var info = provider.Connection.Execute("FT._LIST").ToArray().Select(x => x.ToString()); + +if (info.All(x => x != "person-idx")) +{ + provider.Connection.CreateIndex(typeof(Person)); +} +``` + +- Initialize your collection + +```csharp +var people = provider.RedisCollection(); +``` + +- Insert example + +```csharp +var person = new Person +{ + FirstName = "Rupert", + LastName = "Holmes", + Age = 75, + Verified = false, + Location = new GeoLoc { Longitude = 45.678, Latitude = 45.678 }, + Skills = new string[] { "singing", "songwriting", "playwriting" }, + PersonalStatement = "I like piña coladas and walks in the rain" +}; + +var id = people.Insert(person); +``` + +- Read example + +```csharp +person = people.FindById(id); +``` + +- Update example + +```csharp +person = people.FindById(id); +person.FirstName = "Alex"; +person.LastName = null; +people.Update(person); +``` + +- Update location example + +```csharp +person = people.FindById(id); +person.Location = new GeoLoc { Longitude = 44.678, Latitude = 44.678 }; +people.Update(person); +``` + +- Search examples + +```csharp +// Multiple AND conditions example +people.Where(p => p.Age > 21 && p.FirstName == "Alex").ToList(); + +// Multiple OR conditions example +people.Where(p => p.Age > 75 || p.FirstName == "Alex").ToList(); + +// Multiple AND + OR conditions example +people.Where(p => + (p.Age > 21 && p.FirstName == "Alex") && + (p.Age > 75 || p.FirstName == "Alex") +).ToList(); +``` + +- Delete example + +```csharp +person = people.FindById(id); +people.Delete(person); +``` + +### Useful Resources + +1. [Github repo](https://github.com/redis/redis-om-dotnet) +1. [Getting started docs](https://redis.io/docs/stack/get-started/tutorials/stack-dotnet/) +1. [Getting started video](https://www.youtube.com/watch?v=ZHPXKrJCYNA) + - [Source code](https://github.com/redis-developer/redis-om-dotnet-skeleton-app) diff --git a/docs/howtos/quick-start/images/redis-bloom.svg b/docs/howtos/quick-start/images/redis-bloom.svg new file mode 100644 index 00000000000..077ce95aa9f --- /dev/null +++ b/docs/howtos/quick-start/images/redis-bloom.svg @@ -0,0 +1,14 @@ + + + + + + + + + + + + + + diff --git a/docs/howtos/quick-start/images/redis-graph.svg b/docs/howtos/quick-start/images/redis-graph.svg new file mode 100644 index 00000000000..770a8b62cd5 --- /dev/null +++ b/docs/howtos/quick-start/images/redis-graph.svg @@ -0,0 +1,14 @@ + + + + + + + + + + + + + + diff --git a/docs/howtos/quick-start/images/redis-insight.svg b/docs/howtos/quick-start/images/redis-insight.svg new file mode 100644 index 00000000000..cdacc650183 --- /dev/null +++ b/docs/howtos/quick-start/images/redis-insight.svg @@ -0,0 +1,168 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/docs/howtos/quick-start/images/redis-timeseries.svg b/docs/howtos/quick-start/images/redis-timeseries.svg new file mode 100644 index 00000000000..093c74125fd --- /dev/null +++ b/docs/howtos/quick-start/images/redis-timeseries.svg @@ -0,0 +1,14 @@ + + + + + + + + + + + + + + diff --git a/docs/howtos/quick-start/index-quick-start.mdx b/docs/howtos/quick-start/index-quick-start.mdx new file mode 100644 index 00000000000..205384a270a --- /dev/null +++ b/docs/howtos/quick-start/index-quick-start.mdx @@ -0,0 +1,355 @@ +--- +id: index-quick-start +title: Getting Started +sidebar_label: Getting Started +slug: /howtos/quick-start +authors: [prasan,will] +--- + +import Tabs from '@theme/Tabs'; +import TabItem from '@theme/TabItem'; +import useBaseUrl from '@docusaurus/useBaseUrl'; +import Authors from '@site/src/theme/Authors'; + +import DockerSetup from './setup/_docker-setup.mdx'; +import LinuxSetup from './setup/_linux-setup.mdx'; +import MacOsSetup from './setup/_macos-setup.mdx'; +import WindowsSetup from './setup/_windows-setup.mdx'; + +import CliBasicQuerying from './cli/_cli-basic-querying.mdx'; +import CliSecondaryIndexing from './cli/_cli-secondary-indexing.mdx'; + +import NodeBasicQuerying from './node/_node-basic-querying.mdx'; +import NodeSecondaryIndexing from './node/_node-secondary-indexing.mdx'; + +import PythonBasicQuerying from './python/_python-basic-querying.mdx'; +import PythonSecondaryIndexing from './python/_python-secondary-indexing.mdx'; + +import JavaBasicQuerying from './java/_java-basic-querying.mdx'; +import JavaSecondaryIndexing from './java/_java-secondary-indexing.mdx'; + +import CSharpBasicQuerying from './csharp/_csharp-basic-querying.mdx'; +import CSharpSecondaryIndexing from './csharp/_csharp-secondary-indexing.mdx'; + + + +
+ +Welcome to the getting started for the official Redis Developer Hub! + +If you are new to Redis, we recommend starting with [Redis University (RU101)](https://university.redis.com/courses/ru101/). RU101 is an introductory course, perfect for developers new to Redis. In this course, you’ll learn about the data structures in Redis, and you’ll see how to practically apply them in the real world. + +If you have questions related to Redis, come join the [Redis Discord server](https://discord.gg/redis). Our Discord server is a place where you can learn, share, and collaborate about anything and everything Redis. Connect with users from the community and Redis University. Get your questions answered and learn cool new tips and tricks! Watch for notifications of the latest content from Redis and the community. And share your own content with the community. + +## Setup Redis + +There are essentially two ways you can use Redis: + +- **Cloud Redis**: A hosted and serverless Redis database-as-a-service (DBaaS). The fastest way to deploy Redis Enterprise via Amazon AWS, Google Cloud Platform, or Microsoft Azure. + - [Getting Started](/create/rediscloud) + - [Videos](https://www.youtube.com/playlist?list=PL83Wfqi-zYZG6uGxBagsbqjpsi2XBEj1K) + - [Free Sign-up](https://redis.com/try-free) +- **On-prem/local Redis**: Self-managed Redis using your own server and any operating system (Mac OS, Windows, or Linux). + +If you choose to use local Redis we strongly recommend using Docker. If you choose not to use Docker, use the following instructions based on your OS: + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +## Basic Querying with Redis + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +## Secondary Indexing and Searching with Redis + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +## Sync Redis with Other Databases + +RedisGears adds a dynamic execution framework for your Redis data that enables you to write and execute functions that implement data flows in Redis. + +Consider following example to sync data with MongoDB. + +- Create the below python file and update the MongoDB connection details, database, collection and primary key name to be synced + +```python title="write-behind.py" +# Gears Recipe for a single write behind + +# import redis gears & mongo db libs +from rgsync import RGJSONWriteBehind, RGJSONWriteThrough +from rgsync.Connectors import MongoConnector, MongoConnection + +# change mongodb connection +connection = MongoConnection("", "", "", "", "ENV_MONGODB_CONNECTION_URL") + +# change MongoDB database +db = 'ENV_DB_NAME' + +# change MongoDB collection & it's primary key +collection1Connector = MongoConnector(connection, db, 'ENV_COLLECTION1_NAME', 'ENV_COLLECTION1_PRIMARY_KEY') + +# change redis keys with prefix that must be synced with mongodb collection +RGJSONWriteBehind(GB, keysPrefix='ENV_COLLECTION1_PREFIX_KEY', + connector=collection1Connector, name='Collection1WriteBehind', + version='99.99.99') +``` + +```env +ENV_MONGODB_CONNECTION_URL=mongodb://usrAdmin:passwordAdmin@10.10.20.2:27017/dbSpeedMernDemo?authSource=admin +ENV_DB_NAME=dbSpeedMernDemo +ENV_COLLECTION1_NAME=movies +ENV_COLLECTION1_PRIMARY_KEY=movieId +ENV_COLLECTION1_PREFIX_KEY=movie +``` + +The code above demonstrates how you would sync a "movies" collection in MongoDB with Redis using the "movie" key prefix. + +To get this working you first need to load the python file into redis-server: + +```shell +$ redis-cli rg.pyexecute "`cat write-behind.py`" REQUIREMENTS rgsync pymongo==3.12.0 +``` + +Now, insert a JSON item in to Redis starting with the prefix specified in the python file (i.e. "movie"): + +```shell +# redis-cli command +> JSON.SET movie:123 $ '{"movieId":123,"name":"RRR","isActive": true}' +``` + +Now, verify whether the JSON is inserted into MongoDB. + +### Additional Resources For Syncing with Redis and Other Databases + +1. [Redis gear sync with MongoDB](https://github.com/RedisGears/rgsync/tree/master/examples/mongo) +1. [RG.PYEXECUTE](https://oss.redis.com/redisgears/commands.html#rgpyexecute) +1. [rgsync](https://github.com/RedisGears/rgsync#running-the-recipe) +1. [gears-cli](https://github.com/RedisGears/gears-cli) +1. [RedisGears dynamic script](/howtos/redisgears) + +## Probabilistic Data and Queries with Redis + +Redis Stack supports probabilistic datatypes and queries. Below you will find a stock leaderboard example: + +```shell +# Reserve a new leaderboard filter +> TOPK.RESERVE trending-stocks 12 50 4 0.9 +"OK" + +# Add a new entries to the leaderboard +> TOPK.ADD trending-stocks AAPL AMD MSFT INTC GOOG FB NFLX GME AMC TSLA +1) "null" ... + +# Get the leaderboard +> TOPK.LIST trending-stocks +1) "AAPL" +2) "AMD" +2) "MSFT" ... + +# Get information about the leaderboard +> TOPK.INFO trending-stocks +1) "k" +2) "12" +3) "width" +4) "50" +5) "depth" +6) "4" +7) "decay" +8) "0.90000000000000002" +``` + +More details in [docs](https://redis.io/docs/stack/bloom/) + +## Graph Data and Queries with Redis + +Redis Stack is a NoSQL graph database that translates Cypher queries to matrix operations executed over a GraphBLAS engine. It's useful for social graph operation, fraud detection, and real-time recommendation engines. Below you will find an org chart graph example: + +```shell +# Create any graph, for example an Org Chart +> GRAPH.QUERY OrgChart "CREATE (:Employee {name:'Doug'}), (:Employee {name:'Dani'})-[:REPORTS_TO]->(:Employee {name:'Doug'}), (:Employee {name:'Otto'})-[:REPORTS_TO]->(:Employee {name:'Doug'})" +1) 1) "Labels added: 1" + 2) "Nodes created: 5" + 3) "Properties set: 5" + 4) "Relationships created: 2" + 5) "Cached execution: 0" + 6) "Query internal execution time: 0.324600 milliseconds" + +# Get a list of employees and who they report to +> GRAPH.QUERY OrgChart "MATCH (e:Employee)-[:REPORTS_TO]->(m:Employee) RETURN e.name, m.name" +1) 1) "e.name" + 2) "m.name" +2) 1) 1) "Dani" + 2) "Doug" + 2) 1) "Otto" + 2) "Doug" +3) 1) "Cached execution: 0" + 2) "Query internal execution time: 0.288619 milliseconds" + +# Get a count of how many reports Doug has +> GRAPH.QUERY OrgChart "MATCH (e:Employee)-[:REPORTS_TO]->(m:Employee {name: 'Doug'}) RETURN COUNT(e.name)" +1) 1) "COUNT(e.name)" +2) 1) 1) "2" +3) 1) "Cached execution: 0" + 2) "Query internal execution time: 0.340888 milliseconds" +``` + +More details in [docs](https://redis.io/docs/stack/graph/) + +## TimeSeries Data and Queries with Redis + +Redis Stack supports time-series use cases such as IoT, stock prices, and telemetry. You can ingest and query millions of samples and events at the speed of Redis. You can also use a variety of queries for visualization and monitoring with built-in connectors to popular tools like Grafana, Prometheus, and Telegraf. + +The following example demonstrates how you might store temperature sensor readings in Redis Stack: + +```shell +# Create new time-series, for example temperature readings +> TS.CREATE temperature:raw DUPLICATE_POLICY LAST +"OK" + +# Create a bucket for monthly aggregation +> TS.CREATE temperature:monthly DUPLICATE_POLICY LAST +"OK" + +# Automatically aggregate based on time-weighted average +> TS.CREATERULE temperature:raw temperature:monthly AGGREGATION twa 2629800000 +"OK" + +# Add data to the raw time-series +> TS.MADD temperature:raw 1621666800000 52 ... +1) "1621666800000" ... + +# View the monthly time-weighted average temperatures +> TS.RANGE temperature:monthly 0 + +1) 1) "1621666800000" + 2) "52" ... + +# Delete compaction rule +> TS.DELETERULE temperature:raw temperature:monthly +"OK" + +# Delete partial time-series +> TS.DEL temperature:raw 0 1621666800000 +(integer) 1 +``` + +More details in [docs](https://redis.io/docs/stack/timeseries/) + +## Additional Resources + +- Join the [community](/community/) +- [RedisInsight](https://redis.com/redis-enterprise/redis-insight/) + +
diff --git a/docs/howtos/quick-start/java/_java-basic-querying.mdx b/docs/howtos/quick-start/java/_java-basic-querying.mdx new file mode 100644 index 00000000000..0ec8b083d10 --- /dev/null +++ b/docs/howtos/quick-start/java/_java-basic-querying.mdx @@ -0,0 +1 @@ +TODO: Examples coming soon diff --git a/docs/howtos/quick-start/java/_java-secondary-indexing.mdx b/docs/howtos/quick-start/java/_java-secondary-indexing.mdx new file mode 100644 index 00000000000..0ec8b083d10 --- /dev/null +++ b/docs/howtos/quick-start/java/_java-secondary-indexing.mdx @@ -0,0 +1 @@ +TODO: Examples coming soon diff --git a/docs/howtos/quick-start/node/_node-basic-querying.mdx b/docs/howtos/quick-start/node/_node-basic-querying.mdx new file mode 100644 index 00000000000..e1c2b783e94 --- /dev/null +++ b/docs/howtos/quick-start/node/_node-basic-querying.mdx @@ -0,0 +1,90 @@ +```shell +# install redis in the project +npm install redis --save +``` + +```js +//create client & connect to redis + +import { createClient } from 'redis'; + +const client = createClient({ + //redis[s]://[[username][:password]@][host][:port][/db-number] + url: 'redis://alice:foobared@awesome.redis.server:6380', +}); + +client.on('error', (err) => console.log('Redis Client Error', err)); + +await client.connect(); +``` + +```js +// Check specific keys +const pattern = '*'; +await client.keys(pattern); + +//------------ +// Check number of keys in database +await client.dbsize(); + +//------------ +// set key value +await client.set('key', 'value'); +await client.set('key', 'value', { + EX: 10, + NX: true, +}); + +//------------ +// get value by key +const value = await client.get('key'); + +//------------ +//syntax : delete keys +await client.del('key'); +const keyArr = ['key1', 'key2', 'key3']; +await client.del(...keyArr); + +//------------ +// Check if key exists +await client.exists('key'); + +//------------ +// set expiry to key +const expireInSeconds = 30; +await client.expire('key', expireInSeconds); + +//------------ +// remove expiry from key +await client.persist('key'); + +//------------ +// find (remaining) time to live of a key +await client.ttl('key'); + +//------------ +// increment a number +await client.incr('key'); + +//------------ +// decrement a number +await client.decr('key'); + +//------------ +// use the method below to execute commands directly +await client.sendCommand(['SET', 'key', 'value']); +``` + +```js +//graceful disconnecting +await client.quit(); + +//forceful disconnecting +await client.disconnect(); +``` + +### Additional Resources + +1. [node-redis Github repo](https://github.com/redis/node-redis) +1. [Node.js Redis Crash Course](/develop/node/node-crash-course) +1. JavaScript/NodeJS apps on the [Redis Launchpad](https://launchpad.redis.com/) diff --git a/docs/howtos/quick-start/node/_node-secondary-indexing.mdx b/docs/howtos/quick-start/node/_node-secondary-indexing.mdx new file mode 100644 index 00000000000..5732dc9cfbb --- /dev/null +++ b/docs/howtos/quick-start/node/_node-secondary-indexing.mdx @@ -0,0 +1,149 @@ + +The following example uses [Redis OM Node](https://github.com/redis/redis-om-node), but you can also use [Node Redis](https://github.com/redis/node-redis), [IO Redis](https://github.com/luin/ioredis), or any other supported [client](https://redis.io/resources/clients/) + +```shell +# install RedisOM in the project +npm install redis-om --save +``` + +- create RedisOM Client & connect to redis + +```js +//client.js file + +import { Client } from 'redis-om'; + +// pulls the Redis URL from .env +const url = process.env.REDIS_URL; + +const client = new Client(); +await client.open(url); + +export default client; +``` + +- Create Entity, Schema & Repository + +```js +//person.js file + +import { Entity, Schema } from 'redis-om'; +import client from './client.js'; + +class Person extends Entity {} + +const personSchema = new Schema(Person, { + firstName: { type: 'string' }, + lastName: { type: 'string' }, + age: { type: 'number' }, + verified: { type: 'boolean' }, + location: { type: 'point' }, + locationUpdated: { type: 'date' }, + skills: { type: 'string[]' }, + personalStatement: { type: 'text' }, +}); + +export const personRepository = client.fetchRepository(personSchema); + +//creating index to make person schema searchable +await personRepository.createIndex(); +``` + +```js +import { Router } from 'express'; +import { personRepository } from 'person.js'; +``` + +- Insert example + +```js +const input = { + firstName: 'Rupert', + lastName: 'Holmes', + age: 75, + verified: false, + location: { + longitude: 45.678, + latitude: 45.678, + }, + locationUpdated: '2022-03-01T12:34:56.123Z', + skills: ['singing', 'songwriting', 'playwriting'], + personalStatement: 'I like piña coladas and walks in the rain', +}; +let person = await personRepository.createAndSave(input); +``` + +- Read example + +```js +const id = person.entityId; +person = await personRepository.fetch(id); +``` + +- Update example + +```js +person = await personRepository.fetch(id); + +person.firstName = 'Alex'; + +//null to remove that field +person.lastName = null; + +await personRepository.save(person); +``` + +- Update location sample + +```js +const longitude = 45.678; +const latitude = 45.678; +const locationUpdated = new Date(); + +const person = await personRepository.fetch(id); +person.location = { longitude, latitude }; +person.locationUpdated = locationUpdated; +await personRepository.save(person); +``` + +- Search examples + +```js +// Get all person records +const queryBuilder = personRepository.search(); +const people = await queryBuilder.return.all(); + +// Multiple AND conditions example +const queryBuilder = personRepository + .search() + .where('verified') + .eq(true) // == + .and('age') + .gte(21) // >= + .and('lastName') + .eq(lastName); +//console.log(queryBuilder.query); +const people = await queryBuilder.return.all(); + +// Multiple OR conditions example +const queryBuilder = personRepository + .search() + .where('verified') + .eq(true) + .or((search) => search.where('age').gte(21).and('lastName').eq(lastName)) + .sortAscending('age'); +const people = await queryBuilder.return.all(); +``` + +- Delete example + +```js +await personRepository.remove(id); +``` + +### Useful Resources + +1. [Github repo](https://github.com/redis/redis-om-node) +1. [Getting started docs](https://redis.io/docs/stack/get-started/tutorials/stack-node/) +1. [Getting started video](https://www.youtube.com/watch?v=KUfufrwpBkM) + - [Source code](https://github.com/redis-developer/express-redis-om-workshop) diff --git a/docs/howtos/quick-start/python/_python-basic-querying.mdx b/docs/howtos/quick-start/python/_python-basic-querying.mdx new file mode 100644 index 00000000000..c3fae8b6d11 --- /dev/null +++ b/docs/howtos/quick-start/python/_python-basic-querying.mdx @@ -0,0 +1,69 @@ +```shell +# install redis in the project +pip install redis +``` + +```python +import redis + +pool = redis.ConnectionPool(host='localhost', port=6379, db=0) +r = redis.Redis(connection_pool=pool) + +# Check specific keys +r.keys('*') + +#------------ +# Check number of keys in database +r.dbsize() + +#------------ +# set key value +r.set('key', 'value') +r.set('key', 'value', ex=10, nx=True) + +#------------ +# get value by key +value = r.get('key') + +#------------ +# syntax : delete keys +r.delete('key') +r.delete('key1', 'key2', 'key3') + +#------------ +# Check if key exists +r.exists('key') + +#------------ +# set expiry to key +expireInSeconds = 30 +r.expire('key', expireInSeconds) + +#------------ +# remove expiry from key +r.persist('key') + +#------------ +# find (remaining) time to live of a key +r.ttl('key') + +#------------ +# increment a number +r.incr('key') + +#------------ +# decrement a number +r.decr('key') + +#------------ +# use the method below to execute commands directly +r.execute_command('SET', 'key', 'value') +``` + +- For more information, checkout the + +### Additional Resources + +1. [redis-py Github repo](https://github.com/redis/redis-py) +1. [Using Redis with Python and FastAPI](/develop/python/fastapi) +1. Python apps on the [Redis Launchpad](https://launchpad.redis.com/) diff --git a/docs/howtos/quick-start/python/_python-secondary-indexing.mdx b/docs/howtos/quick-start/python/_python-secondary-indexing.mdx new file mode 100644 index 00000000000..b284c131461 --- /dev/null +++ b/docs/howtos/quick-start/python/_python-secondary-indexing.mdx @@ -0,0 +1,129 @@ +The following example uses [Redis OM Python](https://github.com/redis/redis-om-python), but you can also use [redis-py](https://github.com/redis/redis-py) or any other supported [client](https://redis.io/resources/clients/) + +```shell +# install Redis OM in the project +pip install redis-om +``` + +Create a JSON model + +```python +import datetime +import dateutil.parser +from typing import List, Optional + +from redis_om import ( + EmbeddedJsonModel, + JsonModel, + Field, + Migrator, +) + +class Point(EmbeddedJsonModel): + longitude: float = Field(index=True) + latitude: float = Field(index=True) + + +class Person(JsonModel): + first_name: str = Field(index=True) + last_name: Optional[str] = Field(index=True) + age: int = Field(index=True) + verified: bool + location: Point + location_updated: datetime.datetime = Field(index=True) + skills: List[str] + personal_statement: str = Field(index=True, full_text_search=True) + + +# Before running queries, we need to run migrations to set up the +# indexes that Redis OM will use. You can also use the `migrate` +# CLI tool for this! +Migrator().run() +``` + +- Insert example + +```python +person = Person(**{ + "first_name": "Rupert", + "last_name": "Holmes", + "age": 75, + "verified": False, + "location": { + "longitude": 45.678, + "latitude": 45.678 + }, + "location_updated": dateutil.parser.isoparse("2022-03-01T12:34:56.123Z"), + "skills": ["singing", "songwriting", "playwriting"], + "personal_statement": "I like piña coladas and walks in the rain" +}).save() +``` + +- Read example + +```python +id = person.pk +person = Person.get(id) +``` + +- Update example + +```python +person = Person.get(id) +person.first_name = "Alex" +person.last_name = None +person.save() +``` + +- Update embedded JSON example + +```python +person = Person.get(id) +person.location = Point(longitude=44.678, latitude=44.678) +person.location_updated = datetime.datetime.now() +person.save() +``` + +- Search examples + +```python +# Get all Person records + +all = Person.find().all() + +# Multiple AND conditions example + +people = Person.find( + (Person.age > 21) & + (Person.first_name == "Alex") +).all() + +# Multiple OR conditions example + +people = Person.find( + (Person.age > 75) | + (Person.first_name == "Alex") +).all() + +# Multiple AND + OR conditions example + +people = Person.find( + ((Person.age > 21) & + (Person.first_name == "Alex")) & + ((Person.age > 75) | + (Person.first_name == "Alex")) +).all() +``` + +- Delete example + +```python +Person.get(id).delete() +``` + +### Useful Resources + +1. [Github repo](https://github.com/redis/redis-om-python) +1. [Getting started docs](https://redis.io/docs/stack/get-started/tutorials/stack-python/) +1. [Getting started video](https://www.youtube.com/watch?v=PPT1FElAS84) + - [Source code](https://github.com/redis-developer/redis-om-python-flask-skeleton-app) diff --git a/docs/howtos/quick-start/setup/_docker-setup.mdx b/docs/howtos/quick-start/setup/_docker-setup.mdx new file mode 100644 index 00000000000..2cea742eb40 --- /dev/null +++ b/docs/howtos/quick-start/setup/_docker-setup.mdx @@ -0,0 +1,16 @@ + +The `docker run` command below exposes redis-server on port 6379 and RedisInsight on port 8001. You can use RedisInsight by pointing your browser to `http://localhost:8001`. + +```shell +# install +$ docker run -d --name redis-stack -p 6379:6379 -p 8001:8001 redis/redis-stack:latest +``` + +You can use `redis-cli` to connect to the server at `localhost:6379`. If you don’t have `redis-cli` installed locally, you can run it from the Docker container like below: + +```shell +# connect +$ docker exec -it redis-stack redis-cli +``` + +Detailed Docker instructions can be viewed [here](/create/docker/redis-on-docker) diff --git a/docs/howtos/quick-start/setup/_linux-setup.mdx b/docs/howtos/quick-start/setup/_linux-setup.mdx new file mode 100644 index 00000000000..19a8f4874e8 --- /dev/null +++ b/docs/howtos/quick-start/setup/_linux-setup.mdx @@ -0,0 +1,61 @@ + + +### Using APT with Ubuntu/Debian + +Works with Ubuntu 16.04, 18.04, or 20.04 and Debian 11 + +```shell +curl -fsSL https://packages.redis.io/gpg | sudo gpg --dearmor -o /usr/share/keyrings/redis-archive-keyring.gpg +echo "deb [signed-by=/usr/share/keyrings/redis-archive-keyring.gpg] https://packages.redis.io/deb $(lsb_release -cs) main" | sudo tee /etc/apt/sources.list.d/redis.list +sudo apt-get update +sudo apt-get install redis-stack-server +``` + +### From the official RPM Feed + +Works with RHEL7/CentOS7 or RHEL8/CentOS8 + +Create the file /etc/yum.repos.d/redis.repo with the following contents: + +``` +[Redis] +name=Redis +baseurl=http://packages.redis.io/rpm/rhel7 +enabled=1 +gpgcheck=1 +``` + +```shell +curl -fsSL https://packages.redis.io/gpg > /tmp/redis.key +sudo rpm --import /tmp/redis.key +sudo yum install epel-release +sudo yum install redis-stack-server +``` + +### With snap + +Download the [latest Redis Stack snap package](https://redis.io/download/#redis-stack-downloads). + +To install, run: + +```shell +$ sudo snap install --dangerous --classic +``` + +### With AppImage + +Download the [latest Redis Stack AppImage package](https://redis.io/download/#redis-stack-downloads). + +To enable the install, run: + +```shell +$ chmod a+x +``` + +To install run: + +```shell +$ ./ +``` + +Detailed Linux instructions can be viewed [here](/create/linux/) diff --git a/docs/howtos/quick-start/setup/_macos-setup.mdx b/docs/howtos/quick-start/setup/_macos-setup.mdx new file mode 100644 index 00000000000..38c0f405bce --- /dev/null +++ b/docs/howtos/quick-start/setup/_macos-setup.mdx @@ -0,0 +1,10 @@ +```shell +# install redis-stack +$ brew tap redis-stack/redis-stack +$ brew install --cask redis-stack + +# start redis-stack +$ redis-stack-server +``` + +Detailed MacOS instructions can be viewed [here](/create/homebrew/) diff --git a/docs/howtos/quick-start/setup/_windows-setup.mdx b/docs/howtos/quick-start/setup/_windows-setup.mdx new file mode 100644 index 00000000000..8ae4a7271f6 --- /dev/null +++ b/docs/howtos/quick-start/setup/_windows-setup.mdx @@ -0,0 +1,16 @@ + +Redis is not officially supported on Windows, so we recommend using Docker. + +Please follow the Docker instructions, or watch the following video that covers using Redis through WSL on Windows. + + +
+ +
diff --git a/docusaurus.config.js b/docusaurus.config.js index 48a596117fe..4d98ceca8eb 100644 --- a/docusaurus.config.js +++ b/docusaurus.config.js @@ -56,6 +56,12 @@ module.exports = { title: 'Developer Growth Manager at Redis', image: 'profile_pic_will_johnston.jpg', }, + prasan: { + name: 'Prasan Kumar', + link: 'https://www.linkedin.com/in/prasankumar93/', + title: 'Technical Solutions Developer at Redis', + image: 'profile_pic_prasan_kumar.jpg', + }, ryan: { name: 'Ryan Gray', link: 'https://www.linkedin.com/in/ryan-t-gray/', @@ -212,7 +218,7 @@ module.exports = { position: 'right', }, { - to: '/create/rediscloud', + to: '/howtos/quick-start', activeBasePath: 'docs', label: 'Get started', position: 'right', @@ -306,14 +312,14 @@ module.exports = { // Useful if you want to support a single color mode disableSwitch: false, }, - // announcementBar: { - // id: 'redisconf20201cfp', // Any value that will identify this message. - // content: - // 'RedisDays Available Now On-Demand.', - // backgroundColor: '#fff', // Defaults to `#fff`. - // textColor: '#000', // Defaults to `#000`. - // isCloseable: true, // Defaults to `true`. - // }, + // announcementBar: { + // id: 'redisconf20201cfp', // Any value that will identify this message. + // content: + // 'RedisDays Available Now On-Demand.', + // backgroundColor: '#fff', // Defaults to `#fff`. + // textColor: '#000', // Defaults to `#000`. + // isCloseable: true, // Defaults to `true`. + // }, }), presets: [ [ diff --git a/sidebars.js b/sidebars.js index 6445fa3e8fe..84dc48f7789 100644 --- a/sidebars.js +++ b/sidebars.js @@ -5,6 +5,11 @@ module.exports = { label: 'Home', href: '/', }, + { + type: 'doc', + label: 'Quick Start', + id: 'howtos/quick-start/index-quick-start', + }, { type: 'category', label: 'Create', @@ -71,6 +76,7 @@ module.exports = { ], }, 'create/homebrew/index-homebrew', + 'create/linux/index-linux', 'create/windows/index-windows', 'create/from-source/index-from-source', 'create/jenkins/index-jenkins', diff --git a/static/img/profile_pic_prasan_kumar.jpg b/static/img/profile_pic_prasan_kumar.jpg new file mode 100644 index 00000000000..b1258e026d4 Binary files /dev/null and b/static/img/profile_pic_prasan_kumar.jpg differ