3
0

Merge branch 'jenkins-build-4' into 'master'

Auto-merge for build 4

See merge request puppet/puppet_cd!2
This commit is contained in:
2025-10-21 19:05:13 +00:00
15 changed files with 832 additions and 48 deletions

19
.vscode/settings.json vendored
View File

@@ -1,11 +1,28 @@
{
"cSpell.words": [
"appender",
"asctime",
"basedirt",
"cachedir",
"devel",
"fastapi",
"getenv",
"hashlib",
"hmac",
"httpx",
"isoformat",
"kahadb",
"levelname",
"logappender",
"pydantic",
"pylint",
"pytest",
"requestlogging",
"springframework",
"startswith",
"Supress",
"trapperkeeper"
"trapperkeeper",
"utcnow",
"uvicorn"
]
}

View File

@@ -123,6 +123,16 @@
</li>
<li>
<span class='object_link'><a href="puppet_classes/puppet_cd_3A_3Ar10k_3A_3Ainstall.html" title="puppet_classes::puppet_cd::r10k::install (puppet_class)">puppet_cd::r10k::install</a></span>
</li>
<li>
<span class='object_link'><a href="puppet_classes/puppet_cd_3A_3Ar10k_3A_3Awebhook.html" title="puppet_classes::puppet_cd::r10k::webhook (puppet_class)">puppet_cd::r10k::webhook</a></span>
</li>
<li>
<span class='object_link'><a href="puppet_classes/puppet_cd_3A_3Aserver_3A_3Aservice.html" title="puppet_classes::puppet_cd::server::service (puppet_class)">puppet_cd::server::service</a></span>

View File

@@ -113,6 +113,20 @@
</li>
<li id="object_puppet_classes::puppet_cd::r10k::install" class="even">
<div class="item">
<span class='object_link'><a href="puppet_classes/puppet_cd_3A_3Ar10k_3A_3Ainstall.html" title="puppet_classes::puppet_cd::r10k::install (puppet_class)">puppet_cd::r10k::install</a></span>
</div>
</li>
<li id="object_puppet_classes::puppet_cd::r10k::webhook" class="odd">
<div class="item">
<span class='object_link'><a href="puppet_classes/puppet_cd_3A_3Ar10k_3A_3Awebhook.html" title="puppet_classes::puppet_cd::r10k::webhook (puppet_class)">puppet_cd::r10k::webhook</a></span>
</div>
</li>
<li id="object_puppet_classes::puppet_cd::server::service" class="even">
<div class="item">
<span class='object_link'><a href="puppet_classes/puppet_cd_3A_3Aserver_3A_3Aservice.html" title="puppet_classes::puppet_cd::server::service (puppet_class)">puppet_cd::server::service</a></span>

View File

@@ -109,7 +109,12 @@
11
12
13
14</pre>
14
15
16
17
18
19</pre>
</td>
<td>
<pre class="code"><span class="info file"># File 'manifests/main/config.pp', line 6</span>
@@ -122,6 +127,11 @@ class puppet_cd::main::config (
if $pt_use_puppetdb == true {
include puppet_cd::puppetdb::service
}
if $pt_use_r10k == true {
include puppet_cd::r10k::install
include puppet_cd::r10k::webhook
}
}</pre>
</td>
</tr>

View File

