AppManager: App installation status monitoring

Change-Id: I64f4ae0d27892b74f8827a275907cb75da09a758
diff --git a/core/installer/status/background.go b/core/installer/status/background.go
new file mode 100644
index 0000000..bebffde
--- /dev/null
+++ b/core/installer/status/background.go
@@ -0,0 +1,47 @@
+package status
+
+import (
+	"sync"
+	"time"
+)
+
+type ste struct {
+	status Status
+	error  error
+}
+
+type backgroundMonitor struct {
+	l        sync.Locker
+	m        ResourceMonitor
+	interval time.Duration
+	cache    map[ResourceRef]ste
+}
+
+func NewBackgroundMonitor(m ResourceMonitor, interval time.Duration) ResourceMonitor {
+	return &backgroundMonitor{
+		&sync.Mutex{},
+		m,
+		interval,
+		map[ResourceRef]ste{},
+	}
+}
+
+func (m *backgroundMonitor) Get(ref ResourceRef) (Status, error) {
+	m.l.Lock()
+	defer m.l.Unlock()
+	if ret, ok := m.cache[ref]; ok {
+		return ret.status, ret.error
+	}
+	m.cache[ref] = ste{StatusNotFound, nil}
+	go func() {
+		st, err := m.m.Get(ref)
+		m.l.Lock()
+		m.cache[ref] = ste{st, err}
+		m.l.Unlock()
+		if IsStatusTerminal(st) {
+			return
+		}
+		time.Sleep(m.interval)
+	}()
+	return StatusNotFound, nil
+}