syntax = "proto3";
package ethereum.validator.accounts.v2;

import "proto/prysm/v1alpha1/health.proto";
import "proto/prysm/v1alpha1/beacon_chain.proto";
import "proto/prysm/v1alpha1/node.proto";
import "google/api/annotations.proto";
import "google/protobuf/empty.proto";

option csharp_namespace = "Ethereum.Validator.Accounts.V2";
option go_package = "github.com/prysmaticlabs/prysm/proto/prysm/v1alpha1/validator-client;validatorpb";
option java_multiple_files = true;
option java_outer_classname = "WebProto";
option java_package = "org.ethereum.validator.accounts.v2";
option php_namespace = "Ethereum\\Validator\\Accounts\\V2";

service Wallet {
    rpc CreateWallet(CreateWalletRequest) returns (CreateWalletResponse) {
        option (google.api.http) = {
            post: "/v2/validator/wallet/create",
            body: "*"
        };
    }
    rpc WalletConfig(google.protobuf.Empty) returns (WalletResponse) {
        option (google.api.http) = {
            get: "/v2/validator/wallet"
        };
    }
    rpc ImportAccounts(ImportAccountsRequest) returns (ImportAccountsResponse) {
        option (google.api.http) = {
            post: "/v2/validator/wallet/keystores/import",
            body: "*"
        };
    }
    rpc ValidateKeystores(ValidateKeystoresRequest) returns (google.protobuf.Empty) {
        option (google.api.http) = {
            post: "/v2/validator/wallet/keystores/validate",
            body: "*"
        };
    }
    rpc RecoverWallet(RecoverWalletRequest) returns (CreateWalletResponse) {
        option (google.api.http) = {
            post: "/v2/validator/wallet/recover"
            body: "*"
        };
    }
}

service Accounts {
    rpc ListAccounts(ListAccountsRequest) returns (ListAccountsResponse) {
        option (google.api.http) = {
            get: "/v2/validator/accounts"
        };
    }
    rpc BackupAccounts(BackupAccountsRequest) returns (BackupAccountsResponse) {
        option (google.api.http) = {
            post: "/v2/validator/accounts/backup",
            body: "*"
        };
    }
    rpc DeleteAccounts(DeleteAccountsRequest) returns (DeleteAccountsResponse) {
        option (google.api.http) = {
            post: "/v2/validator/wallet/accounts/delete",
            body: "*"
        };
    }
    rpc VoluntaryExit(VoluntaryExitRequest) returns (VoluntaryExitResponse) {
        option (google.api.http) = {
            post: "/v2/validator/accounts/voluntary-exit",
            body: "*"
        };
    }
}

service Beacon {
    rpc GetBeaconStatus(google.protobuf.Empty) returns (BeaconStatusResponse) {
        option (google.api.http) = {
            get: "/v2/validator/beacon/status"
        };
    }
    rpc GetValidatorParticipation(
        ethereum.eth.v1alpha1.GetValidatorParticipationRequest
    ) returns (ethereum.eth.v1alpha1.ValidatorParticipationResponse) {
        option (google.api.http) = {
            get: "/v2/validator/beacon/participation"
        };
    }
    rpc GetValidatorPerformance(
        ethereum.eth.v1alpha1.ValidatorPerformanceRequest
    ) returns (ethereum.eth.v1alpha1.ValidatorPerformanceResponse) {
        option (google.api.http) = {
            get: "/v2/validator/beacon/summary"
        };
    }
    rpc GetValidators(
        ethereum.eth.v1alpha1.ListValidatorsRequest
    ) returns (ethereum.eth.v1alpha1.Validators) {
        option (google.api.http) = {
            get: "/v2/validator/beacon/validators"
        };
    }
    rpc GetValidatorBalances(
        ethereum.eth.v1alpha1.ListValidatorBalancesRequest
    ) returns (ethereum.eth.v1alpha1.ValidatorBalances) {
        option (google.api.http) = {
            get: "/v2/validator/beacon/balances"
        };
    }
    rpc GetValidatorQueue(google.protobuf.Empty) returns (ethereum.eth.v1alpha1.ValidatorQueue) {
        option (google.api.http) = {
            get: "/v2/validator/beacon/queue"
        };
    }
    rpc GetPeers(google.protobuf.Empty) returns (ethereum.eth.v1alpha1.Peers) {
        option (google.api.http) = {
            get: "/v2/validator/beacon/peers"
        };
    }
}

