Créditos: Vetor de tecnologia criado por pikisuperstar - www.freepik.com

Como desenvolvedores, muitas vezes nos encontramos em situa??es em que devemos construir algo, mas n?o temos tempo adequado para desenvolver da maneira que gostaríamos. E nem sempre podemos atrasar os prazos, porque o “ tempo de coloca??o no mercado ” às vezes desempenha um papel crucial no sucesso do produto. Ent?o, o que fazemos? Cortamos atalhos, assumimos riscos calculados, deixamos de lado o purista em você (melhores práticas, cobertura de teste de unidade e bla bla bla). Acho que seria terrivelmente semelhante para a maioria de vocês também.

A história de hoje é sobre como nós construímos uma alta escala , tolerante a falhas , distribuído sistema Leaderboard / Scoring, em cerca de tempo de uma semana em uma equipe de três pessoas.

Haverá principalmente esses baldes de aprendizagem neste blog

  1. Técnico : como você realmente constrói esse sistema, tópicos como design de sistema distribuído, escalabilidade, resiliência e disponibilidade devem ser cobertos.
  2. Trabalhar contra o tempo : como você entrega em um curto espa?o de tempo, que tipo de compensa??o você faz, como tomar decis?es mais rapidamente.
  3. Ciclo de vida de desenvolvimento : você também obtém uma prévia do ciclo de vida de desenvolvimento de produto, que tipo de coisas acontece na constru??o de um bom software.

Capítulo 1: Os requisitos

Tudo come?ou quando nossa equipe de produto disse que é a temporada da copa do mundo T20 e queremos construir um sistema de quiz para nossos usuários, para previs?o de curto prazo.

O caso de uso era que, no início de um over, os usuários seriam solicitados a prever um cenário para o qual teriam 20/30 segundos. E no final do over moderator estará submetendo, o que realmente aconteceu entre todos os cenários previstos. E a pontua??o funcionaria com base em quem respondeu corretamente e quanto tempo levou para responder.

Assim, imediatamente após obter o requisito, fizemos uma estimativa de esfor?o e isso claramente n?o estava cabendo em nosso or?amento, ent?o cortamos recursos que poderíamos pular na v0. Isso é importante porque em um prazo apertado você pode querer fornecer menos recursos do que fornecer recursos incompletos.

Este será um blog voltado principalmente para back-end, desculpe, n?o serei capaz de explicar como essas lindas UIs foram feitas.

Capítulo 2: Design

O próximo passo foi obviamente projetar o Sistema, que é popularmente conhecido como Design de Alto Nível. Essa foi a parte mais desafiadora e também a mais divertida para mim. N?o fizemos um design extenso de baixo nível e atendemos a todas as chamadas de modelagem durante a implementa??o.

Etapa 1: estimativa de escala

Antes de come?ar qualquer coisa, fizemos uma estimativa aproximada de que tipo de tráfego nos atingiria. Dada a escala do nosso sistema, estimamos que talvez 50 mil pessoas se engajar?o no questionário. Portanto, pretendemos construir para 100 mil usuários. Mas a maioria das pessoas provavelmente responderia nos primeiros 10 segundos em uma janela de 30 segundos. O que nos dá aproximadamente uma meta de qps de 20k.

Minha regra é que um novo sistema sempre projete o sistema para o dobro do número de usuários previstos. Para que caso você acabe tendo mais usuários o seu sistema n?o falhe em escalar. E os usuários geralmente crescem com o tempo, ent?o você n?o precisa ficar mudando o sistema constantemente. Mas isso n?o significa que você coloque o dobro da infraestrutura no lugar do que é realmente necessário. Eu normalmente teria o escalonamento automático habilitado em meus sistemas, ent?o sempre que houver picos de tráfego, o sistema se escalonará sozinho.

(Fizemos outras estimativas quanto ao armazenamento no cache também, mas as ignoramos para manter o artigo curto)

Etapa 2: Identificar APIs de alta escala

