feat(plantare): reproduction-commitment data layer (schema v9)
The Plantare — a promise to reproduce seed and return some (data-model §2.7, the seed-domain Pledge with return_kind=similar). NOT a sale. Local-first v1: your honest ledger of commitments (from/to a person by name); the bilateral signed cross-party form is a later social-layer phase. - New Plantares table (SyncColumns): varietyId, direction (iReturn/owedToMe), counterparty, owedDescription, madeOn, dueBy, status (open/returned/ forgiven), settledOn, note. schemaVersion 8 -> 9 with a guarded createTable migration; schema exported + migration-test helper regenerated. - VarietyRepository: createPlantare / watchPlantares / watchPlantaresForVariety / setPlantareStatus / deletePlantare (soft-delete, CRDT-stamped). - Included in backups + sync: InventorySnapshot + JSON codec (round-trips isDeleted) + exportInventory/exportForSync/importInventory, so commitments survive restore and replicate LWW like every other row. Tests: v1..v8 -> v9 migration + fresh v9; repo create/list/settle/reopen/ delete; and a backup round-trip preserving a commitment. 13 green. UI (detail section + Plantares screen) follows.
This commit is contained in:
parent
0e41293de5
commit
81094f25a8
12 changed files with 5418 additions and 60 deletions
|
|
@ -22,6 +22,7 @@ part 'database.g.dart';
|
|||
Parties,
|
||||
Attachments,
|
||||
ExternalLinks,
|
||||
Plantares,
|
||||
],
|
||||
)
|
||||
class AppDatabase extends _$AppDatabase {
|
||||
|
|
@ -29,7 +30,7 @@ class AppDatabase extends _$AppDatabase {
|
|||
|
||||
/// Current schema version; also stamped into interchange exports so an
|
||||
/// importer knows which app generation wrote the file (data-model §7).
|
||||
static const int currentSchemaVersion = 8;
|
||||
static const int currentSchemaVersion = 9;
|
||||
|
||||
@override
|
||||
int get schemaVersion => currentSchemaVersion;
|
||||
|
|
@ -138,6 +139,13 @@ class AppDatabase extends _$AppDatabase {
|
|||
await m.createTable(conditionChecks);
|
||||
}
|
||||
}
|
||||
// v9: Plantares — reproduction commitments (data-model §2.7). Guarded so a
|
||||
// half-migrated dev database re-runs cleanly (see the v7 note above).
|
||||
if (from < 9) {
|
||||
if (!await _hasTable('plantares')) {
|
||||
await m.createTable(plantares);
|
||||
}
|
||||
}
|
||||
},
|
||||
);
|
||||
|
||||
|
|
|
|||
File diff suppressed because it is too large
Load diff
|
|
@ -86,3 +86,18 @@ enum AttachmentKind { photo, doc }
|
|||
|
||||
/// Polymorphic parent of an Attachment / ExternalLink.
|
||||
enum ParentType { variety, lot, movement }
|
||||
|
||||
/// Whose reproduction promise a Plantare is, seen from this app's owner
|
||||
/// (data-model §2.7). A Plantare is a commitment to REPRODUCE and return seed —
|
||||
/// not a sale.
|
||||
enum PlantareDirection {
|
||||
/// I received seed and promised to grow it out and return some.
|
||||
iReturn,
|
||||
|
||||
/// I gave seed and the other person promised to return some.
|
||||
owedToMe,
|
||||
}
|
||||
|
||||
/// Lifecycle of a Plantare. Framed as a promise, not a debt (data-model §2.7):
|
||||
/// `forgiven` (not "defaulted") when it's let go.
|
||||
enum PlantareStatus { open, returned, forgiven }
|
||||
|
|
|
|||
|
|
@ -173,6 +173,45 @@ class Attachments extends Table with SyncColumns {
|
|||
IntColumn get sortOrder => integer().withDefault(const Constant(0))();
|
||||
}
|
||||
|
||||
/// A Plantare — a REPRODUCTION commitment (data-model §2.7), the seed-domain
|
||||
/// name for the generic `Pledge` (`return_kind = similar`). Seed changes hands
|
||||
/// and the receiver promises to grow it out and return some. NOT a sale.
|
||||
///
|
||||
/// Local-first v1: your own honest ledger of commitments (from/to a person by
|
||||
/// name). The bilateral, cryptographically SIGNED, cross-party form
|
||||
/// (debtor/creditor keys + both signatures, tied to a shared `Movement`) is a
|
||||
/// later social-layer phase — those columns are deferred, not invented now.
|
||||
class Plantares extends Table with SyncColumns {
|
||||
/// The seed the commitment is about — what gets reproduced. Nullable so a
|
||||
/// commitment can be jotted before it's linked to a catalogued variety.
|
||||
TextColumn get varietyId => text().nullable()(); // → Variety
|
||||
|
||||
/// Whose promise it is (I return / owed to me).
|
||||
TextColumn get direction => textEnum<PlantareDirection>()();
|
||||
|
||||
/// The other party as a human name (v1). A key/Party link arrives with the
|
||||
/// signed cross-party form.
|
||||
TextColumn get counterparty => text().nullable()();
|
||||
|
||||
/// What's promised back, in the grower's own words
|
||||
/// ("un puñado la próxima temporada").
|
||||
TextColumn get owedDescription => text().nullable()();
|
||||
|
||||
/// When the promise was made (ms since epoch).
|
||||
IntColumn get madeOn => integer()();
|
||||
|
||||
/// Optional return-by date (ms since epoch) — a gentle reminder, not a deadline.
|
||||
IntColumn get dueBy => integer().nullable()();
|
||||
|
||||
TextColumn get status =>
|
||||
textEnum<PlantareStatus>().withDefault(const Constant('open'))();
|
||||
|
||||
/// When it was returned or forgiven (ms since epoch).
|
||||
IntColumn get settledOn => integer().nullable()();
|
||||
|
||||
TextColumn get note => text().nullable()();
|
||||
}
|
||||
|
||||
/// Any pasted URL (Wikipedia, forum…). Polymorphic parent.
|
||||
class ExternalLinks extends Table with SyncColumns {
|
||||
TextColumn get parentType => textEnum<ParentType>()();
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue