Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
61 commits
Select commit Hold shift + click to select a range
2d92792
feat:add charging address.
ssun0121 Nov 23, 2023
61a5920
feat:change type to string.
ssun0121 Nov 24, 2023
b3acc84
Merge branch 'master' into feature/calculate-fee
ssun0121 Nov 24, 2023
4a95366
feat:change output structure.
ssun0121 Nov 27, 2023
ac7fb26
feat:Modifying the description.
ssun0121 Nov 28, 2023
6c27a29
feat:change output property.
ssun0121 Nov 28, 2023
ea085f3
test:add test.
ssun0121 Nov 28, 2023
5c6c669
feat: add ModifyTokenIssuerAndOwner, SetTokenIssuerAndOwnerModificati…
kaiwenzhengaelf Dec 7, 2023
a1cb698
fix: format code
kaiwenzhengaelf Dec 7, 2023
82b284a
fix: ModifyTokenIssuerAndOwner
kaiwenzhengaelf Dec 7, 2023
242638e
fix: assert message
kaiwenzhengaelf Dec 8, 2023
c910c95
Merge pull request #3490 from AElfProject/feature/modify-issuer-owner
kaiwenzhengaelf Dec 8, 2023
913ed5b
fix:change SetTokenIssuerAndOwnerModificationEnabled to SetTokenIssue…
kaiwenzhengaelf Dec 8, 2023
c521d69
fix: improve semantic accuracy
kaiwenzhengaelf Dec 8, 2023
1864d2e
fix: typo
kaiwenzhengaelf Dec 8, 2023
b403f2f
fix: remove redundant message
kaiwenzhengaelf Dec 8, 2023
3a0445d
feat: add ut
kaiwenzhengaelf Dec 9, 2023
c391774
Merge pull request #3494 from AElfProject/fix/modify-issuer-owner
jason-aelf Dec 9, 2023
7541806
Merge pull request #3493 from AElfProject/release/1.6.1
jason-aelf Dec 10, 2023
2bf43ff
Add ProfitContract state to limit the max profit receiving period count.
jason-aelf Jan 8, 2024
b3011d1
Change the logic of calculating max profit receiving period count
jason-aelf Jan 10, 2024
4ed4215
Fix wrong period of profits.
jason-aelf Jan 11, 2024
c05c2c3
Add comments for method 'GetMaximumPeriodCountForProfitableDetail'
jason-aelf Jan 12, 2024
456d45e
Add one time claimable profit amount to return value
jason-aelf Jan 16, 2024
89c8604
Fix build error
jason-aelf Jan 17, 2024
39d1120
Enhance ProfitContract with methods for getting all profit amount
jason-aelf Jan 23, 2024
06d1e43
Remove duplicate codes
jason-aelf Jan 23, 2024
07adf84
Change to return all profit amount
jason-aelf Jan 23, 2024
d32538f
Fix unit test error
jason-aelf Jan 23, 2024
20f4821
Merge branch 'release/2.0.0' into feature/calculate-fee
jason-aelf Jan 23, 2024
ef9ae57
Remove duplicate codes
jason-aelf Jan 24, 2024
0c8e1dc
Merge pull request #3519 from AElfProject/feature/change-max-profit-r…
jason-aelf Jan 31, 2024
7edbdc7
feat:remove nft decimal restriction
louis4li Feb 22, 2024
6c4f6c8
feat: create token on specified chain
louis4li Feb 26, 2024
5f364ff
feat: add seed when cross chain create
louis4li Feb 29, 2024
0815a2b
feat: SetSymbolSeed update
louis4li Feb 29, 2024
ab522bb
feat: add batch approve
louis4li Feb 29, 2024
2d30519
Merge pull request #3526 from AElfProject/release/1.7.0
jason-aelf Feb 29, 2024
7d84b6b
feat: update MaximumBatchApproveCount check
louis4li Mar 1, 2024
7095554
feat:update description
louis4li Mar 1, 2024
079c247
Merge branch 'release/1.8.0' into feature/remove-nft-decimal-restriction
jason-aelf Mar 1, 2024
eb4ceaa
feat: ApproveInputList distinct
louis4li Mar 1, 2024
109e92f
Merge pull request #3525 from AElfProject/feature/remove-nft-decimal-…
jason-aelf Mar 1, 2024
2c92a32
Merge branch 'release/1.8.0' into feature/create-token-on-specified-c…
jason-aelf Mar 1, 2024
cc028e2
feat: method rename
louis4li Mar 1, 2024
b4263e3
feat: update BatchApproveInputCount check
louis4li Mar 1, 2024
db75acf
feat:seed cannot create token on side chain
louis4li Mar 2, 2024
4787599
Merge remote-tracking branch 'origin/feature/create-token-on-specifie…
louis4li Mar 2, 2024
664382e
Merge pull request #3531 from AElfProject/feature/create-token-on-spe…
jason-aelf Mar 3, 2024
cdd34cd
Merge branch 'release/1.8.0' into feature/batch-approve
jason-aelf Mar 3, 2024
aa1b5b3
feat:rename MaxBatchApproveCount
louis4li Mar 3, 2024
ede52ed
Merge remote-tracking branch 'origin/feature/batch-approve' into feat…
louis4li Mar 3, 2024
4f7f563
feat:update BatchApprove check
louis4li Mar 3, 2024
7dbd094
Merge pull request #3532 from AElfProject/feature/batch-approve
jason-aelf Mar 3, 2024
2753cb9
feat:Compatibility with historical NFT creations
louis4li Mar 6, 2024
777e040
feat:Modify the verification order
louis4li Mar 7, 2024
821000d
Merge remote-tracking branch 'origin/release/1.8.0' into feature/crea…
louis4li Mar 7, 2024
9133b3c
Merge pull request #3534 from AElfProject/feature/create-token-on-spe…
louis4li Mar 7, 2024
88e0c3c
Merge branch 'master' into release/1.8.0
jason-aelf Mar 28, 2024
1842512
Merge pull request #3536 from AElfProject/release/1.8.0
jason-aelf Mar 28, 2024
40bf0de
Resolve conflicts
eanzhao May 17, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions contract/AElf.Contracts.MultiToken/TokenContractConstants.cs
Original file line number Diff line number Diff line change
Expand Up @@ -22,4 +22,6 @@ public static class TokenContractConstants
public const string SeedCollectionSymbol = "SEED-0";
public const string SeedOwnedSymbolExternalInfoKey = "__seed_owned_symbol";
public const string SeedExpireTimeExternalInfoKey = "__seed_exp_time";
public const string NftCreateChainIdExternalInfoKey = "__nft_create_chain_id";
public const int DefaultMaxBatchApproveCount = 100;
}
2 changes: 2 additions & 0 deletions contract/AElf.Contracts.MultiToken/TokenContractState.cs
Original file line number Diff line number Diff line change
Expand Up @@ -65,4 +65,6 @@ public partial class TokenContractState : ContractState
public SingletonState<Address> VoteContractAddress { get; set; }