Após a estimativa de escala, identificamos rapidamente quais s?o as APIs de alta escala e onde o processamento poderia ser alto para que pudéssemos fazer um design escalável seletivamente para elas. O resto das APIs de baixa escala com as quais n?o nos importamos ou com as quais gastamos muito tempo.

Essas s?o as APIs de alta escala que identificamos

  1. Obtenha a pontua??o e a classifica??o do usuário
  2. Obter tabela de classifica??o
  3. Calcule a tabela de classifica??o (principalmente processamento de dados, n?o API)
  4. Postar resposta do usuário

Etapa 3: considera??es de design

Imediatamente após ver o requisito, duas coisas ficaram muito evidentes para mim.

  1. Precisaremos de processamento assíncrono e distribuído para cálculo de pontua??o e classifica??o pelos motivos mais óbvios. Se você está planejando executar o cálculo da pontua??o de forma síncrona em um único nó para 1 milh?o de usuários ou mais, boa sorte para você ??. A ideia é simples, dividimos uma grande tarefa em tarefas menores e as executamos em nós diferentes, e deixamos que fa?am isso em seu próprio ritmo. E também queremos que esse processo seja tolerante a falhas .
  2. Cache será nosso amigo para ler as classifica??es de um usuário e a tabela de classifica??o. Por duas raz?es principalmente, velocidade e facilidade de dimensionamento . Um cache é muito mais rápido que o banco de dados para opera??es de leitura simples e, geralmente, é mais fácil dimensionar o cluster Redis / Memcached / Hazelcast do que o Postgres .

Etapa 4: Projete o sistema

Ao tomar as decis?es de design desta vez, optei por ir com técnicos que eu conhecia e n?o queria me aventurar a encontrar o que poderia ser a melhor tecnologia para este caso de uso. Por exemplo, eu tinha familiaridade com o Redis , ent?o, para cache, era a escolha óbvia. Além disso, sempre que ou?o o placar, ele se traduz automaticamente em conjuntos classificados do Redis em minha mente. E para o processamento assíncrono, Kafka continua sendo minha escolha número um. Com o tempo adequado, provavelmente faria um pouco mais de explora??o, mas, por enquanto, n?o iria vagar por terras selvagens para encontrar a melhor tecnologia porque n?o tinha TEMPO !!!!

uma. API de resposta do usuário post

Portanto, essa API permitiria que nossos usuários enviassem respostas para o questionário. O principal desafio aqui era que isso geraria muitas opera??es de grava??o simultaneas , o que aumentaria muito a carga em nosso banco de dados. Ent?o tivemos que fazer duas coisas

  1. Diminuir a carga no banco de dados
  2. Gere algum tipo de contrapress?o ou deixe os operadores do banco de dados trabalharem em seu próprio ritmo, para que o banco de dados n?o seja sobrecarregado

Minha solu??o goto para diminuir a carga de grava??o é fazer lotes . Portanto, se eu tivesse que fazer 10 opera??es de grava??o, agruparia-as para obter uma única consulta e, em seguida, executaria 1 opera??o de grava??o de banco de dados.

E a contrapress?o quase grita filas de mensagens .

Combinando os dois, a solu??o que encontramos é esta ...

N?o se desespere, deixe-me explicar o que está acontecendo

  1. As respostas do usuário s?o recebidas pelo receptor de resposta e um código de status HTTP 202 é retornado. O que é como dizer que recebi sua solicita??o e vou processá-la, mas vá em frente e fa?a o que estava fazendo. Esta é a primeira etapa do processamento assíncrono, em que n?o bloqueamos o chamador.
  2. O receptor de resposta coloca a resposta do usuário em uma fila de mensagens, que é novamente particionada para fins de escalabilidade / disponibilidade / redundancia . Você pode entender o particionamento com bastante facilidade se já conhece Kafka. Caso n?o o fa?a, apenas considere que é uma forma de distribuir suas mensagens em sua fila em várias filas menores isoladas que podem residir tecnicamente em nós diferentes. Se você conhece a fragmenta??o de banco de dados , é a mesma coisa, mas principalmente para filas de mensagens. Sinta-se à vontade para ler mais sobre Kafka aqui .
  3. Agora, essas respostas brutas s?o recebidas pelo batcher. Em seguida, ele cria lotes de 10 mensagens e os envia para o próximo estágio de processamento.
  4. O gravador do banco de dados pega os lotes e faz consultas de inser??o no banco de dados. A contrapress?o é introduzida principalmente pelo gravador DB, ele pega as mensagens em seu próprio ritmo, já que o consumidor da mensagem era baseado em pull . E assim evitamos a sobrecarga do banco de dados. E como ele está trabalhando em lotes em vez de executar 100 consultas de banco de dados, executamos apenas 10 consultas de banco de dados.

