Related-Prod: PROD-22546 Related-Prod: PROD-22664 Change-Id: I66a35ef3d2436541ef70f02e2631fa8d4d86e5e9pull/124/merge
automatic_reboot: true | automatic_reboot: true | ||||
automatic_reboot_time: "02:00" | automatic_reboot_time: "02:00" | ||||
Linux with cron jobs | |||||
Managing cron tasks | |||||
------------------- | |||||
There are two data structures that are related to managing cron itself and | |||||
cron tasks: | |||||
.. code-block:: yaml | |||||
linux: | |||||
system: | |||||
cron: | |||||
and | |||||
.. code-block:: yaml | |||||
linux: | |||||
system: | |||||
job: | |||||
`linux:system:cron` manages cron packages, services, and '/etc/cron.allow' file. | |||||
'deny' files are managed the only way - we're ensuring they are absent, that's | |||||
a requirement from CIS 5.1.8 | |||||
'cron' pillar structure is the following: | |||||
.. code-block:: yaml | |||||
linux: | |||||
system: | |||||
cron: | |||||
enabled: true | |||||
pkgs: [ <cron packages> ] | |||||
services: [ <cron services> ] | |||||
user: | |||||
<username>: | |||||
enabled: true | |||||
To add user to '/etc/cron.allow' use 'enabled' key as shown above. | |||||
'/etc/cron.deny' is not managed as CIS 5.1.8 requires it was removed. | |||||
A user would be ignored if any of the following is true: | |||||
* user is disabled in `linux:system:user:<username>` | |||||
* user is disabled in `linux:system:cron:user:<username>` | |||||
`linux:system:job` manages individual cron tasks. | |||||
By default, it will use name as an identifier, unless identifier key is | By default, it will use name as an identifier, unless identifier key is | ||||
explicitly set or False (then it will use Salt's default behavior which is | explicitly set or False (then it will use Salt's default behavior which is | ||||
hour: 2 | hour: 2 | ||||
minute: 0 | minute: 0 | ||||
Managing 'at' tasks | |||||
------------------- | |||||
Pillar for managing `at` tasks is similar to one for `cron` tasks: | |||||
.. code-block:: yaml | |||||
linux: | |||||
system: | |||||
at: | |||||
enabled: true | |||||
pkgs: [ <at packages> ] | |||||
services: [ <at services> ] | |||||
user: | |||||
<username>: | |||||
enabled: true | |||||
To add a user to '/etc/at.allow' use 'enabled' key as shown above. | |||||
'/etc/at.deny' is not managed as CIS 5.1.8 requires it was removed. | |||||
A user will be ignored if any of the following is true: | |||||
* user is disabled in `linux:system:user:<username>` | |||||
* user is disabled in `linux:system:at:user:<username>` | |||||
Linux security limits (limit sensu user memory usage to max 1GB): | Linux security limits (limit sensu user memory usage to max 1GB): | ||||
.. code-block:: yaml | .. code-block:: yaml |
# This file is managed by Salt, do not edit | |||||
{%- for user_name in users %} | |||||
{{ user_name }} | |||||
{%- endfor %} | |||||
{# IMPORTANT: This file SHOULD ends with a newline #} |
}, | }, | ||||
}, grain='os_family', merge=salt['pillar.get']('linux:system')) %} | }, grain='os_family', merge=salt['pillar.get']('linux:system')) %} | ||||
{% set at = salt['grains.filter_by']({ | |||||
'Debian': { | |||||
'enabled': false, | |||||
'pkgs': ['at'], | |||||
'services': ['atd'], | |||||
'user': {} | |||||
}, | |||||
}, grain='os_family', merge=salt['pillar.get']('linux:system:at')) %} | |||||
{% set cron = salt['grains.filter_by']({ | |||||
'Debian': { | |||||
'enabled': false, | |||||
'pkgs': ['cron'], | |||||
'services': ['cron'], | |||||
'user': {} | |||||
}, | |||||
}, grain='os_family', merge=salt['pillar.get']('linux:system:cron')) %} | |||||
{% set banner = salt['grains.filter_by']({ | {% set banner = salt['grains.filter_by']({ | ||||
'BaseDefaults': { | 'BaseDefaults': { | ||||
'enabled': false, | 'enabled': false, |
{%- from "linux/map.jinja" import system, at with context %} | |||||
{%- if at.get('enabled', false) %} | |||||
at_packages: | |||||
pkg.installed: | |||||
- names: {{ at.pkgs }} | |||||
at_services: | |||||
service.running: | |||||
- enable: true | |||||
- names: {{ at.services }} | |||||
- require: | |||||
- pkg: at_packages | |||||
{%- if grains.get('noservices') %} | |||||
- onlyif: /bin/false | |||||
{%- endif %} | |||||
{%- set allow_users = [] %} | |||||
{%- for user_name, user_params in at.get('user', {}).items() %} | |||||
{%- set user_enabled = user_params.get('enabled', false) and | |||||
system.get('user', {}).get( | |||||
user_name, {'enabled': true}).get('enabled', true) %} | |||||
{%- if user_enabled %} | |||||
{%- do allow_users.append(user_name) %} | |||||
{%- endif %} | |||||
{%- endfor %} | |||||
etc_at_allow: | |||||
{%- if allow_users %} | |||||
file.managed: | |||||
- name: /etc/at.allow | |||||
- template: jinja | |||||
- source: salt://linux/files/cron_users.jinja | |||||
- user: root | |||||
- group: root | |||||
- mode: 0600 | |||||
- defaults: | |||||
users: {{ allow_users | yaml }} | |||||
- require: | |||||
- cron_packages | |||||
{%- else %} | |||||
file.absent: | |||||
- name: /etc/at.allow | |||||
{%- endif %} | |||||
{# | |||||
/etc/at.deny should be absent to comply with | |||||
CIS 5.1.8 Ensure at/cron is restricted to authorized users | |||||
#} | |||||
etc_at_deny: | |||||
file.absent: | |||||
- name: /etc/at.deny | |||||
{%- else %} | |||||
fake_linux_system_at: | |||||
test.nop: | |||||
- comment: Fake state to satisfy 'require sls:linux.system.at' | |||||
{%- endif %} |
{%- from "linux/map.jinja" import system, cron with context %} | |||||
{%- if cron.get('enabled', false) %} | |||||
cron_packages: | |||||
pkg.installed: | |||||
- names: {{ cron.pkgs }} | |||||
cron_services: | |||||
service.running: | |||||
- enable: true | |||||
- names: {{ cron.services }} | |||||
- require: | |||||
- pkg: cron_packages | |||||
{%- if grains.get('noservices') %} | |||||
- onlyif: /bin/false | |||||
{%- endif %} | |||||
{%- set allow_users = [] %} | |||||
{%- for user_name, user_params in cron.get('user', {}).items() %} | |||||
{%- set user_enabled = user_params.get('enabled', false) and | |||||
system.get('user', {}).get( | |||||
user_name, {'enabled': true}).get('enabled', true) %} | |||||
{%- if user_enabled %} | |||||
{%- do allow_users.append(user_name) %} | |||||
{%- endif %} | |||||
{%- endfor %} | |||||
etc_cron_allow: | |||||
{%- if allow_users %} | |||||
file.managed: | |||||
- name: /etc/cron.allow | |||||
- template: jinja | |||||
- source: salt://linux/files/cron_users.jinja | |||||
- user: root | |||||
- group: root | |||||
- mode: 0600 | |||||
- defaults: | |||||
users: {{ allow_users | yaml }} | |||||
- require: | |||||
- cron_packages | |||||
{%- else %} | |||||
file.absent: | |||||
- name: /etc/cron.allow | |||||
{%- endif %} | |||||
{# | |||||
/etc/cron.deny should be absent to comply with | |||||
CIS 5.1.8 Ensure at/cron is restricted to authorized users | |||||
#} | |||||
etc_cron_deny: | |||||
file.absent: | |||||
- name: /etc/cron.deny | |||||
etc_crontab: | |||||
file.managed: | |||||
- name: /etc/crontab | |||||
- user: root | |||||
- group: root | |||||
- mode: 0600 | |||||
- replace: False | |||||
- require: | |||||
- cron_packages | |||||
etc_cron_dirs: | |||||
file.directory: | |||||
- names: | |||||
- /etc/cron.d | |||||
- /etc/cron.daily | |||||
- /etc/cron.hourly | |||||
- /etc/cron.monthly | |||||
- /etc/cron.weekly | |||||
- user: root | |||||
- group: root | |||||
- dir_mode: 0600 | |||||
- recurse: | |||||
- ignore_files | |||||
- require: | |||||
- cron_packages | |||||
{%- else %} | |||||
fake_linux_system_cron: | |||||
test.nop: | |||||
- comment: Fake state to satisfy 'require sls:linux.system.cron' | |||||
{%- endif %} |
include: | include: | ||||
- linux.system.env | - linux.system.env | ||||
- linux.system.profile | - linux.system.profile | ||||
- linux.system.at | |||||
- linux.system.cron | |||||
{%- if system.repo|length > 0 %} | {%- if system.repo|length > 0 %} | ||||
- linux.system.repo | - linux.system.repo | ||||
{%- endif %} | {%- endif %} |
include: | include: | ||||
- linux.system.user | - linux.system.user | ||||
- linux.system.cron | |||||
{%- for name, job in system.job.items() %} | |||||
{%- for name, job in system.job.items() %} | |||||
{%- set job_user = job.get('user', 'root') %} | |||||
linux_job_{{ job.command }}: | linux_job_{{ job.command }}: | ||||
{%- if job.enabled|default(True) %} | |||||
{%- if job.get('enabled', True) %} | |||||
cron.present: | cron.present: | ||||
- name: > | - name: > | ||||
{{ job.command }} | {{ job.command }} | ||||
{%- if job.get('identifier', True) %} | |||||
{%- if job.get('identifier', True) %} | |||||
- identifier: {{ job.get('identifier', job.get('name', name)) }} | - identifier: {{ job.get('identifier', job.get('name', name)) }} | ||||
{%- endif %} | |||||
- user: {{ job.user|default("root") }} | |||||
{%- if job.minute is defined %} | |||||
{%- endif %} | |||||
- user: {{ job_user }} | |||||
{%- if job.minute is defined %} | |||||
- minute: '{{ job.minute }}' | - minute: '{{ job.minute }}' | ||||
{%- endif %} | |||||
{%- if job.hour is defined %} | |||||
{%- endif %} | |||||
{%- if job.hour is defined %} | |||||
- hour: '{{ job.hour }}' | - hour: '{{ job.hour }}' | ||||
{%- endif %} | |||||
{%- if job.daymonth is defined %} | |||||
{%- endif %} | |||||
{%- if job.daymonth is defined %} | |||||
- daymonth: '{{ job.daymonth }}' | - daymonth: '{{ job.daymonth }}' | ||||
{%- endif %} | |||||
{%- if job.month is defined %} | |||||
{%- endif %} | |||||
{%- if job.month is defined %} | |||||
- month: '{{ job.month }}' | - month: '{{ job.month }}' | ||||
{%- endif %} | |||||
{%- if job.dayweek is defined %} | |||||
{%- endif %} | |||||
{%- if job.dayweek is defined %} | |||||
- dayweek: '{{ job.dayweek }}' | - dayweek: '{{ job.dayweek }}' | ||||
{%- endif %} | |||||
{%- if job.user|default("root") in system.get('user', {}).keys() %} | |||||
{%- endif %} | |||||
- require: | - require: | ||||
- user: system_user_{{ job.user|default("root") }} | |||||
{%- endif %} | |||||
{%- else %} | |||||
- sls: linux.system.cron | |||||
{%- if job_user in system.get('user', {}).keys() %} | |||||
- user: system_user_{{ job_user }} | |||||
{%- endif %} | |||||
{%- else %} | |||||
cron.absent: | cron.absent: | ||||
- name: {{ job.command }} | - name: {{ job.command }} | ||||
{%- if job.get('identifier', True) %} | |||||
{%- if job.get('identifier', True) %} | |||||
- identifier: {{ job.get('identifier', job.get('name', name)) }} | - identifier: {{ job.get('identifier', job.get('name', name)) }} | ||||
{%- endif %} | |||||
{%- endif %} | {%- endif %} | ||||
{%- endif %} | |||||
{%- endfor %} | |||||
{%- endfor %} | |||||
{%- endif %} | {%- endif %} |
fqdn: linux.ci.local | fqdn: linux.ci.local | ||||
system: | system: | ||||
enabled: true | enabled: true | ||||
at: | |||||
enabled: true | |||||
user: | |||||
root: | |||||
enabled: true | |||||
testuser: | |||||
enabled: true | |||||
cron: | |||||
enabled: true | |||||
user: | |||||
root: | |||||
enabled: true | |||||
testuser: | |||||
enabled: true | |||||
cluster: default | cluster: default | ||||
name: linux | name: linux | ||||
domain: ci.local | domain: ci.local |