Hva er portkartlegging? Datamigrasjonsteknologi i store prosjekter

Problem

Du har lastet opp en regnskapsutgiftsrapport og ønsker å vise den til ledelsen. For å gjøre dette må du kombinere dataene til regnskapsartikler - i henhold til. Du vet hvordan BU- og CU-artiklene forholder seg til hverandre, men hver gang tar det deg for mye tid å utarbeide en slik rapport manuelt.

Løsning

Vi vil vurdere denne saken som en fortsettelse av den forrige. La oss forestille oss at du har laget følgende referanse i Excel:

Figur 2.1. Katalog: kartlegging av BU- og UU-artikler


Til venstre er en kostnadspost (BU), til høyre er en post for administrasjonsregnskap (CU). Det er viktig at kostnadsposten kun vises én gang i den første kolonnen, ellers vil ikke kartleggingsmekanismen fungere som den skal.

(Det engelske ordet mapping er forresten oversatt med kartlegging eller korrespondanse, så oppslagsverket i dette tilfellet er en slags generell regel for hvordan BU-artiklene finner sin kartlegging i UU-artikkelen).

Figur 2.2. Flat tabell: utgiftsrapport (fra "Kontoomsetning 20")


Merk at i 7. kolonne har kolonnen "UU-artikkel" dukket opp. Overfor hver kostnadspost legger vi ned en post med administrasjonsregnskap. Dette kan gjøres manuelt, men det er mye mer praktisk å bruke dette verktøyet:

Figur 2.3. Flat tabell: utgiftsrapport (fra "Kontoomsetning 20")


Nederst i skjemaet er navnene på sidene angitt: "Hoved" er en flat tabell som inneholder data om kostnader (fig. 2.2), "ref" er en oppslagsbok (fig. 2.1).

Kolonnenummer er angitt øverst i skjemaet. Så i dette tilfellet, hvis dataene i kolonne 1 i referanseboken og 3 på hovedsiden er de samme, kopieres dataene fra 2. kolonne i referanseboken til 7. kolonne på hovedsiden.

Det er også mange tilleggsalternativer i dette skjemaet. For eksempel kan du aktivere avmerkingsboksene "Funksjon # 2" og "Funksjon # 3", og deretter vil overføring av data fra kolonne 2 i oppslagsboken til kolonne 7 på hovedsiden være mulig dersom referansen og hovedsiden sammenfaller i to eller til og med tre attributter samtidig.

Som et resultat av en så enkel operasjon, ved hjelp av pivottabellen, kan du bygge en rekke forskjellige analytiske rapporter, der en av kuttene vil vises på analytikeren "UU-skolen". For eksempel noe som dette:

Figur 2.4. Rebar Shop kostnadsrapport


Sammenligning av kartlegging med VLOOKUP ()

Mange brukere er kjent og bruker funksjonen VLOOKUP () i slike situasjoner. Imidlertid fungerer VLOOKUP ()-funksjonen bra bare på små mengder data, mens dette skjemaet gjør en utmerket jobb med å behandle Excel-regneark, selv om du har for eksempel 5000 rader i referansen og 300 000 rader på neste side. Prøv å sjekke, og du vil se at VLOOKUP () mislykkes på slike volumer. I tillegg skaper funksjonen VLOOKUP () en betydelig belastning på Excel, og tvinger den til å utføre store mengder beregninger. Kartleggingsskjemaet unngår denne ulempen: det starter en gang, varer i flere sekunder (i store mengder minutter), og etter det opprettes ingen ekstra belastninger på Excel-filen.

I denne artikkelen ønsker vi å systematisere vår erfaring med datamigrering i store bedriftsprosjekter knyttet til overgangen til kunder til å jobbe i 1C: Enterprise 8-konfigurasjoner.

I dette tilfellet vil hovedvekten i artikkelen først og fremst legges på den teknologiske komponenten i migrasjonsprosessen. Den organisatoriske komponenten påvirkes også, men i mindre grad.

Begreper og definisjoner

Ved datamigrering er det vanlig å forstå den endelige arbeidsrekkefølgen, et prosjekt rettet mot en engangs massiv overføring av data fra kildesystemer (historiske systemer) til et mottakssystem. I dette tilfellet avsluttes driften av disse dataene i kildesystemene.

Skille datamigrering fra dataintegrasjon. Integrasjon, i motsetning til migrering, er en permanent del av IT-arkitekturen, og er ansvarlig for flyten av data mellom ulike systemer og datalagre – og er en prosess, ikke en prosjektaktivitet.

Generelt ser migrasjonsordningen slik ut:

Ris. 1

Historiske systemer- databaser over Kundens selskap, som planlegges helt eller delvis erstattet ved innføring av nytt system.

Mottakersystem- målsystem, vilkårlig konfigurasjon "1C: Enterprise 8".

Innledende data- data lastet ut fra historiske systemer til et vilkårlig xls-filformat. I dette tilfellet ser xls-formatet ut til å være et av de mest praktiske, siden muligheten til å laste opp til en xls-fil er tilstede i mange regnskapssystemer fra "tidligere generasjoner".

Det er mulig å betrakte xml-filformatet som et moderne alternativ som transport.

Det er også muligheter for bruk av iscenesettelsesdatabasen.

Transformasjon, konvertering- prosessen med å konvertere rådata til data for lasting. Datatransformasjon skjer i henhold til malene for lasting. Transformasjonen resulterer i data for lasting.

Last ned data- data beregnet for å lastes inn i mottakssystemet. I denne artikkelen, så vel som de originale dataene, vurderes xls-formatet.

Datamaler for å laste ned- en beskrivelse av datatabellene som skal lastes inn i målsystemet.

Migrasjonsstadier

La oss vurdere trinn for trinn prosessen med å forberede og gjennomføre migrering.

De organisatoriske stadiene av migrasjonen inkluderer følgende punkter:

· Definer en migrasjonsstrategi. På dette stadiet er Leverandøren og Kunden enige om teknologien for å utføre migrasjonsarbeid;

· Fastsettelse av sammensetningen av arbeidsgruppen om migrasjon. Arbeidsgruppen bør omfatte spesialister fra både Leverandøren og Kunden, som er tilstrekkelig kjent med driften av historiske systemer (fra Kundens side) og målsystemet (fra Leverandørens side);

· Foreløpig migrasjonsplan. Migrasjonsplanen vil bli justert flere ganger i løpet av prosjektet;

· Perioder med datoer for utlasting av data fra historiske systemer, datavolumer. Datasnittperioder for migreringer, datoer for test og endelige migreringer. Denne informasjonen kan tilskrives migrasjonsplanen;

· Sammensetning av data som skal migreres. Referansedata, klassifiserere, transaksjonsdata, saldoer, omsetninger, etc .;

· Problemer med å kontrollere kvaliteten, riktigheten og integriteten til data under migrasjonsprosessen og på slutten;