Isso resolve 30% do nosso problema, vamos pular para o próximo.

b. Pontua??o e cálculo da tabela de classifica??o

Agora, o elefante na sala, o maior problema, o cálculo do placar. Se você vir este sistema, n?o é como um sistema de questionário tradicional, em que sabemos a resposta correta de antem?o. Portanto, n?o podemos calcular as pontua??es e o placar assim que alguém responde. Temos que calcular a pontua??o e a classifica??o de todos os usuários assim que o moderador enviar as respostas corretas. Portanto, um grande peda?o de trabalho de uma só vez. é bastante evidente que nem nossos nós nem nosso servidor de banco de dados podem lidar com isso adequadamente em uma sincroniza??omoda. Ent?o, o que fazemos? Voltamos às nossas filas de mensagens de amigo para processamento assíncrono novamente. Legal para que possamos calcular as pontua??es de forma assíncrona, mas e o placar? Isso precisa estar disponível o tempo todo, certo? E a classifica??o? Até e a menos que as pontua??es de todos os usuários tenham sido calculadas, você n?o pode realmente colocar as classifica??es, certo? E calcular a classifica??o especificamente pode ser um problema difícil.

Agora, quem vai nos salvar disso? N?o se preocupe, meu amigo, lembra que mencionei o Redis brevemente ao falar sobre cache? Eles têm uma coisa linda chamada conjunto ordenado (que cria??o incrível, obrigado Redis Labs ??). Em um conjunto classificado, você pode adicionar chaves com uma pontua??o e o Redis irá ordená-la de acordo em O (log (N)) . Isso resolverá nosso problema de classifica??o ??. Ele também nos permite executar consultas de intervalo, como me dê os 5 primeiros, ou me dê a classifica??o para uma chave específica, e tudo isso acontece em O (log (N)). Isso é exatamente o que precisamos aqui.

Os elementos s?o adicionados a uma tabela hash que mapeia objetos Redis para pontua??es. Ao mesmo tempo, os elementos s?o adicionados a uma lista de ignorar pontua??es de mapeamento para objetos Redis (portanto, os objetos s?o classificados por pontua??es nesta "visualiza??o") - Conjunto interno ordenado

Bammmmmm o problema da tabela de classifica??o também está resolvido.

Tudo bem, n?o é fácil. Fiquei muito feliz por ter conseguido uma solu??o viável rapidamente. Agora vamos pular de volta para nossa prancheta de desenho.