service SlashingProtection {
    rpc ExportSlashingProtection(google.protobuf.Empty) returns (ExportSlashingProtectionResponse) {
        option (google.api.http) = {
            get: "/v2/validator/slashing-protection/export"
        };
    }
    rpc ImportSlashingProtection(ImportSlashingProtectionRequest) returns (google.protobuf.Empty) {
        option (google.api.http) = {
            post: "/v2/validator/slashing-protection/import"
            body: "*"
        };
    }
}

service Health {
    rpc GetBeaconNodeConnection(google.protobuf.Empty) returns (NodeConnectionResponse) {
        option (google.api.http) = {
            get: "/v2/validator/health/node_connection"
        };
    }
    rpc GetLogsEndpoints(google.protobuf.Empty) returns (LogsEndpointResponse) {
        option (google.api.http) = {
            get: "/v2/validator/health/logs/endpoints"
        };
    }
    rpc GetVersion(google.protobuf.Empty) returns (VersionResponse) {
        option (google.api.http) = {
            get: "/v2/validator/health/version"
        };
    }
    rpc StreamBeaconLogs(google.protobuf.Empty) returns (stream ethereum.eth.v1alpha1.LogsResponse) {
        option (google.api.http) = {
            get: "/v2/validator/health/logs/beacon/stream"
        };
    }
    rpc StreamValidatorLogs(google.protobuf.Empty) returns (stream ethereum.eth.v1alpha1.LogsResponse) {
        option (google.api.http) = {
            get: "/v2/validator/health/logs/validator/stream"
        };
    }
}

service Auth {
    rpc Initialize(google.protobuf.Empty) returns (InitializeAuthResponse) {
        option (google.api.http) = {
            get: "/v2/validator/initialize",
        };
    }
}

// Type of key manager for the wallet, either derived, imported, or remote.
enum KeymanagerKind {
    DERIVED = 0;
    IMPORTED = 1;
    REMOTE = 2;
    WEB3SIGNER = 3;
}

message CreateWalletRequest {
    // Path on disk where the wallet will be stored.
    KeymanagerKind keymanager = 1;

    // Password for the wallet.
    string wallet_password = 2;
    // Mnemonic in case the user is creating a derived wallet.
    string mnemonic = 3;
    // Number of accounts.
    uint64 num_accounts = 4;

    // Remote address such as host.example.com:4000 for a gRPC remote signer server.
    string remote_addr = 5;
    // Path to client.crt for secure TLS connections to a remote signer server.
    string remote_crt_path = 6;
    // Path to client.key for secure TLS connections to a remote signer server.
    string remote_key_path = 7;
    // Path to ca.crt for secure TLS connections to a remote signer server.
    string remote_ca_crt_path = 8;
}

message CreateWalletResponse {
    WalletResponse wallet = 1;
}

message EditWalletConfigRequest {
    string remote_addr = 1;
    string remote_crt_path = 2;
    string remote_key_path = 3;
    string remote_ca_crt_path = 4;
}

message GenerateMnemonicResponse {
    string mnemonic = 1;
}

message WalletResponse {
    string wallet_path = 1;
    KeymanagerKind keymanager_kind = 2;
}

message RecoverWalletRequest {
    string mnemonic = 1;
    uint64 num_accounts = 2;
    string wallet_password = 3;
    string language = 4;
    string mnemonic25th_word = 5;
}

message ValidateKeystoresRequest {
    // JSON-encoded keystore files to validate.
    repeated string keystores = 1;

    // Password for the keystore files.
    string keystores_password = 2;
}