· Problemer med å rulle tilbake til en tidligere tilstand i tilfelle feil.

La oss dvele mer detaljert på de teknologiske stadiene av migrasjon.

Ris. 2

1. Forberede maler for datalasting

En datalastmal inneholder tekniske beskrivelser av datatabellene for lasting, algoritmer og innlastingsregler for gjeldende mal.

Hver mal er generelt ment for én eller flere relaterte tabeller på målmålsystemet.

Malen angir:

Beskrivelse av alle feltene i xls-datafilen som skal lastes, inkludert:

o Feltnavn

o Tegn på obligatorisk utfylling av feltet

o Eksempel på utfylling av feltet

o Merk

Beskrivelse av reglene for lasting av tabellen til målsystemet basert på dataene for lasting (rekkefølge i tilfelle av flere relaterte tabeller, søkealgoritmer for nøkkelfelt, etc.)

· Beskrivelse av å fylle ut feltene i tabellene til målsystemet direkte i tilfelle noe annet enn å overføre data "en til en" fra datafilen for lasting er tenkt. Relevant for referansefelt, for eksempel.

I løpet av arbeidet med denne fasen skal entreprenøren også klargjøre en loader for datafiler for lasting. Når det gjelder arbeid med xls-filer, er ikke denne oppgaven spesielt vanskelig.

2 identifiserende datakilder

Dette trinnet kan starte sammen med forrige trinn "1. Forbereder maler for datalasting ".

Som en del av dette stadiet bestemmer Kundens spesialister fra hvilke systemer og hvilke data som kan lastes ned. Du bør også bestemme hvilke data Kan være kan være nødvendig.

Som regel, i store migrasjonsprosjekter, kan identifisering av en fullstendig uttømmende liste over datakilder ta ganske lang tid og skjer mens du arbeider i påfølgende stadier.

Det er ikke uvanlig i situasjoner der, for å sikre integriteten til informasjon i fremtiden, noen data må overføres fra trykte kilder (digitalisert) eller til og med legges inn i tabeller fra ordene til kundens nøkkelmedarbeidere.

På dette stadiet bør du imidlertid prøve å identifisere så mye av de nødvendige dataene som mulig.

3. Laste ned rådata

Prosessen med å laste ut data fra historiske systemer kan ta tilstrekkelig tid, spesielt hvis det er mange systemer, de er forskjellige og forskjellige avdelinger av kunden er ansvarlige for dem. Det er nødvendig å ta hensyn til dette øyeblikket under test og endelig migrering.

Det mest praktiske alternativet ser ut til å være opplasting til xls-filer. Mange eldre IT-systemer støtter dette alternativet.

Det kan også være muligheter for opplasting til csv-format, dbf, xml-formater og andre.

Det skal bemerkes at av en eller annen grunn (for eksempel sikkerhetsproblemer) kan ikke kunden alltid gi fullstendige dataopplastinger på dette stadiet! Kun en datastruktur og noen få testelementer. Dermed kan det oppstå en situasjon at det under test- og sluttbelastninger vil bli funnet data av lav kvalitet i kildetabellene, noe som vil føre til uplanlagte feil.

For å minimere dette problemet, bør volumene av testnedlastinger fra historiske systemer diskuteres på forhånd.

4 datakartlegging

Kartlegging (datakartlegging) - generelt, prosessen med å kartlegge data fra historiske systemer og mottakssystemet. Det vil si rådataene og dataene som skal lastes ned.

Kartleggingsstadiet er det mest tidkrevende stadiet og kan ta mer enn 50 % av alt arbeid med migreringsoppgaven.

På dette stadiet er hele arbeidsgruppen i migrasjonsprosjektet fullt ut involvert.

I prosessen med datakartlegging er det nødvendig å fremheve undertrinnene til tabellkartlegging og feltkartlegging.

· Kartleggingstabeller, eller malkartlegging - kartlegging av tabeller med kildedata og datamaler for lasting. Korrespondansen kan være enten 1:1 eller N:N. Som et resultat av dette arbeidet utarbeides og vedlikeholdes et register over tabellkartlegging. Dette undertrinnet er nødvendig for neste undertrinn av feltkartlegging og for å holde styr på den generelle tilstanden til kartleggingen.

Gruppe av 1C maler

Malnavn 1C

Filnavn

kilde

Regler for generering av kildefiler

Ansvarlig

Status

Merk

NSI

Prøve_

Nomenklatur

Nomenk

latura.xls

Still inn valg i system N
... Lagre til txt
... Åpne i xls, kolonner - tekst
... Første linje - overskrift
... Antall kolonner - 15
... Sammenlign antall linjer i txt og xls
... Arknavnet er alltid "Sheet1"

Ivanov I.I.

i jobb

· Feltkartlegging - kartlegging av tabellfelt innenfor den allerede definerte kartleggingen av tabeller. Resultatet av dette arbeidet er et register over feltkartlegging.

Nei.

Cl. felt

Påbudt, bindende

Navn på 1C-malfeltet "Template_Nomenclature"

Beskrivelse

Feltnavn "Nomenclature.xls"

Fyllingsalgoritme

Kode

Katalogvarekode

Kode

Navn

Navn

Ja

Denne gruppen

Inneholder en av verdiene:
... 1 - for grupper
... 0 - for elementer

Hvis kodelengde = 11 tegn og siste 4 tegn<>"0000", så er dette elementet "0", ellers er gruppen "1".

Fullt navn

Katalogelementnavn

Navn

Hvis denne gruppen = 1, deretter "", ellers, hvis denne gruppen = 0, så navn.

Som en del av denne fasen bør det også gjennomføres et eventuelt arbeid med datanormalisering.

5. Utarbeidelse av transformasjonsregler

I motsetning til de tidligere stadiene, er dette stadiet teknisk og involverer arbeidet til entreprenørens utbygger.

Basert på avtalte registre over kartleggingsfelt, utvikler Entreprenørens spesialister datatransformasjonsregler.

For operativt arbeid under de forberedende migreringsstadiene og videre, under test- og endelige migreringer, er det viktig at det er et praktisk utviklingsmiljø for regler (skript) for datatransformasjon og et miljø for konvertering av kildedata til data for lasting.

Dessuten inkluderer kravene til dette miljøet:

· Bekvemmelighet og hastighet på utvikling av transformasjonsregler;

· Datakonverteringshastighet. Filer inn og ut kan være hundretusenvis av linjer!

· Evne til å jobbe med flere inndatafiler samtidig;

· Evne til å lagre transformasjonsregler i separate filer.

For våre migrasjonsprosjekter har vi utviklet en spesialisert utviklerarbeidsstasjon som tar utgangspunkt i standardbehandlingen til 1C Query Console.

Behandlingen av "Query Console" er forbedret for å gjøre det mulig å sende direkte forespørsler til xls-filer.

Her er et eksempel på å kombinere to kilde xls-filer Ansatte.xls


Ansatt kode

