Palestra Puppet Hora Livre

Preview:

DESCRIPTION

Palestra ministrada em Campo Grande/MS no dia 12/12/12 na UNAES.

Citation preview

Gestão e Automação de Servidores com Puppet

Guto Carvalho < gutocarvalho@gmail.com >

Campo Grande/MS - 2012/12/12 - Hora Livre

Wednesday, December 12, 12

Hora Livre - Ano 4

Wednesday, December 12, 12

Wednesday, December 12, 12

Consultor/SysAdmin (LPIC-3) na 4Linux

12 anos de experiência com tecnologias FOSS

Blogueiro FOSS há 6 anos no site gutocarvalho.net

Atuação em vários projetos de Governo no MDA, MINC, EBC/RADIOBRÁS, MPS/DATAPREV, ITI/PR, CEF, MD/SIPAM, DETRAN/DF, CAIXA

Há 2 anos trabalhando com gerência de configurações em ambientes virtualizados e clouds privadas em Brasília

Palestrante em eventos como FISL, LATINOWARE, CONSEGI, ENECOMP, FLISOL e CLOUDCONF

whoami

Wednesday, December 12, 12

Plano de Trabalho

05 minutos de apresentação

50 minutos de palestra

10 minutos para perguntas

Wednesday, December 12, 12

Agenda

Administração de servidores e serviços

Causas, efeitos e consequências da administração artesanal

Um novo caminho com a gerência de configurações

Puppet como solução de gerência de configurações

Apresentando características e recursos do Puppet

Benefícios, resultados concretos e Puppet no Brasil

Wednesday, December 12, 12

Já ouviu falar do sysadmin?

Wednesday, December 12, 12

O que faz um sysadmin?Administra servidores e serviços e a infraestrutura de rede

Oferece suporte aos desenvolvedores e usuários

Sustenta ambiente de desenvolvimento, testes, homol e produção e faz deploy de aplicações

Sustenta sistemas estruturantes (DHCP, DNS, PROXY, LDAP, MAIL, IM)

Cuida dos ambientes de banco de dados

Sustenta, monitora e trabalha para que aplicações e ambientes funcionem

Cuida do Backup, lava, passa e faz cafézinho...

Wednesday, December 12, 12

Multi-tarefas

Wednesday, December 12, 12

Multi-disciplinar

Wednesday, December 12, 12

SysAdminsWednesday, December 12, 12

Visão do SysadminEm relação a infraestrutura que ele tem que administra

Wednesday, December 12, 12

Visão do SysadminEm relação ao seu dia-a-dia de trabalho e tratamento de demandas

Wednesday, December 12, 12

Realidade do Sysadmin

Wednesday, December 12, 12

Ferramentas e métodos não tão modernos e nem tão atraentes

Wednesday, December 12, 12

Desafios do Sysadmin em 2012

Wednesday, December 12, 12

Administração de Servidores e Serviços

Wednesday, December 12, 12

Virtualização - Tendência

Wednesday, December 12, 12

Virt. e seus BenefíciosMenor consumo de energia

Melhor aproveitamento de espaço físico

Melhor aproveitamento de hardware (sem hw ocioso)

Maior segurança com isolamento de ambientes

Pode-se trabalhar disponibilidade e balanceamento

Facilidade de provisionamento e gerenciamento

Wednesday, December 12, 12

Cloud Computing - Tendência

Wednesday, December 12, 12

Cloud e seus BenefíciosHiper escalável

Rápida e elástica

Abstração de hardware

Infraestrutura dinâmica

Alta disponibilidade

Investimento atraente para projetos emergentes

Wednesday, December 12, 12

O crescimento do seu parque é inevitávelPoucas máquinas físicas podem ser tornar dezenas, centenas ou milhares de nodes em poucos meses.

Wednesday, December 12, 12

Como Administrar 500 VM’s?

Wednesday, December 12, 12

Ambiente híbrido e complexo

Servidores Linux Debian 5.0 e 6.0 em 32 e 64 bits

Servidores Linux Centos 5 e Centos 6 em 32 e 64 bits

Servidores RHEL 4, 5 e 6 em 64 bits

FreeBSD, OpenBSD e OSX

Servidores Windows 2003 e 2008

Wednesday, December 12, 12

Configuração artesanal?

Wednesday, December 12, 12

