成人国产在线小视频_日韩寡妇人妻调教在线播放_色成人www永久在线观看_2018国产精品久久_亚洲欧美高清在线30p_亚洲少妇综合一区_黄色在线播放国产_亚洲另类技巧小说校园_国产主播xx日韩_a级毛片在线免费

資訊專欄INFORMATION COLUMN

Spring Boot QuickStart (5) - Spring Data JPA

sutaking / 3353人閱讀

摘要:關(guān)聯(lián)關(guān)系的關(guān)聯(lián)關(guān)系定義上,感覺并不是很靈活,姿勢也比較難找。如,定義在關(guān)聯(lián)關(guān)系上的參數(shù)可以設(shè)置級聯(lián)的相關(guān)東西。因?yàn)樾蛄谢瘯婕暗綄?shí)體類關(guān)聯(lián)對象的獲取,會觸發(fā)所有的關(guān)聯(lián)關(guān)系。

接(4) - Database 系列.

Java Persistence API,可以理解就是 Java 一個(gè)持久化標(biāo)準(zhǔn)或規(guī)范,Spring Data JPA 是對它的實(shí)現(xiàn)。并且提供多個(gè) JPA 廠商適配,如 Hibernate、Apache 的 OpenJpa、Eclipse的EclipseLink等。

spring-boot-starter-data-jpa 默認(rèn)使用的是 Hibernate 實(shí)現(xiàn)。

直接引入依賴:


    org.springframework.boot
    spring-boot-starter-data-jpa

開啟 SQL 調(diào)試:

spring.jpa.database=mysql
spring.jpa.show-sql=true

在 SpringBoot + Spring Data Jpa 中,不需要額外的配置什么,只需要編寫實(shí)體類(Entity)與數(shù)據(jù)訪問接口(Repository)就能開箱即用,Spring Data JPA 能基于接口中的方法規(guī)范命名自動的幫你生成實(shí)現(xiàn)(根據(jù)方法命名生成實(shí)現(xiàn),是不是很牛逼?)

Spring Data JPA 還默認(rèn)提供了幾個(gè)常用的Repository接口:

Repository: 僅僅是一個(gè)標(biāo)識,沒有任何方法,方便 Spring 自動掃描識別

CrudRepository: 繼承 Repository,實(shí)現(xiàn)了一組 CRUD 相關(guān)的方法

PagingAndSortingRepository: 繼承 CrudRepository,實(shí)現(xiàn)了一組分頁排序相關(guān)的方法

JpaRepository: 繼承 PagingAndSortingRepository,實(shí)現(xiàn)一組JPA規(guī)范相關(guān)的方法

推薦教程:Spring Data JPA實(shí)戰(zhàn)入門訓(xùn)練 https://course.tianmaying.com...

Entity 實(shí)體和 Respository 接口

根據(jù) user 表結(jié)構(gòu),我們定義好 User 實(shí)體類與 UserRespository 接口類。

這里,還自定義了一個(gè) @Query 接口,為了體驗(yàn)下自定義查詢。因?yàn)槭褂昧?lombok,所以實(shí)體類看起來很干凈。

User.java

@Data
@Entity
public class User {
    @Id
    @GeneratedValue
    private Long id;

    @Column(nullable = false)
    private String name;

    @Column(nullable = false, unique = true, updatable = false)
    @JsonProperty(value = "email")
    private String username;

    @Column(nullable = false)
    @JsonIgnore
    private String password;

    @Column(nullable = false)
    @JsonIgnore
    private String salt;

    @Column(nullable = true)
    private Date birthday;

    @Column(nullable = false)
    private String sex;

    @Column(nullable = true)
    @JsonFormat(pattern="yyyy-MM-dd HH:mm:ss")
    private Timestamp access;

    @Column(nullable = true)
    @JsonFormat(pattern="HH:mm:ss")
    private Time accessTime;

    @Column(nullable = false)
    private Integer state;

    @Column(nullable = false, insertable = false, updatable = false)
    @JsonFormat(pattern="yyyy-MM-dd HH:mm:ss")
    private Timestamp created;

