kovidgoyal/kitty · error · ValueError

No valid action specified in file transmission command

Error message

No valid action specified in file transmission command

What it means

FileTransmissionCommand.deserialize parses the OSC 52-style escape sequence payload into a FileTransmissionCommand. If no recognizable action field was set, ans.action remains Action.invalid and the payload is rejected as malformed.

Source

Thrown at kitty/file_transmission.py:358

            field = fmap.get(key)
            if field is None:
                return
            if inspect.isclass(field.type) and issubclass(field.type, Enum):
                setattr(ans, field.name, field.type[str(val, 'utf-8')])
            elif field.type == bytes | memoryview:
                setattr(ans, field.name, base64_decode(val))
            elif field.type is int:
                setattr(ans, field.name, int(val))
            elif field.type is str:
                if field.metadata.get('base64'):
                    sval = base64_decode(val).decode('utf-8')
                else:
                    sval = safe_string(str(val, 'utf-8'))
                setattr(ans, field.name, sval)

        parse_ftc(data, handle_item)
        if ans.action is Action.invalid:
            raise ValueError('No valid action specified in file transmission command')

        return ans


class IdentityDecompressor:
    def __call__(self, data: bytes | memoryview, is_last: bool = False) -> bytes:
        return bytes(data)


class ZlibDecompressor:
    def __init__(self) -> None:
        import zlib

        self.d = zlib.decompressobj(wbits=0)

    def __call__(self, data: bytes | memoryview, is_last: bool = False) -> bytes:
        ans = self.d.decompress(data)
        if is_last:

View on GitHub (pinned to 6d5d0c4406)

Solutions

  1. Verify the emitter builds the sequence with a valid action (e.g. 'action=file' then 'action=data').
  2. Capture the raw sequence and test with kitty --debug-input to spot mangling.
  3. Update both ends to the same kitty protocol version.
Defensive patterns

Strategy: validation

Validate before calling

from kitty.file_transmission import Action
# before deserialize, sanity-check the raw payload contains an action token
assert b'action=' in data or data.startswith(('file,', 'data,')), 'no action in payload'

Try / catch

try:
    ftc = FileTransmissionCommand.deserialize(data)
except ValueError as e:
    log_bad_frame(data); return  # drop malformed frame

Prevention

When it happens

Trigger: _on_osc / handle_serialized_command receiving an OSC file-transmission sequence whose p1/p2 tokens contain no valid action key, or garbage bytes that parse into no known field.

Common situations: A bug in the sending side (kitten/remote app) constructing the escape sequence; a terminal multiplexer or filter mangling escape sequences; log-replay tooling feeding truncated sequences.

Related errors


AI-assisted analysis of kovidgoyal/kitty@6d5d0c4406 (2026-08-27). Data as JSON: /api/errors/b09b82dbed93a959. Report an issue: GitHub.