Simplesmente uma AULA de sistemas distribuidos. Ótimo conteúdo. Esse nível de conhecimento eu só fui ter na faculdade e raramente vejo em português na internet.
Adorei este conteúdo, IDs era uma das coisas que mais me quebravam a cabeça na questão de performance e aplicabilidade. Eu realmente não encontrei outro vídeo igual a este. Esse conteúdo que o diegão fez tem um baita valor. Parabéns, DIegão. Baita aula
Simplesmente gratificante entrar aqui e ter esse tipo de conteúdo pra consumir. Fico feliz de estar na Rocket e poder entender e conectar esses conteudos com meu aprendizado atual. Começando a construir minhas bases. Sensacional ❤❤
Em 13:04 ele diz que todo algorítimo de geração de dado único tem risco de colisão "porque na computação nada é aleatório". Porém o risco de colisão não é apenas por causa da aleatoriedade, mas também por conta do tamanho do domínio dos algorítimos. Você pode fazer algorítimos com aleatoriedade real (usando os hardware random number generator, ou a entropia de vários sistemas naturais como som ambiente, imagens dinâmicas de processos físicos aleatórios etc) e mesmo assim haver colisão. A analogia é se o ID for gerado por um dado. Um dado é aleatório, mas o domínio só vai de 1 a 6. Se você jogar o dado 7 vezes, terá 7 resultados aleatórios e obrigatoriamente uma colisão no mínimo.
Você pode usar UUID e Incremental ao mesmo tempo. Usa o incremental como sua primary key e cria uma coluna para o uuid como por exemplo "external_refid", dai tu passa a usar o refid para tudo o que precisar fora do seu backend. Isso é util para não expor o incremental ao mesmo tempo que você tem as vantagens dele
Como sempre um conteúdo maravilhoso, mas gostaria de colocar os meus dois centavos para tentar contribuir. Na questão da pesquisa por faixa de ID também poderíamos usar na clausula WHERE a faixa de ID, por exemplo: SELECT * FROM TABELA WHERE ID BETWEEN 980 AND 1000, pois usaríamos da mesma forma o índice ( método usado seria INDEX RANGE SCAN). Durante a explicação da geração dos IDs foi colocado que a aplicação não teria como saber o ID a priori, mas na verdade, teríamos a opção de usar o objeto SEQUENCE do banco de dados. Vc poderia, inclusive, combinar o SEQUENCE com TRIGGER. A TRIGGER usaria automaticamente a SEQUENCE para fornecer o próximo número para o ID caso o DEV não o passasse. Isso poderia ajudar em necessidades de cargas de dados legados onde fosse necessário aproveitar os mesmos IDs. Obviamente, depois de um processo de carga, seria necessário "resetar" a SEQUENCE para o último valor carregado para que a aplicação pudesse continuar sozinha. Os meus comentários não invalidam em nada a apresentação e minha intenção e de apenas contribuir para a questão.
Eu utilizo uuid, na maioria das vezes faço API, eu ordeno com created_at (já tive caso de ter encontrado o registro com mesmo timestamp), e para minimizar os registros da db utilizo multitenancy a nível de base dados (não seja tanta vantagens em fazer a nível de tabelas), de modo mais mecânico como a fazer backup de informações antigas e depois apago.
Bom vídeo. Eu, particularmente, gosto muito de uuid, pois já tive que fazer junção de dados com sequence e foi um BO enorme trabalhar um monte de ID igual. No final tive que reescrever as chaves... loucura! Bacana mostrar Snowflake ID e semelhantes, mas na minha opinião, "created_at" com timestamp(3) já torna o campo suficientemente ordenável para a maioria das aplicações.
@@vitvitvitvitvitvitvitvit cara, muito difícil de acontecer em uma aplicação comum pois as datas são persistidas com milissegundos, saca este exemplo real (2024-04-19 01:08:48.277 e 2024-04-19 01:08:48.688), repara a casa dos milissegundos (277 e 688). Estes dados foram inseridos juntos e ainda assim deu uma diferença grande.
Uso sempre o nanoid com 21 char, na minha opinião é o melhor dos mundos, a colisão aconteceria em ~41 milhões de anos com a inserção de 1.000 ids por segundo.
Considerações: - Existem variações do UUID, e a versão 4 é ordenável. - Indiferente de conter ou não na url um id amigável, é seu dever no backend fazer a segurança do acesso - Para a maioria gigantesca das aplicações o custo extra de um id maior (tamanho de banco e etc) nunca será um problema
Criei recentemente uma aplicação, e, na hora de discutir a estratégia de Id (as legadas usavam Identity/auto-increment, eu queria usar Guid), o DBA implicou com o Guid dizendo que, o fato dele não ser ordenável, traria uma perda de performance muito grande no BD. Acabei recorrendo ao ULID, tem suas desvantagens, principalmente por não ser muito popular, mas atendeu muito bem ao projeto. Dei uma olhada no snowflake mas o custo de implementação não valeria a pena.
2:50 esse ponto positivo de paginacão em sql não faz sentido, a maneira mais eficaz de paginar é utilizando OFFSET (Skip) e FETCH (Take) na consulta sql, o id não influencia em nada na paginacão, a não ser os caracteres a mais que irão ser retornado a mais na consulta caso seja usado guid/uid.
a partir do momento que você precisa fazer um SORT vc já acaba com a condição de "ordenável" da chave ID, afinal você obrigatoriamente vai aplicar uma ordenação por um campo no bd, e pra isso existe indexes
Olá, ainda estou a ver o vídeo muito obrigada mas já tenho algumas perguntas ! O do snowflake usar o timestamp para ordenação não pressupõe o mesmo problema de repetição que tinha o create_at ? Mesmo que depois sejam diferentes pela máquina .. Depois, para evitar conflitos a 100%, não se poderia usar o username para gerar ese id, já que é único ? Valeu mano Muito bom
Sei q o vídeo e sobre bancos relacionais e tal, mas qual sua opinião sobre o ObjectId do MongoDB? Será q ele é suficiente pra grandes projetos como um Twitter da vida, ou teríamos q usar um SnowflakeID também?
vc pode criptografar o id, para usuario e no backend descriptografa e busca os dados necessarios , uso assim no laravel fica a mesma coisa no banco de dados e o usuario sempre irá ver criptografado
Mas ainda vai ter problemas de legibilidade e caso tu precise de alguma forma encontrar essa informação, tu vai ter que ter acesso a chave secreta da criptografia
Bem, acredito que houve uma simplificação ingênua na comparação de que a diferença entre armazenar um integer ocupa menos espaço que uma string. Vários bancos de dados relacionais reservam espaço em disco sobre o tamanho da página que o registro ocupa, e não necessariamente o que está escrito dentro da página, portanto é uma falácia dizer que necessariamente por ter dados inteiros ou texto vão ocupar mais ou menos espaço. Espero que isso leve a mais pessoas pesquisarem sobre o tema (:
Não sei se a solução de pegar os últimos registros a partir da ordem dos registros funciona... E se já houver registros deletados? Mas, com certeza, o espaço ocupado e o tempo de processamento contam bastante a favor do auto incremento. Tem uma boa explicação do problema de se usar uuid no vídeo do Theo (th-cam.com/video/a-K2C3sf1_Q/w-d-xo.htmlsi=_NNKfuFI5o-x9jxz). Ele sugere o uso do nanoid.
Funciona porque é um cursor. Se tiver registro apagado depois do where id > ponteiro, o banco de dados vai contar normalmente apenas os registros que ele encontrou, retornando ao atingir o valor definido no limit ou ao esgotar as linhas da tabela. O cursor é apenas uma referência de onde você parou na última página, um ponto de partida.
Solução, concatenar no UUID em algum lugar dele, um valor numérico ordenado e fragmentado entre as posições do UUID e coloca um pré processamento no back pra pegar de qual user estamos recebendo aquele UUID. Por nada!
@@ivambergsilva591 Valeu mano, eu não tenho o hábito de usar muito o discord, raramente acessso, mas essas lives do Diego eu quero muito ficar acompanhando então vou seguir ele lá na Twitch também, muito obrigado!
o custo computacional de se criar um id é assim tão relevante? O snow flake parece bem completo, precisamos de tantas soluções? Me parece que criar uma coluna para ordenação é mais interessante, é mais simples e o custo computacional não é assim tão alto, mas não colocaria o nome de public_id, ter 2 ids parece confuso
Essa forma de paginar não é a ideial, ele meio que tentou forcar um ponto positivo que não existe. Uma paginacão bem feita voce ira utilizar OFFSET (skip) e FETCH (Take ).
Uma dúvida, mas se eu usar a opção where para fazer a paginação com o id não corre o risco de repetir o dado, pois algum desse registro pode ser apagado e essa sequência ser quebrada?
É porque demora mais e alguém pode ter criado ao mesmo tempo, pelo id é mais difícil, pq é auto Incremento e também pra ordenar id custa menos, porque é número e é pequeno
Eu sei que é natural pensar que daria pra fazer paginação desse jeito aí (id > 980), mas na realidade não funciona porque muitas vezes teremos filtros aplicados.
eu colocaria no mínimo na casa dos milhares para milhões em um certo período de tempo. Na empresa que trabalho, lidamos com mais de 15k inserções por minuto e isso não é muito se comparado com twitter, instagram, discord...
Depende da máquina, aplicação e banco. Mas vc pode tratar 100/200k por segundo como algo que já seria muito. Mas ainda sim não tão muito. Apenas algo p vc se preocupar c filas, pools e afins.
Seria bacana falar sobre o fato do next nao permitir cachear arquivos que são carregados dinámicamente durante a execução em produção. Sempre retorna erro 404, e para contornar o problema, precisa criar um servidor customizado... Chatao isso
@@melkyvinicius6201 Não sei o que é prioridade para você, mas no dia que tiver uma filha e ela ouvir uma pessoa falando palavras que não é de comum, vai entender. Desejo o melhor para você.
@@Bruno-cg4vu Relaxa, o JonnyBorgesdev sabe o que 'e melhor para a gente. A qualidade do codigo dele e alta, ou seja, esta alinhada com o tamanho do ego dele.
Simplesmente uma AULA de sistemas distribuidos. Ótimo conteúdo. Esse nível de conhecimento eu só fui ter na faculdade e raramente vejo em português na internet.
Sim. Por isso que os caras da Rocketseat são sensacionais, muito conteúdo gratuito, com extrema qualidade 🥳🎉
Adorei este conteúdo, IDs era uma das coisas que mais me quebravam a cabeça na questão de performance e aplicabilidade. Eu realmente não encontrei outro vídeo igual a este. Esse conteúdo que o diegão fez tem um baita valor. Parabéns, DIegão. Baita aula
Curti muito Diego, acho que a Rocket ganha muito se começar a trazer pra cá mais conteúdos fundamentais não específicos de uma linguagem.
Simplesmente gratificante entrar aqui e ter esse tipo de conteúdo pra consumir. Fico feliz de estar na Rocket e poder entender e conectar esses conteudos com meu aprendizado atual. Começando a construir minhas bases. Sensacional ❤❤
Simplesmente facinante ❤.
Entrega muito contéudo em um único vídeo e o melhor totalmente grátis
Em 13:04 ele diz que todo algorítimo de geração de dado único tem risco de colisão "porque na computação nada é aleatório". Porém o risco de colisão não é apenas por causa da aleatoriedade, mas também por conta do tamanho do domínio dos algorítimos. Você pode fazer algorítimos com aleatoriedade real (usando os hardware random number generator, ou a entropia de vários sistemas naturais como som ambiente, imagens dinâmicas de processos físicos aleatórios etc) e mesmo assim haver colisão. A analogia é se o ID for gerado por um dado. Um dado é aleatório, mas o domínio só vai de 1 a 6. Se você jogar o dado 7 vezes, terá 7 resultados aleatórios e obrigatoriamente uma colisão no mínimo.
Que vídeo de alto valor, parabéns, ainda existem TH-camrs Tech que realmente fazem conteudo interessante.
Muito bom, eu nem sabia desses problemas que podem ter. Ou seja nunca fiz uma aplicação que tem inserções absurdas
Você pode usar UUID e Incremental ao mesmo tempo.
Usa o incremental como sua primary key e cria uma coluna para o uuid como por exemplo "external_refid", dai tu passa a usar o refid para tudo o que precisar fora do seu backend.
Isso é util para não expor o incremental ao mesmo tempo que você tem as vantagens dele
5:29
Que tal algo semelhante ao ObjectId do MongoDB? Ele é time Sortable e tem 12 bytes.
Como sempre um conteúdo maravilhoso, mas gostaria de colocar os meus dois centavos para tentar contribuir.
Na questão da pesquisa por faixa de ID também poderíamos usar na clausula WHERE a faixa de ID, por exemplo: SELECT * FROM TABELA WHERE ID BETWEEN 980 AND 1000, pois usaríamos da mesma forma o índice ( método usado seria INDEX RANGE SCAN). Durante a explicação da geração dos IDs foi colocado que a aplicação não teria como saber o ID a priori, mas na verdade, teríamos a opção de usar o objeto SEQUENCE do banco de dados. Vc poderia, inclusive, combinar o SEQUENCE com TRIGGER. A TRIGGER usaria automaticamente a SEQUENCE para fornecer o próximo número para o ID caso o DEV não o passasse. Isso poderia ajudar em necessidades de cargas de dados legados onde fosse necessário aproveitar os mesmos IDs. Obviamente, depois de um processo de carga, seria necessário "resetar" a SEQUENCE para o último valor carregado para que a aplicação pudesse continuar sozinha. Os meus comentários não invalidam em nada a apresentação e minha intenção e de apenas contribuir para a questão.
Que vídeo RICO em informações, muito massa!!!
Entendi alguma coisa que o Diego disse? Com certeza não, mas a didática e a forma de explicar é sensacional
geralmente eu gosto de atribuir os indexes que vou utilizar para realizar buscar independente do id e uso UUIDv4 como id.
Eu utilizo uuid, na maioria das vezes faço API, eu ordeno com created_at (já tive caso de ter encontrado o registro com mesmo timestamp), e para minimizar os registros da db utilizo multitenancy a nível de base dados (não seja tanta vantagens em fazer a nível de tabelas), de modo mais mecânico como a fazer backup de informações antigas e depois apago.
esse video ficou mt bom, esses cortes facilitou mt assistir ao video
Bom vídeo. Eu, particularmente, gosto muito de uuid, pois já tive que fazer junção de dados com sequence e foi um BO enorme trabalhar um monte de ID igual. No final tive que reescrever as chaves... loucura!
Bacana mostrar Snowflake ID e semelhantes, mas na minha opinião, "created_at" com timestamp(3) já torna o campo suficientemente ordenável para a maioria das aplicações.
com timestamp(3) não aconteceria o problema que diego disse? eu só fiz site interno e sempre uso id auto incremental mesmo por ser mais fácil.
@@vitvitvitvitvitvitvitvit cara, muito difícil de acontecer em uma aplicação comum pois as datas são persistidas com milissegundos, saca este exemplo real (2024-04-19 01:08:48.277 e 2024-04-19 01:08:48.688), repara a casa dos milissegundos (277 e 688). Estes dados foram inseridos juntos e ainda assim deu uma diferença grande.
@@vitvitvitvitvitvitvitvit sim, pois a data é persistida com milissegundos.
É muito raro, quase impossível. O timestamp do PostgreSQL já tem resolução em nanosegundos 🙂
Que conteúdo foda, me tirou várias dúvidas !
Que conteúdo de altíssimo nível 👏
Por favor Diegão, traz mais conteúdos técnicos como esse
Eu aqui me perguntando como que faz uma paginação, e o Daniel explicando isso no vídeo também, xô correr ali pro meu Backend rapidin hahahaha
Uso sempre o nanoid com 21 char, na minha opinião é o melhor dos mundos, a colisão aconteceria em ~41 milhões de anos com a inserção de 1.000 ids por segundo.
Considerações:
- Existem variações do UUID, e a versão 4 é ordenável.
- Indiferente de conter ou não na url um id amigável, é seu dever no backend fazer a segurança do acesso
- Para a maioria gigantesca das aplicações o custo extra de um id maior (tamanho de banco e etc) nunca será um problema
Muito bom, interessante e direto ao ponto.
Criei recentemente uma aplicação, e, na hora de discutir a estratégia de Id (as legadas usavam Identity/auto-increment, eu queria usar Guid), o DBA implicou com o Guid dizendo que, o fato dele não ser ordenável, traria uma perda de performance muito grande no BD. Acabei recorrendo ao ULID, tem suas desvantagens, principalmente por não ser muito popular, mas atendeu muito bem ao projeto. Dei uma olhada no snowflake mas o custo de implementação não valeria a pena.
2:50 esse ponto positivo de paginacão em sql não faz sentido, a maneira mais eficaz de paginar é utilizando OFFSET (Skip) e FETCH (Take) na consulta sql, o id não influencia em nada na paginacão, a não ser os caracteres a mais que irão ser retornado a mais na consulta caso seja usado guid/uid.
a partir do momento que você precisa fazer um SORT vc já acaba com a condição de "ordenável" da chave ID, afinal você obrigatoriamente vai aplicar uma ordenação por um campo no bd, e pra isso existe indexes
Olá, ainda estou a ver o vídeo muito obrigada
mas já tenho algumas perguntas !
O do snowflake usar o timestamp para ordenação não pressupõe o mesmo problema de repetição que tinha o create_at ?
Mesmo que depois sejam diferentes pela máquina ..
Depois, para evitar conflitos a 100%, não se poderia usar o username para gerar ese id, já que é único ?
Valeu mano
Muito bom
Simplesmente genial! 🙌
Vale adicionar que os uuid dao uma quebrada em index clusterizadas. Sql server tem o global uniqueidentifier que da uma mitigada nisso
Sei q o vídeo e sobre bancos relacionais e tal, mas qual sua opinião sobre o ObjectId do MongoDB? Será q ele é suficiente pra grandes projetos como um Twitter da vida, ou teríamos q usar um SnowflakeID também?
vc pode criptografar o id, para usuario e no backend descriptografa e busca os dados necessarios , uso assim no laravel
fica a mesma coisa no banco de dados e o usuario sempre irá ver criptografado
Mas ainda vai ter problemas de legibilidade e caso tu precise de alguma forma encontrar essa informação, tu vai ter que ter acesso a chave secreta da criptografia
Cara muito bom esse conteúdo !!!!!
"Onde é que começa essa desgraça?, onde é que termina essa desgraça?"
Fernandes, Diego - 2024
kkkkkkkkk!!!
Bem, acredito que houve uma simplificação ingênua na comparação de que a diferença entre armazenar um integer ocupa menos espaço que uma string.
Vários bancos de dados relacionais reservam espaço em disco sobre o tamanho da página que o registro ocupa, e não necessariamente o que está escrito dentro da página, portanto é uma falácia dizer que necessariamente por ter dados inteiros ou texto vão ocupar mais ou menos espaço. Espero que isso leve a mais pessoas pesquisarem sobre o tema (:
valeu Diego pela info top de mais
Não sei se a solução de pegar os últimos registros a partir da ordem dos registros funciona... E se já houver registros deletados?
Mas, com certeza, o espaço ocupado e o tempo de processamento contam bastante a favor do auto incremento.
Tem uma boa explicação do problema de se usar uuid no vídeo do Theo (th-cam.com/video/a-K2C3sf1_Q/w-d-xo.htmlsi=_NNKfuFI5o-x9jxz). Ele sugere o uso do nanoid.
Funciona porque é um cursor. Se tiver registro apagado depois do where id > ponteiro, o banco de dados vai contar normalmente apenas os registros que ele encontrou, retornando ao atingir o valor definido no limit ou ao esgotar as linhas da tabela. O cursor é apenas uma referência de onde você parou na última página, um ponto de partida.
kct, esse conteúdo foi foda
Qual seu Mac Diego?
Dito isso, usarei apenas ID e UUID juntos.
Solução, concatenar no UUID em algum lugar dele, um valor numérico ordenado e fragmentado entre as posições do UUID e coloca um pré processamento no back pra pegar de qual user estamos recebendo aquele UUID.
Por nada!
Galera por favor, me respondam onde é e quando acontecem essas lives de onde tiram esses cortes?
poderiam avisar por email/insta, as notificações da twitch não chegam para mim
Na Twitch, pow. No canal dele.
É avisado no discord, toda vez
Qual é o canal dele?@@ivambergsilva591
@@ivambergsilva591 Valeu mano, eu não tenho o hábito de usar muito o discord, raramente acessso, mas essas lives do Diego eu quero muito ficar acompanhando então vou seguir ele lá na Twitch também, muito obrigado!
o custo computacional de se criar um id é assim tão relevante? O snow flake parece bem completo, precisamos de tantas soluções? Me parece que criar uma coluna para ordenação é mais interessante, é mais simples e o custo computacional não é assim tão alto, mas não colocaria o nome de public_id, ter 2 ids parece confuso
Alguém tem um exemplo de cursor based pagination usando ulid ou outro id time sortable? Tentei mas n consegui 😅
2:45 substituir o offset por comparação com id numérico? E se os ids não forem contíguos? 🤔
Essa forma de paginar não é a ideial, ele meio que tentou forcar um ponto positivo que não existe. Uma paginacão bem feita voce ira utilizar OFFSET (skip) e FETCH (Take ).
Aula perfeita
Não é só utilizar um timestamp + nanoid, por ex?
Otimo conteudo pra mim que so usava ShortId() em tudo haha
Onde é feito essas lives?
Uma dúvida, mas se eu usar a opção where para fazer a paginação com o id não corre o risco de repetir o dado, pois algum desse registro pode ser apagado e essa sequência ser quebrada?
Qual essa ferramenta que ele usa para digitar na tela alguém sabe ? 😅
Confesso que não entendo muito bem a necessidade do id ser sortable. Podemos usar outro campo para ordenação que não o id ( ex. Data de criação)
É porque demora mais e alguém pode ter criado ao mesmo tempo, pelo id é mais difícil, pq é auto Incremento e também pra ordenar id custa menos, porque é número e é pequeno
Alguém sabe dizer onde o Diego grava essas lives?
Eu sei que é natural pensar que daria pra fazer paginação desse jeito aí (id > 980), mas na realidade não funciona porque muitas vezes teremos filtros aplicados.
cara qual app é esse q ele usa pra fazer notas e navegar ao mesmo tempo?
Vou ter que refatorar mais uma app....poxa Diegão 😂
muitas inserções seriam tipo quanto?
eu colocaria no mínimo na casa dos milhares para milhões em um certo período de tempo. Na empresa que trabalho, lidamos com mais de 15k inserções por minuto e isso não é muito se comparado com twitter, instagram, discord...
Depende da máquina, aplicação e banco. Mas vc pode tratar 100/200k por segundo como algo que já seria muito. Mas ainda sim não tão muito. Apenas algo p vc se preocupar c filas, pools e afins.
Caralho que AULA da porra
baita aula
F para eu com meus Guid em multitenant com uma base pra 100 cliente no momento =D
Seria bacana falar sobre o fato do next nao permitir cachear arquivos que são carregados dinámicamente durante a execução em produção. Sempre retorna erro 404, e para contornar o problema, precisa criar um servidor customizado... Chatao isso
youtu.be/gD_jNycK=1:00 Id legivel em url não é ponto positivo, muito pelo contrario, isso abre muita brecha para ataques.
gran video
"Eita..."' hahahahahah
Cara, pra que xingar?????
E qual é o problema??!
Sério cara? Então tá bom de voltar pro fundamental, pqp
@@odevrenan na grande maioria, minha filha de 5 anos está proximo. Não deu outra ela perguntou "Pai o que é !"#$"? Entendeu?
@@melkyvinicius6201 Não sei o que é prioridade para você, mas no dia que tiver uma filha e ela ouvir uma pessoa falando palavras que não é de comum, vai entender. Desejo o melhor para você.
Deus me livre 😂
Vou passar a odiar os benditos IDs 😅
Nem assisti o video porque UUID ou autoincrement NUNCA devem ser utilizados em um banco de dados, abraço.
O que deve ser usado então na sua opinião ?
Ué, tem dois ERP onde eu trabalho e são grandes internamente e usa autoincremente
@@Bruno-cg4vu Relaxa, o JonnyBorgesdev sabe o que 'e melhor para a gente.
A qualidade do codigo dele e alta, ou seja, esta alinhada com o tamanho do ego dele.
Poderia por gentileza nos mostrar a melhor solução?
falou "nunca" já sei que tá errado