    @Column(nullable = false, insertable = false, updatable = false)
    @JsonFormat(pattern="yyyy-MM-dd HH:mm:ss")
    private Timestamp updated;
}

@Data 是 lombok 的注解,自動生成Getter,Setter,toString,構(gòu)造函數(shù)等

@Entity 注解這是個(gè)實(shí)體類

@Table 注解表相關(guān),如別名等

@Id 注解主鍵,@GeneratedValue 表示自動生成

@DynamicUpdate,@DynamicInsert 注解可以動態(tài)的生成insert、update 語句,默認(rèn)會生成全部的update

@Column 標(biāo)識一些字段特性,字段別名,是否允許為空,是否唯一,是否進(jìn)行插入和更新(比如由MySQL自動維護(hù))

@Transient 標(biāo)識該字段并非數(shù)據(jù)庫字段映射

@JsonProperty 定義 Spring JSON 別名,@JsonIgnore 定義 JSON 時(shí)忽略該字段,@JsonFormat 定義 JSON 時(shí)進(jìn)行格式化操作

UserRepository.java

public interface UserRepository extends JpaRepository, UserCustomRepository {
    User findByUsername(String username);

    @Transactional
    @Modifying
    @Query("UPDATE User SET state = ?2 WHERE id = ?1 ")
    Integer saveState(Long id, Integer state);
}

@Transactional 用來標(biāo)識事務(wù),一般修改、刪除會用到, @Modifying 標(biāo)識這是個(gè)修改、刪除的Query

@Param 標(biāo)注在參數(shù)上,可用于標(biāo)識參數(shù)式綁定(不使用 ?1 而使用 :param)

好了,接下來我們就可以進(jìn)行單表的增、刪、改、查分頁排序操作了:

@Autowired
private UserRepository userRepository;
    
User user = new User();
userRepository.save(user); // 插入或保存
userRepository.saveFlush(user); // 保存并刷新
userRepository.exists(1) // 主鍵查詢是否存在
userRepository.findOne(1); // 主鍵查詢單條
userRepository.delete(1); // 主鍵刪除
userRepository.findByUsername("[email protected]"); // 查詢單條
userRepository.findAll(pageable); // 帶排序和分頁的查詢列表
userRepository.saveState(1, 0); // 更新單個(gè)字段

通常,exist(),delete()之類的方法,我們可能直接會操作 UserRepository,但是一般情況下,在 UserRepository 上面還會提供一個(gè) UserService 來進(jìn)行一系列的操作(比如數(shù)據(jù)校驗(yàn),邏輯判斷之類)

分頁和排序

PagingAndSortingRepository 和 JpaRepository 接口都具有分頁和排序的功能。因?yàn)楹笳呃^承自前者。比如下面這個(gè)方法:

Page findAll(Pageable var1);

Pageable 是Spring Data庫中定義的一個(gè)接口,該接口是所有分頁相關(guān)信息的一個(gè)抽象,通過該接口,我們可以得到和分頁相關(guān)所有信息(例如pageNumber、pageSize等),這樣,Jpa就能夠通過pageable參數(shù)來組裝一個(gè)帶分頁信息的SQL語句。

Page 類也是Spring Data提供的一個(gè)接口,該接口表示一部分?jǐn)?shù)據(jù)的集合以及其相關(guān)的下一部分?jǐn)?shù)據(jù)、數(shù)據(jù)總數(shù)等相關(guān)信息,通過該接口,我們可以得到數(shù)據(jù)的總體信息(數(shù)據(jù)總數(shù)、總頁數(shù)...)以及當(dāng)前數(shù)據(jù)的信息(當(dāng)前數(shù)據(jù)的集合、當(dāng)前頁數(shù)等)

Pageable只是一個(gè)抽象的接口??梢酝ㄟ^兩種途徑生成 Pageable 對象:

通過參數(shù),自己接收參數(shù),自己構(gòu)造生成 Pageable 對象

@RequestMapping(value = "", method = RequestMethod.GET)
public Object page(@RequestParam(name = "page", required = false) Integer page,
                  @RequestParam(name="size", required = false) Integer size) {
                  
   Sort sort = new Sort(Sort.Direction.DESC, "id");
   Pageable pageable = new PageRequest(page, size, sort);

   Page users = userRepository.findAll(pageable);

   return this.responseData(users);
}