Parece um pouco intimidante, n?o? Deixe-me explicar

  1. Assim que o moderador envia a resposta correta, uma mensagem de gatilho de cálculo de pontua??o é enviada, que é para iniciar todo o pipeline de processamento .
  2. O batcher recebe a mensagem de gatilho e gera um par de offset DB e objeto de limite dependendo de quantas pessoas responderam corretamente. Por exemplo, se 10 pessoas respondessem corretamente e o tamanho do lote fosse 5, seriam gerados dois objetos (lotes). Lote 1 {deslocamento: 0, limite: 5}, lote 2 {deslocamento: 5, limite 5}. porque nós fazemos isso? Para que possamos executar o processamento em lote ou executar consultas paginadas ao banco de dados e n?o acabar chamando o banco de dados sem qualquer limite. Portanto, se eu tivesse que obter 1 milh?o de registros do banco de dados e fizer isso de uma só vez, haveria muitos problemas em muitos lugares. Ent?o, dividimos isso em partes menores e executamos consultas menores, mas múltiplas, que retornariam um número menor de linhas.
  3. O processador de lote do usuário agora receberá essas mensagens em lote e executará as consultas do banco de dados de acordo. O processador que recebe a mensagem {offset: 0, limit: 5}, obterá os primeiros 5 ids de usuários do banco de dados (fará outra opera??o em lote também, mas isso é um pouco difícil de explicar aqui, ent?o pule). E depois disso, dizemos adeus ao processamento em lote e alternamos para o processamento em fluxo . Porque o processador de lote agora colocará 5 IDs de usuário na fila que ser?o processados ??pelo próximo processador.
  4. Agora, a calculadora de pontua??o do usuário recebe ids de usuários individuais e executa a lógica de pontua??o para calcular as pontua??es de usuários individuais. Em seguida, fa?a 1 atualiza??o do banco de dados para modificar a pontua??o do usuário. Em seguida, ele atualiza a pontua??o desse usuário específico no conjunto classificado e o Redis atribui ou atualiza internamente a classifica??o. E uma vez finalizado o processamento dessa etapa, teremos as pontua??es de todos os usuários de nosso banco de dados e a classifica??o + pontua??o de todos os usuários de nosso Redis. E como temos a classifica??o de todos no conjunto classificado, poderíamos simplesmente executar uma consulta de intervalo para obter a tabela de classifica??o com uma velocidade extremamente rápida .

A maior parte do nosso problema está resolvido agora, pois para obter a pontua??o e a classifica??o do usuário, poderíamos apenas fazer uma consulta do Redis e n?o chegar ao banco de dados. E isso também torna nossos tempos de resposta mais rápidos .

Isso conclui a fase de design principal. Havia também banco de dados, design de API e outras coisas que estou pulando aqui.

Capítulo 4: Implementa??o

A conclus?o do projeto resolveu 70% dos nossos problemas e sabíamos que poderíamos resolver isso, ent?o iríamos pular para o desenvolvimento rapidamente.

Em um mundo ideal, eu iria criar um novo servi?o, experimentar uma nova linguagem como Go , para um processamento paralelo melhor e mais rápido e outras coisas. Mas, dada a linha do tempo, n?o era a coisa certa a se fazer. Nós nos prendemos ao nosso servi?o NodeJS principal e colocamos tudo lá. Os puristas do microsservi?o podem perder o controle depois de ver esta declara??o, mas em uma corrida contra o tempo, seus diretores às vezes precisam ficar em segundo plano. Entre as muitas desvantagens , esta foi uma das principais liga??es que recebemos.

Apart from this, we also had to cut down on unit and integration tests, the guilt of which is still haunting us. But we are backfilling the tests gradually post-release.

I guess after seeing the detailed design posted above you should be able to implement your own, hence I am not gonna do a code deep dive this time ??

Chapter 5: Deployment and Monitoring

After a few bug fixes and QA sign-off, we were good to go. Job done right? No, my friend we still had to set up heavy monitoring for this piece. Since it was developed in a very short time I at least was a little underconfident. We by default had tracing enabled on this service via LightStep. So apart from traces, I had set up dedicated monitoring of traffic, error rates, latency dashboards, alerts for all the APIs. And post go-live I and my teammates, we got onto a call and we monitored the system in and out for at least an hour, from RAM and CPU usages to Error logs. So always give equal weightage to observability and monitoring as well. There were small issues on the production system and we were only able to catch them early because of monitoring.

Chapter 6: Retrospective

The system works, but after a breather, it’s important to do a retrospective and identify things that we missed and work upon them. I am sure we missed a ton of stuff and cut a lot of corners and got a huge scope of improvement. For example here are a couple of…

Things we could do better

  1. We used the already existing Postgres DB for this since the driver, ORM and the supporting infrastructure were already there. But I would probably explore a bit on the database solutions.
  2. NodeJS is awesome, but I feel Go would be a better fitting solution for this. We could have explored this.
  3. I tried writing a query to calculate the score in the DB only and failed miserably. I could probably write that and could do batch processing for score calculation as well, reducing the DB operations even further.
  4. We could not run extensive load and performance tests, which is a must.
  5. We could have written two different stages for DB score update and Redis sorted set update, that would be a cleaner implementation.