Vale a pena insistir?Wednesday, December 12, 12

Administação Host a Host?

Wednesday, December 12, 12

Acesso Secure Shell (ssh) em loop?

Wednesday, December 12, 12

Shellscript?

Wednesday, December 12, 12

Será que o modelo artesanal escala?

Wednesday, December 12, 12

Quantos SysAdmins são necessários para administrar 500 servidores?

Wednesday, December 12, 12

Qual a velocidade nas mudanças em seu ambiente?

Wednesday, December 12, 12

Qual a probabilidade de falhas decorrentes de mudanças manuais?

Wednesday, December 12, 12

Você consegue manter todo o seu ambiente padronizado?

Wednesday, December 12, 12

Trabalhar fora de expediente para dar conta das demandas se tornou regra ao

invés de exceção?

Wednesday, December 12, 12

Seu custo com equipes técnicas está aumentando devido aos trabalho

fora de expediente?

Wednesday, December 12, 12

Você começa a ter a sensação de estar sendo engolido por seu ambiente?

Wednesday, December 12, 12

Está difícil colocar suas configurações nos trilhos?

Wednesday, December 12, 12

Administração artesanal não escala, não importaquantas pessoas estejamenvolvidas

No entanto, é possível enxergaras causas, efeitos e consequênciasgeradas por um modelo equivocado de administração

Wednesday, December 12, 12

Você vai começar a perceber que

Fica mais difícil encontrar problemas em seu parque

Não é mais tão simples manter as coisas funcionando

É quase impossível manter o parque padronizado

Sua produtividade diminui a medida que o ambiente cresce

Você não consegue mais documentar e planejar mudanças

Wednesday, December 12, 12

Você vai começar a perceber que

Você não consegue mais entregar demandas no tempo acordado

Sua equipe está sempre exausta e desmotivada

Sua equipe não tem mais direito a finais de semana, feriados

Você não tem tempo para pensar em segurança e performance

Uma simples atualização de software pode levar semanas

Wednesday, December 12, 12

Tarefas repetitivas

Wednesday, December 12, 12

A maioria das demandas de um sysdmin envolve execução de tarefas repetitivas

Wednesday, December 12, 12

Wednesday, December 12, 12

Tarefas repetitivasCriação de usuários

Elaboração de scripts

Configuração de serviços

Configurações de monitoramento

Criação de imagens de ambientes

Configuração do sistema operacional

Instalação, atualização e remoção de pacotes

Wednesday, December 12, 12

Remover Nagios e Instalar Zabbix em 500 máquinas

Wednesday, December 12, 12

Instalação de Zabbix-Agent

Acessar o servidor por ssh e se tornar root

Configurar repositório YUM, APT ou Ports

Instalar pacote zabbix-agent

Remover pacote nagios

Ajustar arquivo de configuração Zabbix

Reiniciar Zabbix Agent

Wednesday, December 12, 12

Instalação de Zabbix-Agent

10 minutos por máquina

5000 minutos ou 83.3 horas de trabalho repetitivo

10 dias para instalar o zabbix-agent no parque

1 analista alocado exclusivamente para isto 8HPD

Considere re-trabalho devido ao modelo manual

Wednesday, December 12, 12

Criar o usuário do novo sysadmin em 500 máquinas

Wednesday, December 12, 12

Criação de usuário para sysadmin

Acessar o servidor por ssh

Se tornar root

Criar usuário

Setar senha temporária

Configurar privilégios no sudo

Wednesday, December 12, 12

Instalação de Zabbix-Agent

7 minutos por máquina

3500 minutos ou 58.3 horas de trabalho repetitivo

7 dias para criar o usuário no parque

1 analista alocado exclusivamente para isto 8HPD

Considere re-trabalho devido ao modelo manual

Considere que o usuário vai ter que trocar a senha nas 500 máquinas

Wednesday, December 12, 12

Mas eu não posso usar LDAP para autenticar meus usuários, não seria

melhor?

Wednesday, December 12, 12

Autenticação LDAP em Debian

Você precisa manter as configurações do PAM e módulo LDAP

Arquivos a serem mantidos ldap.conf, nsswitch.conf, libnss-ldap.conf

Pacotes a serem mantidos ldap-utils, libpam-ldap, libnss-ldap e nscd

Você ainda precisa ter um usuário coringa em caso de problema no LDAP