這種方式你可以靈活的定義傳參。

通過 @PageableDefault 注解,會把參數(shù)自動注入成 Pageable 對象,默認(rèn)是三個(gè)參數(shù)值:

page=,第幾頁,從0開始,默認(rèn)為第0頁
size=,每一頁的大小
sort=,排序相關(guān)的信息,例如sort=firstname&sort=lastname,desc

@RequestMapping(value = "/search", method = RequestMethod.GET)
public Object search(@PageableDefault(size = 3, sort = "id", direction = Sort.Direction.DESC) Pageable pageable) {
   Page users = userRepository.findAll(pageable);

   return this.responseData(users);
}

看起來,這種方式更優(yōu)雅一些。

關(guān)聯(lián)關(guān)系

Spring Data JPA 的關(guān)聯(lián)關(guān)系定義上,感覺并不是很靈活,姿勢也比較難找。

視頻教程:http://www.jikexueyuan.com/co...

OneToOne 一對一

一對一的關(guān)系,拿 user,user_detail 來說,一般應(yīng)用起來,有以下幾種情況:

主鍵直接關(guān)聯(lián):user(id, xx);user_detail(id, xx) 或 user(id, xx),user_detail(user_id, xx) 其中 id, userid 為主鍵

主表含外鍵的關(guān)聯(lián):user(id, role_id, xx);role(id, xx) 。 其中 id 為自增主鍵

附表含外鍵的關(guān)聯(lián):user(id, xx);user_detail(id, user_id, xx) 。其中 id 為自增主鍵

主表含外鍵的關(guān)聯(lián):用戶->角色是一對一,而角色->用戶是多對一,而大部分情況,我們是通過 user 表來查詢某個(gè)角色的列表,而通過 role 來查詢某個(gè)角色的列表可能性很小。

附表表含外鍵的關(guān)聯(lián):其實(shí)和主表含外鍵的關(guān)聯(lián)完全相反,關(guān)聯(lián)的定義也是相反的。

主鍵ID關(guān)聯(lián)

單向關(guān)聯(lián),直接在 User 上定義 @OneToOne 與 @PrimaryKeyJoinColumn 即可完成

@Entity
@Data
public class User {
...
     @OneToOne
    @PrimaryKeyJoinColumn
    private UserDetail detail;
...
}

// 獲取的user,會包含detail屬性
User user = userRepository.findOne(userId);

雙向關(guān)聯(lián),除了要定義 User 的 @OneToOne,還需要定義 UserDetail 的 @OneToOne,用 mappedBy 指示 User 表的屬性名。

@Entity
@Data
public class UserDetail {
...
    @OneToOne(mappedBy = "detail")
    private User user;
...
}

出問題了,雙向關(guān)聯(lián),涉及到一個(gè)循環(huán)引用無限遞歸的問題,這個(gè)問題會發(fā)生在 toString、 JSON 轉(zhuǎn)換上??赡苓@只是個(gè)基礎(chǔ)問題,但對于我這個(gè)入門漢,抓瞎了好長時(shí)間。

解決辦法:

分別給User、UserDetail的關(guān)聯(lián)屬性加上:@JsonManagedReference、@JsonBackReference注解,解決 JSON 問題

給 UserDetail 實(shí)體類加上 @ToString(exclude = "user") 注解,解決 toString 的問題。

所以 UserDetail 最終造型應(yīng)該是這樣的:

@Entity
@Data
@ToString(exclude = "user")
public class UserDetail {
...

    @OneToOne(mappedBy = "detail")
    @JsonBackReference
    private User user;
}

// 現(xiàn)在可以進(jìn)行雙向查詢了
User user1 = userRepository.findOne(userId);
userDetail userdetail = userDetailRepository.findOne(userId);
User user2 = userdetail.getUser();

@PrimaryKeyJoinColumn 注解主要用于主鍵關(guān)聯(lián),注意實(shí)體屬性需要使用 @Id 的為主鍵,假如現(xiàn)在是:user(id, xx),user_detail(user_id, xx) 這種情況。則需要在 User 類上自定義它的屬性:

// User
@OneToOne
@PrimaryKeyJoinColumn(referencedColumnName = "user_id")
@JsonManagedReference
private UserDetail detail;
主表含外鍵

使用 @JoinColumn 注解即可完成,默認(rèn)使用的外鍵是(屬性名+下劃線+id)。關(guān)聯(lián)附表的主鍵 id。

可以通過 name=,referencedColumnName= 屬性重新自定義。

@Entity
@Data
public class User {
...
    // 屬性名為role,所以 @JoinColumn 會默認(rèn)外鍵是 role_id
    @OneToOne
    @JoinColumn
    @JsonManagedReference
    private Role role;
...
}

對于 user->role 的表關(guān)聯(lián)需求,我們不需要定義 OneToOne 反向關(guān)系,并且 role->user 本來是個(gè)一對多關(guān)系。

附表含外鍵

這種情況一般也會經(jīng)常出現(xiàn),它可以保證每個(gè)表都有一個(gè)自增主鍵的id

因?yàn)橥怄I在附表上,所以需要反過來,在 User 上定義 mapped。

如果是雙向關(guān)聯(lián),同樣需要加上忽略 toString(),JSON 的注解

@Entity
@Data
public class User {
...
    @OneToOne(mappedBy = "user")
    @JsonManagedReference
    private UserDetail detail;
...
}

@Entity
@Data
@ToString(exclude = "user")
public class UserDetail {
...
    @OneToOne
    @JoinColumn
    @JsonBackReference
    private User user;
...
}

User user1 = userRepository.findOne(userId);

// 給 UserDetail 定義一個(gè)獨(dú)立的 findByUserId 接口,這樣可以通過操作 UserDetail 反向獲取到 user 的數(shù)據(jù)
userDetail userdetail = userDetailRepository.findByUserId(userId);
User user2 = userdetail.getUser();

實(shí)際上,在上面的例子里面,考慮實(shí)際的場景,幾乎不需要定義 OneToOne 的反向關(guān)聯(lián)(偽需求),這樣就不用解決循環(huán)引用的問題了。這里只是意淫,不是嗎?

現(xiàn)在有個(gè)問題出現(xiàn)了,這種情況下(附表含外鍵),我如何定義 User->UserDetail 的單向關(guān)系呢?

關(guān)聯(lián)關(guān)系:一對多

接著上面的例子,Role -> User 實(shí)際上是個(gè)一對多的關(guān)系。但我們一般不會這么做。直接通過 User 就可以查詢嘛。所以這里演示另一個(gè)例子。

User->Order 是一對多,Order->User 是多對一,定義 Order 實(shí)體,注意@Table 注解,因?yàn)?order 是 MySQL 關(guān)鍵詞(此處中槍)

@Entity
@Data
@Table(name = "`order`")
public class Order {
    @Id
    @GeneratedValue
    private Long id;

    @Column(nullable = false)
    private String name;
}

然后在 User 中定義 @OneToMany,因?yàn)槭且粚Χ?,所以返回的是List,并且一般設(shè)置為 LAZY

@OneToMany(fetch = FetchType.LAZY)
@JoinColumn(name="user_id")
private List orders;

測試一下:

User user = userService.findOne(userId);
if (user != null) {
     // LAZY 的緣故,在 getOrders 才會觸發(fā)獲取操作
     List orders = user.getOrders();
     return this.responseData(orders);
}

再看看反向關(guān)聯(lián),也就是 @ManyToOne,稍作調(diào)整

User 實(shí)體類
@OneToMany(fetch = FetchType.LAZY, mappedBy = "user")
private List orders;

Order 實(shí)體類
@ManyToOne
private User user;

再測試一下:

Order order = orderRepository.findOne(orderId);
if (order != null) {
    User user = order.getUser();
    return this.responseData(user);
}
總結(jié)

想想實(shí)際場景,我們不太需要定義 User->Order 這種關(guān)聯(lián),因?yàn)橛脩艨赡苡泻芏嘤唵?,這個(gè)量是無可預(yù)測的。這時(shí)候這種關(guān)聯(lián)查詢,不能分頁,沒有意義(也可能是我姿勢不對)。