Parting notes

We did the best we could in that short time. Even the implementation diverted slightly from the original design. But it’s okay, trade-offs are constantly going to be there. Even though we completed the core functionality in a week approximately, there were small patches that we had to do post that.

I hope you were able to learn a thing or two about system design and software development today ??

Credits

Shout out to my awesome teammates Akash Raj and Aashirwad Kashyap, we all worked together to build this in just about a week.

Thanks for reading!

I am Aritra Das, I am a Developer, and I really enjoy building complex Distributed Systems. Feel free to reach out to me on Linkedin or Twitter for anything related to tech.

Happy learning…

Suggested posts

6 principais vantagens dos desenvolvedores da Europa Oriental

6 principais vantagens dos desenvolvedores da Europa Oriental

Compreendendo por que empresas estrangeiras est?o procurando contratar desenvolvedores da Rússia, Ucrania e Bielo-Rússia Por mais de 6 anos, gerencio o Desenvolvimento de Software da Rocketech com um parceiro, com sede em Cingapura e uma equipe totalmente distribuída. Estamos desenvolvendo produtos de TI e desenvolvendo dois formatos de servi?o: outstaff e Dedicated Team.

Você deve randomizar seu fluxo de trabalho, e aqui está o porquê

Sou uma daquelas pessoas que constantemente procura a melhor maneira de fazer as coisas. Planejamento, Pomodoro, listas de afazeres, agendamento ... você escolhe, provavelmente já experimentei.

Related posts

IA em smartphones ??

IA em smartphones ??

Os smartphones evoluíram com o tempo e continuam a ser o dispositivo mais popular do mercado. No entanto, nos últimos anos, a inteligência artificial tem despertado o interesse das pessoas.

Pessoas pobres n?o merecem ser felizes

Porque se eles est?o felizes, como podemos ser gratos?

Pessoas pobres n?o merecem ser felizes

Que sentimentos passou pela sua cabe?a ao ler o título deste artigo? Nervoso? Incomodado? Assustado? “Como alguém se atreve a escrever isso ?!” N?o, isso n?o é escrever para desacreditar os pobres, muito pelo contrário. Também n?o estou escrevendo sobre crian?as hospedadas que precisam comer macarr?o instantaneo no final de cada mês.

Acompanhe os seus passos de bebê - Que a??o inspiradora você está realizando hoje?

Acompanhe os seus passos de bebê - Que a??o inspiradora você está realizando hoje?

Acompanhe seus passos de bebê Uma frase ficou presa no abismo hipnotizante da minha mente: “Se você n?o marcar pontos, como saberá que está ganhando?” Depois de ouvir isso, meu consciente, subconsciente e inconsciente estavam dan?ando e festejando como se o mundo tivesse acabado de ser revelado para mim. Se eu N?O mantiver a pontua??o, como diabos vou saber que estou pelo menos progredindo? A resposta é N?O.

Assuma o controle de seus aplicativos de mensagens

Assuma o controle de seus aplicativos de mensagens

Tenho tendência a cair na desorganiza??o. Ent?o, eu gosto de um sistema.

MORE COOL STUFF

O treinador de basquete do Duke Blue Devils, Mike Krzyzewski, é casado?

O treinador de basquete do Duke Blue Devils, Mike Krzyzewski, é casado?

A aposentadoria de Mike Krzyzewski do basquete Duke no final da atual temporada lhe dará mais tempo com sua esposa e família.

Qual é a altura de Nicholas Braun em 'Sucess?o'?

Qual é a altura de Nicholas Braun em 'Sucess?o'?

Os f?s de 'Succession' n?o podem deixar de notar a altura incomum de Greg, também conhecido como Nicholas Braun. Ele realmente se eleva acima dos membros do elenco?

"The Pioneer Woman" Ree Drummond Pratos do Dia de A??o de Gra?as para a temporada de férias de 2021

