Skip to content

Commit

Permalink
add history candlesticks api
Browse files Browse the repository at this point in the history
  • Loading branch information
sunli829 committed Oct 16, 2023
1 parent e49a808 commit 7d1b18f
Show file tree
Hide file tree
Showing 26 changed files with 891 additions and 130 deletions.
1 change: 1 addition & 0 deletions c/cbindgen.toml
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,7 @@ cpp_compat = true
"COptionQuote" = "lb_option_quote_t"
"CDate" = "lb_date_t"
"CTime" = "lb_time_t"
"CDateTime" = "lb_datetime_t"
"CWarrantQuote" = "lb_warrant_quote_t"
"CSecurityDepth" = "lb_security_depth_t"
"CSecurityBrokers" = "lb_security_brokers_t"
Expand Down
42 changes: 36 additions & 6 deletions c/csrc/include/longbridge.h
Original file line number Diff line number Diff line change
Expand Up @@ -1153,6 +1153,17 @@ typedef struct lb_date_t {
uint8_t day;
} lb_date_t;

typedef struct lb_time_t {
uint8_t hour;
uint8_t minute;
uint8_t second;
} lb_time_t;

typedef struct lb_datetime_t {
struct lb_date_t date;
struct lb_time_t time;
} lb_datetime_t;

/**
* An request to create a watchlist group
*/
Expand Down Expand Up @@ -2055,12 +2066,6 @@ typedef struct lb_issuer_info_t {
const char *name_hk;
} lb_issuer_info_t;

typedef struct lb_time_t {
uint8_t hour;
uint8_t minute;
uint8_t second;
} lb_time_t;

/**
* The information of trading session
*/
Expand Down Expand Up @@ -3214,6 +3219,31 @@ void lb_quote_context_candlesticks(const struct lb_quote_context_t *ctx,
lb_async_callback_t callback,
void *userdata);

/**
* Get security history candlesticks by offset
*/
void lb_quote_context_history_candlesticks_by_offset(const struct lb_quote_context_t *ctx,
const char *symbol,
enum lb_period_t period,
enum lb_adjust_type_t adjust_type,
bool forward,
struct lb_datetime_t time,
uintptr_t count,
lb_async_callback_t callback,
void *userdata);

/**
* Get security history candlesticks by date
*/
void lb_quote_context_history_candlesticks_by_date(const struct lb_quote_context_t *ctx,
const char *symbol,
enum lb_period_t period,
enum lb_adjust_type_t adjust_type,
const struct lb_date_t *start,
const struct lb_date_t *end,
lb_async_callback_t callback,
void *userdata);

/**
* Get option chain expiry date list
*/
Expand Down
66 changes: 65 additions & 1 deletion c/src/quote_context/context.rs
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ use crate::{
LB_WATCHLIST_GROUP_NAME, LB_WATCHLIST_GROUP_SECURITIES,
},
},
types::{cstr_array_to_rust, cstr_to_rust, CCow, CDate, CMarket, CVec, ToFFI},
types::{cstr_array_to_rust, cstr_to_rust, CCow, CDate, CDateTime, CMarket, CVec, ToFFI},
};

pub type COnQuoteCallback = extern "C" fn(*const CQuoteContext, *const CPushQuote, *mut c_void);
Expand Down Expand Up @@ -584,6 +584,70 @@ pub unsafe extern "C" fn lb_quote_context_candlesticks(
});
}

/// Get security history candlesticks by offset
#[no_mangle]
pub unsafe extern "C" fn lb_quote_context_history_candlesticks_by_offset(
ctx: *const CQuoteContext,
symbol: *const c_char,
period: CPeriod,
adjust_type: CAdjustType,
forward: bool,
time: CDateTime,
count: usize,
callback: CAsyncCallback,
userdata: *mut c_void,
) {
let ctx_inner = (*ctx).ctx.clone();
let symbol = cstr_to_rust(symbol);
execute_async(callback, ctx, userdata, async move {
let rows: CVec<CCandlestickOwned> = ctx_inner
.history_candlesticks_by_offset(
symbol,
period.into(),
adjust_type.into(),
forward,
time.into(),
count,
)
.await?
.into();
Ok(rows)
});
}