Wednesday, December 12, 12

Como alterar vários arquivos de configuração em 500 máquinas em um caso de mudança na

estrutura da árvore LDAP?

Wednesday, December 12, 12

Remover usuários antigos é tão complicado quanto criar novos

Wednesday, December 12, 12

Rastreamento de mudanças e falta de padrões

Wednesday, December 12, 12

Se você pedir para dois sysadmins instalarem um servidor você terá

dois ambientes diferentes

Wednesday, December 12, 12

Falta de padronização

Wednesday, December 12, 12

O que devemos padronizar?

DNS (resolv.conf)

Usuários e Privilégios

NTP (data/hora)

Pacotes Sysadmins

Rotas

Hosts e Hostnames

Repositórios

Logs e Autenticação

Firewall

Hardening, Tuning

Wednesday, December 12, 12

Falta de processos e procedimentos de execução de atividades e demandas

Wednesday, December 12, 12

Desvantagens do modelo Artesanal

Wednesday, December 12, 12

Desvantagens do modelo artesanal

Falta de padronização, processos e procedimentos

Documentação inexpressiva ou inexistente

Falta de planejamento para execução das demandas

Desconhecimento dos riscos envolvidos

Alto índice de falhas humanas

Wednesday, December 12, 12

Desvantagens do modelo artesanal

Baixo índice de disponibilidade dos serviços oferecidos

Demora na aplicação de mudanças

Demora na correção de problemas

Equipe desmotivada

Atividades repetitivas e desgastantes

Wednesday, December 12, 12

Desvantagens do modelo artesanal

Equipe sempre sobrecarregada

Alta rotatividade da equipe

Alto custo com horas extras

Profissionais insatisfeiros

Baixa credibilidade perante clientes e gestores

Wednesday, December 12, 12

Como resolvo estes problemas?Como obtenho controle e padronização em meu ambiente ?

Wednesday, December 12, 12

Gerência de Configurações

Wednesday, December 12, 12

Padronização

Wednesday, December 12, 12

Automatização

Wednesday, December 12, 12

Controle

Wednesday, December 12, 12

Integridade

Wednesday, December 12, 12

Desempenho

Wednesday, December 12, 12

Agilidade nas mudanças

Wednesday, December 12, 12

PuppetFerramenta de nova geração que implementa gerência de

configurações para seu ambiente.

Wednesday, December 12, 12

Visão Rápida

Framework Open Source para Gerência de Configurações

Oferece um conjunto de ferramentas para manipular estados

Nos permite trabalhar a Infraestrutura como código

Oferece uma linguagem declarativa para descrever configurações de sistemas e serviços

Não é programação

Wednesday, December 12, 12

Sobre a ferramenta

Criado por Luke Kaines (CEO e Fundador Puppetlabs)

Empresa PuppetLabs mantém a Ferramenta

Ferramenta OpenSource (Licença Apache)

Empresa oferece Suporte Corporativo e Versão Enterpris

Empresa recebeu investimentos da VMWARE, GOOGLE e CISCO

Wednesday, December 12, 12

Sobre a ferramenta

Criado por Luke Kaines (CEO e Fundador Puppetlabs)

Empresa PuppetLabs mantém a Ferramenta

Ferramenta OpenSource (Licença Apache)

Empresa oferece Suporte Corporativo e Versão Enterpris

Empresa recebeu investimentos da VMWARE, GOOGLE e CISCO

Wednesday, December 12, 12

Feito por um SysAdmin para SysAdmins

Wednesday, December 12, 12

Desenhada para uso DevOps

Wednesday, December 12, 12

Visão DevOpsWednesday, December 12, 12

Desenvolvedor que lançar novas versões de forma rápida e eficiente

Sysadmin quer manter o parque integro e funcionando minimizando riscos de incidentes

Wednesday, December 12, 12

Especificações e Características

Escrito em Ruby

Extensível usando código Ruby

Funciona em modo Autônomo (serverless)

Funciona em modo Cliente/Servidor usando API REST

Provê comunicação segura usando SSL

Suporte a 19 sistemas operacionais (Linux, Unix, BSD...)

Wednesday, December 12, 12

Quem usa o Puppet?

Wednesday, December 12, 12

ArquiteturaComo funciona o Puppet?

Wednesday, December 12, 12

Resource Abstraction Layer

Wednesday, December 12, 12

Puppet: RAL

Resource Abstraction Layer = RAL

Camada de Abstração de Recursos

Fale o que você quer que seja feito

Não se preocupe em como será feito

O Puppet sabe como fazer

Wednesday, December 12, 12

Instale Pacote X

Wednesday, December 12, 12

Remova usuário Z

Wednesday, December 12, 12

(Re)inicie serviço Y

Wednesday, December 12, 12

Tratamento de Informações

O grande diferencial do Puppet é a forma como ele trata as informações de seus nodes

Wednesday, December 12, 12

Tratamento de informações

No Puppet tudo é modelado e tratado como ‘dado’

O estado atual de um node (servidor) é um dado

Um pacote instalado em um node é um dado

Um usuário em um servidor é um dado

Wednesday, December 12, 12

Os dados são inseridos em catálogos para serem utilizados

O catálogo é processado pelo node e as modificações são aplicadas de acordo com o que foi

declarado.

Wednesday, December 12, 12

Processamento do Catálogo

1) Agente Requisita Catálogo1.1) Agente envia Fatos para Master2) Master Processa Fatos e Compara2.1) Master Produz e envia Catálogo3) Node Recebe, Compara e Aplica4) Node informa estado atual ao Master5) Sistema reflete catálogo

Wednesday, December 12, 12

Idempotência

Wednesday, December 12, 12

A idempotência é a propriedade que algumas operações têm de poderem ser aplicadas várias

vezes sem que o valor do resultado se altere após a aplicação inicial. (fonte: wikipedia)

Wednesday, December 12, 12

ConfiguraçõesVoláteis e Dados

Puppet MasterMódulos Estáticos

Puppet visão geral

LDAP DNS MONIT SYSLOG

JBOSS APACHE MYSQL PGSQL

Puppet Agents

Camada de Aplicação

Camada de Serviços Estruturantes

Wednesday, December 12, 12

O que acontece quando adicionamos um node ao nosso parque?

Wednesday, December 12, 12

Adicionando node ao parque

ZABBIX

JBOSS

POSTGRESQL

MEMCACHED

NGINX

Wednesday, December 12, 12

Adicionando node ao parque

ZABBIX

POSTGRESQL

MEMCACHED

NGINX

Adicionar um novo node representa N mudanças

JBOSS

Wednesday, December 12, 12

Adicionando node ao parque

sysadmin-utilszabbix-agent

ntpconflocaleshostsusers

localmtasmtpdvimrc

backup-agentapt-repos

ZABBIX

POSTGRESQL

MEMCACHED

NGINX

JBOSS

Wednesday, December 12, 12

Como o Puppet pode ajudar?

Automatizando todo o seu ambiente

Provendo maior produtividade com menor esforço

Padronizando seus nodes logo após a criação e instalação

Modificando configurações de forma controlada

Mantendo o estado declarado para cada node/instância

Wednesday, December 12, 12

Insira o Puppet na imagem de instalação de seus nodes.

Wednesday, December 12, 12

Pare de administrar e começe a desenvolver sua infra

Wednesday, December 12, 12

Não tenha medo de realizar atualizações, o puppet faz pra você!

Wednesday, December 12, 12

Você pode fazer deploy de sua APPVocê pode controlar a versão de sua APP

Wednesday, December 12, 12

Como é o funcionamento do Puppet em Rede?

Wednesday, December 12, 12

Puppet Visão em Rede

Puppet Master

Puppet Client

8140 TCPClient

puppetd -t

8139 TCPServer

puppetrunSSL

Wednesday, December 12, 12

Arquitetura Cliente/Servidor

O agente gera um certificado digital

O master precisa autorizar o certificado

Sem autorização o agente não pode se comunicar

Toda a comunicação entre agente e master é segura

Wednesday, December 12, 12

Fluxo Cliente/Servidor

Instalação do node

Wednesday, December 12, 12

Fluxo Cliente/Servidor

Instalação do node

Inicialização do puppet

Wednesday, December 12, 12

Fluxo Cliente/Servidor

Instalação do node

Geração de Certificado

Inicialização do puppet

Wednesday, December 12, 12

Fluxo Cliente/Servidor

Instalação do node

Geração de Certificado

Envio de Certificado

Inicialização do puppet

Wednesday, December 12, 12

Fluxo Cliente/Servidor

Instalação do node

Geração de Certificado

Master Assina Certificado

Envio de Certificado

Inicialização do puppet

Wednesday, December 12, 12

Fluxo Cliente/Servidor

Instalação do node

Geração de Certificado

Agente Sincroniza

Master Assina Certificado

Envio de Certificado

Inicialização do puppet

Wednesday, December 12, 12

Fluxo Cliente/Servidor

Instalação do node

Geração de Certificado

Agente Sincroniza

Master Assina Certificado

Envio de Certificado

Inicialização do puppet

Modalidades de Assinatura de CertificadoAssinatura pode ser manualAssinatura pode ser automática por domínioAssinatura pode ser automática em qualquer requisição

Wednesday, December 12, 12

O agente se comunica com o master a cada N minutos

Wednesday, December 12, 12

E quais os recursos disponíveis para gerenciar sistemas e serviços?

Como manipulo estados do meu ambiente?

Wednesday, December 12, 12

Funcionalidades do Puppet

Resource Types

Parâmetros e Meta-parâmetros

Templates e Definições

Classes e Módulos

Funções e Condicionais

Wednesday, December 12, 12

Puppet Resource Types

Arquivos e Diretórios

Usuários

Alias

Pacotes

Serviços

Yum Repos

Augeas

Hosts

SSH

Cron

O puppet oferece 38 tipos de recursos nativos, e você pode estendê-lo.

Wednesday, December 12, 12

Resource Type: PackagesSuporte a 23 tipos de provedores de pacotes

Faz a abstração do OS

Declare se o pacote deve estar presente ou ausente

Declare se o pacote deve sempre estar em sua última versão

Wednesday, December 12, 12

Resource Type: ServicesSuporta 11 tipos de sistemas INIT para inicializar serviços

Declare se um serviço deve estar sempre rodando

Declare se um serviço deve ser carregado no boot

Declare se um serviço depende de um pacote ou arquivo

Wednesday, December 12, 12

Resource Type: FileEspecifique permissões e owners

Declare arquivos, diretórios e links

Controle de mudanças usando até 15 tipos de checksums

Wednesday, December 12, 12

ExemplosWednesday, December 12, 12

Instala, Configura e Inicia

# aptitude install apache2

# update-rc.d -f apache2 defaults

# cp ~/httpd.conf /etc/apache2/

# invoke-rc.d apache2 start

debian-way

Wednesday, December 12, 12

package { 'apache2':ensure => present,}

 service { 'apache2':

ensure => running,enable => true,}

file { 'httpd.conf':path => “/etc/apache2/httpd.conf”,source => “/etc/puppet/files/httpd.conf”,}

Instala, Configura e Inicia

Wednesday, December 12, 12

package { 'apache2':ensure => present,}

 service { 'apache2':

ensure => running,enable => true,}

file { 'httpd.conf':path => “/etc/apache2/httpd.conf”,source => “/etc/puppet/files/httpd.conf”,}

Instala, Configura e Inicia

resource typeparameter

titlevalue

Wednesday, December 12, 12

Variáveis e FatosFatos (facter)

vimpackage => vim-puppet,

apacheservice => apache2,

ntpconfrhel => ntp.conf.rhel,

Variáveisdomainfqdnhostnameinterfacesipaddress_eth0ipaddress_eth1ipaddress_lolsbdistidlsbdistrelease

=> hacklab,=> puppetmaster.hacklab,=> puppetmaster,=> eth0,eth1,lo,=> 10.0.2.15,=> 192.168.56.150,=> 127.0.0.1,=> debian,=> 6.0.5,

Wednesday, December 12, 12