A Pioneer Woman Ree Drummond está aqui para prepará-lo para o Dia de A??o de Gra?as. Aqui est?o alguns de seus melhores acompanhamentos.

Por que Lady Gaga usou um vestido à prova de balas para esta apresenta??o

Por que Lady Gaga usou um vestido à prova de balas para esta apresenta??o

Na posse do presidente Biden, o vestido à prova de balas de Lady Gaga faz uma declara??o se você concorda com ela ou n?o.

Experimente nossas mini palavras cruzadas

Experimente nossas mini palavras cruzadas

Atualizado semanalmente, nossas mini palavras cruzadas combinam nossas leituras favoritas do HowStuffWorks com pistas inteligentes!

O que funciona melhor: cápsulas de lavanderia, detergentes em pó ou líquidos?

O que funciona melhor: cápsulas de lavanderia, detergentes em pó ou líquidos?

Lavar roupa já é ruim o suficiente sem ter que se preocupar em escolher o detergente certo. Ent?o, qual é o melhor? Ou isso importa?

A verdadeira história do povo azul de Kentucky

A verdadeira história do povo azul de Kentucky

As famílias Fugates e Combs na zona rural de Kentucky perderam a loteria genética, ambos compartilhando um raro tra?o recessivo que fazia sua pele parecer azul quando eles se casaram. Qual foi a causa disso? E o que aconteceu com as famílias?

O 'nascimento virginal' da California Condor poderia resgatar as espécies?

Dois filhotes sem pai est?o sendo criados em um programa para salvar o condor da Califórnia da extin??o. Como esses nascimentos 'virgens' s?o possíveis?

Por US $ 125.000, você pode comprar um Monster Truck em miniatura para seu filho

Por US $ 125.000, você pode comprar um Monster Truck em miniatura para seu filho

Todos nós sabemos o que significa mimado, mas para a defini??o mais verdadeira da palavra, você n?o precisa ir mais longe do que este monster truck em miniatura projetado para crian?as que é movido por um motor Ford real de quatro cilindros que o leva a uma velocidade máxima de 25 milhas por hora. é aproximadamente metade do tamanho de verdadeiros monster trucks como Bigfoot e Grave Digger, e é feito sob medida com uma estrutura de rolo de tubo de a?o de duas polegadas contínua que é forte o suficiente para resistir a quedas e capotamentos.

Assista a esta introdu??o confidencial ao Edsel, apenas 60 anos tarde demais

Assista a esta introdu??o confidencial ao Edsel, apenas 60 anos tarde demais

Em um ponto, o narrador neste filme promocional de pré-lan?amento secreto de 30 minutos para o Edsel diz "Edsel: o carro que já está fazendo história automotiva para a Ford Motor Company!" Essa é uma declara??o muito presciente. O Edsel fez absolutamente história automotiva.

A produ??o de carros da América está mudando lentamente para o México

A produ??o de carros da América está mudando lentamente para o México

Bom Dia! Bem-vindo ao The Morning Shift, seu resumo das notícias automobilísticas que você tanto deseja, tudo em um só lugar, todas as manh?s da semana. Aqui est?o as histórias importantes que você precisa saber.

O filme animado do Batman e Harley Quinn está tendo sua própria série de quadrinhos

O filme animado do Batman e Harley Quinn está tendo sua própria série de quadrinhos

Imagem: DC Comics Warner Bros. ' O último filme animado da DC, Batman e Harley Quinn, se passa em um mundo onde Harley deu as costas ao Coringa, apenas para ser amarrada ao mundo das capas e fantasias mais uma vez para ajudar Batman a salvar o mundo de Poison Ivy.

Kulture, filha de Cardi B e Offset, mostra lindas tran?as novas no Instagram

Kulture, filha de Cardi B e Offset, mostra lindas tran?as novas no Instagram

A filha de 3 anos de Cardi B e Offset, Kulture, exibiu seu novo penteado tran?ado no Instagram.

Selena Gomez dá um beijo na bochecha de Cara Delevingne por Kiss Cam no Knicks Game

