2012-02-18 25 views
6

Tôi đang cố gắng tránh tình trạng chạy đua khi thay thế phần mềm đằng sau Dịch vụ bù nhìn.Làm cách nào để tôi có thể chặn con rối trước khi thay thế một tệp?

Để làm điều đó, con rối cần phải dừng dịch vụ, thay thực thi, sau đó bắt đầu dịch vụ. Có cách nào để nói con rối làm việc đó không? Cách làm việc ưa thích của nó dường như là thay thế tệp thực thi, sau đó kiểm tra trạng thái và bắt đầu lại dịch vụ nếu cần.

(. Ví dụ này được contrived Tình trạng đua thực là hư không gần đơn giản này ...)

Đây là con rối biểu hiện tôi đang sử dụng để mô phỏng vấn đề này:

$O = '1' 
$I = '2' 

exec { hi : 
     command => '/bin/echo "$(/bin/date +%s) puppet says hello" >> /tmp/freebird.log' , 
     } 

file { exe : 
     name => "/tmp/freebird" , 
     ensure => present , 
     owner => "root" , 
     group => "root" , 
     mode => "0555" , 
     source => "/root/test-v$I" , 
     } 

file { init : 
     name => '/etc/init.d/freebird' , 
     ensure => present, 
     owner => "root", 
     group => "root", 
     mode => "0555", 
     source => "/root/test.init" , 
     } 

service { freebird : 
     ensure => running, 
     enable => true, 
     hasrestart => true, 
     hasstatus => true, 
     require => [ File[init], File[exe] ], 
     } 

Đây là test-v1 tệp. Tệp test-v2 giống nhau nhưng với v=2.

#!/bin/bash 
v=1 

while true 
do 
     echo "$(date +%s) $v" >> /tmp/freebird-v.log 
     sleep 1 
done 

Và kịch bản init.d: ​​

#!/bin/bash 
# 
# /etc/rc.d/init.d/freebird 

# chkconfig: 2345 90 10 
# description:  freebird 
# Provides:   freebird 
# Required-Start: $syslog $remote_fs 
# Should-Start: 
# Required-Stop:  $syslog $remote_fs 
# Should-Stop: 
# Default-Start:  2 3 4 5 
# Default-Stop:  0 1 6 
# Short-Description: freebird 


# Source function library. 
. /etc/rc.d/init.d/functions 

xme=freebird 
export PATH=/sbin:/bin:/usr/sbin:/usr/bin 

function L() { 
     echo "$(date +%s) $*" 1>&2 
     echo "$(date +%s) $*" >> /tmp/$xme.log 
     } 


case "$1" in 
     (start) L $1 $xme 
       (/tmp/$xme &) 
       ;; 
     (stop) L $1 $xme 
       fuser -k /tmp/$xme 
       ;; 
     (status) L $1 $xme 
       /sbin/fuser /tmp/$xme >/dev/null 2>&1 
       ;; 
     (restart) L $1 $xme 
       $0 stop 
       $0 start 
       ;; 
     (*) 
       echo "Usage: $xme {start|stop|status|restart]" 
       exit 1 
       ;; 
esac 

Trả lời

2

Tôi đang cố gắng để tránh tình trạng chủng tộc khi thay thế các phần mềm đằng sau một vụ rối.

Để làm điều đó, con rối cần dừng dịch vụ, thay thế tệp thực thi, sau đó khởi động dịch vụ. Có cách nào để nói con rối làm việc đó không? Cách làm việc ưa thích của nó dường như là thay thế tệp thực thi, sau đó kiểm tra trạng thái và bắt đầu lại dịch vụ nếu cần.

Vì vậy, vấn đề với những gì Puppet hiện đang làm là luôn khởi động lại dịch vụ sau khi thay thế một số tệp nhất định?

Nếu có, bạn nên sử dụng mối quan hệ thông báo/đăng ký để luôn kích hoạt dịch vụ khởi động lại sau khi các tệp đã được thay thế. Lấy ví dụ của bạn service, chúng tôi có thể thêm đăng ký vào các tệp tạo thành tệp (giống như cách bạn có thể làm với cấu hình) và điều này sẽ kích hoạt khởi động lại nếu một trong hai thay đổi đó.

service { freebird : 
     ensure => running, 
     enable => true, 
     hasrestart => true, 
     hasstatus => true, 
     require => [ File[init], File[exe] ], 
     subscribe => [ File[init], File[exe] ], 
     } 

Cách khác để thực hiện việc này là sử dụng quản lý gói hệ điều hành mà Puppet hỗ trợ tốt. Sau đó bạn sẽ kích hoạt khởi động lại (hoặc dừng/khởi động trong cài đặt trước/sau) từ các kịch bản gói, để lại Puppet để đảm bảo dịch vụ được cấu hình và chạy. Có một cái nhìn tại fpm project của Jordan Sissel cho một công cụ để dễ dàng xây dựng nhiều định dạng gói.

+0

M0dlx, cảm ơn bạn. Nhận xét của bạn đã đẩy tôi vào đúng đường dẫn. Nếu tôi làm tất cả từ đầu, tôi chắc chắn sẽ sử dụng tính năng cài đặt sẵn của trình đóng gói OS thay vì buộc con rối xử lý việc này. Và fpm làm cho điều đó dễ dàng hơn nhiều ... – bugi

+0

@ m0dlx, tôi có một nghi ngờ. Điều gì sẽ xảy ra nếu tệp kê khai của tôi giống như 'Tệp ['X'], Tệp ['Y'], Tệp ['Z'] -> Dịch vụ ['XYZ'] {đăng ký: Tệp ['X', 'Y']}' ? Dịch vụ sẽ được thực hiện/khởi động lại chỉ sau khi 'file 'Z'' đã được tạo hay nó sẽ khởi động lại @ mọi khoảnh khắc' tập tin X/Y/Z' đã được sửa đổi. – harshad

1

Tôi sẽ đặt lại câu hỏi cho sự rõ ràng và tìm kiếm, sau đó cung cấp giải pháp.

Tuy nhiên, tôi khuyên bạn nên sử dụng tính năng cài đặt trước của hệ thống đóng gói gốc của mình nếu bạn có tùy chọn để làm như vậy.

Q: Cách mô phỏng tập lệnh cài đặt sẵn của rpm qua con rối. Một trường hợp sử dụng là dừng dịch vụ bù rối trước khi cài đặt tệp thực thi, sau đó khởi động lại sau khi thay thế tệp. Điều này trái ngược với thứ tự bình thường của con rối thay thế tệp, sau đó khởi động lại dịch vụ.

May mắn thay, trường hợp sử dụng của tôi đã yêu cầu sự lộn xộn của liên kết tượng trưng.Nếu không, vui lòng đăng giải pháp của bạn.

Để chạy thử nghiệm bao gồm các tập tin dưới đây, tôi sửa $tversion trong test.pp sau đó dán vào thiết bị đầu cuối của tôi:

fuser /tmp/freebird-v.log /tmp/freebird 
: > /tmp/freebird.log 
echo ==== >> /tmp/freebird.log ; puppet apply --verbose --onetime --no-daemonize test.pp 2>&1 | tee ~/D ; cat /tmp/freebird.log 
ps auxww|grep freebird 
fuser /tmp/freebird-v.log /tmp/freebird 

file test.pp:

$tversion = '1' 

exec { hi : 
     command => '/bin/echo "$(/bin/date +%s) puppet says hello" >> /tmp/freebird.log' , 
     } 

file { exe : 
     name => "/tmp/freebird-v$tversion" , 
     ensure => present , 
     owner => "root" , 
     group => "root" , 
     mode => "0555" , 
     content => template("/root/test-template") , 
     } 

file { exe_ln : 
     name => "/tmp/freebird" , 
     ensure => link , 
     owner => "root" , 
     group => "root" , 
     mode => "0555" , 
     target => "/tmp/freebird-v$tversion" , 
     } 

file { init : 
     name => '/etc/init.d/freebird' , 
     ensure => present, 
     owner => "root", 
     group => "root", 
     mode => "0555", 
     source => "/root/test.init" , 
     } 

exec { freebird_stop_if_incoherent : 
     command => '/sbin/service freebird stop' , 
     refreshonly => false , # required for when entering at exe_ln 
     onlyif => "/sbin/service freebird status && ! test /tmp/freebird -ef '/tmp/freebird-v$tversion'" , # short-circuits the refreshonly for most cases 
     } 

service { freebird : 
     ensure => running, 
     enable => true, 
     hasrestart => true, 
     hasstatus => true, 
     } 

File[exe_ln]   <~ Exec[freebird_stop_if_incoherent] 
Service[freebird]  <- File[exe_ln] 

Tệp mẫu thử:

#!/bin/bash 
v=<%= tversion %> 

while true 
do 
     echo "$(date +%s) $v" >> /tmp/freebird-v.log 
     sleep 1 
done 

file test.init:

#!/bin/bash 
# 
# /etc/rc.d/init.d/freebird 

# chkconfig: 2345 90 10 
# description:  freebird 
# Provides:   freebird 
# Required-Start: $syslog $remote_fs 
# Should-Start: 
# Required-Stop:  $syslog $remote_fs 
# Should-Stop: 
# Default-Start:  2 3 4 5 
# Default-Stop:  0 1 6 
# Short-Description: freebird 


# Source function library. 
. /etc/rc.d/init.d/functions 

xme=freebird 
export PATH=/sbin:/bin:/usr/sbin:/usr/bin 

function L() { 
     local pid=$$ 
     local ppid=$(ps l $pid |awk '{print $4}' |tail -1) 
     local extra="-- $(ps $ppid|tail -1|sed 's,^[^/]*/,/, ; s,/[0-9][^/]*/,/,')" 
     echo "$(date +%s) $pid $ppid $* $extra" 1>&2 
     echo "$(date +%s) $pid $ppid $* $extra" >>/tmp/$xme.log 2>&1 
     } 


case "$1" in 
     (start) L $1 $xme 
       fuser /tmp/$xme >/dev/null 2>&1 || (/tmp/$xme &) 
       ;; 
     (stop) L $1 $xme 
       fuser /tmp/$xme 2>&1 
       fuser -k /tmp/$xme 1>&2 ||true 
       fuser /tmp/$xme 2>&1 
       true 
       ;; 
     (status) L $1 $xme 
       /sbin/fuser /tmp/$xme >/dev/null 2>&1 
       ;; 
     (restart) L $1 $xme 
       fuser -k /tmp/$xme 1>&2 ||true 
       (/tmp/$xme &) 
       ;; 
     (*) 
       echo "Usage: $xme {start|stop|status|restart]" 
       exit 1 
       ;; 
esac 
Các vấn đề liên quan