Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

chain release2.9 compatibility Grace Period and overdue #3387

Open
wants to merge 57 commits into
base: development
Choose a base branch
from

Conversation

0oM4R
Copy link
Contributor

@0oM4R 0oM4R commented Sep 7, 2024

Description

We have new accurate way to resume/unlock contracts on tfchain2.9, this pull request is for replace the old way as it is no longer supported.

General idea:

Now the amount required to resume the contract is described as Overdue.
The overdue amount basically is the sum of three parts:

  1. Total over draft: is the sum of additional overdraft and standard overdraft.
  2. Unbilled NU: is the unbilled amount of network usage.
  3. The estimated cost of the contract for the total period: this part is dependent on the contract type and if the contract is on a rented node or not.

Note:

  • The total period is the time since the last billing added to the allowance period.
  • If the contract is a rent contract, will add both of ipv4 cost and the total overdue of all associated contracts.

Changes

Please node: you may notice that we have multiple functions that generally do the same thing but require different arguments.
for example: we need some information that is already in the contract type,
so instead of requesting the contract in side the function we are passing it.
but in some cases we only have the contract id? we provide a function that take the contract id and then request the contract then pass it to the inner function.

TFChain client

  1. Fixed the generateTypes.bash:
  • the old script required to have ts-node installed, now we can run those commands using yarn.
  1. In contracts, we add some functions that help in grid client new features.

Grid client:

  • add deprecated annotation to the no longer supported functions that are associated with locked amount.
  • Calculator module: added a function to calculate the name pricing.
  • Contract module:
    • added some functions that calculate overdue, you can pass the contract, or the contract id.
    • add functions to unlock contracts, all contracts, and batch unlock using array of contracts or array of contractss ids
    • we are using gridproxy in unlock contracts

Dashboard

support new functions in grid client, refactor, and remove the deprecated gird client functions.
we have some changes in the flow:

  • If the user select node contracts, and some of them are on a rent contract, we will show the rent contract id with the selected contracts
    Screenshot from 2024-09-09 15-18-12

  • if use click on grace period chip of node contract with ipv4 on rented node the content of the dialog depends on the rent contract state:

    • if the rent contract state is Created : will get the node contract overdue, and user will be able to unlock the contract.

    • If on Grace period: will show a message that you will have to check the rent contract and unlock it.
      Screenshot from 2024-09-10 15-06-56

fix loading spinner in loading locked amount details:
Screenshot from 2024-09-09 14-55-38

Related Issues

#3340
#3364

Tested Scenarios

  • show contract/s cost : this will be nearly from pricing calculator if the contract got billed right before moving to the grace period as in this case overdue will be small for example, name contract cost should be about 0.025 tfts

  • select node contracts on rented node that its contract on grace period,

  • unlock all contracts associated with rent contract: in this case to verify that the node contract got billed, use smarContractModule/contractPaymentState call, the additional and standred overdraft should be 0

  • Unlock single or multiple contracts

  • in any case we should'n have a contract got billed twice: you can add log line to log the ids in batchUnlock contracts
    Tips:

  • To send contract to a grace period, you need to follow some steps
    1- empty you walet, this can be done by polkadot UI Balances/TransferAll
    2- get the contract Id, must be billable one like rent contract or node contract on shared node, name contract, and call smarContractsModule/billcontractForBlock using any other funded account.

  • to send node contract with public ip on rented node to grace period and keep it's rent contract is on created state

    • fund you wallet, and call bill contract for block for the rent contract,
    • then send the node contract with ipv4 only to grace period as mentioned

Documentation PR

For UI changes, Please provide the Documetation PR on info_grid

Checklist

  • Tests included
  • Build pass
  • Documentation
  • Code format and docstrings
  • Screenshots/Video attached (needed for UI changes)

- a method to get NU billing information
- a method to get contract payment state
- a method to get used resources by the node contract
- some related interfaces
enhance code readablity.
reduce number of requests by passing the contract info to all chiled functions
- use proxy url in unlockMycontracts
- refactor unlockContracts to accept array of contracts
- add function to unlock contracts by their ids
- add function that takes only contract to unlock it
- add calculate overdue functions
mUSD converter will return the price in mTFT
fix unique name price calc
fix imports
- add contracts on rented node to the rent node overdue
it is storing the rent contract on a map by the node id, and ignore the unwanted calculations
unlock dialog now will check if the node contract on rented node or not; if so will retrive the rent contract cost and store the and will avoid duplication
state: [ContractState.GracePeriod],
numberOfPublicIps: 1,
});

Copy link
Member

Choose a reason for hiding this comment

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

Can we handle the case where there are no returned contracts and return early?

if (!contract.details.number_of_public_ips) return 0;

const ipPrice = (await this.client.pricingPolicies.get({ id: 1 })).ipu.value / 10 ** 7;
return ipPrice * 30 * 24;
Copy link
Member

