tx · BYbomZ8figSv7VyqSjeS9Tidu8n5nSm5efzTaY495PQd

3PH75p2rmMKCV2nyW4TsAdFgFtmc61mJaqA:  -0.02400000 Waves

2023.03.07 16:06 [3545202] smart account 3PH75p2rmMKCV2nyW4TsAdFgFtmc61mJaqA > SELF 0.00000000 Waves

{ "type": 13, "id": "BYbomZ8figSv7VyqSjeS9Tidu8n5nSm5efzTaY495PQd", "fee": 2400000, "feeAssetId": null, "timestamp": 1678194416266, "version": 2, "chainId": 87, "sender": "3PH75p2rmMKCV2nyW4TsAdFgFtmc61mJaqA", "senderPublicKey": "3GtkwhnMmG1yeozW51o4dJ1x3BDToPaLBXyBWKGdAc2e", "proofs": [ "4C73o3c5hN6UxVL1LzusFgTQuhEic7MTZDg2xL11s77XihP91xNLhgb1oBgdNqjedVDxAYYdaHjxSHHCP3ZJTZkr" ], "script": "base64:AAIFAAAAAAAAADwIAhIDCgEIEgASBAoCCAgSBAoCCAgSABIAEgMKAQgSAwoBCBIDCgEIEgMKAQgSAwoBCBIDCgEIEgMKAQgAAAAwAAAAAApwZXJjaFByaWNlCQAAaAAAAAIAAAAAAAAAAGQAAAAAAAAPQkAAAAAABXNjYWxlAAAAAAAAACcQAAAAAAZzY2FsZTIAAAAAAAAPQkABAAAACmlzU2lja0R1Y2sAAAABAAAABmR1Y2tJZAkAASwAAAACBQAAAAZkdWNrSWQCAAAABV9zaWNrAQAAABR0cnlHZXRTdHJpbmdFeHRlcm5hbAAAAAIAAAAHYWRkcmVzcwAAAANrZXkEAAAAByRtYXRjaDAJAAQdAAAAAgUAAAAHYWRkcmVzcwUAAAADa2V5AwkAAAEAAAACBQAAAAckbWF0Y2gwAgAAAAZTdHJpbmcEAAAAAWEFAAAAByRtYXRjaDAFAAAAAWECAAAAAAEAAAAMdHJ5R2V0U3RyaW5nAAAAAQAAAANrZXkJAQAAABR0cnlHZXRTdHJpbmdFeHRlcm5hbAAAAAIFAAAABHRoaXMFAAAAA2tleQEAAAAJZ2V0T3JhY2xlAAAAAAkBAAAAB0FkZHJlc3MAAAABCQACWQAAAAEJAQAAAAx0cnlHZXRTdHJpbmcAAAABAgAAABRzdGF0aWNfb3JhY2xlQWRkcmVzcwEAAAANZ2V0RWdnQXNzZXRJZAAAAAAJAAJZAAAAAQkBAAAAFHRyeUdldFN0cmluZ0V4dGVybmFsAAAAAgkBAAAACWdldE9yYWNsZQAAAAACAAAAEXN0YXRpY19lZ2dBc3NldElkAQAAABNnZXRJbmN1YmF0b3JBZGRyZXNzAAAAAAkBAAAAB0FkZHJlc3MAAAABCQACWQAAAAEJAQAAABR0cnlHZXRTdHJpbmdFeHRlcm5hbAAAAAIJAQAAAAlnZXRPcmFjbGUAAAAAAgAAABdzdGF0aWNfaW5jdWJhdG9yQWRkcmVzcwEAAAARZ2V0UmViaXJ0aEFkZHJlc3MAAAAACQEAAAAHQWRkcmVzcwAAAAEJAAJZAAAAAQkBAAAAFHRyeUdldFN0cmluZ0V4dGVybmFsAAAAAgkBAAAACWdldE9yYWNsZQAAAAACAAAAFXN0YXRpY19yZWJpcnRoQWRkcmVzcwEAAAATZ2V0U3dvcFByb21vQWRkcmVzcwAAAAAJAQAAAAdBZGRyZXNzAAAAAQkAAlkAAAABCQEAAAAUdHJ5R2V0U3RyaW5nRXh0ZXJuYWwAAAACCQEAAAAJZ2V0T3JhY2xlAAAAAAIAAAAXc3RhdGljX3N3b3BQcm9tb0FkZHJlc3MBAAAAEWdldEJyZWVkZXJBZGRyZXNzAAAAAAkBAAAAB0FkZHJlc3MAAAABCQACWQAAAAEJAQAAABR0cnlHZXRTdHJpbmdFeHRlcm5hbAAAAAIJAQAAAAlnZXRPcmFjbGUAAAAAAgAAABVzdGF0aWNfYnJlZWRlckFkZHJlc3MBAAAAFWdldFJlZkNvbnRyYWN0QWRkcmVzcwAAAAAJAQAAAAdBZGRyZXNzAAAAAQkAAlkAAAABCQEAAAAUdHJ5R2V0U3RyaW5nRXh0ZXJuYWwAAAACCQEAAAAJZ2V0T3JhY2xlAAAAAAIAAAAZc3RhdGljX3JlZkNvbnRyYWN0QWRkcmVzcwEAAAAPZ2V0SXRlbXNBZGRyZXNzAAAAAAkBAAAAB0FkZHJlc3MAAAABCQACWQAAAAEJAQAAABR0cnlHZXRTdHJpbmdFeHRlcm5hbAAAAAIJAQAAAAlnZXRPcmFjbGUAAAAAAgAAABNzdGF0aWNfaXRlbXNBZGRyZXNzAQAAABJnZXRNZXRhcmFjZUFkZHJlc3MAAAAACQEAAAAHQWRkcmVzcwAAAAEJAAJZAAAAAQkBAAAAFHRyeUdldFN0cmluZ0V4dGVybmFsAAAAAgkBAAAACWdldE9yYWNsZQAAAAACAAAAFnN0YXRpY19tZXRhUmFjZUFkZHJlc3MBAAAAFGdldEFjY0Jvb3N0ZXJBZGRyZXNzAAAAAAkBAAAAB0FkZHJlc3MAAAABCQACWQAAAAEJAQAAABR0cnlHZXRTdHJpbmdFeHRlcm5hbAAAAAIJAQAAAAlnZXRPcmFjbGUAAAAAAgAAABhzdGF0aWNfYWNjQm9vc3RlckFkZHJlc3MBAAAAD2dldFByb3h5U3Rha2luZwAAAAAJAQAAABR0cnlHZXRTdHJpbmdFeHRlcm5hbAAAAAIJAQAAAAlnZXRPcmFjbGUAAAAAAgAAABxzdGF0aWNfcHJveHlTdGFraW5nQ29udHJhY3RzAQAAAA5nZXRNYWludGVuYW5jZQAAAAAJAQAAABR0cnlHZXRTdHJp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ABZwcmV2aW91c0ludGVyZXN0SGVpZ2h0AAAAEXRvdGFsRmFybWluZ1Bvd2VyCQAAZAAAAAIFAAAAEHByZXZpb3VzSW50ZXJlc3QJAABpAAAAAgkAAGgAAAACCQAAaAAAAAIFAAAABXNjYWxlCQEAAAARZ2V0UmV3YXJkUGVyQmxvY2sAAAAACQAAZQAAAAIFAAAABmhlaWdodAUAAAAWcHJldmlvdXNJbnRlcmVzdEhlaWdodAUAAAARdG90YWxGYXJtaW5nUG93ZXIBAAAAEmdldEN1cnJlbnRJbnRlcmVzdAAAAAADCQAAZgAAAAIJAQAAAA10cnlHZXRJbnRlZ2VyAAAAAQIAAAASdG90YWxfZmFybWluZ1Bvd2VyAAAAAAAAAAAABAAAABBwcmV2aW91c0ludGVyZXN0CQEAAAANdHJ5R2V0SW50ZWdlcgAAAAECAAAAF3RvdGFsX2xhc3RDaGVja0ludGVyZXN0BAAAABZwcmV2aW91c0ludGVyZXN0SGVpZ2h0CQEAAAANdHJ5R2V0SW50ZWdlcgAAAAECAAAAHXRvdGFsX2xhc3RDaGVja0ludGVyZXN0SGVpZ2h0BAAAABF0b3RhbEZhcm1pbmdQb3dlcgkBAAAADXRyeUdldEludGVnZXIAAAABAgAAABJ0b3RhbF9mYXJtaW5nUG93ZXIJAQAAAAxjYWxjSW50ZXJlc3QAAAADBQAAABBwcmV2aW91c0ludGVyZXN0BQAAABZwcmV2aW91c0ludGVyZXN0SGVpZ2h0BQAAABF0b3RhbEZhcm1pbmdQb3dlcgMJAQAAAAIhPQAAAAIJAQAAAA10cnlHZXRJbnRlZ2VyAAAAAQIAAAARdG90YWxfc3RhcnRIZWlnaHQAAAAAAAAAAAAJAQAAAA10cnlHZXRJbnRlZ2VyAAAAAQIAAAAXdG90YWxfbGFzdENoZWNrSW50ZXJlc3QJAAACAAAAAQIAAAAcZmFybWluZyBpcyBub3QgbGF1bmNoZWQsIHlldAEAAAAUY2FsY0Fzc2V0UmV3YXJkRGVsdGEAAAADAAAAB2FkZHJlc3MAAAAHYXNzZXRJZAAAABFhc3NldEZhcm1pbmdQb3dlcgQAAAAWbGFzdENoZWNrQXNzZXRJbnRlcmVzdAkBAAAADXRyeUdldEludGVnZXIAAAABCQABLAAAAAIJAAEsAAAAAgkAASwAAAACCQABLAAAAAICAAAACGFkZHJlc3NfBQAAAAdhZGRyZXNzAgAAAAdfYXNzZXRfBQAAAAdhc3NldElkAgAAABJfbGFzdENoZWNrSW50ZXJlc3QEAAAAD2N1cnJlbnRJbnRlcmVzdAkBAAAAEmdldEN1cnJlbnRJbnRlcmVzdAAAAAAJAABoAAAAAgUAAAARYXNzZXRGYXJtaW5nUG93ZXIJAABlAAAAAgUAAAAPY3VycmVudEludGVyZXN0BQAAABZsYXN0Q2hlY2tBc3NldEludGVyZXN0AQAAABRhZGRBc3NldElkVG9HZW5FbnRyeQAAAAIAAAAHYXNzZXRJZAAAAAhhc3NldEdlbgQAAAAMY3VycmVudFZhbHVlCQEAAAAMdHJ5R2V0U3RyaW5nAAAAAQkAASwAAAACCQABLAAAAAICAAAAB2Fzc2V0c18FAAAACGFzc2V0R2VuAgAAAAdfbG9ja2VkAwkAAAAAAAACBQAAAAxjdXJyZW50VmFsdWUCAAAAAAUAAAAHYXNzZXRJZAkAASwAAAACCQABLAAAAAIFAAAADGN1cnJlbnRWYWx1ZQIAAAABLAUAAAAHYXNzZXRJZAEAAAAOZ2V0U3Rha2VSZXN1bHQAAAAEAAAAB2FkZHJlc3MAAAAHYXNzZXRJZAAAABFhc3NldEZhcm1pbmdQb3dlcgAAAAh1bnN0YWtlcgQAAAAFYXNzZXQJAAJYAAAAAQUAAAAHYXNzZXRJZAkABEwAAAACCQEAAAAMSW50ZWdlckVudHJ5AAAAAgIAAAASdG90YWxfZmFybWluZ1Bvd2VyCQAAZAAAAAIJAQAAAA10cnlHZXRJbnRlZ2VyAAAAAQIAAAASdG90YWxfZmFybWluZ1Bvd2VyBQAAABFhc3NldEZhcm1pbmdQb3dlcgkABEwAAAACCQEAAAAMSW50ZWdlckVudHJ5AAAAAgIAAAAXdG90YWxfbGFzdENoZWNrSW50ZXJlc3QJAQAAABJnZXRDdXJyZW50SW50ZXJlc3QAAAAACQAETAAAAAIJAQAAAAxJbnRlZ2VyRW50cnkAAAACAgAAAB10b3RhbF9sYXN0Q2hlY2tJbnRlcmVzdEhlaWdodAUAAAAGaGVpZ2h0CQAETAAAAAIJAQAAAAtTdHJpbmdFbnRyeQAAAAIJAAEsAAAAAgkAASwAAAACAgAAAAZhc3NldF8FAAAABWFzc2V0AgAAAAZfb3duZXIFAAAAB2FkZHJlc3MJAARMAAAAAgkBAAAADEludGVnZXJFbnRyeQAAAAIJAAEsAAAAAgkAASwAAAACCQABLAAAAAIJAAEsAAAAAgIAAAAIYWRkcmVzc18FAAAAB2FkZHJlc3MCAAAAB19hc3NldF8FAAAABWFzc2V0AgAAAA1fZmFybWluZ1Bvd2VyBQAAABFhc3NldEZhcm1pbmdQb3dlcgkABEwAAAACCQEAAAAMSW50ZWdlckVudHJ5AAAAAgkAASwAAAACCQABLAAAAAIJAAEsAAAAAgkAASwAAAACAgAAAAhhZGRyZXNzXwUAAAAHYWRkcmVzcwIAAAAHX2Fzc2V0XwUAAAAFYXNzZXQCAAAAEl9sYXN0Q2hlY2tJbnRlcmVzdAkBAAAAEmdldEN1cnJlbnRJbnRlcmVzdAAAAAAJAARMAAAAAgkBAAAAC1N0cmluZ0VudHJ5AAAAAgkAASwAAAACCQABLAAAAAIJAAEsAAAAAgkAASwAAAACAgAAAAhhZGRyZXNzXwUAAAAHYWRkcmVzcwIAAAAHX2Fzc2V0XwUAAAAFYXNzZXQCAAAACV91bnN0YWtlcgUAAAAIdW5zdGFrZXIFAAAAA25pbAEAAAAQZ2V0VW5zdGFrZVJlc3VsdAAAAAYAAAAHYWRkcmVzcwAAAAdhc3NldElkAAAABWNvbG9yAAAABmNhbGxlcgAAAApyZWFsQ2FsbGVyAAAACWNsYWltRWdncwQAAAAGbG9ja2VkCQEAAAAIaXNMb2NrZWQAAAAAAwkAAAAAAAACBQAAAAZsb2NrZWQFAAAABmxvY2tlZAQAAAAFYXNzZXQJAAJYAAAAAQUAAAAHYXNzZXRJZAQAAAAIdW5zdGFrZXIJAQAAAAx0cnlHZXRTdHJpbmcAAAABCQABLAAAAAIJAAEsAAAAAgkAASwAAAACCQABLAAAAAICAAAACGFkZHJlc3NfBQAAAAdhZGRyZXNzAgAAAAdfYXNzZXRfBQAAAAVhc3NldAIAAAAJX3Vuc3Rha2VyAwMJAQAAAAIhPQAAAAIFAAAACHVuc3Rha2VyAgAAAAAJAQAAAAIhPQAAAAIFAAAACHVuc3Rha2VyBQAAAApyZWFsQ2FsbGVyBwkAAAIAAAABAgAAAFdGVU46IEl0IHNlZW1zIGR1Y2sgd2FzIHN0YWtlZCB0aHJvdWggYSBkYXBwLCBub3QgZGlyZWN0bHksIHBsZWFzZSB1bnN0YWtlIHRocm91Z2ggZGFwcCEEAAAAEWFzc2V0RmFybWluZ1Bvd2VyCQEAAAAdZ2V0TGFzdEtub3duQXNzZXRGYXJtaW5nUG93ZXIAAAACBQAAAAdhZGRyZXNzBQAAAAVhc3NldAMJAQAAAAEhAAAAAQkAAGYAAAACBQAAABFhc3NldEZhcm1pbmdQb3dlcgAAAAAAAAAAAAkAAAIAAAABAgAAACpGR1U6IEFzc2V0IGZhcm1pbmcgcG93ZXIgbm90IGJpZ2dlciB0aGVuIDAEAAAAEGFzc2V0UmV3YXJkRGVsdGEJAQAAABRjYWxjQXNzZXRSZXdhcmREZWx0YQAAAAMFAAAAB2FkZHJlc3MFAAAABWFzc2V0BQAAABFhc3NldEZhcm1pbmdQb3dlcgQAAAAMZmFybWVkQW1vdW50CQAAZAAAAAIFAAAAEGFzc2V0UmV3YXJkRGVsdGEJAQAAAA10cnlHZXRJbnRlZ2VyAAAAAQkAASwAAAACCQABLAAAAAIJAAEsAAAAAgkAASwAAAACAgAAAAhhZGRyZXNzXwUAAAAHYWRkcmVzcwIAAAAHX2Fzc2V0XwUAAAAFYXNzZXQCAAAAFl9sYXN0Q2hlY2tGYXJtZWRBbW91bnQEAAAAD3dpdGhkcmF3bkFtb3VudAkBAAAADXRyeUdldEludGVnZXIAAAABCQABLAAAAAIJAAEsAAAAAgkAASwAAAACCQABLAAAAAICAAAACGFkZHJlc3NfBQAAAAdhZGRyZXNzAgAAAAdfYXNzZXRfBQAAAAVhc3NldAIAAAAQX3dpdGhkcmF3bkFtb3VudAQAAAAGcmV3YXJkCQAAaQAAAAIJAABlAAAAAgUAAAAMZmFybWVkQW1vdW50BQAAAA93aXRoZHJhd25BbW91bnQJAABoAAAAAgUAAAAFc2NhbGUAAAAAAAAAAGQEAAAADmlzV2l0aG91dFBlcmNoCQEAAAANdHJ5R2V0Qm9vbGVhbgAAAAEJAAEsAAAAAgkAASwAAAACCQABLAAAAAIJAAEsAAAAAgIAAAAIYWRkcmVzc18FAAAAB2FkZHJlc3MCAAAAB19hc3NldF8FAAAABWFzc2V0AgAAAA5fd2l0aG91dF9wZXJjaAQAAAANc2lja25lc3NDaGVjawcEAAAAE3Jld2FyZEFmdGVyU2lja05lc3MDBQAAAA1zaWNrbmVzc0NoZWNrAAAAAAAAAAAABQAAAAZyZXdhcmQEAAAADWFwcGVuZFBlcmNoZXMDBQAAAA5pc1dpdGhvdXRQZXJjaAkABEwAAAACCQEAAAALRGVsZXRlRW50cnkAAAABCQABLAAAAAIJAAEsAAAAAgkAASwAAAACCQABLAAAAAICAAAACGFkZHJlc3NfBQAAAAdhZGRyZXNzAgAAAAdfYXNzZXRfBQAAAAVhc3NldAIAAAAOX3dpdGhvdXRfcGVyY2gFAAAAA25pbAkABEwAAAACCQEAAAAMSW50ZWdlckVudHJ5AAAAAgkAASwAAAACCQABLAAAAAIJAAEsAAAAAgIAAAAIYWRkcmVzc18FAAAAB2FkZHJlc3MCAAAAEl9wZXJjaGVzQXZhaWxhYmxlXwUAAAAFY29sb3IJAABkAAAAAgkBAAAADXRyeUdldEludGVnZXIAAAABCQABLAAAAAIJAAEsAAAAAgkAASwAAAACAgAAAAhhZGRyZXNzXwUAAAAHYWRkcmVzcwIAAAASX3BlcmNoZXNBdmFpbGFibGVfBQAAAAVjb2xvcgAAAAAAAAAAAQUAAAADbmlsBAAAAAZzZW5kVHgDBQAAAAljbGFpbUVnZ3MJAAUUAAAAAgkABEwAAAACCQEAAAAOU2NyaXB0VHJhbnNmZXIAAAADBQAAAAZjYWxsZXIJAABoAAAAAgUAAAATcmV3YXJkQWZ0ZXJTaWNrTmVzcwAAAAAAAA9CQAkBAAAADWdldEVnZ0Fzc2V0SWQAAAAABQAAAANuaWwJAABoAAAAAgUAAAATcmV3YXJkQWZ0ZXJTaWNrTmVzcwAAAAAAAA9CQAkABRQAAAACBQAAAANuaWwAAAAAAAAAAAAJAAUUAAAAAgkABE4AAAACCQAETgAAAAIJAAROAAAAAgkABEwAAAACCQEAAAAMSW50ZWdlckVudHJ5AAAAAgIAAAASdG90YWxfZmFybWluZ1Bvd2VyCQAAZQAAAAIJAQAAAA10cnlHZXRJbnRlZ2VyAAAAAQIAAAASdG90YWxfZmFybWluZ1Bvd2VyBQAAABFhc3NldEZhcm1pbmdQb3dlcgkABEwAAAACCQEAAAAMSW50ZWdlckVudHJ5AAAAAgIAAAAXdG90YWxfbGFzdENoZWNrSW50ZXJlc3QJAQAAABJnZXRDdXJyZW50SW50ZXJlc3QAAAAACQAETAAAAAIJAQAAAAxJbnRlZ2VyRW50cnkAAAACAgAAAB10b3RhbF9sYXN0Q2hlY2tJbnRlcmVzdEhlaWdodAUAAAAGaGVpZ2h0CQAETAAAAAIJAQAAAAtEZWxldGVFbnRyeQAAAAEJAAEsAAAAAgkAASwAAAACAgAAAAZhc3NldF8FAAAABWFzc2V0AgAAAAZfb3duZXIJAARMAAAAAgkBAAAAC0RlbGV0ZUVudHJ5AAAAAQkAASwAAAACCQABLAAAAAIJAAEsAAAAAgkAASwAAAACAgAAAAhhZGRyZXNzXwUAAAAHYWRkcmVzcwIAAAAHX2Fzc2V0XwUAAAAFYXNzZXQCAAAACV91bnN0YWtlcgkABEwAAAACCQEAAAAMSW50ZWdlckVudHJ5AAAAAgkAASwAAAACCQABLAAAAAIJAAEsAAAAAgkAASwAAAACAgAAAAhhZGRyZXNzXwUAAAAHYWRkcmVzcwIAAAAHX2Fzc2V0XwUAAAAFYXNzZXQCAAAADV9mYXJtaW5nUG93ZXIAAAAAAAAAAAAJAARMAAAAAgkBAAAADEludGVnZXJFbnRyeQAAAAIJAAEsAAAAAgkAASwAAAACCQABLAAAAAIJAAEsAAAAAgIAAAAIYWRkcmVzc18FAAAAB2FkZHJlc3MCAAAAB19hc3NldF8FAAAABWFzc2V0AgAAABJfbGFzdENoZWNrSW50ZXJlc3QJAQAAABJnZXRDdXJyZW50SW50ZXJlc3QAAAAACQAETAAAAAIJAQAAAAxJbnRlZ2VyRW50cnkAAAACCQABLAAAAAIJAAEsAAAAAgkAASwAAAACCQABLAAAAAICAAAACGFkZHJlc3NfBQAAAAdhZGRyZXNzAgAAAAdfYXNzZXRfBQAAAAVhc3NldAIAAAAQX3dpdGhkcmF3bkFtb3VudAkAAGQAAAACBQAAAA93aXRoZHJhd25BbW91bnQJAABoAAAAAgUAAAATcmV3YXJkQWZ0ZXJTaWNrTmVzcwUAAAAGc2NhbGUyCQAETAAAAAIJAQAAAAxJbnRlZ2VyRW50cnkAAAACCQABLAAAAAIJAAEsAAAAAgkAASwAAAACCQABLAAAAAICAAAACGFkZHJlc3NfBQAAAAdhZGRyZXNzAgAAAAdfYXNzZXRfBQAAAAVhc3NldAIAAAAWX2xhc3RDaGVja0Zhcm1lZEFtb3VudAkAAGQAAAACCQEAAAANdHJ5R2V0SW50ZWdlcgAAAAEJAAEsAAAAAgkAASwAAAACCQABLAAAAAIJAAEsAAAAAgIAAAAIYWRkcmVzc18FAAAAB2FkZHJlc3MCAAAAB19hc3NldF8FAAAABWFzc2V0AgAAABZfbGFzdENoZWNrRmFybWVkQW1vdW50BQAAABBhc3NldFJld2FyZERlbHRhBQAAAANuaWwFAAAADWFwcGVuZFBlcmNoZXMJAARMAAAAAgkBAAAADlNjcmlwdFRyYW5zZmVyAAAAAwUAAAAGY2FsbGVyAAAAAAAAAAABBQAAAAdhc3NldElkBQAAAANuaWwIBQAAAAZzZW5kVHgAAAACXzEIBQAAAAZzZW5kVHgAAAACXzIJAAACAAAAAQIAAAAkU3RyaWN0IHZhbHVlIGlzIG5vdCBlcXVhbCB0byBpdHNlbGYuAQAAABNjYWxjdWxhdGVQZXJjaFByaWNlAAAAAQAAAAdhZGRyZXNzBAAAABFoYXNBcnRlZmFjdFN0YWtlZAkBAAAAFHRyeUdldFN0cmluZ0V4dGVybmFsAAAAAgkBAAAAFGdldEFjY0Jvb3N0ZXJBZGRyZXNzAAAAAAkAASwAAAACCQABLAAAAAICAAAAC0FSVC1YTUlTVExfBQAAAAdhZGRyZXNzAgAAAAZfb3duZXIDCQAAAAAAAAIFAAAAEWhhc0FydGVmYWN0U3Rha2VkAgAAAAAFAAAACnBlcmNoUHJpY2UJAABoAAAAAgkAAGkAAAACBQAAAApwZXJjaFByaWNlAAAAAAAAAAAKAAAAAAAAAAAJAQAAABBpc1Byb3h5U3Rha2luZ1NjAAAAAQAAAAdhZGRyZXNzBAAAABBhbGxvd2VkQ29udHJhY3RzCQEAAAAPZ2V0UHJveHlTdGFraW5nAAAAAAQAAAAUYWxsb3dlZENvbnRyYWN0c0xpc3QJAAS1AAAAAgUAAAAQYWxsb3dlZENvbnRyYWN0cwIAAAABOwkBAAAAAiE9AAAAAgkABE8AAAACBQAAABRhbGxvd2VkQ29udHJhY3RzTGlzdAUAAAAHYWRk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AAAAEmdldENmTWFzdGVyQWRkcmVzcwAAAAAJAAQlAAAAAQgFAAAAAWkAAAAGY2FsbGVyCQAEJQAAAAEIBQAAAAFpAAAADG9yaWdpbkNhbGxlcgQAAAAHYXNzZXRJZAkAAlkAAAABBQAAAAVhc3NldAQAAAANc2lja25lc3NDaGVjawcDBQAAAA1zaWNrbmVzc0NoZWNrBAAAABFhc3NldEZhcm1pbmdQb3dlcgkBAAAAHWdldExhc3RLbm93bkFzc2V0RmFybWluZ1Bvd2VyAAAAAgUAAAAHYWRkcmVzcwUAAAAFYXNzZXQJAARMAAAAAgkBAAAADEludGVnZXJFbnRyeQAAAAICAAAAEnRvdGFsX2Zhcm1pbmdQb3dlcgkAAGUAAAACCQEAAAANdHJ5R2V0SW50ZWdlcgAAAAECAAAAEnRvdGFsX2Zhcm1pbmdQb3dlcgUAAAARYXNzZXRGYXJtaW5nUG93ZXIJAARMAAAAAgkBAAAADEludGVnZXJFbnRyeQAAAAIJAAEsAAAAAgkAASwAAAACCQABLAAAAAIJAAEsAAAAAgIAAAAIYWRkcmVzc18FAAAAB2FkZHJlc3MCAAAAB19hc3NldF8FAAAABWFzc2V0AgAAAA1fZmFybWluZ1Bvd2VyAAAAAAAAAAAABQAAAANuaWwEAAAAEWFzc2V0RmFybWluZ1Bvd2VyCQEAAAAdZ2V0TGFzdEtub3duQXNzZXRGYXJtaW5nUG93ZXIAAAACBQAAAAdhZGRyZXNzBQAAAAVhc3NldAQAAAAQYXNzZXRSZXdhcmREZWx0YQkBAAAAFGNhbGNBc3NldFJld2FyZERlbHRhAAAAAwUAAAAHYWRkcmVzcwUAAAAFYXNzZXQFAAAAEWFzc2V0RmFybWluZ1Bvd2VyBAAAAAxmYXJtZWRBbW91bnQJAABkAAAAAgUAAAAQYXNzZXRSZXdhcmREZWx0YQkBAAAADXRyeUdldEludGVnZXIAAAABCQABLAAAAAIJAAEsAAAAAgkAASwAAAACCQABLAAAAAICAAAACGFkZHJlc3NfBQAAAAdhZGRyZXNzAgAAAAdfYXNzZXRfBQAAAAVhc3NldAIAAAAWX2xhc3RDaGVja0Zhcm1lZEFtb3VudAQAAAAPd2l0aGRyYXduQW1vdW50CQEAAAANdHJ5R2V0SW50ZWdlcgAAAAEJAAEsAAAAAgkAASwAAAACCQABLAAAAAIJAAEsAAAAAgIAAAAIYWRkcmVzc18FAAAAB2FkZHJlc3MCAAAAB19hc3NldF8FAAAABWFzc2V0AgAAABBfd2l0aGRyYXduQW1vdW50BAAAAAZyZXdhcmQJAABpAAAAAgkAAGUAAAACBQAAAAxmYXJtZWRBbW91bnQFAAAAD3dpdGhkcmF3bkFtb3VudAkAAGgAAAACBQAAAAVzY2FsZQAAAAAAAAAAZAMJAABnAAAAAgAAAAAAAAAAAAUAAAAGcmV3YXJkCQAAAgAAAAECAAAAIUZDUjogeW91IGhhdmUgbm8gRUdHcyB0byB3aXRoZHJhdwkABRQAAAACCQAETAAAAAIJAQAAAAxJbnRlZ2VyRW50cnkAAAACCQABLAAAAAIJAAEsAAAAAgkAASwAAAACCQABLAAAAAICAAAACGFkZHJlc3NfBQAAAAdhZGRyZXNzAgAAAAdfYXNzZXRfBQAAAAVhc3NldAIAAAAQX3dpdGhkcmF3bkFtb3VudAkAAGQAAAACCQEAAAANdHJ5R2V0SW50ZWdlcgAAAAEJAAEsAAAAAgkAASwAAAACCQABLAAAAAIJAAEsAAAAAgIAAAAIYWRkcmVzc18FAAAAB2FkZHJlc3MCAAAAB19hc3NldF8FAAAABWFzc2V0AgAAABBfd2l0aGRyYXduQW1vdW50CQAAaAAAAAIFAAAABnJld2FyZAUAAAAGc2NhbGUyCQAETAAAAAIJAQAAAA5TY3JpcHRUcmFuc2ZlcgAAAAMJAQAAAAdBZGRyZXNzAAAAAQkAAlkAAAABBQAAAAdhZGRyZXNzCQAAaAAAAAIFAAAABnJld2FyZAAAAAAAAA9CQAkBAAAADWdldEVnZ0Fzc2V0SWQAAAAABQAAAANuaWwJAABoAAAAAgUAAAAGcmV3YXJkAAAAAAAAD0JACQAAAgAAAAECAAAAJFN0cmljdCB2YWx1ZSBpcyBub3QgZXF1YWwgdG8gaXRzZWxmLgAAAAFpAQAAAAhoZWFsRHVjawAAAAEAAAAGZHVja0lkBAAAAAdhZGRyZXNzAwkBAAAAEGlzUHJveHlTdGFraW5nU2MAAAABCQAEJQAAAAEIBQAAAAFpAAAABmNhbGxlcgkABCUAAAABCAUAAAABaQAAAAxvcmlnaW5DYWxsZXIJAAQlAAAAAQgFAAAAAWkAAAAGY2FsbGVyBAAAAAxmYXJtaW5nUG93ZXIICQEAAAAUZ2V0QXNzZXRGYXJtaW5nUG93ZXIAAAACCQABmwAAAAEFAAAABmR1Y2tJZAUAAAAHYWRkcmVzcwAAAAJfMgkABEwAAAACCQEAAAAMSW50ZWdlckVudHJ5AAAAAgIAAAASdG90YWxfZmFybWluZ1Bvd2VyCQAAZAAAAAIJAQAAAA10cnlHZXRJbnRlZ2VyAAAAAQIAAAASdG90YWxfZmFybWluZ1Bvd2VyBQAAAAxmYXJtaW5nUG93ZXIJAARMAAAAAgkBAAAADEludGVnZXJFbnRyeQAAAAIJAAEsAAAAAgkAASwAAAACCQABLAAAAAIJAAEsAAAAAgIAAAAIYWRkcmVzc18FAAAAB2FkZHJlc3MCAAAAB19hc3NldF8FAAAABmR1Y2tJZAIAAAANX2Zhcm1pbmdQb3dlcgUAAAAMZmFybWluZ1Bvd2VyBQAAAANuaWwAAAABAAAAAnR4AQAAAAZ2ZXJpZnkAAAAAAwkBAAAACWlzVGVzdEVudgAAAAAJAAH0AAAAAwgFAAAAAnR4AAAACWJvZHlCeXRlcwkAAZEAAAACCAUAAAACdHgAAAAGcHJvb2ZzAAAAAAAAAAAACAUAAAACdHgAAAAPc2VuZGVyUHVibGljS2V5BAAAAAlmaXJzdFVzZXIBAAAAIN7WxlHkUxbQZYDrAZoqC9D3l1H6HHaRfpuOBkN3F70lBAAAAApzZWNvbmRVc2VyAQAAACDBbN+O7dONc4+Lovn6iQ/0dc1EG1RyUqO0nNJWpC3gdQQAAAAJdGhpcmRVc2VyAQAAACDnW/SOqtL5SZ5uhCa4+X4f3GeofdwruNTqe83yaArBJQQAAAAPZmlyc3RVc2VyU2lnbmVkAwkAAfQAAAADCAUAAAACdHgAAAAJYm9keUJ5dGVzCQABkQAAAAIIBQAAAAJ0eAAAAAZwcm9vZnMAAAAAAAAAAAAFAAAACWZpcnN0VXNlcgAAAAAAAAAAAQMJAAH0AAAAAwgFAAAAAnR4AAAACWJvZHlCeXRlcwkAAZEAAAACCAUAAAACdHgAAAAGcHJvb2ZzAAAAAAAAAAABBQAAAAlmaXJzdFVzZXIAAAAAAAAAAAEDCQAB9AAAAAMIBQAAAAJ0eAAAAAlib2R5Qnl0ZXMJAAGRAAAAAggFAAAAAnR4AAAABnByb29mcwAAAAAAAAAAAgUAAAAJZmlyc3RVc2VyAAAAAAAAAAABAAAAAAAAAAAABAAAABBzZWNvbmRVc2VyU2lnbmVkAwkAAfQAAAADCAUAAAACdHgAAAAJYm9keUJ5dGVzCQABkQAAAAIIBQAAAAJ0eAAAAAZwcm9vZnMAAAAAAAAAAAAFAAAACnNlY29uZFVzZXIAAAAAAAAAAAEDCQAB9AAAAAMIBQAAAAJ0eAAAAAlib2R5Qnl0ZXMJAAGRAAAAAggFAAAAAnR4AAAABnByb29mcwAAAAAAAAAAAQUAAAAKc2Vjb25kVXNlcgAAAAAAAAAAAQMJAAH0AAAAAwgFAAAAAnR4AAAACWJvZHlCeXRlcwkAAZEAAAACCAUAAAACdHgAAAAGcHJvb2ZzAAAAAAAAAAACBQAAAApzZWNvbmRVc2VyAAAAAAAAAAABAAAAAAAAAAAABAAAAA90aGlyZFVzZXJTaWduZWQDCQAB9AAAAAMIBQAAAAJ0eAAAAAlib2R5Qnl0ZXMJAAGRAAAAAggFAAAAAnR4AAAABnByb29mcwAAAAAAAAAAAAUAAAAJdGhpcmRVc2VyAAAAAAAAAAABAwkAAfQAAAADCAUAAAACdHgAAAAJYm9keUJ5dGVzCQABkQAAAAIIBQAAAAJ0eAAAAAZwcm9vZnMAAAAAAAAAAAEFAAAACXRoaXJkVXNlcgAAAAAAAAAAAQMJAAH0AAAAAwgFAAAAAnR4AAAACWJvZHlCeXRlcwkAAZEAAAACCAUAAAACdHgAAAAGcHJvb2ZzAAAAAAAAAAACBQAAAAl0aGlyZFVzZXIAAAAAAAAAAAEAAAAAAAAAAAAEAAAAD3NpZ25hdHVyZXNDb3VudAkAAGQAAAACCQAAZAAAAAIFAAAAD2ZpcnN0VXNlclNpZ25lZAUAAAAQc2Vjb25kVXNlclNpZ25lZAUAAAAPdGhpcmRVc2VyU2lnbmVkBAAAAAckbWF0Y2gwBQAAAAJ0eAkAAGcAAAACBQAAAA9zaWduYXR1cmVzQ291bnQAAAAAAAAAAAL3Crff", "height": 3545202, "applicationStatus": "succeeded", "spentComplexity": 0 } View: original | compacted Prev: 3CTrUqFetAemXcyj5wiCmYAPumxYspnX2EKzrgdu36G5 Next: AAKAmXwEhrvuVLTbRxYahmXtwXZ46J7SQmQfYtQihge6 Diff:
OldNewDifferences
6767
6868
6969 func getBurnAddress () = Address(fromBase58String(tryGetStringExternal(getOracle(), "static_burnAddress")))
70-
71-
72-func getSicknessAddress () = Address(fromBase58String(tryGetStringExternal(getOracle(), "static_sicknessAddress")))
7370
7471
7572 let RefererReward = 5
241238 let withdrawnAmount = tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_withdrawnAmount"))
242239 let reward = ((farmedAmount - withdrawnAmount) / (scale * 100))
243240 let isWithoutPerch = tryGetBoolean((((("address_" + address) + "_asset_") + asset) + "_without_perch"))
244- let sicknessCheck = asBoolean(invoke(getSicknessAddress(), "checkIfDuckGetSick", [asset], nil))
245- if ((sicknessCheck == sicknessCheck))
246- then {
247- let rewardAfterSickNess = if (sicknessCheck)
248- then 0
249- else reward
250- let appendPerches = if (isWithoutPerch)
251- then [DeleteEntry((((("address_" + address) + "_asset_") + asset) + "_without_perch"))]
252- else [IntegerEntry(((("address_" + address) + "_perchesAvailable_") + color), (tryGetInteger(((("address_" + address) + "_perchesAvailable_") + color)) + 1))]
253- let sendTx = if (claimEggs)
254- then $Tuple2([ScriptTransfer(caller, (rewardAfterSickNess * 1000000), getEggAssetId())], (rewardAfterSickNess * 1000000))
255- else $Tuple2(nil, 0)
256- $Tuple2(((([IntegerEntry("total_farmingPower", (tryGetInteger("total_farmingPower") - assetFarmingPower)), IntegerEntry("total_lastCheckInterest", getCurrentInterest()), IntegerEntry("total_lastCheckInterestHeight", height), DeleteEntry((("asset_" + asset) + "_owner")), DeleteEntry((((("address_" + address) + "_asset_") + asset) + "_unstaker")), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_farmingPower"), 0), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_lastCheckInterest"), getCurrentInterest()), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_withdrawnAmount"), (withdrawnAmount + (rewardAfterSickNess * scale2))), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_lastCheckFarmedAmount"), (tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_lastCheckFarmedAmount")) + assetRewardDelta))] ++ appendPerches) ++ [ScriptTransfer(caller, 1, assetId)]) ++ sendTx._1), sendTx._2)
257- }
258- else throw("Strict value is not equal to itself.")
241+ let sicknessCheck = false
242+ let rewardAfterSickNess = if (sicknessCheck)
243+ then 0
244+ else reward
245+ let appendPerches = if (isWithoutPerch)
246+ then [DeleteEntry((((("address_" + address) + "_asset_") + asset) + "_without_perch"))]
247+ else [IntegerEntry(((("address_" + address) + "_perchesAvailable_") + color), (tryGetInteger(((("address_" + address) + "_perchesAvailable_") + color)) + 1))]
248+ let sendTx = if (claimEggs)
249+ then $Tuple2([ScriptTransfer(caller, (rewardAfterSickNess * 1000000), getEggAssetId())], (rewardAfterSickNess * 1000000))
250+ else $Tuple2(nil, 0)
251+ $Tuple2(((([IntegerEntry("total_farmingPower", (tryGetInteger("total_farmingPower") - assetFarmingPower)), IntegerEntry("total_lastCheckInterest", getCurrentInterest()), IntegerEntry("total_lastCheckInterestHeight", height), DeleteEntry((("asset_" + asset) + "_owner")), DeleteEntry((((("address_" + address) + "_asset_") + asset) + "_unstaker")), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_farmingPower"), 0), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_lastCheckInterest"), getCurrentInterest()), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_withdrawnAmount"), (withdrawnAmount + (rewardAfterSickNess * scale2))), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_lastCheckFarmedAmount"), (tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_lastCheckFarmedAmount")) + assetRewardDelta))] ++ appendPerches) ++ [ScriptTransfer(caller, 1, assetId)]) ++ sendTx._1), sendTx._2)
259252 }
260253 }
261254 }
310303 }
311304
312305
306+func getBool (key) = match getBoolean(this, key) {
307+ case b: Boolean =>
308+ b
309+ case _ =>
310+ false
311+}
312+
313+
314+func isTestEnv () = getBool("TESTENV")
315+
316+
313317 @Callable(i)
314318 func configureOracle (oracle) = if ((i.caller != this))
315319 then throw("FCO: admin only")
325329
326330
327331 @Callable(i)
328-func buyPerch (color,refererAddress) = {
332+func buyPerch (colorI,refererAddress) = {
329333 let locked = isLocked()
330334 if ((locked == locked))
331- then if ((0 > value(indexOf(["B", "R", "G", "Y"], color))))
332- then throw("you need to set color properly")
333- else {
334- let exactPrice = calculatePerchPrice(toString(i.caller))
335- let leftToPay = if ((i.originCaller == i.caller))
336- then {
337- let amountPaidByCoupons = asInt(invoke(getCouponsAddress(), "useCoupons", [exactPrice], nil))
338- if ((amountPaidByCoupons == amountPaidByCoupons))
339- then (exactPrice - amountPaidByCoupons)
340- else throw("Strict value is not equal to itself.")
341- }
342- else exactPrice
343- let payment = if ((leftToPay != 0))
344- then {
345- let firstPayment = value(i.payments[0])
346- if ((firstPayment.assetId != getEggAssetId()))
347- then throw(("FBP: You can attach only EGG tokens with the following asset id: " + toBase58String(getEggAssetId())))
348- else if ((firstPayment.amount != leftToPay))
349- then throw(((("FBP: To buy a perch you currently need the following amount of EGGlets: " + toString(leftToPay)) + " ") + toString(i.caller)))
350- else {
351- let refererRewardForPerch = fraction(leftToPay, RefererReward, 100)
352- let refCall = invoke(getRefContractAddress(), "refPayment", [refererAddress], [AttachedPayment(getEggAssetId(), refererRewardForPerch)])
353- if ((refCall == refCall))
354- then {
355- let burnCall = invoke(getBurnAddress(), "burnAttachedPayments", nil, [AttachedPayment(getEggAssetId(), (leftToPay - refererRewardForPerch))])
356- if ((burnCall == burnCall))
357- then leftToPay
358- else throw("Strict value is not equal to itself.")
359- }
360- else throw("Strict value is not equal to itself.")
361- }
362- }
363- else 0
364- if ((payment == payment))
365- then {
366- let perchAmountKey = ((("address_" + toString(i.caller)) + "_perchesAvailable_") + color)
367- let perchAmount = tryGetInteger(perchAmountKey)
335+ then {
336+ let color = if ((colorI == "U"))
337+ then "B"
338+ else colorI
339+ if ((0 > value(indexOf(["B", "R", "G", "Y"], color))))
340+ then throw("you need to set color properly")
341+ else {
342+ let exactPrice = calculatePerchPrice(toString(i.caller))
343+ let leftToPay = if ((i.originCaller == i.caller))
344+ then {
345+ let amountPaidByCoupons = asInt(invoke(getCouponsAddress(), "useCoupons", [exactPrice], nil))
346+ if ((amountPaidByCoupons == amountPaidByCoupons))
347+ then (exactPrice - amountPaidByCoupons)
348+ else throw("Strict value is not equal to itself.")
349+ }
350+ else exactPrice
351+ let payment = if ((leftToPay != 0))
352+ then {
353+ let firstPayment = value(i.payments[0])
354+ if ((firstPayment.assetId != getEggAssetId()))
355+ then throw(("FBP: You can attach only EGG tokens with the following asset id: " + toBase58String(getEggAssetId())))
356+ else if ((firstPayment.amount != leftToPay))
357+ then throw(((("FBP: To buy a perch you currently need the following amount of EGGlets: " + toString(leftToPay)) + " ") + toString(i.caller)))
358+ else {
359+ let refererRewardForPerch = fraction(leftToPay, RefererReward, 100)
360+ let refCall = invoke(getRefContractAddress(), "refPayment", [refererAddress], [AttachedPayment(getEggAssetId(), refererRewardForPerch)])
361+ if ((refCall == refCall))
362+ then {
363+ let burnCall = invoke(getBurnAddress(), "burnAttachedPayments", nil, [AttachedPayment(getEggAssetId(), (leftToPay - refererRewardForPerch))])
364+ if ((burnCall == burnCall))
365+ then leftToPay
366+ else throw("Strict value is not equal to itself.")
367+ }
368+ else throw("Strict value is not equal to itself.")
369+ }
370+ }
371+ else 0
372+ if ((payment == payment))
373+ then {
374+ let perchAmountKey = ((("address_" + toString(i.caller)) + "_perchesAvailable_") + color)
375+ let perchAmount = tryGetInteger(perchAmountKey)
368376 [IntegerEntry(perchAmountKey, (perchAmount + 1))]
369- }
370- else throw("Strict value is not equal to itself.")
371- }
377+ }
378+ else throw("Strict value is not equal to itself.")
379+ }
380+ }
372381 else throw("Strict value is not equal to itself.")
373382 }
374383
414423 else if ((0 >= availablePerches))
415424 then throw(("no perches available for the color " + color))
416425 else {
417- let $t01466614739 = getAssetFarmingPower(assetId, address)
418- let assetGen = $t01466614739._1
419- let assetFarmingPower = $t01466614739._2
426+ let $t01491114984 = getAssetFarmingPower(assetId, address)
427+ let assetGen = $t01491114984._1
428+ let assetFarmingPower = $t01491114984._2
420429 (getStakeResult(address, assetId, assetFarmingPower, realCaller) ++ [IntegerEntry(((("address_" + address) + "_perchesAvailable_") + color), (availablePerches - 1))])
421430 }
422431 }
440449 if ((pmt.amount != 1))
441450 then throw("NFT is not attached")
442451 else {
443- let $t01536315436 = getAssetFarmingPower(assetId, address)
444- let assetGen = $t01536315436._1
445- let assetFarmingPower = $t01536315436._2
452+ let $t01560815681 = getAssetFarmingPower(assetId, address)
453+ let assetGen = $t01560815681._1
454+ let assetFarmingPower = $t01560815681._2
446455 let asset = toBase58String(assetId)
447456 let realCaller = toString(i.caller)
448457 (getStakeResult(address, assetId, assetFarmingPower, realCaller) ++ [BooleanEntry((((("address_" + address) + "_asset_") + asset) + "_without_perch"), true)])
516525 then toString(i.caller)
517526 else toString(i.originCaller)
518527 let assetId = fromBase58String(asset)
519- let sicknessCheck = asBoolean(invoke(getSicknessAddress(), "checkIfDuckGetSick", [asset], nil))
520- if ((sicknessCheck == sicknessCheck))
521- then if (sicknessCheck)
522- then {
523- let assetFarmingPower = getLastKnownAssetFarmingPower(address, asset)
528+ let sicknessCheck = false
529+ if (sicknessCheck)
530+ then {
531+ let assetFarmingPower = getLastKnownAssetFarmingPower(address, asset)
524532 [IntegerEntry("total_farmingPower", (tryGetInteger("total_farmingPower") - assetFarmingPower)), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_farmingPower"), 0)]
525- }
526- else {
527- let assetFarmingPower = getLastKnownAssetFarmingPower(address, asset)
528- let assetRewardDelta = calcAssetRewardDelta(address, asset, assetFarmingPower)
529- let farmedAmount = (assetRewardDelta + tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_lastCheckFarmedAmount")))
530- let withdrawnAmount = tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_withdrawnAmount"))
531- let reward = ((farmedAmount - withdrawnAmount) / (scale * 100))
532- if ((0 >= reward))
533- then throw("FCR: you have no EGGs to withdraw")
534- else $Tuple2([IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_withdrawnAmount"), (tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_withdrawnAmount")) + (reward * scale2))), ScriptTransfer(Address(fromBase58String(address)), (reward * 1000000), getEggAssetId())], (reward * 1000000))
535- }
536- else throw("Strict value is not equal to itself.")
533+ }
534+ else {
535+ let assetFarmingPower = getLastKnownAssetFarmingPower(address, asset)
536+ let assetRewardDelta = calcAssetRewardDelta(address, asset, assetFarmingPower)
537+ let farmedAmount = (assetRewardDelta + tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_lastCheckFarmedAmount")))
538+ let withdrawnAmount = tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_withdrawnAmount"))
539+ let reward = ((farmedAmount - withdrawnAmount) / (scale * 100))
540+ if ((0 >= reward))
541+ then throw("FCR: you have no EGGs to withdraw")
542+ else $Tuple2([IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_withdrawnAmount"), (tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_withdrawnAmount")) + (reward * scale2))), ScriptTransfer(Address(fromBase58String(address)), (reward * 1000000), getEggAssetId())], (reward * 1000000))
543+ }
537544 }
538545 else throw("Strict value is not equal to itself.")
539546 }
542549
543550 @Callable(i)
544551 func healDuck (duckId) = {
545- let sicknessCheck = asBoolean(invoke(getSicknessAddress(), "healDuck", [duckId], i.payments))
546- if ((sicknessCheck == sicknessCheck))
547- then {
548- let address = if (isProxyStakingSc(toString(i.caller)))
549- then toString(i.originCaller)
550- else toString(i.caller)
551- let farmingPower = getAssetFarmingPower(toBytes(duckId), address)._2
552+ let address = if (isProxyStakingSc(toString(i.caller)))
553+ then toString(i.originCaller)
554+ else toString(i.caller)
555+ let farmingPower = getAssetFarmingPower(toBytes(duckId), address)._2
552556 [IntegerEntry("total_farmingPower", (tryGetInteger("total_farmingPower") + farmingPower)), IntegerEntry((((("address_" + address) + "_asset_") + duckId) + "_farmingPower"), farmingPower)]
553- }
554- else throw("Strict value is not equal to itself.")
555557 }
556558
559+
560+@Verifier(tx)
561+func verify () = if (isTestEnv())
562+ then sigVerify(tx.bodyBytes, tx.proofs[0], tx.senderPublicKey)
563+ else {
564+ let firstUser = base58'FzsTVRXqD46KW5yj6qGNVrsouvWjpCQvD1446A96iGt4'
565+ let secondUser = base58'E23yUg8eun5nXB1nZRDf7RTyRADKxQhGNXdpTYonEvtU'
566+ let thirdUser = base58'Ga8WEBTPXbHuoXRD355mQ6ms8PsM2RFYKeA1mEP32CFe'
567+ let firstUserSigned = if (sigVerify(tx.bodyBytes, tx.proofs[0], firstUser))
568+ then 1
569+ else if (sigVerify(tx.bodyBytes, tx.proofs[1], firstUser))
570+ then 1
571+ else if (sigVerify(tx.bodyBytes, tx.proofs[2], firstUser))
572+ then 1
573+ else 0
574+ let secondUserSigned = if (sigVerify(tx.bodyBytes, tx.proofs[0], secondUser))
575+ then 1
576+ else if (sigVerify(tx.bodyBytes, tx.proofs[1], secondUser))
577+ then 1
578+ else if (sigVerify(tx.bodyBytes, tx.proofs[2], secondUser))
579+ then 1
580+ else 0
581+ let thirdUserSigned = if (sigVerify(tx.bodyBytes, tx.proofs[0], thirdUser))
582+ then 1
583+ else if (sigVerify(tx.bodyBytes, tx.proofs[1], thirdUser))
584+ then 1
585+ else if (sigVerify(tx.bodyBytes, tx.proofs[2], thirdUser))
586+ then 1
587+ else 0
588+ let signaturesCount = ((firstUserSigned + secondUserSigned) + thirdUserSigned)
589+ match tx {
590+ case _ =>
591+ (signaturesCount >= 2)
592+ }
593+ }
557594
Full:
OldNewDifferences
11 {-# STDLIB_VERSION 5 #-}
22 {-# SCRIPT_TYPE ACCOUNT #-}
33 {-# CONTENT_TYPE DAPP #-}
44 let perchPrice = (100 * 1000000)
55
66 let scale = 10000
77
88 let scale2 = 1000000
99
1010 func isSickDuck (duckId) = (duckId + "_sick")
1111
1212
1313 func tryGetStringExternal (address,key) = match getString(address, key) {
1414 case a: String =>
1515 a
1616 case _ =>
1717 ""
1818 }
1919
2020
2121 func tryGetString (key) = tryGetStringExternal(this, key)
2222
2323
2424 func getOracle () = Address(fromBase58String(tryGetString("static_oracleAddress")))
2525
2626
2727 func getEggAssetId () = fromBase58String(tryGetStringExternal(getOracle(), "static_eggAssetId"))
2828
2929
3030 func getIncubatorAddress () = Address(fromBase58String(tryGetStringExternal(getOracle(), "static_incubatorAddress")))
3131
3232
3333 func getRebirthAddress () = Address(fromBase58String(tryGetStringExternal(getOracle(), "static_rebirthAddress")))
3434
3535
3636 func getSwopPromoAddress () = Address(fromBase58String(tryGetStringExternal(getOracle(), "static_swopPromoAddress")))
3737
3838
3939 func getBreederAddress () = Address(fromBase58String(tryGetStringExternal(getOracle(), "static_breederAddress")))
4040
4141
4242 func getRefContractAddress () = Address(fromBase58String(tryGetStringExternal(getOracle(), "static_refContractAddress")))
4343
4444
4545 func getItemsAddress () = Address(fromBase58String(tryGetStringExternal(getOracle(), "static_itemsAddress")))
4646
4747
4848 func getMetaraceAddress () = Address(fromBase58String(tryGetStringExternal(getOracle(), "static_metaRaceAddress")))
4949
5050
5151 func getAccBoosterAddress () = Address(fromBase58String(tryGetStringExternal(getOracle(), "static_accBoosterAddress")))
5252
5353
5454 func getProxyStaking () = tryGetStringExternal(getOracle(), "static_proxyStakingContracts")
5555
5656
5757 func getMaintenance () = tryGetStringExternal(getOracle(), "static_maintenance")
5858
5959
6060 func getCfMasterAddress () = Address(fromBase58String(tryGetStringExternal(getOracle(), "static_cfMasterAddress")))
6161
6262
6363 func getDuckWrapperSc () = Address(fromBase58String(tryGetStringExternal(getOracle(), "static_duckWrapper")))
6464
6565
6666 func getCouponsAddress () = Address(fromBase58String(tryGetStringExternal(getOracle(), "static_couponsAddress")))
6767
6868
6969 func getBurnAddress () = Address(fromBase58String(tryGetStringExternal(getOracle(), "static_burnAddress")))
70-
71-
72-func getSicknessAddress () = Address(fromBase58String(tryGetStringExternal(getOracle(), "static_sicknessAddress")))
7370
7471
7572 let RefererReward = 5
7673
7774 func getRewardPerBlock () = 548
7875
7976
8077 func isLocked () = if ((getMaintenance() != ""))
8178 then throw(getMaintenance())
8279 else 0
8380
8481
8582 func tryGetInteger (key) = match getInteger(this, key) {
8683 case b: Int =>
8784 b
8885 case _ =>
8986 0
9087 }
9188
9289
9390 func tryGetBoolean (key) = match getBoolean(this, key) {
9491 case b: Boolean =>
9592 b
9693 case _ =>
9794 false
9895 }
9996
10097
10198 func tryGetBooleanExternal (address,key) = match getBoolean(address, key) {
10299 case b: Boolean =>
103100 b
104101 case _ =>
105102 false
106103 }
107104
108105
109106 func getAssetOrigin (generation) = if ((generation == "G"))
110107 then getIncubatorAddress()
111108 else getBreederAddress()
112109
113110
114111 func getAssetRarity (genotype,generation) = {
115112 let quantity = valueOrErrorMessage(getInteger(getAssetOrigin(generation), (("stats_" + genotype) + "_quantity")), (("stats_" + genotype) + "_quantity not found"))
116113 let power = pow((10000 / quantity), 4, 5, 1, 2, FLOOR)
117114 if ((power > 0))
118115 then power
119116 else 2
120117 }
121118
122119
123120 func asString (value) = match value {
124121 case string: String =>
125122 string
126123 case _ =>
127124 throw("FAS: wrong type, expected: String")
128125 }
129126
130127
131128 func asInt (value) = match value {
132129 case int: Int =>
133130 int
134131 case _ =>
135132 throw("FAI: wrong type, expected: Int")
136133 }
137134
138135
139136 func asBoolean (value) = match value {
140137 case boolean: Boolean =>
141138 boolean
142139 case _ =>
143140 throw("FAB: wrong type, expected: Boolean")
144141 }
145142
146143
147144 func getAssetFarmingPower (assetId,address) = if (if ((value(assetInfo(assetId)).issuer == getBreederAddress()))
148145 then true
149146 else (value(assetInfo(assetId)).issuer == getIncubatorAddress()))
150147 then {
151148 let farmBoost = asInt(invoke(getItemsAddress(), "calculateFarmingPowerBoost", [toBase58String(assetId), address], nil))
152149 if ((farmBoost == farmBoost))
153150 then {
154151 let assetName = value(assetInfo(assetId)).name
155152 let isJackpot = (takeRight(value(assetName), 1) == "U")
156153 let farmGen = if (isJackpot)
157154 then ""
158155 else asString(invoke(getBreederAddress(), "getGenFromName", [assetName], nil))
159156 if ((farmGen == farmGen))
160157 then {
161158 let rarity = if (isJackpot)
162159 then 100
163160 else {
164161 let generation = take(takeRight(assetName, 2), 1)
165162 getAssetRarity(farmGen, generation)
166163 }
167164 let totalFarmingPower = (rarity + fraction(rarity, farmBoost, 100))
168165 $Tuple2(farmGen, totalFarmingPower)
169166 }
170167 else throw("Strict value is not equal to itself.")
171168 }
172169 else throw("Strict value is not equal to itself.")
173170 }
174171 else throw("not valid NFT")
175172
176173
177174 func getLastKnownAssetFarmingPower (address,assetId) = tryGetInteger((((("address_" + address) + "_asset_") + assetId) + "_farmingPower"))
178175
179176
180177 func getAssetsByGen (gen) = {
181178 let s = tryGetString(("assets_" + gen))
182179 if ((s == ""))
183180 then nil
184181 else split(s, ",")
185182 }
186183
187184
188185 func calcInterest (previousInterest,previousInterestHeight,totalFarmingPower) = (previousInterest + (((scale * getRewardPerBlock()) * (height - previousInterestHeight)) / totalFarmingPower))
189186
190187
191188 func getCurrentInterest () = if ((tryGetInteger("total_farmingPower") > 0))
192189 then {
193190 let previousInterest = tryGetInteger("total_lastCheckInterest")
194191 let previousInterestHeight = tryGetInteger("total_lastCheckInterestHeight")
195192 let totalFarmingPower = tryGetInteger("total_farmingPower")
196193 calcInterest(previousInterest, previousInterestHeight, totalFarmingPower)
197194 }
198195 else if ((tryGetInteger("total_startHeight") != 0))
199196 then tryGetInteger("total_lastCheckInterest")
200197 else throw("farming is not launched, yet")
201198
202199
203200 func calcAssetRewardDelta (address,assetId,assetFarmingPower) = {
204201 let lastCheckAssetInterest = tryGetInteger((((("address_" + address) + "_asset_") + assetId) + "_lastCheckInterest"))
205202 let currentInterest = getCurrentInterest()
206203 (assetFarmingPower * (currentInterest - lastCheckAssetInterest))
207204 }
208205
209206
210207 func addAssetIdToGenEntry (assetId,assetGen) = {
211208 let currentValue = tryGetString((("assets_" + assetGen) + "_locked"))
212209 if ((currentValue == ""))
213210 then assetId
214211 else ((currentValue + ",") + assetId)
215212 }
216213
217214
218215 func getStakeResult (address,assetId,assetFarmingPower,unstaker) = {
219216 let asset = toBase58String(assetId)
220217 [IntegerEntry("total_farmingPower", (tryGetInteger("total_farmingPower") + assetFarmingPower)), IntegerEntry("total_lastCheckInterest", getCurrentInterest()), IntegerEntry("total_lastCheckInterestHeight", height), StringEntry((("asset_" + asset) + "_owner"), address), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_farmingPower"), assetFarmingPower), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_lastCheckInterest"), getCurrentInterest()), StringEntry((((("address_" + address) + "_asset_") + asset) + "_unstaker"), unstaker)]
221218 }
222219
223220
224221 func getUnstakeResult (address,assetId,color,caller,realCaller,claimEggs) = {
225222 let locked = isLocked()
226223 if ((locked == locked))
227224 then {
228225 let asset = toBase58String(assetId)
229226 let unstaker = tryGetString((((("address_" + address) + "_asset_") + asset) + "_unstaker"))
230227 if (if ((unstaker != ""))
231228 then (unstaker != realCaller)
232229 else false)
233230 then throw("FUN: It seems duck was staked throuh a dapp, not directly, please unstake through dapp!")
234231 else {
235232 let assetFarmingPower = getLastKnownAssetFarmingPower(address, asset)
236233 if (!((assetFarmingPower > 0)))
237234 then throw("FGU: Asset farming power not bigger then 0")
238235 else {
239236 let assetRewardDelta = calcAssetRewardDelta(address, asset, assetFarmingPower)
240237 let farmedAmount = (assetRewardDelta + tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_lastCheckFarmedAmount")))
241238 let withdrawnAmount = tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_withdrawnAmount"))
242239 let reward = ((farmedAmount - withdrawnAmount) / (scale * 100))
243240 let isWithoutPerch = tryGetBoolean((((("address_" + address) + "_asset_") + asset) + "_without_perch"))
244- let sicknessCheck = asBoolean(invoke(getSicknessAddress(), "checkIfDuckGetSick", [asset], nil))
245- if ((sicknessCheck == sicknessCheck))
246- then {
247- let rewardAfterSickNess = if (sicknessCheck)
248- then 0
249- else reward
250- let appendPerches = if (isWithoutPerch)
251- then [DeleteEntry((((("address_" + address) + "_asset_") + asset) + "_without_perch"))]
252- else [IntegerEntry(((("address_" + address) + "_perchesAvailable_") + color), (tryGetInteger(((("address_" + address) + "_perchesAvailable_") + color)) + 1))]
253- let sendTx = if (claimEggs)
254- then $Tuple2([ScriptTransfer(caller, (rewardAfterSickNess * 1000000), getEggAssetId())], (rewardAfterSickNess * 1000000))
255- else $Tuple2(nil, 0)
256- $Tuple2(((([IntegerEntry("total_farmingPower", (tryGetInteger("total_farmingPower") - assetFarmingPower)), IntegerEntry("total_lastCheckInterest", getCurrentInterest()), IntegerEntry("total_lastCheckInterestHeight", height), DeleteEntry((("asset_" + asset) + "_owner")), DeleteEntry((((("address_" + address) + "_asset_") + asset) + "_unstaker")), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_farmingPower"), 0), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_lastCheckInterest"), getCurrentInterest()), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_withdrawnAmount"), (withdrawnAmount + (rewardAfterSickNess * scale2))), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_lastCheckFarmedAmount"), (tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_lastCheckFarmedAmount")) + assetRewardDelta))] ++ appendPerches) ++ [ScriptTransfer(caller, 1, assetId)]) ++ sendTx._1), sendTx._2)
257- }
258- else throw("Strict value is not equal to itself.")
241+ let sicknessCheck = false
242+ let rewardAfterSickNess = if (sicknessCheck)
243+ then 0
244+ else reward
245+ let appendPerches = if (isWithoutPerch)
246+ then [DeleteEntry((((("address_" + address) + "_asset_") + asset) + "_without_perch"))]
247+ else [IntegerEntry(((("address_" + address) + "_perchesAvailable_") + color), (tryGetInteger(((("address_" + address) + "_perchesAvailable_") + color)) + 1))]
248+ let sendTx = if (claimEggs)
249+ then $Tuple2([ScriptTransfer(caller, (rewardAfterSickNess * 1000000), getEggAssetId())], (rewardAfterSickNess * 1000000))
250+ else $Tuple2(nil, 0)
251+ $Tuple2(((([IntegerEntry("total_farmingPower", (tryGetInteger("total_farmingPower") - assetFarmingPower)), IntegerEntry("total_lastCheckInterest", getCurrentInterest()), IntegerEntry("total_lastCheckInterestHeight", height), DeleteEntry((("asset_" + asset) + "_owner")), DeleteEntry((((("address_" + address) + "_asset_") + asset) + "_unstaker")), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_farmingPower"), 0), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_lastCheckInterest"), getCurrentInterest()), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_withdrawnAmount"), (withdrawnAmount + (rewardAfterSickNess * scale2))), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_lastCheckFarmedAmount"), (tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_lastCheckFarmedAmount")) + assetRewardDelta))] ++ appendPerches) ++ [ScriptTransfer(caller, 1, assetId)]) ++ sendTx._1), sendTx._2)
259252 }
260253 }
261254 }
262255 else throw("Strict value is not equal to itself.")
263256 }
264257
265258
266259 func calculatePerchPrice (address) = {
267260 let hasArtefactStaked = tryGetStringExternal(getAccBoosterAddress(), (("ART-XMISTL_" + address) + "_owner"))
268261 if ((hasArtefactStaked == ""))
269262 then perchPrice
270263 else ((perchPrice / 10) * 9)
271264 }
272265
273266
274267 func isProxyStakingSc (address) = {
275268 let allowedContracts = getProxyStaking()
276269 let allowedContractsList = split(allowedContracts, ";")
277270 (indexOf(allowedContractsList, address) != unit)
278271 }
279272
280273
281274 func unstakeNFTInternal (asset,i,claimEgg) = {
282275 let assetId = fromBase58String(asset)
283276 let realCaller = toString(i.caller)
284277 let address = if (isProxyStakingSc(toString(i.caller)))
285278 then toString(i.originCaller)
286279 else realCaller
287280 let color = takeRight(value(assetInfo(assetId)).name, 1)
288281 if ((color == "U"))
289282 then throw("FUN: use another function to unstake Jackpot NFT")
290283 else {
291284 let result = getUnstakeResult(address, assetId, color, i.caller, realCaller, claimEgg)
292285 result
293286 }
294287 }
295288
296289
297290 func unstakeJackpotInternal (asset,i,claimEgg) = {
298291 let assetId = fromBase58String(asset)
299292 let realCaller = toString(i.caller)
300293 let address = if (isProxyStakingSc(toString(i.caller)))
301294 then toString(i.originCaller)
302295 else realCaller
303296 let color = tryGetString((((("address_" + address) + "_asset_") + asset) + "_perchColor"))
304297 if ((takeRight(value(value(assetInfo(assetId)).name), 1) != "U"))
305298 then throw("jackpot only")
306299 else {
307300 let result = getUnstakeResult(address, assetId, color, i.caller, realCaller, claimEgg)
308301 result
309302 }
310303 }
311304
312305
306+func getBool (key) = match getBoolean(this, key) {
307+ case b: Boolean =>
308+ b
309+ case _ =>
310+ false
311+}
312+
313+
314+func isTestEnv () = getBool("TESTENV")
315+
316+
313317 @Callable(i)
314318 func configureOracle (oracle) = if ((i.caller != this))
315319 then throw("FCO: admin only")
316320 else [StringEntry("static_oracleAddress", oracle)]
317321
318322
319323
320324 @Callable(i)
321325 func init () = if ((i.caller != this))
322326 then throw("FI: admin only")
323327 else [IntegerEntry("total_startHeight", height)]
324328
325329
326330
327331 @Callable(i)
328-func buyPerch (color,refererAddress) = {
332+func buyPerch (colorI,refererAddress) = {
329333 let locked = isLocked()
330334 if ((locked == locked))
331- then if ((0 > value(indexOf(["B", "R", "G", "Y"], color))))
332- then throw("you need to set color properly")
333- else {
334- let exactPrice = calculatePerchPrice(toString(i.caller))
335- let leftToPay = if ((i.originCaller == i.caller))
336- then {
337- let amountPaidByCoupons = asInt(invoke(getCouponsAddress(), "useCoupons", [exactPrice], nil))
338- if ((amountPaidByCoupons == amountPaidByCoupons))
339- then (exactPrice - amountPaidByCoupons)
340- else throw("Strict value is not equal to itself.")
341- }
342- else exactPrice
343- let payment = if ((leftToPay != 0))
344- then {
345- let firstPayment = value(i.payments[0])
346- if ((firstPayment.assetId != getEggAssetId()))
347- then throw(("FBP: You can attach only EGG tokens with the following asset id: " + toBase58String(getEggAssetId())))
348- else if ((firstPayment.amount != leftToPay))
349- then throw(((("FBP: To buy a perch you currently need the following amount of EGGlets: " + toString(leftToPay)) + " ") + toString(i.caller)))
350- else {
351- let refererRewardForPerch = fraction(leftToPay, RefererReward, 100)
352- let refCall = invoke(getRefContractAddress(), "refPayment", [refererAddress], [AttachedPayment(getEggAssetId(), refererRewardForPerch)])
353- if ((refCall == refCall))
354- then {
355- let burnCall = invoke(getBurnAddress(), "burnAttachedPayments", nil, [AttachedPayment(getEggAssetId(), (leftToPay - refererRewardForPerch))])
356- if ((burnCall == burnCall))
357- then leftToPay
358- else throw("Strict value is not equal to itself.")
359- }
360- else throw("Strict value is not equal to itself.")
361- }
362- }
363- else 0
364- if ((payment == payment))
365- then {
366- let perchAmountKey = ((("address_" + toString(i.caller)) + "_perchesAvailable_") + color)
367- let perchAmount = tryGetInteger(perchAmountKey)
335+ then {
336+ let color = if ((colorI == "U"))
337+ then "B"
338+ else colorI
339+ if ((0 > value(indexOf(["B", "R", "G", "Y"], color))))
340+ then throw("you need to set color properly")
341+ else {
342+ let exactPrice = calculatePerchPrice(toString(i.caller))
343+ let leftToPay = if ((i.originCaller == i.caller))
344+ then {
345+ let amountPaidByCoupons = asInt(invoke(getCouponsAddress(), "useCoupons", [exactPrice], nil))
346+ if ((amountPaidByCoupons == amountPaidByCoupons))
347+ then (exactPrice - amountPaidByCoupons)
348+ else throw("Strict value is not equal to itself.")
349+ }
350+ else exactPrice
351+ let payment = if ((leftToPay != 0))
352+ then {
353+ let firstPayment = value(i.payments[0])
354+ if ((firstPayment.assetId != getEggAssetId()))
355+ then throw(("FBP: You can attach only EGG tokens with the following asset id: " + toBase58String(getEggAssetId())))
356+ else if ((firstPayment.amount != leftToPay))
357+ then throw(((("FBP: To buy a perch you currently need the following amount of EGGlets: " + toString(leftToPay)) + " ") + toString(i.caller)))
358+ else {
359+ let refererRewardForPerch = fraction(leftToPay, RefererReward, 100)
360+ let refCall = invoke(getRefContractAddress(), "refPayment", [refererAddress], [AttachedPayment(getEggAssetId(), refererRewardForPerch)])
361+ if ((refCall == refCall))
362+ then {
363+ let burnCall = invoke(getBurnAddress(), "burnAttachedPayments", nil, [AttachedPayment(getEggAssetId(), (leftToPay - refererRewardForPerch))])
364+ if ((burnCall == burnCall))
365+ then leftToPay
366+ else throw("Strict value is not equal to itself.")
367+ }
368+ else throw("Strict value is not equal to itself.")
369+ }
370+ }
371+ else 0
372+ if ((payment == payment))
373+ then {
374+ let perchAmountKey = ((("address_" + toString(i.caller)) + "_perchesAvailable_") + color)
375+ let perchAmount = tryGetInteger(perchAmountKey)
368376 [IntegerEntry(perchAmountKey, (perchAmount + 1))]
369- }
370- else throw("Strict value is not equal to itself.")
371- }
377+ }
378+ else throw("Strict value is not equal to itself.")
379+ }
380+ }
372381 else throw("Strict value is not equal to itself.")
373382 }
374383
375384
376385
377386 @Callable(i)
378387 func addFreePerch (address,color) = {
379388 let locked = isLocked()
380389 if ((locked == locked))
381390 then if ((0 > value(indexOf(["B", "R", "G", "Y"], color))))
382391 then throw("you need to set color properly")
383392 else if (if (if ((i.caller != getRebirthAddress()))
384393 then (i.caller != this)
385394 else false)
386395 then (i.caller != getSwopPromoAddress())
387396 else false)
388397 then throw("rebirth and swop promo only")
389398 else {
390399 let perchAmountKey = ((("address_" + address) + "_perchesAvailable_") + color)
391400 let perchAmount = tryGetInteger(perchAmountKey)
392401 $Tuple2([IntegerEntry(perchAmountKey, (perchAmount + 1))], "")
393402 }
394403 else throw("Strict value is not equal to itself.")
395404 }
396405
397406
398407
399408 @Callable(i)
400409 func stakeNFT () = {
401410 let locked = isLocked()
402411 if ((locked == locked))
403412 then {
404413 let pmt = value(i.payments[0])
405414 let assetId = value(value(i.payments[0]).assetId)
406415 let realCaller = toString(i.caller)
407416 let address = if (isProxyStakingSc(toString(i.caller)))
408417 then toString(i.originCaller)
409418 else realCaller
410419 let color = takeRight(value(assetInfo(assetId)).name, 1)
411420 let availablePerches = tryGetInteger(((("address_" + address) + "_perchesAvailable_") + color))
412421 if ((pmt.amount != 1))
413422 then throw("NFT is not attached")
414423 else if ((0 >= availablePerches))
415424 then throw(("no perches available for the color " + color))
416425 else {
417- let $t01466614739 = getAssetFarmingPower(assetId, address)
418- let assetGen = $t01466614739._1
419- let assetFarmingPower = $t01466614739._2
426+ let $t01491114984 = getAssetFarmingPower(assetId, address)
427+ let assetGen = $t01491114984._1
428+ let assetFarmingPower = $t01491114984._2
420429 (getStakeResult(address, assetId, assetFarmingPower, realCaller) ++ [IntegerEntry(((("address_" + address) + "_perchesAvailable_") + color), (availablePerches - 1))])
421430 }
422431 }
423432 else throw("Strict value is not equal to itself.")
424433 }
425434
426435
427436
428437 @Callable(i)
429438 func stakeNFTWithoutPerch () = {
430439 let locked = isLocked()
431440 if ((locked == locked))
432441 then {
433442 let dappToCall = toString(i.caller)
434443 if (!(isProxyStakingSc(dappToCall)))
435444 then throw("FSNWP: Only trusted smart contracts can stake without a perch!")
436445 else {
437446 let pmt = value(i.payments[0])
438447 let assetId = value(value(i.payments[0]).assetId)
439448 let address = toString(i.originCaller)
440449 if ((pmt.amount != 1))
441450 then throw("NFT is not attached")
442451 else {
443- let $t01536315436 = getAssetFarmingPower(assetId, address)
444- let assetGen = $t01536315436._1
445- let assetFarmingPower = $t01536315436._2
452+ let $t01560815681 = getAssetFarmingPower(assetId, address)
453+ let assetGen = $t01560815681._1
454+ let assetFarmingPower = $t01560815681._2
446455 let asset = toBase58String(assetId)
447456 let realCaller = toString(i.caller)
448457 (getStakeResult(address, assetId, assetFarmingPower, realCaller) ++ [BooleanEntry((((("address_" + address) + "_asset_") + asset) + "_without_perch"), true)])
449458 }
450459 }
451460 }
452461 else throw("Strict value is not equal to itself.")
453462 }
454463
455464
456465
457466 @Callable(i)
458467 func unstakeNFT (asset) = unstakeNFTInternal(asset, i, true)
459468
460469
461470
462471 @Callable(i)
463472 func unstakeNFTWithoutClaim (asset) = unstakeNFTInternal(asset, i, false)
464473
465474
466475
467476 @Callable(i)
468477 func stakeJackpot (color) = {
469478 let locked = isLocked()
470479 if ((locked == locked))
471480 then {
472481 let pmt = value(i.payments[0])
473482 let assetId = value(pmt.assetId)
474483 let realCaller = toString(i.caller)
475484 let address = if (isProxyStakingSc(toString(i.caller)))
476485 then toString(i.originCaller)
477486 else realCaller
478487 let availablePerches = tryGetInteger(((("address_" + address) + "_perchesAvailable_") + color))
479488 let assetIssuer = value(assetInfo(assetId)).issuer
480489 if ((pmt.amount != 1))
481490 then throw("NFT is not attached")
482491 else if (if ((assetIssuer == getIncubatorAddress()))
483492 then true
484493 else (assetIssuer == getBreederAddress()))
485494 then if ((takeRight(value(value(assetInfo(assetId)).name), 1) != "U"))
486495 then throw("jackpot only")
487496 else if ((0 >= availablePerches))
488497 then throw(("FSJ: no perches available for the color " + color))
489498 else {
490499 let farmingPower = getAssetFarmingPower(assetId, address)
491500 (getStakeResult(address, assetId, farmingPower._2, realCaller) ++ [IntegerEntry(((("address_" + address) + "_perchesAvailable_") + color), (availablePerches - 1)), StringEntry((((("address_" + address) + "_asset_") + toBase58String(assetId)) + "_perchColor"), color)])
492501 }
493502 else throw("asset is not valid")
494503 }
495504 else throw("Strict value is not equal to itself.")
496505 }
497506
498507
499508
500509 @Callable(i)
501510 func unstakeJackpot (asset) = unstakeJackpotInternal(asset, i, true)
502511
503512
504513
505514 @Callable(i)
506515 func unstakeJackpotWithoutClaimEgg (asset) = unstakeJackpotInternal(asset, i, false)
507516
508517
509518
510519 @Callable(i)
511520 func claimReward (asset) = {
512521 let locked = isLocked()
513522 if ((locked == locked))
514523 then {
515524 let address = if ((i.originCaller == getCfMasterAddress()))
516525 then toString(i.caller)
517526 else toString(i.originCaller)
518527 let assetId = fromBase58String(asset)
519- let sicknessCheck = asBoolean(invoke(getSicknessAddress(), "checkIfDuckGetSick", [asset], nil))
520- if ((sicknessCheck == sicknessCheck))
521- then if (sicknessCheck)
522- then {
523- let assetFarmingPower = getLastKnownAssetFarmingPower(address, asset)
528+ let sicknessCheck = false
529+ if (sicknessCheck)
530+ then {
531+ let assetFarmingPower = getLastKnownAssetFarmingPower(address, asset)
524532 [IntegerEntry("total_farmingPower", (tryGetInteger("total_farmingPower") - assetFarmingPower)), IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_farmingPower"), 0)]
525- }
526- else {
527- let assetFarmingPower = getLastKnownAssetFarmingPower(address, asset)
528- let assetRewardDelta = calcAssetRewardDelta(address, asset, assetFarmingPower)
529- let farmedAmount = (assetRewardDelta + tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_lastCheckFarmedAmount")))
530- let withdrawnAmount = tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_withdrawnAmount"))
531- let reward = ((farmedAmount - withdrawnAmount) / (scale * 100))
532- if ((0 >= reward))
533- then throw("FCR: you have no EGGs to withdraw")
534- else $Tuple2([IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_withdrawnAmount"), (tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_withdrawnAmount")) + (reward * scale2))), ScriptTransfer(Address(fromBase58String(address)), (reward * 1000000), getEggAssetId())], (reward * 1000000))
535- }
536- else throw("Strict value is not equal to itself.")
533+ }
534+ else {
535+ let assetFarmingPower = getLastKnownAssetFarmingPower(address, asset)
536+ let assetRewardDelta = calcAssetRewardDelta(address, asset, assetFarmingPower)
537+ let farmedAmount = (assetRewardDelta + tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_lastCheckFarmedAmount")))
538+ let withdrawnAmount = tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_withdrawnAmount"))
539+ let reward = ((farmedAmount - withdrawnAmount) / (scale * 100))
540+ if ((0 >= reward))
541+ then throw("FCR: you have no EGGs to withdraw")
542+ else $Tuple2([IntegerEntry((((("address_" + address) + "_asset_") + asset) + "_withdrawnAmount"), (tryGetInteger((((("address_" + address) + "_asset_") + asset) + "_withdrawnAmount")) + (reward * scale2))), ScriptTransfer(Address(fromBase58String(address)), (reward * 1000000), getEggAssetId())], (reward * 1000000))
543+ }
537544 }
538545 else throw("Strict value is not equal to itself.")
539546 }
540547
541548
542549
543550 @Callable(i)
544551 func healDuck (duckId) = {
545- let sicknessCheck = asBoolean(invoke(getSicknessAddress(), "healDuck", [duckId], i.payments))
546- if ((sicknessCheck == sicknessCheck))
547- then {
548- let address = if (isProxyStakingSc(toString(i.caller)))
549- then toString(i.originCaller)
550- else toString(i.caller)
551- let farmingPower = getAssetFarmingPower(toBytes(duckId), address)._2
552+ let address = if (isProxyStakingSc(toString(i.caller)))
553+ then toString(i.originCaller)
554+ else toString(i.caller)
555+ let farmingPower = getAssetFarmingPower(toBytes(duckId), address)._2
552556 [IntegerEntry("total_farmingPower", (tryGetInteger("total_farmingPower") + farmingPower)), IntegerEntry((((("address_" + address) + "_asset_") + duckId) + "_farmingPower"), farmingPower)]
553- }
554- else throw("Strict value is not equal to itself.")
555557 }
556558
559+
560+@Verifier(tx)
561+func verify () = if (isTestEnv())
562+ then sigVerify(tx.bodyBytes, tx.proofs[0], tx.senderPublicKey)
563+ else {
564+ let firstUser = base58'FzsTVRXqD46KW5yj6qGNVrsouvWjpCQvD1446A96iGt4'
565+ let secondUser = base58'E23yUg8eun5nXB1nZRDf7RTyRADKxQhGNXdpTYonEvtU'
566+ let thirdUser = base58'Ga8WEBTPXbHuoXRD355mQ6ms8PsM2RFYKeA1mEP32CFe'
567+ let firstUserSigned = if (sigVerify(tx.bodyBytes, tx.proofs[0], firstUser))
568+ then 1
569+ else if (sigVerify(tx.bodyBytes, tx.proofs[1], firstUser))
570+ then 1
571+ else if (sigVerify(tx.bodyBytes, tx.proofs[2], firstUser))
572+ then 1
573+ else 0
574+ let secondUserSigned = if (sigVerify(tx.bodyBytes, tx.proofs[0], secondUser))
575+ then 1
576+ else if (sigVerify(tx.bodyBytes, tx.proofs[1], secondUser))
577+ then 1
578+ else if (sigVerify(tx.bodyBytes, tx.proofs[2], secondUser))
579+ then 1
580+ else 0
581+ let thirdUserSigned = if (sigVerify(tx.bodyBytes, tx.proofs[0], thirdUser))
582+ then 1
583+ else if (sigVerify(tx.bodyBytes, tx.proofs[1], thirdUser))
584+ then 1
585+ else if (sigVerify(tx.bodyBytes, tx.proofs[2], thirdUser))
586+ then 1
587+ else 0
588+ let signaturesCount = ((firstUserSigned + secondUserSigned) + thirdUserSigned)
589+ match tx {
590+ case _ =>
591+ (signaturesCount >= 2)
592+ }
593+ }
557594

github/deemru/w8io/3ef1775 
73.13 ms