如果是有限的 XToMany 關(guān)聯(lián),是有意義的。比如配置管理。一個(gè)應(yīng)用擁有有限的多項(xiàng)配置?

Order->User 這種關(guān)聯(lián)是有意義的。拿到一個(gè) order_id 去反查用戶信息。

關(guān)聯(lián)關(guān)系:多對多

Order <-> Product 是多對多的關(guān)系,關(guān)聯(lián)表是 order_product,

Order 實(shí)體配置 @ManyToMany 屬性,不需要定義 OrderProduct 實(shí)體類,

// @JoinTable 實(shí)際可以省略,因?yàn)槭褂玫氖悄J(rèn)配置
@ManyToMany(fetch = FetchType.LAZY)
@JoinTable(
   name = "order_product",
   joinColumns = @JoinColumn(name = "order_id"),
   inverseJoinColumns = @JoinColumn(name = "product_id"))
@JsonManagedReference
private List products;

這樣就定義了單向關(guān)聯(lián),雙向關(guān)聯(lián)類似在 Product 實(shí)體配置:

@ManyToMany(mappedBy = "products", fetch = FetchType.LAZY)
@JsonIgnore
private List orders;

好了,這樣就OK了,實(shí)際按照上面的解釋,Product -> Order 是不太有意義的。

屬性參數(shù)

@OneToOne的屬性:

cascade 屬性表示級聯(lián)操作策略,有 CascadeType.ALL 等值。

fetch 屬性表示實(shí)體的加載方式,有 FetchType.LAZY 和 FetchType.EAGER 兩種取值,默認(rèn)值為 EAGER

拿OneToOne來說,如果是 EAGER 方式,那么會產(chǎn)生一個(gè)連接查詢,如果是 LAZY 方式,則是兩個(gè)查詢。并且第二個(gè)查詢會在用的時(shí)候才會觸發(fā)(僅僅.getXXX是不夠的)。

級聯(lián)

在未定義級聯(lián)的情況下,我們通常需要手動插入。

如 user(id, xx),user_detail(id, user_id, xx)

User user = new User();
userRepository.save(user);

UserDetail userDetail = new UserDetail();
userDetail.setUserId(user.getId());
userDetailRepository.save(userDetail);

定義在關(guān)聯(lián)關(guān)系上的 cascade 參數(shù)可以設(shè)置級聯(lián)的相關(guān)東西。

經(jīng)過一番研究,這部分暫時(shí)我還沒搞明白正確姿勢,玩不轉(zhuǎn)。

復(fù)雜的查詢 問題總結(jié) 數(shù)據(jù)庫默認(rèn)值字段,插入后不會自動返回默認(rèn)值。Entity not return default value after insert

一般關(guān)鍵表會記錄創(chuàng)建、更新時(shí)間,滿足基本審計(jì)需求,以前我喜歡使用 MySQL 默認(rèn)值特性,這樣應(yīng)用層就可以不用管他們了,如:

`created` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
`updated` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,

在實(shí)體中,我們要忽略插入和更新對他們的操作。

@Column(nullable = false, insertable = false, updatable = false)
@JsonFormat(pattern="yyyy-MM-dd HH:mm:ss")
private Timestamp created;

@Column(nullable = false, insertable = false, updatable = false)
@JsonFormat(pattern="yyyy-MM-dd HH:mm:ss")
private Timestamp updated;

看起來不錯(cuò)哦,工作正常,但是:

Spring Data Jpa 在 save() 完成以后,對于這種數(shù)據(jù)庫默認(rèn)插入的值,拿不到回寫的數(shù)據(jù)啊,無論我嘗試網(wǎng)上的方法使用 saveAndFlush() 還是手動 flush() 都是扯淡。

這個(gè)坑,我踩了好久,到現(xiàn)在,依然不知道這種情況怎么解決。

臨時(shí)解決方案:

拋棄數(shù)據(jù)庫默認(rèn)值特性,在實(shí)體類借助 @PrePersist、@PreUpdate 手動實(shí)現(xiàn),如果有多個(gè)表,遵循同一規(guī)范,可以搞個(gè)基類,雖然不太爽,但是能正常工作。