Choose a reason for hiding this comment

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

Why not use the number of public IPs in the contract instead?
FYI, from the tfchain side, I can create a contract that reserves more than one public IP. Since it is a valid case, despite some client limitations or restrictions, it should be handled when calculating the contract costs as it may be created with different clients.

/** Other contract types need the node information */
const nodeDetails = await proxy.nodes.byId(contract.details.nodeId);

const certified = nodeDetails.certificationType == CertificationType.Certified ? true : false;
Copy link
Member

Choose a reason for hiding this comment

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

Do you need the ternary operator here?
The condition nodeDetails.certificationType == CertificationType.Certified already evaluates to true or false.

Also, it is better to use === to avoid unexpected behavior caused by implicit type conversion.


// cost of the current billing period with the mentioned allowance time
const totalPeriodCost = contractCostTFT.times(totalPeriodTime);
const overdue = totalOverDraft.add(unbilledNU);
Copy link
Member

Choose a reason for hiding this comment

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

As previously explained in my other comment, You can't add them directly.

const { standardOverdraft, additionalOverdraft, lastUpdatedSeconds } =
await this.client.contracts.getContractPaymentState(contractInfo.contract_id);

/**Calculate the elapsed seconds since last pilling*/
Copy link
Member

Choose a reason for hiding this comment

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

There is a small typo here "pilling" -> "billing"

const overdue = totalOverDraft.add(unbilledNU);

//convert to TFT
const OverdueTFT = overdue.div(10 ** 7);
Copy link
Member

Choose a reason for hiding this comment

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

OverdueTFT name should follow camelCase convention.

if (nodeDetails.rented) {
if (!contract.details.number_of_public_ips) return 0;

const ipPrice = (await this.client.pricingPolicies.get({ id: 1 })).ipu.value / 10 ** 7;
Copy link
Member

Choose a reason for hiding this comment

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

I would avoid using magic numbers like 10 ** 7 and define it as constant TFT_CONVERSION_FACTOR (maybe in the client) then use it everywhere else for clarity and maintainability.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

add for the current file, will open an issue to make it global value for the grid client


// cost of the current billing period with the mentioned allowance time
const totalPeriodCost = contractCostTFT.times(totalPeriodTime);
const overdue = totalOverDraft.add(unbilledNU);
Copy link
Member

Choose a reason for hiding this comment

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

Another point to consider regarding unbilled NU is that it may be eligible for a discount or subject to an added premium:

  • A discount may apply based on the user's balance.
  • A premium is added when a certified node is used.

This has already been handled for overdraft stored on the contract payment state, as well as the cost of the contract retrieved from the calc module.

separate node contracts on rented node cost calculations to multiple functions
create constants with numbers repeatedly  used in the calculations
enhance docstring
@0oM4R 0oM4R marked this pull request as draft September 19, 2024 15:17
@0oM4R 0oM4R marked this pull request as ready for review September 22, 2024 12:27
@sameh-farouk
Copy link
Member

sameh-farouk commented Sep 30, 2024

@0oM4R I attempted a quick test, but it didn't go well.

Screenshot_20240930_160919

Screenshot_20240930_160829

@sameh-farouk
Copy link
Member

Another point, it seems you haven't incorporated the changes discussed in the tg group yet.

Unlock All/ Unlock -> Resume All / Resume
Locked Balance -> On hold
Show in UI: Available and On hold

@0oM4R
Copy link
Contributor Author

0oM4R commented Sep 30, 2024

Another point, it seems you haven't incorporated the changes discussed in the tg group yet.

Unlock All/ Unlock -> Resume All / Resume
Locked Balance -> On hold
Show in UI: Available and On hold

there is a separate issue for it #3400

@0oM4R
Copy link
Contributor Author

0oM4R commented Sep 30, 2024

Screenshot from 2024-09-30 17-59-09
Screenshot from 2024-09-30 17-59-42

works fine with me but we should handle the zero tft case in the ui

@0oM4R I attempted a quick test, but it didn't go well.

Screenshot_20240930_160919

Screenshot_20240930_160829

@sameh-farouk
Copy link
Member

works fine with me but we should handle the zero tft case in the ui

Sorry, My bad.
I didn't pull the latest changes. So I will give it another try tomorrow.

@sameh-farouk
Copy link
Member

Calculations looks much better now.

sameh-farouk
sameh-farouk previously approved these changes Oct 2, 2024
@0oM4R
Copy link
Contributor Author

0oM4R commented Oct 3, 2024

Test report:
will update this comment with the tested scenarios in details

Rent contract without any node contracts on it

image
image

the allowance window in the next scenarios is 60 seconds

skip the node contracts on rented nodes as it already calculated in rent contract
we were ignoring the elapsed seconds for node contracts and we assume that it is the same as rent contract
reorder the calculation logic to be easier in debugging
pass the contracts by id as the contracts do not have the public_ips_number field
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.

3 participants