public SingletonState<bool> TokenIssuerAndOwnerModificationDisabled { get; set; }

public SingletonState<int> MaxBatchApproveCount { get; set; }
}
58 changes: 51 additions & 7 deletions contract/AElf.Contracts.MultiToken/TokenContract_Actions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -32,8 +32,6 @@ public override Empty InitializeFromParentChain(InitializeFromParentChainInput i
/// <returns></returns>
public override Empty Create(CreateInput input)
{
// can not call create on side chain
Assert(State.SideChainCreator.Value == null, "Failed to create token if side chain creator already set.");
var inputSymbolType = GetCreateInputSymbolType(input.Symbol);
if (input.Owner == null)
{
Expand All @@ -52,6 +50,9 @@ private Empty CreateToken(CreateInput input, SymbolType symbolType = SymbolType.
AssertValidCreateInput(input, symbolType);
if (symbolType == SymbolType.Token || symbolType == SymbolType.NftCollection)
{
// can not call create on side chain
Assert(State.SideChainCreator.Value == null,
"Failed to create token if side chain creator already set.");
if (!IsAddressInCreateWhiteList(Context.Sender) &&
input.Symbol != TokenContractConstants.SeedCollectionSymbol)
{
Expand Down Expand Up @@ -253,14 +254,35 @@ public override Empty Approve(ApproveInput input)
{
AssertValidInputAddress(input.Spender);
AssertValidToken(input.Symbol, input.Amount);
State.Allowances[Context.Sender][input.Spender][input.Symbol] = input.Amount;
Approve(input.Spender, input.Symbol, input.Amount);
return new Empty();
}

private void Approve(Address spender, string symbol, long amount)
{
State.Allowances[Context.Sender][spender][symbol] = amount;
Context.Fire(new Approved
{
Owner = Context.Sender,
Spender = input.Spender,
Symbol = input.Symbol,
Amount = input.Amount
Spender = spender,
Symbol = symbol,
Amount = amount
});
}

public override Empty BatchApprove(BatchApproveInput input)
{
Assert(input != null && input.Value != null && input.Value.Count > 0, "Invalid input .");
Assert(input.Value.Count <= GetMaxBatchApproveCount(), "Exceeds the max batch approve count.");
foreach (var approve in input.Value)
{
AssertValidInputAddress(approve.Spender);
AssertValidToken(approve.Symbol, approve.Amount);
}
var approveInputList = input.Value.GroupBy(approve => approve.Symbol + approve.Spender, approve => approve)
.Select(approve => approve.Last()).ToList();
foreach (var approve in approveInputList)
Approve(approve.Spender, approve.Symbol, approve.Amount);
return new Empty();
}

Expand Down Expand Up @@ -468,7 +490,6 @@ public override Empty CrossChainCreateToken(CrossChainCreateTokenInput input)
Owner = validateTokenInfoExistsInput.Owner ?? validateTokenInfoExistsInput.Issuer
};
RegisterTokenInfo(tokenInfo);

Context.Fire(new TokenCreated
{
Symbol = validateTokenInfoExistsInput.Symbol,
Expand Down Expand Up @@ -626,4 +647,27 @@ public override BoolValue GetTokenIssuerAndOwnerModificationEnabled(Empty input)
Value = !State.TokenIssuerAndOwnerModificationDisabled.Value
};
}

public override Empty SetMaxBatchApproveCount(Int32Value input)
{
Assert(input.Value > 0, "Invalid input.");
AssertSenderAddressWith(GetDefaultParliamentController().OwnerAddress);
State.MaxBatchApproveCount.Value = input.Value;
return new Empty();
}

public override Int32Value GetMaxBatchApproveCount(Empty input)
{
return new Int32Value
{
Value = GetMaxBatchApproveCount()
};
}

private int GetMaxBatchApproveCount()
{
return State.MaxBatchApproveCount.Value == 0
? TokenContractConstants.DefaultMaxBatchApproveCount
: State.MaxBatchApproveCount.Value;
}
}
4 changes: 0 additions & 4 deletions contract/AElf.Contracts.MultiToken/TokenContract_NFTHelper.cs
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,4 @@ private SymbolType GetCreateInputSymbolType(string symbol)
return words[1] == TokenContractConstants.CollectionSymbolSuffix ? SymbolType.NftCollection : SymbolType.Nft;
}

private void AssertNFTCreateInput(CreateInput input)
{
Assert(input.Decimals == 0, "NFT's decimals must be 0");
}
}
23 changes: 17 additions & 6 deletions contract/AElf.Contracts.MultiToken/TokenContract_NFT_Actions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -9,23 +9,34 @@ public partial class TokenContract
{
private Empty CreateNFTCollection(CreateInput input)
{
AssertNFTCreateInput(input);
return CreateToken(input, SymbolType.NftCollection);
}

private Empty CreateNFTInfo(CreateInput input)
{
AssertNFTCreateInput(input);
var nftCollectionInfo = AssertNftCollectionExist(input.Symbol);
input.IssueChainId = input.IssueChainId == 0 ? nftCollectionInfo.IssueChainId : input.IssueChainId;
Assert(input.IssueChainId == nftCollectionInfo.IssueChainId,
"NFT create ChainId must be collection's issue chainId");

Assert(
input.IssueChainId == nftCollectionInfo.IssueChainId,
"NFT issue ChainId must be collection's issue chainId");
if (nftCollectionInfo.ExternalInfo != null && nftCollectionInfo.ExternalInfo.Value.TryGetValue(
TokenContractConstants.NftCreateChainIdExternalInfoKey,
out var nftCreateChainId) && long.TryParse(nftCreateChainId, out var nftCreateChainIdLong))
{
Assert(nftCreateChainIdLong == Context.ChainId,
"NFT create ChainId must be collection's NFT create chainId");
}
else
{
Assert(State.SideChainCreator.Value == null,
"Failed to create token if side chain creator already set.");
}

var owner = nftCollectionInfo.Owner ?? nftCollectionInfo.Issuer;
Assert(Context.Sender == owner && owner == input.Owner, "NFT owner must be collection's owner");

if (nftCollectionInfo.Symbol == TokenContractConstants.SeedCollectionSymbol)
{
Assert(input.Decimals == 0 && input.TotalSupply == 1, "SEED must be unique.");
Assert(input.ExternalInfo.Value.TryGetValue(TokenContractConstants.SeedOwnedSymbolExternalInfoKey,
out var ownedSymbol), "OwnedSymbol does not exist.");
Assert(input.ExternalInfo.Value.TryGetValue(TokenContractConstants.SeedExpireTimeExternalInfoKey,
Expand Down
66 changes: 54 additions & 12 deletions contract/AElf.Contracts.Profit/ProfitContract.cs
Original file line number Diff line number Diff line change
Expand Up @@ -769,18 +769,19 @@ public override Empty ClaimProfits(ClaimProfitsInput input)
Context.LogDebug(() =>
$"Profitable details: {profitableDetails.Aggregate("\n", (profit1, profit2) => profit1.ToString() + "\n" + profit2)}");

var profitableDetailCount =
Math.Min(ProfitContractConstants.ProfitReceivingLimitForEachTime, profitableDetails.Count);
var maxProfitReceivingPeriodCount = GetMaximumPeriodCountForProfitableDetail(profitableDetailCount);
// Only can get profit from last profit period to actual last period (profit.CurrentPeriod - 1),
// because current period not released yet.
for (var i = 0;
i < Math.Min(ProfitContractConstants.ProfitReceivingLimitForEachTime, profitableDetails.Count);
i++)
for (var i = 0; i < profitableDetailCount; i++)
{
var profitDetail = profitableDetails[i];
if (profitDetail.LastProfitPeriod == 0)
// This detail never performed profit before.
profitDetail.LastProfitPeriod = profitDetail.StartPeriod;

ProfitAllPeriods(scheme, profitDetail, beneficiary);
ProfitAllPeriods(scheme, profitDetail, beneficiary, maxProfitReceivingPeriodCount);
}

var profitDetailsToRemove = profitableDetails
Expand All @@ -807,7 +808,41 @@ public override Empty ClaimProfits(ClaimProfitsInput input)
return new Empty();
}

private Dictionary<string, long> ProfitAllPeriods(Scheme scheme, ProfitDetail profitDetail, Address beneficiary,
/// <summary>
/// This method calculates the maximum period count for a profitable detail
/// based on the number of profitable details and the maximum profit receiving period
/// For example:
/// If the number of profitable detail is 10 and the maximum profit receiving period is 100,
/// the maximum period count for a profitable detail will be 10.
/// If the number of profitable detail is 10 and the maximum profit receiving period is 5,
/// the maximum period count for a profitable detail will be 1.
/// </summary>
/// <param name="profitableDetailCount">The number of profitable details</param>
/// <returns></returns>
private int GetMaximumPeriodCountForProfitableDetail(int profitableDetailCount)
{
// Get the maximum profit receiving period count
var maxPeriodCount = GetMaximumProfitReceivingPeriodCount();
// Check if the maximum period count is greater than the profitable detail count
// and if the profitable detail count is greater than 0
return maxPeriodCount > profitableDetailCount && profitableDetailCount > 0
// Divide the maximum period count by the profitable detail count
? maxPeriodCount.Div(profitableDetailCount)
// If the conditions are not met, return 1 as the maximum period count
: 1;
}

public override Empty SetMaximumProfitReceivingPeriodCount(Int32Value input)
{
ValidateContractState(State.ParliamentContract, SmartContractConstants.ParliamentContractSystemName);
Assert(Context.Sender == State.ParliamentContract.GetDefaultOrganizationAddress.Call(new Empty()),
"No permission.");
Assert(input.Value > 0, "Invalid maximum profit receiving period count.");
State.MaximumProfitReceivingPeriodCount.Value = input.Value;
return new Empty();
}

private Dictionary<string, long> ProfitAllPeriods(Scheme scheme, ProfitDetail profitDetail, Address beneficiary, long maxProfitReceivingPeriodCount,
bool isView = false, string targetSymbol = null)
{
var profitsMap = new Dictionary<string, long>();
Expand All @@ -818,13 +853,11 @@ private Dictionary<string, long> ProfitAllPeriods(Scheme scheme, ProfitDetail pr
foreach (var symbol in symbols)
{
var totalAmount = 0L;
for (var period = profitDetail.LastProfitPeriod;
period <= (profitDetail.EndPeriod == long.MaxValue
? Math.Min(scheme.CurrentPeriod - 1,
profitDetail.LastProfitPeriod.Add(ProfitContractConstants
.MaximumProfitReceivingPeriodCountOfOneTime))
: Math.Min(scheme.CurrentPeriod - 1, profitDetail.EndPeriod));
period++)
var targetPeriod = Math.Min(scheme.CurrentPeriod - 1, profitDetail.EndPeriod);
var maxProfitPeriod = profitDetail.EndPeriod == long.MaxValue
? Math.Min(scheme.CurrentPeriod - 1, profitDetail.LastProfitPeriod.Add(maxProfitReceivingPeriodCount))
: Math.Min(targetPeriod, profitDetail.LastProfitPeriod.Add(maxProfitReceivingPeriodCount));
for (var period = profitDetail.LastProfitPeriod; period <= maxProfitPeriod; period++)
{
var periodToPrint = period;
var detailToPrint = profitDetail;
Expand Down Expand Up @@ -885,6 +918,15 @@ private Dictionary<string, long> ProfitAllPeriods(Scheme scheme, ProfitDetail pr

return profitsMap;
}

private int GetMaximumProfitReceivingPeriodCount()
{
var maxPeriodCount = State.MaximumProfitReceivingPeriodCount.Value;
maxPeriodCount = maxPeriodCount == 0
? ProfitContractConstants.DefaultMaximumProfitReceivingPeriodCountOfOneTime
: maxPeriodCount;
return maxPeriodCount;
}

private void ValidateContractState(ContractReferenceState state, string contractSystemName)
{
Expand Down
2 changes: 1 addition & 1 deletion contract/AElf.Contracts.Profit/ProfitContractConstants.cs
Original file line number Diff line number Diff line change
Expand Up @@ -6,5 +6,5 @@ public class ProfitContractConstants
public const int DefaultProfitReceivingDuePeriodCount = 10;
public const int MaximumProfitReceivingDuePeriodCount = 1024;
public const int TokenAmountLimit = 5;
public const int MaximumProfitReceivingPeriodCountOfOneTime = 100;
public const int DefaultMaximumProfitReceivingPeriodCountOfOneTime = 100;
}
2 changes: 2 additions & 0 deletions contract/AElf.Contracts.Profit/ProfitContractState.cs
Original file line number Diff line number Diff line change
Expand Up @@ -17,4 +17,6 @@ public partial class ProfitContractState : ContractState
public MappedState<string, MethodFees> TransactionFees { get; set; }

public SingletonState<AuthorityInfo> MethodFeeController { get; set; }

public SingletonState<int> MaximumProfitReceivingPeriodCount { get; set; }
}
Loading