Etternavn

Navn

mellomnavn

Fødselsdato

2423

Ivanov

Ivan

Ivanovich

17.11.1992

1523

Petrov

Basilikum

Aleksandrovich

04.02.1991

4363

Sidorov

Kirill

Nikolaevich

01.05.1995

Denisov

Denis

Denisovich

01.01.1990

og Drift.xls med sider:

Avskrivninger

Ansatt kode

Dato

Sum

2423

01.02.2014

1523

02.02.2014

4363

03.02.2014

04.02.2014

100000

2423

05.02.2014

1523

06.02.2014

4363

07.02.2014

2356

08.02.2014

140000

2423

09.02.2014

1523

10.02.2014

4363

11.02.2014

23523

12.02.2014

80000

og Kvitteringer:

Ansatt kode

Dato

Sum

01.05.2004

02.05.2004

03.05.2004

04.05.2004

2423Fødselsdato

Kvitteringsbeløp

Beløp som skal debiteres

Ivanov Ivan Ivanovich

2423

17.11.1992

1341234

1010

Petrov Vasily Alexandrovich

1523

04.02.1991

245245

Denisov Denis Denisovich

01.01.1990

380000

320000

Kirill Sidorov

4363

01.05.1995

613382

26336

TOTAL:

2579861

347842

Merk at eksemplet er kunstig, spesielt valgt for å demonstrere alle mulige stadier av datakildetransformasjon.

Den teknologiske sekvensen av transformasjonsoperasjoner her er som følger:

Ved å bruke Access SQL-spørringsspråket (som gir betydelige tilleggsfunksjoner sammenlignet med 1C-spørringsspråket), opprettes en innledende spørring som trekker ut data fra xls-filen til 1C-miljøet. I dette tilfellet, allerede på dette stadiet, er ulike kontroller og datanormalisering mulig.

ADO datatilgangsteknologi gir høyhastighetsytelse.

Ris. 3

2. Spørring i 1C-språk - hovedspørringen som implementerer feltkartleggingsalgoritmen. Og også: berikelse av de innlastede dataene med data fra 1C-databasen, omgruppering, kombinert med resultatene av spørringer til andre xls-kildefiler, etc.

3. Etterbehandling av 1C-søkeresultatet, om nødvendig. Det implementeres ved hjelp av et skript på 1C-språket.

For eksempel implementerer vi her tillegg av "TOTAL"-linjen ved kolonnene for beløpene.

4. Skrive det endelige datasettet til xls-filen.

I det generelle tilfellet, ved utgangen, får vi de endelige filene for lasting i mål 1C-databasen.

Dette verktøyet lar deg også lagre reglene for konvertering av data til en egen xml-fil:

I tillegg arbeidsevne v batch-modus, som er spesielt viktig når det er en stor mengde heterogene migrerende data.

I løpet av de foregående stadiene avsluttes den forberedende delen av arbeidet som helhet - alle datakilder er identifisert, kildedata er lastet ut fra kildene, maler for innlasting i måldatabasen er utarbeidet, datakartlegging har blitt utarbeidet, og til slutt har datatransformasjonsskript blitt utviklet.

Det skal bemerkes at før den endelige migreringen, bør du definitivt gjennomføre flere tester. Under testmigrasjoner identifiserer entreprenøren sammen med kundene:

Konverteringsfeil, datainnlastingsfeil

Gjennomfør en foreløpig vurdering av kvaliteten på data som er lastet inn i målsystemet

Basert på resultatene fra testmigreringer, utarbeide/oppdatere en plan for den endelige migreringen

7 dataavstemming

Kvalitetskontrollen av de innlastede dataene bør utføres både etter testmigreringer og ved slutten av den endelige migreringen. Under avstemming kan følgende indikatorer kontrolleres:

· Sammenfall av de totale beløpene av saldoer, dokumenter;

· Kvantitative samsvar, for eksempel antall anleggsmidler;

· Korrekt utfylling av individuelle prøveenheter;

Vær oppmerksom på at visse kontroller av migrerende data, datanormaliseringsproblemer må løses gjennom alle migreringsprosesser. Du bør alltid spørre deg selv hva som må gjøres på det nåværende stadiet for å unngå feil i påfølgende stadier.

For eksempel:

· Se etter duplikater etter nøkkelfelt. Det er mulig og nødvendig å utføre mer på de første dataene;

· Støping av felttyper;

· Referanseintegritet;

· Matematiske inkonsekvenser. For eksempel se etter tomme numeriske felt, som er planlagt å deles under transformasjon;

· Generelt kontrollerer obligatorisk utfylling av felt;

· Erstatning av ugyldige tegn. For eksempel engelske tegn i kyrilliske felt ("o", "a", "e", etc.) Dette gjelder spesielt for nøkkelfelt!

Sjekke verdiene til strengfelt for samsvar med typene av mottakersystemet (lengdebegrensninger)

Etter fullføring av den endelige migreringen, i henhold til en forhåndsbestemt migrasjonsstrategi og migrasjonsplan, tas det en beslutning om videre drift av de historiske systemene.

Ofte avsluttes operasjonen umiddelbart etter den endelige avstemmingen av dataene og registrering av suksessen med migreringen - brukerne av det nye systemet fører ikke lenger journaler parallelt i to systemer, men bytter fullstendig til det nye systemet. Samtidig forblir tilgangen til det gamle systemet i lesemodus.

I noen tilfeller kan parallelldrift av to systemer forekomme under prøvedriften (OE) og enda mer enn denne perioden. Spørsmålet om parallellbrukers arbeid i to systemer er nært knyttet til spørsmålet om muligheten for å rulle tilbake til det gamle systemet dersom migreringen (eller generelt arbeidet med det nye systemet!) anses som utilfredsstillende.

Konklusjon

Avslutningsvis vil jeg bemerke at når det kommer til migrering av store transaksjonssystemer, som inkluderer mange 1C: Enterprise-konfigurasjoner, kan overgangen til et nytt system være svært tidkrevende.

Derfor bør det huskes at ethvert slikt prosjekt krever nøye forberedelse og må ledsages av en individuell plan. Uansett hvilken type systemer som migreres, størrelsen på databaser osv., ser imidlertid den generelle migreringsordningen nesten identisk ut.


I forrige del så vi på typene relasjoner (en-til-en, en-til-mange, mange-til-mange), samt én bokklasse og dens kartleggingsklasse BookMap. I den andre delen vil vi oppdatere Bok-klassen, lage resten av klassene og relasjonene mellom dem, slik det ble vist i forrige kapittel i Databasediagrammet, plassert over underoverskriften 1.3.1 Relasjoner.

Klasser og tilordningskode (Med kommentarer)

Klassebok

