let encode al header =
begin match al.Sam.rname with
| Some rname -> find_ref_id header rname
| None -> Ok (-1)
end
>>= fun ref_id ->
let read_name = Option.value ~default:"*" al.Sam.qname in
let seq = Option.value ~default:"*" al.Sam.seq in
let pos = (Option.value ~default:0 al.Sam.pos) - 1 in
let bin = reg2bin pos (pos + String.(length seq)) in
let mapq = Option.value ~default:255 al.Sam.mapq in
let l_read_name = String.length read_name + 1 in
encode_bin_mq_nl ~bin ~mapq ~l_read_name
>>= fun bin_mq_nl ->
let flags = (al.Sam.flags :> int) in
let n_cigar_ops = List.length al.Sam.cigar in
encode_flag_nc ~flags ~n_cigar_ops
>>= fun flag_nc ->
begin match al.Sam.rnext with
| Some `Equal_to_RNAME -> Ok ref_id
| Some (`Value s) -> find_ref_id header s
| None -> Ok (-1)
end
>>= fun next_ref_id ->
let pnext = Option.value ~default:0 al.Sam.pnext - 1 in
let tlen = Option.value ~default:0 al.Sam.tlen in
let cigar = string_of_cigar_ops al.Sam.cigar in
Result.List.map al.Sam.qual ~f:(Biocaml_phred_score.to_char ~offset:`Offset33)
>>| String.of_char_list
>>= fun qual ->
let optional = string_of_optional_fields al.Sam.optional_fields in
Ok {
ref_id; pos; bin_mq_nl; flag_nc; cigar;
next_ref_id; pnext; tlen; seq; qual; optional;
read_name
}