@@ -77,6 +77,10 @@
<span class='object_link'><a href="puppet_cd_3A_3Amain_3A_3Ainstall.html" title="puppet_classes::puppet_cd::main::install (puppet_class)">puppet_cd::main::install</a></span><br/>
<span class='object_link'><a href="puppet_cd_3A_3Ar10k_3A_3Ainstall.html" title="puppet_classes::puppet_cd::r10k::install (puppet_class)">puppet_cd::r10k::install</a></span><br/>
<span class='object_link'><a href="puppet_cd_3A_3Ar10k_3A_3Awebhook.html" title="puppet_classes::puppet_cd::r10k::webhook (puppet_class)">puppet_cd::r10k::webhook</a></span><br/>
<span class='object_link'><a href="puppet_cd_3A_3Apuppetdb_3A_3Adirs.html" title="puppet_classes::puppet_cd::puppetdb::dirs (puppet_class)">puppet_cd::puppetdb::dirs</a></span><br/>
<span class='object_link'><a href="puppet_cd_3A_3Apuppetdb_3A_3Afiles.html" title="puppet_classes::puppet_cd::puppetdb::files (puppet_class)">puppet_cd::puppetdb::files</a></span><br/>
@@ -242,6 +246,24 @@
</li>
<li>
<span class='name'>pt_r10k_pkg</span>
<span class='type'>(<tt>Array</tt>)</span>
<em class="default">(defaults to: <tt>[&#39;ruby&#39;,&#39;ruby-devel&#39;]</tt>)</em>
&mdash;
<div class='inline'>
<p>the packages for r10k to install</p>
</div>
</li>
<li>
<span class='name'>pt_no_ssl_port</span>
@@ -296,24 +318,6 @@
</li>
<li>
<span class='name'>pt_manage_user</span>
<span class='type'>(<tt>Boolean</tt>)</span>
<em class="default">(defaults to: <tt>true</tt>)</em>
&mdash;
<div class='inline'>
<p>whether to manage the puppet user</p>
</div>
</li>
<li>
<span class='name'>pt_user</span>
@@ -1376,6 +1380,109 @@
</li>
<li>
<span class='name'>pt_use_r10k</span>
<span class='type'>(<tt>Boolean</tt>)</span>
<em class="default">(defaults to: <tt>false</tt>)</em>
&mdash;
<div class='inline'>
<p>whether to use r10k service</p>
</div>
</li>
<li>
<span class='name'>pt_use_r10k_webhook</span>
<span class='type'>(<tt>Boolean</tt>)</span>
<em class="default">(defaults to: <tt>false</tt>)</em>
&mdash;
<div class='inline'>
<p>whether to use r10k webhook service</p>
</div>
</li>
<li>
<span class='name'>pt_r10k_remote</span>
<span class='type'>(<tt>String</tt>)</span>
<em class="default">(defaults to: <tt>&#39;git@gitlab.example.net/repo.git&#39;</tt>)</em>
&mdash;
<div class='inline'>
<p>the remote url for the r10k control repo</p>
</div>
</li>
<li>
<span class='name'>pt_r10k_prefix</span>
<span class='type'>(<tt>Boolean</tt>)</span>
<em class="default">(defaults to: <tt>false</tt>)</em>
&mdash;
<div class='inline'>
<p>the r10k prefix. defaults to false</p>
</div>
</li>
<li>
<span class='name'>pt_r10k_basedir</span>
<span class='type'>(<tt>String</tt>)</span>
<em class="default">(defaults to: <tt>&#39;/etc/puppetlabs/code/environments&#39;</tt>)</em>
&mdash;
<div class='inline'>
<p>the base directory for r10k.yaml</p>
</div>
</li>
<li>
<span class='name'>pt_manage_user</span>
<span class='type'>(<tt>Boolean</tt>)</span>
<em class="default">(defaults to: <tt>true</tt>)</em>
</li>
</ul>
@@ -1387,11 +1494,6 @@
<pre class="lines">
81
82
83
84
85
86
87
88
@@ -1524,10 +1626,32 @@
215
216
217
218</pre>
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240</pre>
</td>
<td>
<pre class="code"><span class="info file"># File 'manifests/params.pp', line 81</span>
<pre class="code"><span class="info file"># File 'manifests/params.pp', line 86</span>
class puppet_cd::params (
@@ -1540,6 +1664,7 @@ class puppet_cd::params (
String $pt_agent_pkg = &#39;puppet-agent&#39;,
String $pt_server_pkg = &#39;puppetserver&#39;,
Array $pt_db_pkg = [&#39;puppetdb&#39;,&#39;puppetdb-termini&#39;],
Array $pt_r10k_pkg = [&#39;ruby&#39;,&#39;ruby-devel&#39;],
# user settings
## puppet user
@@ -1583,7 +1708,7 @@ class puppet_cd::params (
String $pt_storeconfigs_backend = &#39;puppetdb&#39;,
String $pt_parser = &#39;current&#39;,
Boolean $pt_cert_revocation = true,
## puppetdb
## puppetdb
Boolean $pt_use_puppetdb = false,
String $pt_logging_max_file_size = &#39;200MB&#39;,
String $pt_logging_max_history = &#39;90&#39;,
@@ -1611,8 +1736,19 @@ class puppet_cd::params (
String $pt_repl_port = &#39;8082&#39;,
String $pt_repl_host = &#39;127.0.0.1&#39;,
# r10k
Boolean $pt_use_r10k = false,
Boolean $pt_use_r10k_webhook = false,
String $pt_r10k_remote = &#39;git@gitlab.example.net/repo.git&#39;,
Boolean $pt_r10k_prefix = false,
String $pt_r10k_basedir = &#39;/etc/puppetlabs/code/environments&#39;,
) {
$fqdn = $facts[&#39;networking&#39;][&#39;fqdn&#39;]
# facts
$fqdn = $facts[&#39;networking&#39;][&#39;fqdn&#39;]
$domain = $facts[&#39;networking&#39;][&#39;domain&#39;]
$os_name = $facts[&#39;os&#39;][&#39;name&#39;]
$os_release = $facts[&#39;os&#39;][&#39;release&#39;][&#39;major&#39;]
# directories
## puppet
@@ -1632,6 +1768,8 @@ class puppet_cd::params (
$pt_puppetdb_ssl = &quot;${pt_puppetdb_main}/ssl&quot;
$pt_puppetdb_log = &#39;/var/log/puppetlabs/puppetdb&#39;
$pt_puppetdb_var_dir = &#39;/opt/puppetlabs/server/data/puppetdb&#39;
## r10k
$pt_r10k_dir = &quot;${pt_main_dir}/r10k&quot;
# files
## puppet
@@ -1641,22 +1779,25 @@ class puppet_cd::params (
$pt_hiera_config = &quot;${pt_puppetdir}/hiera.yaml&quot;
## puppetdb
$pt_bootstrap_conf = &quot;${pt_puppetdb_main}/bootstrap.cfg&quot;
$pt_bootstrap_erb = &#39;cd_puppet/puppetdb/bootstrap.cfg.erb&#39;
$pt_bootstrap_erb = &#39;puppet_cd/puppetdb/bootstrap.cfg.erb&#39;
$pt_puppetdb_access_log = &quot;${pt_puppetdb_log}/puppetdb-access&quot;
$pt_request_logging_conf = &quot;${pt_puppetdb_main}/request-logging.xml&quot;
$pt_request_logging_erb = &#39;cd_puppet/puppetdb/request_logging.xml.erb&#39;
$pt_request_logging_erb = &#39;puppet_cd/puppetdb/request_logging.xml.erb&#39;
$pt_logback_conf = &quot;${pt_puppetdb_main}/logback.xml&quot;
$pt_logback_erb = &#39;cd_puppet/puppetdb/logback.xml.erb&#39;
$pt_logback_erb = &#39;puppet_cd/puppetdb/logback.xml.erb&#39;
$pt_puppetdb_config_ini = &quot;${pt_puppetdb_conf_d}/config.ini&quot;
$pt_puppetdb_config_erb = &#39;cd_puppet/puppetdb/config.ini.erb&#39;
$pt_puppetdb_config_erb = &#39;puppet_cd/puppetdb/config.ini.erb&#39;
$pt_puppetdb_database_ini = &quot;${pt_puppetdb_conf_d}/database.ini&quot;
$pt_puppetdb_database_erb = &#39;cd_puppet/puppetdb/database.ini.erb&#39;
$pt_puppetdb_database_erb = &#39;puppet_cd/puppetdb/database.ini.erb&#39;
$pt_puppetdb_jetty_ini = &quot;${pt_puppetdb_conf_d}/jetty.ini&quot;
$pt_puppetdb_jetty_erb = &#39;cd_puppet/puppetdb/jetty.ini.erb&#39;
$pt_puppetdb_jetty_erb = &#39;puppet_cd/puppetdb/jetty.ini.erb&#39;
$pt_puppetdb_conf_file = &quot;${pt_puppetdir}/puppetdb.conf&quot;
$pt_puppetdb_conf_erb = &#39;cd_puppet/puppetdb/puppetdb.conf.erb&#39;
$pt_puppetdb_conf_erb = &#39;puppet_cd/puppetdb/puppetdb.conf.erb&#39;
$pt_puppetdb_repl_ini = &quot;${pt_puppetdb_conf_d}/repl.ini&quot;
$pt_puppetdb_repl_erb = &#39;cd_puppet/puppetdb/repl.ini.erb&#39;
$pt_puppetdb_repl_erb = &#39;puppet_cd/puppetdb/repl.ini.erb&#39;
## r10k
$pt_r10k_file = &quot;${pt_r10k_dir}/r10k.yaml&quot;
$pt_r10k_erb = &#39;puppet_cd/r10k/r10k.yaml.erb&#39;
# service
$pt_server_service = &#39;puppetserver&#39;

View File

@@ -0,0 +1,180 @@
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>
Puppet Class: puppet_cd::r10k::install
&mdash; Documentation by YARD 0.9.36
</title>
<link rel="stylesheet" href="../css/style.css" type="text/css" />
<link rel="stylesheet" href="../css/common.css" type="text/css" />
<script type="text/javascript">
pathId = "puppet_classes::puppet_cd::r10k::install";
relpath = '../';
</script>
<script type="text/javascript" charset="utf-8" src="../js/jquery.js"></script>
<script type="text/javascript" charset="utf-8" src="../js/app.js"></script>
</head>
<body>
<div class="nav_wrap">
<iframe id="nav" src="../puppet_class_list.html?1"></iframe>
<div id="resizer"></div>
</div>
<div id="main" tabindex="-1">
<div id="header">
<div id="menu">
<a href="../_index.html">Index (p)</a> &raquo;
<span class='title'><span class='object_link'>Puppet Classes</span></span>
&raquo;
<span class="title">puppet_cd::r10k::install</span>
</div>
<div id="search">
<a class="full_list_link" id="puppet_class_list_link"
href="../puppet_class_list.html">
<svg width="24" height="24">
<rect x="0" y="4" width="24" height="4" rx="1" ry="1"></rect>
<rect x="0" y="12" width="24" height="4" rx="1" ry="1"></rect>
<rect x="0" y="20" width="24" height="4" rx="1" ry="1"></rect>
</svg>
</a>
</div>
<div class="clear"></div>
</div>
<div id="content"><h1>Puppet Class: puppet_cd::r10k::install</h1>
<div class="box_info">
<dl>
<dt>Inherits:</dt>
<dd><span class='object_link'><a href="puppet_cd_3A_3Aparams.html" title="puppet_classes::puppet_cd::params (puppet_class)">puppet_cd::params</a></span></dd>
</dl>
<dl>
<dt>Defined in:</dt>
<dd>
manifests/r10k/install.pp
</dd>
</dl>
</div>
<h2>Summary</h2>
Class manages r10k installation for the puppet_cd module.
<h2>Overview</h2>
<div class="docstring">
<div class="discussion">
<p>puppet_cd::r10k::install.pp Module name: puppet_cd Author: Arne Teuke (arne_teuke@confdroid)</p>
</div>
</div>
<div class="tags">
</div><div class="method_details_list">
<table class="source_code">
<tr>
<td>
<pre class="lines">
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35</pre>
</td>
<td>
<pre class="code"><span class="info file"># File 'manifests/r10k/install.pp', line 6</span>
class puppet_cd::r10k::install (
) inherits puppet_cd::params {
if ($pt_pm_fqdn == $fqdn) and ($pt_use_r10k == true) {
# install required packages
package { $pt_r10k_pkg:
ensure =&gt; $pt_pkg_ensure,
before =&gt; Package[&#39;r10k&#39;],
}
# install r10k via gem
package { &#39;r10k&#39;:
ensure =&gt; $pt_pkg_ensure,
provider =&gt; gem,
}
# configure r10k.yaml
file { $pt_r10k_file:
ensure =&gt; file,
owner =&gt; &#39;root&#39;,
group =&gt; &#39;root&#39;,
mode =&gt; &#39;0440&#39;,
selrange =&gt; s0,
selrole =&gt; object_r,
seltype =&gt; puppet_etc_t,
seluser =&gt; unconfined_u,
content =&gt; template($pt_r10k_erb),
}
}
}</pre>
</td>
</tr>
</table>
</div>
</div>
<div id="footer">
Generated by <a href="http://yardoc.org" title="Yay! A Ruby Documentation Tool" target="_parent">yard</a>.
</div>
</div>
</body>
</html>

View File

@@ -0,0 +1,130 @@
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>
Puppet Class: puppet_cd::r10k::webhook
&mdash; Documentation by YARD 0.9.36
</title>
<link rel="stylesheet" href="../css/style.css" type="text/css" />
<link rel="stylesheet" href="../css/common.css" type="text/css" />
<script type="text/javascript">
pathId = "puppet_classes::puppet_cd::r10k::webhook";
relpath = '../';
</script>
<script type="text/javascript" charset="utf-8" src="../js/jquery.js"></script>
<script type="text/javascript" charset="utf-8" src="../js/app.js"></script>
</head>
<body>
<div class="nav_wrap">
<iframe id="nav" src="../puppet_class_list.html?1"></iframe>
<div id="resizer"></div>
</div>
<div id="main" tabindex="-1">
<div id="header">
<div id="menu">
<a href="../_index.html">Index (p)</a> &raquo;
<span class='title'><span class='object_link'>Puppet Classes</span></span>
&raquo;
<span class="title">puppet_cd::r10k::webhook</span>
</div>
<div id="search">
<a class="full_list_link" id="puppet_class_list_link"
href="../puppet_class_list.html">
<svg width="24" height="24">
<rect x="0" y="4" width="24" height="4" rx="1" ry="1"></rect>
<rect x="0" y="12" width="24" height="4" rx="1" ry="1"></rect>
<rect x="0" y="20" width="24" height="4" rx="1" ry="1"></rect>
</svg>
</a>
</div>
<div class="clear"></div>
</div>
<div id="content"><h1>Puppet Class: puppet_cd::r10k::webhook</h1>
<div class="box_info">
<dl>
<dt>Inherits:</dt>
<dd><span class='object_link'><a href="puppet_cd_3A_3Aparams.html" title="puppet_classes::puppet_cd::params (puppet_class)">puppet_cd::params</a></span></dd>
</dl>
<dl>
<dt>Defined in:</dt>
<dd>
manifests/r10k/webhook.pp
</dd>
</dl>
</div>
<h2>Summary</h2>
Class manages r10k webhook settings for the puppet_cd module.
<h2>Overview</h2>
<div class="docstring">
<div class="discussion">
<p>puppet_cd::r10k::webhook.pp Module name: puppet_cd Author: Arne Teuke (arne_teuke@confdroid)</p>
</div>
</div>
<div class="tags">
</div><div class="method_details_list">
<table class="source_code">
<tr>
<td>
<pre class="lines">
6
7
8
9
10</pre>
</td>
<td>
<pre class="code"><span class="info file"># File 'manifests/r10k/webhook.pp', line 6</span>
class puppet_cd::r10k::webhook (
) inherits puppet_cd::params {
}</pre>
</td>
</tr>
</table>
</div>
</div>
<div id="footer">
Generated by <a href="http://yardoc.org" title="Yay! A Ruby Documentation Tool" target="_parent">yard</a>.
</div>
</div>
</body>
</html>

View File

@@ -11,4 +11,9 @@ class puppet_cd::main::config (
if $pt_use_puppetdb == true {
include puppet_cd::puppetdb::service
}
if $pt_use_r10k == true {
include puppet_cd::r10k::install
include puppet_cd::r10k::webhook
}
}

View File

@@ -10,10 +10,10 @@
# @param [String] pt_agent_pkg the packages for agents to install
# @param [String] pt_server_pkg the server packages to install
# @param [Array] pt_db_pkg the packages for puppetdb
# @param [Array] pt_r10k_pkg the packages for r10k to install
# @param [String] pt_no_ssl_port non-ssl port number for puppetdb
# @param [String] pt_ssl_port ssl port for puppetdb
# @param [Boolean] pt_use_ssl_only whether to use ssl only.
# @param [Boolean] pt_manage_user whether to manage the puppet user
# @param [String] pt_user the puppet user
# @param [String] pt_user_comment the user comment
# @param [String] pt_user_home the user home
@@ -77,6 +77,11 @@
# @param [Boolean] pt_enable_repl whether to allow puppetdb replication
# @param [String] pt_repl_port the replication port
# @param [String] pt_repl_host the replication host
# @param [Boolean] pt_use_r10k whether to use r10k service
# @param [Boolean] pt_use_r10k_webhook whether to use r10k webhook service
# @param [String] pt_r10k_remote the remote url for the r10k control repo
# @param [Boolean] pt_r10k_prefix the r10k prefix. defaults to false
# @param [String] pt_r10k_basedir the base directory for r10k.yaml
###############################################################################
class puppet_cd::params (
@@ -89,6 +94,7 @@ class puppet_cd::params (
String $pt_agent_pkg = 'puppet-agent',
String $pt_server_pkg = 'puppetserver',
Array $pt_db_pkg = ['puppetdb','puppetdb-termini'],
Array $pt_r10k_pkg = ['ruby','ruby-devel'],
# user settings
## puppet user
@@ -132,7 +138,7 @@ class puppet_cd::params (
String $pt_storeconfigs_backend = 'puppetdb',
String $pt_parser = 'current',
Boolean $pt_cert_revocation = true,
## puppetdb
## puppetdb
Boolean $pt_use_puppetdb = false,
String $pt_logging_max_file_size = '200MB',
String $pt_logging_max_history = '90',
@@ -160,8 +166,19 @@ class puppet_cd::params (
String $pt_repl_port = '8082',
String $pt_repl_host = '127.0.0.1',
# r10k
Boolean $pt_use_r10k = false,
Boolean $pt_use_r10k_webhook = false,
String $pt_r10k_remote = 'git@gitlab.example.net/repo.git',
Boolean $pt_r10k_prefix = false,
String $pt_r10k_basedir = '/etc/puppetlabs/code/environments',
) {
$fqdn = $facts['networking']['fqdn']
# facts
$fqdn = $facts['networking']['fqdn']
$domain = $facts['networking']['domain']
$os_name = $facts['os']['name']
$os_release = $facts['os']['release']['major']
# directories
## puppet
@@ -181,6 +198,8 @@ class puppet_cd::params (
$pt_puppetdb_ssl = "${pt_puppetdb_main}/ssl"
$pt_puppetdb_log = '/var/log/puppetlabs/puppetdb'
$pt_puppetdb_var_dir = '/opt/puppetlabs/server/data/puppetdb'
## r10k
$pt_r10k_dir = "${pt_main_dir}/r10k"
# files
## puppet
@@ -190,22 +209,25 @@ class puppet_cd::params (
$pt_hiera_config = "${pt_puppetdir}/hiera.yaml"
## puppetdb
$pt_bootstrap_conf = "${pt_puppetdb_main}/bootstrap.cfg"
$pt_bootstrap_erb = 'cd_puppet/puppetdb/bootstrap.cfg.erb'
$pt_bootstrap_erb = 'puppet_cd/puppetdb/bootstrap.cfg.erb'
$pt_puppetdb_access_log = "${pt_puppetdb_log}/puppetdb-access"
$pt_request_logging_conf = "${pt_puppetdb_main}/request-logging.xml"
$pt_request_logging_erb = 'cd_puppet/puppetdb/request_logging.xml.erb'
$pt_request_logging_erb = 'puppet_cd/puppetdb/request_logging.xml.erb'
$pt_logback_conf = "${pt_puppetdb_main}/logback.xml"
$pt_logback_erb = 'cd_puppet/puppetdb/logback.xml.erb'
$pt_logback_erb = 'puppet_cd/puppetdb/logback.xml.erb'
$pt_puppetdb_config_ini = "${pt_puppetdb_conf_d}/config.ini"
$pt_puppetdb_config_erb = 'cd_puppet/puppetdb/config.ini.erb'
$pt_puppetdb_config_erb = 'puppet_cd/puppetdb/config.ini.erb'
$pt_puppetdb_database_ini = "${pt_puppetdb_conf_d}/database.ini"
$pt_puppetdb_database_erb = 'cd_puppet/puppetdb/database.ini.erb'
$pt_puppetdb_database_erb = 'puppet_cd/puppetdb/database.ini.erb'
$pt_puppetdb_jetty_ini = "${pt_puppetdb_conf_d}/jetty.ini"
$pt_puppetdb_jetty_erb = 'cd_puppet/puppetdb/jetty.ini.erb'
$pt_puppetdb_jetty_erb = 'puppet_cd/puppetdb/jetty.ini.erb'
$pt_puppetdb_conf_file = "${pt_puppetdir}/puppetdb.conf"
$pt_puppetdb_conf_erb = 'cd_puppet/puppetdb/puppetdb.conf.erb'
$pt_puppetdb_conf_erb = 'puppet_cd/puppetdb/puppetdb.conf.erb'
$pt_puppetdb_repl_ini = "${pt_puppetdb_conf_d}/repl.ini"
$pt_puppetdb_repl_erb = 'cd_puppet/puppetdb/repl.ini.erb'
$pt_puppetdb_repl_erb = 'puppet_cd/puppetdb/repl.ini.erb'
## r10k
$pt_r10k_file = "${pt_r10k_dir}/r10k.yaml"
$pt_r10k_erb = 'puppet_cd/r10k/r10k.yaml.erb'
# service
$pt_server_service = 'puppetserver'

35
manifests/r10k/install.pp Normal file
View File

@@ -0,0 +1,35 @@
## puppet_cd::r10k::install.pp
# Module name: puppet_cd
# Author: Arne Teuke (arne_teuke@confdroid)
# @summary Class manages r10k installation for the puppet_cd module.
###############################################################################
class puppet_cd::r10k::install (
) inherits puppet_cd::params {
if ($pt_pm_fqdn == $fqdn) and ($pt_use_r10k == true) {
# install required packages
package { $pt_r10k_pkg:
ensure => $pt_pkg_ensure,
before => Package['r10k'],
}
# install r10k via gem
package { 'r10k':
ensure => $pt_pkg_ensure,
provider => gem,
}
# configure r10k.yaml
file { $pt_r10k_file:
ensure => file,
owner => 'root',
group => 'root',
mode => '0440',
selrange => s0,
selrole => object_r,
seltype => puppet_etc_t,
seluser => unconfined_u,
content => template($pt_r10k_erb),
}
}
}

10
manifests/r10k/webhook.pp Normal file
View File

@@ -0,0 +1,10 @@
## puppet_cd::r10k::webhook.pp
# Module name: puppet_cd
# Author: Arne Teuke (arne_teuke@confdroid)
# @summary Class manages r10k webhook settings for the puppet_cd module.
###############################################################################
class puppet_cd::r10k::webhook (
) inherits puppet_cd::params {
}

0
templates/puppetdb/logback.xml.erb Executable file → Normal file
View File

View File

@@ -0,0 +1,7 @@
:cachedir: /var/cache/r10k
:sources:
:puppet:
remote: <%= @pt_r10k_remote %>
prefix: <&= @pt_r10k_prefix %>
basedir: '<%= @pt_r10k_basedir %>'

View File

@@ -0,0 +1,5 @@
pytest==7.4.3
pytest-cov==4.1.0
httpx==0.25.2
flake8==6.1.0
pylint==3.0.1

View File

@@ -0,0 +1,198 @@
#!/usr/bin/env python3
"""
Custom r10k Webhook Server for Puppet Control Repo
"""
from datetime import datetime
import os
import subprocess
import logging
import hmac
import hashlib
from fastapi import FastAPI, Request, HTTPException, BackgroundTasks
from fastapi.responses import JSONResponse
import uvicorn
from pydantic import BaseModel
# Configure logging
logging.basicConfig(
level=logging.INFO,
format='%(asctime)s - %(levelname)s - %(message)s',
handlers=[
logging.FileHandler('/var/log/r10k-webhook.log'),
logging.StreamHandler()
]
)
logger = logging.getLogger(__name__)
app = FastAPI(title="r10k Webhook Server")
class WebhookPayload(BaseModel):
"""Data model for webhook payload"""
ref: str
project: dict
commits: list
def run_r10k_deploy() -> bool:
"""Run r10k deploy command"""
try:
cmd = [
'/usr/bin/r10k', 'deploy',
'-v',
'-c', '/etc/puppetlabs/r10k/r10k.conf'
]
logger.info("Starting r10k deploy...")
result = subprocess.run(
cmd,
capture_output=True,
text=True,
check=True
)
logger.info("r10k deploy successful!")
logger.debug("r10k stdout: %s", result.stdout)
if result.stderr:
logger.warning("r10k stderr: %s", result.stderr)
return True
except subprocess.CalledProcessError as e:
logger.error("r10k deploy failed: %s", e)
logger.error("stdout: %s", e.stdout)
logger.error("stderr: %s", e.stderr)
return False
except FileNotFoundError:
logger.error("r10k binary not found")
return False
except PermissionError:
logger.error("Permission denied running r10k")
return False
def validate_signature(payload: bytes, signature: str, secret: str) -> bool:
"""Validate webhook signature"""
if not secret:
return True
expected = hmac.new(
secret.encode(),
payload,
hashlib.sha256
).hexdigest()
if signature.startswith('sha256='):
return hmac.compare_digest(signature, f'sha256={expected}')
return hmac.compare_digest(signature, expected)
@app.post("/webhook")
async def webhook_handler(
request: Request,
background_tasks: BackgroundTasks
):
"""Handle incoming webhook requests"""
body = await request.body()
headers = dict(request.headers)
event_type = headers.get(
'x-gitlab-event',
headers.get('x-github-event', 'unknown')
)
signature = headers.get(
'x-gitlab-token',
headers.get('x-hub-signature-256', '')
)
print(
f"DEBUG: Received webhook: event_type={event_type}, "
f"headers={headers}"
)
logger.info(
"Received webhook: event_type=%s, headers=%s",
event_type,
headers
)
webhook_secret = os.getenv('R10K_WEBHOOK_SECRET', '')
is_valid = validate_signature(body, signature, webhook_secret)
if webhook_secret and not is_valid:
logger.warning("Invalid webhook signature")
raise HTTPException(status_code=403, detail="Invalid signature")
try:
payload = await request.json()
ref = payload.get('ref', '')
branch = ref.split('/')[-1] if '/' in ref else ref
print(
f"DEBUG: Parsed payload: ref={ref}, "
f"branch={branch}"
)
logger.info("Parsed payload: ref=%s, branch=%s", ref, branch)
if branch not in ['main', 'master']:
logger.info("Ignoring non-main branch: %s", branch)
return JSONResponse({
"status": "ignored",
"branch": branch
})
# Match GitLab event types explicitly
valid_events = [
'push hook', 'merge request hook',
'push', 'Push', 'Push Hook'
]
normalized_event = event_type.lower().strip()
print(f"DEBUG: Normalized event: {normalized_event}")
logger.info("Normalized event: %s", normalized_event)
if normalized_event in valid_events:
logger.info("Triggering r10k for %s on %s", event_type, branch)
background_tasks.add_task(run_r10k_deploy)
return JSONResponse({
"status": "accepted",
"message": "r10k deploy triggered",
"timestamp": datetime.utcnow().isoformat(),
"branch": branch
})
logger.info("Ignoring event type: %s", event_type)
return JSONResponse({
"status": "ignored",
"event": event_type
})
except ValueError as e:
logger.error("Webhook processing error: %s", e)
raise HTTPException(
status_code=400,
detail="Invalid payload"
) from e
@app.get("/health")
async def health_check():
"""Health check endpoint"""
result = subprocess.run(
['r10k', '--version'],
capture_output=True,
text=True,
check=True
)
return {
"status": "healthy",
"r10k_version": result.stdout.strip()
}
if __name__ == "__main__":
uvicorn.run(
"webhook_server:app",
host="0.0.0.0",
port=8080,
log_level="info"
)