木偶:file_line计算os.path.join

时间:2018-12-11 08:15:48

标签: mysql regex django puppet

我正在尝试替换Django设置行

'NAME': os.path.join(BASE_DIR , 'db.sqlite3'),

作者

'NAME': os.path.join(BASE_DIR , 'db.mysql'),

但找不到它。

带有ENGINE参数的另一行工作正常。问题必须出在“ os.path.join”部分。

  # replace sqlite3 db with mysql
    file { '/var/www/mysite/mysite/settings.py':
      ensure => present,
    }
    file_line { 'replace db engine':
      path                => '/var/www/mysite/mysite/settings.py',
      replace             => true,
      line                => "'ENGINE': 'django.db.backends.mysql',",
      match               => "'ENGINE': 'django.db.backends.sqlite3',",
      append_on_no_match  => false,
    }

    file_line { 'replace db name':
      path                => '/var/www/mysite/mysite/settings.py',
      replace             => true,
      line                => "\'NAME\': os.path.join(BASE_DIR , \'db.mysql\'),",
      match               => "\'NAME\': os.path.join(BASE_DIR , \'db.sqlite3\'),",
      append_on_no_match  => false,
    }

我尝试使用\'而不使用\。

有人可以帮忙吗?

编辑: 因此,如果我事先添加了以下内容:

  class { '::mysql::server':
    root_password    => 'strongpassword',
    override_options => { 'mysqld' => { 'max_connections' => '1024' } }
  }

  mysql::db { 'mynewDB':
    user     => 'admin',
    password => 'secret',
    host     => 'master.puppetlabs.vm',
    sql        => '/tmp/states.sql',
    require => File['/tmp/states.sql'],
  }

然后我将NAME参数替换为“ mynewDB”吗? 我理解正确吗?

1 个答案:

答案 0 :(得分:3)

您需要记住,match资源的file_line参数传达的是正则表达式,而不是纯字符串。 Puppet使用Ruby的正则表达式。与其他方言一样,在方言中,括号(())是元字符,表示分组。如果要将它们解释为文字,则必须转义它们。此外,由于Ruby正则表达式使用与Puppet字符串相同的转义字符,因此,您还必须对转义字符进行转义,以将其通过Puppet传递给基础正则表达式引擎。另一方面,您不必在双引号字符串内转义单引号,反之亦然,尽管这样做并没有害处。

示例:

file_line { 'replace db name':
  path                => '/var/www/mysite/mysite/settings.py',
  replace             => true,
  line                => "'NAME': os.path.join(BASE_DIR , 'db.mysql'),",
  match               => "'NAME': os.path.join\\(BASE_DIR , 'db.sqlite3'\\),",
  append_on_no_match  => false,
}

但这是一个糟糕的设计。如果要确保正确命名所需的数据库(无论实际名称是什么),则应尽可能最大程度地以不依赖于的方式匹配要管理的行当前数据库名称。

我不了解Django的详细信息,但是如果您只能依赖设置文件中指定的一个NAME属性,那么您可以执行以下操作:

file_line { 'replace db name':
  path                => '/var/www/mysite/mysite/settings.py',
  replace             => true,
  line                => 'Whatever the line should really be',
  match               => "\\s*'NAME':.*",
  append_on_no_match  => false,
}

那里的match表达式匹配带有任意数量的前导空格的行,后跟文字字符'NAME':,后跟任何内容

但是您还应该考虑file_line是否完全适合该工作。仅当您需要容纳在Puppet外部管理文件的某些部分时,这才有意义,这是一种令人不舒服的情况,尽管有时我们会遇到这种情况。不过,如果可能的话,最好让Puppet管理整个文件,包括其完整内容。