@MappedSuperclass
@Getter
@Setter
public class BaseEntity {
    @Column(nullable = false, updatable = false)
    @JsonFormat(pattern="yyyy-MM-dd HH:mm:ss")
    private Timestamp created;

    @Column(nullable = false)
    @JsonFormat(pattern="yyyy-MM-dd HH:mm:ss")
    private Timestamp updated;

    @PrePersist
    public void basePrePersist() {
       long timestamp = new java.util.Date().getTime();
       created = new Timestamp(timestamp);
       updated = new Timestamp(timestamp);
    }
    
    @PreUpdate
    public void basePreUpdate() {
       updated = new Timestamp(new java.util.Date().getTime());
    }
}
OneToOne 關(guān)聯(lián)關(guān)系,指定 FetchType.LAZY,JSON 時(shí)會出錯(cuò),得不到數(shù)據(jù)

原因大概是,JSON序列化的時(shí)候,數(shù)據(jù)還沒有fetch到,出錯(cuò)信息如下:

Could not write JSON: No serializer found for class org.hibernate.proxy.pojo.javassist.JavassistLazyInitializer and no properties discovered to create BeanSerializer

解決方法:

application.properties 增加配置項(xiàng):

spring.jackson.serialization.fail-on-empty-beans=false

然而你會發(fā)現(xiàn)最終的 JSON 多出來兩個(gè)key,分別是handler、hibernateLazyInitializer

所以還需要在實(shí)體類上增加注解:

@JsonIgnoreProperties({"hibernateLazyInitializer", "handler"})

搞定!

關(guān)于循環(huán)引用和 Lazy Fetch

接上個(gè)問題,這里要思考一個(gè)問題場景:

Lazy Fetch 在 JSON 序列化實(shí)體類時(shí)失效

我們定義了一個(gè) User 實(shí)體類,這個(gè)實(shí)體類有幾個(gè)關(guān)聯(lián),比如 OneToOne和 OneToMany,并且設(shè)置了Lazy,我們執(zhí)行了 findOne 查詢并返回結(jié)果,在 RestController 的時(shí)候,會默認(rèn)執(zhí)行 Jackson 的序列化JSON 操作。

因?yàn)樾蛄谢瘯婕暗綄?shí)體類關(guān)聯(lián)對象的獲取,會觸發(fā)所有的關(guān)聯(lián)關(guān)系。生成一大堆的查詢 SQL, 這樣 LAZY 就失去意義了啊,比如我只想要 User 單表的基本信息怎么辦?

stackoverflow 可以搜到了好多類似問題,我目前還沒找到正確的姿勢。

可以想象的是,不應(yīng)當(dāng)將實(shí)體類直接返回給客戶端,應(yīng)該再定義一個(gè)返回?cái)?shù)據(jù)的DTO,將實(shí)體類的數(shù)據(jù)復(fù)制到DTO,然后返回并JSON。然而這樣好蛋疼,隨便一個(gè)項(xiàng)目你至少需要定義實(shí)體類,輸入?yún)?shù)的DTO,輸出參數(shù)的DTO。

問題暫放這里。

循環(huán)引用

我們雖然通過 @JsonBackReference 和 JsonManagedReference 來解決。但是有時(shí)候,對于兩個(gè) OneToOne 實(shí)體,我們都需要 JSON 序列化怎么辦?如 User 與 UserDetail

另一個(gè)辦法,給實(shí)體類加上 @JsonIdentityInfo:

@JsonIdentityInfo(generator=ObjectIdGenerators.PropertyGenerator.class, property="id")

這樣好處是顯而易見的,只需要在實(shí)體類上注解一下即可。

猜測原理是引入了id,檢測了主鍵是否一致,決定是否引用下去。如 User->UserDetail->User。

所以他還會多一次查詢,并且關(guān)聯(lián)數(shù)據(jù)上會多一個(gè)關(guān)聯(lián)關(guān)系的 id 的字段。

文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請注明本文地址:http://systransis.cn/yun/67271.html

