Skip to content

feat: deliver Concord Coston2 MVP and product handoff - #1

Merged
etvjay merged 108 commits into
mainfrom
agent/concord-rebuild
Aug 14, 2026
Merged

etvjay merged 108 commits into
mainfrom
agent/concord-rebuild

Conversation

@etvjay

@etvjay etvjay commented Aug 12, 2026 •

Copy link
Copy Markdown
Owner

Concord Coston2 MVP and judge handoff

Concord coordinates a persistent FXRP-backed syndicated capital facility on Flare Coston2:

  • AccordRegistry and CapitalFacility record Root Accord → Child Accord lineage, funding, multi-child draw legs, repayment, and restored capacity.
  • The official Flare FCC scaffold validates signed provider quotes and deterministic lowest-fee-first CoFill.
  • The shared SDK, REST/OpenAPI, CLI, MCP, and existing React frontend use the same unsigned-intent and evidence model.
  • The implementation and docs now explain Accord, Makkari, CoFill, FCC proxy, TEE, and Redis in plain language.

Recorded Coston2 proof

The canonical evidence is in config/coston2/concord-deployment.json:

  • Chain 114 with current six-decimal Coston2 USDT0 test token.
  • AccordRegistry: 0x68b19a3967760489b57341669cd7ea960b5f7367
  • CapitalFacility: 0xfaff601a18a9fca33378953515aa0f3ef9286ecd
  • FCC extension 66188 and the recorded simulated-development TEE path.
  • Three funded Child Accords, a 4 USDT0 multi-child draw, repayment, and restored 9 USDT0 capacity.
  • FCC run 31733200629, recovery run 31733740564, and lifecycle run 31734593116.

Validation for this head

Head: 2147ec8

Current hosted development checkpoint

Northflank project concord in europe-west runs concord-fcc-proxy, concord-fcc-tee, and private Redis concord-redis. The Worker relay and direct proxy both return HTTP 200 for /info, extension 66188, chain ID 114:

The current simulated identity 0xb1e7a4c1930f1f3c4905b34fafc9c1b8359029a5 is ephemeral and not yet registered onchain. No registration, availability, pause, dispatch, or other Coston2 broadcast was made for it. The stale PRODUCTION record remains untouched. The frontend has no public deployment URL yet and remains a separate next pass.

This change preserves the no-write gate: registration, stale-machine pause, and any live FCC dispatch require separate explicit operator confirmation.

Post-merge cleanup

Main is now 113a34b. Manual workflows, Northflank source refs, and frontend documentation links target main; the deleted feature branch and superseded local branch are no longer part of the handoff. Frontend behavior and deployment remain a separate next pass.

@etvjay etvjay changed the title feat: rebuild Concord MVP foundation feat: build Concord MVP foundation and integration surfaces Aug 12, 2026
@etvjay etvjay changed the title feat: build Concord MVP foundation and integration surfaces feat: deliver Concord Coston2 MVP and product handoff Aug 14, 2026
@etvjay
etvjay marked this pull request as ready for review August 14, 2026 18:48
@etvjay
etvjay merged commit 55614f7 into main Aug 14, 2026
30 checks passed
@etvjay
etvjay deleted the agent/concord-rebuild branch August 14, 2026 18:49

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 2147ec8517

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

function draw(bytes32 drawId, bytes32 rootId, uint256 amount) external nonReentrant {
ConcordTypes.RootAccord storage root = _root(rootId);
if (msg.sender != root.borrower) revert Unauthorized();
if (root.state != ConcordTypes.RootState.ACTIVE || amount == 0) revert InvalidState();

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Enforce accord expiry before allowing draws

When block.timestamp passes either root.validUntil or an active child's validUntil, the stored state remains ACTIVE until someone separately calls an expiry function, so this check and the child-selection loop still permit a draw. The resulting nonzero drawnPrincipal then prevents expireChild from returning the provider's funds, extending exposure beyond the agreed validity boundary; reject draws after root expiry and exclude expired children from allocation.

Useful? React with 👍 / 👎.

Comment on lines +199 to +200
if err == nil {
e.finalized[round] = true

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Authenticate finalization before making it irreversible

Because ConcordInstructionSender.sendFinalizeRound is public and this handler does not authenticate the action sender or bind the request fields to on-chain round state, any caller can omit Quotes, provide a small target and permissive public round parameters, and successfully finalize once any stored quote can cover that target. The downstream verifier will reject that altered result, but this assignment permanently makes the legitimate finalization return "already been finalized," allowing an untrusted caller to deny service for the round.

Useful? React with 👍 / 👎.

Comment on lines +149 to +150
if req.EvaluationTime == 0 {
req.EvaluationTime = uint64(time.Now().Unix())

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Evaluate quote expiry using trusted current time

A nonzero EvaluationTime is accepted directly from the finalization payload and later used to validate every quote's ValidUntil. A quote can therefore expire after submission while the finalizer supplies an earlier timestamp and still receives a successful allocation; since evaluation time is absent from the result digest, the on-chain verification path cannot detect that stale offer. Ignore caller-supplied time and evaluate against a trusted TEE or chain timestamp.

Useful? React with 👍 / 👎.

Comment on lines +131 to +136
e.mu.Lock()
key := roundKey(req.RoundID)
if e.quotes[key] == nil {
e.quotes[key] = make(map[string]types.QuoteRequest)
}
e.quotes[key][provider] = req

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Reject quote submissions after finalization begins

If a provider submits while finalizing[round] is set, or at any time after finalized[round] becomes true, this write still returns Accepted: true; the in-progress finalization already captured its snapshot, and a later finalization is forbidden. The provider is therefore told its quote was accepted even though it can never participate in the round, so check both lifecycle flags under this lock before storing the quote.

Useful? React with 👍 / 👎.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants