From 7b4e1d82a62da1adaa30b2868bd8fab0d6b9539e Mon Sep 17 00:00:00 2001 From: hackbard Date: Sat, 11 Oct 2014 20:39:21 +0200 Subject: [PATCH 1/1] initial go code to examine gnucash data --- gocash.go | 152 ++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 152 insertions(+) create mode 100644 gocash.go diff --git a/gocash.go b/gocash.go new file mode 100644 index 0000000..88b84d9 --- /dev/null +++ b/gocash.go @@ -0,0 +1,152 @@ +package main + +import ( + "encoding/xml" + "fmt" + "io/ioutil" + "os" +) + +type Account struct { + XMLName xml.Name `xml:"account"` + Name string `xml:"name"` + AccountId string `xml:"id"` + ParentId string `xml:"parent"` +} + +type Split struct { + XMLName xml.Name `xml:"split"` + Id string `xml:"id"` + Value string `xml:"value"` + Quantity string `xml:"quantity"` + AccountId string `xml:"account"` +} + +type Transaction struct { + XMLName xml.Name `xml:"transaction"` + Id string `xml:"id"` + Date string `xml:"date-posted>date"` + Description string `xml:"description"` + Spl []Split `xml:"splits>split"` +} + +type ParsedData struct { + XMLName xml.Name `xml:"gnc-v2"` + DataCnt []string `xml:"count-data"` + Accnt []Account `xml:"book>account"` + Trn []Transaction `xml:"book>transaction"` +} + +// 'global' data +var data ParsedData + +func main() { + + // open xml file + file, err := os.Open("c13_skr03.gnucash") + if err != nil { + fmt.Println("Error opening file:", err) + return + } + defer file.Close() + + // read xml file + xmldata, err := ioutil.ReadAll(file) + if err != nil { + fmt.Println("Error reading file:", err) + return + } + + // unmarshal xml data + err = xml.Unmarshal(xmldata,&data) + if err != nil { + fmt.Println("Error unmarshaling xml data:", err) + return + } + + // whooha, this is our data! + fmt.Println("Parsed accounts:",len(data.Accnt)) + fmt.Println("Parsed transactions:",len(data.Trn)) + + // + // hardcoded account ids we have to look at + // + // wareneingang 19% and 7% + pid_buy_n := string("8e3b7c42e3173ed85f3d4736e82afb4d") + pid_buy_s := string("0cfd2ceb45fff89b9d1b7ce3af66cdf3") + // abziehbare vst 19% and 7% + aid_vst_n := string("7c449e13125d6b93043f963628106db2") + aid_vst_s := string("006643c1c0a91f2b40614c75a49c6295") + + // account maps + type amap struct { + pid string + num int + taxval int + buy bool + tax bool + } + accnt := make(map[string]amap) + + for ac := range data.Accnt { + aid := data.Accnt[ac].AccountId + pid := data.Accnt[ac].ParentId + // general map + accnt[aid]=amap{ + pid,ac,0,false,false, + } + tmp := accnt[aid] + switch { + case pid == pid_buy_n: + tmp.taxval=19 + tmp.buy=true + accnt[aid]=tmp + //accnt[aid].taxval=19 + //accnt[aid].buy=true + case pid == pid_buy_s: + //accnt[aid].tax=7 + //accnt[aid].buy=true + case aid == aid_vst_n: + //accnt[aid].taxval=19 + //accnt[aid].buy=true + //accnt[aid].tax=true + case aid == aid_vst_s: + //accnt[aid].tax=7 + //accnt[aid].buy=true + //accnt[aid].tax=true + // there will be more assignments later on! + } + } + + // check transactions + for tc := range data.Trn { + for tsc := range data.Trn[tc].Spl { + aid := data.Trn[tc].Spl[tsc].AccountId + switch { + case accnt[aid].buy: + var ret bool + switch accnt[aid].taxval { + case 19: + ret=check_buy(&data.Trn[tc],aid_vst_n) + case 7: + ret=check_buy(&data.Trn[tc],aid_vst_s) + } + anum := accnt[aid].num + if ret == false { + fmt.Println("Problem:", data.Accnt[anum].Name) + } + } + } + } + +} + +func check_buy(ta *Transaction,id string) bool { + for sc := range ta.Spl { + if ta.Spl[sc].AccountId == id { + return true + } + } + return false +} + -- 2.39.2