Why Ansible skip items in inserafter? I have about 10 hosts that I run a playbook for them with serial:1. in this playbook there is this code which append output of all commands in one file:

    - name: copy the output to a local file
      lineinfile:
       dest: "{{ myshell_output4.stdout }}"
       line: "{{ item }}"
       insertafter: EOF
      with_items:
        - "########################################################"
        - "###############HOSTNAME:{{ inventory_hostname }}################"
        - "{{ myshell_output3.stdout }}"
        - "########################END#############################"
     delegate_to: localhost


it is always working for the first host but for others it only insert second and third line and skip first and last line. the out put of file is like this:

  ########################################################
  ###############HOSTNAME:12.15.1.1################
  (some output here)
  ########################END#############################
  ###############HOSTNAME:12.15.2.2################
  (some output here)
  ###############HOSTNAME:12.15.3.3################
  (some output here)
  .
  .


why this happen and how i can prevent it?
Apparently delegate_to and lininfile or blockinfile do not work properly together, https://github.com/ansible/ansible/issues/28313.

Module blockinfile

It seems redundant lines have not been written as you would expect. Eventually, blockinfile without a marker does the job.

- name: copy the output to a local file
  blockinfile:
    dest: "{{ myshell_output4.stdout }}"
    marker: false
    block: |
      ########################################################
      ###############HOSTNAME:{{ inventory_hostname }}################
      {{ myshell_output3.stdout }}
      ########################END#############################
  delegate_to: localhost


Concatenate files at the end

Alternatively, you can write to different files and concatenate those files after all tasks have run.

- name: copy the output to a local file
  copy:
    content: |
      ########################################################
      ###############HOSTNAME:{{ inventory_hostname }}################
      {{ myshell_output3.stdout }}
      ########################END#############################
    dest: tmp/{{ inventory_hostname }}
  delegate_to: localhost

- name: log files are concatenated
  assemble:
    src: tmp/
    dest: "{{ myshell_output4.stdout }}"
  delegate_to: localhost
  run_once: true

- name: tmp folder is absent
  path:
    src: tmp/
    state: absent
  delegate_to: localhost
  run_once: true


In case your local file myshell_output4.stdout does exist already and you want to append to an  existing file, you assemble the files tmp/* into tmp/assembled and the append them with lineinfile.

- name: append assembled to a local file
  lineinfile:
    dest: "{{ myshell_output4.stdout }}"
    line: "{{ lookup('file', tmp/assembled) }}"
  delegate_to: localhost
  run_once: true