Updated on 2026-08-14
This commit is contained in:
parent
9bfdafd678
commit
f0ba8cca13
8 changed files with 134 additions and 95 deletions
|
|
@ -20,7 +20,7 @@ class ResponseJsonConverter {
|
|||
private fun init(): Gson {
|
||||
val builder = GsonBuilder().apply {
|
||||
registerTypeAdapter(ByteArray::class.java, ByteTypeAdapter(fieldConverter))
|
||||
registerTypeAdapter(SigningMethod::class.java, SigningMethodTypeAdapter(fieldConverter))
|
||||
registerTypeAdapter(SigningMethodMask::class.java, SigningMethodTypeAdapter(fieldConverter))
|
||||
registerTypeAdapter(SettingsMask::class.java, SettingsMaskTypeAdapter(fieldConverter))
|
||||
registerTypeAdapter(ProductMask::class.java, ProductMaskTypeAdapter(fieldConverter))
|
||||
registerTypeAdapter(Date::class.java, DateTypeAdapter())
|
||||
|
|
@ -62,8 +62,8 @@ class ProductMaskTypeAdapter(
|
|||
|
||||
class SigningMethodTypeAdapter(
|
||||
private val fieldConverter: ResponseFieldConverter
|
||||
) : JsonSerializer<SigningMethod> {
|
||||
override fun serialize(src: SigningMethod, typeOfSrc: Type, context: JsonSerializationContext): JsonElement {
|
||||
) : JsonSerializer<SigningMethodMask> {
|
||||
override fun serialize(src: SigningMethodMask, typeOfSrc: Type, context: JsonSerializationContext): JsonElement {
|
||||
return JsonArray().apply {
|
||||
fieldConverter.signingMethodList(src).forEach { add(it) }
|
||||
}
|
||||
|
|
@ -86,32 +86,17 @@ class ResponseFieldConverter {
|
|||
fun productMaskList(productMask: ProductMask?): List<String> {
|
||||
val mask = productMask ?: return emptyList()
|
||||
|
||||
val signingMap = mutableMapOf(
|
||||
ProductMask.note to "Note",
|
||||
ProductMask.tag to "Tag",
|
||||
ProductMask.idCard to "IdCard",
|
||||
ProductMask.idIssuer to "IdIssuer"
|
||||
)
|
||||
return signingMap.filter { mask.contains(it.key) }.map { it.value }
|
||||
return Product.values().filter { mask.contains(it) }.map { it.name }
|
||||
}
|
||||
|
||||
fun signingMethod(signingMethod: SigningMethod?): String {
|
||||
return signingMethodList(signingMethod).print(wrap = false)
|
||||
fun signingMethod(signingMask: SigningMethodMask?): String {
|
||||
return signingMethodList(signingMask).print(wrap = false)
|
||||
}
|
||||
|
||||
fun signingMethodList(signingMethod: SigningMethod?): List<String> {
|
||||
val methods = signingMethod ?: return emptyList()
|
||||
fun signingMethodList(signingMask: SigningMethodMask?): List<String> {
|
||||
val mask = signingMask ?: return emptyList()
|
||||
|
||||
val signingMap = mutableMapOf(
|
||||
SigningMethod.signHash to "Hash",
|
||||
SigningMethod.signRaw to "Raw",
|
||||
SigningMethod.signHashValidatedByIssuer to "HashValidatedByIssuer",
|
||||
SigningMethod.signRawValidatedByIssuer to "RawValidatedByIssuer",
|
||||
SigningMethod.signHashValidatedByIssuerAndWriteIssuerData to "HashValidatedByIssuerAndWriteIssuerData",
|
||||
SigningMethod.signRawValidatedByIssuerAndWriteIssuerData to "RawValidatedByIssuerAndWriteIssuerData",
|
||||
SigningMethod.signPos to "Pos"
|
||||
)
|
||||
return signingMap.filter { methods.contains(it.key) }.map { it.value }
|
||||
return SigningMethod.values().filter { mask.contains(it) }.map { it.name }
|
||||
}
|
||||
|
||||
fun settingsMask(settingsMask: SettingsMask?): String {
|
||||
|
|
@ -124,7 +109,7 @@ class ResponseFieldConverter {
|
|||
return Settings.values().filter { masks.contains(it) }.map { it.name }
|
||||
}
|
||||
|
||||
fun byteArray(byteArray: ByteArray?): String {
|
||||
return byteArray?.toHexString() ?: ""
|
||||
fun byteArray(byteArray: ByteArray?): String? {
|
||||
return byteArray?.toHexString()
|
||||
}
|
||||
}
|
||||
|
|
@ -30,7 +30,7 @@ class ResponseResources {
|
|||
holder.register(CardId.issuerPublicKey, Resources(R.string.response_card_issuer_data_public_key, R.string.info_response_card_issuer_data_public_key))
|
||||
holder.register(CardId.curve, Resources(R.string.response_card_curve, R.string.info_response_card_curve))
|
||||
holder.register(CardId.maxSignatures, Resources(R.string.response_card_max_signatures, R.string.info_response_card_max_signatures))
|
||||
holder.register(CardId.signingMethod, Resources(R.string.response_card_signing_method, R.string.response_card_signing_method))
|
||||
holder.register(CardId.signingMethod, Resources(R.string.response_card_signing_method, R.string.info_response_card_signing_method))
|
||||
holder.register(CardId.pauseBeforePin2, Resources(R.string.response_card_pause_before_pin2, R.string.info_response_card_allow_pin2))
|
||||
holder.register(CardId.walletPublicKey, Resources(R.string.response_card_wallet_public_key, R.string.info_response_card_wallet_public_key))
|
||||
holder.register(CardId.walletRemainingSignatures, Resources(R.string.response_card_wallet_remaining_signatures, R.string.info_response_card_wallet_remaining_signatures))
|
||||
|
|
|
|||
|
|
@ -1,33 +1,27 @@
|
|||
package com.tangem.tangemtest.ucase.variants.responses.converter
|
||||
|
||||
import com.tangem.commands.Card
|
||||
import com.tangem.commands.CardData
|
||||
import com.tangem.commands.Settings
|
||||
import com.tangem.commands.SettingsMask
|
||||
import com.tangem.commands.*
|
||||
import com.tangem.tangemtest.R
|
||||
import com.tangem.tangemtest._arch.structure.Id
|
||||
import com.tangem.tangemtest._arch.structure.StringId
|
||||
import com.tangem.tangemtest._arch.structure.abstraction.*
|
||||
import com.tangem.tangemtest._arch.structure.abstraction.Item
|
||||
import com.tangem.tangemtest._arch.structure.abstraction.ItemGroup
|
||||
import com.tangem.tangemtest._arch.structure.abstraction.iterate
|
||||
import com.tangem.tangemtest._arch.structure.impl.BoolItem
|
||||
import com.tangem.tangemtest._arch.structure.impl.TextItem
|
||||
import com.tangem.tangemtest.ucase.domain.responses.ResponseFieldConverter
|
||||
import com.tangem.tangemtest.ucase.variants.personalize.BlockId
|
||||
import com.tangem.tangemtest.ucase.variants.responses.CardDataId
|
||||
import com.tangem.tangemtest.ucase.variants.responses.CardId
|
||||
import ru.dev.gbixahue.eu4d.lib.kotlin.stringOf
|
||||
import com.tangem.tangemtest.ucase.variants.responses.item.TextHeaderItem
|
||||
|
||||
/**
|
||||
[REDACTED_AUTHOR]
|
||||
*/
|
||||
class CardConverter : ModelToItems<Card> {
|
||||
|
||||
private val fieldConverter = ResponseFieldConverter()
|
||||
class CardConverter : BaseResponseConverter<Card>() {
|
||||
|
||||
override fun convert(from: Card): List<Item> {
|
||||
val itemList = mutableListOf<Item>()
|
||||
itemList.add(simpleFields(from))
|
||||
itemList.add(cardData(from.cardData))
|
||||
itemList.add(settingsMask(from.settingsMask))
|
||||
commonGroup(itemList, from)
|
||||
cardDataGroup(itemList, from.cardData)
|
||||
settingsMaskGroup(itemList, from.settingsMask)
|
||||
hideEmptyNullFields(itemList)
|
||||
|
||||
return itemList
|
||||
|
|
@ -35,70 +29,66 @@ class CardConverter : ModelToItems<Card> {
|
|||
|
||||
private fun hideEmptyNullFields(itemList: MutableList<Item>) {
|
||||
itemList.iterate {
|
||||
val data = it.getData<Any?>()
|
||||
val isHidden = if (data == null) true
|
||||
else when (data) {
|
||||
is String -> data.isEmpty()
|
||||
else -> false
|
||||
}
|
||||
if (it is ItemGroup) return@iterate
|
||||
|
||||
if (isHidden) it.viewModel.viewState.isVisibleState.value = false
|
||||
if (it.getData<Any?>() == null) it.viewModel.viewState.isVisibleState.value = false
|
||||
}
|
||||
}
|
||||
|
||||
private fun simpleFields(from: Card): Item {
|
||||
val group = createGroup(BlockId.Common)
|
||||
private fun commonGroup(itemList: MutableList<Item>, from: Card) {
|
||||
val group = createGroup(CardId.empty, addHeaderItem = false)
|
||||
itemList.add(group)
|
||||
|
||||
group.addItem(TextItem(CardId.cardId, from.cardId))
|
||||
group.addItem(TextItem(CardId.manufacturerName, from.manufacturerName))
|
||||
group.addItem(TextItem(CardId.status, stringOf(from.status)))
|
||||
group.addItem(TextItem(CardId.status, valueToString(from.status)))
|
||||
group.addItem(TextItem(CardId.firmwareVersion, from.firmwareVersion))
|
||||
group.addItem(TextItem(CardId.cardPublicKey, fieldConverter.byteArray(from.cardPublicKey)))
|
||||
group.addItem(TextItem(CardId.issuerPublicKey, fieldConverter.byteArray(from.issuerPublicKey)))
|
||||
group.addItem(TextItem(CardId.curve, stringOf(from.curve)))
|
||||
group.addItem(TextItem(CardId.maxSignatures, stringOf(from.maxSignatures)))
|
||||
group.addItem(TextItem(CardId.signingMethod, fieldConverter.signingMethod(from.signingMethod)))
|
||||
group.addItem(TextItem(CardId.pauseBeforePin2, stringOf(from.pauseBeforePin2)))
|
||||
group.addItem(TextItem(CardId.curve, valueToString(from.curve)))
|
||||
group.addItem(TextItem(CardId.maxSignatures, valueToString(from.maxSignatures)))
|
||||
group.addItem(TextItem(CardId.pauseBeforePin2, valueToString(from.pauseBeforePin2)))
|
||||
group.addItem(TextItem(CardId.walletPublicKey, fieldConverter.byteArray(from.walletPublicKey)))
|
||||
group.addItem(TextItem(CardId.walletRemainingSignatures, stringOf(from.walletRemainingSignatures)))
|
||||
group.addItem(TextItem(CardId.walletSignedHashes, stringOf(from.walletSignedHashes)))
|
||||
group.addItem(TextItem(CardId.health, stringOf(from.health)))
|
||||
group.addItem(TextItem(CardId.isActivated, stringOf(from.isActivated)))
|
||||
group.addItem(TextItem(CardId.activationSeed, stringOf(from.activationSeed)))
|
||||
group.addItem(TextItem(CardId.paymentFlowVersion, stringOf(from.paymentFlowVersion)))
|
||||
group.addItem(TextItem(CardId.userCounter, stringOf(from.userCounter)))
|
||||
// block.addItem(TextItem(CardId.UserProtectedCounter, stringOf(from.userProtectedCounter)))
|
||||
return group
|
||||
group.addItem(TextItem(CardId.walletRemainingSignatures, valueToString(from.walletRemainingSignatures)))
|
||||
group.addItem(TextItem(CardId.walletSignedHashes, valueToString(from.walletSignedHashes)))
|
||||
group.addItem(TextItem(CardId.health, valueToString(from.health)))
|
||||
group.addItem(TextItem(CardId.isActivated, valueToString(from.isActivated)))
|
||||
group.addItem(TextItem(CardId.activationSeed, valueToString(from.activationSeed)))
|
||||
group.addItem(TextItem(CardId.paymentFlowVersion, valueToString(from.paymentFlowVersion)))
|
||||
group.addItem(TextItem(CardId.userCounter, valueToString(from.userCounter)))
|
||||
|
||||
val settingsMask = from.settingsMask ?: return
|
||||
|
||||
group.addItem(TextHeaderItem(CardId.signingMethod, ""))
|
||||
Settings.values().forEach { group.addItem(BoolItem(StringId(it.name), settingsMask.contains(it))) }
|
||||
}
|
||||
|
||||
private fun cardData(from: CardData?): Item {
|
||||
val group = createGroup(BlockId.Common, R.color.group_card_data)
|
||||
val data = from ?: return group
|
||||
private fun cardDataGroup(itemList: MutableList<Item>, cardData: CardData?) {
|
||||
val data = cardData ?: return
|
||||
|
||||
// group.addItem(TextItem(StringResId(R.string.response_card_card_data)))
|
||||
val group = createGroup(CardId.cardData, R.color.group_card_data)
|
||||
itemList.add(group)
|
||||
group.addItem(TextItem(CardDataId.batchId, data.batchId))
|
||||
// Format: Year (2 bytes) | Month (1 byte) | Day (1 byte)
|
||||
group.addItem(TextItem(CardDataId.manufactureDateTime, stringOf(data.manufactureDateTime)))
|
||||
group.addItem(TextItem(CardDataId.manufactureDateTime, valueToString(data.manufactureDateTime)))
|
||||
group.addItem(TextItem(CardDataId.issuerName, data.issuerName))
|
||||
group.addItem(TextItem(CardDataId.blockchainName, data.blockchainName))
|
||||
group.addItem(TextItem(CardDataId.manufacturerSignature, fieldConverter.byteArray(data.manufacturerSignature)))
|
||||
group.addItem(TextItem(CardDataId.productMask, fieldConverter.productMask(data.productMask)))
|
||||
group.addItem(TextItem(CardDataId.tokenSymbol, data.tokenSymbol))
|
||||
group.addItem(TextItem(CardDataId.tokenContractAddress, data.tokenContractAddress))
|
||||
group.addItem(TextItem(CardDataId.tokenDecimal, data.tokenSymbol))
|
||||
|
||||
return group
|
||||
val productMask = data.productMask ?: return
|
||||
|
||||
group.addItem(TextHeaderItem(CardDataId.productMask, ""))
|
||||
Product.values().forEach { group.addItem(BoolItem(StringId(it.name), productMask.contains(it))) }
|
||||
}
|
||||
|
||||
private fun settingsMask(from: SettingsMask?): Item {
|
||||
private fun settingsMaskGroup(itemList: MutableList<Item>, from: SettingsMask?) {
|
||||
val data = from ?: return
|
||||
|
||||
val group = createGroup(CardId.settingsMask, R.color.group_settings_mask)
|
||||
val data = from ?: return group
|
||||
itemList.add(group)
|
||||
|
||||
Settings.values().forEach { group.addItem(BoolItem(StringId(it.name), data.contains(it))) }
|
||||
return group
|
||||
}
|
||||
|
||||
private fun createGroup(id: Id, colorId: Int? = null): ItemGroup {
|
||||
return if (colorId == null) SimpleItemGroup(id)
|
||||
else SimpleItemGroup(id, BaseItemViewModel(viewState = ViewState(bgColor = colorId)))
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,12 @@
|
|||
package com.tangem.tangemtest.ucase.variants.responses.item
|
||||
|
||||
import com.tangem.tangemtest._arch.structure.Id
|
||||
import com.tangem.tangemtest._arch.structure.abstraction.BaseItemViewModel
|
||||
import com.tangem.tangemtest._arch.structure.abstraction.ItemViewModel
|
||||
import com.tangem.tangemtest._arch.structure.abstraction.ViewState
|
||||
import com.tangem.tangemtest._arch.structure.impl.TypedItem
|
||||
|
||||
open class TextHeaderItem(id: Id, viewModel: ItemViewModel) : TypedItem<String>(id, viewModel) {
|
||||
constructor(id: Id, value: String? = null, viewState: ViewState = ViewState())
|
||||
: this(id, BaseItemViewModel(value, viewState))
|
||||
}
|
||||
|
|
@ -6,6 +6,7 @@ import com.tangem.tangemtest._arch.structure.impl.BoolItem
|
|||
import com.tangem.tangemtest._arch.structure.impl.TextItem
|
||||
import com.tangem.tangemtest._arch.widget.ItemWidgetBuilder
|
||||
import com.tangem.tangemtest._arch.widget.abstraction.ViewWidget
|
||||
import com.tangem.tangemtest.ucase.variants.responses.item.TextHeaderItem
|
||||
|
||||
/**
|
||||
[REDACTED_AUTHOR]
|
||||
|
|
@ -13,6 +14,7 @@ import com.tangem.tangemtest._arch.widget.abstraction.ViewWidget
|
|||
class ResponseItemBuilder : ItemWidgetBuilder {
|
||||
override fun build(item: BaseItem, parent: ViewGroup): ViewWidget? {
|
||||
return when (item) {
|
||||
is TextHeaderItem -> ResponseHeaderWidget(parent, item)
|
||||
is TextItem -> ResponseTextWidget(parent, item)
|
||||
is BoolItem -> CheckBoxWidget(parent, item)
|
||||
else -> null
|
||||
|
|
|
|||
|
|
@ -4,6 +4,7 @@ import android.view.ViewGroup
|
|||
import android.widget.TextView
|
||||
import com.tangem.tangemtest.R
|
||||
import com.tangem.tangemtest._arch.structure.impl.TextItem
|
||||
import com.tangem.tangemtest.ucase.variants.responses.item.TextHeaderItem
|
||||
|
||||
/**
|
||||
[REDACTED_AUTHOR]
|
||||
|
|
@ -27,4 +28,18 @@ class ResponseTextWidget(
|
|||
tvName.text = getName()
|
||||
tvValue.text = data
|
||||
}
|
||||
}
|
||||
|
||||
class ResponseHeaderWidget(
|
||||
parent: ViewGroup,
|
||||
private val typedItem: TextHeaderItem
|
||||
) : ResponseWidget(parent, typedItem) {
|
||||
override fun getLayoutId(): Int = R.layout.w_response_item_header
|
||||
|
||||
private val tvName: TextView = view.findViewById(R.id.tv_name)
|
||||
|
||||
init {
|
||||
tvName.text = getName()
|
||||
|
||||
}
|
||||
}
|
||||
35
tangem-demo/src/main/res/layout/w_response_item_header.xml
Normal file
35
tangem-demo/src/main/res/layout/w_response_item_header.xml
Normal file
|
|
@ -0,0 +1,35 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:id="@+id/root"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:background="@color/field_header_background">
|
||||
|
||||
<LinearLayout
|
||||
android:id="@+id/container_field"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="vertical"
|
||||
android:padding="@dimen/def_indent"
|
||||
android:paddingBottom="8dp">
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_name"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:textColor="@color/field_content"
|
||||
android:textSize="16sp"
|
||||
tools:text="Custom blockchain" />
|
||||
|
||||
<include layout="@layout/w_field_description" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
<include
|
||||
layout="@layout/m_divider_h"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="1dp"
|
||||
android:layout_gravity="bottom" />
|
||||
|
||||
</FrameLayout>
|
||||
|
|
@ -57,7 +57,7 @@
|
|||
<string name="info_response_card_status">Current status of the card</string>
|
||||
<string name="info_response_card_firmware_version">Version of Tangem COS</string>
|
||||
<string name="info_response_card_public_key">Public key that is used to authenticate the card against manufacturer’s database. It is generated one time during card manufacturing. See Security section for more details.</string>
|
||||
<string name="info_response_card_settings_mask">Card settings defined by personalization (bit mask: 0 – Enabled, 1 – Disabled):</string>
|
||||
<string name="info_response_card_settings_mask">Card settings defined by personalization.</string>
|
||||
<string name="info_response_card_is_reusable">Defines what happens when user calls PURGE_WALLET command:
|
||||
\n0 - Card will switch to Purged state
|
||||
\n1 - Card will switch to Empty state and let create a new wallet again</string>
|
||||
|
|
@ -72,29 +72,29 @@
|
|||
<string name="info_response_card_one_apdu_at_time">Card will execute only one command during one communication session, thus requiring user to physically take the card away from the host after each action (all commands except for READ_CARD).</string>
|
||||
<string name="info_response_card_use_ndef">Whether the card should emulate NDEF. In default configuration, two NDEF records are loaded during personalization: (1) Tangem web site address, (2) name of Android App package in Google Play Store.</string>
|
||||
<string name="info_response_card_use_dynamic_ndef">0 – Disable dynamic generation of NDEF for iOS. See Dynamic NDEF section for more details.
|
||||
/n1 – Enable dynamic NDEF for iOS.</string>
|
||||
\n1 – Enable dynamic NDEF for iOS.</string>
|
||||
<string name="info_response_card_smart_security_delay">Security delay Pause_Before_PIN2 will not be applied if PIN2 is not default.</string>
|
||||
<string name="info_response_card_allow_unencrypted">Whether the card supports unencrypted NFC communication. See NFC communication section for more details.</string>
|
||||
<string name="info_response_card_allow_fast_encryption">Whether the card supports fast encrypted NFC communication. See NFC communication section for more details.</string>
|
||||
<string name="info_response_card_protect_issuer_data_against_replay">0 – No replay protection on write issuer data
|
||||
/n1 – Enable replay protection on write issuer data (card will require additional Issuer_Data_Counter incremented on each write)</string>
|
||||
\n1 – Enable replay protection on write issuer data (card will require additional Issuer_Data_Counter incremented on each write)</string>
|
||||
<string name="info_response_card_allow_select_blockchain">0 – Wallet elliptic curve and blockchain information stored during PERSONALIZE command and never change
|
||||
/n1 – Wallet elliptic curve and blockchain information can be changed on CREATE_WALLET command</string>
|
||||
\n1 – Wallet elliptic curve and blockchain information can be changed on CREATE_WALLET command</string>
|
||||
<string name="info_response_card_disable_precomputed_ndef">0 – Enable precomputed dynamic NDEF to work around iPhone 7+ NFC bug.
|
||||
/n1 – Disable precomputed dynamic NDEF. See Dynamic NDEF section for more details.</string>
|
||||
\n1 – Disable precomputed dynamic NDEF. See Dynamic NDEF section for more details.</string>
|
||||
<string name="info_response_card_security_delay_if_validated">0 – Enforce security delay in SIGN command if the issuer validates the transaction (for signing methods 2, 3, 4 and 5).
|
||||
/n1 – Skip security delay in SIGN command if the issuer validates the transaction (for signing methods 2, 3, 4 and 5).</string>
|
||||
\n1 – Skip security delay in SIGN command if the issuer validates the transaction (for signing methods 2, 3, 4 and 5).</string>
|
||||
<string name="info_response_card_skip_pin2_cvc_if_validated_by_issuer">0 – Require and check PIN2 and CVC in SIGN command if the issuer validates the transaction (for signing method 2, 3, 4 and 5).
|
||||
/n1 – Skip checking PIN2 and CVC in SIGN command if the issuer validates the transaction (for signing method 2, 3, 4 and 5).</string>
|
||||
\n1 – Skip checking PIN2 and CVC in SIGN command if the issuer validates the transaction (for signing method 2, 3, 4 and 5).</string>
|
||||
<string name="info_response_card_skip_security_delay_if_validated_by_linked_terminal">1 - Store Terminal_PublicKey public key of linked terminal no each SIGN command, skip security delay if valid signature of transaction is made with Terminal_PrivateKey is provided in SIGN command</string>
|
||||
<string name="info_response_card_restrict_overwrite_issuer_ex_data"></string>
|
||||
<string name="info_info_response_card_prohibit_overwriting_issuer_ex_data"></string>
|
||||
<string name="info_response_card_require_terminal_tx_sig">0 – Skip checking terminal’s signature when signing POS transaction
|
||||
/n1 – Check terminal’s signature when signing POS transaction</string>
|
||||
\n1 – Check terminal’s signature when signing POS transaction</string>
|
||||
<string name="info_response_card_require_terminal_cert_sig">0 – Skip checking acquirer’s signature of terminal certificate when signing POS transaction
|
||||
/n1 – Check acquirer’s signature of terminal certificate when signing POS transaction</string>
|
||||
\n1 – Check acquirer’s signature of terminal certificate when signing POS transaction</string>
|
||||
<string name="info_response_card_check_pin3">0 – Additionally encrypt POS transaction signature with key derived from PIN3 when the transaction amount exceeds PIN3 floor limit
|
||||
/n1 – Require terminal to send PIN3 to card when the POS transaction amount exceeds PIN3_Floor_Limit</string>
|
||||
\n1 – Require terminal to send PIN3 to card when the POS transaction amount exceeds PIN3_Floor_Limit</string>
|
||||
<string name="info_response_card_card_data">Detailed information about card contents. Format is defined by the card issuer. Cards complaint with Tangem Wallet application should have TLV format described in Personalization section.</string>
|
||||
<string name="info_response_card_issuer_data_public_key">Public key that is used by the card issuer to sign Issuer_Data field. See Security section for more details.</string>
|
||||
<string name="info_response_card_curve">Explicit text name of the elliptic curve used for all wallet key operations.</string>
|
||||
|
|
@ -106,12 +106,12 @@
|
|||
<string name="info_response_card_wallet_signed_hashes">Total number of signed single hashes returned by the card in SIGN command responses since card personalization. Sums up array elements within all SIGN commands.</string>
|
||||
<string name="info_response_card_health">Any non-zero value indicates that the card experiences some hardware problems. User should withdraw the value to other blockchain wallet as soon as possible. Non-zero Health tag will also appear in responses of all other commands.</string>
|
||||
<string name="info_response_card_is_activated">Whether the card requires issuer’s confirmation of activation.
|
||||
/n0 – card will require issuer’s confirmation of activation,
|
||||
/notherwise this field will not be returned (card is activated and operational).</string>
|
||||
\n0 – card will require issuer’s confirmation of activation,
|
||||
\notherwise this field will not be returned (card is activated and operational).</string>
|
||||
<string name="info_response_card_activation_seed">A random challenge generated by PERSONALIZE command that should be signed and returned to COS by the issuer to confirm the card has been activated. See ACTIVATE_CARD command for more details.
|
||||
/nThis field will not be returned if the card is activated.</string>
|
||||
\nThis field will not be returned if the card is activated.</string>
|
||||
<string name="info_response_card_payment_flow_version">Version of POS payment scheme supported by COS ([0x02,0x01] for version 2.30)
|
||||
/nReturned only if SigningMethod ‘6’ enabling POS transactions is supported by card.</string>
|
||||
\nReturned only if SigningMethod ‘6’ enabling POS transactions is supported by card.</string>
|
||||
<string name="info_response_card_user_counter">This value can be initialized by App and will be increased by COS with the execution of each SIGN command. For example, this field can store blockchain “nonce” for a quick one-touch transaction on POS terminals. Returned only if SigningMethod =6.</string>
|
||||
<string name="info_response_card_user_protected_counter">This value can be initialized by App (with PIN2 confirmation) and will be increased by COS with the execution of each SIGN command. For example, this field can store blockchain “nonce” for a quick one-touch transaction on POS terminals. Returned only if SigningMethod =6.</string>
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue