A grande entrevista com Martin Kleppmann: “Descobrindo o futuro dos sistemas de dados distribuídos”



Dr. Martin Kleppmann é pesquisador em sistemas distribuídos da Universidade de Cambridge e autor do aclamado "Designing Data-Intensive Applications" (O'Reilly Media, 2017).

Kevin Scott, CTO da Microsoft disse uma vez : “Este livro deve ser leitura obrigatória para engenheiros de software. "Projetar aplicativos com uso intensivo de dados é um recurso raro que conecta teoria e prática para ajudar os desenvolvedores a tomar decisões inteligentes ao projetar e implementar a infraestrutura e os sistemas de dados".

Os principais interesses de pesquisa de Martin incluem software de colaboração, CRDTs e verificação formal de algoritmos distribuídos. Anteriormente, ele era engenheiro de software e empreendedor de várias empresas de Internet, incluindo LinkedIn e Rapportive, onde trabalhou em infraestrutura de dados em larga escala.

Vadim Tsesko ( @incubos ) é um engenheiro de software líder da Odnoklassniki que trabalha na equipe da Plataforma Principal. Os interesses científicos e de engenharia da Vadim incluem sistemas distribuídos, data warehouses e verificação de sistemas de software.

Conteúdo:


  • Mudando de negócios para pesquisa acadêmica;
  • Discussão sobre "Design de aplicativos intensivos em dados";
  • Bom senso contra exageros artificiais e marketing agressivo;
  • Armadilhas do teorema da PAC e outros erros da indústria;
  • Benefícios da descentralização;
  • Blockchains, Dat, IPFS, Filecoin, WebRTC;
  • Novos CRDTs. Verificação formal com Isabelle;
  • Origem do evento. Abordagem de baixo nível. Transações XA
  • Apache Kafka, PostgreSQL, Memcached, Redis, Elasticsearch;
  • Como aplicar todas essas ferramentas à vida real;
  • Público-alvo esperado das palestras de Martin e da conferência Hydra.




Passando da pesquisa comercial para a acadêmica


Vadim : A primeira pergunta que gostaria de fazer é realmente importante para mim. Você fundou o Go Test It e o Rapportive e projetava e projetava sistemas de grande escala no LinkedIn há um tempo. Então você decidiu mudar da engenharia industrial para a academia. Poderia explicar a motivação para essa decisão? O que você ganhou e o que teve que sacrificar?

Martin : Tem sido um processo muito interessante. Como você parece sugerir, poucas pessoas mudam nessa direção. Muitas pessoas vão da academia para a indústria, mas não muitas. O que é compreensível, porque eu tive que fazer um corte salarial bastante grande para voltar à academia. Mas o que eu realmente amo em pesquisa é a liberdade de trabalhar em tópicos que acho interessantes e que considero importantes, mesmo que esses tópicos não levem imediatamente a um produto comercialmente viável nos próximos 6 meses. Obviamente, em uma empresa, o material que você cria precisa se transformar em um produto que pode ser vendido de uma forma ou de outra. Por outro lado, as coisas nas quais estou trabalhando agora são tópicos realmente importantes para o futuro de como construímos software e como a Internet funciona. Mas ainda não entendemos esses tópicos o suficiente para começar a criar produtos comerciais: ainda estamos tentando descobrir, fundamentalmente, como essas tecnologias devem ser. E como essa é uma pesquisa fundamental, percebi que é melhor fazer isso em uma universidade do que tentar fazer isso em uma empresa, porque em uma universidade sou livre para trabalhar em coisas que podem não se tornar comercialmente viáveis ​​por mais dez anos, e tudo bem Não há problema em trabalhar com um horizonte de tempo muito maior quando você estiver pesquisando.



"Projetando aplicativos intensivos em dados"


Vadim : Definitivamente voltaremos aos seus interesses atuais de pesquisa. Enquanto isso, vamos falar sobre seu último livro, Designing Data-Intensive Applications . Sou um grande fã do seu livro e acredito que seja um dos melhores guias para a construção de sistemas distribuídos modernos. Você cobriu quase todas as realizações notáveis ​​atualizadas.

Martin : Obrigado, fico feliz que você ache útil.

Vadim : Apenas para aqueles leitores azarados que ainda não leram seu livro, você poderia citar várias realizações importantes no campo de sistemas distribuídos hoje em dia?

Martin : Bem, o objetivo do livro não é tanto explicar uma tecnologia específica; o objetivo é fornecer um guia para todo o cenário de diferentes sistemas que são usados ​​para armazenar e processar dados. Existem muitos bancos de dados, processadores de fluxo, ferramentas de processamento em lote, todos os tipos de ferramentas de replicação e assim por diante, e é realmente difícil obter uma visão geral. Se você está tentando criar um aplicativo específico, é realmente difícil saber qual banco de dados você deve usar e quais ferramentas são as mais apropriadas para o problema que você está tentando resolver. Muitos livros de computação existentes simplesmente não responderam a esse problema de maneira satisfatória. Descobri que, se você está lendo um livro sobre Cassandra, por exemplo, ele explica por que Cassandra é maravilhosa, mas geralmente não fala sobre coisas para as quais não é um bom ajuste. Então, o que eu realmente queria fazer neste livro foi identificar as principais perguntas que você precisa se perguntar se está tentando construir algum tipo de sistema em grande escala. E, respondendo a essas perguntas, você pode ajudar a descobrir quais tecnologias são apropriadas e quais são menos apropriadas para o problema específico que você está tentando resolver - porque, em geral, não existe uma tecnologia perfeita para tudo. E assim, o livro está tentando ajudá-lo a descobrir os prós e contras de diferentes tecnologias em diferentes configurações.



Bom senso contra hype artificial e marketing agressivo


Vadim : De fato, muitas vezes - se não sempre - existem muitas tecnologias com funções, recursos e modelos de dados sobrepostos. E você não pode acreditar em todas essas chavões de marketing. Você precisa ler os white papers para aprender os internos e até tentar ler o código-fonte para entender como ele funciona exatamente.

Martin : E eu descobri que você frequentemente tem que ler nas entrelinhas, porque muitas vezes a documentação realmente não diz para quais coisas um determinado banco de dados é ruim. A verdade é que todo banco de dados é péssimo em algum tipo de carga de trabalho, a questão é apenas saber quais são eles. Então, sim, às vezes você precisa ler as diretrizes de implantação para as pessoas das operações e tentar fazer engenharia reversa a partir daquilo que realmente está acontecendo no sistema.

Vadim : Você acha que o setor não possui o vocabulário comum ou um conjunto de critérios para comparar soluções diferentes para o mesmo problema? Coisas semelhantes são chamadas por nomes diferentes, algumas coisas são omitidas que devem sempre ser claras e declaradas explicitamente, como garantias de transação. O que você acha?

Martin : Sim, acho que um problema que nossa indústria tem é que, frequentemente, quando as pessoas falam sobre uma ferramenta específica, há muita publicidade sobre tudo. O que é compreensível, porque as ferramentas são feitas por várias empresas e, obviamente, essas empresas querem promover seus produtos; portanto, essas empresas enviarão pessoas para conferências para falar sobre o quão maravilhoso é seu produto. Será disfarçado de conversa sobre tecnologia, mas essencialmente ainda é uma atividade de vendas. Como indústria, poderíamos realmente fazer com mais honestidade as vantagens e desvantagens de algum produto. E parte disso requer uma terminologia comum, porque, caso contrário, você simplesmente não pode comparar as coisas em pé de igualdade. Mas, além de uma terminologia compartilhada, precisamos de maneiras de raciocinar sobre coisas nas quais certas tecnologias são boas ou ruins.



Armadilhas do teorema da PAC e outros erros da indústria


Vadim : Minha próxima pergunta é bastante controversa. Você poderia citar algum erro grave no setor em que se deparou durante sua carreira? Talvez tecnologias supervalorizadas ou soluções amplamente praticadas das quais devíamos nos livrar há muito tempo? Pode ser um mau exemplo, mas compare o JSON sobre HTTP / 1.1 com o gRPC muito mais eficiente sobre HTTP / 2. Ou existe um ponto de vista alternativo?

Martin : Eu acho que em muitos casos existem boas razões para uma tecnologia fazer uma coisa e não outra. Então, eu estou muito hesitante em chamar as coisas de erros, porque na maioria dos casos é uma questão de trade-offs. No seu exemplo de JSON sobre HTTP / 1.1 versus buffers de protocolo sobre HTTP / 2, acho que existem argumentos bastante razoáveis ​​para os dois lados. Por exemplo, se você deseja usar Buffers de Protocolo, precisa definir seu esquema, e um esquema pode ser uma coisa maravilhosa, pois ajuda a documentar exatamente qual comunicação está acontecendo. Mas algumas pessoas acham os esquemas irritantes, especialmente se estão nos estágios iniciais de desenvolvimento e estão mudando os formatos de dados com muita frequência. Então aí está, há uma questão de trade-offs; em algumas situações, uma é melhor, em outras, a outra é melhor.

Em termos de erros reais que considero simplesmente ruins, há apenas um número bastante pequeno de coisas. Uma opinião que tenho é que o teorema da PAC é fundamentalmente ruim e simplesmente não é útil. Sempre que as pessoas usam o Teorema do CAP para justificar decisões de design, acho que muitas vezes estão interpretando mal o que o CAP está realmente dizendo ou afirmando o óbvio de uma maneira. A CAP como teorema tem um problema de que está realmente apenas afirmando o óbvio. Além disso, ele fala sobre apenas um modelo de consistência muito definido, ou seja, linearizabilidade, e um modelo de disponibilidade muito definido, que é: você deseja que cada réplica esteja totalmente disponível para leitura e gravação, mesmo que não possa se comunicar com outras réplicas. Essas são definições razoáveis, mas são muito estreitas e muitos aplicativos simplesmente não caem no caso de precisar precisamente dessa definição de consistência ou precisamente dessa definição de disponibilidade. E para todos os aplicativos que usam uma definição diferente dessas palavras, o Teorema do CAP não diz nada. É simplesmente uma declaração vazia. Para mim, isso é um erro.

E enquanto estamos reclamando, se você está me pedindo para citar erros, outro grande erro que eu vejo na indústria de tecnologia é a mineração de criptomoedas, que eu acho que é um desperdício tão flagrante de eletricidade. Eu simplesmente não consigo entender por que as pessoas pensam que é uma boa ideia.

Vadim : Falando sobre o teorema do CAP, muitas tecnologias de armazenamento são realmente ajustáveis, em termos de coisas como AP ou CP. Você pode escolher o modo em que operam.

Martin : Sim. Além disso, existem muitas tecnologias que não são consistentes nem disponíveis sob a definição estrita do Teorema da PAC. Eles são literalmente apenas P! Nem CP, nem CA, nem AP, apenas P. Ninguém diz isso, porque isso pareceria ruim, mas honestamente, essa poderia ser uma decisão de design perfeitamente razoável a ser tomada. Existem muitos sistemas para os quais isso é realmente totalmente bom. Essa é realmente uma das razões pelas quais eu acho que o CAP é uma maneira inútil de falar sobre as coisas: porque há uma grande parte do espaço de design que ele simplesmente não captura, onde há bons projetos perfeitamente razoáveis ​​para o software que ele usa. simplesmente não permite que você fale.


Benefícios da descentralização


Vadim : Falando sobre aplicativos com uso intensivo de dados hoje, que outros grandes desafios, problemas não resolvidos ou tópicos importantes de pesquisa você pode citar? Até onde eu sei, você é um dos principais defensores da computação e armazenamento descentralizados.

Martin : Sim. Uma das teses por trás da minha pesquisa é que, no momento, confiamos demais em servidores e centralização. Se você pensar em como a Internet foi originalmente projetada no dia em que evoluiu da ARPANET, ela foi concebida como uma rede muito resiliente, na qual os pacotes poderiam ser enviados por várias rotas diferentes e ainda assim chegariam ao destino. E se uma bomba nuclear atingisse uma cidade americana em particular, o restante da rede continuaria funcionando, pois apenas trafegaria pelas partes com falha do sistema. Este foi um projeto da Guerra Fria.

E então decidimos colocar tudo na nuvem, e agora basicamente tudo tem que passar por um dos datacenters da AWS, como us-east-1 em algum lugar da Virgínia. Nós retiramos esse ideal de poder usar descentralmente várias partes diferentes da rede, e colocamos nesses servidores nos quais tudo depende, e agora é extremamente centralizado. Por isso, estou interessado em descentralização, no sentido de transferir parte do poder e controle dos dados desses servidores e voltar aos usuários finais.

Uma coisa que quero acrescentar neste contexto é que muitas pessoas falando sobre descentralização estão falando sobre coisas como criptomoedas, porque também estão tentando uma forma de descentralização pela qual o controle é desviado de uma autoridade central como um banco e para uma rede de nós cooperantes. Mas esse não é realmente o tipo de descentralização que me interessa: acho que essas criptomoedas ainda são extremamente centralizadas, no sentido de que se você deseja fazer uma transação Bitcoin, precisa fazê-lo na rede Bitcoin - você precisa usar a rede do Bitcoin, para que tudo seja centralizado nessa rede específica. O modo como ele é construído é descentralizado no sentido de que não possui um único nó de controle, mas a rede como um todo é extremamente centralizada, pois qualquer transação que você precise fazer deve fazer através dessa rede. Você não pode fazer isso de outra maneira. Eu sinto que ainda é uma forma de centralização.

No caso de uma criptomoeda, essa centralização pode ser inevitável, porque você precisa fazer coisas como evitar gastos duplos, e isso é difícil sem uma rede que alcance consenso sobre exatamente quais transações ocorreram e quais não ocorreram. E é exatamente isso que a rede Bitcoin faz. Mas existem muitos aplicativos que não exigem algo como uma blockchain, que podem realmente lidar com um modelo de dados muito mais flexível que flui pelo sistema. E esse é o tipo de sistema descentralizado no qual estou mais interessado.

Vadim : Você poderia citar alguma tecnologia promissora ou subvalorizada no campo de sistemas descentralizados, além da blockchain? Uso o IPFS há algum tempo.

Martin : Para o IPFS, examinei-o um pouco, embora ainda não o tenha usado. Nós fizemos algum trabalho com o projeto Dat , que é um pouco semelhante ao IPFS no sentido de que também é uma tecnologia de armazenamento descentralizada. A diferença é que o IPFS possui o Filecoin , uma criptomoeda , anexada a ele como uma forma de pagar pelos recursos de armazenamento, enquanto o Dat não possui nenhuma blockchain anexada a ele - é apenas uma maneira de replicar dados em várias máquinas de maneira P2P.

Para o projeto em que estou trabalhando, o Dat se encaixou perfeitamente, porque queríamos criar um software de colaboração no qual vários usuários diferentes pudessem editar documentos ou bancos de dados, e quaisquer alterações nesses dados seriam enviadas a qualquer pessoa mais quem precisa ter uma cópia desses dados. Podemos usar o Dat para fazer essa replicação de maneira P2P, e o Dat cuida de todas as coisas no nível da rede, como passagem NAT e passagem por firewalls - é um problema bastante complicado apenas para obter os pacotes de uma extremidade à outra . E então construímos uma camada sobre isso, usando CRDTs, que é uma maneira de permitir que várias pessoas editem algum documento ou conjunto de dados e troquem essas edições de maneira eficiente. Eu acho que você provavelmente também pode criar esse tipo de coisa no IPFS: você provavelmente pode ignorar o aspecto Filecoin e usar o aspecto de replicação P2P, e provavelmente também fará o trabalho.

Vadim : Claro, embora o uso do IPFS possa levar a uma menor capacidade de resposta, porque o Dat subjacente do WebRTC conecta os nós P2P diretamente, e o IPFS funciona como uma tabela de hash distribuída.

Martin : Bem, o WebRTC está em um nível diferente da pilha, pois se destina principalmente a conectar duas pessoas que podem estar fazendo uma vídeo chamada; de fato, o software que estamos usando para esta entrevista agora pode estar usando o WebRTC. E o WebRTC fornece um canal de dados que você pode usar para enviar dados binários arbitrários sobre ele, mas criar um sistema de replicação completo ainda é um pouco de trabalho. E isso é algo que Dat ou IPFS já fazem.

Você mencionou a capacidade de resposta - certamente é uma coisa a se pensar. Digamos que você queira criar o próximo Google Docs de maneira descentralizada. Com o Google Docs, a unidade de alterações que você faz é uma única tecla. Cada letra que você digita no teclado pode ser enviada em tempo real aos seus colaboradores, o que é ótimo do ponto de vista da rápida colaboração em tempo real. Mas também significa que, ao longo da escrita de um documento grande, você poderá ter centenas de milhares dessas edições de caracteres únicos que se acumulam, e muitas dessas tecnologias no momento não são muito boas para compactar esse tipo de edição de dados. Você pode manter todas as edições que já fez no seu documento, mas mesmo se você enviar apenas cem bytes para cada pressionamento de tecla que você fizer e escrever um documento um pouco maior com, digamos, 100.000 pressionamentos de tecla, você repentinamente agora possui 10 MB de dados para um documento que seria apenas algumas dezenas de kilobytes normalmente. Portanto, temos essa enorme sobrecarga para a quantidade de dados que precisa ser enviada, a menos que sejamos mais inteligentes na compactação e empacotamento de alterações.

Em vez de enviar a alguém a lista completa de todos os caracteres que já foram digitados, podemos apenas enviar o estado atual do documento e depois enviar as atualizações que ocorreram desde então. Mas muitos desses sistemas ponto a ponto ainda não têm uma maneira de fazer instantâneos de estado de uma maneira que seja eficiente o suficiente para usá-los para algo como o Google Docs. Na verdade, essa é uma área na qual estou trabalhando ativamente, tentando encontrar algoritmos melhores para sincronizar usuários diferentes para algo como um documento de texto, onde não queremos manter cada pressionamento de tecla porque isso seria muito caro e queremos para fazer um uso mais eficiente da largura de banda da rede.



Novos CRDTs. Verificação formal com isabelle


Vadim : Você conseguiu compactar esses dados de pressionamento de tecla substancialmente? Você inventou novos CRDTs ou algo semelhante?

Martin : Sim. Até o momento, temos apenas protótipos para isso, ainda não foi totalmente implementado e ainda precisamos fazer mais algumas experiências para medir a eficiência da prática. Mas desenvolvemos alguns esquemas de compactação que parecem muito promissores. No meu protótipo, reduzi-o de cerca de 100 bytes por edição para algo como 1,7 bytes de sobrecarga por edição. E isso é muito mais razoável, é claro. Mas, como eu disse, essas experiências ainda estão em andamento, e o número ainda pode mudar um pouco. Mas acho que a questão é que ainda há muito espaço para otimização, para que possamos melhorar ainda mais.

Vadim : Então é sobre isso que sua palestra será realizada na conferência Hydra , estou certo?

Martin : Sim, exatamente. Darei uma rápida introdução à área de CRDTs, software colaborativo e alguns dos problemas que surgem nesse contexto. Depois, descreverei algumas das pesquisas que estamos fazendo nesta área. Tem sido muito divertido, porque a pesquisa que estamos fazendo tem uma série de preocupações diferentes. No lado mais aplicado, temos uma implementação JavaScript desses algoritmos, e estamos usando isso para criar peças reais de software, tentando usá-lo para ver como ele se comporta. No outro extremo, temos trabalhado com métodos formais para provar que esses algoritmos estão corretos, porque alguns desses algoritmos são bastante sutis e queremos ter certeza de que os sistemas que estamos criando estão realmente corretos, ou seja, que eles sempre atingem um estado consistente. No passado, havia muitos algoritmos que realmente não conseguiram fazer isso, que estavam simplesmente errados, ou seja, em certos casos extremos, eles permaneceriam permanentemente inconsistentes. E assim, para evitar esses problemas que os algoritmos tiveram no passado, usamos métodos formais para provar que nossos algoritmos estão corretos.

Vadim : Uau. Você realmente usa provadores de teoremas, como Coq ou Isabelle ou qualquer outra coisa?

Martin : Exatamente, estamos usando Isabelle para isso.

Você pode assistir à palestra de Martin "Prova de correção de sistemas distribuídos com Isabelle" na conferência The Strange Loop, em setembro.

Vadim : Parece ótimo! Essas provas serão publicadas?

Martin : Sim, nosso primeiro conjunto de provas já é público. Publicamos isso há um ano e meio: era uma estrutura para verificar CRDTs e verificamos três CRDTs específicas nessa estrutura, sendo a principal delas a RGA ( Replicated Growable Array ), que é uma CRDT para edição de texto colaborativa. Embora não seja muito complicado, é um algoritmo bastante sutil e, portanto, é um bom caso em que é necessária prova, porque não é óbvio, apenas olhando para ele, que realmente está correto. E assim a prova nos dá a certeza adicional de que realmente está correta. Nosso trabalho anterior foi sobre a verificação de alguns CRDTs existentes, e nosso trabalho mais recente nesta área é sobre nossos próprios CRDTs para novos modelos de dados que estamos desenvolvendo e provando que nossos próprios CRDTs também estão corretos.

Vadim : Qual é o tamanho da prova comparada à descrição do algoritmo? Porque às vezes pode ser um problema.

Martin : Sim, isso é um problema - as provas costumam dar muito trabalho. Penso no nosso exemplo mais recente ... Na verdade, deixe-me dar uma rápida olhada no código. A descrição do algoritmo e das estruturas de dados é de cerca de 60 linhas de código. Portanto, é um algoritmo bastante pequeno. A prova tem mais de 800 linhas. Portanto, temos uma proporção aproximada de 12: 1 entre a prova e o código. E isso é infelizmente bastante típico. A prova é uma grande quantidade de trabalho adicional. Por outro lado, uma vez que temos a prova, ganhamos uma certeza muito forte na correção do algoritmo. Além disso, como seres humanos, entendemos o algoritmo muito melhor. Muitas vezes, acho que, ao tentar formalizá-lo, acabamos entendendo o que estamos tentando formalizar muito melhor do que antes. E isso por si só é realmente um resultado útil deste trabalho: além da própria prova, obtemos um entendimento mais profundo, e isso geralmente é muito útil para criar melhores implementações.

Vadim : Você poderia descrever o público-alvo da sua palestra, quão duro será? Qual é o conhecimento preliminar que você espera que o público tenha?

Martin : Eu gosto de tornar minhas palestras acessíveis com o mínimo de conhecimento prévio possível e tento elevar todos ao mesmo nível. Cubro muito material, mas começo com uma base baixa. Eu esperaria que as pessoas tivessem alguma experiência geral em sistemas distribuídos: como você envia alguns dados através de uma rede usando TCP, ou talvez uma idéia aproximada de como o Git funciona, que é um modelo bastante bom para essas coisas. Mas isso é tudo o que você precisa, realmente. Então, entender o trabalho que estamos realizando ainda não é muito difícil. Eu explico tudo pelo exemplo, usando figuras para ilustrar tudo. Felizmente, todos serão capazes de acompanhar.



Origem do evento. Abordagem de baixo nível. Transações XA


Vadim : Parece realmente ótimo. Na verdade, temos algum tempo e gostaria de discutir um de seus artigos recentes sobre o processamento de eventos on-line. Você é um grande defensor da ideia de fornecimento de eventos, está correto?

Martin : Sim, claro.

Vadim : Atualmente, essa abordagem está ganhando força e, em busca de todas as vantagens do log de operações globalmente ordenado, muitos engenheiros tentam implantá-la em qualquer lugar. Você poderia descrever alguns casos em que a fonte de eventos não é a melhor opção? Apenas para evitar seu uso indevido e possível decepção com a própria abordagem.

Martin : Existem duas camadas diferentes da pilha sobre as quais precisamos falar primeiro. A fonte de eventos, conforme proposta por Greg Young e alguns outros, é um mecanismo para modelagem de dados, ou seja: se você possui um esquema de banco de dados e está começando a perder o controle, porque existem muitas tabelas diferentes e eles ' todos são modificados por transações diferentes - a fonte de eventos é uma maneira de trazer melhor clareza a esse modelo de dados, porque os eventos podem expressar muito diretamente o que está acontecendo no nível comercial. Qual é a ação que o usuário executou? Efetivamente, o que você está fazendo com o sourcing de eventos é separar a ação (o evento) dos seus efeitos, que acontecem em algum ponto a jusante.

Eu vim para essa área de um ângulo um pouco diferente, que é um ponto de vista de nível inferior do uso de sistemas como o Kafka para a construção de sistemas altamente escalonáveis. Essa visão é semelhante no sentido de que, se você estiver usando algo como Kafka, está usando eventos, mas isso não significa que você esteja necessariamente usando a fonte de eventos. E, inversamente, você não precisa usar o Kafka para fazer a fonte do evento; você pode fazer a fonte de eventos em um banco de dados regular ou pode usar um banco de dados especial projetado especificamente para a fonte de eventos. Portanto, essas duas idéias são semelhantes, mas nenhuma exige a outra, elas apenas têm alguma sobreposição.

O caso de querer usar um sistema como o Kafka é principalmente o argumento de escalabilidade: nesse caso, você simplesmente recebe tantos dados que não pode processá-los de maneira realista em um banco de dados de nó único; portanto, é necessário particioná-lo em alguns e usar um log de eventos como o Kafka oferece uma boa maneira de espalhar esse trabalho por várias máquinas. Ele fornece uma maneira boa e baseada em princípios para dimensionar sistemas. É especialmente útil se você deseja integrar vários sistemas de armazenamento diferentes. Portanto, se, por exemplo, você deseja atualizar não apenas seu banco de dados relacional, mas também, digamos, um índice de pesquisa de texto completo como o Elasticsearch, ou um sistema de armazenamento em cache como Memcached ou Redis ou algo assim, e você deseja que um evento tenha um atualizando o efeito em todos esses sistemas diferentes, algo como Kafka é muito útil.

Em termos da pergunta que você fez (quais são as situações em que eu não usaria essa abordagem de fornecimento de eventos ou log de eventos) - acho difícil dizer com precisão, mas como regra geral, eu diria: use o que for mais simples . Ou seja, o que estiver mais próximo do domínio que você está tentando implementar. E assim, se a coisa que você está tentando implementar é muito bem mapeada para um banco de dados relacional, no qual você apenas insere, atualiza e exclui algumas linhas, use um banco de dados relacional e insira, atualize e exclua algumas linhas. Não há nada errado com os bancos de dados relacionais e usá-los como estão. Eles funcionaram bem para nós por um longo tempo e continuam a fazê-lo. Mas se você estiver em uma situação em que está realmente lutando para usar esse tipo de banco de dados, por exemplo, porque a complexidade do modelo de dados está ficando fora de controle, faz sentido mudar para algo como uma fonte de eventos abordagem.

Da mesma forma, no nível mais baixo (escalabilidade), se o tamanho dos seus dados for tal que você possa colocá-los no PostgreSQL em uma única máquina - provavelmente isso é bom, basta usar o PostgreSQL em uma única máquina. Mas se você está no ponto em que não há como uma única máquina lidar com sua carga, você precisa escalar um sistema grande, então faz sentido procurar em sistemas mais distribuídos como o Kafka. Eu acho que o princípio geral aqui é: use o que for mais simples para a tarefa específica que você está tentando resolver.

Vadim : É realmente um bom conselho. Conforme seu sistema evolui, você não pode prever com precisão a direção do desenvolvimento, todas as consultas, padrões e fluxos de dados.

Martin : Exatamente, e para esse tipo de situação, os bancos de dados relacionais são incríveis, porque são muito flexíveis, especialmente se você incluir o suporte JSON que eles têm agora. O PostgreSQL agora tem um suporte muito bom para JSON. Você pode adicionar um novo índice se desejar consultar de uma maneira diferente. Você pode simplesmente alterar o esquema e continuar executando os dados em uma estrutura diferente. Portanto, se o tamanho do conjunto de dados não for muito grande e a complexidade não for muito grande, os bancos de dados relacionais funcionarão bem e fornecerão uma grande flexibilidade.

Vadim : Vamos falar um pouco mais sobre o fornecimento de eventos. Você mencionou um exemplo interessante com vários consumidores consumindo eventos de uma fila baseada em Kafka ou algo semelhante. Imagine que novos documentos sejam publicados e vários sistemas estejam consumindo eventos: um sistema de pesquisa baseado no Elasticsearch, que torna os documentos pesquisáveis, um sistema de cache que os coloca no cache de valor-chave baseado no Memcached e um sistema de banco de dados relacional que atualiza alguns tabelas em conformidade. Um documento pode ser uma oferta de venda de carros ou um anúncio imobiliário. Todos esses sistemas de consumo funcionam simultaneamente e simultaneamente.

Martin : Então, sua pergunta é como você lida com o fato de que, se você tiver esses vários consumidores, alguns deles podem ter sido atualizados, mas outros ainda não viram uma atualização e ainda estão um pouco atrasados?

Vadim : Sim, exatamente. Um usuário acessa seu site, entra em uma consulta de pesquisa, obtém alguns resultados de pesquisa e clica em um link. Mas ela obtém o código de status HTTP 404 porque não existe essa entidade no banco de dados, que ainda não foi capaz de consumir e persistir o documento.

Martin : Sim, isso é realmente um desafio. Idealmente, o que você deseja é o que chamaríamos de "consistência causal" nesses diferentes sistemas de armazenamento. Se um sistema contiver alguns dados dos quais você depende, os outros sistemas analisados ​​também conterão essas dependências. Infelizmente, reunir esse tipo de consistência causal em diferentes tecnologias de armazenamento é realmente muito difícil, e isso não é culpa da fonte de eventos, porque, independentemente da abordagem ou sistema usado para enviar as atualizações para os vários sistemas diferentes, você sempre pode acabar com algum tipo de problema de simultaneidade.

No seu exemplo de gravação de dados no Memcached e no Elasticsearch, mesmo se você tentar fazer as gravações nos dois sistemas simultaneamente, poderá haver um pouco de atraso na rede, o que significa que eles chegam em momentos ligeiramente diferentes nesses sistemas diferentes, e processado com um tempo ligeiramente diferente. E, portanto, alguém que está lendo esses dois sistemas pode ver um estado inconsistente. Agora, existem alguns projetos de pesquisa que estão trabalhando pelo menos para alcançar esse tipo de consistência causal, mas ainda é difícil se você quiser usar algo como Elasticsearch ou Memcached ou algo assim.

Uma boa solução aqui seria que você seja apresentado, conceitualmente, com um instantâneo consistente no momento exato, tanto no índice de pesquisa quanto no cache e no banco de dados. Se você trabalha apenas dentro de um banco de dados relacional, obtém algo chamado isolamento de instantâneo, e o ponto de isolamento de instantâneo é que, se você estiver lendo no banco de dados, parece que você tem sua própria cópia privada de todo banco de dados. Qualquer coisa que você olhar no banco de dados, todos os dados que você consultar serão o estado a partir desse momento, de acordo com o instantâneo. Portanto, mesmo que os dados tenham sido alterados posteriormente por outra transação, você realmente verá os dados mais antigos, porque esses dados mais antigos fazem parte de um instantâneo consistente.

E agora, no caso em que você tem o Elasticsearch e o Memcached, realmente o que você idealmente deseja é um instantâneo consistente entre esses dois sistemas. Infelizmente, porém, nem o Memcached, nem o Redis, nem o Elasticsearch têm um mecanismo eficiente para criar esses tipos de instantâneos que podem ser coordenados com diferentes sistemas de armazenamento. Cada sistema de armazenamento apenas pensa por si e normalmente apresenta o valor mais recente de cada chave, e não possui esse recurso para olhar para trás e apresentar uma versão um pouco mais antiga dos dados, porque a versão mais recente dos dados ainda não está disponível. consistente.

Eu realmente não tenho uma boa resposta para como seria a solução. Receio que a solução exija alterações de código em qualquer sistema de armazenamento que participe desse tipo de coisa. Portanto, serão necessárias alterações no Elasticsearch e no Redis, no Memcached e em qualquer outro sistema. E eles teriam que adicionar algum tipo de mecanismo para snapshots point-in-time que sejam baratos o suficiente para que você possa usá-lo o tempo todo, porque você pode querer o snapshot várias vezes por segundo - não é apenas uma vez dia-instantâneo, é muito refinado. No momento, os sistemas subjacentes não existem em termos de capacidade de fazer esses tipos de instantâneos em diferentes sistemas de armazenamento. É um tópico de pesquisa realmente interessante. Espero que alguém trabalhe nisso, mas ainda não vi respostas realmente convincentes para esse problema.

Vadim : Sim, precisamos de algum tipo de Controle de Concorrência Multiversão compartilhado.

Martin : Exatamente, como os sistemas de transações distribuídas. As transações distribuídas do XA o levarão até lá, mas infelizmente o XA, como está, não é muito adequado porque funciona apenas se você estiver usando o controle de concorrência baseado em bloqueio. Isso significa que, se você ler alguns dados, precisará travar um bloqueio para que ninguém possa modificar esses dados enquanto você tiver esse bloqueio. E esse tipo de controle de simultaneidade baseado em bloqueio tem um desempenho terrível; portanto, nenhum sistema realmente usa isso na prática atualmente. Mas se você não tiver esse bloqueio, não obterá o comportamento de isolamento necessário em um sistema como transações distribuídas XA. Talvez o que precisamos seja de um novo protocolo para transações distribuídas que permita o isolamento de instantâneos como o mecanismo de isolamento em diferentes sistemas. Mas acho que ainda não vi nada que implemente isso.

Vadim : Sim, espero que alguém esteja trabalhando nisso.

Martin : Sim, seria realmente importante. Também no contexto de microsserviços, por exemplo: a maneira como as pessoas promovem que você deve criar microsserviços é que cada microsserviço tenha seu próprio armazenamento, seu próprio banco de dados e você não tenha um serviço acessando diretamente o banco de dados de outro serviço, porque isso quebraria o encapsulamento do serviço. Portanto, cada serviço gerencia apenas seus próprios dados.

Por exemplo, você tem um serviço para gerenciar usuários, e ele possui um banco de dados para os usuários, e todo mundo que deseja descobrir algo sobre os usuários precisa passar pelo serviço do usuário. Do ponto de vista do encapsulamento, isso é bom: você está ocultando detalhes do esquema do banco de dados de outros serviços, por exemplo.

But from the point of view of consistency across different services — well, you've got a huge problem now, because of exactly the thing we were discussing: we might have data in two different services that depends upon each other in some way, and you could easily end up with one service being slightly ahead of or slightly behind the other in terms of timing, and then you could end up with someone who reads across different services, getting inconsistent results. And I don't think anybody building microservices currently has an answer to that problem.

Vadim : It is somewhat similar to workflows in our society and government, which are inherently asynchronous and there are no guarantees of delivery. You can get your passport number, then you can change it, and you need to prove that you changed it, and that you are the same person.

Martin : Yes, absolutely. As humans we have ways of dealing with this, for example, we might know that oh, sometimes that database is a bit outdated, I'll just check back tomorrow. And then tomorrow it's fine. But if it's software that we're building, we have to program all that kind of handling into the software. The software can't think for itself.

Vadim : Definitely, at least not yet. I have another question about the advantages of event sourcing. Event sourcing gives you the ability to stop processing events in case of a bug, and resume consuming events having deployed the fix, so that the system is always consistent. It's a really strong and useful property, but it might not be acceptable in some cases like banking where you can imagine a system that continues to accept financial transactions, but the balances are stale due to suspended consumers waiting for a bugfix from developers. What might be a workaround in such cases?

Martin : I think it's a bit unlikely to stop the consumer, deploying the fix and then restart it, because, as you say, the system has got to continue running, you can't just stop it. I think what is more likely to happen is: if you discover a bug, you let the system continue running, but while it continues running with the buggy code, you produce another version of the code that is fixed, you deploy that fixed version separately and run the two in parallel for a while. In the fixed version of the code you might go back in history and reprocess all of the input events that have happened since the buggy code was deployed, and maybe write the results to a different database. Once you've caught up again you've got two versions of the database, which are both based on the same event inputs, but one of the two processed events with the buggy code and the other processed the events with the correct code. At that point you can do the switchover, and now everyone who reads the data is going to read the correct version instead of the buggy version, and you can shut down the buggy version. That way you never need to stop the system from running, everything keeps working all the time. And you can take the time to fix the bug, and you can recover from the bug because you can reprocess those input events again.

Vadim : Indeed, it's a really good option if the storage systems are under your control, and we are not talking about side effects applied to external systems.

Martin : Yes, you're right, once we send the data to external systems it gets more difficult because you might not be able to easily correct it. But this is again something you find in financial accounting, for example. In a company, you might have quarterly accounts. At the end of the quarter, everything gets frozen, and all of the revenue and profit calculations are based on the numbers for that quarter. But then it can happen that actually, some delayed transaction came in, because somebody forgot to file a receipt in time. The transaction comes in after the calculations for the quarter have been finalized, but it still belongs in that earlier quarter.

What accountants do in this case is that in the next quarter, they produce corrections to the previous quarter's accounts. And typically those corrections will be a small number, and that's no problem because it doesn't change the big picture. But at the same time, everything is still accounted for correctly. At the human level of these accounting systems that has been the case ever since accounting systems were invented, centuries ago. It's always been the case that some late transactions would come in and change the result for some number that you thought was final, but actually, it wasn't because the correction could still come in. And so we just build the system with the mechanism to perform such corrections. I think we can learn from accounting systems and apply similar ideas to many other types of data storage systems, and just accept the fact that sometimes they are mostly correct but not 100% correct and the correction might come in later.

Vadim : It's a different point of view to building systems.

Martin : It is a bit of a new way of thinking, yes. It can be disorienting when you come across it at first. But I don't think there's really a way round it, because this impreciseness is inherent in the fact that we do not know the entire state of the world — it is fundamental to the way distributed systems work. We can't just hide it, we can't pretend that it doesn't happen, because that imprecision is necessarily exposed in the way we process the data.



Professional growth and development


Vadim : Do you think that conferences like Hydra are anticipated? Most distributed systems are quite different, and it is hard to imagine that many attendees will get to work and will start applying what they have learned in day-to-day activities.

Martin : It is broad, but I think that a lot of the interesting ideas in distributed systems are conceptual. So the insights are not necessarily like «use this database» or «use this particular technology». They are more like ways of thinking about systems and about software. And those kinds of ideas can be applied quite widely. My hope is that when attendees go away from this conference, the lessons they take away are not so much what piece of software they should be using or which programming language they should be using – really, I don't mind about that – but more like how to think about the systems they are building.

Vadim : Why do you think it's important to give conference talks on such complex topics as your talk, compared to publishing papers, covering all their details and intricacies? Or should anyone do both?

Martin : I think they serve different purposes. When we write papers, the purpose is to have a very definitive, very precise analysis of a particular problem, and to go really deep in that. On the other hand, the purpose of a talk is more to get people interested in a topic and to start a conversation around it. I love going to conferences partly because of the discussions I then have around the talk, where people come to me and say: «oh, we tried something like this, but we ran into this problem and that problem, what do you think about that?» Then I get to think about other people's problems, and that's really interesting because I get to learn a lot from that.

So, from my point of view, the selfish reason for going to conferences is really to learn from other people, what their experiences have been, and to help share the experiences that we've made in the hope that other people will find them useful as well. But fundamentally, a conference talk is often an introduction to a subject, whereas a paper is a deep analysis of a very narrow question. I think those are different genres and I think we need both of them.

Vadim : And the last question. How do you personally grow as a professional engineer and a researcher? Could you please recommend any conferences, blogs, books, communities for those who wish to develop themselves in the field of distributed systems?

Martin : That's a good question. Certainly, there are things to listen to and to read. There's no shortage of conference talks that have been recorded and put online. There are books like my own book for example, which provides a bit of an introduction to the topic, but also lots of references to further reading. So if there are any particular detailed questions that you're interested in, you can follow those references and find the original papers where these ideas were discussed. They can be a very valuable way of learning about something in greater depth.

A really important part is also trying to implement things and seeing how they work out in practice, and talking to other people and sharing your experiences. Part of the value of a conference is that you get to talk to other people as well, live. But you can have that through other mechanisms as well; for example, there's a Slack channel that people have set up for people interested in distributed systems . If that's your thing you can join that. You can, of course, talk to your colleagues in your company and try to learn from them. I don't think there's one right way of doing this — there are many different ways through which you can learn and get a deeper experience, and different paths will work for different people.

Vadim : Thank you very much for your advice and interesting discussion! It has been a pleasure talking to you.

Martin : No problem, yeah, it's been nice talking to you.

Vadim : Let's meet at the conference .

Source: https://habr.com/ru/post/pt458056/


All Articles