Skip to content

Latest commit

History

168 Commits

Folders and files

NameName
Last commit message
Last commit date

Repository files navigation

Anima

Anima allows you to query database like SQL and Stream. a simple DSL syntax, supports multiple databases, integrates well with Java8, supports multiple relational mappings, and is a database manipulation tool.

Document

Travis BuildCodacy BadgecodecovLicenseTwitter URL

Feature

  • Simple DSL
  • H2、MySQL、SQLite、PostgreSQL、Oracle、SqlServer
  • Paging support
  • Flexible configuration
  • Connection pool support
  • Support LocalDateLocalDateTime
  • Support lambda expression
  • Relationship (hasOnehasManybelongsTo)
  • SQL performance statistics
  • Based Java8

Usage

Latest snapshot version

If you want to prioritize new features or some BUG fixes you can use it, you need to specify the snapshot repository in pom.xml

<repository>
<id>snapshots-repo</id>
<url>https://oss.sonatype.org/content/repositories/snapshots</url>
<releases>
<enabled>false</enabled>
</releases>
<snapshots>
<enabled>true</enabled>
</snapshots>
</repository>
<dependency>
<groupId>com.hellokaton</groupId>
<artifactId>anima</artifactId>
<version>0.3.1</version>
</dependency>

Here's the RELEASE version.

As Gradle

compile'com.hellokaton:anima:0.3.1'

As Maven

<dependency>
<groupId>com.hellokaton</groupId>
<artifactId>anima</artifactId>
<version>0.3.1</version>
</dependency>

📒 Although Anima can also be used by adding a jar package, we do not recommend doing this.

Examples

Open Connection

// MySQLAnima.open("jdbc:mysql://127.0.0.1:3306/demo", "root", "123456");
// SQLiteAnima.open("jdbc:sqlite:./demo.db");
// H2Anima.open("jdbc:h2:file:~/demo;FILE_LOCK=FS;PAGE_SIZE=1024;CACHE_SIZE=8192", "sa", "");
// DataSourceDruidDataSourcedataSource = newDruidDataSource();
dataSource.setDriverClassName("com.mysql.jdbc.Driver");
dataSource.setUrl(blade.environment().getOrNull("jdbc.url"));
dataSource.setUsername(blade.environment().getOrNull("jdbc.username"));
dataSource.setPassword(blade.environment().getOrNull("jdbc.password"));
Anima.open(dataSource);

📕 This operation only needs one time

publicclassUserextendsModel {
privateIntegerid;
privateStringuserName;
privateIntegerage;
publicUser() {
}
publicUser(StringuserName, Integerage) {
this.userName = userName;
this.age = age;
}
}

Table Structure

CREATETABLE `users` (
`id` IDENTITY PRIMARY KEY,
`user_name`varchar(50) NOT NULL,
`age`int(11)
)

Query

longcount = select().from(User.class).count();
// SELECT COUNT(*) FROM userslongcount = select().from(User.class).where("age > ?", 15).isNotNull("user_name").count();
// SELECT COUNT(*) FROM users WHERE age > ? AND user_name IS NOT NULLUseruser = select().from(User.class).byId(2);
// SELECT * FROM users WHERE id = ?List<User> users = select().from(User.class).byIds(1, 2, 3);
// SELECT * FROM users WHERE id IN (?, ?, ?)Stringname = select().bySQL(String.class, "select user_name from users limit 1").one();
List<String> names = select().bySQL(String.class, "select user_name from users limit ?", 3);
List<User> users = select().from(User.class).all();
// SELECT * FROM usersList<User> users = select().from(User.class).like("user_name", "%o%").all();
// SELECT * FROM users WHERE user_name LIKE ?

Limit

List<User> users = select().from(User.class).order("id desc").limit(5);
// SELECT * FROM users ORDER BY id desc

Paging

Page<User> userPage = select().from(User.class).order("id desc").page(1, 3);
// SELECT * FROM users ORDER BY id desc LIMIT ?, ?

Map

select().from(User.class).map(User::getUserName).limit(3).collect(Collectors.toList());

