TomKivy
TomKivy

Reputation: 408

Kivy storage JsonStore: can't make async saving to work (the async.put method)

I made some small kivy app that shows the content of a json-file on disc. I made some buttons that increase the values in the json-file and this works fine. The label shows the updated values of the file. The problem is that I want to do the same thing the asynchronous way (for reasons of economy). Unfortunately I can't figure that one out. The documentation on the storage module ([http://kivy.org/docs/api-kivy.storage.html][1]) is very short and I didn't find any example. Here is my code, the commented out sections need fixing and any other tips on storage are more than welcome!

import kivy
kivy.require('1.9.1')

from kivy.uix.boxlayout import BoxLayout
from kivy.uix.gridlayout import GridLayout

from kivy.uix.button import Button
from kivy.uix.label import Label
from kivy.storage.jsonstore import JsonStore
from kivy.app import App
from kivy.clock import Clock
from functools import partial

# The initial content of the json file
initial_user_stats = {"words":{"word1":{"tries":0,"succes":0},"word2":{"tries":0,"succes":0}}}

#let's imagine John logged in and a json file is created on disc
user_stats = JsonStore ("john.json")
user_stats["words"]=initial_user_stats["words"]


class MyQuizScreen(BoxLayout):
    def __init__(self, **kwargs):
        super(MyQuizScreen, self).__init__(**kwargs)
        self.orientation = "vertical"
        self.spacing = "4dp"
        self.content_label = Label(halign = "center", font_size = "16dp", size_hint_y = .25) 
        self.add_widget(self.content_label)
        grid = GridLayout(cols = 2)
        grid.add_widget(Button(text="increase 'tries'\nof word 1\n(synchronous)", on_press = partial(self.sync_button_callback, "word1", "tries")))
        grid.add_widget(Button(text="increase 'succes'\nof word 1\n(synchronous)", on_press = partial(self.sync_button_callback, "word1", "succes")))
        grid.add_widget(Button(text="increase 'tries'\nof word 2\n(synchronous)", on_press = partial(self.sync_button_callback, "word2", "tries")))
        grid.add_widget(Button(text="increase 'succes'\nof word 2\n(synchronous)", on_press = partial(self.sync_button_callback, "word2", "succes")))

        #The next lines were not working, I couldn't figure out the async way of doing things (now it works in 1.9.1)

        grid.add_widget(Button(text="increase 'tries'\nof word 1\n(a_synchronous)",on_press = partial(self.async_button_callback, "word1", "tries")))
        grid.add_widget(Button(text="increase 'succes'\nof word 1\n(a_synchronous)", on_press = partial(self.async_button_callback, "word1", "succes")))
        grid.add_widget(Button(text="increase 'tries'\nof word 2\n(na_synchronous)", on_press = partial(self.async_button_callback, "word2", "tries")))
        grid.add_widget(Button(text="increase 'succes'\nof word 2\n(a_synchronous)", on_press = partial(self.async_button_callback, "word2", "succes")))
        self.add_widget(grid)

        Clock.schedule_interval(self.update_text_label, .2)

    def sync_button_callback(self, key, subkey, button):
        user_stats["words"][key][subkey] += 1
        user_stats.put("words", **user_stats["words"]) 

    def async_button_callback(self, key, subkey, button):
        # Here the error occured
        user_stats["words"][key][subkey] += 1
        user_stats.async_put(self.my_async_callback, "words", **user_stats["words"])

    def my_async_callback(self, store, key, result):
        print "store:", store
        print "key:", key
        print "result", result

    def update_text_label(self,*args):
        stats_dict = dict (user_stats)
        x = stats_dict.items()
        self.content_label.text = "The json file on disc:\n\n" + str(x)
        self.content_label.text_size = self.content_label.size


class QuizApp(App):
    def build(self):
        root = MyQuizScreen()
        return root

if __name__ == '__main__':
    QuizApp().run()

Upvotes: 0

Views: 277

Answers (1)

TomKivy
TomKivy

Reputation: 408

According to a developer on irc chat it is a bug in kivy 1.9.0 and only the sync methods should be used (april 13th 2015). So the code above is working (as the async methods are commented out).

Upvotes: 1

Related Questions