/// Get security history candlesticks by date
#[no_mangle]
pub unsafe extern "C" fn lb_quote_context_history_candlesticks_by_date(
ctx: *const CQuoteContext,
symbol: *const c_char,
period: CPeriod,
adjust_type: CAdjustType,
start: *const CDate,
end: *const CDate,
callback: CAsyncCallback,
userdata: *mut c_void,
) {
let ctx_inner = (*ctx).ctx.clone();
let symbol = cstr_to_rust(symbol);
let start = if start.is_null() {
None
} else {
Some((*start).into())
};
let end = if end.is_null() {
None
} else {
Some((*end).into())
};
execute_async(callback, ctx, userdata, async move {
let rows: CVec<CCandlestickOwned> = ctx_inner
.history_candlesticks_by_date(symbol, period.into(), adjust_type.into(), start, end)
.await?
.into();
Ok(rows)
});
}

/// Get option chain expiry date list
#[no_mangle]
pub unsafe extern "C" fn lb_quote_context_option_chain_expiry_date_list(
Expand Down
39 changes: 38 additions & 1 deletion c/src/types/datetime.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
use time::{Date, Month, Time};
use time::{Date, Month, PrimitiveDateTime, Time};

use crate::types::ToFFI;

Expand Down Expand Up @@ -58,6 +58,12 @@ impl From<Time> for CTime {
}
}

impl From<CTime> for Time {
fn from(time: CTime) -> Self {
Time::from_hms(time.hour, time.minute, time.second).expect("invalid time")
}
}

impl ToFFI for CTime {
type FFIType = Self;

Expand All @@ -66,3 +72,34 @@ impl ToFFI for CTime {
*self
}
}

#[derive(Debug, Copy, Clone)]
#[repr(C)]
pub struct CDateTime {
pub date: CDate,
pub time: CTime,
}

impl From<PrimitiveDateTime> for CDateTime {
fn from(datetime: PrimitiveDateTime) -> Self {
Self {
date: datetime.date().into(),
time: datetime.time().into(),
}
}
}

impl From<CDateTime> for PrimitiveDateTime {
fn from(datetime: CDateTime) -> Self {
PrimitiveDateTime::new(datetime.date.into(), datetime.time.into())
}
}

impl ToFFI for CDateTime {
type FFIType = Self;

#[inline]
fn to_ffi_type(&self) -> Self::FFIType {
*self
}
}
2 changes: 1 addition & 1 deletion c/src/types/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ use std::{ffi::CStr, os::raw::c_char};

pub(crate) use array::CVec;
pub(crate) use cow::CCow;
pub(crate) use datetime::{CDate, CTime};
pub(crate) use datetime::{CDate, CDateTime, CTime};
pub(crate) use decimal::CDecimal;
pub(crate) use language::CLanguage;
pub(crate) use market::CMarket;
Expand Down
19 changes: 19 additions & 0 deletions cpp/include/quote_context.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -128,6 +128,25 @@ class QuoteContext
AdjustType adjust_type,
AsyncCallback<QuoteContext, std::vector<Candlestick>> callback) const;

/// Get security history candlesticks by offset
void history_candlesticks_by_offset(
const std::string& symbol,
Period period,
AdjustType adjust_type,
bool forward,
DateTime datetime,
uintptr_t count,
AsyncCallback<QuoteContext, std::vector<Candlestick>> callback) const;

/// Get security history candlesticks by date
void history_candlesticks_by_date(
const std::string& symbol,
Period period,
AdjustType adjust_type,
std::optional<Date> start,
std::optional<Date> end,
AsyncCallback<QuoteContext, std::vector<Candlestick>> callback) const;

/// Get option chain expiry date list
void option_chain_expiry_date_list(
const std::string& symbol,
Expand Down
6 changes: 6 additions & 0 deletions cpp/include/types.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,12 @@ struct Time
uint8_t second;
};

