Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[ansible/xray] Expect - extra characters after close-quote #424

Open
EmptyByte opened this issue Oct 28, 2024 · 4 comments
Open

[ansible/xray] Expect - extra characters after close-quote #424

EmptyByte opened this issue Oct 28, 2024 · 4 comments
Labels
bug Something isn't working

Comments

@EmptyByte
Copy link

The following error is returned when running tasks Interactive with expect:

extra characters after close-quote
    while executing
"send ""h"
    invoked from within
"expect {
                    -nocase -re {(data|installation) directory \(.*} {
                send "/opt/jfrog/xray\n"
            }
               ..."
    ("while" body line 2)
    invoked from within
"while { $CYCLE_END == 0 } {
    expect {
                    -nocase -re {(data|installation) directory \(.*} {
                send "/opt/jfrog/xray\..."

Ansible/ansible_collections/jfrog/platform/roles/xray/tasks/expect.yml

- name: Prepare expect scenario script
  ansible.builtin.set_fact:
    expect_scenario: |
        set timeout 300
        spawn {{ exp_executable_cmd }}
        expect_before timeout { exit 1 }
        set CYCLE_END 0
        set count 0

        while { $CYCLE_END == 0 } {
            expect {
                {% for each_request in exp_scenarios %}
                    -nocase -re {{ '{' }}{{ each_request.expecting }}.*} {
                        send "{{ each_request.sending }}\n"
                    }
                {% endfor %}
                eof {
                    set CYCLE_END 1
                }
            }
            set count "[expr $count + 1]"
            if { $count > 16} {
                exit 128
            }
        }

        expect eof
        lassign [wait] pid spawnid os_error_flag value

        if {$os_error_flag == 0} {
            puts "INSTALLER_EXIT_STATUS-$value"
        } else {
            puts "INSTALLER_EXIT_STATUS-$value"
        }

Maybe the task should have proper closing:

- name: Prepare expect scenario script
  ansible.builtin.set_fact:
    expect_scenario: |
        set timeout 300
        spawn {{ exp_executable_cmd }}
        expect_before timeout { exit 1 }
        set CYCLE_END 0
        set count 0

        while { $CYCLE_END == 0 } {
            expect {
                {% for each_request in exp_scenarios %}
                    -nocase -re {{ '{' }}{{ each_request.expecting }}.*{{ '}' }} {
                        send "{{ each_request.sending }}\n"
                    }
                {% endfor %}
                eof {
                    set CYCLE_END 1
                }
            }
            set count "[expr $count + 1]"
            if { $count > 16 } {
                exit 12
            }
        }

        expect eof
        lassign [wait] pid spawnid os_error_flag value

        if {$os_error_flag == 0} {
            puts "INSTALLER_EXIT_STATUS-$value"
        } else {
            puts "INSTALLER_EXIT_STATUS-$value"
        }
@EmptyByte EmptyByte changed the title [ansible/xray] [ansible/xray] Expect - extra characters after close-quote Oct 28, 2024
@chukka
Copy link
Collaborator

chukka commented Nov 18, 2024

@EmptyByte Thanks for raising this issue , Would you mind raising this as a Pull Request, Happy to take this in upcoming releases :)

@chukka chukka added the bug Something isn't working label Nov 22, 2024
@chukka
Copy link
Collaborator

chukka commented Nov 22, 2024

@EmptyByte I still see this issue after your suggested code ! can you please verify one more time

Also, it doesn't impact install/upgrade flow , WDYT ?

@EmptyByte
Copy link
Author

EmptyByte commented Nov 26, 2024

@chukka sorry, I could not test my assumption. This expect scenario is hard to manage (also it may not return the exit code and thus may not fail correctly.

You can try to force quote:

send "{{ each_request.sending }}\n"

to

send "{{ each_request.sending | quote }}\n"

Alternatively we may revisit the structure completely and print the results from these vars (giving the following more or less) ?

# Variable for expect script
xray_expect_install: "./install.sh -u {{ xray_user }} -g {{ xray_group }}"

# Scenario for expect script
xray_expect_scenario:
  default:
    - question: "(data|installation) directory \\("
      response: "{{ xray_home }}"
    - question: "jfrog url( \\(.+\\))?:(?!.*Skipping prompt)"
      response: "{{ jfrog_url }}"
    - question: "join key:(?!.*Skipping prompt)"
      response: "{{ join_key }}"
    - question: "please specify the ip address of this machine(?!.*Skipping prompt)"
      response: "{{ ansible_host }}"
    - question: "are you adding an additional node"
      response: "{% if xray_ha_node_type is defined and xray_ha_node_type == 'master' %}n{% else %}y{% endif %}"
    - question: "do you want to install postgresql"
      response: "n"
    - question: "(postgresql|database) url"
      response: "{{ xray_db_url }}"
    - question: "(postgresql|database) password"
      response: "{{ xray_db_password }}"
    - question: "(postgresql|database) username"
      response: "{{ xray_db_user }}"
    - question: "confirm database password"
      response: "{{ xray_db_password }}"
    - question: "rabbitmq active node name:"
      response: "{{ ansible_machine_id }}"
    - question: "rabbitmq active node ip:"
      response: "{{ ansible_host }}"

# Expect script
xray_expect_script: |
  set timeout 300
  spawn {{ xray_expect_install }}
  expect_before timeout { exit 1 }
  set CYCLE_END 0
  set count 0

  while { $CYCLE_END == 0 } {
      expect {
          {% for request in xray_expect_scenario.default %}
              -nocase -re {{ '{' }}{{ request.question }}.*{{ '}' }} {
                  send "{{ request.response | quote }}\r"
              }
          {% endfor %}
          eof {
              set CYCLE_END 1
          }
      }
      set count "[expr $count + 1]"
      if { $count > 16 } {
          exit 128
      }
  }

  expect eof
  lassign [wait] pid spawnid os_error_flag value

  if {$os_error_flag == 0} {
    puts "exit status: $value"
  } else {
    puts "errno: $value"
  }

Then inside install.yml

- name: Check if install.sh wrapper script exists
  become: true
  ansible.builtin.stat:
    path: "{{ xray_install_script_path }}/install.sh"
  register: stat_xray_install_script

- name: Include expect variables
  ansible.builtin.include_vars: script/expect.yml
  when:
    - stat_xray_install_script.stat.exists
    - not xray_upgrade_only | bool or 
      (download_xray is defined and download_xray is succeeded and xray_upgrade_only | bool)

- name: Execute expect script
  become: true
  ansible.builtin.shell:
    cmd: "{{ xray_expect_script }}"
    executable: '/usr/bin/expect'
    chdir: "{{ xray_install_script_path }}"
  environment:
    YQ_PATH: "{{ xray_thirdparty_path }}/yq"
  register: reg_expect_script_results
  when:
    - stat_xray_install_script.stat.exists
    - not xray_upgrade_only | bool or 
      (download_xray is defined and download_xray is succeeded and xray_upgrade_only | bool)

@EmptyByte
Copy link
Author

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Projects
None yet
Development

No branches or pull requests

2 participants