Filter

select().from(User.class).filter(u -> u.getAge() > 10).collect(Collectors.toList());

Lambda

Useruser = select().from(User.class).where(User::getUserName).eq("jack").one();
// SELECT * FROM users WHERE user_name = ?
List<User> user = select().from(User.class)
.where(User::getUserName).notNull()
.and(User::getAge).gt(10)
.all();
// SELECT * FROM users WHERE user_name IS NOT NULL AND age > ?
select().from(User.class).order(User::getId, OrderBy.DESC).order(User::getAge, OrderBy.ASC).all();
// SELECT * FROM users ORDER BY id DESC, age ASC

Join

@Table(name = "order_info")
@DatapublicclassOrderInfoextendsModel {
privateLongid;
privateIntegeruid;
@Column(name = "productname")
privateStringproductName;
privateLocalDateTimecreateTime;
@IgnoreprivateUseruser;
@IgnoreprivateAddressaddress;
}
// HasOneOrderInfoorderInfo = select().from(OrderInfo.class)
.join(
Joins.with(Address.class).as(OrderInfo::getAddress)
.on(OrderInfo::getId, Address::getOrderId)
).byId(3);
orderInfo = select().from(OrderInfo.class)
.join(
Joins.with(Address.class).as(OrderInfo::getAddress)
.on(OrderInfo::getId, Address::getOrderId)
)
.join(
Joins.with(User.class).as(OrderInfo::getUser)
.on(OrderInfo::getUid, User::getId)
).byId(3);
// ManyToOneorderInfo = select().from(OrderInfo.class)
.join(
Joins.with(User.class).as(OrderInfo::getUser)
.on(OrderInfo::getUid, User::getId)
).byId(3);
// OneToManyUserDtouserDto = select().from(UserDto.class).join(
Joins.with(OrderInfo.class).as(UserDto::getOrders)
.on(UserDto::getId, OrderInfo::getUid)
).byId(1);

Insert

Integerid = newUser("biezhi", 100).save().asInt();
// INSERT INTO users(id,user_name,age) VALUES (?,?,?)

or

Anima.save(newUser("jack", 100));

Batch Save

List<User> users = newArrayList<>();
users.add(newUser("user1", 10));
users.add(newUser("user2", 11));
users.add(newUser("user3", 12));
Anima.saveBatch(users);

📘 This operation will begin a transaction and rollback when there is a transaction that is unsuccessful.

Update

intresult = update().from(User.class).set("user_name", newName).where("id", 1).execute();
// UPDATE users SET username = ? WHERE id = ?

or

intresult = update().from(User.class).set("user_name", newName).where("id", 1).execute();
// UPDATE users SET user_name = ? WHERE id = ?

or

Useruser = newUser();
user.setId(1);
user.setUserName("jack");
user.update();
// UPDATE users SET user_name = ? WHERE id = ?
update().from(User.class).set(User::getUserName, "base64").updateById(2);
update().from(User.class).set(User::getUserName, "base64").where(User::getId).eq(2).execute();

Delete

intresult = delete().from(User.class).where("id", 1).execute();
// DELETE FROM users WHERE id = ?

or

Useruser = newUser();
user.setAge(15);
user.setUserName("jack");
user.delete();
// DELETE FROM users WHERE user_name = ? and age = ?
delete().from(User.class).where(User::getId).deleteById(3);
delete().from(User.class).where(User::getId).eq(1).execute();
delete().from(User.class).where(User::getAge).lte(20).execute();

Transaction

Anima.atomic(() -> {
inta = 1 / 0;
newUser("apple", 666).save();
}).catchException(e -> Assert.assertEquals(ArithmeticException.class, e.getClass()));

📗 Anima uses the atomic method to complete a transaction. normally, the code will not throw an exception. when a RuntimeException is caught, the transaction will be rollback.

Test Code

See here

License

Apache2

About

Minimal database operation library.

Topics

Resources

Stars

230 stars

Watchers

12 watching

Forks

Releases

Packages

Used by

Contributors

Languages