Skip to content

query, resp: Add dynamic list examples #33

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 3 commits into from
Sep 12, 2024
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -2,6 +2,13 @@

All changes in this project will be noted in this file.

## 0.8.11

### Additions

- Added `QList` and `RList` for using dynamic lists
- Allow using references for custom types in `query!` macro

## 0.8.10

### Fixes
2 changes: 1 addition & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
@@ -9,7 +9,7 @@ license = "Apache-2.0"
name = "skytable"
readme = "README.md"
repository = "https://github.com/skytable/client-rust"
version = "0.8.10"
version = "0.8.11"

# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
[dependencies]
4 changes: 3 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
@@ -2,7 +2,9 @@

## Introduction

This library is the official client for the free and open-source NoSQL database [Skytable](https://github.com/skytable/skytable). First, go ahead and install Skytable by following the instructions [here](https://docs.skytable.io/getting-started). This library supports all Skytable versions that work with the [Skyhash 2 Protocol](https://docs.skytable.io/protocol/overview). This version of the library was tested with the latest Skytable release (release [0.8.3](https://github.com/skytable/skytable/releases/v0.8.3)). [Read more about supported versions here](#version-support).
This library is the official client for the free and open-source NoSQL database [Skytable](https://github.com/skytable/skytable). First, go ahead and install Skytable by following the instructions [here](https://docs.skytable.io/getting-started). This library supports all Skytable versions that work with the [Skyhash 2 Protocol](https://docs.skytable.io/protocol/overview). This version of the library was tested with the latest Skytable release (release [0.8.4](https://github.com/skytable/skytable/releases/v0.8.4)). [Read more about supported versions here](#version-support).

**📁 You can [find some usage examples in this folder here](/examples)**.

## Definitive example

80 changes: 80 additions & 0 deletions examples/dynamic_lists_advanced.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
/*
assume the model is created using:

> create space myapp
> create model myapp.mydb(username: string, password: string, data: [string])

-------------

This is an example just like `dynamic_lists_simple.rs` but using a struct instead
*/

use skytable::{
query::{QList, SQParam},
response::{FromResponse, RList},
Config,
};

#[derive(Debug, PartialEq)]
struct User {
username: String,
password: String,
data: Vec<String>,
}

impl User {
fn new(username: String, password: String, data: Vec<String>) -> Self {
Self {
username,
password,
data,
}
}
}

impl SQParam for User {
fn append_param(&self, q: &mut Vec<u8>) -> usize {
self.username.append_param(q)
+ self.password.append_param(q)
+ QList::new(&self.data).append_param(q)
}
}

impl FromResponse for User {
fn from_response(resp: skytable::response::Response) -> skytable::ClientResult<Self> {
let (username, password, data) = resp.parse::<(_, _, RList<String>)>()?;
Ok(Self::new(username, password, data.into_values()))
}
}

fn get_data_from_api() -> User {
User {
username: "sayan".to_owned(),
password: "ulw06afuMCAg+1gh2lh1Y9xTIr/dUv2vqGLeZ39cVrE=".to_owned(),
data: vec![
"stuff".to_owned(),
"from".to_owned(),
"the".to_owned(),
"api".to_owned(),
],
}
}

fn main() {
let mut db = Config::new_default("root", "password12345678")
.connect()
.unwrap();
let data_from_api = get_data_from_api();
db.query_parse::<()>(&skytable::query!(
"insert into myapp.mydb { username: ?, password: ?, data: ? }",
&data_from_api
))
.unwrap();
let fetched_user: User = db
.query_parse(&skytable::query!(
"select * from myapp.mydb where username = ?",
"sayan"
))
.unwrap();
assert_eq!(data_from_api, fetched_user);
}
41 changes: 41 additions & 0 deletions examples/dynamic_lists_simple.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
/*
assume the model is created using:

> create space myapp
> create model myapp.mydb(username: string, password: string, data: [string])
*/

use skytable::{query::QList, response::RList, Config};

fn get_list_data_from_api() -> Vec<String> {
vec![
"stuff".to_owned(),
"from".to_owned(),
"the".to_owned(),
"api".to_owned(),
]
}

fn main() {
let mut db = Config::new_default("root", "password12345678")
.connect()
.unwrap();
let data_from_api = get_list_data_from_api();
let q = skytable::query!(
"insert into myapp.mydb { username: ?, password: ?, data: ? }",
"sayan",
"ulw06afuMCAg+1gh2lh1Y9xTIr/dUv2vqGLeZ39cVrE=",
QList::new(&data_from_api)
);
db.query_parse::<()>(&q).unwrap(); // expect this data to be inserted correctly
// now fetch this data
let (username, password, data): (String, String, RList<String>) = db
.query_parse(&skytable::query!(
"select * from myapp.mydb where username = ?",
"sayan"
))
.unwrap();
assert_eq!(username, "sayan");
assert_eq!(password, "ulw06afuMCAg+1gh2lh1Y9xTIr/dUv2vqGLeZ39cVrE=");
assert_eq!(data.into_values(), data_from_api);
}
4 changes: 3 additions & 1 deletion src/lib.rs
Original file line number Diff line number Diff line change
@@ -21,6 +21,8 @@
//! The client-driver is distributed under the liberal [Apache-2.0 License](https://www.apache.org/licenses/LICENSE-2.0) and hence
//! you can use it in your applications without any licensing issues.
//!
//! **📁 You can [find some usage examples in this folder here](https://github.com/skytable/client-rust/tree/v0.8.11/examples)**.
//!
//! ## Definitive example
//!
//! ```no_run
@@ -35,7 +37,7 @@
//! userid: String,
//! pass: String,
//! followers: u64,
//! email: Option<String>
//! email: Option<String>,
//! }
//!
//! let our_user = User { userid: "user".into(), pass: "pass".into(), followers: 120, email: None };
24 changes: 6 additions & 18 deletions src/query.rs
Original file line number Diff line number Diff line change
@@ -290,6 +290,12 @@ where
}
}

impl<'a, T: SQParam> SQParam for &'a T {
fn append_param(&self, q: &mut Vec<u8>) -> usize {
T::append_param(self, q)
}
}

/// Use this when you need to use `null`
pub struct Null;
impl SQParam for Null {
@@ -350,14 +356,6 @@ impl<const N: usize> SQParam for [u8; N] {
1
}
}
impl<'a, const N: usize> SQParam for &'a [u8; N] {
fn append_param(&self, buf: &mut Vec<u8>) -> usize {
buf.push(5);
pushlen!(buf, self.len());
buf.extend(*self);
1
}
}
impl SQParam for Vec<u8> {
fn append_param(&self, buf: &mut Vec<u8>) -> usize {
buf.push(5);
@@ -366,11 +364,6 @@ impl SQParam for Vec<u8> {
1
}
}
impl<'a> SQParam for &'a Vec<u8> {
fn append_param(&self, q: &mut Vec<u8>) -> usize {
self.as_slice().append_param(q)
}
}
// str
impl<'a> SQParam for &'a str {
fn append_param(&self, buf: &mut Vec<u8>) -> usize {
@@ -380,11 +373,6 @@ impl<'a> SQParam for &'a str {
1
}
}
impl<'a> SQParam for &'a String {
fn append_param(&self, q: &mut Vec<u8>) -> usize {
self.as_str().append_param(q)
}
}
impl SQParam for String {
fn append_param(&self, buf: &mut Vec<u8>) -> usize {
self.as_str().append_param(buf)
2 changes: 1 addition & 1 deletion src/response.rs
Original file line number Diff line number Diff line change
@@ -414,7 +414,7 @@ impl<T: FromRow> Deref for Rows<T> {

/// A list received from a response
#[derive(Debug, PartialEq, Clone)]
pub struct RList<T: FromValue = Value>(Vec<T>);
pub struct RList<T = Value>(Vec<T>);

impl<T: FromValue> From<Vec<T>> for RList<T> {
fn from(values: Vec<T>) -> Self {