Ok, vamos dividir:
- Como as junções são construídas entre duas tabelas em vários bancos de dados? (Um exemplo de código aqui seria útil).
Isso é bem direto. Os Objetos SQL possuem de uma a quatro partes:
Servername.databasename.schemaname.tablename
Se todas as suas tabelas estiverem no mesmo servidor no mesmo banco de dados, com o mesmo proprietário / esquema, você poderá ignorar as três primeiras partes e usar o que está mais acostumado:
Select a.*,b.* from
tableA a inner join
tableB b on a.col1=b.col1
Se uma de suas tabelas estiver em um banco de dados diferente e ambas usarem o esquema padrão para seus bancos de dados, basta adicionar o banco de dados à segunda tabela:
Select a.*,b.* from
tableA a inner join
databaseC..tableB b on a.col1 = b.col1
Se você estiver em um terceiro banco de dados diferente de qualquer um dos que você está consultando, use os dois nomes de banco de dados explicitamente:
Select a.*,b.* from
databaseD..tableA a inner join
databaseC..tableB b on a.col1 = b.col1
Se você acabar usando diferentes esquemas e / ou proprietários, poderá adicioná-los em:
Select a.*,b.* from
databaseD.john.tableA a inner join
databaseC.accounting.tableB b on a.col1 = b.col1
Por fim, se você for muito cuidadoso e tiver um bom motivo, poderá ingressar em uma tabela (geralmente pequena) em outro servidor:
Select a.* from
databaseD.john.TableA a inner join
ATLANTA.databaseC.accounting.tableB b on a.col1 = b.col1
- Quando é hora de ir além de uma configuração de 1 banco de dados / 1 servidor? Quão comum é fazer isso? Existem estratégias especiais para rastrear quais tabelas estão em qual banco de dados?
Vou combinar esses dois porque eles vão juntos. Você geralmente quase sempre está bem em começar com a suposição de que um servidor de banco de dados e um servidor é suficiente até que suas restrições de design / negócios / técnicas o forcem a usar mais.
Portanto, para responder à sua segunda pergunta primeiro, como você geralmente tem um motivo para ter bancos de dados separados, deve ser bastante óbvio conhecer o design do seu sistema onde algo está.
Quanto a quando / por que é necessário ir além de um único banco de dados. Geralmente, é uma mistura de regras de negócios, políticas e / ou razões técnicas.
Por exemplo, onde trabalho, temos 16 bancos de dados espalhados por 4 servidores. Temos um MainDB, ImageDB, referencetableDB, HighvolumeTransactionDB, ReportingDB, StagingDB, ProcessingDB, ArchiveDB, FinancialDB. Para dar alguns exemplos de por que eles são diferentes:
- FinancialDB, informações confidenciais
- DB de imagem, diferentes requisitos específicos de armazenamento e recuperação
- ReferênciaDB, baixa transação, alta leitura
- O ReportingDB, leitura muito alta, precisa ser restaurado / replicado para vários outros ambientes, ao contrário de muitos outros dados
- StagingDB, nada permanente, apenas um tempdb reforçado que temos mais controle sobre
- O MainDB faz interface com todos os outros bancos de dados, mas precisa de backups diferenciais, então ... dividimos o
- As tabelas HighVolumeTransaction (que são relativamente transitórias) para seu próprio banco de dados para manter o tamanho razoável do backup.
- Arquivar, muitos dos mesmos dados de Principal e de Relatórios, mas com períodos de retenção mais longos e consultas mais difíceis, aprofundando os dados. Se isso ainda fosse combinado com Principal / Relatórios, atrapalhava nosso sistema.
• O código do aplicativo precisa saber que um ou mais bancos de dados estão espalhados por vários servidores? Caso contrário, em que nível as solicitações são filtradas?
Em um sentido amplo, eles provavelmente o fazem. No mínimo, eles precisam saber em qual servidor estão apontando na cadeia de conexão do banco de dados. Processamento, geração de relatórios, principal etc.
A partir daí, eles precisam de um contexto de banco de dados para executar. Geralmente, esse seria o mais usado para o aplicativo, talvez até o original do banco de dados / um servidor dias do aplicativo. Você PODE ter o aplicativo alternar explicitamente o contexto do banco de dados em todas as chamadas, mas isso dificulta o ajuste do banco de dados sem alterar o aplicativo.
A abordagem usual (ou pelo menos a MY usual) é sempre acessar por um ou talvez dois bancos de dados principais.
Em seguida, crie visualizações em outros bancos de dados conforme necessário, combinados com a interface com o banco de dados através de procedimentos armazenados.
Então, para ilustrar:
Digamos que você deseja obter as informações demográficas, dados de vendas e saldo de crédito de um cliente, distribuídos por três tabelas originalmente todas no MainDB.
Então você escreve uma chamada a partir do seu aplicativo:
Select c.ClientName, c.ClientAddress, s.totalSales,f.CreditBlance from
Clients c join Sales s on c.clientid = s.clientid inner join AccountReceivable f on
c.clientid=f.clientid where c.clientid = @clientid
Impressionante. No entanto, agora, sempre que alterar um nome de coluna ou renomear / mover uma tabela, você deverá atualizar o código do aplicativo. Em vez disso, fazemos duas coisas:
criar clientes, vendas, visualizações de contas a receber (você não usaria o Select *, mas estou demonstrando aqui)
Use MainDB
GO
Create view v_Clients as select * from Clients
Create view v_Sales as select * from Sales
Create view v_AccountReceivable as select * from AccountReceivable
Go
Em seguida, também criaríamos um procedimento armazenado, spGetClientSalesAR
Create proc spGetClientSalesAR @clientID int
as
Select c.ClientName as ClientName,
c.ClientAddress as ClientAddress,
s.totalSales as TotalSales,
f.CreditBlance as CreditBalance
from
v_Clients c join v_Sales s
on c.clientid = s.clientid
inner join v_AccountReceivable f
on c.clientid=f.clientid
where c.clientid = @clientid
E faça com que seu aplicativo ligue para isso.
Agora, desde que eu não mude a interface nesse proc armazenado, posso fazer praticamente qualquer coisa que precise fazer no banco de dados de back-end para aumentar ou diminuir a escala.
No extremo, eu poderia até tornar meu MainDB antigo apenas um monte de procedimentos e visualizações armazenados em shell, de modo que, por baixo das visualizações que criamos, parecesse o seguinte:
Create view v_Clients as select * from ServerX.DatabaseY.dbo.Clients
Create view v_Sales as select * from ServerQ.DatabaseP.dbo.Sales
Create view v_AccountReceivable as select * from ServerJ.DatabaseK.dbo.AccountReceivable
E seu aplicativo nunca saberia a diferença (assumindo canais rápidos e dados bem preparados, entre outras coisas).
Obviamente, isso é extremo e eu mentiria se dissesse que tudo foi planejado dessa maneira, mas o uso de procedimentos / visualizações armazenados, mesmo que você o faça durante a refatoração, permitirá muita flexibilidade à medida que o aplicativo cresce a partir de um humilde banco de dados / servidor. começando.