message ListAccountsRequest {
    // Whether or not to return the raw RLP deposit tx data.
    bool get_deposit_tx_data = 1;

    // The maximum number of accounts to return in the response.
    // This field is optional.
    int32 page_size = 2;

    // A pagination token returned from a previous call to `ListAccounts`
    // that indicates where this listing should continue from.
    // This field is optional.
    string page_token = 3;

    // Whether to return all available accounts in a single response.
    bool all = 4;
}

message ListAccountsResponse {
    repeated Account accounts = 1;

    // A pagination token returned from a previous call to `ListAccounts`
    // that indicates from where listing should continue.
    // This field is optional.
    string next_page_token = 2;

    // Total count matching the request.
    int32 total_size = 3;
}

message Account {
    // The validating public key.
    bytes validating_public_key = 1;
    // The human readable account name.
    string account_name = 2;
    // The deposit data transaction RLP bytes.
    bytes deposit_tx_data = 3;
    // The derivation path (if using HD wallet).
    string derivation_path = 4;
}

message AccountRequest {
    // A list of validator public keys.
    repeated bytes public_keys = 1;
    // A list of validator indices.
    repeated uint64 indices = 2;
}

message NodeConnectionResponse {
    // The host address of the beacon node the validator
    // client is connected to.
    string beacon_node_endpoint = 1;
    // Whether the connection is active.
    bool connected = 2;
    // Whether the beacon node is currently synchronizing to chain head.
    bool syncing = 3;
    // The chain genesis time.
    uint64 genesis_time = 4;
    // Address of the validator deposit contract in the eth1 chain.
    bytes deposit_contract_address = 5;
}

message LogsEndpointResponse {
	string validator_logs_endpoint = 1;
	string beacon_logs_endpoint = 2;
}

message VersionResponse {
	string beacon = 1;
	string validator = 2;
}

message HasWalletResponse {
    // Whether or not the user has a wallet on disk.
    bool wallet_exists = 1;
}

message ImportAccountsRequest {
    // JSON-encoded keystore files to import during wallet creation.
    repeated string keystores_imported = 1;

    // Password to unlock imported keystore files.
    string keystores_password = 2;
}

message ImportAccountsResponse {
    repeated bytes imported_public_keys = 1;
}

message InitializeAuthRequest {
    string token = 1;
}

message InitializeAuthResponse {
    bool has_signed_up = 1;
    bool has_wallet = 2;
}

message BeaconStatusResponse {
    // The host address of the beacon node the validator
    // client is connected to.
    string beacon_node_endpoint = 1;
    // Whether the connection is active.
    bool connected = 2;
    // Whether the beacon node is currently synchronizing to chain head.
    bool syncing = 3;
    // The chain genesis time.
    uint64 genesis_time = 4;
    // Address of the validator deposit contract in the eth1 chain.
    bytes deposit_contract_address = 5;
    // The head of the chain from the beacon node.
    ethereum.eth.v1alpha1.ChainHead chain_head = 6;
}

message VoluntaryExitRequest {
    // List of public keys to voluntarily exit.
    repeated bytes public_keys = 1;
}

message VoluntaryExitResponse {
    // List of keys that successfully exited.
    repeated bytes exited_keys = 1;
}

message BackupAccountsRequest {
    // List of public keys to backup.
    repeated bytes public_keys = 1;

    string backup_password = 2;
}

message BackupAccountsResponse {
    // Zip file containing backed up keystores.
    bytes zip_file = 1;
}

message DeleteAccountsRequest {
    // List of public keys to delete.
    repeated bytes public_keys_to_delete = 1;
}

message DeleteAccountsResponse {
    // List of public keys successfully deleted.
    repeated bytes deleted_keys = 1;
}

message ExportSlashingProtectionResponse {
    // JSON representation of the slash protection
    string file = 1;
}

message ImportSlashingProtectionRequest {
    // JSON representation of the slash protection
    string slashing_protection_json = 1;
}
