summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/amount.cc4
-rw-r--r--src/annotate.cc6
-rw-r--r--src/commodity.cc12
-rw-r--r--src/commodity.h16
-rw-r--r--src/pool.cc2
-rw-r--r--src/py_account.cc222
-rw-r--r--src/py_amount.cc3
-rw-r--r--src/py_balance.cc3
-rw-r--r--src/py_commodity.cc272
-rw-r--r--src/py_item.cc113
-rw-r--r--src/py_journal.cc456
-rw-r--r--src/py_post.cc141
-rw-r--r--src/py_utils.cc44
-rw-r--r--src/py_value.cc172
-rw-r--r--src/py_xact.cc138
-rw-r--r--src/pyinterp.cc2
-rw-r--r--src/value.h3
-rw-r--r--tools/Makefile.am1
18 files changed, 1122 insertions, 488 deletions
diff --git a/src/amount.cc b/src/amount.cc
index 435cdea4..e9b971f8 100644
--- a/src/amount.cc
+++ b/src/amount.cc
@@ -770,7 +770,7 @@ commodity_t& amount_t::commodity() const
bool amount_t::has_commodity() const
{
- return commodity_ && commodity_ != commodity_->parent().null_commodity;
+ return commodity_ && commodity_ != commodity_->pool().null_commodity;
}
void amount_t::annotate(const annotation_t& details)
@@ -795,7 +795,7 @@ void amount_t::annotate(const annotation_t& details)
<< *this << std::endl << details);
if (commodity_t * ann_comm =
- this_base->parent().find_or_create(*this_base, details))
+ this_base->pool().find_or_create(*this_base, details))
set_commodity(*ann_comm);
#ifdef ASSERTS_ON
else
diff --git a/src/annotate.cc b/src/annotate.cc
index 9c676086..45a4e7c8 100644
--- a/src/annotate.cc
+++ b/src/annotate.cc
@@ -185,12 +185,12 @@ annotated_commodity_t::strip_annotations(const keep_details_t& what_to_keep)
(keep_date && details.date) ||
(keep_tag && details.tag))
{
- new_comm = parent().find_or_create
+ new_comm = pool().find_or_create
(referent(), annotation_t(keep_price ? details.price : none,
keep_date ? details.date : none,
keep_tag ? details.tag : none));
} else {
- new_comm = parent().find_or_create(base_symbol());
+ new_comm = pool().find_or_create(base_symbol());
}
assert(new_comm);
@@ -199,7 +199,7 @@ annotated_commodity_t::strip_annotations(const keep_details_t& what_to_keep)
void annotated_commodity_t::write_annotations(std::ostream& out) const
{
- details.print(out, parent().keep_base);
+ details.print(out, pool().keep_base);
}
} // namespace ledger
diff --git a/src/commodity.cc b/src/commodity.cc
index d896572f..a0827e7a 100644
--- a/src/commodity.cc
+++ b/src/commodity.cc
@@ -375,7 +375,7 @@ commodity_t::check_for_updated_price(const optional<price_point_t>& point,
const optional<datetime_t>& moment,
const optional<commodity_t&>& in_terms_of)
{
- if (parent().get_quotes && ! has_flags(COMMODITY_NOMARKET)) {
+ if (pool().get_quotes && ! has_flags(COMMODITY_NOMARKET)) {
bool exceeds_leeway = true;
if (point) {
@@ -389,8 +389,8 @@ commodity_t::check_for_updated_price(const optional<price_point_t>& point,
DEBUG("commodity.download", "slip.now = " << seconds_diff);
}
- DEBUG("commodity.download", "leeway = " << parent().quote_leeway);
- if (seconds_diff < parent().quote_leeway)
+ DEBUG("commodity.download", "leeway = " << pool().quote_leeway);
+ if (seconds_diff < pool().quote_leeway)
exceeds_leeway = false;
}
@@ -398,7 +398,7 @@ commodity_t::check_for_updated_price(const optional<price_point_t>& point,
DEBUG("commodity.download",
"attempting to download a more current quote...");
if (optional<price_point_t> quote =
- parent().get_commodity_quote(*this, in_terms_of)) {
+ pool().get_commodity_quote(*this, in_terms_of)) {
if (! in_terms_of ||
(quote->price.has_commodity() &&
quote->price.commodity() == *in_terms_of))
@@ -411,7 +411,7 @@ commodity_t::check_for_updated_price(const optional<price_point_t>& point,
commodity_t::operator bool() const
{
- return this != parent().null_commodity;
+ return this != pool().null_commodity;
}
bool commodity_t::symbol_needs_quotes(const string& symbol)
@@ -568,7 +568,7 @@ void commodity_t::parse_symbol(char *& p, string& symbol)
bool commodity_t::valid() const
{
- if (symbol().empty() && this != parent().null_commodity) {
+ if (symbol().empty() && this != pool().null_commodity) {
DEBUG("ledger.validate",
"commodity_t: symbol().empty() && this != null_commodity");
return false;
diff --git a/src/commodity.h b/src/commodity.h
index 25397131..f65df1b9 100644
--- a/src/commodity.h
+++ b/src/commodity.h
@@ -222,8 +222,6 @@ protected:
#endif // HAVE_BOOST_SERIALIZATION
};
- static bool symbol_needs_quotes(const string& symbol);
-
shared_ptr<base_t> base;
commodity_pool_t * parent_;
@@ -247,28 +245,31 @@ public:
operator bool() const;
- bool is_annotated() const {
- return annotated;
- }
-
virtual bool operator==(const commodity_t& comm) const {
if (comm.annotated)
return comm == *this;
return base.get() == comm.base.get();
}
+ static bool symbol_needs_quotes(const string& symbol);
+
virtual commodity_t& referent() {
return *this;
}
virtual const commodity_t& referent() const {
return *this;
}
+
+ bool is_annotated() const {
+ return annotated;
+ }
+
virtual commodity_t& strip_annotations(const keep_details_t&) {
return *this;
}
virtual void write_annotations(std::ostream&) const {}
- commodity_pool_t& parent() const {
+ commodity_pool_t& pool() const {
return *parent_;
}
@@ -329,7 +330,6 @@ public:
optional<history_t&> history(const optional<commodity_t&>& commodity);
-public:
// These methods provide a transparent pass-through to the underlying
// base->varied_history object.
diff --git a/src/pool.cc b/src/pool.cc
index 06a4706c..b08c8fad 100644
--- a/src/pool.cc
+++ b/src/pool.cc
@@ -118,7 +118,7 @@ string commodity_pool_t::make_qualified_name(const commodity_t& comm,
std::ostringstream name;
comm.print(name);
- details.print(name, comm.parent().keep_base);
+ details.print(name, comm.pool().keep_base);
DEBUG("amounts.commodities", "make_qualified_name for "
<< *comm.qualified_symbol << std::endl << details);
diff --git a/src/py_account.cc b/src/py_account.cc
new file mode 100644
index 00000000..7fa30d0a
--- /dev/null
+++ b/src/py_account.cc
@@ -0,0 +1,222 @@
+/*
+ * Copyright (c) 2003-2009, John Wiegley. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *
+ * - Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * - Neither the name of New Artisans LLC nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include <system.hh>
+
+#include "pyinterp.h"
+#include "account.h"
+#include "post.h"
+
+namespace ledger {
+
+using namespace boost::python;
+
+namespace {
+
+ long accounts_len(account_t& account)
+ {
+ return account.accounts.size();
+ }
+
+ account_t& accounts_getitem(account_t& account, long i)
+ {
+ static long last_index = 0;
+ static account_t * last_account = NULL;
+ static accounts_map::iterator elem;
+
+ long len = account.accounts.size();
+
+ if (labs(i) >= len) {
+ PyErr_SetString(PyExc_IndexError, _("Index out of range"));
+ throw_error_already_set();
+ }
+
+ if (&account == last_account && i == last_index + 1) {
+ last_index = i;
+ return *(*++elem).second;
+ }
+
+ long x = i < 0 ? len + i : i;
+ elem = account.accounts.begin();
+ while (--x >= 0)
+ elem++;
+
+ last_account = &account;
+ last_index = i;
+
+ return *(*elem).second;
+ }
+
+ account_t * py_find_account_1(journal_t& journal, const string& name)
+ {
+ return journal.find_account(name);
+ }
+
+ account_t * py_find_account_2(journal_t& journal, const string& name,
+ const bool auto_create)
+ {
+ return journal.find_account(name, auto_create);
+ }
+
+ account_t::xdata_t& py_xdata(account_t& account) {
+ return account.xdata();
+ }
+
+} // unnamed namespace
+
+void export_account()
+{
+ scope().attr("ACCOUNT_EXT_SORT_CALC") = ACCOUNT_EXT_SORT_CALC;
+ scope().attr("ACCOUNT_EXT_HAS_NON_VIRTUALS") = ACCOUNT_EXT_HAS_NON_VIRTUALS;
+ scope().attr("ACCOUNT_EXT_HAS_UNB_VIRTUALS") = ACCOUNT_EXT_HAS_UNB_VIRTUALS;
+ scope().attr("ACCOUNT_EXT_AUTO_VIRTUALIZE") = ACCOUNT_EXT_AUTO_VIRTUALIZE;
+ scope().attr("ACCOUNT_EXT_VISITED") = ACCOUNT_EXT_VISITED;
+ scope().attr("ACCOUNT_EXT_MATCHING") = ACCOUNT_EXT_MATCHING;
+ scope().attr("ACCOUNT_EXT_TO_DISPLAY") = ACCOUNT_EXT_TO_DISPLAY;
+ scope().attr("ACCOUNT_EXT_DISPLAYED") = ACCOUNT_EXT_DISPLAYED;
+
+ class_< account_t::xdata_t::details_t > ("AccountXDataDetails")
+ .def_readonly("total", &account_t::xdata_t::details_t::total)
+ .def_readonly("calculated", &account_t::xdata_t::details_t::calculated)
+ .def_readonly("gathered", &account_t::xdata_t::details_t::gathered)
+
+ .def_readonly("posts_count", &account_t::xdata_t::details_t::posts_count)
+ .def_readonly("posts_virtuals_count",
+ &account_t::xdata_t::details_t::posts_virtuals_count)
+ .def_readonly("posts_cleared_count",
+ &account_t::xdata_t::details_t::posts_cleared_count)
+ .def_readonly("posts_last_7_count",
+ &account_t::xdata_t::details_t::posts_last_7_count)
+ .def_readonly("posts_last_30_count",
+ &account_t::xdata_t::details_t::posts_last_30_count)
+ .def_readonly("posts_this_month_count",
+ &account_t::xdata_t::details_t::posts_this_month_count)
+
+ .def_readonly("earliest_post",
+ &account_t::xdata_t::details_t::earliest_post)
+ .def_readonly("earliest_cleared_post",
+ &account_t::xdata_t::details_t::earliest_cleared_post)
+ .def_readonly("latest_post",
+ &account_t::xdata_t::details_t::latest_post)
+ .def_readonly("latest_cleared_post",
+ &account_t::xdata_t::details_t::latest_cleared_post)
+
+ .def_readonly("filenames", &account_t::xdata_t::details_t::filenames)
+ .def_readonly("accounts_referenced",
+ &account_t::xdata_t::details_t::accounts_referenced)
+ .def_readonly("payees_referenced",
+ &account_t::xdata_t::details_t::payees_referenced)
+
+ .def(self += self)
+
+ .def("update", &account_t::xdata_t::details_t::update)
+ ;
+
+ class_< account_t::xdata_t > ("AccountXData")
+#if 1
+ .def("flags", &supports_flags<uint_least16_t>::flags)
+ .def("has_flags", &supports_flags<uint_least16_t>::has_flags)
+ .def("set_flags", &supports_flags<uint_least16_t>::set_flags)
+ .def("clear_flags", &supports_flags<uint_least16_t>::clear_flags)
+ .def("add_flags", &supports_flags<uint_least16_t>::add_flags)
+ .def("drop_flags", &supports_flags<uint_least16_t>::drop_flags)
+#endif
+
+ .def_readonly("self_details", &account_t::xdata_t::self_details)
+ .def_readonly("family_details", &account_t::xdata_t::family_details)
+ .def_readonly("reported_posts", &account_t::xdata_t::reported_posts)
+ .def_readonly("sort_values", &account_t::xdata_t::sort_values)
+ ;
+
+ scope().attr("ACCOUNT_NORMAL") = ACCOUNT_NORMAL;
+ scope().attr("ACCOUNT_KNOWN") = ACCOUNT_KNOWN;
+ scope().attr("ACCOUNT_TEMP") = ACCOUNT_TEMP;
+
+ class_< account_t > ("Account")
+#if 1
+ .def("flags", &supports_flags<>::flags)
+ .def("has_flags", &supports_flags<>::has_flags)
+ .def("set_flags", &supports_flags<>::set_flags)
+ .def("clear_flags", &supports_flags<>::clear_flags)
+ .def("add_flags", &supports_flags<>::add_flags)
+ .def("drop_flags", &supports_flags<>::drop_flags)
+#endif
+
+ .add_property("parent",
+ make_getter(&account_t::parent,
+ return_value_policy<reference_existing_object>()))
+
+ .def_readwrite("name", &account_t::name)
+ .def_readwrite("note", &account_t::note)
+ .def_readonly("depth", &account_t::depth)
+ .def_readonly("accounts", &account_t::accounts)
+ .def_readonly("posts", &account_t::posts)
+
+ .def(self_ns::str(self))
+
+ .def("fullname", &account_t::fullname)
+ .def("partial_name", &account_t::partial_name)
+
+ .def("add_account", &account_t::add_account)
+ .def("remove_account", &account_t::remove_account)
+
+ .def("find_account", &account_t::find_account,
+ return_value_policy<reference_existing_object>())
+ .def("find_account_re", &account_t::find_account,
+ return_value_policy<reference_existing_object>())
+
+ .def("add_post", &account_t::add_post)
+ .def("remove_post", &account_t::remove_post)
+
+ .def("valid", &account_t::valid)
+
+ .def("__len__", accounts_len)
+ .def("__getitem__", accounts_getitem, return_internal_reference<1>())
+
+ .def("has_xdata", &account_t::has_xdata)
+ .def("clear_xdata", &account_t::clear_xdata)
+ .def("xdata", py_xdata,
+ return_value_policy<reference_existing_object>())
+
+ .def("amount", &account_t::amount)
+ .def("total", &account_t::total)
+
+ .def("self_details", &account_t::self_details,
+ return_value_policy<reference_existing_object>())
+ .def("family_details", &account_t::family_details,
+ return_value_policy<reference_existing_object>())
+
+ .def("has_xflags", &account_t::has_xflags)
+ .def("children_with_flags", &account_t::children_with_flags)
+ ;
+}
+
+} // namespace ledger
diff --git a/src/py_amount.cc b/src/py_amount.cc
index efae7514..c6b3284a 100644
--- a/src/py_amount.cc
+++ b/src/py_amount.cc
@@ -282,9 +282,6 @@ internal precision."))
.def("parse_conversion", &amount_t::parse_conversion)
.staticmethod("parse_conversion")
- .def("print_", py_print)
- .def("dump", &amount_t::dump)
-
.def("valid", &amount_t::valid)
;
diff --git a/src/py_balance.cc b/src/py_balance.cc
index 2d940876..effc6937 100644
--- a/src/py_balance.cc
+++ b/src/py_balance.cc
@@ -211,9 +211,6 @@ void export_balance()
.def("strip_annotations", &balance_t::strip_annotations)
- .def("print_", py_print)
- .def("dump", &balance_t::dump)
-
.def("valid", &balance_t::valid)
;
diff --git a/src/py_commodity.cc b/src/py_commodity.cc
index 4932df97..c0412a45 100644
--- a/src/py_commodity.cc
+++ b/src/py_commodity.cc
@@ -33,20 +33,149 @@
#include "pyinterp.h"
#include "commodity.h"
+#include "annotate.h"
+#include "pool.h"
namespace ledger {
using namespace boost::python;
-void py_add_price(commodity_t& commodity,
- const datetime_t& date,
- const amount_t& price)
-{
- commodity.add_price(date, price);
-}
+namespace {
+
+ commodity_t * py_create_1(commodity_pool_t& pool,
+ const string& symbol)
+ {
+ return pool.create(symbol);
+ }
+ commodity_t * py_create_2(commodity_pool_t& pool,
+ const string& symbol,
+ const annotation_t& details)
+ {
+ return pool.create(symbol, details);
+ }
+
+ commodity_t * py_find_or_create_1(commodity_pool_t& pool,
+ const string& symbol)
+ {
+ return pool.find_or_create(symbol);
+ }
+ commodity_t * py_find_or_create_2(commodity_pool_t& pool,
+ const string& symbol,
+ const annotation_t& details)
+ {
+ return pool.find_or_create(symbol, details);
+ }
+
+ commodity_t * py_find_1(commodity_pool_t& pool,
+ const string& name)
+ {
+ return pool.find(name);
+ }
+
+ commodity_t * py_find_2(commodity_pool_t& pool,
+ const string& symbol,
+ const annotation_t& details)
+ {
+ return pool.find(symbol, details);
+ }
+
+ // Exchange one commodity for another, while recording the factored price.
+
+ void py_exchange_3(commodity_pool_t& pool,
+ commodity_t& commodity,
+ const amount_t& per_unit_cost,
+ const datetime_t& moment)
+ {
+ pool.exchange(commodity, per_unit_cost, moment);
+ }
+
+ cost_breakdown_t py_exchange_5(commodity_pool_t& pool,
+ const amount_t& amount,
+ const amount_t& cost,
+ const bool is_per_unit,
+ const boost::optional<datetime_t>& moment,
+ const boost::optional<string>& tag)
+ {
+ return pool.exchange(amount, cost, is_per_unit, moment, tag);
+ }
+
+ void py_add_price_2(commodity_t& commodity,
+ const datetime_t& date, const amount_t& price) {
+ commodity.add_price(date, price);
+ }
+
+ void py_add_price_3(commodity_t& commodity, const datetime_t& date,
+ const amount_t& price, const bool reflexive) {
+ commodity.add_price(date, price, reflexive);
+ }
+
+ bool py_keep_all_0(keep_details_t& details) {
+ return details.keep_all();
+ }
+ bool py_keep_all_1(keep_details_t& details, const commodity_t& comm) {
+ return details.keep_all(comm);
+ }
+
+ bool py_keep_any_0(keep_details_t& details) {
+ return details.keep_any();
+ }
+ bool py_keep_any_1(keep_details_t& details, const commodity_t& comm) {
+ return details.keep_any(comm);
+ }
+
+} // unnamed namespace
void export_commodity()
{
+ class_< commodity_pool_t, boost::noncopyable > ("CommodityPool", no_init)
+ .add_property("null_commodity",
+ make_getter(&commodity_pool_t::null_commodity,
+ return_value_policy<reference_existing_object>()),
+ make_setter(&commodity_pool_t::null_commodity,
+ with_custodian_and_ward<1, 2>()))
+ .add_property("default_commodity",
+ make_getter(&commodity_pool_t::default_commodity,
+ return_value_policy<reference_existing_object>()),
+ make_setter(&commodity_pool_t::default_commodity,
+ with_custodian_and_ward<1, 2>()))
+
+ .add_property("keep_base",
+ make_getter(&commodity_pool_t::keep_base),
+ make_setter(&commodity_pool_t::keep_base))
+ .add_property("price_db",
+ make_getter(&commodity_pool_t::price_db),
+ make_setter(&commodity_pool_t::price_db))
+ .add_property("quote_leeway",
+ make_getter(&commodity_pool_t::quote_leeway),
+ make_setter(&commodity_pool_t::quote_leeway))
+ .add_property("get_quotes",
+ make_getter(&commodity_pool_t::get_quotes),
+ make_setter(&commodity_pool_t::get_quotes))
+ .add_property("get_commodity_quote",
+ make_getter(&commodity_pool_t::get_commodity_quote),
+ make_setter(&commodity_pool_t::get_commodity_quote))
+
+ .def("make_qualified_name", &commodity_pool_t::make_qualified_name)
+
+ .def("create", py_create_1, return_value_policy<reference_existing_object>())
+ .def("create", py_create_2, return_value_policy<reference_existing_object>())
+
+ .def("find_or_create", py_find_or_create_1,
+ return_value_policy<reference_existing_object>())
+ .def("find_or_create", py_find_or_create_2,
+ return_value_policy<reference_existing_object>())
+
+ .def("find", py_find_1, return_value_policy<reference_existing_object>())
+ .def("find", py_find_2, return_value_policy<reference_existing_object>())
+
+ .def("exchange", py_exchange_3, with_custodian_and_ward<1, 2>())
+ .def("exchange", py_exchange_5)
+
+ .def("parse_price_directive", &commodity_pool_t::parse_price_directive)
+ .def("parse_price_expression", &commodity_pool_t::parse_price_expression,
+ return_value_policy<reference_existing_object>())
+ ;
+
scope().attr("COMMODITY_STYLE_DEFAULTS") = COMMODITY_STYLE_DEFAULTS;
scope().attr("COMMODITY_STYLE_SUFFIXED") = COMMODITY_STYLE_SUFFIXED;
scope().attr("COMMODITY_STYLE_SEPARATED") = COMMODITY_STYLE_SEPARATED;
@@ -55,29 +184,136 @@ void export_commodity()
scope().attr("COMMODITY_NOMARKET") = COMMODITY_NOMARKET;
scope().attr("COMMODITY_BUILTIN") = COMMODITY_BUILTIN;
scope().attr("COMMODITY_WALKED") = COMMODITY_WALKED;
+ scope().attr("COMMODITY_KNOWN") = COMMODITY_KNOWN;
+ scope().attr("COMMODITY_PRIMARY") = COMMODITY_PRIMARY;
+
+ class_< commodity_t, boost::noncopyable > ("Commodity", no_init)
+#if 1
+ .def("flags", &delegates_flags<uint_least16_t>::flags)
+ .def("has_flags", &delegates_flags<uint_least16_t>::has_flags)
+ .def("set_flags", &delegates_flags<uint_least16_t>::set_flags)
+ .def("clear_flags", &delegates_flags<uint_least16_t>::clear_flags)
+ .def("add_flags", &delegates_flags<uint_least16_t>::add_flags)
+ .def("drop_flags", &delegates_flags<uint_least16_t>::drop_flags)
+#endif
+
+ .add_static_property("european_by_default",
+ make_getter(&commodity_t::european_by_default),
+ make_setter(&commodity_t::european_by_default))
+
+ .def("__nonzero__", &commodity_t::operator bool)
- class_< commodity_t, bases<>,
- commodity_t, boost::noncopyable > ("Commodity", no_init)
.def(self == self)
- .def("drop_flags", &commodity_t::drop_flags)
+ .def("symbol_needs_quotes", &commodity_t::symbol_needs_quotes)
+ .staticmethod("symbol_needs_quotes")
- .def("add_price", py_add_price)
+#if 0
+ .def("referent", &commodity_t::referent,
+ return_value_policy<reference_existing_object>())
+#endif
+
+ .def("is_annotated", &commodity_t::is_annotated)
+ .def("strip_annotations", &commodity_t::strip_annotations,
+ return_value_policy<reference_existing_object>())
+ .def("write_annotations", &commodity_t::write_annotations)
+
+ .def("pool", &commodity_t::pool,
+ return_value_policy<reference_existing_object>())
+ .def("base_symbol", &commodity_t::base_symbol)
+ .def("symbol", &commodity_t::symbol)
+ .def("mapping_key", &commodity_t::mapping_key)
+
+ .def("name", &commodity_t::name)
+ .def("set_name", &commodity_t::set_name)
+ .def("note", &commodity_t::note)
+ .def("set_note", &commodity_t::set_note)
.def("precision", &commodity_t::precision)
- ;
+ .def("set_precision", &commodity_t::set_precision)
+ .def("smaller", &commodity_t::smaller)
+ .def("set_smaller", &commodity_t::set_smaller)
+ .def("larger", &commodity_t::larger)
+ .def("set_larger", &commodity_t::set_larger)
-#if 0
- class_< annotation_t, bases<>,
- commodity_t, boost::noncopyable > ("Annotation", no_init)
+ .def("add_price", py_add_price_2)
+ .def("add_price", py_add_price_3)
+ .def("remove_price", &commodity_t::remove_price,
+ with_custodian_and_ward<1, 3>())
+ .def("find_price", &commodity_t::find_price)
+ .def("check_for_updated_price", &commodity_t::check_for_updated_price)
+
+ .def("valid", &commodity_t::valid)
;
- class_< keep_details_t, bases<>,
- commodity_t, boost::noncopyable > ("KeepDetails", no_init)
+
+ class_< annotation_t > ("Annotation", no_init)
+#if 1
+ .def("flags", &supports_flags<>::flags)
+ .def("has_flags", &supports_flags<>::has_flags)
+ .def("set_flags", &supports_flags<>::set_flags)
+ .def("clear_flags", &supports_flags<>::clear_flags)
+ .def("add_flags", &supports_flags<>::add_flags)
+ .def("drop_flags", &supports_flags<>::drop_flags)
+#endif
+
+ .add_property("price",
+ make_getter(&annotation_t::price),
+ make_setter(&annotation_t::price))
+ .add_property("date",
+ make_getter(&annotation_t::date),
+ make_setter(&annotation_t::date))
+ .add_property("tag",
+ make_getter(&annotation_t::tag),
+ make_setter(&annotation_t::tag))
+
+ .def("__nonzero__", &annotation_t::operator bool)
+
+ .def(self == self)
+
+ .def("valid", &annotation_t::valid)
;
- class_< annotated_commodity_t, bases<>,
- commodity_t, boost::noncopyable > ("AnnotatedCommodity", no_init)
+
+ class_< keep_details_t > ("KeepDetails")
+ .def(init<bool, bool, bool, bool>())
+
+ .add_property("keep_price",
+ make_getter(&keep_details_t::keep_price),
+ make_setter(&keep_details_t::keep_price))
+ .add_property("keep_date",
+ make_getter(&keep_details_t::keep_date),
+ make_setter(&keep_details_t::keep_date))
+ .add_property("keep_tag",
+ make_getter(&keep_details_t::keep_tag),
+ make_setter(&keep_details_t::keep_tag))
+ .add_property("only_actuals",
+ make_getter(&keep_details_t::only_actuals),
+ make_setter(&keep_details_t::only_actuals))
+
+ .def("keep_all", py_keep_all_0)
+ .def("keep_all", py_keep_all_1)
+ .def("keep_any", py_keep_any_0)
+ .def("keep_any", py_keep_any_1)
;
+
+ class_< annotated_commodity_t, bases<commodity_t>,
+ annotated_commodity_t, boost::noncopyable >
+ ("AnnotatedCommodity", no_init)
+ .add_property("details",
+ make_getter(&annotated_commodity_t::details),
+ make_setter(&annotated_commodity_t::details))
+
+ .def(self == self)
+ .def(self == other<commodity_t>())
+
+#if 0
+ .def("referent", &annotated_commodity_t::referent,
+ return_value_policy<reference_existing_object>())
#endif
+
+ .def("strip_annotations", &annotated_commodity_t::strip_annotations,
+ return_value_policy<reference_existing_object>())
+ .def("write_annotations", &annotated_commodity_t::write_annotations)
+ ;
}
} // namespace ledger
diff --git a/src/py_item.cc b/src/py_item.cc
index 0e1fe0f9..ac544c6a 100644
--- a/src/py_item.cc
+++ b/src/py_item.cc
@@ -32,11 +32,40 @@
#include <system.hh>
#include "pyinterp.h"
+#include "scope.h"
+#include "mask.h"
+#include "item.h"
namespace ledger {
using namespace boost::python;
+namespace {
+
+ bool py_has_tag_1s(item_t& item, const string& tag) {
+ return item.has_tag(tag);
+ }
+ bool py_has_tag_1m(item_t& item, const mask_t& tag_mask) {
+ return item.has_tag(tag_mask);
+ }
+ bool py_has_tag_2m(item_t& item, const mask_t& tag_mask,
+ const boost::optional<mask_t>& value_mask) {
+ return item.has_tag(tag_mask, value_mask);
+ }
+
+ boost::optional<string> py_get_tag_1s(item_t& item, const string& tag) {
+ return item.get_tag(tag);
+ }
+ boost::optional<string> py_get_tag_1m(item_t& item, const mask_t& tag_mask) {
+ return item.get_tag(tag_mask);
+ }
+ boost::optional<string> py_get_tag_2m(item_t& item, const mask_t& tag_mask,
+ const boost::optional<mask_t>& value_mask) {
+ return item.get_tag(tag_mask, value_mask);
+ }
+
+} // unnamed namespace
+
#define EXC_TRANSLATOR(type) \
void exc_translate_ ## type(const type& err) { \
PyErr_SetString(PyExc_ArithmeticError, err.what()); \
@@ -46,19 +75,89 @@ using namespace boost::python;
void export_item()
{
-#if 0
- class_< item_t > ("Item")
+ class_< position_t > ("Position")
+ .add_property("pathname",
+ make_getter(&position_t::pathname),
+ make_setter(&position_t::pathname))
+ .add_property("beg_pos",
+ make_getter(&position_t::beg_pos),
+ make_setter(&position_t::beg_pos))
+ .add_property("beg_line",
+ make_getter(&position_t::beg_line),
+ make_setter(&position_t::beg_line))
+ .add_property("end_pos",
+ make_getter(&position_t::end_pos),
+ make_setter(&position_t::end_pos))
+ .add_property("end_line",
+ make_getter(&position_t::end_line),
+ make_setter(&position_t::end_line))
;
+
+ scope().attr("ITEM_NORMAL") = ITEM_NORMAL;
+ scope().attr("ITEM_GENERATED") = ITEM_GENERATED;
+ scope().attr("ITEM_TEMP") = ITEM_TEMP;
+
+ enum_< item_t::state_t > ("State")
+ .value("Uncleared", item_t::UNCLEARED)
+ .value("Cleared", item_t::CLEARED)
+ .value("Pending", item_t::PENDING)
+ ;
+
+#if 0
+ class_< item_t, bases<scope_t> > ("JournalItem", init<uint_least8_t>())
+#else
+ class_< item_t > ("JournalItem", init<uint_least8_t>())
#endif
+#if 1
+ .def("flags", &supports_flags<>::flags)
+ .def("has_flags", &supports_flags<>::has_flags)
+ .def("set_flags", &supports_flags<>::set_flags)
+ .def("clear_flags", &supports_flags<>::clear_flags)
+ .def("add_flags", &supports_flags<>::add_flags)
+ .def("drop_flags", &supports_flags<>::drop_flags)
+#endif
+
+ .add_property("note",
+ make_getter(&item_t::note),
+ make_setter(&item_t::note))
+ .add_property("pos",
+ make_getter(&item_t::pos),
+ make_setter(&item_t::pos))
+ .add_property("metadata",
+ make_getter(&item_t::metadata),
+ make_setter(&item_t::metadata))
+
+ .def("copy_details", &item_t::copy_details)
- //register_optional_to_python<amount_t>();
+ .def(self == self)
+ .def(self != self)
- //implicitly_convertible<string, amount_t>();
+ .def("has_tag", py_has_tag_1s)
+ .def("has_tag", py_has_tag_1m)
+ .def("has_tag", py_has_tag_2m)
+ .def("get_tag", py_get_tag_1s)
+ .def("get_tag", py_get_tag_1m)
+ .def("get_tag", py_get_tag_2m)
-#define EXC_TRANSLATE(type) \
- register_exception_translator<type>(&exc_translate_ ## type);
+ .def("set_tag", &item_t::set_tag)
- //EXC_TRANSLATE(item_error);
+ .def("parse_tags", &item_t::parse_tags)
+ .def("append_note", &item_t::append_note)
+
+ .add_static_property("use_effective_date",
+ make_getter(&item_t::use_effective_date),
+ make_setter(&item_t::use_effective_date))
+
+ .def("date", &item_t::date)
+ .def("effective_date", &item_t::effective_date)
+
+ .def("set_state", &item_t::set_state)
+ .def("state", &item_t::state)
+
+ .def("lookup", &item_t::lookup)
+
+ .def("valid", &item_t::valid)
+ ;
}
} // namespace ledger
diff --git a/src/py_journal.cc b/src/py_journal.cc
index fb693ffc..873645d3 100644
--- a/src/py_journal.cc
+++ b/src/py_journal.cc
@@ -32,334 +32,176 @@
#include <system.hh>
#include "pyinterp.h"
+#include "pyutils.h"
+#include "hooks.h"
+#include "journal.h"
+#include "xact.h"
namespace ledger {
using namespace boost::python;
-#define EXC_TRANSLATOR(type) \
- void exc_translate_ ## type(const type& err) { \
- PyErr_SetString(PyExc_ArithmeticError, err.what()); \
- }
-
-//EXC_TRANSLATOR(journal_error)
-
-void export_journal()
-{
-#if 0
- class_< journal_t > ("Journal")
- ;
-#endif
-
- //register_optional_to_python<amount_t>();
-
- //implicitly_convertible<string, amount_t>();
-
-#define EXC_TRANSLATE(type) \
- register_exception_translator<type>(&exc_translate_ ## type);
-
- //EXC_TRANSLATE(journal_error);
-}
-
-} // namespace ledger
+namespace {
-#if 0
-xact_t& post_xact(const post_t& post)
-{
- return *post.xact;
-}
-
-unsigned int posts_len(xact_base_t& xact)
-{
- return xact.posts.size();
-}
-
-post_t& posts_getitem(xact_base_t& xact, int i)
-{
- static int last_index = 0;
- static xact_base_t * last_xact = NULL;
- static posts_list::iterator elem;
-
- std::size_t len = xact.posts.size();
+ account_t& py_account_master(journal_t& journal) {
+ return *journal.master;
+ }
- if (abs(i) >= len) {
- PyErr_SetString(PyExc_IndexError, _("Index out of range"));
- throw_error_already_set();
+ commodity_pool_t& py_commodity_pool(journal_t& journal) {
+ return *journal.commodity_pool;
}
- if (&xact == last_xact && i == last_index + 1) {
- last_index = i;
- return **++elem;
+ long xacts_len(journal_t& journal)
+ {
+ return journal.xacts.size();
}
- int x = i < 0 ? len + i : i;
- elem = xact.posts.begin();
- while (--x >= 0)
- elem++;
+ xact_t& xacts_getitem(journal_t& journal, long i)
+ {
+ static long last_index = 0;
+ static journal_t * last_journal = NULL;
+ static xacts_list::iterator elem;
- last_xact = &xact;
- last_index = i;
+ long len = journal.xacts.size();
- return **elem;
-}
+ if (labs(i) >= len) {
+ PyErr_SetString(PyExc_IndexError, _("Index out of range"));
+ throw_error_already_set();
+ }
-unsigned int xacts_len(journal_t& journal)
-{
- return journal.xacts.size();
-}
+ if (&journal == last_journal && i == last_index + 1) {
+ last_index = i;
+ return **++elem;
+ }
-xact_t& xacts_getitem(journal_t& journal, int i)
-{
- static int last_index = 0;
- static journal_t * last_journal = NULL;
- static xacts_list::iterator elem;
+ long x = i < 0 ? len + i : i;
+ elem = journal.xacts.begin();
+ while (--x >= 0)
+ elem++;
- std::size_t len = journal.xacts.size();
+ last_journal = &journal;
+ last_index = i;
- if (abs(i) >= len) {
- PyErr_SetString(PyExc_IndexError, _("Index out of range"));
- throw_error_already_set();
+ return **elem;
}
- if (&journal == last_journal && i == last_index + 1) {
- last_index = i;
- return **++elem;
+ long accounts_len(account_t& account)
+ {
+ return account.accounts.size();
}
- int x = i < 0 ? len + i : i;
- elem = journal.xacts.begin();
- while (--x >= 0)
- elem++;
+ account_t& accounts_getitem(account_t& account, long i)
+ {
+ static long last_index = 0;
+ static account_t * last_account = NULL;
+ static accounts_map::iterator elem;
- last_journal = &journal;
- last_index = i;
+ long len = account.accounts.size();
- return **elem;
-}
+ if (labs(i) >= len) {
+ PyErr_SetString(PyExc_IndexError, _("Index out of range"));
+ throw_error_already_set();
+ }
-unsigned int accounts_len(account_t& account)
-{
- return account.accounts.size();
-}
+ if (&account == last_account && i == last_index + 1) {
+ last_index = i;
+ return *(*++elem).second;
+ }
-account_t& accounts_getitem(account_t& account, int i)
-{
- static int last_index = 0;
- static account_t * last_account = NULL;
- static accounts_map::iterator elem;
+ long x = i < 0 ? len + i : i;
+ elem = account.accounts.begin();
+ while (--x >= 0)
+ elem++;
- std::size_t len = account.accounts.size();
+ last_account = &account;
+ last_index = i;
- if (abs(i) >= len) {
- PyErr_SetString(PyExc_IndexError, _("Index out of range"));
- throw_error_already_set();
+ return *(*elem).second;
}
- if (&account == last_account && i == last_index + 1) {
- last_index = i;
- return *(*++elem).second;
+ account_t * py_find_account_1(journal_t& journal, const string& name)
+ {
+ return journal.find_account(name);
}
- int x = i < 0 ? len + i : i;
- elem = account.accounts.begin();
- while (--x >= 0)
- elem++;
-
- last_account = &account;
- last_index = i;
-
- return *(*elem).second;
-}
-
-account_t * py_find_account_1(journal_t& journal, const string& name)
-{
- return journal.find_account(name);
-}
-
-account_t * py_find_account_2(journal_t& journal, const string& name,
- const bool auto_create)
-{
- return journal.find_account(name, auto_create);
-}
-
-bool py_add_xact(journal_t& journal, xact_t * xact) {
- return journal.add_xact(new xact_t(*xact));
-}
-
-void py_add_post(xact_base_t& xact, post_t * post) {
- return xact.add_post(new post_t(*post));
-}
-
-struct xact_base_wrap : public xact_base_t
-{
- PyObject * self;
- xact_base_wrap(PyObject * self_) : self(self_) {}
-
- virtual bool valid() const {
- return call_method<bool>(self, "valid");
- }
-};
-
-struct py_xact_finalizer_t : public xact_finalizer_t {
- object pyobj;
- py_xact_finalizer_t() {}
- py_xact_finalizer_t(object obj) : pyobj(obj) {}
- py_xact_finalizer_t(const py_xact_finalizer_t& other)
- : pyobj(other.pyobj) {}
- virtual bool operator()(xact_t& xact, bool post) {
- return call<bool>(pyobj.ptr(), xact, post);
+ account_t * py_find_account_2(journal_t& journal, const string& name,
+ const bool auto_create)
+ {
+ return journal.find_account(name, auto_create);
}
-};
-std::list<py_xact_finalizer_t> py_finalizers;
-
-void py_add_xact_finalizer(journal_t& journal, object x)
-{
- py_finalizers.push_back(py_xact_finalizer_t(x));
- journal.add_xact_finalizer(&py_finalizers.back());
-}
-
-void py_remove_xact_finalizer(journal_t& journal, object x)
-{
- for (std::list<py_xact_finalizer_t>::iterator i = py_finalizers.begin();
- i != py_finalizers.end();
- i++)
- if ((*i).pyobj == x) {
- journal.remove_xact_finalizer(&(*i));
- py_finalizers.erase(i);
- return;
+ struct py_xact_finalizer_t : public xact_finalizer_t {
+ object pyobj;
+ py_xact_finalizer_t() {}
+ py_xact_finalizer_t(object obj) : pyobj(obj) {}
+ py_xact_finalizer_t(const py_xact_finalizer_t& other)
+ : pyobj(other.pyobj) {}
+ virtual bool operator()(xact_t& xact, bool post) {
+ return call<bool>(pyobj.ptr(), xact, post);
}
-}
+ };
-void py_run_xact_finalizers(journal_t& journal, xact_t& xact, bool post)
-{
- run_hooks(journal.xact_finalize_hooks, xact, post);
-}
+ std::list<py_xact_finalizer_t> py_finalizers;
-#define EXC_TRANSLATOR(type) \
- void exc_translate_ ## type(const type& err) { \
- PyErr_SetString(PyExc_RuntimeError, err.what()); \
+ void py_add_xact_finalizer(journal_t& journal, object x)
+ {
+ py_finalizers.push_back(py_xact_finalizer_t(x));
+ journal.add_xact_finalizer(&py_finalizers.back());
}
-EXC_TRANSLATOR(balance_error)
-EXC_TRANSLATOR(interval_expr_error)
-EXC_TRANSLATOR(format_error)
-EXC_TRANSLATOR(parse_error)
+ void py_remove_xact_finalizer(journal_t& journal, object x)
+ {
+ for (std::list<py_xact_finalizer_t>::iterator i = py_finalizers.begin();
+ i != py_finalizers.end();
+ i++)
+ if ((*i).pyobj == x) {
+ journal.remove_xact_finalizer(&(*i));
+ py_finalizers.erase(i);
+ return;
+ }
+ }
-value_t py_post_amount(post_t * post) {
- return value_t(post->amount);
-}
+ void py_run_xact_finalizers(journal_t& journal, xact_t& xact, bool post)
+ {
+ journal.xact_finalize_hooks.run_hooks(xact, post);
+ }
-post_t::state_t py_xact_state(xact_t * xact) {
- post_t::state_t state;
- if (xact->get_state(&state))
- return state;
- else
- return post_t::UNCLEARED;
-}
+} // unnamed namespace
void export_journal()
{
- scope().attr("POST_NORMAL") = POST_NORMAL;
- scope().attr("POST_VIRTUAL") = POST_VIRTUAL;
- scope().attr("POST_BALANCE") = POST_BALANCE;
- scope().attr("POST_AUTO") = POST_AUTO;
- scope().attr("POST_BULK_ALLOC") = POST_BULK_ALLOC;
- scope().attr("POST_CALCULATED") = POST_CALCULATED;
-
- enum_< post_t::state_t > ("State")
- .value("Uncleared", post_t::UNCLEARED)
- .value("Cleared", post_t::CLEARED)
- .value("Pending", post_t::PENDING)
+ class_< journal_t::fileinfo_t > ("FileInfo")
+ .add_property("filename",
+ make_getter(&journal_t::fileinfo_t::filename),
+ make_setter(&journal_t::fileinfo_t::filename))
+ .add_property("size",
+ make_getter(&journal_t::fileinfo_t::size),
+ make_setter(&journal_t::fileinfo_t::size))
+ .add_property("modtime",
+ make_getter(&journal_t::fileinfo_t::modtime),
+ make_setter(&journal_t::fileinfo_t::modtime))
+ .add_property("from_stream",
+ make_getter(&journal_t::fileinfo_t::from_stream),
+ make_setter(&journal_t::fileinfo_t::from_stream))
;
- class_< post_t > ("Post")
- .def(init<optional<account_t *> >())
- .def(init<account_t *, amount_t, optional<unsigned int, const string&> >())
-
- .def(self == self)
- .def(self != self)
-
- .add_property("xact",
- make_getter(&post_t::xact,
- return_value_policy<reference_existing_object>()))
- .add_property("account",
- make_getter(&post_t::account,
- return_value_policy<reference_existing_object>()))
-
- .add_property("amount", &py_post_amount)
- .def_readonly("amount_expr", &post_t::amount_expr)
- .add_property("cost",
- make_getter(&post_t::cost,
- return_internal_reference<1>()))
- .def_readonly("cost_expr", &post_t::cost_expr)
-
- .def_readwrite("state", &post_t::state)
- .def_readwrite("flags", &post_t::flags)
- .def_readwrite("note", &post_t::note)
-
- .def_readonly("beg_pos", &post_t::beg_pos)
- .def_readonly("beg_line", &post_t::beg_line)
- .def_readonly("end_pos", &post_t::end_pos)
- .def_readonly("end_line", &post_t::end_line)
-
- .def("actual_date", &post_t::actual_date)
- .def("effective_date", &post_t::effective_date)
- .def("date", &post_t::date)
-
- .def("use_effective_date", &post_t::use_effective_date)
-
- .def("valid", &post_t::valid)
- ;
-
- class_< account_t >
- ("Account", init<optional<account_t *, string, string> >()
- [with_custodian_and_ward<1, 2>()])
- .def(self == self)
- .def(self != self)
-
- .def(self_ns::str(self))
-
- .def("__len__", accounts_len)
- .def("__getitem__", accounts_getitem, return_internal_reference<1>())
-
- .add_property("journal",
- make_getter(&account_t::journal,
- return_value_policy<reference_existing_object>()))
- .add_property("parent",
- make_getter(&account_t::parent,
- return_value_policy<reference_existing_object>()))
- .def_readwrite("name", &account_t::name)
- .def_readwrite("note", &account_t::note)
- .def_readonly("depth", &account_t::depth)
- .def_readonly("ident", &account_t::ident)
-
- .def("fullname", &account_t::fullname)
-
- .def("add_account", &account_t::add_account)
- .def("remove_account", &account_t::remove_account)
-
- .def("find_account", &account_t::find_account,
- return_value_policy<reference_existing_object>())
-
- .def("valid", &account_t::valid)
- ;
-
- class_< journal_t > ("Journal")
- .def(self == self)
- .def(self != self)
-
- .def("__len__", xacts_len)
- .def("__getitem__", xacts_getitem, return_internal_reference<1>())
-
+ class_< journal_t, boost::noncopyable > ("Journal")
.add_property("master", make_getter(&journal_t::master,
return_internal_reference<1>()))
- .add_property("basket", make_getter(&journal_t::basket,
- return_internal_reference<1>()))
-
- .def_readonly("sources", &journal_t::sources)
-
- .def_readwrite("price_db", &journal_t::price_db)
+ .add_property("basket",
+ make_getter(&journal_t::basket,
+ return_internal_reference<1>()),
+ make_setter(&journal_t::basket))
+ .add_property("sources", make_getter(&journal_t::sources))
+ .add_property("was_loaded", make_getter(&journal_t::was_loaded))
+ .add_property("commodity_pool",
+ make_getter(&journal_t::commodity_pool,
+ return_internal_reference<1>()))
+#if 0
+ .add_property("xact_finalize_hooks",
+ make_getter(&journal_t::xact_finalize_hooks),
+ make_setter(&journal_t::xact_finalize_hooks))
+#endif
.def("add_account", &journal_t::add_account)
.def("remove_account", &journal_t::remove_account)
@@ -369,58 +211,18 @@ void export_journal()
.def("find_account_re", &journal_t::find_account_re,
return_internal_reference<1>())
- .def("add_xact", py_add_xact)
+ .def("add_xact", &journal_t::add_xact)
.def("remove_xact", &journal_t::remove_xact)
.def("add_xact_finalizer", py_add_xact_finalizer)
.def("remove_xact_finalizer", py_remove_xact_finalizer)
.def("run_xact_finalizers", py_run_xact_finalizers)
- .def("valid", &journal_t::valid)
- ;
-
- class_< xact_base_t, xact_base_wrap, boost::noncopyable > ("XactBase")
- .def("__len__", posts_len)
- .def("__getitem__", posts_getitem,
- return_internal_reference<1>())
-
- .def_readonly("journal", &xact_base_t::journal)
-
- .def_readonly("src_idx", &xact_base_t::src_idx)
- .def_readonly("beg_pos", &xact_base_t::beg_pos)
- .def_readonly("beg_line", &xact_base_t::beg_line)
- .def_readonly("end_pos", &xact_base_t::end_pos)
- .def_readonly("end_line", &xact_base_t::end_line)
-
- .def("add_post", py_add_post)
- .def("remove_post", &xact_base_t::remove_post)
-
- .def(self == self)
- .def(self != self)
-
- .def("finalize", &xact_base_t::finalize)
- .def("valid", &xact_base_t::valid)
- ;
-
- class_< xact_t, bases<xact_base_t> > ("Xact")
- .add_property("date", &xact_t::date)
- .add_property("effective_date", &xact_t::effective_date)
- .add_property("actual_date", &xact_t::actual_date)
-
- .def_readwrite("code", &xact_t::code)
- .def_readwrite("payee", &xact_t::payee)
-
- .add_property("state", &py_xact_state)
+ .def("__len__", xacts_len)
+ .def("__getitem__", xacts_getitem, return_internal_reference<1>())
- .def("valid", &xact_t::valid)
+ .def("valid", &journal_t::valid)
;
-
-#define EXC_TRANSLATE(type) \
- register_error_translator<type>(&exc_translate_ ## type);
-
- EXC_TRANSLATE(balance_error);
- EXC_TRANSLATE(interval_expr_error);
- EXC_TRANSLATE(format_error);
- EXC_TRANSLATE(parse_error);
}
-#endif
+
+} // namespace ledger
diff --git a/src/py_post.cc b/src/py_post.cc
index b1d62464..b4849c3d 100644
--- a/src/py_post.cc
+++ b/src/py_post.cc
@@ -32,33 +32,150 @@
#include <system.hh>
#include "pyinterp.h"
+#include "post.h"
+#include "xact.h"
namespace ledger {
using namespace boost::python;
-#define EXC_TRANSLATOR(type) \
- void exc_translate_ ## type(const type& err) { \
- PyErr_SetString(PyExc_ArithmeticError, err.what()); \
+namespace {
+
+ bool py_has_tag_1s(post_t& post, const string& tag) {
+ return post.has_tag(tag);
+ }
+ bool py_has_tag_1m(post_t& post, const mask_t& tag_mask) {
+ return post.has_tag(tag_mask);
+ }
+ bool py_has_tag_2m(post_t& post, const mask_t& tag_mask,
+ const boost::optional<mask_t>& value_mask) {
+ return post.has_tag(tag_mask, value_mask);
+ }
+
+ boost::optional<string> py_get_tag_1s(post_t& post, const string& tag) {
+ return post.get_tag(tag);
+ }
+ boost::optional<string> py_get_tag_1m(post_t& post, const mask_t& tag_mask) {
+ return post.get_tag(tag_mask);
+ }
+ boost::optional<string> py_get_tag_2m(post_t& post, const mask_t& tag_mask,
+ const boost::optional<mask_t>& value_mask) {
+ return post.get_tag(tag_mask, value_mask);
+ }
+
+ post_t::xdata_t& py_xdata(post_t& post) {
+ return post.xdata();
}
-//EXC_TRANSLATOR(post_error)
+ account_t * py_reported_account(post_t& post) {
+ return post.reported_account();
+ }
+
+} // unnamed namespace
void export_post()
{
-#if 0
- class_< post_t > ("Post")
- ;
+ scope().attr("POST_EXT_RECEIVED") = POST_EXT_RECEIVED;
+ scope().attr("POST_EXT_HANDLED") = POST_EXT_HANDLED;
+ scope().attr("POST_EXT_DISPLAYED") = POST_EXT_DISPLAYED;
+ scope().attr("POST_EXT_DIRECT_AMT") = POST_EXT_DIRECT_AMT;
+ scope().attr("POST_EXT_SORT_CALC") = POST_EXT_SORT_CALC;
+ scope().attr("POST_EXT_COMPOUND") = POST_EXT_COMPOUND;
+ scope().attr("POST_EXT_VISITED") = POST_EXT_VISITED;
+ scope().attr("POST_EXT_MATCHES") = POST_EXT_MATCHES;
+ scope().attr("POST_EXT_CONSIDERED") = POST_EXT_CONSIDERED;
+
+ class_< post_t::xdata_t > ("PostingXData")
+#if 1
+ .def("flags", &supports_flags<uint_least16_t>::flags)
+ .def("has_flags", &supports_flags<uint_least16_t>::has_flags)
+ .def("set_flags", &supports_flags<uint_least16_t>::set_flags)
+ .def("clear_flags", &supports_flags<uint_least16_t>::clear_flags)
+ .def("add_flags", &supports_flags<uint_least16_t>::add_flags)
+ .def("drop_flags", &supports_flags<uint_least16_t>::drop_flags)
#endif
- //register_optional_to_python<amount_t>();
+ .add_property("visited_value",
+ make_getter(&post_t::xdata_t::visited_value),
+ make_setter(&post_t::xdata_t::visited_value))
+ .add_property("compound_value",
+ make_getter(&post_t::xdata_t::compound_value),
+ make_setter(&post_t::xdata_t::compound_value))
+ .add_property("total",
+ make_getter(&post_t::xdata_t::total),
+ make_setter(&post_t::xdata_t::total))
+ .add_property("count",
+ make_getter(&post_t::xdata_t::count),
+ make_setter(&post_t::xdata_t::count))
+ .add_property("date",
+ make_getter(&post_t::xdata_t::date),
+ make_setter(&post_t::xdata_t::date))
+ .add_property("datetime",
+ make_getter(&post_t::xdata_t::datetime),
+ make_setter(&post_t::xdata_t::datetime))
+ .add_property("account",
+ make_getter(&post_t::xdata_t::account),
+ make_setter(&post_t::xdata_t::account))
+ .add_property("sort_values",
+ make_getter(&post_t::xdata_t::sort_values),
+ make_setter(&post_t::xdata_t::sort_values))
+ ;
+
+ scope().attr("POST_VIRTUAL") = POST_VIRTUAL;
+ scope().attr("POST_MUST_BALANCE") = POST_MUST_BALANCE;
+ scope().attr("POST_CALCULATED") = POST_CALCULATED;
+ scope().attr("POST_COST_CALCULATED") = POST_COST_CALCULATED;
+
+ class_< post_t, bases<item_t> > ("Posting")
+ //.def(init<account_t *>())
+
+ .add_property("xact",
+ make_getter(&post_t::xact,
+ return_value_policy<reference_existing_object>()),
+ make_setter(&post_t::xact,
+ with_custodian_and_ward<1, 2>()))
+ .add_property("account",
+ make_getter(&post_t::account,
+ return_value_policy<reference_existing_object>()),
+ make_setter(&post_t::account,
+ with_custodian_and_ward<1, 2>()))
+ .add_property("amount",
+ make_getter(&post_t::amount),
+ make_setter(&post_t::amount))
+ .add_property("cost",
+ make_getter(&post_t::cost),
+ make_setter(&post_t::cost))
+ .add_property("assigned_amount",
+ make_getter(&post_t::assigned_amount),
+ make_setter(&post_t::assigned_amount))
+
+ .def("has_tag", py_has_tag_1s)
+ .def("has_tag", py_has_tag_1m)
+ .def("has_tag", py_has_tag_2m)
+ .def("get_tag", py_get_tag_1s)
+ .def("get_tag", py_get_tag_1m)
+ .def("get_tag", py_get_tag_2m)
- //implicitly_convertible<string, amount_t>();
+ .def("date", &post_t::date)
+ .def("effective_date", &post_t::effective_date)
-#define EXC_TRANSLATE(type) \
- register_exception_translator<type>(&exc_translate_ ## type);
+ .def("must_balance", &post_t::must_balance)
- //EXC_TRANSLATE(post_error);
+ .def("lookup", &post_t::lookup)
+
+ .def("valid", &post_t::valid)
+
+ .def("has_xdata", &post_t::has_xdata)
+ .def("clear_xdata", &post_t::clear_xdata)
+ .def("xdata", py_xdata,
+ return_value_policy<reference_existing_object>())
+
+ .def("add_to_value", &post_t::add_to_value)
+ .def("set_reported_account", &post_t::set_reported_account)
+
+ .def("reported_account", py_reported_account,
+ return_value_policy<reference_existing_object>())
+ ;
}
} // namespace ledger
diff --git a/src/py_utils.cc b/src/py_utils.cc
index cf98c5fe..3e788442 100644
--- a/src/py_utils.cc
+++ b/src/py_utils.cc
@@ -164,6 +164,50 @@ typedef register_python_conversion<std::ostream, ostream_to_python, ostream_from
void export_utils()
{
+ class_< supports_flags<uint_least8_t> > ("SupportFlags8")
+ .def(init<supports_flags<uint_least8_t> >())
+ .def(init<uint_least8_t>())
+
+ .def("flags", &supports_flags<uint_least8_t>::flags)
+ .def("has_flags", &supports_flags<uint_least8_t>::has_flags)
+ .def("set_flags", &supports_flags<uint_least8_t>::set_flags)
+ .def("clear_flags", &supports_flags<uint_least8_t>::clear_flags)
+ .def("add_flags", &supports_flags<uint_least8_t>::add_flags)
+ .def("drop_flags", &supports_flags<uint_least8_t>::drop_flags)
+ ;
+
+ class_< supports_flags<uint_least16_t> > ("SupportFlags16")
+ .def(init<supports_flags<uint_least16_t> >())
+ .def(init<uint_least16_t>())
+
+ .def("flags", &supports_flags<uint_least16_t>::flags)
+ .def("has_flags", &supports_flags<uint_least16_t>::has_flags)
+ .def("set_flags", &supports_flags<uint_least16_t>::set_flags)
+ .def("clear_flags", &supports_flags<uint_least16_t>::clear_flags)
+ .def("add_flags", &supports_flags<uint_least16_t>::add_flags)
+ .def("drop_flags", &supports_flags<uint_least16_t>::drop_flags)
+ ;
+
+#if 0
+ class_< basic_flags_t<uint_least8_t>,
+ bases<supports_flags<uint_least8_t> > > ("BasicFlags8")
+ .def(init<uint_least8_t>())
+
+ .def("plus_flags", &basic_flags_t<uint_least8_t>::plus_flags)
+ .def("minus_flags", &basic_flags_t<uint_least8_t>::minus_flags)
+ ;
+#endif
+
+ class_< delegates_flags<uint_least16_t>,
+ boost::noncopyable > ("DelegatesFlags16", no_init)
+ .def("flags", &delegates_flags<uint_least16_t>::flags)
+ .def("has_flags", &delegates_flags<uint_least16_t>::has_flags)
+ .def("set_flags", &delegates_flags<uint_least16_t>::set_flags)
+ .def("clear_flags", &delegates_flags<uint_least16_t>::clear_flags)
+ .def("add_flags", &delegates_flags<uint_least16_t>::add_flags)
+ .def("drop_flags", &delegates_flags<uint_least16_t>::drop_flags)
+ ;
+
bool_python_conversion();
string_python_conversion();
istream_python_conversion();
diff --git a/src/py_value.cc b/src/py_value.cc
index f6c71920..34ee2d82 100644
--- a/src/py_value.cc
+++ b/src/py_value.cc
@@ -41,8 +41,12 @@ namespace ledger {
using namespace boost::python;
BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS(value_overloads, value, 0, 2)
+BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS(exchange_commodities_overloads,
+ exchange_commodities, 1, 2)
+BOOST_PYTHON_MEMBER_FUNCTION_OVERLOADS(set_string_overloads, set_string, 0, 2)
namespace {
+
expr_t py_value_getattr(const value_t& value, const string& name)
{
if (value.is_scope()) {
@@ -69,28 +73,47 @@ namespace {
return amount.set_string(str);
}
+} // unnamed namespace
+
#define EXC_TRANSLATOR(type) \
void exc_translate_ ## type(const type& err) { \
PyErr_SetString(PyExc_ArithmeticError, err.what()); \
}
- EXC_TRANSLATOR(value_error)
-}
+EXC_TRANSLATOR(value_error)
void export_value()
{
+ enum_< value_t::type_t >("ValueType")
+ .value("VOID", value_t::VOID)
+ .value("BOOLEAN", value_t::BOOLEAN)
+ .value("DATETIME", value_t::DATETIME)
+ .value("DATE", value_t::DATE)
+ .value("INTEGER", value_t::INTEGER)
+ .value("AMOUNT", value_t::AMOUNT)
+ .value("BALANCE", value_t::BALANCE)
+ .value("STRING", value_t::STRING)
+ .value("SEQUENCE", value_t::SEQUENCE)
+ .value("SCOPE", value_t::SCOPE)
+ ;
+
class_< value_t > ("Value")
.def("initialize", &value_t::initialize)
.staticmethod("initialize")
.def("shutdown", &value_t::shutdown)
.staticmethod("shutdown")
- .def(init<double>())
+ .def(init<bool>())
+ .def(init<datetime_t>())
+ .def(init<date_t>())
.def(init<long>())
+ .def(init<double>())
+ .def(init<amount_t>())
+ .def(init<balance_t>())
+ .def(init<mask_t>())
.def(init<std::string>())
- .def(init<date_t>())
- .def(init<datetime_t>())
-
+ // jww (2009-11-02): Need to support conversion of sequences
+ //.def(init<value_t::sequence_t>())
.def(init<value_t>())
.def("is_equal_to", &value_t::is_equal_to)
@@ -100,80 +123,88 @@ void export_value()
.def(self == self)
.def(self == long())
.def(long() == self)
- .def(self == double())
- .def(double() == self)
+ .def(self == other<amount_t>())
+ .def(other<amount_t>() == self)
+ .def(self == other<balance_t>())
+ .def(other<balance_t>() == self)
.def(self != self)
.def(self != long())
.def(long() != self)
- .def(self != double())
- .def(double() != self)
+ .def(self != other<amount_t>())
+ .def(other<amount_t>() != self)
+ .def(self != other<balance_t>())
+ .def(other<balance_t>() != self)
.def(! self)
.def(self < self)
.def(self < long())
.def(long() < self)
- .def(self < double())
- .def(double() < self)
+ .def(self < other<amount_t>())
+ .def(other<amount_t>() < self)
.def(self <= self)
.def(self <= long())
.def(long() <= self)
- .def(self <= double())
- .def(double() <= self)
+ .def(self <= other<amount_t>())
+ .def(other<amount_t>() <= self)
.def(self > self)
.def(self > long())
.def(long() > self)
- .def(self > double())
- .def(double() > self)
+ .def(self > other<amount_t>())
+ .def(other<amount_t>() > self)
.def(self >= self)
.def(self >= long())
.def(long() >= self)
- .def(self >= double())
- .def(double() >= self)
+ .def(self >= other<amount_t>())
+ .def(other<amount_t>() >= self)
.def(self += self)
.def(self += long())
- .def(self += double())
+ .def(self += other<amount_t>())
+ .def(self += other<balance_t>())
- .def(self + self)
- .def(self + long())
- .def(long() + self)
- .def(self + double())
- .def(double() + self)
+ .def(self + self)
+ .def(self + long())
+ .def(long() + self)
+ .def(self + other<amount_t>())
+ .def(other<amount_t>() + self)
+ .def(self + other<balance_t>())
.def(self -= self)
.def(self -= long())
- .def(self -= double())
+ .def(self -= other<amount_t>())
+ .def(self -= other<balance_t>())
- .def(self - self)
- .def(self - long())
- .def(long() - self)
- .def(self - double())
- .def(double() - self)
+ .def(self - self)
+ .def(self - long())
+ .def(long() - self)
+ .def(self - other<amount_t>())
+ .def(other<amount_t>() - self)
+ .def(self - other<balance_t>())
.def(self *= self)
.def(self *= long())
- .def(self *= double())
+ .def(self *= other<amount_t>())
- .def(self * self)
- .def(self * long())
- .def(long() * self)
- .def(self * double())
- .def(double() * self)
+ .def(self * self)
+ .def(self * long())
+ .def(long() * self)
+ .def(self * other<amount_t>())
+ .def(other<amount_t>() * self)
.def(self /= self)
.def(self /= long())
- .def(self /= double())
+ .def(self /= other<amount_t>())
- .def(self / self)
- .def(self / long())
- .def(long() / self)
- .def(self / double())
- .def(double() / self)
+ .def(self / self)
+ .def(self / long())
+ .def(long() / self)
+ .def(self / other<amount_t>())
+ .def(other<amount_t>() / self)
.def("negated", &value_t::negated)
.def("in_place_negate", &value_t::in_place_negate)
@@ -184,15 +215,20 @@ void export_value()
.def("__abs__", &value_t::abs)
.def("rounded", &value_t::rounded)
+ .def("in_place_round", &value_t::in_place_round)
+ .def("truncated", &value_t::truncated)
+ .def("in_place_truncate", &value_t::in_place_truncate)
.def("unrounded", &value_t::unrounded)
-
+ .def("in_place_unround", &value_t::in_place_unround)
.def("reduced", &value_t::reduced)
.def("in_place_reduce", &value_t::in_place_reduce)
-
.def("unreduced", &value_t::unreduced)
.def("in_place_unreduce", &value_t::in_place_unreduce)
.def("value", &value_t::value, value_overloads())
+ .def("price", &value_t::price)
+ .def("exchange_commodities", &value_t::exchange_commodities,
+ exchange_commodities_overloads())
.def("__nonzero__", &value_t::is_nonzero)
.def("is_nonzero", &value_t::is_nonzero)
@@ -206,9 +242,6 @@ void export_value()
.def("is_boolean", &value_t::is_boolean)
.def("set_boolean", &value_t::set_boolean)
- .def("is_boolean", &value_t::is_boolean)
- .def("set_boolean", &value_t::set_boolean)
-
.def("is_datetime", &value_t::is_datetime)
.def("set_datetime", &value_t::set_datetime)
@@ -219,11 +252,17 @@ void export_value()
.def("set_long", &value_t::set_long)
.def("is_amount", &value_t::is_amount)
+ .def("is_amount", &value_t::is_amount)
+
+ .def("is_balance", &value_t::is_balance)
.def("is_balance", &value_t::is_balance)
.def("is_string", &value_t::is_string)
.def("set_string", py_set_string)
+ .def("is_mask", &value_t::is_mask)
+ .def("is_mask", &value_t::is_mask)
+
.def("is_sequence", &value_t::is_sequence)
.def("set_sequence", &value_t::set_sequence)
@@ -232,7 +271,10 @@ void export_value()
.def("__int__", &value_t::to_long)
.def("to_datetime", &value_t::to_datetime)
.def("to_date", &value_t::to_date)
+ .def("to_amount", &value_t::to_amount)
+ .def("to_balance", &value_t::to_balance)
.def("to_string", &value_t::to_string)
+ .def("to_mask", &value_t::to_mask)
.def("to_sequence", &value_t::to_sequence)
.def("__str__", py_dump_relaxed)
@@ -240,59 +282,39 @@ void export_value()
.def("casted", &value_t::casted)
.def("in_place_cast", &value_t::in_place_cast)
-
.def("simplified", &value_t::simplified)
.def("in_place_simplify", &value_t::in_place_simplify)
- // jww (2009-02-07): Allow annotating, and retrieving annotations
+ .def("annotate", &value_t::annotate)
+ .def("is_annotated", &value_t::is_annotated)
+#if 0
+ .def("annotation", &value_t::annotation)
+#endif
.def("strip_annotations", &value_t::strip_annotations)
- // jww (2009-01-28): Allow for transparent exchanging with sequence
- // protocol objects in Python too; and conversion to a list.
#if 0
- // jww (2009-02-07): Methods to implement:
- // Allow accepting and returning tuples as sequences
- // count_commodities
- // has_commodity(COMM)
- // decompose
.def("__getitem__", &value_t::operator[])
#endif
+ .def("__getattr__", py_value_getattr)
.def("push_back", &value_t::push_back)
.def("pop_back", &value_t::pop_back)
.def("size", &value_t::size)
.def("label", &value_t::label)
- .def("dump", &value_t::dump)
- .def("print", &value_t::print)
-
.def("valid", &value_t::valid)
-
- .def("__getattr__", py_value_getattr)
- ;
-
- enum_< value_t::type_t >("ValueType")
- .value("VOID", value_t::VOID)
- .value("BOOLEAN", value_t::BOOLEAN)
- .value("DATETIME", value_t::DATETIME)
- .value("DATE", value_t::DATE)
- .value("INTEGER", value_t::INTEGER)
- .value("AMOUNT", value_t::AMOUNT)
- .value("BALANCE", value_t::BALANCE)
- .value("STRING", value_t::STRING)
- .value("SEQUENCE", value_t::SEQUENCE)
- .value("SCOPE", value_t::SCOPE)
;
scope().attr("NULL_VALUE") = NULL_VALUE;
scope().attr("string_value") = &string_value;
+ scope().attr("mask_value") = &mask_value;
scope().attr("value_context") = &value_context;
register_optional_to_python<value_t>();
- implicitly_convertible<double, value_t>();
implicitly_convertible<long, value_t>();
implicitly_convertible<string, value_t>();
+ // jww (2009-11-02): ask mask objects here
implicitly_convertible<date_t, value_t>();
implicitly_convertible<datetime_t, value_t>();
diff --git a/src/py_xact.cc b/src/py_xact.cc
index b152e272..d98d226c 100644
--- a/src/py_xact.cc
+++ b/src/py_xact.cc
@@ -32,45 +32,141 @@
#include <system.hh>
#include "pyinterp.h"
+#include "pyutils.h"
+#include "xact.h"
+#include "post.h"
namespace ledger {
using namespace boost::python;
-#define EXC_TRANSLATOR(type) \
- void exc_translate_ ## type(const type& err) { \
- PyErr_SetString(PyExc_ArithmeticError, err.what()); \
+namespace {
+
+ long posts_len(xact_base_t& xact)
+ {
+ return xact.posts.size();
}
-//EXC_TRANSLATOR(xact_error)
+ post_t& posts_getitem(xact_base_t& xact, long i)
+ {
+ static long last_index = 0;
+ static xact_base_t * last_xact = NULL;
+ static posts_list::iterator elem;
+
+ long len = xact.posts.size();
+
+ if (labs(i) >= len) {
+ PyErr_SetString(PyExc_IndexError, _("Index out of range"));
+ throw_error_already_set();
+ }
+
+ if (&xact == last_xact && i == last_index + 1) {
+ last_index = i;
+ return **++elem;
+ }
+
+ long x = i < 0 ? len + i : i;
+ elem = xact.posts.begin();
+ while (--x >= 0)
+ elem++;
+
+ last_xact = &xact;
+ last_index = i;
+
+ return **elem;
+ }
+
+} // unnamed namespace
+
+using namespace boost::python;
void export_xact()
{
-#if 0
- class_< xact_base_t > ("XactBase")
- ;
- class_< xact_t > ("Xact")
- ;
- struct_< xact_finalizer_t > ("XactFinalizer")
- ;
- class_< auto_xact_t > ("AutoXact")
+ class_< xact_base_t, bases<item_t> > ("TransactionBase")
+ .add_property("journal",
+ make_getter(&xact_base_t::journal,
+ return_value_policy<reference_existing_object>()),
+ make_setter(&xact_base_t::journal,
+ with_custodian_and_ward<1, 2>()))
+ .add_property("posts",
+ make_getter(&xact_base_t::posts),
+ make_setter(&xact_base_t::posts))
+
+ .def("__len__", posts_len)
+ .def("__getitem__", posts_getitem,
+ return_value_policy<reference_existing_object>())
+
+ .def("add_post", &xact_base_t::add_post, with_custodian_and_ward<1, 2>())
+ .def("remove_post", &xact_base_t::add_post)
+
+ .def("finalize", &xact_base_t::finalize)
+ .def("valid", &xact_base_t::valid)
;
- struct_< auto_xact_finalizer_t > ("AutoXactFinalizer")
+
+ class_< xact_t, bases<xact_base_t> > ("Transaction")
+ .add_property("code",
+ make_getter(&xact_t::code),
+ make_setter(&xact_t::code))
+ .add_property("payee",
+ make_getter(&xact_t::payee),
+ make_setter(&xact_t::payee))
+
+ .def("add_post", &xact_t::add_post, with_custodian_and_ward<1, 2>())
+
+ .def("magnitude", &xact_t::magnitude)
+ .def("idstring", &xact_t::idstring)
+ .def("id", &xact_t::id)
+
+ .def("lookup", &xact_t::lookup)
+
+ .def("valid", &xact_t::valid)
;
- class_< period_xact_t > ("PeriodXact")
+
+ class_< xact_finalizer_t, boost::noncopyable >
+ ("TransactionFinalizer", no_init)
+ .def("__call__", &xact_finalizer_t::operator())
;
- class_< func_finalizer_t > ("FuncFinalizer")
+
+ class_< auto_xact_t, bases<xact_base_t> > ("AutomatedTransaction")
+ .def(init<item_predicate>())
+
+ .add_property("predicate",
+ make_getter(&auto_xact_t::predicate),
+ make_setter(&auto_xact_t::predicate))
+
+ .def("extend_xact", &auto_xact_t::extend_xact)
;
-#endif
- //register_optional_to_python<amount_t>();
+ class_< auto_xact_finalizer_t, bases<xact_finalizer_t> >
+ ("AutomatedTransactionFinalizer")
+ .add_property("journal",
+ make_getter(&auto_xact_finalizer_t::journal,
+ return_value_policy<reference_existing_object>()),
+ make_setter(&auto_xact_finalizer_t::journal,
+ with_custodian_and_ward<1, 2>()))
+ .def("__call__", &auto_xact_finalizer_t::operator())
+ ;
- //implicitly_convertible<string, amount_t>();
+ class_< period_xact_t, bases<xact_base_t> > ("PeriodicTransaction")
+ .def(init<string>())
+
+ .add_property("period",
+ make_getter(&period_xact_t::period),
+ make_setter(&period_xact_t::period))
+ .add_property("period_string",
+ make_getter(&period_xact_t::period_string),
+ make_setter(&period_xact_t::period_string))
+ ;
-#define EXC_TRANSLATE(type) \
- register_exception_translator<type>(&exc_translate_ ## type);
+ class_< func_finalizer_t, bases<xact_finalizer_t> >
+ ("FunctionalFinalizer", init<func_finalizer_t::func_t>())
+ .add_property("func",
+ make_getter(&func_finalizer_t::func),
+ make_setter(&func_finalizer_t::func))
+ .def("__call__", &func_finalizer_t::operator())
+ ;
- //EXC_TRANSLATE(xact_error);
+ scope().attr("extend_xact_base") = &extend_xact_base;
}
} // namespace ledger
diff --git a/src/pyinterp.cc b/src/pyinterp.cc
index 9ad9a906..f565f2c0 100644
--- a/src/pyinterp.cc
+++ b/src/pyinterp.cc
@@ -41,6 +41,7 @@ shared_ptr<python_interpreter_t> python_session;
char * argv0;
+void export_account();
void export_amount();
void export_balance();
void export_chain();
@@ -63,6 +64,7 @@ void export_xact();
void initialize_for_python()
{
+ export_account();
export_amount();
export_balance();
export_chain();
diff --git a/src/value.h b/src/value.h
index 3c5ce286..2ce90fa2 100644
--- a/src/value.h
+++ b/src/value.h
@@ -87,8 +87,7 @@ public:
* The sequence_t member type abstracts the type used to represent a
* resizable "array" of value_t objects.
*/
- typedef std::vector<value_t> sequence_t;
-
+ typedef std::vector<value_t> sequence_t;
typedef sequence_t::iterator iterator;
typedef sequence_t::const_iterator const_iterator;
typedef sequence_t::difference_type difference_type;
diff --git a/tools/Makefile.am b/tools/Makefile.am
index 4dd4a871..11f79050 100644
--- a/tools/Makefile.am
+++ b/tools/Makefile.am
@@ -205,6 +205,7 @@ lib_LTLIBRARIES += libledger_python.la
libledger_python_la_SOURCES = \
src/pyutils.h \
src/pyfstream.h \
+ src/py_account.cc \
src/py_amount.cc \
src/py_balance.cc \
src/py_chain.cc \