carlos / platform Public

Clone
git clone https://amadan.net/carlos/platform

Plain git — no account needed to clone.

Download

Download this file

1package host
2
3import (
4 "context"
5 "crypto/ed25519"
6 "log"
7 "os"
8 "time"
9
10 "github.com/carlosframework/platform/internal/release"
11 "github.com/carlosframework/platform/internal/rootstate"
12)
13
14type rootHistoryMaintenance struct {
15 readback func(context.Context, release.HistoryBinding, func(context.Context) (release.HistoryMigrationStatus, error)) error
16 history *release.RootHistory
17 store release.Store
18 source *proofBindingSource
19 checks rootRestartChecks
20 pub func() (ed25519.PublicKey, error)
21 projection func() (rootstate.Store, error)
22 now func() time.Time
23}
24
25func (m rootHistoryMaintenance) run(ctx context.Context, b release.HistoryBinding) error {
26 resolveContext := func(ctx context.Context, want release.HistoryBinding) (string, error) {
27 _, got, _, err := m.source.unitBinding(ctx, want.Host)
28 if err != nil {
29 return "", err
30 }
31 if got.Route.Account != want.Account || got.Route.App != want.App {
32 return "", os.ErrPermission
33 }
34 return got.Source, nil
35 }
36 resolve := func(want release.HistoryBinding) (string, error) { return resolveContext(ctx, want) }
37 sources := release.HistoryRecoverySources{}
38 defer func() {
39 projection, err := m.projection()
40 if err == nil {
41 err = m.history.ProjectMigrationStatus(projection, b, resolve, sources)
42 projection.Close()
43 }
44 if err != nil {
45 log.Print(err)
46 }
47 if m.readback != nil {
48 err := m.readback(ctx, b, func(readbackCtx context.Context) (release.HistoryMigrationStatus, error) {
49 readbackResolve := func(want release.HistoryBinding) (string, error) { return resolveContext(readbackCtx, want) }
50 return m.history.MigrationStatusWithSources(b, readbackResolve, sources)
51 })
52 if err != nil {
53 log.Print(err)
54 }
55 }
56 }()
57 unresolved, err := m.checks.copyRecoveryHistory(m.history, b)
58 sources.Known, sources.Unresolved = err == nil, unresolved
59 if err != nil {
60 return err
61 }
62 pub, err := m.pub()
63 if err != nil {
64 return err
65 }
66 now := m.now()
67 if err := m.history.ReceiveReconstruction(ctx, m.store, pub, b, now, resolve); err != nil {
68 return err
69 }
70 if err := m.history.ReceiveRecoveryRetirements(ctx, m.store, pub, b, now, resolve); err != nil {
71 return err
72 }
73 return checkUnresolvedRecoveries(m.history, unresolved)
74}
75