Offentlig klasse Bok (// Unik identifikator offentlig virtuell int Id (get; sett;) // Navn offentlig virtuell streng Navn (get; sett;) // Beskrivelse offentlig virtuell streng Beskrivelse (get; sett;) // Vurdering av den fantastiske World public virtual int MfRaiting (get; set;) // Sidetall offentlige virtuelle int PageNumber (get; set;) // Link til bildet offentlig virtuell streng Bilde (get; set;) // Book ankomstdato (filtrer etter ny) elementer!) public virtual DateTime IncomeDate (get; set;) // Sjanger (Many-to-Many) // Hvorfor ISet og ikke IList? Bare én samling (IList) kan velges ved å bruke et JOIN-valg, hvis mer enn én samling er nødvendig for å velge en JOIN, så er det bedre å konvertere dem til en offentlig virtuell ISet ISet-samling Sjangere (få; sett;) // Serier (Mange-til-en) offentlige virtuelle Serier Serier (get; sett;) // Opinion og annet (En-til-en) private Mind _mind; public virtual Mind Mind (få (return _mind ?? (_mind = new Mind ());) set (_mind = value;)) // Author (Many-to-Many) public virtual ISet Forfattere (get; sett;) // Initialiser på forhånd slik at ingen null-unntak blir kastet. offentlig bok () (// Uordnet sett (i en tabell kan det ikke være to nøyaktig samme rader, ellers velger den en og ignorerer den andre) Sjangere = nytt HashSet (); Forfattere = nytt HashSet (); )) // Kartlegging av bokklassen offentlig klasse BookMap: ClassMap (offentlig BookMap () (Id (x => x.Id); Kart (x => x.Name); Kart (x => x.Description); Kart (x => x.MfRaiting); Kart (x = > x.PageNumber); Kart (x => x.Image); Kart (x => x.IncomeDate); // Mange-til-mange-forhold HasManyToMany (x => x.Sjangre) // Cascading-regler Alle - Når objektet lagres, oppdateres eller slettes, sjekkes og // opprettet / oppdatert / lagt til alle avhengige objekter. Cascade.SaveUpdate () // Navnet på den mellomliggende tabellen MÅ være det samme som sjangerklassen! .Table ("Book_Genre" ); HasManyToMany (x = > x.Authors) .Cascade.SaveUpdate () .Table ("Book_Author"); // Mange-til-en-forhold Referanser (x => x.Series); // En-til-en forhold Hovedklasse HasOne (x => x.Mind) .Cascade.All (). Begrenset ();))

Offentlig klasse Forfatter (offentlig virtuell int Id (get; sett;) // Fornavn-Etternavn offentlig virtuell streng Navn (get; sett;) // Biografi offentlig virtuell streng Biografi (get; sett;) // Bøker offentlig virtuell ISet Bøker (get; sett;) // Initialiser forfattere offentlig forfatter () (Bøker = nytt HashSet (); )) // Author Mapping public class AuthorMap: ClassMap (offentlig forfatterkart () (Id (x => x.Id); Kart (x => x.Name); Kart (x => x.Biography); // Mange-til-mange forhold HasManyToMany (x => x .Books) // Cascading rules Alle - Når et objekt lagres, oppdateres eller slettes, blir alle avhengige objekter sjekket og opprettet / oppdatert / lagt til.Cascade.All () // Eieren av samlingen er den andre enden av forholdet (Bok) og den blir lagret først .Invers () // Navnet på mellomtabellen MÅ være det samme som bokklassen! .Table ("Book_Author");))

Klasse sjanger

Offentlig klasse Sjanger (offentlig virtuell int Id (get; sett;) // Sjangernavn offentlig virtuell streng Navn (get; sett;) // Engelsk sjangernavn offentlig virtuell streng EngName (get; sett;) // Bøker offentlig virtuell ISet Bøker (hent; sett;) // Initialiser bøker offentlig Sjanger () (Bøker = nytt HashSet (); )) // Sjangerkartlegging offentlig klasse GenreMap: ClassMap (offentlig sjangerkart () (Id (x => x.Id); Kart (x => x.Name); Kart (x => x.EngName); // Mange-til-mange forhold HasManyToMany (x => x .Books) // Cascading rules Alle - Når et objekt lagres, oppdateres eller slettes, blir alle avhengige objekter sjekket og opprettet / oppdatert / lagt til.Cascade.All () // Eieren av samlingen er den andre enden av forholdet (Bok) og den blir lagret først .Inverse () // Navnet på mellomtabellen MÅ være det samme som for bokklassen! .Table ("Book_Genre")))

Klassens mening:

Offentlig klasse Mind (public virtual int Id (get; set;) // Min mening offentlig virtuell string MyMind (get; set;) // Fantlab opinion public virtual string MindFantLab (get; set;) // Book public virtual Book Book ( få; sett;)) // Tankekartlegging offentlig klasse MindMap: ClassMap (offentlig MindMap () (Id (x => x.Id); Kart (x => x.MyMind); Kart (x => x.MindFantLab); // Ett til ett forhold HasOne (x => x.Book ;)))

Klassesyklus (serie):

Offentlig klasse Series (public virtual int Id (get; set;) public virtual string Name (get; set;) // Jeg opprettet en IList, ikke en ISet, fordi bortsett fra bok, er ikke serier lenger assosiert med noe, selv om du kan gjøre og ISet offentlig virtuell IList Bøker (hent; sett;) // Initialiser bøker. offentlig serie () (Bøker = ny liste (); )) offentlig klasse SerieMap: ClassMap (offentlig SerieKart () (Id (x => x.Id); Kart (x => x.Name); // En-til-mange forhold HasMany (x => x.Books) // // Samlingseieren er .den andre enden av forholdet er (bok) og den vil bli lagret først. .Invers ()))

En liten forklaring
offentlig virtuell ISet Sjangere (få; sett;)
offentlig virtuell ISet Forfattere (få; sett;)

Hvorfor ISet , og ikke, for eksempel, kjent for mange IList ? Hvis vi bruker IList i stedet for ISet, og prøver å kjøre prosjektet, vil vi ikke merke stor forskjell (tabeller og klasser vil bli opprettet). Men når vi går til Book LeftJoin-klassen samtidig med sjanger- og forfattertabellen, og til og med prøver å vise ikke-dupliserte poster fra Book (Distinct Book.Id)-tabellen inn i View, vil Nhibernate gi et unntak og en feil. .
Kan ikke hente flere poser samtidig.
I slike tilfeller bruker vi ISet, spesielt settene er beregnet på dette (ignorer dupliserte poster).

Mange-til-mange forhold.

NHibernate har konseptet med et "master"-bord. Selv om mange-til-mange-forholdet mellom "Bok"- og "Forfatter"-tabellene er det samme (en forfatter kan ha mange bøker, en bok kan ha mange forfattere), krever Nhibernate at programmereren spesifiserer en tabell som lagres som nummer to ( har en. invers ()), det vil si at først vil en post opprettes / oppdateres / slettes i boktabellen, og først deretter i forfattertabellen.
Cascade.All betyr å utføre overlappende operasjoner på lagre, oppdatering og sletting. Det vil si at når et objekt lagres, oppdateres eller slettes, blir alle avhengige objekter sjekket og opprettet / oppdatert / lagt til (Ps. Du kan skrive i stedet for Cascade.All -> .Cascade.SaveUpdate (). Cascade.Delete ())
Method.Table ("Book_Author"); oppretter en "mellomliggende" tabell "Book_Author" i databasen.

Mange-til-en, en-til-mange forhold.

.Constrained ()-metoden forteller NHibernate at for en post fra Book-tabellen må en oppføring fra Mind-tabellen samsvare (ID-en til Mind-tabellen må være lik ID-en til Book-tabellen)

Hvis du starter prosjektet nå og ser på Bibilioteca-databasen, vil nye tabeller med allerede dannede lenker dukke opp.

Deretter fyller du ut de opprettede tabellene med data ...
For å gjøre dette vil vi lage en testapplikasjon som vil lagre data til databasen, oppdatere og slette dem ved å endre HomeController som følger (kommentere ut unødvendige deler av koden):
offentlig ActionResult Index () (bruker (ISession session = NHibernateHelper.OpenSession ()) (bruker (ITTransaction transaction = session.BeginTransaction ()) (// Create, add var createBook = new Book (); createBook.Name = "Metro2033" ; createBook.Description = "Post-apokalyptisk mystikk"; createBook.Authors.Add (ny forfatter (Navn = "Glukhovsky")); createBook.Genres.Add (ny sjanger (Navn = "Post-apokalyptisk mystikk")); createBook .Series = new Series (Navn = "Metro"); createBook.Mind = new Mind (MyMind = "Post-apokalyptisk mystikk"); session.SaveOrUpdate (createBook); // Update (By ID) // var series = session .Få (1); // var updateBook = session.Get (1); //updateBook.Name = "Metro2034"; //updateBook.Description = "Dystopi"; //updateBook.Authors.ElementAt(0).Name = "Glukhovsky"; //updateBook.Genres.ElementAt(0).Name = "Dystopia"; //updateBook.Series = serie; //updateBook.Mind.MyMind = "11111"; //session.SaveOrUpdate(updateBook); // Slett (ved ID) // var deleteBook = session.Get (1); //session.Delete(deleteBook); transaksjon.Forplikte (); ) Sjanger genreAl = null; Forfatter forfatterAl = null; Serie serieAl = null; Mind mindAl = null; var bøker = session.QueryOver () // Left Join with Genres table .JoinAlias​(p => p.Genres, () => .JoinAlias​(p => p.Authors, () => authorAl, JoinType.LeftOuterJoin) .JoinAlias​ ​(p => p .Series, () => seriesAl, JoinType.LeftOuterJoin) .JoinAlias​(p => p.Mind, () => mindAl, JoinType.LeftOuterJoin) // Fjerner duplikattabell-ID-boken. . TransformUsing (Transformers.DistinctRootEntity). Liste (); returnere Vis (bøker);))

En liten forklaring

  1. var bøker = session.QueryOver () Velg * Fra bok;
  2. .JoinAlias ​​​​(p => p.Sjangre, () => genreAl, JoinType.LeftOuterJoin)- som å kjøre et SQL-skript:
    VELG * FRA bok
    indre JOIN Book_Genre PÅ book.id = Book_Genre.Book_id
    VENSTRE JOIN Sjanger PÅ Book_Genre.Genre_id = Genre.id
  3. .TransformUsing (Transformers.DistinctRootEntity)- Som å kjøre et SQL-skript: VELG distinkt Book.Id ..., (fjerner dupliserte poster med samme id)

Typer assosiasjoner
.JoinAlias ​​​​(p => p.Sjangre, () => genreAl, JoinType.LeftOuterJoin)

  1. LeftOuterJoin - Velger alle poster fra venstre tabell ( Bok), og legger deretter til postene til den høyre tabellen ( Sjanger). Hvis ingen samsvarende oppføring er funnet i den høyre tabellen, viser den som Null
  2. RightOuterJoin er det motsatte av LEFT JOIN - den velger alle poster fra den høyre tabellen ( Sjanger) og legger deretter til postene til den venstre tabellen ( Bok)
  3. InnerJoin - velger bare de postene fra de venstre tabellene ( Bok) som har en tilsvarende post fra den høyre tabellen ( Sjanger) og legger deretter til postene fra den høyre tabellen til dem

La oss endre visningen som følger:

Indeksvisning

@modell IEnumerable @ (Layout = null;) Indeks

@ Html.ActionLink ("Opprett ny", "Opprett")

@foreach (var element i modell) ( @ (streng strSeries = item.Series! = null? item.Series.Name: null;) }
@ Html.DisplayNameFor (modell => modell.navn) @ Html.DisplayNameFor (modell => model.Mind) @ Html.DisplayNameFor (modell => modell.serie) @ Html.DisplayNameFor (modell => modell.Forfattere) @ Html.DisplayNameFor (modell => modell.Sjangre) Drift
@ Html.DisplayFor (modelItem => item.Name) @ Html.DisplayFor (modelItem => item.Mind.MyMind)@ Html.DisplayFor (modelItem => strSeries) @foreach (var forfatter i item.Authors) (streng strAuthor = forfatter! = null? author.Name: null; @ Html.DisplayFor (modelItem => strAuthor)
}
@foreach (var sjanger i item.Genres) (streng strGenre = genre! = null? genre.Name: null; @ Html.DisplayFor (modelItem => strGenre)
}
@ Html.ActionLink ("Rediger", "Rediger", ny (id = item.Id)) | @ Html.ActionLink ("Detaljer", "Detaljer", ny (id = item.Id)) | @ Html.ActionLink ("Slett", "Slett", ny (id = item.Id))




Etter å ha sjekket alle operasjonene én etter én, vil vi legge merke til at:
  • Opprettings- og oppdateringsoperasjonene oppdaterer alle data knyttet til boktabellen (fjern Cascade = "save-update" eller cascade = "alle", og de tilknyttede dataene vil ikke bli lagret)
  • Ved sletting slettes data fra tabellene Book, Mind, Book_Author, og resten av dataene slettes ikke, fordi de har Cascade = "save-update"

Kartlegging for klasser som har arv.
Hvordan kartlegge klasser som har arv? La oss si at vi har et slikt eksempel:
// Klasse av todimensjonale former offentlig klasse TwoDShape (// Bredde offentlig virtuell int Bredde (get; sett;) // Høyde offentlig virtuell int Høyde (get; sett;)) // Klassetriangel offentlig klasse Triangel: TwoDShape (/ / Identifikasjonsnummer offentlig virtuell int Id (get; sett;) // Trekantvisning offentlig virtuell streng Stil (get; sett;))

I prinsippet er det ikke noe komplisert i denne tilordningen, vi vil ganske enkelt lage en tilordning for den avledede klassen, det vil si Triangle-tabellen.
// Trekantkartlegging offentlig klasse TriangleMap: ClassMap (offentlig TriangleMap () (Id (x => x.Id); Kart (x => x.Style); Kart (x => x.Høyde); Kart (x => x.Width);))
Etter oppstart av applikasjonen vil følgende (tomme) tabell vises i Biblioteca-databasen

Tagger:

  • asp.net mvc 4
  • dvale
  • sql server
Legg til merkelapper

Havnekartlegging- dette er videresending av mottatte data på en slik måte at data mottatt på en port på en datamaskin automatisk videresendes til en annen port på en annen datamaskin.

Faktisk er det mye lettere teknisk å implementere enn å forklare selve prinsippet. Det kan sammenlignes med en solstråle: hvis du retter en lysstråle inn i et speil, reflekterer og lyser den "automatisk" opp et objekt. Dessuten, hvis du belyste en person og denne personen ikke vet at strålen har blitt reflektert fra speilet, vil han tro at lyset kommer fra stedet der speilet er. Det er det samme her: alle dataene du overfører overføres uten forvrengning til en annen datamaskin, som kan plasseres hvor som helst.

Denne teknologien ligner litt på en proxy-server, men den er mye enklere og mye mindre fleksibel.

Opplegget er omtrent det samme som når du bruker en proxy (man kan si at portmapping ligner på en proxy - men det vil være det samme som å si "bestefar er som et barnebarn" - faktisk er dette bare en proxy som er ligner på portkartlegging):

Din datamaskin >>> datamaskin med portkartlegging >>> ekstern server.

Hva er portkartlegging for?

  1. Hvis organisasjonen bruker en bedrifts proxy, kan du ved å sette opp portmapping på den til en ekstern e-postserver (mail.ru) bruke noen et e-postprogram fra bedriftens nettverk - og du trenger ikke å installere/konfigurere noen ekstra programmer!
  2. På samme måte som et e-postprogram kan du tilpasse nesten alle andre programmer! Hvis bare den støtter TCP/IP.

Dette er selvfølgelig bare de viktigste måtene å bruke portkartlegging på. Det er mange flere aktiviteter hvor det også vil være veldig, veldig nyttig.

Fordeler med havnekartlegging

  1. Dette systemet er veldig enkelt og det er mange programmer på Internett som lar deg implementere denne funksjonen;
  2. Siden dataene overføres 100 % uten forvrengning, er du garantert 100 % anonymitet;
  3. Hvis du bruker dette systemet, trenger du ingen "soksifiers" - siden ingen ekstra initialisering av tilkoblingen er nødvendig, tilsvarer tilkobling til portkartleggeren å koble til en ekstern datamaskin.

Ulemper med havnekartlegging

  1. Dette systemet er ikke fleksibelt. I motsetning til en proxy, der du kan koble til mange nettsteder gjennom én proxy, kan du koble til via én porttilordning bare én server.
  2. For hver ny porttilordning må du endre innstillingene på serveren der denne funksjonen er implementert - dette er ikke tilgjengelig fra klientdatamaskinen.
  3. På internett Nei gratis portkartleggere (på grunn av deres ekstreme begrensninger - én portkartlegging gir tilgang til kun én server), så hvis du vil være virkelig anonym på datamaskinen din, må du ha en server et sted hvor portkartleggingsprogrammet vil bli installert - og nå vil adressen til denne serveren bli "fremhevet" i loggene til nettsteder.

Hvordan jobbe med portkartlegging

Vær oppmerksom på at opplegget for å jobbe med portkartlegging er omtrent det samme som for å jobbe med proxy, bare det er enda enklere. Portmapping er et alias (tilleggsnavn) for datamaskinen den er konfigurert på.

La oss anta at vi har gjort portkartlegging:

192.168.1.255:1234 => www.mail.ru:80 (80. port er porten til webservere)

Deretter, for å åpne mail.ru-nettstedet, kan du bruke 2 metoder - åpne nettstedet i nettleservinduet:

  1. http://www.mail.ru
  2. http://192.168.1.255:1234/
    (i dette tilfellet, sørg for å skrive http://)

Jeg vil gjerne merke: hvis du nødvendig bruk portmapping, så du skal bare bruke den andre adressen... Det vil si, hvis du ikke kan koble til mail.ru, må du bare bruke den interne adressen (http://192.168.1.255:1234/).

Portkartlegging på lokal datamaskin

I tilfellet når portkartlegging gjøres på din egen datamaskin, indikerer de vanligvis:

  1. lokal port - den lokale porten på datamaskinen din som du må koble til for å bruke portkartlegging. Dette tallet kan være alt (fra 1 til 65535), helst mer enn 1000;
  2. ekstern vert - den datamaskinen (verten), på hvilken indikerer portkartlegging. Det kan for eksempel være pop.mail.ru e-postserveren;
  3. ekstern port - datamaskinport, til hvilken tilkobling vil skje via portkartlegging. For å motta e-post (POP3) er dette vanligvis port 110, for å sende e-post (SMTP) er det port 25, for webservere (www ...) er dette vanligvis port 80.

Så i dette tilfellet må du (ved å sette opp portkartlegging) koble til ikke til mail.ru (og lignende), og spesifiser din egen datamaskin som server:

127.0.0.1:lokalport

hvor localport er portnummeret som er spesifisert ved konfigurering av portkartlegging. Dette kan for eksempel være port 1234.

Det vil si at hvis du har laget portmapping til et nettsted, må du skrive: http://127.0.0.1:1234/

Hvis du setter opp e-post, spesifiser som e-postserver 127.0.0.1 - både for å motta og for å sende post. Og ikke glem å finne innstillingene for portnumre (POP3 og SMTP) i e-postklienten din og endre dem i samsvar med dine egne innstillinger i portkartleggingen!


Del 3. Vise data fra en tabell (LIST-operasjon)

I forrige del så vi på typene relasjoner (en-til-en, en-til-mange, mange-til-mange), samt én bokklasse og dens kartleggingsklasse BookMap. I den andre delen vil vi oppdatere Bok-klassen, lage resten av klassene og relasjonene mellom dem, slik det ble vist i forrige kapittel i Databasediagrammet, plassert over underoverskriften 1.3.1 Relasjoner.

Klasser og tilordningskode (Med kommentarer)

Klassebok

Offentlig klasse Bok (// Unik identifikator offentlig virtuell int Id (get; sett;) // Navn offentlig virtuell streng Navn (get; sett;) // Beskrivelse offentlig virtuell streng Beskrivelse (get; sett;) // Vurdering av den fantastiske World public virtual int MfRaiting (get; set;) // Sidetall offentlige virtuelle int PageNumber (get; set;) // Link til bildet offentlig virtuell streng Bilde (get; set;) // Book ankomstdato (filtrer etter ny) elementer!) public virtual DateTime IncomeDate (get; set;) // Sjanger (Many-to-Many) // Hvorfor ISet og ikke IList? Bare én samling (IList) kan velges ved å bruke et JOIN-valg, hvis mer enn én samling er nødvendig for å velge en JOIN, så er det bedre å konvertere dem til en offentlig virtuell ISet ISet-samling Sjangere (få; sett;) // Serier (Mange-til-en) offentlige virtuelle Serier Serier (get; sett;) // Opinion og annet (En-til-en) private Mind _mind; public virtual Mind Mind (få (return _mind ?? (_mind = new Mind ());) set (_mind = value;)) // Author (Many-to-Many) public virtual ISet Forfattere (get; sett;) // Initialiser på forhånd slik at ingen null-unntak blir kastet. offentlig bok () (// Uordnet sett (i en tabell kan det ikke være to nøyaktig samme rader, ellers velger den en og ignorerer den andre) Sjangere = nytt HashSet (); Forfattere = nytt HashSet (); )) // Kartlegging av bokklassen offentlig klasse BookMap: ClassMap (offentlig BookMap () (Id (x => x.Id); Kart (x => x.Name); Kart (x => x.Description); Kart (x => x.MfRaiting); Kart (x = > x.PageNumber); Kart (x => x.Image); Kart (x => x.IncomeDate); // Mange-til-mange-forhold HasManyToMany (x => x.Sjangre) // Cascading-regler Alle - Når objektet lagres, oppdateres eller slettes, sjekkes og // opprettet / oppdatert / lagt til alle avhengige objekter. Cascade.SaveUpdate () // Navnet på den mellomliggende tabellen MÅ være det samme som sjangerklassen! .Table ("Book_Genre" ); HasManyToMany (x = > x.Authors) .Cascade.SaveUpdate () .Table ("Book_Author"); // Mange-til-en-forhold Referanser (x => x.Series); // En-til-en forhold Hovedklasse HasOne (x => x.Mind) .Cascade.All (). Begrenset ();))

Offentlig klasse Forfatter (offentlig virtuell int Id (get; sett;) // Fornavn-Etternavn offentlig virtuell streng Navn (get; sett;) // Biografi offentlig virtuell streng Biografi (get; sett;) // Bøker offentlig virtuell ISet Bøker (get; sett;) // Initialiser forfattere offentlig forfatter () (Bøker = nytt HashSet (); )) // Author Mapping public class AuthorMap: ClassMap (offentlig forfatterkart () (Id (x => x.Id); Kart (x => x.Name); Kart (x => x.Biography); // Mange-til-mange forhold HasManyToMany (x => x .Books) // Cascading rules Alle - Når et objekt lagres, oppdateres eller slettes, blir alle avhengige objekter sjekket og opprettet / oppdatert / lagt til.Cascade.All () // Eieren av samlingen er den andre enden av forholdet (Bok) og den blir lagret først .Invers () // Navnet på mellomtabellen MÅ være det samme som bokklassen! .Table ("Book_Author");))

Klasse sjanger

Offentlig klasse Sjanger (offentlig virtuell int Id (get; sett;) // Sjangernavn offentlig virtuell streng Navn (get; sett;) // Engelsk sjangernavn offentlig virtuell streng EngName (get; sett;) // Bøker offentlig virtuell ISet Bøker (hent; sett;) // Initialiser bøker offentlig Sjanger () (Bøker = nytt HashSet (); )) // Sjangerkartlegging offentlig klasse GenreMap: ClassMap (offentlig sjangerkart () (Id (x => x.Id); Kart (x => x.Name); Kart (x => x.EngName); // Mange-til-mange forhold HasManyToMany (x => x .Books) // Cascading rules Alle - Når et objekt lagres, oppdateres eller slettes, blir alle avhengige objekter sjekket og opprettet / oppdatert / lagt til.Cascade.All () // Eieren av samlingen er den andre enden av forholdet (Bok) og den blir lagret først .Inverse () // Navnet på mellomtabellen MÅ være det samme som for bokklassen! .Table ("Book_Genre")))

Klassens mening:

Offentlig klasse Mind (public virtual int Id (get; set;) // Min mening offentlig virtuell string MyMind (get; set;) // Fantlab opinion public virtual string MindFantLab (get; set;) // Book public virtual Book Book ( få; sett;)) // Tankekartlegging offentlig klasse MindMap: ClassMap (offentlig MindMap () (Id (x => x.Id); Kart (x => x.MyMind); Kart (x => x.MindFantLab); // Ett til ett forhold HasOne (x => x.Book ;)))

Klassesyklus (serie):

Offentlig klasse Series (public virtual int Id (get; set;) public virtual string Name (get; set;) // Jeg opprettet en IList, ikke en ISet, fordi bortsett fra bok, er ikke serier lenger assosiert med noe, selv om du kan gjøre og ISet offentlig virtuell IList Bøker (hent; sett;) // Initialiser bøker. offentlig serie () (Bøker = ny liste (); )) offentlig klasse SerieMap: ClassMap (offentlig SerieKart () (Id (x => x.Id); Kart (x => x.Name); // En-til-mange forhold HasMany (x => x.Books) // // Samlingseieren er .den andre enden av forholdet er (bok) og den vil bli lagret først. .Invers ()))

En liten forklaring
offentlig virtuell ISet Sjangere (få; sett;)
offentlig virtuell ISet Forfattere (få; sett;)

Hvorfor ISet , og ikke, for eksempel, kjent for mange IList ? Hvis vi bruker IList i stedet for ISet, og prøver å kjøre prosjektet, vil vi ikke merke stor forskjell (tabeller og klasser vil bli opprettet). Men når vi går til Book LeftJoin-klassen samtidig med sjanger- og forfattertabellen, og til og med prøver å vise ikke-dupliserte poster fra Book (Distinct Book.Id)-tabellen inn i View, vil Nhibernate gi et unntak og en feil. .
Kan ikke hente flere poser samtidig.
I slike tilfeller bruker vi ISet, spesielt settene er beregnet på dette (ignorer dupliserte poster).

Mange-til-mange forhold.

NHibernate har konseptet med et "master"-bord. Selv om mange-til-mange-forholdet mellom "Bok"- og "Forfatter"-tabellene er det samme (en forfatter kan ha mange bøker, en bok kan ha mange forfattere), krever Nhibernate at programmereren spesifiserer en tabell som lagres som nummer to ( har en. invers ()), det vil si at først vil en post opprettes / oppdateres / slettes i boktabellen, og først deretter i forfattertabellen.
Cascade.All betyr å utføre overlappende operasjoner på lagre, oppdatering og sletting. Det vil si at når et objekt lagres, oppdateres eller slettes, blir alle avhengige objekter sjekket og opprettet / oppdatert / lagt til (Ps. Du kan skrive i stedet for Cascade.All -> .Cascade.SaveUpdate (). Cascade.Delete ())
Method.Table ("Book_Author"); oppretter en "mellomliggende" tabell "Book_Author" i databasen.

Mange-til-en, en-til-mange forhold.

.Constrained ()-metoden forteller NHibernate at for en post fra Book-tabellen må en oppføring fra Mind-tabellen samsvare (ID-en til Mind-tabellen må være lik ID-en til Book-tabellen)

Hvis du starter prosjektet nå og ser på Bibilioteca-databasen, vil nye tabeller med allerede dannede lenker dukke opp.

Deretter fyller du ut de opprettede tabellene med data ...
For å gjøre dette vil vi lage en testapplikasjon som vil lagre data til databasen, oppdatere og slette dem ved å endre HomeController som følger (kommentere ut unødvendige deler av koden):
offentlig ActionResult Index () (bruker (ISession session = NHibernateHelper.OpenSession ()) (bruker (ITTransaction transaction = session.BeginTransaction ()) (// Create, add var createBook = new Book (); createBook.Name = "Metro2033" ; createBook.Description = "Post-apokalyptisk mystikk"; createBook.Authors.Add (ny forfatter (Navn = "Glukhovsky")); createBook.Genres.Add (ny sjanger (Navn = "Post-apokalyptisk mystikk")); createBook .Series = new Series (Navn = "Metro"); createBook.Mind = new Mind (MyMind = "Post-apokalyptisk mystikk"); session.SaveOrUpdate (createBook); // Update (By ID) // var series = session .Få (1); // var updateBook = session.Get (1); //updateBook.Name = "Metro2034"; //updateBook.Description = "Dystopi"; //updateBook.Authors.ElementAt(0).Name = "Glukhovsky"; //updateBook.Genres.ElementAt(0).Name = "Dystopia"; //updateBook.Series = serie; //updateBook.Mind.MyMind = "11111"; //session.SaveOrUpdate(updateBook); // Slett (ved ID) // var deleteBook = session.Get (1); //session.Delete(deleteBook); transaksjon.Forplikte (); ) Sjanger genreAl = null; Forfatter forfatterAl = null; Serie serieAl = null; Mind mindAl = null; var bøker = session.QueryOver () // Left Join with Genres table .JoinAlias​(p => p.Genres, () => .JoinAlias​(p => p.Authors, () => authorAl, JoinType.LeftOuterJoin) .JoinAlias​ ​(p => p .Series, () => seriesAl, JoinType.LeftOuterJoin) .JoinAlias​(p => p.Mind, () => mindAl, JoinType.LeftOuterJoin) // Fjerner duplikattabell-ID-boken. . TransformUsing (Transformers.DistinctRootEntity). Liste (); returnere Vis (bøker);))

En liten forklaring

  1. var bøker = session.QueryOver () Velg * Fra bok;
  2. .JoinAlias ​​​​(p => p.Sjangre, () => genreAl, JoinType.LeftOuterJoin)- som å kjøre et SQL-skript:
    VELG * FRA bok
    indre JOIN Book_Genre PÅ book.id = Book_Genre.Book_id
    VENSTRE JOIN Sjanger PÅ Book_Genre.Genre_id = Genre.id
  3. .TransformUsing (Transformers.DistinctRootEntity)- Som å kjøre et SQL-skript: VELG distinkt Book.Id ..., (fjerner dupliserte poster med samme id)

Typer assosiasjoner
.JoinAlias ​​​​(p => p.Sjangre, () => genreAl, JoinType.LeftOuterJoin)

  1. LeftOuterJoin - Velger alle poster fra venstre tabell ( Bok), og legger deretter til postene til den høyre tabellen ( Sjanger). Hvis ingen samsvarende oppføring er funnet i den høyre tabellen, viser den som Null
  2. RightOuterJoin er det motsatte av LEFT JOIN - den velger alle poster fra den høyre tabellen ( Sjanger) og legger deretter til postene til den venstre tabellen ( Bok)
  3. InnerJoin - velger bare de postene fra de venstre tabellene ( Bok) som har en tilsvarende post fra den høyre tabellen ( Sjanger) og legger deretter til postene fra den høyre tabellen til dem

La oss endre visningen som følger:

Indeksvisning

@modell IEnumerable @ (Layout = null;) Indeks

@ Html.ActionLink ("Opprett ny", "Opprett")

@foreach (var element i modell) ( @ (streng strSeries = item.Series! = null? item.Series.Name: null;) }
@ Html.DisplayNameFor (modell => modell.navn) @ Html.DisplayNameFor (modell => model.Mind) @ Html.DisplayNameFor (modell => modell.serie) @ Html.DisplayNameFor (modell => modell.Forfattere) @ Html.DisplayNameFor (modell => modell.Sjangre) Drift
@ Html.DisplayFor (modelItem => item.Name) @ Html.DisplayFor (modelItem => item.Mind.MyMind)@ Html.DisplayFor (modelItem => strSeries) @foreach (var forfatter i item.Authors) (streng strAuthor = forfatter! = null? author.Name: null; @ Html.DisplayFor (modelItem => strAuthor)
}
@foreach (var sjanger i item.Genres) (streng strGenre = genre! = null? genre.Name: null; @ Html.DisplayFor (modelItem => strGenre)
}
@ Html.ActionLink ("Rediger", "Rediger", ny (id = item.Id)) | @ Html.ActionLink ("Detaljer", "Detaljer", ny (id = item.Id)) | @ Html.ActionLink ("Slett", "Slett", ny (id = item.Id))




Etter å ha sjekket alle operasjonene én etter én, vil vi legge merke til at:
  • Opprettings- og oppdateringsoperasjonene oppdaterer alle data knyttet til boktabellen (fjern Cascade = "save-update" eller cascade = "alle", og de tilknyttede dataene vil ikke bli lagret)
  • Ved sletting slettes data fra tabellene Book, Mind, Book_Author, og resten av dataene slettes ikke, fordi de har Cascade = "save-update"

Kartlegging for klasser som har arv.
Hvordan kartlegge klasser som har arv? La oss si at vi har et slikt eksempel:
// Klasse av todimensjonale former offentlig klasse TwoDShape (// Bredde offentlig virtuell int Bredde (get; sett;) // Høyde offentlig virtuell int Høyde (get; sett;)) // Klassetriangel offentlig klasse Triangel: TwoDShape (/ / Identifikasjonsnummer offentlig virtuell int Id (get; sett;) // Trekantvisning offentlig virtuell streng Stil (get; sett;))

I prinsippet er det ikke noe komplisert i denne tilordningen, vi vil ganske enkelt lage en tilordning for den avledede klassen, det vil si Triangle-tabellen.
// Trekantkartlegging offentlig klasse TriangleMap: ClassMap (offentlig TriangleMap () (Id (x => x.Id); Kart (x => x.Style); Kart (x => x.Høyde); Kart (x => x.Width);))
Etter oppstart av applikasjonen vil følgende (tomme) tabell vises i Biblioteca-databasen

Tags: Legg til tagger