相關(guān)文章

  • Spring Boot QuickStart (1)

    摘要:開始介紹簡化了基于的應(yīng)用開發(fā),你只需要就能創(chuàng)建一個(gè)獨(dú)立的,產(chǎn)品級別的應(yīng)用。該包含很多搭建,快速運(yùn)行項(xiàng)目所需的依賴,并提供一致的,可管理傳遞性的依賴集。日志級別通過標(biāo)識開啟控制臺級別日志記錄,也可以在中指定日志級別配置示例 開始 介紹 Spring Boot 簡化了基于 Spring 的應(yīng)用開發(fā),你只需要 run 就能創(chuàng)建一個(gè)獨(dú)立的,產(chǎn)品級別的 Spring 應(yīng)用。 Spring 平臺...

    klinson 評論0 收藏0
  • Spring Boot QuickStart (4) - Database

    摘要:本文只是引子,后續(xù)更新到獨(dú)立章節(jié)。尤其是,這也是現(xiàn)在號稱流行的組合。幸虧現(xiàn)在看起來不主流了。增刪改查多條件組合查詢分頁,排序等多表關(guān)聯(lián)。而每個(gè)類寫上構(gòu)造函數(shù),,實(shí)在是蛋疼。 本文只是引子,后續(xù)更新到獨(dú)立章節(jié)。 環(huán)境:Spring Boot 1.5.4 到了操作數(shù)據(jù)庫的環(huán)節(jié),以 MySQL 為基準(zhǔn),體驗(yàn)一下數(shù)據(jù)庫的相關(guān)操作,先讓我糾結(jié)一下,至少有以下四種姿勢。 JDBC。原生的 JD...

    FrozenMap 評論0 收藏0
  • Spring Boot [組件學(xué)習(xí)-Spring Data JPA]

    摘要:與的關(guān)系是什么是官方提出的持久化規(guī)范。它為開發(fā)人員提供了一種對象關(guān)聯(lián)映射工具來管理應(yīng)用中的關(guān)系數(shù)據(jù)。他的出現(xiàn)主要是為了簡化現(xiàn)有的持久化開發(fā)工作和整合技術(shù),結(jié)束現(xiàn)在,,等框架各自為營的局面。定義了在對數(shù)據(jù)庫中的對象處理查詢和事務(wù)運(yùn)行時(shí)的的。 導(dǎo)讀: 在上篇文章中對Spring MVC常用的一些注解做了簡要的說明,在這篇文章中主要對Spring Data JPA 做一個(gè)簡要的說明,并附有一...

    andong777 評論0 收藏0
  • 貓頭鷹的深夜翻譯:為什么要使用Spring Boot?

    摘要:初次使用的人往往會困惑,不知道該使用哪種方法。目前來說,團(tuán)隊(duì)推薦使用基于的方法來提供更高的靈活性。配置,從而在應(yīng)用啟動時(shí)執(zhí)行腳本來初始化數(shù)據(jù)庫。目前為止我們沒有任何消息需要配置,所以只在文件夾中創(chuàng)建一個(gè)空的文件。將配置為,它包含的上下文。 前言 spring是一個(gè)用于創(chuàng)建web和企業(yè)應(yīng)用的一個(gè)很流行的框架。和別的只關(guān)注于一點(diǎn)的框架不同,Spring框架通過投資并組合項(xiàng)目提供了大量的功能...

    Jaden 評論0 收藏0
  • 《 Kotlin + Spring Boot : 下一代 Java 服務(wù)端開發(fā) 》

    摘要:下一代服務(wù)端開發(fā)下一代服務(wù)端開發(fā)第部門快速開始第章快速開始環(huán)境準(zhǔn)備,,快速上手實(shí)現(xiàn)一個(gè)第章企業(yè)級服務(wù)開發(fā)從到語言的缺點(diǎn)發(fā)展歷程的缺點(diǎn)為什么是產(chǎn)生的背景解決了哪些問題為什么是的發(fā)展歷程容器的配置地獄是什么從到下一代企業(yè)級服務(wù)開發(fā)在移動開發(fā)領(lǐng)域 《 Kotlin + Spring Boot : 下一代 Java 服務(wù)端開發(fā) 》 Kotlin + Spring Boot : 下一代 Java...

    springDevBird 評論0 收藏0

發(fā)表評論

0條評論

最新活動
閱讀需要支付1元查看
<