Scenario: Run a fixed asset from acquisition to disposal
Goal. Your asset register, procurement or lease system drives a fixed asset through its life in Dynamics 365: it posts the acquisition of an asset book, runs the depreciation proposal for the period, posts the adjustments, depreciation, revaluations and write-downs it decides, moves the asset to another department or location, splits off part of it, reverses a posting made in error, and finally posts the disposal of the asset by sale or by scrap, then reads the transactions back to confirm them.
When to use. Capitalizing assets bought outside D365, period-end depreciation driven by an external close calendar, impairments and revaluations decided in the register, reorganizations that move assets between departments or sites, and retirements decided outside D365. For plain ledger entries use General and intercompany journals; for a fixed asset journal that was entered or imported in D365 and only needs posting, see Post an existing journal; for the retry-safe calling pattern, see Post a journal exactly-once.
Prerequisites
-
Security.
postAcquisition,runDepreciationProposal,postAssetTransaction,transferAssetandsplitAsset: privilegeMGCLatticeFixedAssetsServiceMaintain, in dutyMGCLatticeIntegrationServiceOperationsDuty(operator and administrator roles).postDisposal: privilegeMGCLatticeFixedAssetsDisposalMaintain, in the high-risk dutyMGCLatticeIntegrationServiceHighRiskDuty, held only byMGCLatticeIntegrationAdministratorRole.reverseAssetTransaction: privilegeMGCLatticeFixedAssetsReverseMaintain("Fixed assets - reverse transactions (high-risk)"), in the same high-risk duty. Posting a transaction does not grant reversing it.
A call without the privilege is refused by D365 with HTTP 403.
-
Fixed asset setup in the legal entity.
- A ledger journal name of type Fixed assets with a voucher number sequence (General ledger >
Journal setup > Journal names), on the posting layer of the books you post. USMF:
FACur(current layer). - A fixed asset group (Fixed assets > Setup > Fixed asset groups), a book (Fixed assets > Setup >
Books) and a posting profile with the accounts of every transaction type you post (acquisition,
depreciation, adjustments, revaluation, write-up and write-down, extraordinary and bonus depreciation) and the
sale and scrap setup on its Disposal tab (Fixed assets > Setup > Fixed asset posting profiles).
USMF: group
COMP, book200_SLLR(current layer, depreciation profile200%), posting profileALL, which has accounts for every type except bonus depreciation. - An offset main account that allows manual entry for the acquisition cost and the sale proceeds.
USMF:
110110Bank Account - USD. - An open ledger period for the dates you post.
- Transfers: the transfer number sequence (Fixed assets > Setup > Fixed assets parameters, Number
sequences), and the dimension values and locations you move to (USMF: department
023, locationPROD). - Splits into a new asset: automatic numbering on the asset group, since the split creates the receiving asset.
- Reversals: the reversal voucher and trace number sequences in the general ledger parameters (General ledger > Ledger setup > General ledger parameters, Number sequences; USMF has them).
- A ledger journal name of type Fixed assets with a voucher number sequence (General ledger >
Journal setup > Journal names), on the posting layer of the books you post. USMF:
-
The asset and its book exist. Lattice posts transactions for an asset; it does not create the asset (except the receiving asset of a split). Create it on Fixed assets > Fixed assets > Fixed assets, or with the standard OData entities (step 1).
-
Lattice. A valid license (a never-registered environment is allowed through; an adverse verdict refuses posting with
LicenseNotValid). If your system knows the asset by its own key, register it as a cross-reference and sendAssetIdExternalKeywithExternalSysteminstead ofAssetId(on every operation here; a split also takesToAssetIdExternalKey); see Cross-reference keys.
Steps
The operations are on MGCLatticeFixedAssetService in service group
MGCLatticeFixedAssetsServiceGroup. Send a POST with an OAuth 2.0 bearer token and the request in
_request (see Trial and day-one guide).
-
Create the asset and attach its book (if it does not exist yet). Create the asset in its group with the standard
FixedAssetsV2entity, then attach the book withFixedAssetBooksV2:POST https://<your-environment>/data/FixedAssetsV2{ "FixedAssetGroupId": "COMP", "Name": "Engineering workstation", "dataAreaId": "USMF" }The response carries the new
FixedAssetNumber(from the group's number sequence). Then:POST https://<your-environment>/data/FixedAssetBooksV2{"FixedAssetNumber": "COMP-000001","BookId": "200_SLLR","PostingProfileId": "ALL","DepreciationProfileId": "200%","ServiceLife": 5,"dataAreaId": "USMF"} -
Post the acquisition.
postAcquisitioncreates a fixed asset journal with one acquisition line per request line and posts it:POST https://<your-environment>/api/services/MGCLatticeFixedAssetsServiceGroup/MGCLatticeFixedAssetService/postAcquisition{"_request": {"RequestId": "5e6f7a8b-9c0d-4e1f-8a2b-3c4d5e6f7a8b","LegalEntityId": "USMF","UserContext": "asset-register","JournalNameId": "FACur","Description": "Workstation acquisition","PostingDate": "2026-10-15","Lines": [{"AssetId": "COMP-000001","AssetBookId": "200_SLLR","AcquisitionAmount": 15000.00,"CurrencyCode": "USD","OffsetMainAccountId": "110110","Description": "Workstation"}]}}Every line needs
AssetId,AssetBookIdand a non-zeroAcquisitionAmount;CurrencyCodedefaults to the accounting currency. The answer:Successtrue,DocumentId=PostedDocumentId= the journal number, message "Fixed asset acquisition journal ... posted." The book is now acquired. Each line posts to the book it names only: the book's derived books do not receive the acquisition, so send a line for every book you acquire. -
Run the depreciation proposal.
runDepreciationProposalruns the standard depreciation proposal (the fixed asset journal's Proposals > Depreciation proposal) into a new fixed asset journal, one line per asset book with depreciation due throughDepreciationDate:POST https://<your-environment>/api/services/MGCLatticeFixedAssetsServiceGroup/MGCLatticeFixedAssetService/runDepreciationProposal{"_request": {"RequestId": "7a8b9c0d-1e2f-4a3b-8c4d-5e6f7a8b9c0d","LegalEntityId": "USMF","UserContext": "asset-register","JournalNameId": "FACur","AssetBookId": "200_SLLR","DepreciationDate": "2026-10-31"}}The proposal covers every asset of the book (every book when
AssetBookIdis empty), not only yours, and the journal is not posted.DocumentId=PostedDocumentId= the proposal journal number. The message gives the count ("Depreciation proposal journal ... was created through ... with N proposed line(s). The journal is not posted.") or says nothing was due ("... has no lines: no fixed asset book in the selection has depreciation due."); an asset acquired in the current period often has nothing due yet. Review and post the journal in D365: Fixed assets > Journal entries > Fixed assets journal, select the journal number, open Lines, check the proposed amounts and click Post; or post it withpostLedgerJournal(Post an existing journal). An empty proposal journal can be deleted there. -
Post depreciation, adjustments and revaluations.
postAssetTransactionposts the transactions after acquisition that your register decides, in a new fixed asset journal, as the fixed asset journal page posts them:POST https://<your-environment>/api/services/MGCLatticeFixedAssetsServiceGroup/MGCLatticeFixedAssetService/postAssetTransaction{"_request": {"RequestId": "2d4f6a8c-0e1b-4c3d-9e5f-7a9b1c3d5e7f","LegalEntityId": "USMF","UserContext": "asset-register","JournalNameId": "FACur","Description": "October impairment","PostingDate": "2026-10-31","Lines": [{ "AssetId": "COMP-000001", "AssetBookId": "200_SLLR", "TransactionType": "Depreciation", "CreditAmount": 250.00 },{ "AssetId": "COMP-000001", "AssetBookId": "200_SLLR", "TransactionType": "WriteDownAdj", "CreditAmount": 500.00,"Dimensions": [ { "DimensionName": "Department", "DimensionValue": "023" } ] }]}}TransactionTypePosts AcquisitionAdjAn acquisition adjustment Depreciation,DepreciationAdjDepreciation, a depreciation adjustment ExtraordinaryDepreciation,BonusDepreciationExtraordinary or bonus depreciation RevaluationA revaluation, where the book allows it WriteUpAdj,WriteDownAdjA write-up or write-down adjustment - The type names are not case-sensitive. Acquisitions are posted with
postAcquisition(step 2), disposals withpostDisposal(step 8); any other type is refused. - Each line has exactly one amount, greater than zero, in the accounting currency:
DebitAmountincreases the book's value,CreditAmountdecreases it (a depreciation or a write-down is a credit). - The book's posting profile gives the account and the offset account of the type unless the line sends
OffsetMainAccountId; the line takes the book's financial dimensions, andDimensionsreplaces the ones you name.TransactionDatedefaults toPostingDate(today).ReasonCodeandReasonCommentcarry a financial reason, which the fixed asset parameters can require per type;ConsumptionQuantityis the consumption of a depreciation line on a book that depreciates by consumption. - The depreciation types need a book that depreciates. The derived books of a line's book take the transaction as the fixed asset journal passes it to them, except a derived book that is not acquired.
- A line whose type has no account (or no offset account) in the book's posting profile is refused with
ConfigurationMissingbefore any journal is created. USMF's profileALLhas no bonus depreciation accounts, soBonusDepreciationis refused there until you add them.
The answer:
DocumentIdis the posted journal,PostedDocumentIdthe voucher of its first line, and the message lists every voucher: "Fixed asset journal ... posted with 2 line(s), voucher(s) ...". A journal that does not post is deleted again. - The type names are not case-sensitive. Acquisitions are posted with
-
Move the asset to another department or location.
transferAssetruns the standard asset transfer (the fixed asset page's Transfer asset) and posts what it creates:{"_request": {"RequestId": "4f6b8d0f-2a3c-4e5d-8f7a-9b1d3f5a7c9e","LegalEntityId": "USMF","UserContext": "asset-register","AssetId": "COMP-000001","Dimensions": [ { "DimensionName": "Department", "DimensionValue": "023" } ],"LocationId": "PROD","TransferDate": "2026-11-01","Comment": "Moved to production engineering"}}Send
Dimensions,LocationIdor both. For each book (onlyAssetBookIdwhen you send it; otherwise every open or closed book of the asset that has a posting layer), the transfer posts a general ledger voucher that moves the book's balance from its current dimensions to the new ones, writes an asset transfer transaction and the transfer history, and gives the book the new dimensions. The dimensions you send replace the same dimensions of each book; the others keep their values, and a book that already has the result is left as it is.LocationIdis the asset's location.TransferDatedefaults to today and must be a date of the fiscal calendar.DocumentIdis the asset,PostedDocumentIdthe voucher of the first transferred book (empty when only the location changes). -
Split off part of the asset.
splitAssetruns the standard asset split (the book's Split asset) and posts the split journal it creates, in one transaction:{"_request": {"RequestId": "6a8c0e2a-4b5d-4f6e-9a8b-0c2e4a6c8e0a","LegalEntityId": "USMF","UserContext": "asset-register","AssetId": "COMP-000001","AssetBookId": "200_SLLR","Percent": 40,"JournalNameId": "FACur","SplitDate": "2026-11-15"}}- Send
Percent(greater than 0, at most 100) orQuantity(units, at most the asset's quantity), not both. A quantity is turned into the share it is of the asset's quantity, and the units move to the receiving asset; a percentage moves values only. - The share of the book's acquisition, depreciation and other values moves to the receiving asset's book
(
ToAssetBookId, default the same book). WithoutToAssetIdthe receiving asset is created as a copy of the asset (same group and details, every book copied, none acquired); with it, that existing asset receives the split. Derived books the split asset has not acquired are left out. DocumentIdis the asset that was split,PostedDocumentIdthe asset that received it, and the message names the posted split journal: "40 percent of book 200_SLLR of fixed asset COMP-000001 was split into fixed asset COMP-000002; split journal ... posted." Nothing is kept when the split journal does not post.
- Send
-
Reverse a posting made in error.
reverseAssetTransactionreverses a posted fixed asset voucher of a book with the standard reversal (the fixed asset transactions page's Reverse transaction): the general ledger voucher and every asset transaction of the voucher are reversed, and the book is updated as the standard reversal updates it:{"_request": {"RequestId": "8c0e2a4c-6d7f-4a8b-9c0d-2e4a6c8e0a2c","LegalEntityId": "USMF","UserContext": "asset-register","AssetId": "COMP-000001","AssetBookId": "200_SLLR","Voucher": "<voucher from step 4>","ReversalDate": "2026-11-02","ReasonCode": "ERROR","ReasonComment": "Write-down posted to the wrong asset"}}ReversalDatedefaults to today and cannot be before the transaction;TransactionDateis needed only when the voucher has transactions of the book on several dates.DocumentIdis the reversed voucher,PostedDocumentIdthe reversal voucher. A voucher posted with a vendor or customer transaction is reversed in accounts payable or receivable instead. -
Post the disposal.
postDisposalcreates and posts a fixed asset journal with one disposal line for the asset book. For a sale, setIsSaletotrue, the proceeds inSaleAmount, and the account that receives them inOffsetMainAccountId(without it the sale voucher cannot balance and the post fails):POST https://<your-environment>/api/services/MGCLatticeFixedAssetsServiceGroup/MGCLatticeFixedAssetService/postDisposal{"_request": {"RequestId": "9c0d1e2f-3a4b-4c5d-8e6f-7a8b9c0d1e2f","LegalEntityId": "USMF","UserContext": "asset-register","JournalNameId": "FACur","AssetId": "COMP-000001","AssetBookId": "200_SLLR","IsSale": true,"SaleAmount": 5000.00,"OffsetMainAccountId": "110110","CurrencyCode": "USD","DisposalDate": "2026-12-31"}}For a scrap, send
"IsSale": falseand leave outSaleAmountandOffsetMainAccountId. Always sendIsSale: a request without it is a scrap. The disposal posts to the book you name only, not to its derived books. The answer:DocumentId=PostedDocumentId= the disposal journal number, message "Fixed asset ... disposal posted in journal ...". -
Read the transactions back. Read the Lattice entity
LatticeFixedAssetTransactionsfor the asset and book:GET https://<your-environment>/data/LatticeFixedAssetTransactions?$filter=AssetId eq 'COMP-000001' and BookId eq '200_SLLR' and dataAreaId eq 'usmf'&cross-company=true&$select=AssetTransType,TransactionDate,Voucher,AccountingCurrencyAmountA posted sale has a row with
AssetTransTypeDisposalSale(a scrap:DisposalScrap) on the disposal date; itsVoucheris the disposal voucher. The same read shows theAcquisitionrow from step 2, theDepreciationrows once you posted the proposal journal, a row per transaction of step 4 under its voucher (credits negative), theAssetTransferrow of step 5, the split's acquisition adjustment, and for a reversal a row with the opposite amount under the reversal voucher.
Bulk variants postAcquisitionBatch, runDepreciationProposalBatch, postAssetTransactionBatch,
transferAssetBatch, splitAssetBatch, reverseAssetTransactionBatch and postDisposalBatch take a _requests
list. postAcquisition, runDepreciationProposal, postAssetTransaction and postDisposal can also be queued
with submitAsyncOperation (see API reference, sections 19 and 21). None of the
operations has a preview.
How to verify
- Each response:
Successtrue,Status3. Acquisition, proposal and disposal:DocumentId=PostedDocumentId= the journal number. Transactions: the journal and its first voucher. Transfer: the asset and the first transfer voucher. Split: the split asset and the receiving asset. Reversal: the reversed and the reversal voucher. LatticeFixedAssetTransactionsshowsAcquisition, thenDepreciation(after you post the proposal), the transactions you posted, thenDisposalSaleorDisposalScrapfor the asset book.- A transfer:
FixedAssetBooksV2shows the book's newDimensionDisplayValue, andFixedAssetsV2the asset'sAssetLocationId. A split: the receiving asset exists inFixedAssetsV2, with its book acquired. - The proposal journal's lines: read the standard
AssetJournalLinesentity filtered onJournalBatchNumber(the proposal journal number) anddataAreaId, withcross-company=true; their count matches the message. - In D365: Fixed assets > Journal entries > Fixed assets journal lists the posted journals and the unposted proposal; open the asset on Fixed assets > Fixed assets > Fixed assets and its Books to see the book's status and transactions, and Transfer history for the transfers. A reversed transaction shows as reversed on the book's transactions.
- If you subscribe to business events, Fixed asset acquisition posted and Fixed asset disposal posted fire for the acquisition and disposal transactions.
When it goes wrong
A failed request answers Success false, Status 4, an ErrorCode and a generic Message; the
reasons are in Errors.
| ErrorCode | Typical cause (text in Errors) | What to do |
|---|---|---|
ValidationFailed (1) | No RequestId or unknown LegalEntityId; "JournalNameId is required."; "Journal name ... was not found."; "At least one acquisition line is required."; "Request line N is empty."; "Line N: AssetBookId is required." (or AcquisitionAmount); "Fixed asset ... was not found."; "AssetId is required."; "AssetBookId is required."; proposal: "Journal name ... is a ... journal; this operation needs a ... journal."; transactions: "Line 1: '...' is not a fixed asset transaction type this operation posts."; "Line 1: post acquisitions with postAcquisition." (or disposals with postDisposal); "Line 1: send either DebitAmount or CreditAmount, as an amount greater than zero."; "Journal name ... posts to the ... posting layer, but book ... posts to the ... posting layer."; an unknown book or reason code; transfer: "Send Dimensions, LocationId or both..."; an unknown location; "Fixed asset ... already has these financial dimensions and this location: there is nothing to transfer."; split: "Send either Percent or Quantity."; a percentage or quantity out of range; the asset itself as receiving asset; reversal: no Voucher; "Voucher ... has transactions of book ... on several dates. Send TransactionDate."; a reversal date before the transaction; an AssetIdExternalKey that does not resolve | Correct the request and resend. |
DocumentNotFound (2) | Proposal: "Fixed asset book ... was not found."; transfer and split: an unknown asset; reversal: "Book ... of fixed asset ... has no transaction with voucher ..." | Send an existing asset, book or voucher. |
InvalidStatus (3) | "Book ... of fixed asset ... is not acquired yet. Post the acquisition first."; "Book ... of fixed asset ... is Sold and takes no more transactions." (or Scrapped); transfer: a book that is not open or closed; reversal: a transaction already reversed, or itself a reversal | Post the acquisition first; nothing more can be posted to a disposed book; a reversed transaction needs nothing more. |
DimensionValueNotFound (5) | "Offset main account '...' could not be resolved in the chart of accounts."; a financial dimension or value that does not resolve | Use an account and dimension values of the legal entity. |
ConfigurationMissing (11) | "Journal name ... has no voucher number sequence configured."; "Legal entity ... has no ledger with a chart of accounts."; proposal: the reporting currency amounts of the fixed asset parameters are not updated; transactions: the posting profile has no account or no offset account for the transaction type and book (for example bonus depreciation in USMF, whose profile ALL has no bonus depreciation accounts: nothing is posted); transfer: no transfer number sequence; split: "Fixed asset group ... numbers its assets manually, so the split cannot create the new asset."; reversal: no reversal voucher or trace number sequence | Fix the setup, then resend. For a split into a manually numbered group, create the receiving asset and send ToAssetId. |
BusinessRule (4) | D365 refused the post: posting profile accounts, book not acquired, disposal parameters, an unbalanced sale (no offset account), a closed period; "Journal ... was not posted."; transactions: "book ... does not depreciate, so it takes no Depreciation transactions."; transfer: a date outside the fiscal calendar, a book with no transactions to move, a move between balancing dimensions in public sector (transfer it on the Transfer asset page); split: the standard split refused; reversal: "Voucher ... was posted with a vendor transaction. Reverse it in accounts payable." (or customer), a later transaction on the book, a negative net book value, a closed fiscal period | See below. |
PreviewUnsupported (10) | PreviewMode true: fixed asset operations have no preview | Send without PreviewMode. Nothing was run. |
TransientRuntime (6) | Infrastructure fault; IsRetryable true | Resend with the same RequestId. |
A refused post leaves no journal behind. Acquisition, transaction and disposal journals are committed before
they are posted. When the post fails, the service deletes the unposted journal again and the failed request
releases its RequestId, so fix the cause and resend: the resend creates and posts the journal anew. Only if that
cleanup itself fails does the journal stay unposted on Fixed assets journal; delete it, or correct and post it
in D365 instead of resending. A transfer, a split and a reversal run in one transaction each: when they fail,
nothing is changed (a split that fails creates no receiving asset).
An empty or unexpected proposal. The proposal reports calculation problems as messages rather than
failing: when the message says nothing was due but you expected lines, read InformationalMessages.
Replays and stranded requests work as for every posting service: a repeated RequestId returns the
first result; see Post a journal exactly-once. A queued operation that
fails lands in the dead-letter queue; see Integration operations.
Reference
- API reference: section 14 (Fixed Asset Service), 19 and 21 (bulk and async)
- Endpoint payload specification:
MGCLatticeFixedAssetService - Data entity reference:
LatticeFixedAssetTransactions - Security model
- Cross-reference keys
- Post a journal exactly-once, Post an existing journal
- Integration operations