Selena Gomez dá um beijo na bochecha de Cara Delevingne por Kiss Cam no Knicks Game

"Ela é t?o divertida e extremamente aventureira", Selena Gomez disse anteriormente sobre a amiga Cara Delevingne

Jamie Dornan diz que perdeu o papel de super-homem para Henry Cavill e abordou a Marvel para um papel de super-herói

Jamie Dornan diz que perdeu o papel de super-homem para Henry Cavill e abordou a Marvel para um papel de super-herói

Jamie Dornan revelou que fez o teste para o papel de Superman, mas perdeu para Henry Cavill; e ele falou com a Marvel sobre se juntar ao MCU.

Meghan Markle relembra seu corte de cabelo de infancia inspirado em Andie MacDowell: 'I Was Obsessed'

Meghan Markle relembra seu corte de cabelo de infancia inspirado em Andie MacDowell: 'I Was Obsessed'

'Todo mundo se esqueceu de me dizer,' Você tem cabelo étnico '', disse Meghan Markle no The Ellen Degeneres Show, ao relembrar seu corte de cabelo de infancia, inspirado por Andie MacDowell em Four Weddings and a Funeral.

Languages

野花在线观看免费观看大全-野花视频在线观看免费观看8
国足最新出线概率0.08% 北京冬奥火炬宣传片获金花环奖 速度与激情9 得知母亲出事男子在地铁痛哭 国足战澳大利亚大名单:4归化在列 周冠宇成为中国首位F1车手 安娜贝尔 尚气与十环传奇 胡锡进谈中美元首会晤 红色通缉令 尚气与十环传奇 印度首都准备封城 房价上涨城市创七年新低 拐点来了? 24岁救人牺牲消防员获批为烈士 扫黑风暴 我要我们在一起 意大利错失直接晋级世界杯资格 中美元首会谈重点内容 中国共产党第三个历史决议全文发布 灵媒 意大利错失直接晋级世界杯资格 俄方回应卫星碎片危及国际空间站 中美元首是否达成新共识?中方回应 男子写80页PPT拯救爱情却离婚 动保组织向上饶信州区申请信息公开 许家印为恒大注入超70亿续命资金 动保组织向上饶信州区申请信息公开 千与千寻 意大利错失直接晋级世界杯资格 两个女人 浦发银行回应近3亿存款莫名被质押 罗永浩吐槽苹果文案没文化 大连现超级传播者26人在同一传播链 扫黑风暴 安娜贝尔 中美元首会谈重点内容 长津湖 图兰朵 24岁救人牺牲消防员获批为烈士 房价上涨城市创七年新低 拐点来了? 五个扑水的少年 大连一密接者擅自点外卖聚餐被调查 男子写80页PPT拯救爱情却离婚 #耿直真香哥黑化卖惨# 动保组织向上饶信州区申请信息公开 扫黑风暴 失控玩家 扫黑风暴 许家印为恒大注入超70亿续命资金 外交部回应拜登重申不支持台独 加拿大一枝黄花到底是什么? 中国医生 男子体检血中抽出2升油浆 红色通缉令 大连现超级传播者26人在同一传播链 国际人士热议中共十九届六中全会 俄方回应卫星碎片危及国际空间站 怒火·重案 得知母亲出事男子在地铁痛哭 嘉南传 中美元首是否达成新共识?中方回应 浦发银行回应近3亿存款莫名被质押 斗破苍穹 蜘蛛侠:英雄归来 扫黑风暴 林丹世界排名被正式移除 男子体检血中抽出2升油浆 大连现超级传播者26人在同一传播链 扫黑风暴 林丹世界排名被正式移除 国足战澳大利亚大名单:4归化在列
搜索| 百色市| 湟中县| 巫溪县| 清镇市| 文成县| 安化县| 布拖县| 蚌埠市| 禹州市| 云龙县| 永年县| 柘荣县| 定远县| 屏南县| 永康市| 正阳县| 霍山县| 墨玉县| 渭南市| 新绛县| 无极县| 叙永县| 汾阳市|