Uvod u Spring Batch
1. Uvod
U ovom ćemo se članku usredotočiti na praktični uvod u Spring Batch, usredotočen na kod. Spring Batch je okvir za obradu dizajniran za robusno izvršavanje poslova.
Trenutna je verzija 3.0 koja podržava Spring 4 i Javu 8. Također sadrži JSR-352, što je nova Java specifikacija za serijsku obradu.
Evo nekoliko zanimljivih i praktičnih primjera okvira.
2. Osnove tijeka rada
Spring batch slijedi tradicionalnu batch arhitekturu gdje spremište poslova obavlja posao zakazivanja i interakcije s poslom.
Posao može imati više koraka - i svaki korak obično slijedi slijed čitanja podataka, obrade i pisanja.
I naravno da će okvir za nas ovdje učiniti većinu teškog dizanja - pogotovo kada je riječ o radu na niskim razinama upornosti pri radu - koristeći sqlite za spremište poslova.
2.1. Naš primjer upotrebe
Jednostavna upotreba koju ćemo ovdje riješiti je - migrirat ćemo neke podatke o financijskim transakcijama iz CSV-a u XML.
Ulazna datoteka ima vrlo jednostavnu strukturu - sadrži transakciju po retku koju čine: korisničko ime, korisnički ID, datum transakcije i iznos:
korisničko ime, korisničko ime, datum_ transakcije, iznos_transakcije_devendra, 1234, 31.10.2015., 10000 John, 2134, 12.3.2015., 12321 robin, 2134, 2.2.2015., 23411
3. Maven POM
Ovisnosti potrebne za ovaj projekt su jezgra opruge, šarža opruge i sqlite jdbc konektor:
org.xerial sqlite-jdbc 3.15.1 org.springframework spring-oxm 5.2.0.RELEASE org.springframework spring-jdbc 5.2.0.RELEASE org.springframework.batch spring-batch-core 4.2.0.RELEASE
4. Spring Batch Config
Prvo što ćemo učiniti jest konfigurirati Spring Batch s XML-om:
Naravno, dostupna je i Java konfiguracija:
@Configuration @EnableBatchProcessing javna klasa SpringConfig {@Value ("org / springframework / batch / core / schema-drop-sqlite.sql") private Resource dropReopsitoryTables; @Value ("org / springframework / batch / core / schema-sqlite.sql") private Resource dataReopsitorySchema; @Bean public DataSource dataSource () {DriverManagerDataSource dataSource = novi DriverManagerDataSource (); dataSource.setDriverClassName ("org.sqlite.JDBC"); dataSource.setUrl ("jdbc: sqlite: repozitorij.sqlite"); vratiti dataSource; } @Bean public DataSourceInitializer dataSourceInitializer (DataSource dataSource) baca MalformedURLException {ResourceDatabasePopulator databasePopulator = new ResourceDatabasePopulator (); databasePopulator.addScript (dropReopsitoryTables); databasePopulator.addScript (dataReopsitorySchema); databasePopulator.setIgnoreFailedDrops (true); DataSourceInitializer inicijalizator = novi DataSourceInitializer (); inicijalizator.setDataSource (dataSource); Initializer.setDatabasePopulator (databasePopulator); povrat inicijalizatora; } private JobRepository getJobRepository () baca izuzetak {JobRepositoryFactoryBean factory = new JobRepositoryFactoryBean (); factory.setDataSource (dataSource ()); factory.setTransactionManager (getTransactionManager ()); factory.afterPropertiesSet (); return (JobRepository) factory.getObject (); } private PlatformTransactionManager getTransactionManager () {return new ResourcelessTransactionManager (); } javni JobLauncher getJobLauncher () baca izuzetak {SimpleJobLauncher jobLauncher = novi SimpleJobLauncher (); jobLauncher.setJobRepository (getJobRepository ()); jobLauncher.afterPropertiesSet (); povratak jobLauncher; }}
5. Spring Batch Job Config
Napišimo sada svoj opis posla za CSV to XML rad:
com.baeldung.spring_batch_intro.model.Transaction
I naravno, slična konfiguracija posla temeljena na Javi:
javna klasa SpringBatchConfig {@Autowired private JobBuilderFactory poslovi; @Automobilski privatni koraci StepBuilderFactory; @Value ("input / record.csv") privatni resurs inputCsv; @Value ("datoteka: xml / output.xml") private Resource outputXml; @Bean public ItemReader itemReader () baca UnexpectedInputException, ParseException {FlatFileItemReader reader = new FlatFileItemReader (); DelimitedLineTokenizer tokenizer = novi DelimitedLineTokenizer (); Niz [] tokeni = {"korisničko ime", "userid", "transactiondate", "iznos"}; tokenizer.setNames (tokeni); reader.setResource (inputCsv); DefaultLineMapper lineMapper = novi DefaultLineMapper (); lineMapper.setLineTokenizer (tokenizer); lineMapper.setFieldSetMapper (novi RecordFieldSetMapper ()); reader.setLineMapper (lineMapper); povratni čitač; } @Bean public ItemProcessor itemProcessor () {return new CustomItemProcessor (); } @Bean public ItemWriter itemWriter (Marshaller marshaller) baca MalformedURLException {StaxEventItemWriter itemWriter = new StaxEventItemWriter (); itemWriter.setMarshaller (marshaller); itemWriter.setRootTagName ("actionRecord "); itemWriter.setResource (outputXml); vratiti itemWriter; } @Bean public Marshaller marshaller () {Jaxb2Marshaller marshaller = novi Jaxb2Marshaller (); marshaller.setClassesToBeBound (nova klasa [] {Transaction.class}); maršal za povratak; } @Bean zaštićen korak 1 (čitač ItemReader, procesor ItemProcessor, program Writer ItemWriter) {return steps.get ("step1"). komad (10) .reader (čitač) .procesor (procesor) .writer (pisač) .build (); } @Bean (name = "firstBatchJob") javni posao posla (@Qualifier ("step1") Korak korak1) {return jobs.get ("firstBatchJob"). Start (step1) .build (); }}
U redu, sad kad imamo cijeli config, razstavimo ga i krenimo o njemu.
5.1. Čitajte podatke i stvarajte objekte pomoću Predmet za čitanje
Prvo smo konfigurirali cvsFileItemReader koji će očitavati podatke s zapis.csv i pretvoriti ga u Transakcija objekt:
@SuppressWarnings ("restrikcija") @XmlRootElement (name = "actionRecord ") javna klasa Transakcija {private String korisničko ime; private int userId; privatni LocalDateTime datum transakcije; privatni dvostruki iznos; / * getteri i postavljači za atribute * / @Override public String toString () {return "Transaction [username =" + username + ", userId =" + userId + ",actionDate =" +actionDate + ", amount =" + iznos + "]"; }}
Da bi to učinio - koristi prilagođeni mapper:
javna klasa RecordFieldSetMapper implementira FieldSetMapper {javna transakcija mapFieldSet (FieldSet fieldSet) baca BindException {DateTimeFormatter formatter = DateTimeFormatter.ofPattern ("d / M / yyy"); Transakcijska transakcija = nova Transaction (); action.setUsername (fieldSet.readString ("korisničko ime")); action.setUserId (fieldSet.readInt (1)); action.setAmount (fieldSet.readDouble (3)); String dateString = fieldSet.readString (2); action.setTransactionDate (LocalDate.parse (dateString, formatter) .atStartOfDay ()); povrat transakcije; }}
5.2. Obrada podataka pomoću PredmetProcesor
Stvorili smo vlastiti procesor predmeta, CustomItemProcessor. Ovo ne obrađuje ništa što je povezano s objektom transakcije - sve što radi je prosljeđivanje izvornog objekta koji dolazi iz čitača piscu:
javna klasa CustomItemProcessor implementira ItemProcessor {javni postupak transakcije (stavka transakcije) {return item; }}
5.3. Pisanje predmeta FS-u ItemWriter
Konačno, pohranit ćemo ovo transakcija u xml datoteku koja se nalazi na xml / output.xml:
5.4. Konfiguriranje batch zadatka
Dakle, sve što moramo učiniti je povezati točke s poslom - pomoću serija: posao sintaksa.
Napomena interval-predavanja - to je broj transakcija koje treba zadržati u memoriji prije predaje serije na itemWriter; zadržat će transakcije u memoriji do te točke (ili dok se ne nađe kraj ulaznih podataka):
5.5. Pokretanje skupnog posla
To je to - postavimo i pokrenimo sve:
aplikacija javne klase {public static void main (String [] args) {// Spring Java config AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext (); context.register (SpringConfig.class); context.register (SpringBatchConfig.class); context.refresh (); JobLauncher jobLauncher = (JobLauncher) context.getBean ("jobLauncher"); Posao posla = (Posao) context.getBean ("firstBatchJob"); System.out.println ("Pokretanje skupnog posla"); isprobajte {JobExecution Execution = jobLauncher.run (posao, novi JobParameters ()); System.out.println ("Status posla:" + izvršenje.getStatus ()); System.out.println ("Posao završen"); } catch (Iznimka e) {e.printStackTrace (); System.out.println ("Posao nije uspio"); }}}
6. Zaključak
Ovaj vam vodič daje osnovnu ideju kako raditi s Spring Batchom i kako ga koristiti u jednostavnoj upotrebi.
Pokazuje kako lako možete razviti svoj cjevovod za serijsku obradu i kako možete prilagoditi različite faze čitanja, obrade i pisanja.
The puna provedba ovog vodiča možete pronaći u projektu github - ovo je projekt zasnovan na Eclipseu, pa bi ga trebalo lako uvesti i pokrenuti kakav jest.