struct DateTime
{
Date date;
Time time;
};

/// Language identifer
enum class Language
{
Expand Down
15 changes: 15 additions & 0 deletions cpp/src/convert.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -407,6 +407,12 @@ convert(const Date* date)
};
}

inline lb_time_t
convert(const Time* time)
{
return lb_time_t{ time->hour, time->minute, time->second };
}

inline Time
convert(const lb_time_t* time)
{
Expand All @@ -417,6 +423,15 @@ convert(const lb_time_t* time)
};
}

inline lb_datetime_t
convert(const DateTime* datetime)
{
return lb_datetime_t{
convert(&datetime->date),
convert(&datetime->time),
};
}

inline OptionQuote
convert(const lb_option_quote_t* info)
{
Expand Down
98 changes: 98 additions & 0 deletions cpp/src/quote_context.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -625,6 +625,104 @@ QuoteContext::candlesticks(
new AsyncCallback<QuoteContext, std::vector<Candlestick>>(callback));
}

void
QuoteContext::history_candlesticks_by_offset(
const std::string& symbol,
Period period,
AdjustType adjust_type,
bool forward,
DateTime datetime,
uintptr_t count,
AsyncCallback<QuoteContext, std::vector<Candlestick>> callback) const
{
lb_quote_context_history_candlesticks_by_offset(
ctx_,
symbol.c_str(),
convert(period),
convert(adjust_type),
forward,
convert(&datetime),
count,
[](auto res) {
auto callback_ptr =
callback::get_async_callback<QuoteContext, std::vector<Candlestick>>(
res->userdata);
QuoteContext ctx((const lb_quote_context_t*)res->ctx);
Status status(res->error);

if (status) {
auto rows = (const lb_candlestick_t*)res->data;
std::vector<Candlestick> rows2;
std::transform(rows,
rows + res->length,
std::back_inserter(rows2),
[](auto row) { return convert(&row); });

(*callback_ptr)(AsyncResult<QuoteContext, std::vector<Candlestick>>(
ctx, std::move(status), &rows2));
} else {
(*callback_ptr)(AsyncResult<QuoteContext, std::vector<Candlestick>>(
ctx, std::move(status), nullptr));
}
},
new AsyncCallback<QuoteContext, std::vector<Candlestick>>(callback));
}

void
QuoteContext::history_candlesticks_by_date(
const std::string& symbol,
Period period,
AdjustType adjust_type,
std::optional<Date> start,
std::optional<Date> end,
AsyncCallback<QuoteContext, std::vector<Candlestick>> callback) const
{
lb_date_t cstart, cend;
const lb_date_t* cstart_ptr = nullptr;
const lb_date_t* cend_ptr = nullptr;

if (start) {
cstart = convert(&*start);
cstart_ptr = &cstart;
}

if (end) {
cend = convert(&*end);
cend_ptr = &cend;
}

lb_quote_context_history_candlesticks_by_date(
ctx_,
symbol.c_str(),
convert(period),
convert(adjust_type),
cstart_ptr,
cend_ptr,
[](auto res) {
auto callback_ptr =
callback::get_async_callback<QuoteContext, std::vector<Candlestick>>(
res->userdata);
QuoteContext ctx((const lb_quote_context_t*)res->ctx);
Status status(res->error);

if (status) {
auto rows = (const lb_candlestick_t*)res->data;
std::vector<Candlestick> rows2;
std::transform(rows,
rows + res->length,
std::back_inserter(rows2),
[](auto row) { return convert(&row); });

(*callback_ptr)(AsyncResult<QuoteContext, std::vector<Candlestick>>(
ctx, std::move(status), &rows2));
} else {
(*callback_ptr)(AsyncResult<QuoteContext, std::vector<Candlestick>>(
ctx, std::move(status), nullptr));
}
},
new AsyncCallback<QuoteContext, std::vector<Candlestick>>(callback));
}

void
QuoteContext::option_chain_expiry_date_list(
const std::string& symbol,
Expand Down
Loading

0 comments on commit 7d1b18f

Please sign in to comment.