The Charitable Cause module enables crowdfunding projects: organizations or individuals register a cause (funding target, regulations, benefit), assign managers, and receive donations. User-facing endpoints live in CharitableCauseController (/charitable-causes) for CRUD + assign manager. Admin endpoints live in CharitableCauseAdminController for summary, cause approval, and allocation of open donations (donations without a specific cause) to ACTIVE causes.
Property Value Base URL {HOST}/v1Auth Bearer JWT (header Authorization) or cookie access_token Content-Type application/jsonError envelope { "message": string | string[], "statusCode": number, "error": string }Validation Global ValidationPipe · whitelist: true, forbidNonWhitelisted: true · unknown field → 400 Related modules accounts, users, organizations, payments, transactions Document version v1 · 2026-05-20 Audience Internal FE devs (mobile + web)
Typical flow: create cause → platform admin approves → donor contributes via the payments module (donation flow) → the creator may assign additional managers . Donations without a specific cause (type OPEN) are pooled and allocated by MORIA superadmin via the admin endpoint POST /donations/allocate.
Method Path Auth Summary GET /v1/charitable-causesbearer List causes (scoped by role) GET /v1/charitable-causes/:idbearer Detail of a single cause POST /v1/charitable-causesbearer Create a new cause PATCH /v1/charitable-causes/:idbearer Update a cause DELETE /v1/charitable-causes/:idbearer Deactivate (soft-cancel) POST /v1/charitable-causes/:id/assign-managerbearer Assign an additional manager GET /v1/summary/charitable-causesbearer Statistics summary (admin) GET /v1/donations/openbearer List open donations (MORIA only) POST /v1/donations/allocatebearer Allocate a batch of open donations to a cause (MORIA only) PATCH /v1/charitable-causes/:id/approvebearer Approve a cause (MORIA only)
Auth + scope notes
User endpoints require Bearer + permission read-/create-/update-/delete-charitable-cause. Admin endpoints require role MORIA or ORGANIZATION + additional permissions.
Initial cause status: pending until a MORIA admin performs approve.
OPEN donations (donors that did not pick a specific cause) are listed via GET /donations/open and allocated to ACTIVE causes in batches — atomic, all donations must be valid or the entire batch is rolled back.
Paginated list of causes. Scope depends on role: INDIVIDUAL sees causes tied to their account (or marketplace via organization_id); ORGANIZATION admin sees the org’s causes; MORIA sees all.
bearer
read-charitable-cause
Param Type Default Notes pagenumber 1Page number limitnumber 10Records per page statusenum CharitableCauseStatus optional Status filter; all means no filter order'asc' | 'desc'descSort by created_at organization_idstring (UUID) optional Marketplace lookup; INDIVIDUAL may only use their own organization user_idstring (UUID) optional User filter; layered authorization account_idstring (UUID) optional Account filter; layered authorization
"message" : " Causes fetched successfully " ,
"id" : " 550e8400-e29b-41d4-a716-446655440000 " ,
"name" : " Bantu Korban Banjir " ,
"target_amount" : 10000000 ,
"current_amount" : 2500000 ,
"owner_type" : " organization " ,
"organization_id" : " 660e8400-e29b-41d4-a716-446655440111 " ,
"account_id" : " be2cb7da-e217-401c-8d07-b01e64adfb34 "
Status When it occurs 401 UnauthorizedBearer/cookie token invalid 403 ForbiddenWrong scope (see auth notes)
Detail of a single cause. Response format differs between MOBILE (raw) and WEB (formatted with aggregation). Scope organization_id is passed from the user.
bearer
read-charitable-cause
Param Type Notes idUUID Cause ID
"message" : " Cause retrieved successfully " ,
"id" : " 550e8400-e29b-41d4-a716-446655440000 " ,
"name" : " Bantu Korban Banjir " ,
"description" : " Bantuan untuk korban banjir Jakarta " ,
"target_amount" : 10000000 ,
"current_amount" : 2500000 ,
"location" : " Jakarta, Indonesia " ,
"owner_type" : " organization " ,
"managers" : [ { "user_id" : " ... " , "role" : " manager " } ]
Status When it occurs 400 Bad Requestid is not a UUID401 UnauthorizedBearer/cookie token invalid 403 ForbiddenNo access to the cause 404 Not FoundCause not found
Create a new cause. The initial status is pending until a MORIA admin approves it. The organization_id field is only for MORIA superadmins creating on behalf of an organization.
bearer
create-charitable-cause
RESOURCE_CREATED
Field Type Required Notes account_idstring (UUID) ✓ Account that will receive donations descriptionstring ✓ Cause description currencystring optional Currency (default IDR) target_amountnumber ✓ Funding target (number, not string) regulationsstring ✓ Cause regulations & terms benefitstring ✓ Cause benefit & impact namestring ✓ Cause name locationstring optional Cause location (e.g. Jakarta, Indonesia) organization_idstring optional Only MORIA may send this — create on behalf of someone else
"account_id" : " be2cb7da-e217-401c-8d07-b01e64adfb34 " ,
"name" : " Bantu Korban Banjir " ,
"description" : " Bantuan untuk korban banjir Jakarta " ,
"target_amount" : 10000000 ,
"regulations" : " Dana digunakan untuk kebutuhan pokok korban " ,
"benefit" : " Membantu 500 keluarga terdampak " ,
"location" : " Jakarta, Indonesia "
"message" : " Cause created successfully " ,
"id" : " 550e8400-e29b-41d4-a716-446655440000 " ,
"name" : " Bantu Korban Banjir " ,
"target_amount" : 10000000 ,
Status When it occurs 400 Bad RequestValidation failed (non-numeric target_amount, required field empty) 401 UnauthorizedBearer/cookie token invalid 403 ForbiddenMissing create-charitable-cause permission
Update a cause. Only the creator or a manager may perform this. All fields are optional.
bearer
update-charitable-cause
RESOURCE_UPDATED
Param Type Notes idUUID Cause ID
Field Type Notes descriptionstring New description currencystring Currency target_amountnumber New funding target regulationsstring New regulations benefitstring New benefit namestring New name statusenum CharitableCauseStatus New status
{ "name" : " Bantu Korban Banjir 2026 " , "target_amount" : 15000000 }
"message" : " Cause updated successfully " ,
"data" : { "..." : " CauseDto shape " }
Status When it occurs 400 Bad RequestValidation failed 401 UnauthorizedBearer/cookie token invalid 403 ForbiddenNot the creator/manager 404 Not FoundCause not found
Deactivate a cause (soft-cancel). Status changes to deactivated; the row is not removed and donations already received are not refunded.
bearer
delete-charitable-cause
RESOURCE_DELETED
Param Type Notes idUUID Cause ID
"message" : " Cause cancelled successfully " ,
"data" : { "..." : " CauseDto shape, status='deactivated' " }
Status When it occurs 401 UnauthorizedBearer/cookie token invalid 403 ForbiddenNot the creator 404 Not FoundCause not found
Designate another user as a manager of the cause. Only the creator is allowed — additional managers may update the cause but may not assign further managers.
bearer
update-charitable-cause
Param Type Notes idUUID Cause ID
Field Type Required Notes user_idstring (UUID) ✓ ID of the user to become a manager
{ "user_id" : " be2cb7da-e217-401c-8d07-b01e64adfb34 " }
"message" : " Manager assigned successfully " ,
"data" : { "manager" : { "user_id" : " ... " , "cause_id" : " ... " } }
Status When it occurs 400 Bad RequestUser is already a manager of this cause 401 UnauthorizedBearer/cookie token invalid 403 ForbiddenNot the creator (only the creator may assign) 404 Not FoundCause or user not found
Cause statistics summary for the caller’s organization. Admin endpoint (MORIA / ORGANIZATION). MORIA can also view summaries across organizations.
bearer
MORIA, ORGANIZATION
read-charitable-cause
"message" : " charitable cause summary fetched successfully " ,
"organization_id" : " 660e8400-e29b-41d4-a716-446655440111 " ,
"organization_name" : " Moria Fund " ,
"total_target_amount" : " 100000000.00 " ,
"total_collected_amount" : " 65000000.00 "
Status When it occurs 401 UnauthorizedToken invalid / querying another org (mismatch) 403 ForbiddenRole is not MORIA/ORGANIZATION
List OPEN donations not yet allocated to a specific cause. MORIA superadmin only — typically used to allocate donations to causes in need.
bearer
MORIA
allocate-open-donation
RESOURCE_UPDATED
Param Type Default Notes pagenumber 1Page number limitnumber 20Records per page
"message" : " Unallocated open donations fetched " ,
"id" : " be2cb7da-e217-401c-8d07-b01e64adfb34 " ,
"created_at" : " 2026-05-20T08:30:00.000Z "
Status When it occurs 401 UnauthorizedBearer/cookie token invalid 403 ForbiddenNot MORIA superadmin
Allocate a batch of OPEN donations to a single active cause. Atomic — if any donation is invalid (already allocated / cause not active), the entire batch is rolled back.
bearer
MORIA
allocate-open-donation
RESOURCE_UPDATED
Field Type Required Notes donation_idsstring[] (UUID) ✓ List of donations to allocate — all must be OPEN, not yet allocated, and exist cause_idstring (UUID) ✓ Target cause; must be in status ACTIVE
" be2cb7da-e217-401c-8d07-b01e64adfb34 " ,
" a1f2c3d4-5678-90ab-cdef-1234567890ab "
"cause_id" : " 550e8400-e29b-41d4-a716-446655440000 "
"message" : " Donations allocated " ,
"data" : { "allocated_count" : 2 , "cause_id" : " 550e8400-e29b-41d4-a716-446655440000 " }
Status When it occurs 400 Bad RequestSome donations are non-OPEN / already allocated / cause not active 401 UnauthorizedBearer/cookie token invalid 403 ForbiddenNot MORIA superadmin 404 Not FoundDonation or cause not found
Approve a cause currently in pending. MORIA superadmin only. After approval, the status moves to approved / active per the service logic.
bearer
MORIA
approve-charitable-cause
RESOURCE_UPDATED
Param Type Notes idUUID Cause ID
"message" : " Cause approved successfully " ,
"data" : { "..." : " CauseDto shape, status='active' " }
Status When it occurs 400 Bad RequestCause was already approved 401 UnauthorizedBearer/cookie token invalid 403 ForbiddenNot MORIA superadmin 404 Not FoundCause not found
pending — awaiting MORIA approval
new — newly created (internal variant)
active — accepting donations
approved — approved by admin
in_progress — disbursement in progress
completed — target reached / finished
cancelled — cancelled
rejected — approval rejected
deactivated — soft-cancelled
all — filter sentinel (no filter)
specific — donor picks the cause
open — no cause, allocated by admin
subscription — recurring
organization · individual · moria
"message" : " target_amount must be a number " ,
400 validation · donation already allocated · cause already approved
401 token expired / missing
403 not creator/manager · not MORIA
404 cause/donation not found
500 internal — show a generic toast