Skip to content

Commit

Permalink
feat(cdl): begin implementation of zone loader
Browse files Browse the repository at this point in the history
  • Loading branch information
HoKim98 committed Jul 29, 2024
1 parent 320b5a5 commit c498fcf
Show file tree
Hide file tree
Showing 25 changed files with 359 additions and 207 deletions.
5 changes: 4 additions & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -91,7 +91,10 @@ tracing = { version = "0.1" }
tracing-subscriber = { version = "0.3" }
tracing-subscriber-wasm = { version = "0.1" }
url = { version = "2.5" }
uuid = { version = "1.10", default-features = false, features = ["serde"] }
uuid = { version = "1.10", default-features = false, features = [
"serde",
"v4",
] }
wasm-streams = { version = "0.4" }
web-sys = { version = "0.3", features = [
"FileList",
Expand Down
6 changes: 3 additions & 3 deletions Justfile
Original file line number Diff line number Diff line change
Expand Up @@ -59,13 +59,13 @@ build *ARGS: ( _trunk "build" ARGS )

run *ARGS: ( _trunk "serve" ARGS )

run-examples *ARGS: ( _trunk "serve" "--features" "examples" ARGS )
run-examples *ARGS: ( _trunk "serve" "--features" "examples,full,mock-release" ARGS )

run-gateway *ARGS:
cargo watch -s 'clear && cargo run --package cassette-gateway'
cargo watch -s 'clear && cargo run --package cassette-gateway -- {{ ARGS }}'

run-operator *ARGS:
cargo watch -s 'clear && cargo run --package cassette-operator'
cargo watch -s 'clear && cargo run --package cassette-operator -- {{ ARGS }}'

_oci-build file oci_suffix *ARGS:
mkdir -p "${OCI_BUILD_LOG_DIR}"
Expand Down
4 changes: 2 additions & 2 deletions crates/cassette-core/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ api = ["dep:actix-web"]
ui = ["dep:gloo-net", "dep:patternfly-yew", "dep:tracing", "dep:yew"]

# net
stream = ["dep:anyhow", "dep:wasm-streams"]
stream = ["dep:wasm-streams"]

# for demo ONLY
examples = []
Expand All @@ -38,7 +38,7 @@ cdl = []

[dependencies]
actix-web = { workspace = true, optional = true }
anyhow = { workspace = true, optional = true }
anyhow = { workspace = true }
csv = { workspace = true }
garde = { workspace = true }
gloo-net = { workspace = true, optional = true }
Expand Down
4 changes: 3 additions & 1 deletion crates/cassette-core/src/components/error.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,9 @@ pub fn error(props: &Props) -> Html {

html! {
<Content>
<p>{ msg }</p>
<Alert inline=true title="Error" r#type={ AlertType::Danger }>
{ msg.clone() }
</Alert>
</Content>
}
}
2 changes: 1 addition & 1 deletion crates/cassette-core/src/data/csv.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ use schemars::JsonSchema;
use serde::{Deserialize, Serialize};
use serde_json::Value;

#[derive(Clone, Debug, PartialEq, Serialize, Deserialize, JsonSchema)]
#[derive(Clone, Debug, Default, PartialEq, Serialize, Deserialize, JsonSchema)]
pub struct CsvTable {
pub headers: Vec<String>,
pub records: Vec<Vec<Value>>,
Expand Down
11 changes: 5 additions & 6 deletions crates/cassette-core/src/data/table.rs
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@ impl Default for DataTableLog {
#[derive(Clone, Debug, PartialEq, Serialize, Deserialize, JsonSchema)]
#[serde(tag = "kind", content = "data", rename_all = "SCREAMING_SNAKE_CASE")]
pub enum DataTableSource {
#[cfg(feature = "cdl")]
Cdl(super::cdl::CdlTable),
Csv(super::csv::CsvTable),
Raw(Vec<u8>),
Expand All @@ -39,6 +40,7 @@ pub enum DataTableSource {
impl DataTableSource {
pub fn columns(&self) -> Result<Vec<String>> {
match self {
#[cfg(feature = "cdl")]
DataTableSource::Cdl(data) => Ok(data.columns()),
DataTableSource::Csv(data) => Ok(data.columns()),
DataTableSource::Raw(_) => bail!("Raw data table has no columns"),
Expand All @@ -47,6 +49,7 @@ impl DataTableSource {

pub fn records(self) -> Result<Vec<Vec<Value>>> {
match self {
#[cfg(feature = "cdl")]
DataTableSource::Cdl(data) => Ok(data.records()),
DataTableSource::Csv(data) => Ok(data.records()),
DataTableSource::Raw(_) => bail!("Raw data table has no records"),
Expand All @@ -55,6 +58,7 @@ impl DataTableSource {

pub fn is_empty(&self) -> bool {
match self {
#[cfg(feature = "cdl")]
DataTableSource::Cdl(data) => data.is_empty(),
DataTableSource::Csv(data) => data.is_empty(),
DataTableSource::Raw(data) => data.is_empty(),
Expand All @@ -63,6 +67,7 @@ impl DataTableSource {

pub fn len(&self) -> usize {
match self {
#[cfg(feature = "cdl")]
DataTableSource::Cdl(data) => data.len(),
DataTableSource::Csv(data) => data.len(),
DataTableSource::Raw(data) => data.len(),
Expand Down Expand Up @@ -104,9 +109,3 @@ impl DataTableSourceType {
}
}
}

#[derive(Clone, Debug, PartialEq, Serialize, Deserialize, JsonSchema)]
pub struct DataTableEntry {
pub index: usize,
pub values: Vec<Value>,
}
1 change: 0 additions & 1 deletion crates/cassette-core/src/lib.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
pub mod cassette;
pub mod components;
#[cfg(feature = "ui")]
pub mod data;
pub mod document;
pub mod net;
Expand Down
2 changes: 1 addition & 1 deletion crates/cassette-gateway/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ rustls-tls = [
# plugins

## Connected Data Lake (CDL)
cdl = ["dep:cassette-plugin-cdl-api"]
cdl = ["cassette-core/cdl", "dep:cassette-plugin-cdl-api"]

## Kubernetes
kubernetes = ["dep:cassette-plugin-kubernetes-api"]
Expand Down
11 changes: 5 additions & 6 deletions crates/cassette-gateway/src/actix.rs
Original file line number Diff line number Diff line change
Expand Up @@ -97,7 +97,7 @@ where
{
let scope = web::scope(base_url.unwrap_or(""));
let scope = build_core_services(scope);
let scope = build_plugin_servicess(scope);
let scope = build_plugin_services(scope);

app.route(
base_url.filter(|&path| !path.is_empty()).unwrap_or("/"),
Expand All @@ -114,12 +114,11 @@ fn build_core_services(scope: Scope) -> Scope {
.service(crate::routes::cassette::list)
}

fn build_plugin_servicess(scope: Scope) -> Scope {
fn build_plugin_services(scope: Scope) -> Scope {
#[cfg(feature = "cdl")]
let scope = ::cassette_plugin_cdl_api::build_services(scope);
#[cfg(feature = "kubernetes")]
let scope = scope.route(
"/kube/{path:.*}",
::actix_web::web::route().to(::cassette_plugin_kubernetes_api::handle),
);
let scope = ::cassette_plugin_kubernetes_api::build_services(scope);

scope
}
2 changes: 2 additions & 0 deletions crates/cassette-plugin-cdl-api/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -29,8 +29,10 @@ rustls-tls = ["dash-pipe-provider/rustls-tls"]

[dependencies]
cassette-core = { path = "../cassette-core", features = ["api"] }
cassette-plugin-kubernetes-api = { path = "../cassette-plugin-kubernetes-api" }

actix-web = { workspace = true }
anyhow = { workspace = true }
dash-pipe-provider = { workspace = true, features = ["kafka", "storage"] }
serde = { workspace = true }
tracing = { workspace = true }
15 changes: 4 additions & 11 deletions crates/cassette-plugin-cdl-api/src/lib.rs
Original file line number Diff line number Diff line change
@@ -1,14 +1,7 @@
pub fn add(left: usize, right: usize) -> usize {
left + right
}
mod zone;

#[cfg(test)]
mod tests {
use super::*;
use actix_web::Scope;

#[test]
fn it_works() {
let result = add(2, 2);
assert_eq!(result, 4);
}
pub fn build_services(scope: Scope) -> Scope {
scope.service(self::zone::list)
}
39 changes: 39 additions & 0 deletions crates/cassette-plugin-cdl-api/src/zone.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
use actix_web::{get, HttpRequest, HttpResponse, Responder};
use anyhow::Result;
use cassette_core::{
data::{
csv::CsvTable,
table::{DataTable, DataTableLog, DataTableSource},
},
result::Result as HttpResult,
};
use cassette_plugin_kubernetes_api::{load_client, Client};
use serde::Serialize;

#[get("/cdl/zone")]
pub async fn list(request: HttpRequest) -> impl Responder {
async fn try_handle(client: Client) -> Result<DataTable> {
Ok(DataTable {
name: "cdl-zones".into(),
data: DataTableSource::Csv(CsvTable::default()),
log: DataTableLog::default(),
})
}

match load_client(&request).await {
Ok(client) => response(try_handle(client).await),
Err(error) => HttpResponse::Unauthorized().json(HttpResult::<()>::Err(error.to_string())),
}
}

fn response<T>(result: Result<T>) -> HttpResponse
where
T: Serialize,
{
match result {
Ok(data) => HttpResponse::Ok().json(HttpResult::Ok(data)),
Err(error) => {
HttpResponse::MethodNotAllowed().json(HttpResult::<T>::Err(error.to_string()))
}
}
}
136 changes: 136 additions & 0 deletions crates/cassette-plugin-cdl-zone/src/actor.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,136 @@
use cassette_core::{
cassette::CassetteContext,
components::ComponentRenderer,
task::{TaskResult, TaskState},
};
use patternfly_yew::prelude::*;
use serde::{Deserialize, Serialize};
use yew::prelude::*;

#[derive(Clone, Debug, PartialEq, Deserialize, Properties)]
#[serde(rename_all = "camelCase")]
pub struct Spec {}

#[derive(Clone, Debug, Default, PartialEq, Serialize, Deserialize)]
#[serde(rename_all = "camelCase")]
pub struct State {}

impl ComponentRenderer<Spec> for State {
fn render(self, _ctx: &mut CassetteContext, spec: Spec) -> TaskResult<Option<Self>> {
let Spec {} = spec;

Ok(TaskState::Continue {
body: html! { <Manager/> },
state: Some(Self {}),
})
}
}

#[function_component(Manager)]
fn manager() -> Html {
const TOTAL_ENTRIES: usize = 394;

let offset = use_state_eq(|| 0);
let limit = use_state_eq(|| 5);

let entries = use_memo((*offset, *limit), |(offset, limit)| {
(*offset..(offset + limit).clamp(0, TOTAL_ENTRIES))
.map(ExampleEntry)
.collect::<Vec<_>>()
});

let (entries, _) = use_table_data(MemoizedTableModel::new(entries));

let header = html_nested! {
<TableHeader<Columns>>
<TableColumn<Columns> index={Columns::Select} />
<TableColumn<Columns> label="Decimal" index={Columns::Decimal} />
<TableColumn<Columns> label="Hex" index={Columns::Hex} />
<TableColumn<Columns> label="Button" index={Columns::Button} />
</TableHeader<Columns>>
};

let total_entries = Some(TOTAL_ENTRIES);

let limit_callback = use_callback(limit.clone(), |number, limit| limit.set(number));

let nav_callback = use_callback(
(offset.clone(), *limit),
|page: Navigation, (offset, limit)| {
let o = match page {
Navigation::First => 0,
Navigation::Last => ((TOTAL_ENTRIES - 1) / limit) * limit,
Navigation::Previous => **offset - limit,
Navigation::Next => **offset + limit,
Navigation::Page(n) => n * limit,
};
offset.set(o);
},
);

html! (
<>
<Toolbar>
<ToolbarContent>
// FIXME: add bulk-select support: https://www.patternfly.org/components/table/react-demos/bulk-select/
<ToolbarItem r#type={ToolbarItemType::Pagination}>
<Pagination
{total_entries}
offset={*offset}
entries_per_page_choices={vec![5, 10, 25, 50, 100]}
selected_choice={*limit}
onlimit={&limit_callback}
onnavigation={&nav_callback}
/>
</ToolbarItem>
</ToolbarContent>
</Toolbar>
<Table<Columns, UseTableData<Columns, MemoizedTableModel<ExampleEntry>>>
mode={TableMode::Compact}
{header}
{entries}
/>
<Pagination
{total_entries}
offset={*offset}
entries_per_page_choices={vec![5, 10, 25, 50, 100]}
selected_choice={*limit}
onlimit={&limit_callback}
onnavigation={&nav_callback}
position={PaginationPosition::Bottom}
/>
</>
)
}

#[derive(Clone, Eq, PartialEq)]
pub enum Columns {
Select,
Decimal,
Hex,
Button,
}

#[derive(Clone)]
struct ExampleEntry(usize);

impl TableEntryRenderer<Columns> for ExampleEntry {
fn render_cell(&self, context: CellContext<'_, Columns>) -> Cell {
match context.column {
Columns::Select => html! { <Checkbox /> },
Columns::Decimal => html!(self.0.to_string()),
Columns::Hex => html!(format!("{:x}", self.0)),
Columns::Button => html! {
<Flex modifiers={[ FlexModifier::Shrink ]}>
<FlexItem>
<Button variant={ ButtonVariant::Primary }>{ "Describe" }</Button>
</FlexItem>
<FlexItem>
<Button variant={ ButtonVariant::Danger }>{ "Delete" }</Button>
</FlexItem>
</Flex>
},
}
.into()
}
}
32 changes: 32 additions & 0 deletions crates/cassette-plugin-cdl-zone/src/hooks.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
use std::rc::Rc;

use cassette_core::{
cassette::{CassetteContext, CassetteTaskHandle},
data::table::DataTable,
net::{
fetch::{FetchRequestWithoutBody, FetchState, Method},
gateway::get_gateway,
},
};

pub fn use_fetch(
ctx: &mut CassetteContext,
base_url: Option<String>,
force: bool,
) -> CassetteTaskHandle<FetchState<Rc<DataTable>>> {
let handler_name = "chat completions";
let state = ctx.use_state(handler_name, force, || FetchState::Pending);
{
let state = state.clone();
let base_url = base_url.unwrap_or(get_gateway());
let request = FetchRequestWithoutBody {
method: Method::GET,
name: handler_name,
url: "/cdl/zone",
body: None,
};

request.try_fetch(&base_url, state)
}
state
}
Loading

0 comments on commit c498fcf

Please # to comment.