Condicionaiscase $operatingsystem { CentOS,RedHat: { $package_name = 'ntp', $service_name = 'ntpd', $conf_file = 'ntp.conf.el } Debian,Ubuntu: { $package_name = 'ntp', $service_name = 'ntp', $conf_file = 'ntp.conf.debian', }}....

Wednesday, December 12, 12

Definiçõesproxy::squid { 'ProxyFilial' : http_port squid_mode squid_hostname cache_mem maximum_object_size_in_memory maximum_object_size memory_replacement_policy cache_replacement_policy cache_dir cache_mgr cache_effective_user cache_effective_group dns_nameservers ips_squid }

=> '3128',=> 'transparent',=> 'proxy.4linux',=> '2 GB',=> '6 MB',=> '128 MB',=> 'heap GDSF',=> 'heap LFUDA',=> 'aufs /var/spool/squid 1024 16 256',=> 'monitora@4linux.com.br',=> 'proxy',=> 'proxy',=> '127.0.0.1 10.61.12.2 172.16.1.1',=> '127.0.0.1 192.168.12.3',

Wednesday, December 12, 12

Templates

myorigin = <%= hostname %>mydestination = $myhostname, ..., localhost, <%= fqdn %>

Trecho do template postfix/main.cf.erb

myorigin = servidor.dominiomydestination = $myhostname, ..., localhost, servidor.dominio

Substituição de variáveis por fatos

Wednesday, December 12, 12

Use uma base class para padronizar seus nodes

Wednesday, December 12, 12

Base Classclass linux-server { include sysadmin-utils include zabbix-agent include ntpconf include locales include hosts include users include localmta include vimrc include backup-agent include apt-repos}

Wednesday, December 12, 12

Como declaro um node e como empurro uma configuração?

Wednesday, December 12, 12

Declarando um nodenode “servidor.dominio” { include linux-server include module}

node “balancer.dominio” { include linux-server include apache include php5 include mysql}

Wednesday, December 12, 12

E como acompanho mudanças?

Wednesday, December 12, 12

Puppet Dashboard

Wednesday, December 12, 12

Wednesday, December 12, 12

Posso fazer mudanças em tempo real?

Wednesday, December 12, 12

Marionette Collective

Orquestrador de nodes

Execução de Tarefas Paralelas

Interação com centenas de nodes

Inventário descentralizado

Leitura de meta-dados do Puppet

Similar a Fabric e Capistrano

Wednesday, December 12, 12

Qual o resultado concreto?

Wednesday, December 12, 12

Documentação Instantânea

Wednesday, December 12, 12

Restore e backup de mudanças

Wednesday, December 12, 12

Processos bem definidos

Wednesday, December 12, 12

Ambiente Padronizado

Wednesday, December 12, 12

Tarefas Automatizadas

Wednesday, December 12, 12

Quais os Benefícios Reais?Wednesday, December 12, 12

Benefícios ReaisMaior produtividade em menor tempo

Poucos SysAdmins para muitos nodes

Diminuição de falhas humanas

Maior controle de todo o seu parque

Diminuição do tempo gasto em mudanças

Diminuição do custo de manutenção

Wednesday, December 12, 12

Tecnologia trabalhando para você

Wednesday, December 12, 12

Puppet & Cloud IaaSCloud Tools (FOSS) Cloud Hosts

Ganeti

Wednesday, December 12, 12

Boas PráticasWednesday, December 12, 12

Use API e recursos do fornecedor seja na nuvem, seja em hypervisor.

Wednesday, December 12, 12

Insira o Puppet nos templates de seu Hypervisor

Wednesday, December 12, 12

Desenvolva sua Infra

Wednesday, December 12, 12

Versione suas configurações

Wednesday, December 12, 12

Reaproveite Código

Wednesday, December 12, 12

GitHub & PuppetForge

Wednesday, December 12, 12

Pesquise!

Wednesday, December 12, 12

Puppet em números

727 pessoas online no canal #puppet da irc.freenode.net

8.500 repositórios no GitHub

450 módulos no PuppetForge

4457 usuários ativos na lista puppet-users com 7795 tópicos de discussão

Dados coletados em 2012-08-06 às 10:34 PMWednesday, December 12, 12

Puppet LabsWednesday, December 12, 12

Site/Bloghttp://www.puppetlabs.comhttp://www.puppetlabs.com/blog/http://puppet-br.org/

Twitter@puppetlabs

GitHubhttp://www.github.com/puppelabs

Puppet na rede

Google GroupsPuppet-camp,puppet-users,puppet-users-br,puppet-dev

IRCirc.freenode.org#puppet#puppet-br

Wednesday, December 12, 12

Perguntas?Wednesday, December 12, 12

Obrigado!

twitter @gutocarvalho

e-mail gutocarvalho@gmail.com

slides slideshare.com/gutocarvalho

blog gutocarvalho.net

code github.com/gutocarvalho

Wednesday, December 12, 12

Recommended